Add dummy putValue methods to const link types
Includes a new softTest program to detect regressions. Resolves http://www.aps.anl.gov/epics/core-talk/2017/msg00503.php
This commit is contained in:
@@ -211,6 +211,12 @@ static long dbConstGetValue(struct link *plink, short dbrType, void *pbuffer,
|
||||
return 0;
|
||||
}
|
||||
|
||||
static long dbConstPutValue(struct link *plink, short dbrType,
|
||||
const void *pbuffer, long nRequest)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
static lset dbConst_lset = {
|
||||
1, 0, /* Constant, not Volatile */
|
||||
NULL, NULL,
|
||||
@@ -223,6 +229,6 @@ static lset dbConst_lset = {
|
||||
NULL, NULL, NULL,
|
||||
NULL, NULL,
|
||||
NULL, NULL,
|
||||
NULL, NULL,
|
||||
dbConstPutValue, NULL,
|
||||
NULL, NULL
|
||||
};
|
||||
|
||||
@@ -558,6 +558,12 @@ static long lnkConst_getValue(struct link *plink, short dbrType, void *pbuffer,
|
||||
return 0;
|
||||
}
|
||||
|
||||
static long lnkConst_putValue(struct link *plink, short dbrType,
|
||||
const void *pbuffer, long nRequest)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
/************************* Interface Tables *************************/
|
||||
|
||||
@@ -569,7 +575,7 @@ static lset lnkConst_lset = {
|
||||
NULL, NULL, NULL,
|
||||
NULL, NULL,
|
||||
NULL, NULL,
|
||||
NULL, NULL,
|
||||
lnkConst_putValue, NULL,
|
||||
NULL, NULL
|
||||
};
|
||||
|
||||
|
||||
@@ -67,6 +67,13 @@ testHarness_SRCS += asyncSoftTest.c
|
||||
TESTFILES += ../asyncSoftTest.db
|
||||
TESTS += asyncSoftTest
|
||||
|
||||
TESTPROD_HOST += softTest
|
||||
softTest_SRCS += softTest.c
|
||||
softTest_SRCS += recTestIoc_registerRecordDeviceDriver.cpp
|
||||
testHarness_SRCS += softTest.c
|
||||
TESTFILES += ../softTest.db
|
||||
TESTS += softTest
|
||||
|
||||
TARGETS += $(COMMON_DIR)/asTestIoc.dbd
|
||||
DBDDEPENDS_FILES += asTestIoc.dbd$(DEP)
|
||||
asTestIoc_DBD += base.dbd
|
||||
|
||||
169
src/std/rec/test/softTest.c
Normal file
169
src/std/rec/test/softTest.c
Normal file
@@ -0,0 +1,169 @@
|
||||
/*************************************************************************\
|
||||
* Copyright (c) 2017 UChicago Argonne LLC, as operator of Argonne
|
||||
* National Laboratory.
|
||||
* EPICS BASE is distributed subject to a Software License Agreement found
|
||||
* in file LICENSE that is included with this distribution.
|
||||
\*************************************************************************/
|
||||
|
||||
#include <string.h>
|
||||
|
||||
#include "dbAccess.h"
|
||||
#include "dbStaticLib.h"
|
||||
#include "dbTest.h"
|
||||
#include "dbUnitTest.h"
|
||||
#include "errlog.h"
|
||||
#include "registryFunction.h"
|
||||
#include "subRecord.h"
|
||||
#include "testMain.h"
|
||||
|
||||
static
|
||||
void checkDtyp(const char *rec)
|
||||
{
|
||||
char dtyp[16];
|
||||
|
||||
strcpy(dtyp, rec);
|
||||
strcat(dtyp, ".DTYP");
|
||||
|
||||
testdbGetFieldEqual(dtyp, DBF_LONG, 0); /* Soft Channel = 0 */
|
||||
}
|
||||
|
||||
static
|
||||
void checkInput(const char *rec, int value)
|
||||
{
|
||||
char proc[16];
|
||||
|
||||
testDiag("Checking record '%s'", rec);
|
||||
|
||||
strcpy(proc, rec);
|
||||
strcat(proc, ".PROC");
|
||||
|
||||
testdbPutFieldOk(proc, DBF_CHAR, 1);
|
||||
|
||||
testdbGetFieldEqual(rec, DBF_LONG, value);
|
||||
}
|
||||
|
||||
static
|
||||
void testGroup0(void)
|
||||
{
|
||||
const char ** rec;
|
||||
const char * records[] = {
|
||||
"ai0", "bi0", "di0", "ii0", "li0", "lsi0", "mi0", "si0", NULL
|
||||
};
|
||||
|
||||
testDiag("============ Starting %s ============", EPICS_FUNCTION);
|
||||
|
||||
testdbPutFieldOk("source", DBF_LONG, 1);
|
||||
for (rec = records; *rec; rec++) {
|
||||
checkInput(*rec, 1);
|
||||
checkDtyp(*rec);
|
||||
}
|
||||
|
||||
testdbPutFieldOk("source", DBF_LONG, 0);
|
||||
for (rec = records; *rec; rec++) {
|
||||
checkInput(*rec, 0);
|
||||
}
|
||||
}
|
||||
|
||||
static
|
||||
void testGroup1(void)
|
||||
{
|
||||
const char ** rec;
|
||||
const char * records[] = {
|
||||
"bi1",
|
||||
"ai1", "di1", "ii1", "li1", "lsi1", "mi1", "si1", NULL
|
||||
};
|
||||
int init = 1; /* bi1 initializes to 1 */
|
||||
|
||||
testDiag("============ Starting %s ============", EPICS_FUNCTION);
|
||||
|
||||
for (rec = records; *rec; rec++) {
|
||||
checkInput(*rec, init);
|
||||
init = 9; /* remainder initialize to 9 */
|
||||
}
|
||||
}
|
||||
|
||||
int dest;
|
||||
|
||||
static
|
||||
long destSubr(subRecord *prec)
|
||||
{
|
||||
dest = prec->val;
|
||||
return 0;
|
||||
}
|
||||
|
||||
static
|
||||
void checkOutput(const char *rec, int value)
|
||||
{
|
||||
testDiag("Checking record '%s'", rec);
|
||||
|
||||
testdbPutFieldOk(rec, DBF_LONG, value);
|
||||
|
||||
testOk(dest == value, "value %d output -> %d", value, dest);
|
||||
}
|
||||
|
||||
static
|
||||
void testGroup2(void)
|
||||
{
|
||||
const char ** rec;
|
||||
const char * records[] = {
|
||||
"ao0", "bo0", "io0", "lo0", "lso0", "mo0", "so0", NULL,
|
||||
};
|
||||
|
||||
testDiag("============ Starting %s ============", EPICS_FUNCTION);
|
||||
|
||||
for (rec = records; *rec; rec++) {
|
||||
checkOutput(*rec, 1);
|
||||
checkDtyp(*rec);
|
||||
}
|
||||
checkOutput("do0.B0", 1);
|
||||
checkDtyp("do0");
|
||||
|
||||
for (rec = records; *rec; rec++) {
|
||||
checkOutput(*rec, 0);
|
||||
}
|
||||
checkOutput("do0.B0", 0);
|
||||
}
|
||||
|
||||
static
|
||||
void testGroup3(void)
|
||||
{
|
||||
const char ** rec;
|
||||
const char * records[] = {
|
||||
"ao1", "bo1", "do1.B0", "io1", "lo1", "lso1", "mo1", "so1", NULL,
|
||||
};
|
||||
|
||||
testDiag("============ Starting %s ============", EPICS_FUNCTION);
|
||||
|
||||
for (rec = records; *rec; rec++) {
|
||||
checkOutput(*rec, 0);
|
||||
}
|
||||
}
|
||||
|
||||
void recTestIoc_registerRecordDeviceDriver(struct dbBase *);
|
||||
|
||||
MAIN(softTest)
|
||||
{
|
||||
testPlan(114);
|
||||
|
||||
testdbPrepare();
|
||||
testdbReadDatabase("recTestIoc.dbd", NULL, NULL);
|
||||
|
||||
recTestIoc_registerRecordDeviceDriver(pdbbase);
|
||||
registryFunctionAdd("destSubr", (REGISTRYFUNCTION) destSubr);
|
||||
|
||||
testdbReadDatabase("softTest.db", NULL, NULL);
|
||||
|
||||
eltc(0);
|
||||
testIocInitOk();
|
||||
eltc(1);
|
||||
|
||||
testGroup0();
|
||||
testGroup1();
|
||||
testGroup2();
|
||||
testGroup3();
|
||||
|
||||
testIocShutdownOk();
|
||||
testdbCleanup();
|
||||
|
||||
return testDone();
|
||||
}
|
||||
227
src/std/rec/test/softTest.db
Normal file
227
src/std/rec/test/softTest.db
Normal file
@@ -0,0 +1,227 @@
|
||||
# Group 0 are input records with INP being a DB link to 'source'.
|
||||
# Processing them reads that value.
|
||||
|
||||
record(longin, "source") {}
|
||||
|
||||
record(ai, "ai0") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(INP, "source")
|
||||
}
|
||||
record(bi, "bi0") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(INP, "source")
|
||||
field(ZNAM, "Zero")
|
||||
field(ONAM, "One")
|
||||
}
|
||||
record(int64in, "ii0") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(INP, "source")
|
||||
}
|
||||
record(longin, "li0") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(INP, "source")
|
||||
}
|
||||
record(mbbiDirect, "di0") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(NOBT, 4)
|
||||
field(INP, "source")
|
||||
}
|
||||
record(mbbi, "mi0") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(NOBT, 4)
|
||||
field(INP, "source")
|
||||
field(ZRST, "Zero")
|
||||
field(ONST, "One")
|
||||
field(TWST, "Two")
|
||||
field(THST, "Three")
|
||||
field(FRST, "Four")
|
||||
field(FVST, "Five")
|
||||
field(SXST, "Six")
|
||||
field(SVST, "Seven")
|
||||
field(EIST, "Eight")
|
||||
field(NIST, "Nine")
|
||||
field(TEST, "Ten")
|
||||
field(ELST, "Eleven")
|
||||
field(TWST, "Twelve")
|
||||
field(TTST, "Thirteen")
|
||||
field(FTST, "Fourteen")
|
||||
field(FFST, "Fifteen")
|
||||
}
|
||||
record(lsi, "lsi0") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(SIZV, 40)
|
||||
field(INP, "source")
|
||||
}
|
||||
record(stringin, "si0") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(INP, "source")
|
||||
}
|
||||
|
||||
# Group 1 are input records with INP being a non-zero constant.
|
||||
# Processing them succeeds but does not change VAL.
|
||||
|
||||
record(ai, "ai1") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(INP, {const:9})
|
||||
}
|
||||
record(bi, "bi1") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(INP, {const:1})
|
||||
field(ZNAM, "Zero")
|
||||
field(ONAM, "One")
|
||||
}
|
||||
record(int64in, "ii1") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(INP, {const:9})
|
||||
}
|
||||
record(longin, "li1") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(INP, {const:9})
|
||||
}
|
||||
record(mbbiDirect, "di1") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(NOBT, 4)
|
||||
field(INP, {const:9})
|
||||
}
|
||||
record(mbbi, "mi1") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(NOBT, 4)
|
||||
field(INP, {const:9})
|
||||
field(ZRST, "Zero")
|
||||
field(ONST, "One")
|
||||
field(TWST, "Two")
|
||||
field(THST, "Three")
|
||||
field(FRST, "Four")
|
||||
field(FVST, "Five")
|
||||
field(SXST, "Six")
|
||||
field(SVST, "Seven")
|
||||
field(EIST, "Eight")
|
||||
field(NIST, "Nine")
|
||||
field(TEST, "Ten")
|
||||
field(ELST, "Eleven")
|
||||
field(TWST, "Twelve")
|
||||
field(TTST, "Thirteen")
|
||||
field(FTST, "Fourteen")
|
||||
field(FFST, "Fifteen")
|
||||
}
|
||||
record(lsi, "lsi1") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(SIZV, 40)
|
||||
field(INP, {const:"9"})
|
||||
}
|
||||
record(stringin, "si1") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(INP, {const:"9"})
|
||||
}
|
||||
|
||||
|
||||
# Group 2 are output records with OUT being a DB link to 'dest' with PP.
|
||||
# Putting a value to them writes that value to 'dest'.
|
||||
|
||||
record(sub, "dest") {
|
||||
field(SNAM, "destSubr")
|
||||
}
|
||||
|
||||
record(ao, "ao0") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(OUT, "dest PP")
|
||||
}
|
||||
record(bo, "bo0") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(OUT, "dest PP")
|
||||
field(ZNAM, "Zero")
|
||||
field(ONAM, "One")
|
||||
}
|
||||
record(int64out, "io0") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(OUT, "dest PP")
|
||||
}
|
||||
record(longout, "lo0") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(OUT, "dest PP")
|
||||
}
|
||||
record(mbboDirect, "do0") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(NOBT, 4)
|
||||
field(OUT, "dest PP")
|
||||
}
|
||||
record(mbbo, "mo0") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(NOBT, 4)
|
||||
field(OUT, "dest PP")
|
||||
field(ZRST, "Zero")
|
||||
field(ONST, "One")
|
||||
field(TWST, "Two")
|
||||
field(THST, "Three")
|
||||
field(FRST, "Four")
|
||||
field(FVST, "Five")
|
||||
field(SXST, "Six")
|
||||
field(SVST, "Seven")
|
||||
field(EIST, "Eight")
|
||||
field(NIST, "Nine")
|
||||
field(TEST, "Ten")
|
||||
field(ELST, "Eleven")
|
||||
field(TWST, "Twelve")
|
||||
field(TTST, "Thirteen")
|
||||
field(FTST, "Fourteen")
|
||||
field(FFST, "Fifteen")
|
||||
}
|
||||
record(lso, "lso0") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(OUT, "dest PP")
|
||||
field(SIZV, 40)
|
||||
}
|
||||
record(stringout, "so0") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(OUT, "dest PP")
|
||||
}
|
||||
|
||||
|
||||
# Group 3 are output records with OUT being empty (a constant link).
|
||||
# Putting a value to them must succeed.
|
||||
|
||||
record(ao, "ao1") {
|
||||
field(DTYP, "Soft Channel")
|
||||
}
|
||||
record(bo, "bo1") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(ZNAM, "Zero")
|
||||
field(ONAM, "One")
|
||||
}
|
||||
record(int64out, "io1") {
|
||||
field(DTYP, "Soft Channel")
|
||||
}
|
||||
record(longout, "lo1") {
|
||||
field(DTYP, "Soft Channel")
|
||||
}
|
||||
record(mbboDirect, "do1") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(NOBT, 4)
|
||||
}
|
||||
record(mbbo, "mo1") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(NOBT, 4)
|
||||
field(ZRST, "Zero")
|
||||
field(ONST, "One")
|
||||
field(TWST, "Two")
|
||||
field(THST, "Three")
|
||||
field(FRST, "Four")
|
||||
field(FVST, "Five")
|
||||
field(SXST, "Six")
|
||||
field(SVST, "Seven")
|
||||
field(EIST, "Eight")
|
||||
field(NIST, "Nine")
|
||||
field(TEST, "Ten")
|
||||
field(ELST, "Eleven")
|
||||
field(TWST, "Twelve")
|
||||
field(TTST, "Thirteen")
|
||||
field(FTST, "Fourteen")
|
||||
field(FFST, "Fifteen")
|
||||
}
|
||||
record(lso, "lso1") {
|
||||
field(DTYP, "Soft Channel")
|
||||
field(SIZV, 40)
|
||||
}
|
||||
record(stringout, "so1") {
|
||||
field(DTYP, "Soft Channel")
|
||||
}
|
||||
Reference in New Issue
Block a user