The idea of drivers being able to provide more specific values for STAT and SEVR is attractive, but I'm not sure the mechanism you've proposed is the best way to do it.
- It introduces a large difference in the manner in which I/O Intr scanned records and non I/O Intr scanned records set STAT and SEVR. Non I/O Intr scanned records set the alarm state based on the status return from the interface methods, typically pInterface->write() and pInterface->read(). All existing drivers return one of the asynStatus enum values, and device support always sets STAT=READ_ALARM or WRITE_ALARM, and SEVR=INVALID_ALARM. For those functions we cannot pack STAT and SEVR into the status return, because it is not backwards compatible. This would mean that device support would handle alarms very differently depending on how the record is scanned.
- The auxStatus field is defined to be an asynStatus, which is an enum defined as follows:
typedef enum {
asynSuccess,asynTimeout,asynOverflow,asynError,asynDisconnected,asynDisabled
}asynStatus;
Setting auxStatus to something other than these enums (i.e. packing STAT and SEVR in it) is not clean programming.
I can think of two solutions:
Solution 1) Just use the existing asynStatus enums to set the alarm condition. Allowed values of alarmCondition from alarm.h are:
typedef enum {
epicsAlarmNone = NO_ALARM,
epicsAlarmRead,
epicsAlarmWrite,
epicsAlarmHiHi,
epicsAlarmHigh,
epicsAlarmLoLo,
epicsAlarmLow,
epicsAlarmState,
epicsAlarmCos,
epicsAlarmComm,
epicsAlarmTimeout,
epicsAlarmHwLimit,
epicsAlarmCalc,
epicsAlarmScan,
epicsAlarmLink,
epicsAlarmSoft,
epicsAlarmBadSub,
epicsAlarmUDF,
epicsAlarmDisable,
epicsAlarmSimm,
epicsAlarmReadAccess,
epicsAlarmWriteAccess,
ALARM_NSTATUS
} epicsAlarmCondition;
These could map to the asynStatus enum values as follows:
asynSuccess = epicsAlarmNone
asynTimeout = epicsAlarmTimeout
asynOverflow = epicsAlarmHiHi or epicsAlaramHWLimit ??
asynError = epicsAlarmRead or epicsAlarmWrite (this is the current behavior for all values except asynSuccess)
asynDisconnected = epicsAlarmComm
asynDisabled = epicsAlarmDisable
This mechanism is simple and would provide additional alarm information even for existing drivers based on the status that they return in the interface methods. It restricts the type of alarms that drivers can set to a subset of the possible values, but is this a significant problem? Most of the other values are unlikely to arise in drivers. I think we would need to continue to set SEVR=INVALID_ALARM for all of these conditions.
Solution 2) Add 2 new fields to the pasynUser structure:
epicsAlarmSeverity alarmSeverity;
epicsAlarmCondition alarmCondition;
Drivers can optionally set these values in the pasynUser passed by the interface methods and in the pasynUser passed to callbacks. Device support would handle this as follows:
- If the status return for interface method, or the pasynUser->auxStatus for callbacks is not asynSuccess then
- If pasynUser->alarmSeverity is non-zero use pasynUser->alarmSeverity else use INVALID_ALARM
- If pasynUser->alarmCondition is non-zero use pasynUser->alarmCondition else use WRITE_ALARM or READ_ALARM
This allows more flexibility in how drivers set alarms, at the expense of more work in the driver.
Comments?
Mark
________________________________________
From: Eric Norum [[email protected]]
Sent: Tuesday, May 01, 2012 9:58 PM
To: Mark Rivers
Cc: [email protected] Talk
Subject: Re: asynPortDriver callbacks to I/O Intr, how to propagate an error?
Rather than simply setting READ/INVALID when auxStatus is non-zero, how about passing the STAT in the upper 16 bits of auxStatus and the SEVR in the lower 16-bits. We could provide a macro (asynSetAuxStatus(stat,sevr)) to make this easier.
On May 1, 2012, at 7:20 PM, Mark Rivers wrote:
> Folks,
>
> This request from Angus from about a year ago has come up several times on tech-talk. The problem is that input records with SCAN=I/O Intr did not have a way of having their STAT and SEVR set to indicate a problem with the underlying asyn driver.
>
> I have finally come up with a clean solution to this problem. The solution is for drivers to set the pasynUser->auxStatus field before they do the callbacks to device support. That field in the pasynUser structure is set to 0 (asynSuccess) when the asynUser structure is created, and it is not currently used for any other purpose in the asyn module. This means that using that field for status in callbacks should not break any existing drivers or device support.
>
> I have modified the standard asyn device support so that input records with SCAN=I/O Intr get their status and severity from the pasynUser->auxStatus field. If that field is not asynSuccess then the record is set to STAT=READ, SEVR=INVALID.
>
> I have added support in asynPortDriver for passing status information to clients in callbacks. Each parameter in the parameter library now has an associated asynStatus variable. New functions setParamStatus() and getParamStatus() are provided to access this variable. If setParamStatus(paramIndex, asynError) is called then callParamCallbacks() will cause any input records with SCAN=I/O Intr to go into alarm state.
>
> I've created a new asyn test application, asyn/testErrorsApp, which tests this new feature for all interfaces and all records supported by standard asyn device support. It uses a driver that is based on asynPortDriver.
>
> The release notes have been updated.
>
> All changes are committed to SVN.
>
> https://svn.aps.anl.gov/epics/asyn/trunk/
>
>
> The EPICS modbus application has also been updated to use this new feature. If a Modbus device has communication errors then all input records with SCAN=I/O Intr will go into INVALID alarm. Those changes are also committed to SVN.
>
> https://subversion.xor.aps.anl.gov/synApps/modbus/trunk/
>
> I would appreciate feedback from anyone who can test these before I release asyn R4-19 and modbus R2-4.
>
> Cheers,
> Mark
>
> ________________________________________
> From: [email protected] [[email protected]] on behalf of Angus Gratton [[email protected]]
> Sent: Tuesday, May 10, 2011 7:59 PM
> To: tech-talk
> Subject: asynPortDriver callbacks to I/O Intr, how to propagate an error?
>
> I have some asynPortDriver-derived driver classes for various pieces of
> hardware, most of which are updated when data changes in a DMA read (ie
> the background monitoring thread calls setIntegerParam() then calls
> callParamCallbacks())
>
> The records are all using I/O Intr so they only scan when required.
>
> Sometimes the DMA read indicates that a piece of hardware has gone
> offline. In this case, I'd like to have records using that port scanned
> and updated to INVALID severity, and also see an error logged on the
> console.
>
> If was using periodic scanning, I believe I could override readInt32()
> or equivalent to return asynError status. However, if I want to keep
> using I/O Intr then I can't see any way to do this, either with
> asynPortDriver or with asyn.
>
> What I'm imagining would help me is a method with a name like
> setParamErrorFlag(), that I could call before callParamCallbacks() and
> that would propagate the error state back to the record. I'm still very
> much an asyn newbie though, so maybe I'm looking at this the wrong way.
>
> Thanks in advance for any tips. If this feature doesn't exist and might
> be useful, I'm happy to have a shot at implementing it with a view to
> submitting a patch.
>
> - Angus
>
>
>
> --
> Angus Gratton
> Computer Control Specialist
> Department of Nuclear Physics
> Australian National University
>
> Ph: +61 2 6125 2096
>
>
--
Eric Norum
[email protected]
- Replies:
- Re: asynPortDriver callbacks to I/O Intr, how to propagate an error? Eric Norum
- References:
- RE: asynPortDriver callbacks to I/O Intr, how to propagate an error? Mark Rivers
- Re: asynPortDriver callbacks to I/O Intr, how to propagate an error? Eric Norum
- Navigate by Date:
- Prev:
Re: CA_PROTO_READ_NOTIFY Response Mark Davis
- Next:
Re: asynPortDriver callbacks to I/O Intr, how to propagate an error? Eric Norum
- Index:
1994
1995
1996
1997
1998
1999
2000
2001
2002
2003
2004
2005
2006
2007
2008
2009
2010
2011
<2012>
2013
2014
2015
2016
2017
2018
2019
2020
2021
2022
2023
2024
- Navigate by Thread:
- Prev:
Re: asynPortDriver callbacks to I/O Intr, how to propagate an error? Eric Norum
- Next:
Re: asynPortDriver callbacks to I/O Intr, how to propagate an error? Eric Norum
- Index:
1994
1995
1996
1997
1998
1999
2000
2001
2002
2003
2004
2005
2006
2007
2008
2009
2010
2011
<2012>
2013
2014
2015
2016
2017
2018
2019
2020
2021
2022
2023
2024
|