All,
Some months ago (21 August, to be exact) I sent the following note to
tech-talk:
> It seems that in our system when an Analog Output record with SMSL
> closed_loop has its DOL link marked CPP and is linked to a PV on another
> crate, then if the other crate reboots the scanOnce task generates a
> floating point exception within the Ao record support routines and
> suspends.
I finally got a few hours to look at this and tracked it down to the fact
that the status was not being set bad in dbCaGetLink when the record
severity is being set to INVALID_ALARM (i.e. when the link drops). Since
the status is not bad, the record processes normally with an undefined
value in the VAL field, causing FPE's on RISC architectures. Having found
it, I am surprised that more people haven't stumbled on this.
The revised dbCaGetLink (in file dbCa.c), with the four lines added
highlighted by >>>>, is:
long dbCaGetLink(struct link *plink,short dbrType, char *pdest,
unsigned short *psevr,long *nelements)
{
caLink *pca = (caLink *)plink->value.pv_link.pvt;
long status = 0;
long (*pconvert)();
STATUS semStatus;
short link_action = 0;
if(!pca) {
errlogPrintf("dbCaGetLink: record %s pv_link.pvt is NULL\n",
plink->value.pv_link.precord);
return(-1);
}
semStatus = semTake(pca->lock,WAIT_FOREVER);
if(semStatus!=OK) {
errlogPrintf("dbCaGetLink: semStatus!OK\n");
return(-1);
}
if(!pca->chid || ca_state(pca->chid) != cs_conn) {
pca->sevr = INVALID_ALARM;
>>>> status = -1;
goto done;
}
if(!ca_read_access(pca->chid)) {
pca->sevr = INVALID_ALARM;
>>>> status = -1;
goto done;
}
if((pca->dbrType == DBR_ENUM) && (dbDBRnewToDBRold[dbrType] == DBR_STRING)){
/*Must ask server for DBR_STRING*/
if(!pca->pgetString) {
plink->value.pv_link.pvlMask |= pvlOptInpString;
link_action |= CA_MONITOR_STRING;
}
if(!pca->gotInString) {
pca->sevr = INVALID_ALARM;
>>>> status = -1;
goto done;
}
if(nelements) *nelements = 1;
pconvert=dbFastGetConvertRoutine[dbDBRoldToDBFnew[DBR_STRING]][dbrType];
status = (*(pconvert))(pca->pgetString, pdest, 0);
goto done;
}
if(!pca->pgetNative) {
plink->value.pv_link.pvlMask |= pvlOptInpNative;
link_action |= CA_MONITOR_NATIVE;
}
if(!pca->gotInNative){
pca->sevr = INVALID_ALARM;
>>>> status = -1;
goto done;
}
if(!nelements || *nelements == 1){
pconvert=
dbFastGetConvertRoutine[dbDBRoldToDBFnew[pca->dbrType]][dbrType];
(*(pconvert))(pca->pgetNative, pdest, 0);
}else{
unsigned long ntoget = *nelements;
struct dbAddr dbAddr;
if(ntoget > pca->nelements) ntoget = pca->nelements;
*nelements = ntoget;
pconvert = dbGetConvertRoutine[dbDBRoldToDBFnew[pca->dbrType]][dbrType];
memset((void *)&dbAddr,0,sizeof(dbAddr));
dbAddr.pfield = pca->pgetNative;
/*Following will only be used for pca->dbrType == DBR_STRING*/
dbAddr.field_size = MAX_STRING_SIZE;
/*Ignore error return*/
(*(pconvert))(&dbAddr,pdest,ntoget,ntoget,0);
}
done:
if(psevr) *psevr = pca->sevr;
semGive(pca->lock);
if(link_action) addAction(pca,link_action);
return(status);
}
--
Nick Rees
Joint Astronomy Centre Ph: +1 (808) 961-3756
660 N. Aohoku Place Fax: +1 (808) 961-6516
Hilo, HI. 96720 Internet: [email protected]
- Replies:
- PowerPC woes Nick Rees
- References:
- CPP CA LINK's causing scanOnce to SUSPEND Nick Rees
- Navigate by Date:
- Prev:
TPMC880-10 Ethernet card for PPC. Vladis Korobov
- Next:
PowerPC woes Nick Rees
- 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:
CPP CA LINK's causing scanOnce to SUSPEND Nick Rees
- Next:
PowerPC woes Nick Rees
- 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
|