Argonne National Laboratory

Experimental Physics and
Industrial Control System

2002  2003  2004  2005  <20062007  2008  2009  2010  2011  2012  2013  2014  2015  2016  2017  2018  2019  2020  Index 2002  2003  2004  2005  <20062007  2008  2009  2010  2011  2012  2013  2014  2015  2016  2017  2018  2019  2020 
<== Date ==> <== Thread ==>

Subject: RE: alarm hook
From: "Liyu, Andrei" <liyua@ornl.gov>
To: Andrew Johnson <anj@aps.anl.gov>, Matthias Clausen <Matthias.Clausen@desy.de>, Geoff Savage <savage@fnal.gov>, EPICS core-talk <core-talk@aps.anl.gov>
Cc: "Zhukov, Alexander P." <zhukovap@ornl.gov>
Date: Mon, 19 Jun 2006 14:03:49 -0400
Hi Andrew,

First of all, I agree with place [monitor() -> recGblResetAlarms()]. 
[My first idea [process() -> checkAlarms() -> recGblSetSevr()] wasn't
correct. It is fine from name (Alarm connects to Alarm) but it doesn't
work when Alarm severity changes to No_Alarm status. :( ]

At second, I did in another way.
1. I put my code in the beginning of the function.

unsigned short epicsShareAPI recGblResetAlarms(void *precord)
{
    struct dbCommon *pdbc = precord;
    unsigned short mask,stat,sevr,nsta,nsev,ackt,acks;
    unsigned short stat_mask=0;

	/* Send alarm message */
	char AcMessage[ 200];
	if( pdbc->nsev != pdbc->sevr){
		sprintf( AcMessage,
"PVNAME=%s&SEVERITY=%d&STATUS=%d&TIMESTAMP=%ld.%ld", 
				pdbc->name, pdbc->nsev, pdbc->nsta,
pdbc->time.secPastEpoch, pdbc->time.nsec);
		vFSendMessageToAlarmService( AcMessage);
	}

So I send "PVNAME=%s&SEVERITY=%d&STATUS=%d&TIMESTAMP=%ld.%ld" to alarm
thread (or service) in IOC.

Please, look that I didn't care about 
- Alarm Status changes. I would like to decrease quantity of Alarm
messages!
- about Value. That is not very useful. I suppose that operator is more
interested in values of HIGH, HIHI and other fields. But it is difficult
to provide because it will become sensitive to record type.
I send Alarm status. But I am not sure that it is necessary information
too.

3. I added code to the end of logClient.h and logClient.c and attached
these. I did circular buffer. It should be 2 power x (2, 4, 8, ..., or
1024, 2048, ...). Any record in its thread puts Message in the buffer if
there is place in the buffer. In another (no place) case program
increases global counter. Then record sends Alarm EpicsEvent.
	Alarm thread has small priority. Basically, it sleeps all time.
When it gets Event (or timeout - I haven't explanation why I did that)
and has CPU time Alarm service starts to send ALL messages from the
buffer to Alarm server. Please, look that Alarm service adds ID to each
message. So if alarm subsystem would miss a message as minimum alarm
subsystem has chance to know that.

4. Alarm server is another computer (or another task/process as
minimum). Sasha Zhukov wrote that. I am sure he will provide additional
information if you will need that. 

5. Our subsystem works with Windows IOC, Linux Alarm server and client.
We didn't finish some tails and didn't test very well. We hoped it is
enough to do a standard with Alarm and we can continue if our way was
chose.


At last, I suggest do generic Alarm subsystem definitions/stardards. For
example, real distributed control system can consist from Epics IOCs and
another servers (like, OPC servers). But Alarm subsystem should be once.
Maybe it will good to do 2 sets of definitions. One - for global view,
another - for Epics.

Thanks, Andrei Liyu.



-----Original Message-----
From: Andrew Johnson [mailto:anj@aps.anl.gov] 
Sent: Monday, June 19, 2006 11:36 AM
To: Matthias Clausen; Geoff Savage; EPICS core-talk
Subject: Re: alarm hook

Hi Matthias,

Matthias Clausen wrote:
> 
> in preparation for my meeting with Geoff at Fermilab I wand to send
you 
> the proposed hook into base which Bernd Schoeneburg and Bob already 
> 'somehow' agreed on:
> 
> Here's Berns mail to Bob:
> 
>>
>> recGblResetAlarms is called in monitor() which is called in the end
of 
>> record processing just before recGblFwdLink and after 
>> recGblGetTimeStamp. After calling recGblResetAlarms in monitor() the 
>> value changes are checked (not interesting for us). recGblResetAlarms

>> checks for alarm changes and returns the fist approach of the monitor

>> mask, which is later used for postEvents. postEvents can be called 
>> from anywhere like device support, snl, subroutines, 'homebrew' 
>> records etc. I think recGblResetAlarms is called in the monitor 
>> function of records only. So I think it is the perfect place. Please 
>> check it and correct me if I am wrong.
>>
>> The code could look like this (the end of recGblResetAlarms):
>>
>>     if(sevr!=nsev || stat!=nsta) {
>>
>> ++:    logAlarm (pdbc, sevr, stat);
>> ++:    /* nsev and nsta are in pdbc->sevr and pdbc->stat */
>>
>>         ackt = pdbc->ackt; acks = pdbc->acks;
>>         if(!ackt || nsev>=acks){
>>             pdbc->acks=nsev;
>>             db_post_events(pdbc,&pdbc->acks,DBE_VALUE);
>>         }
>>     }
>>     return(mask);
>> }
> 
> My question:
> Do you also agree with approach?

I agree with the location and arguments of the call, which I believe are

the same as Fermilab have been using.

> And - what would be implemented in base for logAlarm ()?
> This could be an empty function which just returns - or it could be
the 
> 'real' thing where you'll have to check whether alarm logging should
be 
> used at all.
> The empty function could be replaced/ overloaded by the 'real'
function 
> if you want to use putAlarm.

I think we just need a global pointer for the routine which will be 
called if it's not NULL, so your code just sets it to hook in.  Here's 
my proposed patch:


Index: recGbl.h
===================================================================
RCS file: /net/phoebus/epicsmgr/cvsroot/epics/base/src/db/recGbl.h,v
retrieving revision 1.9
diff -u -b -r1.9 recGbl.h
--- recGbl.h    12 Feb 2003 21:22:23 -0000      1.9
+++ recGbl.h    19 Jun 2006 15:25:16 -0000
@@ -30,13 +30,23 @@
       : FALSE\
  )

+/* Structures needed for args */

-/* Global Record Support Routines*/
  struct link;
  struct dbAddr;
  struct dbr_alDouble;
  struct dbr_ctrlDouble;
  struct dbr_grDouble;
+struct dbCommon;
+
+/* Hook Routine */
+
+typedef void (*RECGBL_ALARM_HOOK_ROUTINE)(struct dbCommon *prec,
+    unsigned short sevr, unsigned short stat);
+extern RECGBL_ALARM_HOOK_ROUTINE recGblAlarmHook;
+
+/* Global Record Support Routines */
+
  epicsShareFunc void epicsShareAPI recGblDbaddrError(
      long status, struct dbAddr *paddr, char *pcaller_name);
  epicsShareFunc void epicsShareAPI recGblRecordError(
Index: recGbl.c
===================================================================
RCS file: /net/phoebus/epicsmgr/cvsroot/epics/base/src/db/recGbl.c,v
retrieving revision 1.60.2.2
diff -u -b -r1.60.2.2 recGbl.c
--- recGbl.c    4 Nov 2004 19:21:08 -0000       1.60.2.2
+++ recGbl.c    19 Jun 2006 15:25:16 -0000
@@ -42,6 +42,10 @@
  #include "recGbl.h"


+/* Hook Routines */
+
+RECGBL_ALARM_HOOK_ROUTINE recGblAlarmHook = NULL;
+
  /* local routines */
  static void getMaxRangeValues();

@@ -239,6 +243,7 @@
      if(stat_mask)
          db_post_events(pdbc,&pdbc->stat,stat_mask);
      if(sevr!=nsev || stat!=nsta) {
+       if (recGblAlarmHook) (*recGblAlarmHook)(pdbc, sevr, stat);
         ackt = pdbc->ackt; acks = pdbc->acks;
         if(!ackt || nsev>=acks){
             pdbc->acks=nsev;


If there is general agreement between DESY and FNAL about this, I'll 
commit the change which will then appear in R3-14-9.

- Andrew
-- 
Not everything that can be counted counts,
and not everything that counts can be counted.
   -- Albert Einstein

Attachment: logClient.h
Description: logClient.h

Attachment: logClient.c
Description: logClient.c


Replies:
Re: alarm hook Andrew Johnson

Navigate by Date:
Prev: Re: alarm hook Andrew Johnson
Next: Re: alarm hook Andrew Johnson
Index: 2002  2003  2004  2005  <20062007  2008  2009  2010  2011  2012  2013  2014  2015  2016  2017  2018  2019  2020 
Navigate by Thread:
Prev: Re: alarm hook Andrew Johnson
Next: Re: alarm hook Andrew Johnson
Index: 2002  2003  2004  2005  <20062007  2008  2009  2010  2011  2012  2013  2014  2015  2016  2017  2018  2019  2020 
ANJ, 02 Feb 2012 Valid HTML 4.01! · Home · News · About · Base · Modules · Extensions · Distributions · Download ·
· Search · EPICS V4 · IRMIS · Talk · Bugs · Documents · Links · Licensing ·