Files
epics-base/src/libCom/sydSubrPFO.c
1992-03-09 10:51:26 +00:00

228 lines
6.7 KiB
C
Raw Blame History

This file contains invisible Unicode characters
This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
/* $Id$
* Author: Roger A. Cole
* Date: 12-04-90
*
* Experimental Physics and Industrial Control System (EPICS)
*
* Copyright 1991-92, the Regents of the University of California,
* and the University of Chicago Board of Governors.
*
* This software was produced under U.S. Government contracts:
* (W-7405-ENG-36) at the Los Alamos National Laboratory,
* and (W-31-109-ENG-38) at Argonne National Laboratory.
*
* Initial development by:
* The Controls and Automation Group (AT-8)
* Ground Test Accelerator
* Accelerator Technology Division
* Los Alamos National Laboratory
*
* Co-developed with
* The Controls and Computing Group
* Accelerator Systems Division
* Advanced Photon Source
* Argonne National Laboratory
*
* Modification Log:
* -----------------
* .00 12-04-90 rac initial version
* .01 06-18-91 rac installed in SCCS
* .02 06-19-91 rac replace <fields.h> with <alarm.h>
* .03 02-27-92 rac do ts rounding here instead of sydSubr.c
*
* make options
* -DvxWorks makes a version for VxWorks
* -DNDEBUG don't compile assert() checking
* -DDEBUG compile various debug code, including checks on
* malloc'd memory
*/
/*+/mod***********************************************************************
* TITLE sydSubrPFO.c - acquire synchronous samples from `gsd_...' routines
*
* DESCRIPTION
*
*-***************************************************************************/
#include <genDefs.h>
#define SYD_PRIVATE
#include <sydDefs.h>
#include <alarm.h>
#ifndef INC_tsDefs_h
# include <tsDefs.h>
#endif
#ifndef INCLcadefh
# include <cadef.h>
#endif
#include <gsd_sync_defs.h>
#define PFO_CHAN_DEF
#include <pfoPlotDefs.h>
#ifdef vxWorks
# include <vxWorks.h>
# include <ioLib.h> /* for O_RDWR and O_RDONLY definitions */
# include <stdioLib.h>
#else
# include <stdio.h>
# include <sys/file.h> /* for O_RDWR and O_RDONLY definitions */
#endif
long sydPFOFunc();
long sydPFOFuncGetGR();
long
sydOpenPFO(ppSspec, pHandle)
SYD_SPEC **ppSspec; /* O pointer to synchronous set spec pointer */
void *pHandle; /* I pointer to handle for "source" */
{
long stat;
assert(ppSspec != NULL);
if ((*ppSspec = (SYD_SPEC *)GenMalloc(sizeof(SYD_SPEC))) == NULL)
return S_syd_noMem;
(*ppSspec)->pFunc = sydPFOFunc;
(*ppSspec)->type = SYD_TY_PFO;
if ((stat = sydPFOFunc(*ppSspec, NULL, SYD_FC_INIT, pHandle)) != S_syd_OK){
GenFree((char *)*ppSspec);
*ppSspec = NULL;
return stat;
}
(*ppSspec)->nInBufs = 2;
return sydOpen(ppSspec, pHandle);
}
/*+/subr**********************************************************************
* NAME sydPFOFunc - handle gsd_xxx sync data interactions
*
* DESCRIPTION
*
* sydPFOFunc(pSspec, NULL, SYD_FC_INIT, NULL)
* sydPFOFunc(pSspec, pSChan, SYD_FC_OPEN, pPfoChan)
* sydPFOFunc(pSspec, pSChan, SYD_FC_READ, NULL)
* sydPFOFunc(pSspec, pSChan, SYD_FC_POSITION, NULL)
* sydPFOFunc(pSspec, pSChan, SYD_FC_CLOSE, NULL)
* sydPFOFunc(pSspec, NULL, SYD_FC_FILEINFO, NULL)
* sydPFOFunc(pSspec, NULL, SYD_FC_WRAPUP, NULL)
*
* RETURNS
* S_syd_OK, or
* other code indicating error
*
* BUGS
* o text
*
* SEE ALSO
*
* EXAMPLE
*
*-*/
long
sydPFOFunc(pSspec, pStruct, funcCode, pArg)
SYD_SPEC *pSspec; /* IO pointer to synchronous set spec */
void *pStruct; /* IO pointer to data struct used by funcCode */
enum sydFuncCode funcCode;/* I function code */
void *pArg; /* I pointer to arg, as required by funcCode */
{
SYD_CHAN *pSChan; /* pointer to syncSet channel descriptor */
PFO_CHAN *pPChan; /* pointer to pfo channel struct */
struct gsd_sync_data *pSyn; /* pointer to pfo sync data struct */
long retStat=S_syd_OK;
int bufNum, nBytes;
pSChan = (SYD_CHAN *)pStruct;
if (funcCode == SYD_FC_INIT) {
pSspec->pHandle = NULL;
}
else if (funcCode == SYD_FC_OPEN) {
pPChan = (PFO_CHAN *)pArg;
pSChan->pHandle = (void *)pPChan->pGsd;
pSChan->dbfType = ca_field_type(pPChan->pGsd->pChid);
pSChan->dbrType = pPChan->pGsd->time_type;
assert(dbr_type_is_TIME(pSChan->dbrType));
pSChan->elCount = pPChan->pGsd->count;
sydPFOFuncGetGR(pSspec, pSChan, pPChan);
}
else if (funcCode == SYD_FC_READ) {
pSyn = (struct gsd_sync_data *)pSChan->pHandle;
if (pSyn->svalid != 0) {
bufNum = NEXT_INBUF(pSChan, pSChan->lastInBuf);
nBytes = dbr_size_n(pSChan->dbrType, pSChan->elCount);
bcopy((char *)pSyn->pSdata, (char *)pSChan->pInBuf[bufNum], nBytes);
pSChan->inStatus[bufNum] = SYD_B_FULL;
pSChan->lastInBuf = bufNum;
if (pSChan->firstInBuf < 0)
pSChan->firstInBuf = bufNum;
if (pSspec->roundNsec > 0) {
sydTsRound(&pSChan->pInBuf[bufNum]->tfltval.stamp,
pSspec->roundNsec);
}
}
}
else if (funcCode == SYD_FC_POSITION) {
; /* no action */
}
else if (funcCode == SYD_FC_CLOSE) {
; /* no action */
}
else if (funcCode == SYD_FC_FILEINFO) {
; /* no action */
}
else if (funcCode == SYD_FC_WRAPUP) {
pSspec->pHandle = NULL;
}
return retStat;
}
static long
sydPFOFuncGetGR(pSspec, pSChan, pPChan)
SYD_SPEC *pSspec; /* pointer to syncSet specification */
SYD_CHAN *pSChan; /* pointer to syncSet channel descriptor */
PFO_CHAN *pPChan; /* pointer to pfo channel struct */
{
int i;
if (pSChan->dbrType == DBR_TIME_FLOAT) {
assert(pPChan->dbrGrType == DBR_GR_FLOAT ||
pPChan->dbrGrType == DBR_CTRL_FLOAT);
pSChan->grBuf.gfltval = pPChan->pDbrGr->gfltval;
pSChan->dbrGrType = DBR_GR_FLOAT;
}
else if (pSChan->dbrType == DBR_TIME_SHORT) {
assert(pPChan->dbrGrType == DBR_GR_SHORT ||
pPChan->dbrGrType == DBR_CTRL_SHORT);
pSChan->grBuf.gshrtval = pPChan->pDbrGr->gshrtval;
pSChan->dbrGrType = DBR_GR_SHORT;
}
else if (pSChan->dbrType == DBR_TIME_DOUBLE) {
assert(pPChan->dbrGrType == DBR_GR_DOUBLE ||
pPChan->dbrGrType == DBR_CTRL_DOUBLE);
pSChan->grBuf.gdblval = pPChan->pDbrGr->gdblval;
pSChan->dbrGrType = DBR_GR_DOUBLE;
}
else if (pSChan->dbrType == DBR_TIME_LONG) {
assert(pPChan->dbrGrType == DBR_GR_LONG ||
pPChan->dbrGrType == DBR_CTRL_LONG);
pSChan->grBuf.glngval = pPChan->pDbrGr->glngval;
pSChan->dbrGrType = DBR_GR_LONG;
}
else if (pSChan->dbrType == DBR_TIME_STRING) {
assert(pPChan->dbrGrType == DBR_GR_STRING ||
pPChan->dbrGrType == DBR_CTRL_STRING);
pSChan->grBuf.gstrval = pPChan->pDbrGr->gstrval;
pSChan->dbrGrType = DBR_GR_STRING;
}
else if (pSChan->dbrType == DBR_TIME_ENUM) {
assert(pPChan->dbrGrType == DBR_GR_ENUM ||
pPChan->dbrGrType == DBR_CTRL_ENUM);
pSChan->grBuf.genmval = pPChan->pDbrGr->genmval;
pSChan->dbrGrType = DBR_GR_ENUM;
}
else if (pSChan->dbrType == DBR_TIME_CHAR) {
assert(pPChan->dbrGrType == DBR_GR_CHAR ||
pPChan->dbrGrType == DBR_CTRL_CHAR);
pSChan->grBuf.gchrval = pPChan->pDbrGr->gchrval;
pSChan->dbrGrType = DBR_GR_FLOAT;
}
return S_syd_OK;
}