diff --git a/src/ioc/db/dbAccessDefs.h b/src/ioc/db/dbAccessDefs.h index e0e8f4484..67b529d39 100644 --- a/src/ioc/db/dbAccessDefs.h +++ b/src/ioc/db/dbAccessDefs.h @@ -182,6 +182,7 @@ struct dbr_alDouble {DBRalDouble}; #define S_db_badChoice (M_dbAccess|13) /*Illegal choice*/ #define S_db_badField (M_dbAccess|15) /*Illegal field value*/ #define S_db_lsetLogic (M_dbAccess|17) /*Logic error generating lock sets*/ +#define S_db_noLSET (M_dbAccess|21) /*No link support table or entry*/ #define S_db_noRSET (M_dbAccess|31) /*missing record support entry table*/ #define S_db_noSupport (M_dbAccess|33) /*RSET or DSXT routine not defined*/ #define S_db_BadSub (M_dbAccess|35) /*Subroutine not found*/ diff --git a/src/ioc/db/dbCa.c b/src/ioc/db/dbCa.c index 5f532ad5d..1763fe3e7 100644 --- a/src/ioc/db/dbCa.c +++ b/src/ioc/db/dbCa.c @@ -232,11 +232,8 @@ void dbCaSync(void) void dbCaCallbackProcess(void *userPvt) { struct link *plink = (struct link *)userPvt; - dbCommon *pdbCommon = plink->precord; - dbScanLock(pdbCommon); - pdbCommon->rset->process(pdbCommon); - dbScanUnlock(pdbCommon); + dbLinkAsyncComplete(plink); } void dbCaShutdown(void) @@ -420,6 +417,13 @@ done: return status; } +static long dbCaPutAsync(struct link *plink,short dbrType, + const void *pbuffer,long nRequest) +{ + return dbCaPutLinkCallback(plink, dbrType, pbuffer, nRequest, + dbCaCallbackProcess, plink); +} + long dbCaPutLinkCallback(struct link *plink,short dbrType, const void *pbuffer,long nRequest,dbCaCallback callback,void *userPvt) { @@ -717,7 +721,7 @@ static lset dbCa_lset = { getControlLimits, getGraphicLimits, getAlarmLimits, getPrecision, getUnits, getAlarm, getTimeStamp, - dbCaPutLink, + dbCaPutLink, dbCaPutAsync, scanForward }; diff --git a/src/ioc/db/dbConstLink.c b/src/ioc/db/dbConstLink.c index 90f5d8d6b..38f5d448c 100644 --- a/src/ioc/db/dbConstLink.c +++ b/src/ioc/db/dbConstLink.c @@ -94,7 +94,7 @@ static lset dbConst_lset = { NULL, NULL, NULL, NULL, NULL, NULL, NULL, - NULL, + NULL, NULL, NULL }; diff --git a/src/ioc/db/dbDbLink.c b/src/ioc/db/dbDbLink.c index e4e86316c..58f089126 100644 --- a/src/ioc/db/dbDbLink.c +++ b/src/ioc/db/dbDbLink.c @@ -344,7 +344,7 @@ static lset dbDb_lset = { dbDbGetControlLimits, dbDbGetGraphicLimits, dbDbGetAlarmLimits, dbDbGetPrecision, dbDbGetUnits, dbDbGetAlarm, dbDbGetTimeStamp, - dbDbPutValue, + dbDbPutValue, NULL, dbDbScanFwdLink }; diff --git a/src/ioc/db/dbLink.c b/src/ioc/db/dbLink.c index a07d35caf..a877eec6e 100644 --- a/src/ioc/db/dbLink.c +++ b/src/ioc/db/dbLink.c @@ -38,6 +38,7 @@ #include "db_field_log.h" #include "dbFldTypes.h" #include "dbLink.h" +#include "dbLock.h" #include "dbScan.h" #include "dbStaticLib.h" #include "devSup.h" @@ -149,7 +150,7 @@ long dbLoadLink(struct link *plink, short dbrType, void *pbuffer) if (plset && plset->loadScalar) return plset->loadScalar(plink, dbrType, pbuffer); - return S_db_notFound; + return S_db_noLSET; } long dbLoadLinkArray(struct link *plink, short dbrType, void *pbuffer, @@ -160,7 +161,7 @@ long dbLoadLinkArray(struct link *plink, short dbrType, void *pbuffer, if (plset && plset->loadArray) return plset->loadArray(plink, dbrType, pbuffer, pnRequest); - return S_db_notFound; + return S_db_noLSET; } void dbRemoveLink(struct dbLocker *locker, struct link *plink) @@ -199,7 +200,7 @@ long dbGetNelements(const struct link *plink, long *nelements) lset *plset = plink->lset; if (!plset || !plset->getElements) - return S_db_badField; + return S_db_noLSET; return plset->getElements(plink, nelements); } @@ -235,7 +236,7 @@ long dbGetControlLimits(const struct link *plink, double *low, double *high) lset *plset = plink->lset; if (!plset || !plset->getControlLimits) - return S_db_notFound; + return S_db_noLSET; return plset->getControlLimits(plink, low, high); } @@ -245,7 +246,7 @@ long dbGetGraphicLimits(const struct link *plink, double *low, double *high) lset *plset = plink->lset; if (!plset || !plset->getGraphicLimits) - return S_db_notFound; + return S_db_noLSET; return plset->getGraphicLimits(plink, low, high); } @@ -256,7 +257,7 @@ long dbGetAlarmLimits(const struct link *plink, double *lolo, double *low, lset *plset = plink->lset; if (!plset || !plset->getAlarmLimits) - return S_db_notFound; + return S_db_noLSET; return plset->getAlarmLimits(plink, lolo, low, high, hihi); } @@ -266,7 +267,7 @@ long dbGetPrecision(const struct link *plink, short *precision) lset *plset = plink->lset; if (!plset || !plset->getPrecision) - return S_db_notFound; + return S_db_noLSET; return plset->getPrecision(plink, precision); } @@ -276,7 +277,7 @@ long dbGetUnits(const struct link *plink, char *units, int unitsSize) lset *plset = plink->lset; if (!plset || !plset->getUnits) - return S_db_notFound; + return S_db_noLSET; return plset->getUnits(plink, units, unitsSize); } @@ -287,7 +288,7 @@ long dbGetAlarm(const struct link *plink, epicsEnum16 *status, lset *plset = plink->lset; if (!plset || !plset->getAlarm) - return S_db_notFound; + return S_db_noLSET; return plset->getAlarm(plink, status, severity); } @@ -297,7 +298,7 @@ long dbGetTimeStamp(const struct link *plink, epicsTimeStamp *pstamp) lset *plset = plink->lset; if (!plset || !plset->getTimeStamp) - return S_db_notFound; + return S_db_noLSET; return plset->getTimeStamp(plink, pstamp); } @@ -309,7 +310,7 @@ long dbPutLink(struct link *plink, short dbrType, const void *pbuffer, long status; if (!plset || !plset->putValue) - return S_db_notFound; + return S_db_noLSET; status = plset->putValue(plink, dbrType, pbuffer, nRequest); if (status) { @@ -320,6 +321,33 @@ long dbPutLink(struct link *plink, short dbrType, const void *pbuffer, return status; } +void dbLinkAsyncComplete(struct link *plink) +{ + dbCommon *pdbCommon = plink->precord; + + dbScanLock(pdbCommon); + pdbCommon->rset->process(pdbCommon); + dbScanUnlock(pdbCommon); +} + +long dbPutLinkAsync(struct link *plink, short dbrType, const void *pbuffer, + long nRequest) +{ + lset *plset = plink->lset; + long status; + + if (!plset || !plset->putAsync) + return S_db_noLSET; + + status = plset->putAsync(plink, dbrType, pbuffer, nRequest); + if (status) { + struct dbCommon *precord = plink->precord; + + recGblSetSevr(precord, LINK_ALARM, INVALID_ALARM); + } + return status; +} + void dbScanFwdLink(struct link *plink) { lset *plset = plink->lset; @@ -341,7 +369,7 @@ long dbLoadLinkLS(struct link *plink, char *pbuffer, epicsUInt32 size, return 0; } - return S_db_notFound; + return S_db_noLSET; } long dbGetLinkLS(struct link *plink, char *pbuffer, epicsUInt32 size, diff --git a/src/ioc/db/dbLink.h b/src/ioc/db/dbLink.h index 628483119..834400c73 100644 --- a/src/ioc/db/dbLink.h +++ b/src/ioc/db/dbLink.h @@ -48,6 +48,8 @@ typedef struct lset { long (*getTimeStamp)(const struct link *plink, epicsTimeStamp *pstamp); long (*putValue)(struct link *plink, short dbrType, const void *pbuffer, long nRequest); + long (*putAsync)(struct link *plink, short dbrType, + const void *pbuffer, long nRequest); void (*scanForward)(struct link *plink); } lset; @@ -83,6 +85,9 @@ epicsShareFunc long dbGetTimeStamp(const struct link *plink, epicsTimeStamp *pstamp); epicsShareFunc long dbPutLink(struct link *plink, short dbrType, const void *pbuffer, long nRequest); +epicsShareFunc void dbLinkAsyncComplete(struct link *plink); +epicsShareFunc long dbPutLinkAsync(struct link *plink, short dbrType, + const void *pbuffer, long nRequest); epicsShareFunc void dbScanFwdLink(struct link *plink); epicsShareFunc long dbLoadLinkLS(struct link *plink, char *pbuffer,