/*-------------------------------------------------------------------------- D I L L U D R I V This file contains the implementation of a driver for the Oxford Instruments dillution cryostat using the CC0-510/AVSI temperature controller. Mark Koennecke, October 1997 Copyright: see copyright.h ----------------------------------------------------------------------------*/ #include #include #include #include #include #include #include #include #include #include "evdriver.h" #include "hardsup/dillutil.h" #include "hardsup/el734_def.h" #include "hardsup/el734fix.h" #include "dilludriv.h" /*-----------------------------------------------------------------------*/ typedef struct { pDILLU pData; char *pHost; int iPort; int iChannel; int iLastError; char *pTranslationFile; } DILLUDriv, *pDILLUDriv; /*----------------------------------------------------------------------------*/ static int GetDILLUPos(pEVDriver self, float *fPos) { pDILLUDriv pMe = NULL; int iRet; assert(self); pMe = (pDILLUDriv)self->pPrivate; assert(pMe); iRet = DILLU_Read(&pMe->pData,fPos); if(iRet != 1 ) { pMe->iLastError = iRet; return 0; } if( (*fPos < 0) || (*fPos > 1000) ) { *fPos = -999.; return 0; } return 1; } /*----------------------------------------------------------------------------*/ static int DILLURun(pEVDriver self, float fVal) { pDILLUDriv pMe = NULL; int iRet; assert(self); pMe = (pDILLUDriv )self->pPrivate; assert(pMe); iRet = DILLU_Set(&pMe->pData,fVal); if(iRet != 1) { pMe->iLastError = iRet; return 0; } return 1; } /*--------------------------------------------------------------------------*/ static int DILLUError(pEVDriver self, int *iCode, char *error, int iErrLen) { pDILLUDriv pMe = NULL; assert(self); pMe = (pDILLUDriv)self->pPrivate; assert(pMe); *iCode = pMe->iLastError; DILLU_Error2Text(&pMe->pData,pMe->iLastError,error,iErrLen); return 1; } /*--------------------------------------------------------------------------*/ static int DILLUSend(pEVDriver self, char *pCommand, char *pReply, int iLen) { pDILLUDriv pMe = NULL; int iRet; assert(self); pMe = (pDILLUDriv )self->pPrivate; assert(pMe); iRet = DILLU_Send(&pMe->pData,pCommand, pReply,iLen); if(iRet != 1) { pMe->iLastError = iRet; return 0; } return 1; } /*--------------------------------------------------------------------------*/ static int DILLUInit(pEVDriver self) { pDILLUDriv pMe = NULL; int iRet; assert(self); pMe = (pDILLUDriv )self->pPrivate; assert(pMe); pMe->pData = NULL; iRet = DILLU_Open(&pMe->pData, pMe->pHost, pMe->iPort, pMe->iChannel, 0,pMe->pTranslationFile); if(iRet != 1) { pMe->iLastError = iRet; return 0; } DILLU_Config(&pMe->pData, 1000); return 1; } /*--------------------------------------------------------------------------*/ static int DILLUClose(pEVDriver self) { pDILLUDriv pMe = NULL; int iRet; assert(self); pMe = (pDILLUDriv )self->pPrivate; assert(pMe); DILLU_Close(&pMe->pData); return 1; } /*---------------------------------------------------------------------------*/ static int DILLUFix(pEVDriver self, int iError) { pDILLUDriv pMe = NULL; int iRet; assert(self); pMe = (pDILLUDriv )self->pPrivate; assert(pMe); switch(iError) { /* network errors */ case EL734__BAD_FLUSH: case EL734__BAD_RECV: case EL734__BAD_RECV_NET: case EL734__BAD_RECV_UNKN: case EL734__BAD_RECVLEN: case EL734__BAD_RECV1: case EL734__BAD_RECV1_PIPE: case EL734__BAD_RNG: case EL734__BAD_SEND: case EL734__BAD_SEND_PIPE: case EL734__BAD_SEND_NET: case EL734__BAD_SEND_UNKN: case EL734__BAD_SENDLEN: DILLUClose(self); iRet = DILLUInit(self); if(iRet) { return DEVREDO; } else { return DEVFAULT; } break; /* handable protocoll errors */ case EL734__BAD_TMO: return DEVREDO; break; case DILLU__NODILLFILE: case DILLU__ERRORTABLE: case DILLU__READONLY: case DILLU__OUTOFRANGE: case DILLU__BADMALLOC: case DILLU__FILENOTFOUND: return DEVFAULT; case DILLU__BADREAD: case DILLU__SILLYANSWER: return DEVREDO; default: return DEVFAULT; break; } return DEVFAULT; } /*--------------------------------------------------------------------------*/ static int DILLUHalt(pEVDriver *self) { assert(self); return 1; } /*------------------------------------------------------------------------*/ void KillDILLU(void *pData) { pDILLUDriv pMe = NULL; pMe = (pDILLUDriv)pData; assert(pMe); if(pMe->pHost) { free(pMe->pHost); } if(pMe->pTranslationFile) { free(pMe->pTranslationFile); } free(pMe); } /*------------------------------------------------------------------------*/ pEVDriver CreateDILLUDriv(int argc, char *argv[]) { pEVDriver pNew = NULL; pDILLUDriv pSim = NULL; /* check for arguments */ if(argc < 3) { return NULL; } pNew = CreateEVDriver(argc,argv); pSim = (pDILLUDriv)malloc(sizeof(DILLUDriv)); memset(pSim,0,sizeof(DILLUDriv)); if(!pNew || !pSim) { return NULL; } pNew->pPrivate = pSim; pNew->KillPrivate = KillDILLU; /* initalise pDILLUDriver */ pSim->iLastError = 0; pSim->pHost = strdup(argv[0]); pSim->iPort = atoi(argv[1]); pSim->iChannel = atoi(argv[2]); pSim->pTranslationFile = strdup(argv[3]); /* initialise function pointers */ pNew->SetValue = DILLURun; pNew->GetValue = GetDILLUPos; pNew->Send = DILLUSend; pNew->GetError = DILLUError; pNew->TryFixIt = DILLUFix; pNew->Init = DILLUInit; pNew->Close = DILLUClose; return pNew; }