#include <formatio.h>
#include "H1D.h"
#include "H2D.h"
#include <utility.h>
#include <ansi_c.h>
#include <cvirte.h>
#include <userint.h>
#include "vmusb_ctrl.h"
#include "daq_cvi.h"
static int p1, p2, p3;
static int daq_on;
static int plothandle[4]= {0,0,0, 0};
static int tfID;
static int controlID;
static int verbose;
static int timeout;
extern int ctrlcflag;
#define MAX_THREADS 10
static CmtThreadPoolHandle poolHandle = 0;
#define MAXCH 72
float gSum[6];
float gRawSum[6];
float gMax[6];
float gSumCluster[6];
float gNtdata[MAXCH*3];
int gNabove[5];
double gData[MAXCH]; // korigirani ADC ji
double gAdc[MAXCH]; // raw ADC ji
double gPedestals[MAXCH];
double gPeak[MAXCH];
double gPeakScaling;
double gThreshold;
typedef struct Channel {
int ix;
int iy;
int idx;
};
struct Channel m_geo_ch[16];
char strbuf[0xFF];
int gLog=0;
int printf(const char *format
, ...
) {
va_list aptr;
int ret;
FILE *flog;
SetCtrlVal(p1,P1_IO,strbuf);
if (gLog) {
flog
= fopen ("stdio.log", "a");
}
return(ret);
}
int __stdcall WinMain (HINSTANCE hInstance, HINSTANCE hPrevInstance,
LPSTR lpszCmdLine, int nCmdShow) {
if (InitCVIRTE (hInstance, 0, 0) == 0)
return -1; /* out of memory */
if ((p1 = LoadPanel (0, "vmusb_ctrl.uir", P1)) < 0)
return -1;
if ((p2 = LoadPanel (0, "vmusb_ctrl.uir", P2)) < 0)
return -1;
if ((p3 = LoadPanel (0, "vmusb_ctrl.uir", P3)) < 0)
return -1;
SetStdioPort (CVI_STDIO_WINDOW);
SetSleepPolicy(VAL_SLEEP_MORE);
CmtNewThreadPool (MAX_THREADS, &poolHandle);
DisplayPanel (p1);
RunUserInterface ();
DiscardPanel (p1);
DiscardPanel (p2);
DiscardPanel (p3);
return 0;
}
static void start_timer (double tout) {
timeout = 0;
SetCtrlAttribute (p1, P1_TIMER, ATTR_INTERVAL, tout);
SetCtrlAttribute (p1, P1_TIMER, ATTR_ENABLED, 1);
}
static void stop_timer ( void ) {
SetCtrlAttribute (p1, P1_TIMER, ATTR_ENABLED, 0);
//DRSSetTimeout();
}
int georead(){
int i;
for (i=0; i<64; i++) {
int row=i+1;
double val;
unsigned short sval;
GetTableCellVal (p3, P3_CGEO, MakePoint (3,row), &sval);
fThreshold[i]=sval;
GetTableCellVal (p3, P3_CGEO, MakePoint (4,row), &val);
gPeak[i]=val;
GetTableCellVal (p3, P3_CGEO, MakePoint (5,row), &val);
gPedestals[i]=val;
}
GetCtrlVal(p3, P3_PEAKSCALING, &gPeakScaling );
GetCtrlVal(p3, P3_GTHRESHOLD, &gThreshold );
for (i=0; i<16; i++) {
int row=i+1;
double val;
unsigned short sval, id;
GetTableCellVal (p3, P3_CGEO, MakePoint (1,row), &id);
GetTableCellVal (p3, P3_CGEO, MakePoint (2,row), &sval);
m_geo_ch[id].ix=sval;
GetTableCellVal (p3, P3_CGEO, MakePoint (3,row), &sval);
m_geo_ch[id].iy=sval;
m_geo_ch[id].idx=id;
}
return 0;
}
void CVICALLBACK EndOfThread ( CmtThreadPoolHandle poolhandle,
CmtThreadFunctionID functionID, unsigned int event,
int value, void *callbackData ) {
daq_on=0;
//SetDimming(0);
return ;
}
int CVICALLBACK RefreshGraphs (int panel, int control, int event,
void *callbackData, int eventData1, int eventData2) {
switch (event) {
case EVENT_TIMER_TICK:
// if (!daq_on ) return 0;
case EVENT_COMMIT: {
int ch=0;
int logy=0;
int pmt =0;
int updateplots=0;
GetCtrlVal(p1,P1_RECO, &updateplots);
if (!updateplots) return 0;
GetCtrlVal(p2,P2_PMT, &pmt);
GetCtrlVal(p2,P2_ADC, &ch);
H1D_Draw(10,p2,P2_GRAPHADC,&plothandle[1]);
H2D_Draw(0,p2,P2_GRAPH2D,&plothandle[2]);
}
break;
}
return 0;
}
int vmusb_init(){
int range = 2056;
for (int i=0; i<MAXCH; i++) {
char name[0xFF];
H1D_Init(i, name,name, range, 0 , range);
H1D_SetTitleX(0,"ADC");
H1D_SetTitleY(0,"N");
H1D_Init(100+i, name,name, range, 0 , range);
H1D_SetTitleX(0,"Energy");
H1D_SetTitleY(0,"N");
}
H2D_Init(0, "cog","Center of grg_peakscalingavity", 256, 0 ,1, 256, 0 ,1);
H2D_SetTitleX(0,"x");
H2D_SetTitleY(0,"y");
return 0;
}
double GetEnergy(int ch, int adc){
return (adc-gPedestals[ch])/(gPeak[ch]-gPedestals[ch])*gPeakScaling;
}
int FillHistograms() {
int npmts = 4;
for (int ipmt=0; ipmt<npmts; ipmt++) { // zanka preko pmtjev
int j2= (ipmt/2)*2+1-ipmt%2; // sosednja fotopomnozevalka
float posx[2]= {0,0};
float posy[2]= {0,0};
float sum[2]= {0,0};
float m_threshold =100;
for (int ich=0; ich<16; ich++) { // zanka preko elektronskih kanalov na fotopomnozevalki
int ch= ich+ipmt*16;
if (gMax[ipmt]>m_threshold) {
posx[0]+= gData[ch]*m_geo_ch[ich].ix;
posy[0]+= gData[ch]*m_geo_ch[ich].iy;
sum[0] += gData[ch];
if (gData[ch]> 0.2*gMax[ipmt]) { // pri racunanju pozicije upostevaj le kanale, ki imajo vrednost vecjo od ratio*maksimalna na tisti fotopomnozevalki
posx[1]+= gData[ch]*m_geo_ch[ich].ix;
posy[1]+= gData[ch]*m_geo_ch[ich].iy;
sum[1] += gData[ch];
}
}
}
if ( sum[0] > 0 ) {
float px=posx[0]/sum[0];
float py=posy[0]/sum[0];
H2D_Fill(0, px,py,1);
}
}
return 0;
};
int DecodeData(int n, unsigned int *buf){
int idx=1;
int neve=buf[0]/2;
//++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
for (int nev=0;nev<neve;nev++){
int len=buf[idx];
int sb =buf[idx+1];
unsigned int *pbuf=&buf[idx+2];
if (sb!=0xffab) {
printf("0x%04x!0xffab len=%d\n",sb
,len
);
break;
}
// postavi na nic
#define InitArrayWithAValue(arr,n,x) {for (int i=0;i<n;i++) arr[i]=x;}
InitArrayWithAValue( gSum , 4 , 0);
InitArrayWithAValue( gRawSum , 4 , 0);
InitArrayWithAValue( gMax , 4 , 0);
InitArrayWithAValue( gSumCluster, 4 , 0);
InitArrayWithAValue( gNabove , 4 , 0);
InitArrayWithAValue( gData , MAXCH, 0);
InitArrayWithAValue( gAdc , MAXCH, 0);
//------------------------------------------------------------
for (int i0=0;i0<len-2;i0+=2) {
int data0 = pbuf[i0];
int data1 = pbuf[i0+1];
int geo = (data1 >> 11) & 0x1f;
int ch = (data1&0x1f) | (geo<<5);
int dtype = (data1>>9)&0x3;
int adc = data0&0xfff;
switch (dtype) {
case 0x0:
if (ch<MAXCH) {
H1D_Fill(ch,adc,1);
int ipmt = ch/16;
gAdc[ch]=adc;
gRawSum[ipmt]+=adc;
if (ch<64) gData[ch]= GetEnergy(ch,adc); else gData[ch]=adc;
H1D_Fill(1+ch,gData[ch],1);
gSum[ipmt]+=gData[ch];
if (gData[ch] >gMax[ipmt] ) gMax[ipmt]= gData[ch];
if (gData[ch] >gThreshold ) gNabove[ipmt]++;
}
break;
case 0x10:
case 0x11:
case 0x01:
break;
}
};// for (int i0=0;i0<len-2;i0+=2)
//------------------------------------------------------------
idx+=len+1;
FillHistograms();
} // for (int nev=0;nev<neve;nev++)
//++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
return 0;
}
int vmusb_daq(){
vmusb_init();
// print welcome message
time_t t,told=0, tstart, tstop;
printf("#############################################\n");
printf("Program vmusb version\n");
printf("Compiled on %s %s\n",__DATE__
, __TIME__
);
printf("#############################################\n");
int neve=-1;
char cfname[100]="test.dat";
char fname[0xff];
char fpedname[0xff];
#define BSIZE 10000
uint32_t data[10000];
int oldValue;
//oldValue = SetBreakOnLibraryErrors (0);
daq_init(); /* Function calls that may legitimately return errors. */
//SetBreakOnLibraryErrors (oldValue);
int output=0;
GetCtrlVal(p1,P1_OUTPUT, &output);
GetCtrlVal(p1,P1_FMASK, fpedname);
int fsize=0;
georead();
GetCtrlVal(p1,P1_NEVE, &neve);
// negative argument time ( in s )limited event loop
GetCtrlVal(p1,P1_FNAME, fname);
if (GetFileInfo(fname,&fsize)==1) {
printf( "File %s already exist. Appending ....\n",fname
);
//fprintf(stdout,"Remove the file and restart !!!\n");
//exit(0);
}
FILE *fp=NULL;
if (output
) fp
= fopen(fname
,"a");
//gzFile fp=gzopen(fname,"a");
init();
clear();
int hdr[4]={2}; // recid od run 11 naprej
int i=0;
int ntotal=0;
int counters[30]={0,0,0,0,0, 0,0,0,0,0,0,0};
char names[10][20]={"TRG","CAEN V965"};
tstart=t;
tstop=tstart+360000;
int evetype=0;
GetCtrlVal(p1,P1_EVE, &evetype);
if (evetype) {
double ntime=0;
GetCtrlVal(p1,P1_NTIME, &ntime);
tstop=tstart+ntime;
neve=-1;
}
int reco=0;
GetCtrlVal(p1,P1_RECO, &reco);
for (i=0;i!=neve && !ctrlcflag && t<tstop;i++){
if (t!=told ) {
printf("%d in %2.2f min daq::event() %s\n",i
, (double)(t
-tstart
)/60.
, ctime(&t
));
GetCtrlVal(p1,P1_RECO, &reco);
RefreshGraphs(p2,P2_PMT,EVENT_COMMIT,NULL,0,0);
}
int nb=event(data,BSIZE, counters,t!=told);
SetCtrlVal(p1,P1_CEVE,i);
if (nb>0){
if (reco) DecodeData(nb, data);
// zapis v datoteko
hdr[1]=nb+4*sizeof(int);
hdr[3]=i;
if (fp
) fwrite(hdr
, sizeof(int),4 , fp
);
if (fp
) ntotal
+= fwrite(data
, 1,nb
, fp
);
} else i--;
told=t;
}
end();
printf("Number of Events: %d\n",i
);
if (ctrlcflag
) printf("User Program termination CTRL-C\n");
if (t
>tstop
) printf("Timeout termination tstart# t>tstop: %d# %d >%d\n",(int)t
, (int)tstart
, (int) tstop
);
//gzclose(fp);
printf("%d bytes written to %s\nCounts:\n", (int) (ntotal
*sizeof(int)),fname
);
for (i
=0;i
<2;i
++) printf("%s\t%d\t%d\n",names
[i
],counters
[2*i
],counters
[2*i
+1]) ;
printf("Usage: vmusb [filename] [number of events] [thresholdfile]\n negative number of events = acq time in seconds\n");
disconnect();
return 0;
}
int CVICALLBACK StartCB (int panel, int control, int event,
void *callbackData, int eventData1, int eventData2) {
ThreadFunctionPtr mythread = NULL;
switch (event) {
case EVENT_COMMIT:
controlID= control;
if (panel == p1 && control == P1_START) {
mythread = vmusb_daq;
}
//if (panel == xyscan && control == SCAN_SCAN) mythread = scan;
if (mythread!=NULL) {
printf("New Thread panel=%d button=%d\n", panel
, control
);
// SetDimming(1);
CmtScheduleThreadPoolFunctionAdv (poolHandle, mythread, &controlID,
DEFAULT_THREAD_PRIORITY,
EndOfThread,
EVENT_TP_THREAD_FUNCTION_END,
NULL, RUN_IN_SCHEDULED_THREAD,
&tfID);
}
break;
}
return 0;
}
int CVICALLBACK StopCB (int panel, int control, int event,
void *callbackData, int eventData1, int eventData2) {
switch (event) {
case EVENT_COMMIT:
ctrlcflag=1;
break;
}
return 0;
}
int CVICALLBACK ExitCB (int panel, int control, int event,
void *callbackData, int eventData1, int eventData2) {
switch (event) {
case EVENT_COMMIT:
QuitUserInterface (0);
break;
}
return 0;
}
int CVICALLBACK ShowHistoCB (int panel, int control, int event,
void *callbackData, int eventData1, int eventData2) {
switch (event) {
case EVENT_COMMIT:
DisplayPanel (p2);
break;
}
return 0;
}
int CVICALLBACK SetLogZCB (int panel, int control, int event,
void *callbackData, int eventData1, int eventData2) {
switch (event) {
case EVENT_COMMIT:
GetCtrlVal
(panel
,control
, &log);
SetCtrlAttribute (p2, P2_GRAPH2D, ATTR_YMAP_MODE, VAL_LOG);
} else {
SetCtrlAttribute (p2, P2_GRAPH2D, ATTR_YMAP_MODE, VAL_LINEAR);
}
break;
}
return 0;
}
int CVICALLBACK SetLogYCB (int panel, int control, int event,
void *callbackData, int eventData1, int eventData2) {
switch (event) {
case EVENT_COMMIT:{
GetCtrlVal
(panel
,control
, &log);
SetCtrlAttribute (p2, P2_GRAPHADC, ATTR_YMAP_MODE, VAL_LOG);
} else {
SetCtrlAttribute (p2, P2_GRAPHADC, ATTR_YMAP_MODE, VAL_LINEAR);
}
}
break;
}
return 0;
}
int CVICALLBACK ShowMainCB (int panel, int control, int event,
void *callbackData, int eventData1, int eventData2) {
switch (event) {
case EVENT_COMMIT:
DisplayPanel (p1);
break;
}
return 0;
}
int CVICALLBACK ShowSettingsCB (int panel, int control, int event,
void *callbackData, int eventData1, int eventData2) {
switch (event) {
case EVENT_COMMIT:
DisplayPanel (p3);
break;
}
return 0;
}