- Added makefile_slinux
- Changed mesure to be a silver bullet SKIPPED: psi/ecbcounter.c psi/ecbdriv.c psi/el734hp.c psi/el737hpdriv.c psi/fowrite.c psi/nextrics.c psi/tasscan.c
This commit is contained in:
703
mesure.c
703
mesure.c
@@ -1,12 +1,13 @@
|
||||
/*-------------------------------------------------------------------------
|
||||
M E S U R E
|
||||
|
||||
An object for doing simple four circle diffractometer measurements with
|
||||
An object for doing four circle diffractometer measurements with
|
||||
a single counter.
|
||||
|
||||
copyright: see copyright.h
|
||||
|
||||
Mark Koennecke, April 1998
|
||||
heavily reworked: Mark Koennecke, February-March 2005
|
||||
---------------------------------------------------------------------------*/
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
@@ -19,6 +20,7 @@
|
||||
#include "o2t.h"
|
||||
#include "scan.h"
|
||||
#include "scan.i"
|
||||
#include "stdscan.h"
|
||||
#include "danu.h"
|
||||
#include "integrate.h"
|
||||
#include "hkl.h"
|
||||
@@ -26,6 +28,7 @@
|
||||
#include "evcontroller.h"
|
||||
#include "mesure.h"
|
||||
#include "nxscript.h"
|
||||
#include "fourtable.h"
|
||||
#include "lld.h"
|
||||
|
||||
extern void SNXFormatTime(char *pBueffel, int iLen);
|
||||
@@ -50,7 +53,6 @@
|
||||
and reflection driving */
|
||||
pMotor pOmega; /* motor for omega scans */
|
||||
char *pCOmega; /* name of omega motor */
|
||||
char *pO2T; /* name of omega 2 theta virtual motor */
|
||||
char *pFileRoot; /* where to write files */
|
||||
pDataNumber pDanu; /* where to get data file number */
|
||||
FILE *fRefl; /* reflection profile file */
|
||||
@@ -63,24 +65,77 @@
|
||||
int np; /* number of scan points */
|
||||
float fPreset; /* counting preset */
|
||||
float fStep; /* omega step widths */
|
||||
int iMode; /* omega or omega 2 theta scan flag */
|
||||
long *lCounts; /* array to store counting values */
|
||||
float fPosition[4]; /* the real positions after driving */
|
||||
int iCompact; /* true if compact scan ouput. */
|
||||
int psiMode; /* 1 for psi scan mode, 0 else */
|
||||
int stepList; /* a list of stepwidth ranges */
|
||||
int weak; /* weak flag: remeasure weak reflections */
|
||||
long weakThreshold; /* threshold when a peak is so weak that is has to
|
||||
remeasured */
|
||||
int fastScan; /* flag for using fastscans for scanning reflections */
|
||||
int psiMode; /* 1 for psi scan mode, 0 else */
|
||||
int stepTable; /* mapping of two theta ranges to step width and
|
||||
variable to scan */
|
||||
} Mesure;
|
||||
/*---------------------------------------------------------------------
|
||||
Entries for the stepwidth range list
|
||||
----------------------------------------------------------------------*/
|
||||
typedef struct {
|
||||
float start;
|
||||
float end;
|
||||
float stepWidth;
|
||||
}StepEntry;
|
||||
/*-------------------------------------------------------------------------*/
|
||||
static int SaveMesure(void *pData, char *name, FILE *fd)
|
||||
{
|
||||
pMesure self = (pMesure)pData;
|
||||
|
||||
fprintf(fd,"#Four Circle Dataset Module %s\n",name);
|
||||
if(self->CountMode == eTimer)
|
||||
{
|
||||
fprintf(fd,"%s countmode timer\n",name);
|
||||
}
|
||||
else
|
||||
{
|
||||
fprintf(fd,"%s countmode monitor\n",name);
|
||||
}
|
||||
fprintf(fd,"%s np %d\n", name, self->np);
|
||||
fprintf(fd,"%s preset %f\n", name, self->fPreset);
|
||||
fprintf(fd,"%s step %f\n", name, self->fStep);
|
||||
fprintf(fd,"%s weakthreshold %f\n", name, self->weakThreshold);
|
||||
fprintf(fd,"%s compact %d\n", name, self->iCompact);
|
||||
fprintf(fd,"%s weak %d\n", name, self->weak);
|
||||
fprintf(fd,"%s fastscan %d\n", name, self->fastScan);
|
||||
SaveFourCircleTable(self->stepTable,name,fd);
|
||||
return 1;
|
||||
}
|
||||
/*-------------------------------------------------------------------------*/
|
||||
static void ListMesure(pMesure self, char *name, SConnection *pCon)
|
||||
{
|
||||
Tcl_DString list;
|
||||
char pBuffer[132];
|
||||
|
||||
Tcl_DStringInit(&list);
|
||||
if(self->CountMode == eTimer)
|
||||
{
|
||||
snprintf(pBuffer,131,"%s.countmode timer\n",name);
|
||||
}
|
||||
else
|
||||
{
|
||||
snprintf(pBuffer,131,"%s.countmode monitor\n",name);
|
||||
}
|
||||
Tcl_DStringAppend(&list,pBuffer,-1);
|
||||
snprintf(pBuffer,131,"%s.np %d\n", name, self->np);
|
||||
Tcl_DStringAppend(&list,pBuffer,-1);
|
||||
snprintf(pBuffer,131,"%s.preset %f\n", name, self->fPreset);
|
||||
Tcl_DStringAppend(&list,pBuffer,-1);
|
||||
snprintf(pBuffer,131,"%s.step %f\n", name, self->fStep);
|
||||
Tcl_DStringAppend(&list,pBuffer,-1);
|
||||
snprintf(pBuffer,131,"%s.weakthreshold %f\n", name, self->weakThreshold);
|
||||
Tcl_DStringAppend(&list,pBuffer,-1);
|
||||
snprintf(pBuffer,131,"%s.compact %d\n", name, self->iCompact);
|
||||
Tcl_DStringAppend(&list,pBuffer,-1);
|
||||
snprintf(pBuffer,131,"%s.weak %d\n", name, self->weak);
|
||||
Tcl_DStringAppend(&list,pBuffer,-1);
|
||||
snprintf(pBuffer,131,"%s.fastscan %d\n", name, self->fastScan);
|
||||
Tcl_DStringAppend(&list,pBuffer,-1);
|
||||
SCWrite(pCon,Tcl_DStringValue(&list),eValue);
|
||||
Tcl_DStringFree(&list);
|
||||
}
|
||||
/*--------------------------------------------------------------------------*/
|
||||
pMesure CreateMesure(pHKL pCryst, pScanData pScanner, pMotor pOmega,
|
||||
char *pOm, char *po2t, char *pFileRoot,
|
||||
char *pOm, char *pFileRoot,
|
||||
pDataNumber pDanu)
|
||||
{
|
||||
pMesure pNew = NULL;
|
||||
@@ -100,6 +155,7 @@ typedef struct {
|
||||
memset(pNew,0,sizeof(Mesure));
|
||||
|
||||
pNew->pDes = CreateDescriptor("Mesure");
|
||||
pNew->pDes->SaveStatus = SaveMesure;
|
||||
pNew->pCall = CreateCallBackInterface();
|
||||
if( !pNew->pDes || !pNew->pCall)
|
||||
{
|
||||
@@ -112,7 +168,6 @@ typedef struct {
|
||||
pNew->pCryst = pCryst;
|
||||
pNew->pOmega = pOmega;
|
||||
pNew->pCOmega = strdup(pOm);
|
||||
pNew->pO2T = strdup(po2t);
|
||||
pNew->pFileRoot = strdup(pFileRoot);
|
||||
pNew->pDanu = pDanu;
|
||||
pNew->iCount = 0;
|
||||
@@ -120,14 +175,16 @@ typedef struct {
|
||||
pNew->np = 50;
|
||||
pNew->fStep = 0.05;
|
||||
pNew->fPreset = 2;
|
||||
pNew->iMode = 0;
|
||||
pNew->iCompact = 1;
|
||||
pNew->weak = 0;
|
||||
pNew->weakThreshold = 99999;
|
||||
pNew->fastScan = 0;
|
||||
pNew->psiMode = 0;
|
||||
#ifdef MESSDEBUG
|
||||
pNew->lCounts = (long *)malloc(90*sizeof(long));
|
||||
#endif
|
||||
pNew->lCounts = (long *)malloc(50*sizeof(long));
|
||||
pNew->stepList = LLDcreate(sizeof(StepEntry));
|
||||
pNew->stepTable = MakeFourCircleTable();
|
||||
return pNew;
|
||||
}
|
||||
/*------------------------------------------------------------------------*/
|
||||
@@ -151,13 +208,11 @@ typedef struct {
|
||||
free(self->pFileRoot);
|
||||
if(self->pCOmega)
|
||||
free(self->pCOmega);
|
||||
if(self->pO2T)
|
||||
free(self->pO2T);
|
||||
if(self->fRefl)
|
||||
MesureClose(self);
|
||||
if(self->lCounts)
|
||||
free(self->lCounts);
|
||||
LLDdelete(self->stepList);
|
||||
DeleteFourCircleTable(self->stepTable);
|
||||
free(self);
|
||||
}
|
||||
/*------------------------------------------------------------------------*/
|
||||
@@ -179,9 +234,9 @@ typedef struct {
|
||||
assert(pSics);
|
||||
|
||||
/* check no of parameters
|
||||
inicom name hkl scan omega o2t root danu
|
||||
inicom name hkl scan omega root danu
|
||||
*/
|
||||
if(argc < 8)
|
||||
if(argc < 7)
|
||||
{
|
||||
SCWrite(pCon,
|
||||
"ERROR: Insufficient number of parameters to MesureFactory",eError);
|
||||
@@ -237,28 +292,8 @@ typedef struct {
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* o2t */
|
||||
pCom = FindCommand(pSics,argv[5]);
|
||||
if(pCom)
|
||||
{
|
||||
pDum = (pDummy)pCom->pData;
|
||||
if(pDum)
|
||||
{
|
||||
if(strcmp(pDum->pDescriptor->name,"Omega2Theta") == 0)
|
||||
{
|
||||
pO2T = (pSicsO2T)pCom->pData;
|
||||
}
|
||||
}
|
||||
}
|
||||
if(!pO2T)
|
||||
{
|
||||
sprintf(pBueffel,"ERROR: %s is no omega 2 theta object",argv[5]);
|
||||
SCWrite(pCon,pBueffel,eError);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Data Number */
|
||||
pCom = FindCommand(pSics,argv[7]);
|
||||
pCom = FindCommand(pSics,argv[6]);
|
||||
if(pCom)
|
||||
{
|
||||
pDum = (pDummy)pCom->pData;
|
||||
@@ -272,13 +307,13 @@ typedef struct {
|
||||
}
|
||||
if(!pDanu)
|
||||
{
|
||||
sprintf(pBueffel,"ERROR: %s is no DataNumber object",argv[7]);
|
||||
sprintf(pBueffel,"ERROR: %s is no DataNumber object",argv[6]);
|
||||
SCWrite(pCon,pBueffel,eError);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* finally create the thing */
|
||||
pNew = CreateMesure(pCryst,pScan,pMot,argv[4],argv[5],argv[6],pDanu);
|
||||
pNew = CreateMesure(pCryst,pScan,pMot,argv[4],argv[5],pDanu);
|
||||
if(!pNew)
|
||||
{
|
||||
SCWrite(pCon,"ERROR: no memory in MesureFactory",eError);
|
||||
@@ -359,201 +394,220 @@ typedef struct {
|
||||
|
||||
return 1;
|
||||
}
|
||||
/*------------------------------------------------------------------------*/
|
||||
static void addStepRange(pMesure self, float start, float end, float step)
|
||||
/*-------------------------------------------------------------------------
|
||||
This is slightly tricky: the crystallography module has a scan tolerance.
|
||||
This is supposed to be automatically set. In order to do so, I need
|
||||
the step width which in turn is dependent on two theta. Therefore I calculate
|
||||
two times: the first time with a scan tolerance of 0 to get two theta, the
|
||||
second time with teh scan tolerance ste to a decent value to get the
|
||||
real thing.
|
||||
---------------------------------------------------------------------------*/
|
||||
static int MesureCalculateSettings(pMesure self, float fHKL[3], float fSet[4],
|
||||
float fPsi, SConnection *pCon)
|
||||
{
|
||||
StepEntry se;
|
||||
assert(self != NULL);
|
||||
|
||||
se.start = start;
|
||||
se.end = end;
|
||||
se.stepWidth = step;
|
||||
LLDnodeAppendFrom(self->stepList,&se);
|
||||
}
|
||||
/*------------------------------------------------------------------------*/
|
||||
static float determineStepWidth(pMesure self, float two_theta)
|
||||
{
|
||||
float stepWidth;
|
||||
StepEntry se;
|
||||
int iRet;
|
||||
|
||||
assert(self != NULL);
|
||||
|
||||
stepWidth = self->fStep;
|
||||
iRet = LLDnodePtr2First(self->stepList);
|
||||
while(iRet != 0)
|
||||
int status;
|
||||
float step, tolerance;
|
||||
|
||||
SetHKLScanTolerance(self->pCryst,.0);
|
||||
status = CalculateSettings(self->pCryst,fHKL,fPsi,0,fSet,pCon);
|
||||
if(!status)
|
||||
{
|
||||
LLDnodeDataTo(self->stepList,&se);
|
||||
if(two_theta > se.start && two_theta < se.end)
|
||||
{
|
||||
stepWidth = se.stepWidth;
|
||||
break;
|
||||
}
|
||||
iRet = LLDnodePtr2Next(self->stepList);
|
||||
return status;
|
||||
}
|
||||
return stepWidth;
|
||||
step = GetFourCircleStep(self->stepTable, fSet[0]);
|
||||
if(step < -900.){
|
||||
step = self->fStep;
|
||||
}
|
||||
tolerance = (step * (float)self->np)/2. + .2;
|
||||
SetHKLScanTolerance(self->pCryst,tolerance);
|
||||
return CalculateSettings(self->pCryst,fHKL,fPsi,0,fSet,pCon);
|
||||
}
|
||||
/*--------------------------------------------------------------------------*/
|
||||
int MesureReflection(pMesure self, float fHKL[3], float fPsi,
|
||||
SConnection *pCon)
|
||||
{
|
||||
int iRet, i;
|
||||
float fStart, stepWidth;
|
||||
float fDelta, fSet[4];
|
||||
char pBueffel[132];
|
||||
int iRet;
|
||||
float fSet[4];
|
||||
|
||||
assert(self);
|
||||
|
||||
/* drive to reflection */
|
||||
iRet = DriveHKL(self->pCryst,fHKL,fPsi,0,pCon);
|
||||
|
||||
iRet = MesureCalculateSettings(self,fHKL,fSet,fPsi,pCon);
|
||||
if(!iRet)
|
||||
{
|
||||
return iRet;
|
||||
}
|
||||
return MesureGenReflection(self,fHKL,fSet,pCon);
|
||||
}
|
||||
/*-----------------------------------------------------------------------*/
|
||||
static int DriveToReflection(pMesure self, float fSet[4], SConnection *pCon)
|
||||
{
|
||||
int iRet, i;
|
||||
float fDelta;
|
||||
char pBueffel[132];
|
||||
|
||||
/* store achieved position for reporting */
|
||||
iRet = GetCurrentPosition(self->pCryst,pCon,self->fPosition);
|
||||
if(iRet != 1)
|
||||
{
|
||||
return iRet;
|
||||
}
|
||||
iRet = DriveSettings(self->pCryst,fSet,pCon);
|
||||
if(!iRet)
|
||||
{
|
||||
return iRet;
|
||||
}
|
||||
|
||||
/*
|
||||
check if we are really there.
|
||||
*/
|
||||
CalculateSettings(self->pCryst,fHKL,fPsi,0,fSet,pCon);
|
||||
for(i = 0; i < 4; i++)
|
||||
{
|
||||
fDelta = fSet[i] - self->fPosition[i];
|
||||
if(fDelta < 0.)
|
||||
fDelta = -fDelta;
|
||||
if(fDelta > ANGERR)
|
||||
{
|
||||
sprintf(pBueffel,
|
||||
"ERROR: angle %d positioned badly, aborting Reflection",
|
||||
i);
|
||||
SCWrite(pCon,pBueffel,eError);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
/* calculate scan start */
|
||||
iRet = MotorGetSoftPosition(self->pOmega,pCon,&fStart);
|
||||
if(!iRet)
|
||||
{
|
||||
return iRet;
|
||||
}
|
||||
stepWidth = determineStepWidth(self,self->fPosition[0]);
|
||||
if(stepWidth != self->fStep)
|
||||
{
|
||||
snprintf(pBueffel,130,"Using stepwidth %f",stepWidth);
|
||||
SCWrite(pCon,pBueffel,eWarning);
|
||||
}
|
||||
fStart -= (self->np/2)*stepWidth;
|
||||
|
||||
/* set the scan up */
|
||||
ClearScanVar(self->pScanner);
|
||||
if(self->iMode == 0)
|
||||
{
|
||||
AddScanVar(self->pScanner, pServ->pSics,pCon,self->pCOmega,
|
||||
/* store achieved position for reporting */
|
||||
iRet = GetCurrentPosition(self->pCryst,pCon,self->fPosition);
|
||||
if(iRet != 1)
|
||||
{
|
||||
return iRet;
|
||||
}
|
||||
|
||||
/*
|
||||
check if we are really there.
|
||||
*/
|
||||
for(i = 0; i < 4; i++)
|
||||
{
|
||||
fDelta = fSet[i] - self->fPosition[i];
|
||||
if(fDelta < 0.)
|
||||
fDelta = -fDelta;
|
||||
if(fDelta > ANGERR)
|
||||
{
|
||||
snprintf(pBueffel,131,
|
||||
"ERROR: angle %d positioned badly, aborting Reflection",
|
||||
i);
|
||||
SCWrite(pCon,pBueffel,eError);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
/*-----------------------------------------------------------------------
|
||||
test if this scan has to be remeasured because it is weak
|
||||
------------------------------------------------------------------------*/
|
||||
int weakScan(pMesure self)
|
||||
{
|
||||
int i;
|
||||
long low = 99999, high = -99999;
|
||||
|
||||
/*
|
||||
ths scan is always OK if we do not test for weak conditions
|
||||
*/
|
||||
if(self->weak == 0){
|
||||
return 0;
|
||||
}
|
||||
GetScanCounts(self->pScanner,self->lCounts,self->np);
|
||||
for(i = 0; i < self->np; i++)
|
||||
{
|
||||
if(self->lCounts[i] < low)
|
||||
{
|
||||
low = self->lCounts[i];
|
||||
}
|
||||
if(self->lCounts[i] > high)
|
||||
{
|
||||
high = self->lCounts[i];
|
||||
}
|
||||
}
|
||||
/*
|
||||
I am using the weakest point here as a rough estimate of
|
||||
the background
|
||||
*/
|
||||
if(high - 2 * low > self->weakThreshold)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
/*------------------------------------------------------------------------*/
|
||||
static int ScanReflection(pMesure self, float twoTheta, SConnection *pCon)
|
||||
{
|
||||
float fStart, stepWidth;
|
||||
int iRet;
|
||||
char pBueffel[132];
|
||||
char *scanVar = NULL;
|
||||
|
||||
/* calculate scan start */
|
||||
iRet = MotorGetSoftPosition(self->pOmega,pCon,&fStart);
|
||||
if(!iRet)
|
||||
{
|
||||
return iRet;
|
||||
}
|
||||
scanVar = GetFourCircleScanVar(self->stepTable,(double)twoTheta);
|
||||
if(strcmp(scanVar,"NOT FOUND") == 0)
|
||||
{
|
||||
free(scanVar);
|
||||
scanVar = strdup(self->pCOmega);
|
||||
stepWidth = self->fStep;
|
||||
} else {
|
||||
stepWidth = GetFourCircleStep(self->stepTable,(double)twoTheta);
|
||||
}
|
||||
|
||||
if(stepWidth != self->fStep)
|
||||
{
|
||||
snprintf(pBueffel,130,"Using stepwidth %f",stepWidth);
|
||||
SCWrite(pCon,pBueffel,eWarning);
|
||||
}
|
||||
fStart -= (self->np/2)*stepWidth;
|
||||
|
||||
/* set the scan up */
|
||||
ClearScanVar(self->pScanner);
|
||||
AddScanVar(self->pScanner, pServ->pSics,pCon,scanVar,
|
||||
fStart, stepWidth);
|
||||
free(scanVar);
|
||||
|
||||
/* do the scan */
|
||||
if(self->iCompact)
|
||||
{
|
||||
self->pScanner->CollectScanData = CompactScanData;
|
||||
}
|
||||
if(self->fastScan >= 1)
|
||||
{
|
||||
self->pScanner->ScanDrive = ScanFastDrive;
|
||||
}
|
||||
iRet = SilentScan(self->pScanner,self->np,self->CountMode,
|
||||
self->fPreset,pServ->pSics,pCon);
|
||||
if(weakScan(self))
|
||||
{
|
||||
/*
|
||||
look for interrupts before restarting scan
|
||||
*/
|
||||
if(iRet == 0)
|
||||
{
|
||||
if(SCGetInterrupt(pCon) >= eAbortBatch)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
AddScanVar(self->pScanner, pServ->pSics,pCon,self->pO2T,
|
||||
fStart, stepWidth);
|
||||
SCSetInterrupt(pCon,eContinue);
|
||||
}
|
||||
|
||||
/* do the scan */
|
||||
if(self->iCompact)
|
||||
{
|
||||
self->pScanner->CollectScanData = CompactScanData;
|
||||
}
|
||||
iRet = SilentScan(self->pScanner,self->np,self->CountMode,
|
||||
self->fPreset,pServ->pSics,pCon);
|
||||
}
|
||||
/*
|
||||
redo scan with preset * 5
|
||||
*/
|
||||
SCWrite(pCon,"Remeasuring weak reflection",eWarning);
|
||||
iRet = SilentScan(self->pScanner,self->np,self->CountMode,
|
||||
self->fPreset*5.,pServ->pSics,pCon);
|
||||
|
||||
ResetScanFunctions(self->pScanner);
|
||||
|
||||
return iRet;
|
||||
}
|
||||
}
|
||||
ResetScanFunctions(self->pScanner);
|
||||
return iRet;
|
||||
}
|
||||
/*------------------------------------------------------------------------*/
|
||||
int MesureGenReflection(pMesure self, float fHKL[3], float fSet[4],
|
||||
SConnection *pCon)
|
||||
{
|
||||
|
||||
int iRet, i;
|
||||
float fStart, fDelta, stepWidth;
|
||||
char pBueffel[132];
|
||||
|
||||
assert(self);
|
||||
|
||||
/* drive to reflection */
|
||||
iRet = DriveSettings(self->pCryst,fSet,pCon);
|
||||
iRet = DriveToReflection(self,fSet,pCon);
|
||||
if(!iRet)
|
||||
{
|
||||
return iRet;
|
||||
return iRet;
|
||||
}
|
||||
|
||||
/* store achieved position for reporting */
|
||||
iRet = GetCurrentPosition(self->pCryst,pCon,self->fPosition);
|
||||
if(iRet != 1)
|
||||
{
|
||||
return iRet;
|
||||
}
|
||||
|
||||
/*
|
||||
check if we are really there.
|
||||
*/
|
||||
for(i = 0; i < 4; i++)
|
||||
{
|
||||
fDelta = fSet[i] - self->fPosition[i];
|
||||
if(fDelta < 0.)
|
||||
fDelta = -fDelta;
|
||||
if(fDelta > ANGERR)
|
||||
{
|
||||
sprintf(pBueffel,
|
||||
"ERROR: angle %d positioned badly, aborting Reflection",
|
||||
i);
|
||||
SCWrite(pCon,pBueffel,eError);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
/* calculate scan start */
|
||||
iRet = MotorGetSoftPosition(self->pOmega,pCon,&fStart);
|
||||
if(!iRet)
|
||||
{
|
||||
return iRet;
|
||||
}
|
||||
stepWidth = determineStepWidth(self,self->fPosition[0]);
|
||||
if(stepWidth != self->fStep)
|
||||
{
|
||||
snprintf(pBueffel,130,"Using stepwidth %f",stepWidth);
|
||||
SCWrite(pCon,pBueffel,eWarning);
|
||||
}
|
||||
fStart -= (self->np/2)*stepWidth;
|
||||
|
||||
/* set the scan up */
|
||||
ClearScanVar(self->pScanner);
|
||||
if(self->iMode == 0)
|
||||
{
|
||||
AddScanVar(self->pScanner, pServ->pSics,pCon,self->pCOmega,
|
||||
fStart, stepWidth);
|
||||
}
|
||||
else
|
||||
{
|
||||
AddScanVar(self->pScanner, pServ->pSics,pCon,self->pO2T,
|
||||
fStart, stepWidth);
|
||||
}
|
||||
|
||||
/* do the scan */
|
||||
if(self->iCompact)
|
||||
{
|
||||
self->pScanner->CollectScanData = CompactScanData;
|
||||
}
|
||||
iRet = SilentScan(self->pScanner,self->np,self->CountMode,
|
||||
self->fPreset,pServ->pSics,pCon);
|
||||
ResetScanFunctions(self->pScanner);
|
||||
iRet = ScanReflection(self,fSet[0],pCon);
|
||||
|
||||
return iRet;
|
||||
}
|
||||
@@ -976,6 +1030,65 @@ static float determineStepWidth(pMesure self, float two_theta)
|
||||
fclose(fd);
|
||||
return 1;
|
||||
}
|
||||
/*------------------------------------------------------------------------*/
|
||||
int TestFile(pMesure self, char *pFile, SConnection *pCon)
|
||||
{
|
||||
FILE *fd = NULL;
|
||||
char pBueffel[512], pError[256];
|
||||
int i, iRet;
|
||||
float fHKL[3], fSet[4], fPsi = .0;
|
||||
int count = 0, good = 0;
|
||||
|
||||
assert(self);
|
||||
assert(pCon);
|
||||
|
||||
/* well before doing a thing, open the list file */
|
||||
fd = fopen(pFile,"r");
|
||||
if(!fd)
|
||||
{
|
||||
sprintf(pBueffel,"ERROR: reflection file %s NOT found!",pFile);
|
||||
SCWrite(pCon,pBueffel,eError);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if(self->psiMode > 0){
|
||||
SCWrite(pCon,"WARNING: measuring in psi mode",eWarning);
|
||||
}
|
||||
|
||||
/* loop through space and test! */
|
||||
while(fgets(pBueffel,510,fd) != NULL)
|
||||
{
|
||||
for(i = 0; i < 3;i++)
|
||||
fHKL[i] = 0.;
|
||||
if(self->psiMode > 0){
|
||||
iRet = sscanf(pBueffel,"%f%f%f%f",
|
||||
&fHKL[0],&fHKL[1],&fHKL[2],&fPsi);
|
||||
if(iRet != 4){
|
||||
snprintf(pError,255,"WARNING: skipping bad line %s",pBueffel);
|
||||
SCWrite(pCon,pError,eWarning);
|
||||
continue;
|
||||
}
|
||||
} else {
|
||||
iRet = sscanf(pBueffel,"%f%f%f",&fHKL[0],&fHKL[1],&fHKL[2]);
|
||||
if(iRet != 3){
|
||||
snprintf(pError,255,"WARNING: skipping bad line %s",pBueffel);
|
||||
SCWrite(pCon,pError,eWarning);
|
||||
continue;
|
||||
}
|
||||
}
|
||||
count++;
|
||||
iRet = MesureCalculateSettings(self,fHKL,fSet,fPsi,pCon);
|
||||
if(iRet == 1)
|
||||
{
|
||||
good++;
|
||||
}
|
||||
}
|
||||
fclose(fd);
|
||||
snprintf(pBueffel,511,"Of %d reflections on file, %d are good and %d are rotten",
|
||||
count,good,count-good);
|
||||
SCWrite(pCon,pBueffel,eValue);
|
||||
return 1;
|
||||
}
|
||||
/*------------------------------------------------------------------------*/
|
||||
int MesureGenFile(pMesure self, char *pFile, int iSkip, SConnection *pCon)
|
||||
{
|
||||
@@ -1078,23 +1191,16 @@ static float determineStepWidth(pMesure self, float two_theta)
|
||||
self->fStep = fVal;
|
||||
return 1;
|
||||
}
|
||||
else if(strcmp(name,"weakthreshold") == 0)
|
||||
{
|
||||
self->weakThreshold = (long)nintf(fVal);
|
||||
return 1;
|
||||
}
|
||||
else if(strcmp(name,"preset") == 0)
|
||||
{
|
||||
self->fPreset = fVal;
|
||||
return 1;
|
||||
}
|
||||
else if(strcmp(name,"mode") == 0)
|
||||
{
|
||||
if(fVal <= 0)
|
||||
{
|
||||
self->iMode = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
self->iMode = 1;
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
else if(strcmp(name,"countmode") == 0)
|
||||
{
|
||||
if(fVal < 0.05)
|
||||
@@ -1119,6 +1225,30 @@ static float determineStepWidth(pMesure self, float two_theta)
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
else if(strcmp(name,"weak") == 0)
|
||||
{
|
||||
if(fVal >= 1.)
|
||||
{
|
||||
self->weak = 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
self->weak = 0;
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
else if(strcmp(name,"fastscan") == 0)
|
||||
{
|
||||
if(fVal >= 1.)
|
||||
{
|
||||
self->fastScan = 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
self->fastScan = 0;
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
else if(strcmp(name,"psimode") == 0)
|
||||
{
|
||||
if(fVal >= 1.)
|
||||
@@ -1149,9 +1279,9 @@ static float determineStepWidth(pMesure self, float two_theta)
|
||||
*fVal = self->fStep;
|
||||
return 1;
|
||||
}
|
||||
else if(strcmp(name,"mode") == 0)
|
||||
else if(strcmp(name,"weakthreshold") == 0)
|
||||
{
|
||||
*fVal = self->iMode;
|
||||
*fVal = (float)self->weakThreshold;
|
||||
return 1;
|
||||
}
|
||||
else if(strcmp(name,"preset") == 0)
|
||||
@@ -1176,6 +1306,16 @@ static float determineStepWidth(pMesure self, float two_theta)
|
||||
*fVal = self->iCompact;
|
||||
return 1;
|
||||
}
|
||||
else if(strcmp(name,"fastscan") == 0)
|
||||
{
|
||||
*fVal = (float)self->fastScan;
|
||||
return 1;
|
||||
}
|
||||
else if(strcmp(name,"weak") == 0)
|
||||
{
|
||||
*fVal = (float)self->weak;
|
||||
return 1;
|
||||
}
|
||||
else if(strcmp(name,"psimode") == 0)
|
||||
{
|
||||
*fVal = self->psiMode;
|
||||
@@ -1190,7 +1330,7 @@ static float determineStepWidth(pMesure self, float two_theta)
|
||||
int MesureAction(SConnection *pCon, SicsInterp *pSics, void *pData,
|
||||
int argc, char *argv[])
|
||||
{
|
||||
int iRet, iSkip;
|
||||
int iRet, iSkip, err;
|
||||
char pBueffel[1024];
|
||||
pMesure self = NULL;
|
||||
double d;
|
||||
@@ -1206,6 +1346,15 @@ static float determineStepWidth(pMesure self, float two_theta)
|
||||
SCWrite(pCon,pBueffel,eError);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
catch table processing commands
|
||||
*/
|
||||
iRet = HandleFourCircleCommands(self->stepTable,pCon,argc,argv,&err);
|
||||
if(iRet == 1)
|
||||
{
|
||||
return err;
|
||||
}
|
||||
|
||||
strtolower(argv[1]);
|
||||
/*------ start */
|
||||
@@ -1222,6 +1371,11 @@ static float determineStepWidth(pMesure self, float two_theta)
|
||||
}
|
||||
return iRet;
|
||||
}
|
||||
/*----------- list*/
|
||||
else if(strcmp(argv[1],"list") == 0)
|
||||
{
|
||||
ListMesure(self,argv[0],pCon);
|
||||
}
|
||||
/*------ file */
|
||||
else if(strcmp(argv[1],"file") == 0)
|
||||
{
|
||||
@@ -1317,6 +1471,17 @@ static float determineStepWidth(pMesure self, float two_theta)
|
||||
}
|
||||
return iRet;
|
||||
}
|
||||
/*------- calc */
|
||||
else if(strcmp(argv[1],"calc") == 0)
|
||||
{
|
||||
if(argc < 3)
|
||||
{
|
||||
SCWrite(pCon,"ERROR: expected list file name as parameter for measure ",eError);
|
||||
return 0;
|
||||
}
|
||||
iRet = TestFile(self,argv[2],pCon);
|
||||
return iRet;
|
||||
}
|
||||
/*------- genlist */
|
||||
else if(strcmp(argv[1],"genlist") == 0)
|
||||
{
|
||||
@@ -1398,98 +1563,6 @@ static float determineStepWidth(pMesure self, float two_theta)
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
/*------- mode */
|
||||
if(strcmp(argv[1],"mode") == 0)
|
||||
{
|
||||
if(argc > 2) /* set case */
|
||||
{
|
||||
/* check rights */
|
||||
if(!SCMatchRights(pCon,usUser))
|
||||
{
|
||||
SCWrite(pCon,"ERROR: You are not aurhorised to do this!",eError);
|
||||
return 0;
|
||||
}
|
||||
if(strcmp(argv[2],"omega") == 0)
|
||||
{
|
||||
fVal = 0.;
|
||||
}
|
||||
else if(strcmp(argv[2],"omega2theta") == 0)
|
||||
{
|
||||
fVal = 1.;
|
||||
}
|
||||
else
|
||||
{
|
||||
SCWrite(pCon,"ERROR: Invalid parameter for mode",eError);
|
||||
return 0;
|
||||
}
|
||||
MesureSetPar(self,"mode",fVal);
|
||||
SCSendOK(pCon);
|
||||
return 1;
|
||||
}
|
||||
else /* get case */
|
||||
{
|
||||
MesureGetPar(self,"mode",&fVal);
|
||||
if(fVal < 0.05)
|
||||
{
|
||||
sprintf(pBueffel,"%s.countmode = omega",argv[0]);
|
||||
}
|
||||
else
|
||||
{
|
||||
sprintf(pBueffel,"%s.countmode = omega2theta", argv[0]);
|
||||
}
|
||||
SCWrite(pCon,pBueffel,eValue);
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
else if(strcmp(argv[1],"addrange") == 0)
|
||||
{
|
||||
if(argc < 5)
|
||||
{
|
||||
SCWrite(pCon,"ERROR: not enough arguments to addrange",eError);
|
||||
return 0;
|
||||
}
|
||||
if(!SCMatchRights(pCon,usUser))
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
iRet = Tcl_GetDouble(pSics->pTcl,argv[2],&d);
|
||||
if(iRet != TCL_OK)
|
||||
{
|
||||
snprintf(pBueffel,131,
|
||||
"ERROR: expected numeric value but got %s",argv[2]);
|
||||
SCWrite(pCon,pBueffel,eError);
|
||||
return 0;
|
||||
}
|
||||
start = (float)d;
|
||||
iRet = Tcl_GetDouble(pSics->pTcl,argv[3],&d);
|
||||
if(iRet != TCL_OK)
|
||||
{
|
||||
snprintf(pBueffel,131,
|
||||
"ERROR: expected numeric value but got %s",argv[3]);
|
||||
SCWrite(pCon,pBueffel,eError);
|
||||
return 0;
|
||||
}
|
||||
end = (float)d;
|
||||
iRet = Tcl_GetDouble(pSics->pTcl,argv[4],&d);
|
||||
if(iRet != TCL_OK)
|
||||
{
|
||||
snprintf(pBueffel,131,
|
||||
"ERROR: expected numeric value but got %s",argv[4]);
|
||||
SCWrite(pCon,pBueffel,eError);
|
||||
return 0;
|
||||
}
|
||||
step = (float)d;
|
||||
addStepRange(self,start,end,step);
|
||||
SCSendOK(pCon);
|
||||
return 1;
|
||||
}
|
||||
else if(strcmp(argv[1],"clearrange") == 0)
|
||||
{
|
||||
LLDdelete(self->stepList);
|
||||
self->stepList = LLDcreate(sizeof(StepEntry));
|
||||
SCSendOK(pCon);
|
||||
return 1;
|
||||
}
|
||||
/*------ can be other pars */
|
||||
else
|
||||
{
|
||||
@@ -1539,11 +1612,3 @@ static float determineStepWidth(pMesure self, float two_theta)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
Reference in New Issue
Block a user