• Main Page
  • Related Pages
  • Namespaces
  • Data Structures
  • Files
  • File List
  • Globals

roclib/src_nxyter/FebBase.cxx (r4864/r4162)

Go to the documentation of this file.
00001 //============================================================================
00006 //============================================================================
00007 
00008 #include <string.h>
00009 
00010 #include <stdexcept>
00011 
00012 #include "roc/defines_i2c.h"
00013 #include "roc/I2cDevice.h"
00014 
00015 #include "nxyter/defines_nxyter.h"
00016 #include "nxyter/FebBase.h"
00017 
00018 #include "nxyter/Feb1nxGenB.h"
00019 #include "nxyter/Feb1nxGenC.h"
00020 #include "nxyter/Feb1nxGenD.h"
00021 #include "nxyter/Feb2nxGas.h"
00022 #include "nxyter/Feb4nxBT.h"
00023 
00030 //----------------------------------------------------------------------------
00032 
00039 nxyter::FebBase::FebBase() :
00040   base::Peripheral(),
00041   fPort(0),
00042   fType(0),
00043   fMainAdc(),
00044   fMonAdcDevice(),
00045   fEepromDevice()
00046 {
00047 }
00048 
00049 
00050 nxyter::FebBase::FebBase(base::Board* board, int port, int type) :
00051   base::Peripheral(board),
00052   fPort(port),
00053   fType(type),
00054   fMainAdc(board, port, (type/100==4)),
00055   fMonAdcDevice(board, port, 0),
00056   fEepromDevice(board, port, 0)
00057 {
00058   int numnx = type/100;                     // this holds by convention !!
00059   fNxChip.reserve(numnx);
00060   fNxOffline.reserve(numnx);
00061   fMode4nx = (numnx == 4);
00062   fAdcChannel.reserve(numnx);
00063 }
00064 
00065 //----------------------------------------------------------------------------
00066 
00067 nxyter::FebBase::~FebBase()
00068 {
00069   for (int i=0; i<fNxChip.size(); i++) delete fNxChip[i];
00070 }
00071 
00072 //----------------------------------------------------------------------------
00074 
00086 nxyter::NxChip& nxyter::FebBase::nx(int nxind)
00087 {
00088   return *(fNxChip.at(nxind));
00089 }
00090 
00091 //----------------------------------------------------------------------------
00093 
00102 int nxyter::FebBase::initRoc()
00103 {
00104   int rc = board().put(ROC_NX_FEB4NX, (fMode4nx ? 1 : 0));
00105   if (rc) return rc;
00106   for (int i=0; i<numNx(); i++) {
00107     if (!getNxOffline(i))
00108        rc = adc().setChannelMux(nx(i).getNxNumber(), fAdcChannel[i]);
00109     if (rc) return base::Board::operErrBuildInc(rc, 2*(i+1));
00110 
00111     if (getNxOffline(i))
00112        rc = nx(i).deactivate();
00113     else
00114        rc = nx(i).activate();
00115     if (rc) return base::Board::operErrBuildInc(rc, 2*(i+1)+1);
00116   }
00117   return 0;
00118 }
00119 
00120 
00121 //----------------------------------------------------------------------------
00123 
00127 int nxyter::FebBase::getFebState()
00128 {
00129   for (int i=0; i<numNx(); i++) {
00130      bool active = nx(i).isactive();
00131      setNxOffline(i, !active);
00132   }
00133   return 0;
00134 }
00135 
00136 
00137 //----------------------------------------------------------------------------
00139 
00150 int nxyter::FebBase::probe() 
00151 {
00152   int rc = 0;
00153   
00154   for (int i=0; i<fNxChip.size(); i++) {
00155     if (nx(i).i2c().probe()) {              // !=0 return means probe failed !
00156       setNxOffline(i, true);
00157       rc |= 1<<i;
00158     } else {
00159       setNxOffline(i, false);
00160     }
00161   }
00162   if (adc().probe()) rc |= 1<<5;
00163   return rc;
00164 }
00165 
00166 //----------------------------------------------------------------------------
00168 
00178 int nxyter::FebBase::setToDefault(bool ispos0, bool ispos1)
00179 {
00180   bool pos[4];
00181   for (int i=0; i<4; i++) pos[i] = ispos0;
00182   if (fNxChip.size()==2) pos[1] = ispos1;
00183   if (fNxChip.size()==4) pos[2] = pos[3] = ispos1;
00184 
00185   int rc;
00186   
00187   for (int i=0; i<fNxChip.size(); i++) {
00188     if (getNxOffline(i)) continue;          // skip if offline
00189     rc = nx(i).i2c().setToDefault(pos[i]);
00190     if (rc) return base::Board::operErrBuild(rc, i);
00191   }
00192   rc = adc().setToDefault();
00193   if (rc) return base::Board::operErrBuild(rc, 5);
00194   return 0;
00195 }
00196 
00197 //----------------------------------------------------------------------------
00199 
00200 void nxyter::FebBase::printNxHeadLine(std::ostream& os, int nxind)
00201 {
00202   os << std::dec;
00203   os << "----- nXYTER at port=" << fPort
00204      << " index=" << nxind
00205      << " number=" << nx(nxind).getNxNumber()
00206      << " addr=" << uint32_t(nx(nxind).i2c().getSlaveAddr());
00207   if (getNxOffline(nxind)) {
00208     os << " ----- is set OFFLINE -----";
00209   } else {
00210     os << " --------------------------";
00211   }
00212   os << std::endl;
00213 }
00214 
00215 //----------------------------------------------------------------------------
00217 
00223 void nxyter::FebBase::printRegisters(std::ostream& os, int domask)
00224 {
00225   for (int i=0; i<fNxChip.size(); i++) {
00226     printNxHeadLine(os, i);
00227     if (!getNxOffline(i)) nx(i).i2c().printRegisters(os, domask);
00228   }
00229   os << "----- ADC at port=" << fPort << " --------------------" << std::endl;
00230   adc().printRegisters(os);
00231 }
00232 
00233 //----------------------------------------------------------------------------
00235 
00242 void nxyter::FebBase::resetNxI2cBus()
00243 {
00244   board().operPPP(ROC_NX_I2C_SWITCH, fPort,
00245                   ROC_NX_I2C_RESET,  0,
00246                   ROC_NX_I2C_RESET,  1);
00247 }
00248 
00249 //----------------------------------------------------------------------------
00251 
00264 void nxyter::FebBase::resetNxI2cRegister()
00265 {
00266   board().operPPP(ROC_NX_I2C_SWITCH,    fPort,
00267                   ROC_NX_I2C_REGRESET,  0,
00268                   ROC_NX_I2C_REGRESET,  1);
00269 }
00270 
00271 //----------------------------------------------------------------------------
00273 
00283 int nxyter::FebBase::setNxTestModes(bool testpuls, bool testtrig, 
00284                                     int calselect)
00285 {
00286   for (int i=0; i<fNxChip.size(); i++) {
00287     int rc = nx(i).i2c().setTestModes(testpuls, testtrig, calselect);
00288     if (rc) return base::Board::operErrBuild(rc, i);
00289   }
00290   return 0;
00291 }
00292 
00293 //----------------------------------------------------------------------------
00295 
00303 int nxyter::FebBase::setNxRegisterAll(uint8_t reg, uint8_t val, bool veri)
00304 {
00305    for (int i=0; i<fNxChip.size(); i++) {
00306       if (getNxOffline(i)) continue;          // skip if offline
00307       int rc = nx(i).i2c().setRegister(reg, val, veri);
00308       if (rc) return base::Board::operErrBuild(rc, i);
00309    }
00310    return 0;
00311 }
00312 
00313 //----------------------------------------------------------------------------
00314 // ! return number of monitor ADC channels, 0 if not supported
00315 
00316 int nxyter::FebBase::getNumMonAdc()
00317 {
00318    if (!monAdcSupport()) return 0;
00319 
00320    return 4;
00321 }
00322 
00323 //----------------------------------------------------------------------------
00325 
00334 int nxyter::FebBase::getMonAdc(int ch, uint16_t &val)
00335 {
00336   val = 0;
00337   if (!monAdcSupport()) return -1;
00338   if (ch < 0 || ch > 3) return -2;
00339 
00340   uint8_t mask = 1 << (ch+4);
00341   uint16_t adcval;
00342   int rc = fMonAdcDevice.getRegister16(mask, adcval);
00343   val = adcval & 0xfff;                     // strip 4 MSB (hold channel num)
00344   if (((adcval>>12) & 0x3) != ch) rc = -3;  // check for valid channel id
00345   return rc;
00346 }
00347 
00348 //----------------------------------------------------------------------------
00359 void nxyter::FebBase::addNxChip(int addr, int nxnum, int adcmux)
00360 {
00361   if (fNxChip.size() >= fNxChip.capacity()) 
00362     throw std::out_of_range("FATAL ERROR: addNxChip(), extraneous call");
00363 
00364   fNxChip.push_back(new nxyter::NxChip(getBoard(), fPort, addr, nxnum));
00365   fNxOffline.push_back(false);
00366   fAdcChannel.push_back(adcmux);
00367 }
00368   
00369 //----------------------------------------------------------------------------
00371 
00377 const char* nxyter::FebBase::typeToString(int type)
00378 {
00379   switch (type) {
00380     case kFeb1nx     : return "Feb1nx";
00381     case kFeb1nxGenB : return "Feb1nxGenB";
00382     case kFeb1nxGenC : return "Feb1nxGenC";
00383     case kFeb1nxGenD : return "Feb1nxGenD";
00384     case kFeb2nx     : return "Feb2nx";
00385     case kFeb2nxGas  : return "Feb2nxGas";
00386     case kFeb4nx     : return "Feb4nx";
00387     case kFeb4nxBT   : return "Feb4nxBT";
00388   }  
00389   return "";
00390 }
00391 
00392 //----------------------------------------------------------------------------
00394 
00401 int nxyter::FebBase::stringToType(const char* str)
00402 {
00403   if (strcmp(str, "Feb1nx")==0)     return kFeb1nx;
00404   if (strcmp(str, "Feb1nxGenB")==0) return kFeb1nxGenB;
00405   if (strcmp(str, "Feb1nxGenC")==0) return kFeb1nxGenC;
00406   if (strcmp(str, "Feb1nxGenD")==0) return kFeb1nxGenD;
00407   if (strcmp(str, "Feb2nx")==0)     return kFeb2nx;
00408   if (strcmp(str, "Feb2nxGas")==0)  return kFeb2nxGas;
00409   if (strcmp(str, "Feb4nx")==0)     return kFeb4nx;
00410   if (strcmp(str, "Feb4nxBT")==0)   return kFeb4nxBT;
00411 
00412   return 0;
00413 }
00414 
00415 //----------------------------------------------------------------------------
00417 
00447 void nxyter::FebBase::discoverFebs(base::Board* board,
00448                                    int& typeport0, int& typeport1, 
00449                                    bool liberal)
00450 {
00451   static const int dim_nxlist = 7;
00452   int nxaddr[dim_nxlist];
00453   int nxtype[dim_nxlist];
00454   
00455   nxaddr[0] =  8;  nxtype[0] = kFeb1nxGenC;
00456   nxaddr[1] = 40;  nxtype[1] = kFeb2nxGas;
00457   nxaddr[2] = 48;  nxtype[2] = kFeb2nxGas;
00458   nxaddr[3] = 72;  nxtype[3] = kFeb4nxBT;
00459   nxaddr[4] = 82;  nxtype[4] = kFeb4nxBT;
00460   nxaddr[5] = 84;  nxtype[5] = kFeb4nxBT;
00461   nxaddr[6] = 88;  nxtype[6] = kFeb4nxBT;
00462   
00463   bool ok_adc[2];
00464   int  num_adc = 0;
00465   bool ok_nx[2][dim_nxlist];
00466   int  numnx_1nxGen[2];
00467   int  numnx_2nxGas[2];
00468   int  numnx_4nxBT[2];
00469   numnx_1nxGen[0] = numnx_1nxGen[1] = 0;
00470   numnx_2nxGas[0] = numnx_2nxGas[1] = 0;
00471   numnx_4nxBT[0]  = numnx_4nxBT[1]  = 0;
00472 
00473   // first probe everything possible
00474   for (int port=0; port<=1; port++) {
00475     nxyter::MainAdc adc(board, port);
00476     if ( (ok_adc[port] = (adc.probe() == 0)) ) num_adc++;
00477 
00478     for (int i=0; i<dim_nxlist; i++) {
00479       nxyter::NxChip nx(board, port, nxaddr[i], 0);
00480       if ( (ok_nx[port][i] = (nx.i2c().probe() == 0)) ) {
00481         if (nxtype[i] == kFeb1nxGenC) numnx_1nxGen[port]++;
00482         if (nxtype[i] == kFeb2nxGas)  numnx_2nxGas[port]++;
00483         if (nxtype[i] == kFeb4nxBT)   numnx_4nxBT[port]++;
00484       }
00485     }
00486   }
00487   
00488   typeport0 = 0;
00489   typeport1 = 0;
00490   if (num_adc==0) return;
00491 
00492   int typeport[2];
00493   typeport[0] = 0;
00494   typeport[1] = 0;
00495   
00496   // in the non-liberal case ask for all
00497   if (not liberal) {
00498     if (ok_adc[0]) {
00499       if (numnx_1nxGen[0]==1) typeport[0] = kFeb1nxGenC;
00500       if (numnx_2nxGas[0]==2) typeport[0] = kFeb2nxGas;
00501       if (numnx_4nxBT[0]==4)  typeport[0] = kFeb4nxBT;
00502     }
00503     if (ok_adc[1] && typeport[0]!=kFeb4nx) {
00504       if (numnx_1nxGen[1]==1) typeport[1] = kFeb1nxGenC;
00505       if (numnx_2nxGas[1]==2) typeport[1] = kFeb2nxGas;
00506     }
00507 
00508     // in the liberal case one nXYTER is enough (Note that ranges are distinct)
00509   } else {
00510     if (ok_adc[0]) {
00511       if (numnx_1nxGen[0]>0) typeport[0] = kFeb1nxGenC;
00512       if (numnx_2nxGas[0]>0) typeport[0] = kFeb2nxGas;
00513       if (numnx_4nxBT[0]>0)  typeport[0] = kFeb4nxBT;
00514     }
00515     if (ok_adc[1] && typeport[0]!=kFeb4nx) {
00516       if (numnx_1nxGen[1]>0) typeport[1] = kFeb1nxGenC;
00517       if (numnx_2nxGas[1]>0) typeport[1] = kFeb2nxGas;
00518     }
00519   }
00520 
00521   // Now check whether a monitor I2C ADC is detected, if yes map
00522   //    Feb1nxGenC -> Feb1nxGenD
00523 
00524   for (int port=0; port<=1; port++) {
00525     if (typeport[port]) {
00526       uint16_t val;
00527       roc::I2cDevice i2c(board, port, 41);
00528       int rc = i2c.getRegister16(0x10, val);
00529       if (rc == 0) {
00530         if (typeport[port] == kFeb1nxGenC) typeport[port] = kFeb1nxGenD;
00531       }
00532     }
00533   }
00534 
00535   typeport0 = typeport[0];
00536   typeport1 = typeport[1];  
00537 }
00538 
00539 //----------------------------------------------------------------------------
00541 
00549 nxyter::FebBase* nxyter::FebBase::newFeb(base::Board* board, int port, int type)
00550 {
00551    if ((port<0) || (port>1)) return 0;
00552 
00553    switch (type) {
00554      case kFeb1nxGenB : return new Feb1nxGenB(board, port);
00555      case kFeb1nxGenC : return new Feb1nxGenC(board, port);
00556      case kFeb1nxGenD : return new Feb1nxGenD(board, port);
00557      case kFeb2nxGas  : return new Feb2nxGas(board, port);
00558      case kFeb4nxBT   : return new Feb4nxBT(board);
00559    }
00560    return 0;
00561 }

Generated on Tue Dec 10 2013 04:52:23 for ROCsoft by  doxygen 1.7.1