Ferdi's fixes
This commit is contained in:
131
multicounter.c
131
multicounter.c
@@ -77,9 +77,12 @@ static int MMCCHalt(void *pData)
|
|||||||
/*-------------------------------------------------------------------------*/
|
/*-------------------------------------------------------------------------*/
|
||||||
static int MMCCStart(void *pData, SConnection * pCon)
|
static int MMCCStart(void *pData, SConnection * pCon)
|
||||||
{
|
{
|
||||||
int i, status;
|
int i, status, controlMonitor;
|
||||||
|
int slavePreset, oneYear = 32000000;
|
||||||
pCounter pCount = NULL;
|
pCounter pCount = NULL;
|
||||||
pMultiCounter self = NULL;
|
pMultiCounter self = NULL;
|
||||||
|
char buffer[128];
|
||||||
|
CounterMode slaveMode;
|
||||||
|
|
||||||
pCount = (pCounter) pData;
|
pCount = (pCounter) pData;
|
||||||
if (pCount != NULL) {
|
if (pCount != NULL) {
|
||||||
@@ -90,12 +93,25 @@ static int MMCCStart(void *pData, SConnection * pCon)
|
|||||||
if (!GetCountLock(pCount->pCountInt, pCon)) {
|
if (!GetCountLock(pCount->pCountInt, pCon)) {
|
||||||
return HWFault;
|
return HWFault;
|
||||||
}
|
}
|
||||||
|
controlMonitor = GetControlMonitor((pCounter) pCount);
|
||||||
|
if (pCount->pDriv->eMode == ePreset) {
|
||||||
|
slaveMode = eTimer;
|
||||||
|
slavePreset = oneYear;
|
||||||
|
} else {
|
||||||
|
slaveMode = pCount->pDriv->eMode;
|
||||||
|
slavePreset = pCount->pDriv->fPreset;
|
||||||
|
}
|
||||||
|
|
||||||
for (i = 0; i < self->nSlaves; i++) {
|
for (i = 0; i < self->nSlaves; i++) {
|
||||||
ReleaseCountLock(self->slaves[i]);
|
ReleaseCountLock(self->slaves[i]);
|
||||||
|
if (i == controlMonitor) {
|
||||||
self->slaves[i]->SetCountParameters(self->slaveData[i],
|
self->slaves[i]->SetCountParameters(self->slaveData[i],
|
||||||
pCount->pDriv->fPreset,
|
pCount->pDriv->fPreset,
|
||||||
pCount->pDriv->eMode);
|
pCount->pDriv->eMode);
|
||||||
|
} else {
|
||||||
|
self->slaves[i]->SetCountParameters(self->slaveData[i],
|
||||||
|
slavePreset, slaveMode);
|
||||||
|
}
|
||||||
status = self->slaves[i]->StartCount(self->slaveData[i], pCon);
|
status = self->slaves[i]->StartCount(self->slaveData[i], pCon);
|
||||||
if (status != OKOK) {
|
if (status != OKOK) {
|
||||||
MMCCHalt(pData);
|
MMCCHalt(pData);
|
||||||
@@ -112,10 +128,18 @@ static int MMCCStart(void *pData, SConnection * pCon)
|
|||||||
/*-------------------------------------------------------------------------*/
|
/*-------------------------------------------------------------------------*/
|
||||||
static int MMCCStatus(void *pData, SConnection * pCon)
|
static int MMCCStatus(void *pData, SConnection * pCon)
|
||||||
{
|
{
|
||||||
int status, i;
|
int status, ctrStatus, i, controlMonitor;
|
||||||
|
pCounter pCountController = NULL, pSlaveCounter = NULL;
|
||||||
pCounter pCount = NULL, pMaster = NULL;;
|
pCounter pCount = NULL, pMaster = NULL;;
|
||||||
pMultiCounter self = NULL;
|
pMultiCounter self = NULL;
|
||||||
pDummy pDum = NULL;
|
pDummy pDum = NULL;
|
||||||
|
enum {
|
||||||
|
eIdle,
|
||||||
|
eBusy,
|
||||||
|
ePause,
|
||||||
|
eNoBeam,
|
||||||
|
eFault
|
||||||
|
} statusLevel;
|
||||||
|
|
||||||
pCount = (pCounter) pData;
|
pCount = (pCounter) pData;
|
||||||
if (pCount != NULL) {
|
if (pCount != NULL) {
|
||||||
@@ -132,6 +156,44 @@ static int MMCCStatus(void *pData, SConnection * pCon)
|
|||||||
status = self->slaves[0]->CheckCountStatus(self->slaveData[0], pCon);
|
status = self->slaves[0]->CheckCountStatus(self->slaveData[0], pCon);
|
||||||
pMaster = (pCounter)self->slaveData[0];
|
pMaster = (pCounter)self->slaveData[0];
|
||||||
pCount->pDriv->fLastCurrent = GetControlValue(pMaster);
|
pCount->pDriv->fLastCurrent = GetControlValue(pMaster);
|
||||||
|
controlMonitor = GetControlMonitor((pCounter) pCount);
|
||||||
|
pCountController = (pCounter) self->slaveData[controlMonitor];
|
||||||
|
|
||||||
|
/* counter states = HWIdle, HWBusy, HWPause, HWNoBeam, HWFault */
|
||||||
|
status = HWIdle;
|
||||||
|
statusLevel = eIdle;
|
||||||
|
for (i = 0; i < self->nSlaves; i++) {
|
||||||
|
pSlaveCounter = (pCounter) self->slaveData[i];
|
||||||
|
ctrStatus = self->slaves[i]->CheckCountStatus(pSlaveCounter, pCon);
|
||||||
|
if (statusLevel >= eFault)
|
||||||
|
continue;
|
||||||
|
switch (ctrStatus) {
|
||||||
|
case HWFault:
|
||||||
|
statusLevel = eFault;
|
||||||
|
status = HWFault;
|
||||||
|
break;
|
||||||
|
case HWNoBeam:
|
||||||
|
if (statusLevel < eNoBeam)
|
||||||
|
statusLevel = eNoBeam;
|
||||||
|
status = HWNoBeam;
|
||||||
|
break;
|
||||||
|
case HWPause:
|
||||||
|
if (statusLevel < ePause)
|
||||||
|
statusLevel = ePause;
|
||||||
|
status = HWPause;
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
if (pCountController->pDriv->eMode == ePreset && i == controlMonitor
|
||||||
|
&& ctrStatus == HWIdle) {
|
||||||
|
statusLevel = eBusy; /* Allow transition to HWPause or higher */
|
||||||
|
status = HWIdle;
|
||||||
|
} else if (statusLevel < eBusy && ctrStatus != HWIdle) {
|
||||||
|
/* ffr: We expect !HWIdle means HWBusy, if not the existing code should handle the exception */
|
||||||
|
statusLevel = eBusy;
|
||||||
|
status = ctrStatus;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
if (status == HWIdle || status == HWFault) {
|
if (status == HWIdle || status == HWFault) {
|
||||||
/*
|
/*
|
||||||
stop counting on slaves when finished or when an error
|
stop counting on slaves when finished or when an error
|
||||||
@@ -231,7 +293,8 @@ static void loadCountData(pCounter pCount, const char *data)
|
|||||||
|
|
||||||
pPtr = (char *) data;
|
pPtr = (char *) data;
|
||||||
pPtr = getNextMMCCNumber(pPtr, pNumber);
|
pPtr = getNextMMCCNumber(pPtr, pNumber);
|
||||||
pCount->pDriv->fTime = atof(pNumber);
|
// SICS-195 get time from controlling monitor
|
||||||
|
// pCount->pDriv->fTime = atof(pNumber);
|
||||||
while (pPtr != NULL && i < MAXCOUNT) {
|
while (pPtr != NULL && i < MAXCOUNT) {
|
||||||
pPtr = getNextMMCCNumber(pPtr, pNumber);
|
pPtr = getNextMMCCNumber(pPtr, pNumber);
|
||||||
pCount->pDriv->lCounts[i] = atoi(pNumber);
|
pCount->pDriv->lCounts[i] = atoi(pNumber);
|
||||||
@@ -245,14 +308,19 @@ static int MMCCTransfer(void *pData, SConnection * pCon)
|
|||||||
int i, retVal = OKOK, status;
|
int i, retVal = OKOK, status;
|
||||||
char pBueffel[132];
|
char pBueffel[132];
|
||||||
pCounter pCount = NULL;
|
pCounter pCount = NULL;
|
||||||
|
pCounter pCountController = NULL, pCountSlave;
|
||||||
pMultiCounter self = NULL;
|
pMultiCounter self = NULL;
|
||||||
int tclStatus;
|
int tclStatus;
|
||||||
|
int controlMonitor;
|
||||||
|
double avCntRt;
|
||||||
|
|
||||||
pCount = (pCounter) pData;
|
pCount = (pCounter) pData;
|
||||||
if (pCount != NULL) {
|
if (pCount != NULL) {
|
||||||
self = (pMultiCounter) pCount->pDriv->pData;
|
self = (pMultiCounter) pCount->pDriv->pData;
|
||||||
}
|
}
|
||||||
assert(self);
|
assert(self);
|
||||||
|
controlMonitor = GetControlMonitor(pCount);
|
||||||
|
pCountController = (pCounter) self->slaveData[controlMonitor];
|
||||||
|
|
||||||
for (i = 0; i < self->nSlaves; i++) {
|
for (i = 0; i < self->nSlaves; i++) {
|
||||||
status = self->slaves[i]->TransferData(self->slaveData[i], pCon);
|
status = self->slaves[i]->TransferData(self->slaveData[i], pCon);
|
||||||
@@ -261,8 +329,18 @@ static int MMCCTransfer(void *pData, SConnection * pCon)
|
|||||||
snprintf(pBueffel,sizeof(pBueffel)-1,
|
snprintf(pBueffel,sizeof(pBueffel)-1,
|
||||||
"WARNING: slave histogram %d failed to transfer data", i);
|
"WARNING: slave histogram %d failed to transfer data", i);
|
||||||
SCWrite(pCon, pBueffel, eWarning);
|
SCWrite(pCon, pBueffel, eWarning);
|
||||||
|
} else if (pCountController->pDriv->eMode == ePreset) {
|
||||||
|
if (i != controlMonitor) {
|
||||||
|
pCountSlave = (pCounter) self->slaveData[i];
|
||||||
|
avCntRt =
|
||||||
|
pCountSlave->pDriv->lCounts[0] / pCountSlave->pDriv->fTime;
|
||||||
|
pCountSlave->pDriv->lCounts[0] =
|
||||||
|
avCntRt * pCountController->pDriv->fTime;
|
||||||
|
pCountSlave->pDriv->fTime = pCountController->pDriv->fTime;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
pCount->pDriv->fTime = pCountController->pDriv->fTime;
|
||||||
if (self->transferScript != NULL) {
|
if (self->transferScript != NULL) {
|
||||||
MacroPush(pCon);
|
MacroPush(pCon);
|
||||||
tclStatus = Tcl_Eval(InterpGetTcl(pServ->pSics), self->transferScript);
|
tclStatus = Tcl_Eval(InterpGetTcl(pServ->pSics), self->transferScript);
|
||||||
@@ -461,6 +539,30 @@ int MakeMultiCounter(SConnection * pCon, SicsInterp * pSics,
|
|||||||
pDriv->pData = self;
|
pDriv->pData = self;
|
||||||
pDriv->KillPrivate = KillMultiDriver;
|
pDriv->KillPrivate = KillMultiDriver;
|
||||||
pDriv->iNoOfMonitors = MAXCOUNT;
|
pDriv->iNoOfMonitors = MAXCOUNT;
|
||||||
|
/*
|
||||||
|
now loop through the remaining arguments, thereby entering them into
|
||||||
|
the slave list.
|
||||||
|
*/
|
||||||
|
self->nSlaves = 0;
|
||||||
|
for (i = 2; i < argc; i++) {
|
||||||
|
pCom = FindCommand(pSics, argv[i]);
|
||||||
|
if (!pCom) {
|
||||||
|
snprintf(pBueffel,sizeof(pBueffel)-1, "ERROR: object %s not found in MakeMultiCounter",
|
||||||
|
argv[i]);
|
||||||
|
SCWrite(pCon, pBueffel, eError);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
pCount = GetCountableInterface(pCom->pData);
|
||||||
|
if (!pCount) {
|
||||||
|
snprintf(pBueffel,sizeof(pBueffel)-1, "ERROR: object %s is NOT countable", argv[i]);
|
||||||
|
SCWrite(pCon, pBueffel, eError);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
self->slaves[self->nSlaves] = pCount;
|
||||||
|
self->slaveData[self->nSlaves] = pCom->pData;
|
||||||
|
self->nSlaves++;
|
||||||
|
}
|
||||||
|
pDriv->iNoOfMonitors = self->nSlaves;
|
||||||
pNew = CreateCounter(argv[1], pDriv);
|
pNew = CreateCounter(argv[1], pDriv);
|
||||||
if (pNew == NULL) {
|
if (pNew == NULL) {
|
||||||
SCWrite(pCon, "ERROR: out of memory in MakeMultiCounter", eError);
|
SCWrite(pCon, "ERROR: out of memory in MakeMultiCounter", eError);
|
||||||
@@ -483,29 +585,6 @@ int MakeMultiCounter(SConnection * pCon, SicsInterp * pSics,
|
|||||||
pNew->pCountInt->TransferData = MMCCTransfer;
|
pNew->pCountInt->TransferData = MMCCTransfer;
|
||||||
pNew->pCountInt->SetCountParameters = MMCCParameter;
|
pNew->pCountInt->SetCountParameters = MMCCParameter;
|
||||||
|
|
||||||
/*
|
|
||||||
now loop through the remaining arguments, thereby entering them into
|
|
||||||
the slave list.
|
|
||||||
*/
|
|
||||||
for (i = 2; i < argc; i++) {
|
|
||||||
pCom = FindCommand(pSics, argv[i]);
|
|
||||||
if (!pCom) {
|
|
||||||
snprintf(pBueffel,sizeof(pBueffel)-1, "ERROR: object %s not found in MakeMultiCounter",
|
|
||||||
argv[i]);
|
|
||||||
SCWrite(pCon, pBueffel, eError);
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
pCount = GetCountableInterface(pCom->pData);
|
|
||||||
if (!pCount) {
|
|
||||||
snprintf(pBueffel,sizeof(pBueffel)-1, "ERROR: object %s is NOT countable", argv[i]);
|
|
||||||
SCWrite(pCon, pBueffel, eError);
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
self->slaves[self->nSlaves] = pCount;
|
|
||||||
self->slaveData[self->nSlaves] = pCom->pData;
|
|
||||||
self->nSlaves++;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
now install our action command and we are done
|
now install our action command and we are done
|
||||||
*/
|
*/
|
||||||
|
|||||||
Reference in New Issue
Block a user