/*----------------------------------------------------------------------- N X S C R I P T This is a class for scripting the contents of NeXus files from SICS. copyright: see file COPYRIGHT Mark Koennecke, February 2003 Mark Koennecke, January 2004 ------------------------------------------------------------------------*/ #include #include #include #include #include #include #include #include #include #include "fortify.h" #include "sics.h" #include "splitter.h" #include "HistMem.h" #include "motor.h" #include "counter.h" #include "sicsvar.h" #include "danu.h" #include "udpquieck.h" #include "nxdict.h" #include "nxscript.h" #include "sicsdata.h" extern char *trim(char *str); /* missing in nxdict.h: */ NXstatus NXDdefget(NXdict handle, char *pKey, char *pBuffer, int iBufLen); /*------------------------------------------------------------------------*/ char *makeFilename(SicsInterp *pSics, SConnection *pCon) { pSicsVariable pPath = NULL, pPref = NULL, pEnd = NULL; char *pRes = NULL; int iLen, iNum, iYear, thousand; char pNumText[10], pBueffel[256]; CommandList *pCom = NULL; DIR *dir = NULL; /* Try, get all the Variables */ pPath = FindVariable(pSics,"sicsdatapath"); pPref = FindVariable(pSics,"sicsdataprefix"); pCom = FindCommand(pSics,"sicsdatanumber"); pEnd = FindVariable(pSics,"sicsdatapostfix"); if( (!pPath) || (!pPref) || (!pCom) || (!pEnd) ){ SCWrite(pCon, "ERROR: cannot read variables for automatic data file name creation", eError); SCWrite(pCon, "ERROR: This is a VERY, VERY, VERY serious installation problem", eError); SCWrite(pCon,"ERROR: your data will be dumped into emergency.hdf",eError); return NULL; } /* find length */ iLen = strlen(pPath->text) + 4; /* extra 4 for dir number */ iLen += strlen(pPref->text); iLen += 10; /* for number + year */ iLen += strlen(pEnd->text); iLen += 10; /* safety margin */ /* allocate memory */ pRes = (char *)malloc(iLen*sizeof(char)); if(!pRes){ SCWrite(pCon,"ERROR: no memory in makeFilename",eError); return NULL; } memset(pRes,0,iLen); /* increment the data file number */ iNum = IncrementDataNumber(pCom->pData,&iYear); if(iNum < 0){ SCWrite(pCon,"ERROR: cannot increment data number!",eError); SCWrite(pCon,"ERROR: your data will be dumped to emergency.hdf",eError); free(pRes); return NULL; } strcpy(pRes,pPath->text); thousand = (int)floor(iNum/1000.); snprintf(pNumText,9,"%3.3d",thousand); strcat(pRes,pNumText); /* check for existence of directory and create if neccessary */ dir = opendir(pRes); if(dir == NULL){ mkdir(pRes,S_IRWXU | S_IRGRP | S_IXGRP); snprintf(pBueffel,255,"Creating dir: %s", pRes); SCWrite(pCon,pBueffel,eWarning); } else { closedir(dir); } /* build the rest of the filename */ strcat(pRes,"/"); strcat(pRes,pPref->text); sprintf(pNumText,"%4.4d",iYear); strcat(pRes,pNumText); strcat(pRes,"n"); sprintf(pNumText,"%6.6d",iNum); strcat(pRes,pNumText); strcat(pRes,pEnd->text); return pRes; } /*---------------------------------------------------------------------*/ void changeExtension(char *filename, char *newExtension){ char *pPtr = NULL; pPtr = strrchr(filename,(int)'.'); assert(pPtr != NULL); pPtr++; assert(strlen(pPtr) >= strlen(newExtension)); strcpy(pPtr,newExtension); } /*======================== Action =======================================*/ static int handleFileOperations(SConnection *pCon, pNXScript self, int argc, char *argv[]){ int status,i, iVal; NXaccess access; char buffer[512]; if(strcmp(argv[1],"close") == 0){ /* close everything! and send a message to trigger file synchronisation to the central server */ if(self->fileHandle == NULL){ SCSendOK(pCon); return 1; } i = 511; iVal = NX_CHAR; NXgetattr(self->fileHandle,"file_name",buffer,&i,&iVal); NXclose(&self->fileHandle); NXDclose(self->dictHandle,NULL); self->fileHandle = NULL; self->dictHandle = NULL; SendQuieck(QUIECK,buffer); SCSendOK(pCon); return 1; } else if(strcmp(argv[1],"reopen") == 0){ access = NXACC_RDWR; } else if(strcmp(argv[1],"create4") == 0){ access = NXACC_CREATE4; unlink(argv[2]); /* kill file for overwrite */ } else if(strcmp(argv[1],"create5") == 0){ access = NXACC_CREATE5; unlink(argv[2]); /* kill file for overwrite */ } else if(strcmp(argv[1],"createxml") == 0){ access = NXACC_CREATEXML; } else { return 0; } if(argc < 4){ SCWrite(pCon,"ERROR: insufficient number of arguments for file operation", eError); return -1; } /* be considerate: close files left open */ if(self->fileHandle != NULL){ NXclose(&self->fileHandle); self->fileHandle = NULL; } if(self->dictHandle != NULL){ NXDclose(self->dictHandle, NULL); self->dictHandle = NULL; } /* now initialize ourselves */ status = NXopen(argv[2],access,&self->fileHandle); if(status != NX_OK){ sprintf(buffer,"ERROR: failed to open %s",argv[2]); SCWrite(pCon,buffer,eError); return -1; } status = NXDinitfromfile(argv[3],&self->dictHandle); if(status != NX_OK){ sprintf(buffer,"ERROR: failed to open dictionary %s",argv[3]); SCWrite(pCon,buffer,eError); return -1; } SCSendOK(pCon); return 1; } /*----------------------------------------------------------------------*/ static void putMotor(SConnection *pCon, SicsInterp *pSics, pNXScript self, int argc, char *argv[]){ int status; pMotor brumm = NULL; float fVal; char buffer[132], dummy[256]; if(argc < 4){ SCWrite(pCon,"ERROR: insufficient number of arguments to putmotor", eError); return; } /* find motor */ brumm = (pMotor)FindCommandData(pSics,argv[3],"Motor"); if(!brumm){ sprintf(buffer,"ERROR: motor %s not found!", argv[3]); SCWrite(pCon,buffer,eError); return; } /* do position */ status = MotorGetSoftPosition(brumm, pCon,&fVal); if(!status){ sprintf(buffer,"ERROR: failed to read position of %s", argv[3]); SCWrite(pCon,buffer,eError); return; } status = NXDputalias(self->fileHandle,self->dictHandle,argv[2],&fVal); if(status != NX_OK){ sprintf(buffer,"ERROR: failed to write %s with alias %s", argv[3],argv[2]); SCWrite(pCon,buffer,eError); return; } /* if alias_null is available: write zero point */ strcpy(buffer,argv[2]); strcat(buffer,"_null"); if(NXDdefget(self->dictHandle,buffer,dummy,255)){ MotorGetPar(brumm,"softzero",&fVal); status = NXDputalias(self->fileHandle,self->dictHandle,buffer, &fVal); if(status != NX_OK){ sprintf(buffer,"ERROR: failed to write %s zero with alias %s", argv[3],argv[2]); SCWrite(pCon,buffer,eError); return; } } } /*---------------------------------------------------------------------*/ static void putCounter(SConnection *pCon, SicsInterp *pSics, pNXScript self, int argc, char *argv[]){ pCounter cter = NULL; float fVal; long counts; char buffer[256], newAlias[256], dummy[80]; int status, i, icounts; CounterMode eMode; if(argc < 4){ SCWrite(pCon,"ERROR: insufficient number of arguments to putcounter", eError); return; } memset(dummy,0,80*sizeof(char)); /* find counter */ cter = (pCounter)FindCommandData(pSics,argv[3],"SingleCounter"); if(!cter){ sprintf(buffer,"ERROR: counter %s not found!", argv[3]); SCWrite(pCon,buffer,eError); return; } /* do preset */ fVal = GetCounterPreset(cter); strcpy(newAlias,argv[2]); strcat(newAlias,"_preset"); status = NXDputalias(self->fileHandle,self->dictHandle,newAlias,&fVal); if(status != NX_OK){ sprintf(buffer,"ERROR: failed to write preset to %s", newAlias); SCWrite(pCon,buffer,eError); } /* do countmode */ eMode = GetCounterMode(cter); strcpy(newAlias,argv[2]); strcat(newAlias,"_mode"); if(eMode == eTimer){ strcpy(dummy,"timer"); } else { strcpy(dummy,"monitor"); } status = NXDputalias(self->fileHandle,self->dictHandle,newAlias,dummy); if(status != NX_OK){ sprintf(buffer,"ERROR: failed to write counter mode to %s", newAlias); SCWrite(pCon,buffer,eError); } /* do time */ fVal = GetCountTime(cter,pCon); strcpy(newAlias,argv[2]); strcat(newAlias,"_time"); if(NXDdefget(self->dictHandle,newAlias,dummy,79)){ status = NXDputalias(self->fileHandle,self->dictHandle,newAlias,&fVal); if(status != NX_OK){ sprintf(buffer,"ERROR: failed to write count time to %s", newAlias); SCWrite(pCon,buffer,eError); } } /* do counter and monitors */ for(i = 0; i < 10; i++){ sprintf(newAlias,"%s_%2.2d",argv[2],i); if(NXDdefget(self->dictHandle,newAlias,dummy,79)){ counts = GetMonitor(cter,i,pCon); icounts = (int)counts; status = NXDputalias(self->fileHandle,self->dictHandle,newAlias, &icounts); } } return; } /*----------------------------------------------------------------------*/ static void putSicsData(SConnection *pCon, SicsInterp *pSics, pNXScript self, int argc, char *argv[]){ pSICSData data = NULL; int status; char buffer[256]; if(argc < 4){ SCWrite(pCon,"ERROR: insufficient number of arguments to putSicsData", eError); return; } /* find data */ data = (pSICSData)FindCommandData(pSics,argv[3],"SICSData"); if(data == NULL){ snprintf(buffer,255,"ERROR: sicsdata %s not found!", argv[3]); SCWrite(pCon,buffer,eError); return; } status = NXDputalias(self->fileHandle,self->dictHandle,argv[2],data->data); if(status != NX_OK){ sprintf(buffer,"ERROR: failed to write sicsdata to %s", argv[2]); SCWrite(pCon,buffer,eError); } } /*----------------------------------------------------------------------*/ static void updateHMDim(NXScript *self, pHistMem mem){ int iDim[MAXDIM]; int i, rank, timeLength, status; char dummy[40], value[20]; const float *timeBin; /* update the dimension variables in the dictionary */ GetHistDim(mem,iDim,&rank); for(i = 0; i < rank; i++){ sprintf(dummy,"dim%1.1d", i); sprintf(value,"%d",iDim[i]); status = NXDupdate(self->dictHandle,dummy,value); if(status == 0) { NXDadd(self->dictHandle,dummy,value); } } timeBin = GetHistTimeBin(mem,&timeLength); if(timeLength > 2){ sprintf(dummy,"%d",timeLength); status = NXDupdate(self->dictHandle,"timedim",dummy); if(status == 0) { NXDadd(self->dictHandle,"timedim",dummy); } } } /*---------------------------------------------------------------------- The sequence of things is important in here: The code for updating the dimensions variables also applies the time binning to the length. Thus subsets can only be checked for after that. And then we can allocate memory. -------------------------------------------------------------------------*/ static void putHistogramMemory(SConnection *pCon, SicsInterp *pSics, pNXScript self, int argc, char *argv[]){ pHistMem mem = NULL; int status, start, length, i, subset = 0; HistInt *iData = NULL; char buffer[256]; if(argc < 4){ SCWrite(pCon,"ERROR: insufficient number of arguments to puthm", eError); return; } /* find Histogram Memory */ mem = (pHistMem)FindCommandData(pSics,argv[3],"HistMem"); if(!mem){ sprintf(buffer,"ERROR: HistMem %s not found!", argv[3]); SCWrite(pCon,buffer,eError); return; } /* default: everything */ start = 0; length = GetHistLength(mem); updateHMDim(self,mem); /* check for further arguments specifying a subset */ if(argc > 5){ subset = 1; status = Tcl_GetInt(InterpGetTcl(pSics),argv[4],&start); if(status != TCL_OK){ sprintf(buffer,"ERROR: failed to convert %s to integer", argv[4]); SCWrite(pCon,buffer,eError); return; } status = Tcl_GetInt(InterpGetTcl(pSics),argv[5],&length); if(status != TCL_OK){ sprintf(buffer,"ERROR: failed to convert %s to integer", argv[5]); SCWrite(pCon,buffer,eError); return; } } /* read HM */ if(subset){ iData = (HistInt *)malloc(length*sizeof(HistInt)); if(!iData){ SCWrite(pCon,"ERROR: out of memory for reading histogram memory", eError); return; } memset(iData,0,length*sizeof(HistInt)); status = GetHistogramDirect(mem,pCon,0,start,start+length,iData, length*sizeof(HistInt)); }else{ /* status = GetHistogram(mem,pCon,0,start,length,iData, length*sizeof(HistInt)); */ iData = GetHistogramPointer(mem,pCon); if(iData == NULL){ status = 0; } else { status = 1; } } if(!status){ SCWrite(pCon,"ERROR: failed to read histogram memory",eError); if(subset){ free(iData); } return; } /* finally: write */ status = NXDputalias(self->fileHandle, self->dictHandle,argv[2],iData); if(status != NX_OK){ sprintf(buffer,"ERROR: failed to write histogram memory data"); SCWrite(pCon,buffer,eError); } if(subset){ free(iData); } SCSendOK(pCon); return; } /*--------------------------------------------------------------------- defunct as of december 2003 */ static void putHistogramMemoryChunked(SConnection *pCon, SicsInterp *pSics, pNXScript self, int argc, char *argv[]){ pHistMem mem = NULL; int status, start, length, i, noChunks, chunkDim[MAXDIM], rank; HistInt *iData = NULL; char buffer[256]; int subset; if(argc < 5){ SCWrite(pCon,"ERROR: insufficient number of arguments to puthmchunked", eError); return; } /* find Histogram Memory */ mem = (pHistMem)FindCommandData(pSics,argv[3],"HistMem"); if(!mem){ sprintf(buffer,"ERROR: HistMem %s not found!", argv[3]); SCWrite(pCon,buffer,eError); return; } /* default: everything */ start = 0; length = GetHistLength(mem); updateHMDim(self,mem); /* check for an argument defining the number of chunks */ status = Tcl_GetInt(InterpGetTcl(pSics),argv[4],&noChunks); if(status != TCL_OK){ sprintf(buffer,"ERROR: failed to convert %s to integer", argv[4]); SCWrite(pCon,buffer,eError); return; } /* read HM */ if(subset){ iData = (HistInt *)malloc(length*sizeof(HistInt)); if(!iData){ SCWrite(pCon,"ERROR: out of memory for reading histogram memory", eError); return; } memset(iData,0,length*sizeof(HistInt)); status = GetHistogramDirect(mem,pCon,0,start,start+length,iData, length*sizeof(HistInt)); }else{ /* status = GetHistogram(mem,pCon,0,start,length,iData, length*sizeof(HistInt)); */ iData = GetHistogramPointer(mem,pCon); if(iData == NULL){ status = 0; } else { status = 1; } } if(!status){ SCWrite(pCon,"ERROR: failed to read histogram memory",eError); if(subset){ free(iData); } return; } /* finally: write */ status = NXDputalias(self->fileHandle, self->dictHandle,argv[2],iData); if(status != NX_OK){ sprintf(buffer,"ERROR: failed to write histogram memory data"); SCWrite(pCon,buffer,eError); } if(subset){ free(iData); } SCSendOK(pCon); return; } /*-------------------------------------------------------------------*/ static void putTimeBinning(SConnection *pCon, SicsInterp *pSics, pNXScript self, int argc, char *argv[]){ pHistMem mem = NULL; int i, status, timeLength; char buffer[256], defString[512], dummy[40]; const float *timeBin; float *timeCopy = NULL; if(argc < 4){ SCWrite(pCon,"ERROR: insufficient number of arguments to puttimebinning", eError); return; } /* find Histogram Memory */ mem = (pHistMem)FindCommandData(pSics,argv[3],"HistMem"); if(!mem){ sprintf(buffer,"ERROR: HistMem %s not found!", argv[3]); SCWrite(pCon,buffer,eError); return; } /* build definition string */ status = NXDdefget(self->dictHandle,argv[2],buffer,254); if(!status){ sprintf(buffer,"ERROR: alias %s for time binning not found", argv[2]); SCWrite(pCon,buffer,eError); return; } timeBin = GetHistTimeBin(mem,&timeLength); sprintf(defString,"%s -dim {%d} ",buffer,timeLength); /* Divide the time binning when appropriate and write */ if(self->timeDivisor != 1){ timeCopy = (float *)malloc(timeLength*sizeof(float)); if(timeCopy == NULL){ SCWrite(pCon,"ERROR: out of memory writing time binning",eError); return; } for(i = 0; i < timeLength; i++){ timeCopy[i] = timeBin[i]/self->timeDivisor; } status = NXDputdef(self->fileHandle, self->dictHandle, defString,(void *)timeCopy); free(timeCopy); } else { status = NXDputdef(self->fileHandle, self->dictHandle, defString,(void *)timeBin); } if(status != NX_OK){ sprintf(buffer,"ERROR: failed to write time binning"); SCWrite(pCon,buffer,eError); } SCSendOK(pCon); return; } /*----------------------------------------------------------------------*/ static void putArray(SConnection *pCon, SicsInterp *pSics, pNXScript self, int argc, char *argv[]){ float *data = NULL; int length, i, status; char num[20]; char buffer[256], defString[512], *varData; Tcl_Interp *tcl = NULL; double dVal; if(argc < 5){ SCWrite(pCon,"ERROR: insufficient number of arguments to array", eError); return; } tcl = InterpGetTcl(pSics); assert(tcl != NULL); /* get array length */ status = Tcl_GetInt(tcl,argv[4],&length); if(status != TCL_OK){ sprintf(buffer,"ERROR: failed to convert %s to integer",argv[4]); SCWrite(pCon,buffer,eError); return; } /* allocate */ if(length > 0){ data = (float *)malloc(length*sizeof(float)); } if(data == NULL){ SCWrite(pCon,"ERROR: out of memory or invalid length",eError); return; } memset(data,0,length*sizeof(float)); /* try getting data */ for(i = 0; i < length; i++){ sprintf(num,"%d",i); varData = (char *)Tcl_GetVar2(tcl,argv[3],num,0); if(varData != NULL){ status = Tcl_GetDouble(tcl,varData,&dVal); if(status != TCL_OK){ sprintf(buffer,"ERROR: failed to convert %s to double", varData); SCWrite(pCon,buffer,eError); } data[i] = (float)dVal; } else { snprintf(buffer,254,"WARNING: failed to find array element %d", i); SCWrite(pCon,buffer,eError); } } /* build definition string */ status = NXDdefget(self->dictHandle,argv[2],buffer,254); if(!status){ sprintf(buffer,"ERROR: alias %s for array not found", argv[2]); SCWrite(pCon,buffer,eError); free(data); return; } snprintf(defString,511,"%s -dim {%d} ",buffer,length); /* write it! */ status = NXDputdef(self->fileHandle,self->dictHandle,defString,data); if(status != NX_OK){ sprintf(buffer,"ERROR: failed to write array"); SCWrite(pCon,buffer,eError); } free(data); SCSendOK(pCon); } /*----------------------------------------------------------------------*/ static void putIntArray(SConnection *pCon, SicsInterp *pSics, pNXScript self, int argc, char *argv[]){ int *data = NULL; int length, i, status; char num[20]; char buffer[256], defString[512], *varData; Tcl_Interp *tcl = NULL; int iVal; if(argc < 5){ SCWrite(pCon,"ERROR: insufficient number of arguments to array", eError); return; } tcl = InterpGetTcl(pSics); assert(tcl != NULL); /* get array length */ status = Tcl_GetInt(tcl,argv[4],&length); if(status != TCL_OK){ sprintf(buffer,"ERROR: failed to convert %s to integer",argv[4]); SCWrite(pCon,buffer,eError); return; } /* allocate */ if(length > 0){ data = (int *)malloc(length*sizeof(int)); } if(data == NULL){ SCWrite(pCon,"ERROR: out of memory or invalid length",eError); return; } memset(data,0,length*sizeof(int)); /* try getting data */ for(i = 0; i < length; i++){ sprintf(num,"%d",i); varData = (char *)Tcl_GetVar2(tcl,argv[3],num,0); if(varData != NULL){ status = Tcl_GetInt(tcl,varData,&iVal); if(status != TCL_OK){ sprintf(buffer,"ERROR: failed to convert %s to int", varData); SCWrite(pCon,buffer,eError); } data[i] = iVal; } else { snprintf(buffer,254,"WARNING: failed to find array element %d", i); SCWrite(pCon,buffer,eError); } } /* build definition string */ status = NXDdefget(self->dictHandle,argv[2],buffer,254); if(!status){ sprintf(buffer,"ERROR: alias %s for array not found", argv[2]); SCWrite(pCon,buffer,eError); free(data); return; } snprintf(defString,511,"%s -dim {%d} ",buffer,length); /* write it! */ status = NXDputdef(self->fileHandle,self->dictHandle,defString,data); if(status != NX_OK){ sprintf(buffer,"ERROR: failed to write array"); SCWrite(pCon,buffer,eError); } free(data); SCSendOK(pCon); } /*----------------------------------------------------------------------*/ static void putGlobal(SConnection *pCon, SicsInterp *pSics, pNXScript self, int argc, char *argv[]){ char value[1024]; int status; if(argc < 4){ SCWrite(pCon,"ERROR: insufficient number of arguments to putglobal", eError); return; } Arg2Text(argc-3,&argv[3],value,1023); status = NXputattr(self->fileHandle,argv[2],value,strlen(value), NX_CHAR); if(status != NX_OK){ SCWrite(pCon,"ERROR: failed to write attribute",eError); } SCSendOK(pCon); } /*-----------------------------------------------------------------------*/ static int handlePut(SConnection *pCon, SicsInterp *pSics, pNXScript self, int argc, char *argv[]){ int status, iVal; char buffer[1024], defString[1024], numBuf[25]; double dVal; float fVal; /*============ */ if(strcmp(argv[1],"putfloat") == 0){ if(argc < 4){ SCWrite(pCon,"ERROR: insufficient number of arguments to putfloat", eError); return 1; } status = Tcl_GetDouble(InterpGetTcl(pSics),argv[3],&dVal); if(status != TCL_OK){ sprintf(buffer,"ERROR: failed to convert %s to float", argv[3]); SCWrite(pCon,buffer,eError); return 1; } fVal = (float)dVal; status = NXDputalias(self->fileHandle, self->dictHandle, argv[2],&fVal); if(status != NX_OK){ sprintf(buffer,"ERROR: failed to write %f to alias %s", fVal, argv[2]); SCWrite(pCon,buffer,eError); } return 1; } else if(strcmp(argv[1],"putint") == 0){ if(argc < 4){ SCWrite(pCon,"ERROR: insufficient number of arguments to putint", eError); return 1; } status = Tcl_GetInt(InterpGetTcl(pSics),argv[3],&iVal); if(status != TCL_OK){ sprintf(buffer,"ERROR: failed to convert %s to int", argv[3]); SCWrite(pCon,buffer,eError); return 1; } status = NXDputalias(self->fileHandle, self->dictHandle, argv[2],&iVal); if(status != NX_OK){ sprintf(buffer,"ERROR: failed to write %d to alias %s", iVal, argv[2]); SCWrite(pCon,buffer,eError); } return 1; } else if (strcmp(argv[1],"puttext") == 0){ /*====================*/ if(argc < 4){ SCWrite(pCon,"ERROR: insufficient number of arguments to puttext", eError); return 1; } Arg2Text(argc-3,&argv[3],buffer,1023); trim(buffer); status = NXDdefget(self->dictHandle,argv[2],defString,1023); if(status != NX_OK){ sprintf(buffer,"ERROR: alias %s not found in puttext", argv[2]); SCWrite(pCon,buffer,eError); return 1; } if(strlen(defString) < 900){ strcat(defString," -dim {"); sprintf(numBuf,"%d",strlen(buffer)+1); strcat(defString,numBuf); strcat(defString," }"); } else { SCWrite(pCon,"ERROR: out of definition string space in puttext", eError); return 1; } status = NXDputdef(self->fileHandle,self->dictHandle, defString,buffer); if(status != NX_OK){ sprintf(buffer,"ERROR: failed to write alias %s", argv[2]); SCWrite(pCon,buffer,eError); } return 1; } else if(strcmp(argv[1],"putmot") == 0){ /*=========== */ putMotor(pCon,pSics,self,argc,argv); return 1; } else if(strcmp(argv[1],"putcounter") == 0){ /* ================*/ putCounter(pCon,pSics,self, argc,argv); return 1; }else if(strcmp(argv[1],"puthm") == 0){ /*=================*/ putHistogramMemory(pCon,pSics,self,argc, argv); return 1; }else if(strcmp(argv[1],"puttimebinning") == 0){ /*=================*/ putTimeBinning(pCon,pSics,self,argc,argv); }else if(strcmp(argv[1],"putarray") == 0){ /*================*/ putArray(pCon,pSics,self,argc,argv); }else if(strcmp(argv[1],"putintarray") == 0){ /*================*/ putIntArray(pCon,pSics,self,argc,argv); }else if(strcmp(argv[1],"putglobal") == 0){ /*===============*/ putGlobal(pCon,pSics,self,argc,argv); }else if(strcmp(argv[1],"putsicsdata") == 0){ /*===============*/ putSicsData(pCon,pSics,self,argc,argv); } else { SCWrite(pCon,"ERROR: put command not recognised",eError); } return 1; } /*----------------------------------------------------------------------*/ static void makeLink(SConnection *pCon, SicsInterp *pSics, pNXScript self, int argc, char *argv[]){ int status; char pBueffel[256]; if(argc < 4){ SCWrite(pCon,"ERROR: insufficient number of arguments to makelink", eError); return; } status = NXDaliaslink(self->fileHandle, self->dictHandle, argv[2],argv[3]); if(status != NX_OK){ snprintf(pBueffel,255,"ERROR: linking %s against %s failed", argv[2], argv[3]); SCWrite(pCon,pBueffel,eError); return; } SCSendOK(pCon); } /*----------------------------------------------------------------------*/ static void updateDictVar(SConnection *pCon, pNXScript self, int argc, char *argv[]){ int status; if(self->dictHandle == NULL){ SCWrite(pCon,"ERROR: cannot update variable, dictionary not open", eError); return; } if(argc < 4){ SCWrite(pCon,"ERROR: insufficient number of arguments to updateDictVar", eError); return; } NXDupdate(self->dictHandle,argv[2],argv[3]); } /*-----------------------------------------------------------------------*/ int NXScriptAction(SConnection *pCon, SicsInterp *pSics, void *pData, int argc, char *argv[]){ pNXScript self = (pNXScript)pData; char *pFile = NULL; int status; /* preliminary checks */ assert(self); if(!SCMatchRights(pCon,usUser)){ return 1; } if(argc < 2){ SCWrite(pCon,"ERROR: no keyword found",eError); return 1; } strtolower(argv[1]); if(strcmp(argv[1],"makefilename") == 0){ pFile = makeFilename(pSics,pCon); if(pFile != NULL){ SCWrite(pCon,pFile,eValue); free(pFile); return 1; } else { SCWrite(pCon,"ERROR: failed to create filename",eError); return 0; } } else if(strcmp(argv[1],"divisor") == 0){ if(argc < 3) { SCWrite(pCon,"ERROR: no diviso found",eError); return 1; } if(!SCMatchRights(pCon,usMugger)){ return 1; } self->timeDivisor = atoi(argv[2]); return 1; } status = handleFileOperations(pCon,self,argc,argv); if(status < 0){ return 0; } else if(status == 1){ return 1; } /* if we are here, we can only continue if files are open */ if(self->fileHandle == NULL || self->dictHandle == NULL){ SCWrite(pCon,"ERROR: cannot write, files not open",eError); return 1; } if(strcmp(argv[1],"updatedictvar") == 0){ updateDictVar(pCon,self,argc,argv); return 1; } if(strstr(argv[1],"put") != NULL){ handlePut(pCon,pSics,self,argc,argv); return 1; } if(strcmp(argv[1],"makelink") == 0){ makeLink(pCon,pSics,self,argc,argv); return 1; } return 1; } /*=============== make it ==============================================*/ static void KillNXScript(void *pData){ pNXScript self = (pNXScript)pData; if(self == NULL){ return; } if(self->pDes){ DeleteDescriptor(self->pDes); } if(self->fileHandle){ NXclose(&self->fileHandle); } if(self->dictHandle){ NXDclose(self->dictHandle, NULL); } free(self); } /*----------------------------------------------------------------------*/ int MakeNXScript(SConnection *pCon, SicsInterp *pSics, void *pData, int argc, char *argv[]){ pNXScript self = NULL; int status; self = (pNXScript)malloc(sizeof(NXScript)); if(self == NULL){ SCWrite(pCon,"ERROR: no memory for NXscript creation",eError); return 0; } memset(self,0,sizeof(NXScript)); self->pDes = CreateDescriptor("NXScript"); if(self->pDes == NULL){ SCWrite(pCon,"ERROR: no memory for NXscript creation",eError); free(self); return 0; } self->timeDivisor = 1; /* create with with a default name if none specified */ if(argc > 1){ status = AddCommand(pSics,argv[1],NXScriptAction,KillNXScript,self); } else { status = AddCommand(pSics,"nxscript",NXScriptAction,KillNXScript,self); } if(!status){ SCWrite(pCon,"ERROR: duplicate NXScript object not created",eError); KillNXScript(self); return 0; } return 1; }