This is Unofficial EPICS BASE Doxygen Site
pdbgroup.cpp File Reference
#include <stdio.h>
#include <epicsStdio.h>
#include <epicsAtomic.h>
#include <dbAccess.h>
#include <dbChannel.h>
#include <dbStaticLib.h>
#include <pv/pvAccess.h>
#include <pv/configuration.h>
#include <pv/epicsException.h>
#include "helper.h"
#include "pdbgroup.h"
#include "pdb.h"
+ Include dependency graph for pdbgroup.cpp:

Go to the source code of this file.

Typedefs

typedef epicsGuard< epicsMutex > Guard
 

Functions

void pdb_group_event (void *user_arg, struct dbChannel *chan, int eventsRemaining, struct db_field_log *pfl)
 

Typedef Documentation

typedef epicsGuard<epicsMutex> Guard

Definition at line 28 of file pdbgroup.cpp.

Function Documentation

void pdb_group_event ( void *  user_arg,
struct dbChannel *  chan,
int  eventsRemaining,
struct db_field_log *  pfl 
)

Definition at line 30 of file pdbgroup.cpp.

32 {
33  DBEvent *evt=(DBEvent*)user_arg;
34  unsigned idx = evt->index;
35  try{
36  PDBGroupPV::shared_pointer self(std::tr1::static_pointer_cast<PDBGroupPV>(((PDBGroupPV*)evt->self)->shared_from_this()));
37  PDBGroupPV::Info& info = self->members[idx];
38 
40  {
41 
42  Guard G(self->lock);
43 
44  self->scratch.clear();
45  if(evt->dbe_mask&DBE_PROPERTY || !self->monatomic)
46  {
47  DBScanLocker L(dbChannelRecord(info.chan));
48  self->members[idx].pvif->put(self->scratch, evt->dbe_mask, pfl);
49 
50  } else {
51  // we ignore 'pfl' (and the dbEvent queue) when collecting an atomic snapshot
52 
53  DBManyLocker L(info.locker); // lock only those records in the triggers list
54  FOREACH(PDBGroupPV::Info::triggers_t::const_iterator, it, end, info.triggers)
55  {
56  size_t i = *it;
57  // go get a consistent snapshot we must ignore the db_field_log which came through the dbEvent buffer
58  LocalFL FL(NULL, self->members[i].chan); // create a read fl if needed
59  self->members[i].pvif->put(self->scratch, evt->dbe_mask, FL.pfl);
60  }
61  }
62 
63  if(!(evt->dbe_mask&DBE_PROPERTY)) {
64  if(!info.had_initial_VALUE) {
65  info.had_initial_VALUE = true;
66  assert(self->initial_waits>0);
67  self->initial_waits--;
68  }
69  } else {
70  if(!info.had_initial_PROPERTY) {
71  info.had_initial_PROPERTY = true;
72  assert(self->initial_waits>0);
73  self->initial_waits--;
74  }
75  }
76 
77  if(self->initial_waits==0) {
78  self->interested_iterating = true;
79 
80  FOREACH(PDBGroupPV::interested_t::const_iterator, it, end, self->interested) {
81  PDBGroupMonitor& mon = **it;
82  mon.post(G, self->scratch); // G unlocked
83  }
84 
85  {
86  Guard G(self->lock);
87 
88  assert(self->interested_iterating);
89 
90  while(!self->interested_add.empty()) {
91  PDBGroupPV::interested_t::iterator first(self->interested_add.begin());
92  self->interested.insert(*first);
93  self->interested_add.erase(first);
94  }
95 
96  temp.swap(self->interested_remove);
97  for(PDBGroupPV::interested_remove_t::iterator it(temp.begin()),
98  end(temp.end()); it != end; ++it)
99  {
100  self->interested.erase(static_cast<PDBGroupMonitor*>(it->get()));
101  }
102 
103  self->interested_iterating = false;
104 
105  self->finalizeMonitor();
106  }
107  }
108  }
109 
110  }catch(std::tr1::bad_weak_ptr&){
111  /* We are racing destruction of the PDBGroupPV, but things are ok.
112  * The destructor is running, but has not completed db_cancel_event()
113  * so storage is still valid.
114  * Just do nothing
115  */
116  }catch(std::exception& e){
117  std::cerr<<"Unhandled exception in pdb_group_event(): "<<e.what()<<"\n"
118  <<SHOW_EXCEPTION(e)<<"\n";
119  }
120 }
DBManyLock locker
Definition: pdbgroup.h:96
void * self
Definition: pvif.h:218
#define assert(exp)
Declare that a condition should be true.
Definition: epicsAssert.h:70
#define FOREACH(ITERTYPE, IT, END, C)
Definition: helper.h:6
int i
Definition: scan.c:967
shared_ptr< T > static_pointer_cast(shared_ptr< U > const &r) BOOST_NOEXCEPT
Definition: shared_ptr.hpp:788
std::set< BaseMonitor::shared_pointer > interested_remove_t
Definition: pdbgroup.h:114
#define NULL
Definition: catime.c:38
#define SHOW_EXCEPTION(EI)
bool had_initial_PROPERTY
Definition: pdbgroup.h:99
Definition: pvif.h:241
#define DBE_PROPERTY
Definition: caeventmask.h:42
unsigned dbe_mask
Definition: pvif.h:217
bool post(guard_t &guard, const epics::pvData::BitSet &updated, no_overflow)
post update if queue not full, if full return false w/o overflow
Definition: pvahelper.h:136
unsigned index
Definition: pvif.h:219
Definition: pvif.h:214
triggers_t triggers
Definition: pdbgroup.h:95
bool had_initial_VALUE
Definition: pdbgroup.h:99