00001 #include <stdio.h>
00002 #include <string.h>
00003 #include <arpa/inet.h>
00004
00005 #include <rtsLog.h>
00006 #include <rtsSystems.h>
00007 #include <rts.h>
00008 #include <daqFormats.h>
00009
00010
00011
00012 #include "daq_tof.h"
00013
00014
00015 enum { ADCD = 0, TDCD, A2DD, SCAD };
00016
00017 const unsigned short gaindata[32] = {
00018 8, 15, 15, 15,
00019 15, 15, 15, 15,
00020 15, 15, 15, 15,
00021 15, 15, 15, 15,
00022 15, 15, 15, 15,
00023 15, 15, 15, 15,
00024 15, 15, 15, 15,
00025 15, 0, 0, 0 };
00026
00027 const float decal[5] = {0., 0.38748E-1, 0.332922E-4, 0.20618E-6, -0.2188E-8};
00028 const float calib[7] = {0., 2.5928E-2, -7.602961E-7, 4.637791E-11,
00029 -2.165394E-13,6.048144E-20, -7.293422E-25};
00030 const float calib2[7] = {0., 2.5929192E-2, -2.1316967E-7, 7.9018692E-10,
00031 4.2527777E-13, 1.330447E-16, 2.0241446E-20};
00032 const float calibration[16] = {
00033 305.175E-6, 152.580E-6, 0, 76.290E-6,
00034 0, 38.150E-6, 19.073E-6, 0,
00035 9.536E-6, 4.786E-6, 0, 2.384E-6,
00036 1.192E-6, 596.046E-9, 0, 298.023E-9
00037 };
00038
00039
00040
00041
00042 int tof_reader(char *m, struct tof_t *tof, u_int driver)
00043 {
00044 struct DATAP *datap = (struct DATAP *)m ;
00045 struct TOFP *tofp ;
00046 struct TOFADCD *tofadcd;
00047 struct TOFTDCD *toftdcd;
00048 struct TOFA2DD *tofa2dd;
00049 struct TOFSCAD *tofscad;
00050 struct TOFDDLR *ddlr ;
00051 int do_swap ;
00052 int data_words ;
00053
00054 u_int blen ;
00055 int len, off ;
00056
00057 tof->mode = 1 ;
00058 tof->max_channels = 48+48+32+12 ;
00059 tof->channels = 0 ;
00060
00061 memset(tof->ddl_words,0,sizeof(tof->ddl_words)) ;
00062
00063 if(datap == NULL) return 0 ;
00064
00065 if(datap->bh.byte_order != DAQ_RAW_FORMAT_ORDER) {
00066 do_swap = 1 ;
00067 }
00068 else {
00069 do_swap = 0 ;
00070 }
00071
00072 len = (datap->det[TOF_ID].len) ;
00073 if(len == 0) return 0 ;
00074
00075 off = (datap->det[TOF_ID].off) ;
00076 if(off == 0) return 0 ;
00077
00078
00079 off = qswap32(do_swap,off) ;
00080 len = qswap32(do_swap,len) ;
00081
00082
00083 len *= 4 ;
00084
00085 LOG(DBG,"TOF len %d, off %d",len,off,0,0,0);
00086
00087 tofp = (struct TOFP *)((u_int *)m + off) ;
00088
00089 if(checkBank(tofp->bh.bank_type,CHAR_TOFP) < 0) {
00090 return -1 ;
00091 }
00092
00093 if(tofp->bh.token == 0) {
00094 LOG(DBG,"token 0 - skipping ...",0,0,0,0,0);
00095 return 0;
00096 }
00097
00098 u_int fmt_version ;
00099 if(tofp->bh.byte_order != DAQ_RAW_FORMAT_ORDER) {
00100 fmt_version = swap32(tofp->bh.format_ver) ;
00101 }
00102 else {
00103 fmt_version = tofp->bh.format_ver ;
00104 }
00105
00106 int max_contrib ;
00107 if(fmt_version >= 0x50000) {
00108 LOG(NOTE,"TOF FY05+ data version 0x%X",fmt_version) ;
00109 max_contrib = 8 ;
00110 }
00111 else {
00112 LOG(DBG,"TOF pre-FY05 data version 0x%X",fmt_version) ;
00113 max_contrib = 4 ;
00114 }
00115
00116
00117
00118 memset(tof->adc,0,sizeof(tof->adc));
00119 memset(tof->tdc,0,sizeof(tof->tdc));
00120 memset(tof->a2d,0,sizeof(tof->a2d));
00121 memset(tof->sca,0,sizeof(tof->sca));
00122
00123 int bank_t;
00124
00125
00126
00127 for(bank_t=0; bank_t<max_contrib; bank_t++) {
00128 if(tofp->type[bank_t].len <= 0) continue;
00129 switch (bank_t) {
00130 case ADCD:
00131 tofadcd = (struct TOFADCD *)((u_int *)tofp + l2h32(tofp->type[bank_t].off));
00132 if(checkBank(tofadcd->bh.bank_type,CHAR_TOFADCD) < 0) {
00133 return -1;
00134 }
00135
00136 blen = l2h32(tofadcd->bh.length) ;
00137 blen -= sizeof(struct bankHeader)/4 ;
00138
00139 LOG(DBG,"TOFADCD has %d items",blen,0,0,0,0) ;
00140 if(blen > sizeof(tof->adc)/sizeof(tof->adc[0])) {
00141 LOG(ERR,"TOFADCD too big [%d > %d] - skipping!",blen,sizeof(tof->adc)/sizeof(tof->adc[0]),0,0,0) ;
00142 break ;
00143 }
00144
00145 for(u_int i=0;i<blen;i++) {
00146 tof->adc[i] = (( (l2h32(tofadcd->data[i])) & 0xffff0000)>>16);
00147 if(tof->adc[i] > 1024) tof->adc[i] = 1024;
00148 tof->channels++ ;
00149 }
00150 break;
00151
00152 case TDCD:
00153 toftdcd = (struct TOFTDCD *)((u_int *)tofp + l2h32(tofp->type[bank_t].off));
00154 if(checkBank(toftdcd->bh.bank_type,CHAR_TOFTDCD) < 0) {
00155 return -1;
00156 }
00157
00158 blen = l2h32(toftdcd->bh.length) ;
00159 blen -= sizeof(struct bankHeader)/4 ;
00160
00161 LOG(DBG,"TOFTDCD has %d items",blen,0,0,0,0) ;
00162 if(blen > sizeof(tof->tdc)/sizeof(tof->tdc[0])) {
00163 LOG(ERR,"TOFTDCD too big [%d > %d] - skipping!",blen,sizeof(tof->tdc)/sizeof(tof->tdc[0]),0,0,0) ;
00164 break ;
00165 }
00166
00167 for(u_int i=0;i<blen;i++) {
00168 tof->tdc[i] = (( (l2h32(toftdcd->data[i])) & 0xffff0000)>>16);
00169 if(tof->tdc[i] > 2048) tof->tdc[i] = 2048;
00170
00171 if(i==41)tof->tdc[i] = 0;
00172 tof->channels++ ;
00173 }
00174 break;
00175
00176 case A2DD:
00177 tofa2dd = (struct TOFA2DD *)((u_int *)tofp + l2h32(tofp->type[bank_t].off));
00178 if(checkBank(tofa2dd->bh.bank_type,CHAR_TOFA2DD) < 0) {
00179 return -1;
00180 }
00181 tof->a2d[0] = (int)((int) (l2h32(tofa2dd->data[0])) >>16)*calibration[gaindata[0]]/.001-273.;
00182 tof->channels++;
00183 for(int i=1;i<29;i++) {
00184 float V, uncorT;
00185 if( (i!=13) && (i!= 14) && (i!=15)) {
00186 V = short( (l2h32(tofa2dd->data[i])) >>16)*calibration[gaindata[i]]/.000001;
00187 if(V<0) {
00188 uncorT = calib2[0]+calib2[1]*V+calib2[2]*V*V+calib2[3]*V*V*V+calib2[4]*V*V*V*V+calib2[5]*V*V*V*V*V+calib2[6]*V*V*V*V*V*V;
00189 } else {
00190 uncorT = calib[0]+calib[1]*V+calib[2]*V*V+calib[3]*V*V*V+calib[4]*V*V*V*V+calib[5]*V*V*V*V*V+calib[6]*V*V*V*V*V*V;
00191 }
00192 tof->a2d[i] = uncorT+tof->a2d[0];
00193 if(tof->a2d[i] < 0) tof->a2d[i] = 0;
00194 if(tof->a2d[i] > 100) tof->a2d[i] = 100;
00195 tof->channels++ ;
00196 } else {
00197 tof->a2d[i] = 0;
00198 tof->channels++ ;
00199 }
00200 }
00201
00202
00203 for(int i=29;i<32;i++) {
00204 tof->a2d[i] = ((short)((l2h32(tofa2dd->data[i]))>>16)-3280)/13.08;
00205 if(tof->a2d[i] < 0) tof->a2d[i] = 0;
00206 tof->channels++ ;
00207 }
00208 break;
00209
00210 case SCAD:
00211 tofscad = (struct TOFSCAD *)((u_int *)tofp + l2h32(tofp->type[bank_t].off));
00212 if(checkBank(tofscad->bh.bank_type,CHAR_TOFSCAD) < 0) {
00213 return -1;
00214 }
00215 for(int i=0;i<12;i++) {
00216 tof->sca[i] = (( (l2h32(tofscad->data[i])) & 0xffffff00)>>8);
00217 tof->channels++ ;
00218 }
00219 break;
00220
00221 default:
00222 ddlr = (struct TOFDDLR *)((u_int *)tofp + l2h32(tofp->type[bank_t].off)) ;
00223 if(checkBank(ddlr->bh.bank_type,CHAR_TOFDDLR) < 0) {
00224 return -1 ;
00225 }
00226
00227 LOG(DBG,"TOFDDLR %d: length %d words",bank_t-3,l2h32(ddlr->bh.length)-10) ;
00228 data_words = l2h32(ddlr->bh.length) - 10 ;
00229
00230 tof->ddl_words[bank_t-4] = data_words ;
00231
00232 u_int *data_word_p = (u_int *)ddlr->data ;
00233 for(int i=0;i<data_words;i++) {
00234 if(i<10000) {
00235 tof->ddl[bank_t-4][i] = l2h32(data_word_p[i]) ;
00236 }
00237 LOG(DBG,"DDLR %d: %3d: 0x%08X",bank_t-3,i,l2h32(data_word_p[i])) ;
00238 }
00239
00240 break;
00241 }
00242 }
00243 return len ;
00244
00245 }
00246