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

roclib/src_base/Board.cxx (r4864/r4190)

Go to the documentation of this file.
00001 #include "base/Board.h"
00002 
00003 #include <stdio.h>
00004 #include <stdarg.h>
00005 #include <string.h>
00006 
00007 //----------------------------------------------------------------------------
00009 
00010 const char* base::roleToString(base::ClientRole role)
00011 {
00012    switch (role) {
00013       case roleNone: return 0;
00014       case roleObserver: return "Observer";
00015       case roleControl: return "Control";
00016       case roleDAQ: return "DAQ";
00017    }
00018    return 0;
00019 }
00020 
00021 //----------------------------------------------------------------------------
00023 
00024 base::ClientRole base::defineClientRole(const char* name, base::ClientRole dflt)
00025 {
00026    if ((name==0) || (strlen(name)==0)) return dflt;
00027    if (strcmp(name,"Observer")==0) return roleObserver;
00028    if (strcmp(name,"Control")==0) return roleControl;
00029    if (strcmp(name,"DAQ")==0) return roleDAQ;
00030    return dflt;
00031 }
00032 
00033 
00034 
00035 base::Board::Board() :
00036    fBrdFactory(0),
00037    fDefaultTimeout(2.),
00038    fVerbosity(0),
00039    fOperTrace(1),
00040    fRole(roleNone),
00041    fBrdNumber(0)
00042 {
00043 }
00044 
00045 base::Board::~Board()
00046 {
00047 }
00048 
00049 //----------------------------------------------------------------------------
00051 
00064 void base::Board::Debug(int lvl, const char *fmt, ...)
00065 {
00066    if (!fmt || (lvl>getVerbosity())) return;
00067 
00068    va_list args;
00069    va_start(args, fmt);
00070 
00071    int  result(128), length(128);
00072    char *buffer = 0;
00073    while (result==length) {
00074       if (buffer) delete [] buffer;
00075       length *= 2;
00076       buffer = new char [length + 1];
00077       memset(buffer, 0, length + 1);
00078       result = vsnprintf(buffer, length, fmt, args);
00079       if (result<0) break;
00080    }
00081 
00082    if (fBrdFactory)
00083       fBrdFactory->ShowDebug(lvl, buffer);
00084    else
00085       fprintf(lvl<0 ? stderr : stdout, "%s\n", buffer);
00086 
00087    delete [] buffer;
00088    va_end(args);
00089 }
00090 
00091 
00092 
00093 //----------------------------------------------------------------------------
00095 
00103 void base::Board::traceOper(OperList& lst, int rc)
00104 {
00105    if (fOperTrace == 0) return;
00106    if (fOperTrace == 1 && rc != kOperNetworkErr) return;
00107    if (fOperTrace == 2 && rc == 0) return;
00108 
00109    for (int i=0; i<lst.number(); i++) {
00110       const char* aname = findRegNameByAddress(lst.oper(i).addr);
00111       if (aname==0) aname = "???";
00112 
00113       if (lst.number() == 1) {
00114          Debug(0, "%3s   (%u,%08x %-27s) %s 0x%08x %10d %s",
00115                   (lst.oper(i).isput ? "put" : "get"),
00116                   GetBoardId(), lst.oper(i).addr, aname,
00117                   (lst.oper(i).isput) ? "<-" : "->",
00118                   lst.oper(i).value, lst.oper(i).value,
00119                   (rc == 0) ? "ok" : "FAIL");
00120 
00121       } else {
00122          const char* stat = "";
00123          if (i == lst.number()-1) stat = (rc == 0) ? "ok" : "FAIL";
00124          Debug(0, "op[%02d](%u,%08x %-27s) %s 0x%08x %10d %s",
00125                i, GetBoardId(), lst.oper(i).addr, aname,
00126                (lst.oper(i).isput ? "<-" : "->"),
00127                lst.oper(i).value, lst.oper(i).value, stat);
00128       }
00129 
00130       if (rc != 0) {
00131          std::string str = operErrToString(rc);
00132          Debug(0, "   %s", str.c_str());
00133       }
00134    }
00135 }
00136 
00137 int base::Board::operGen(bool* isput,
00138                         uint32_t* addr,
00139                         uint32_t* value,
00140                         int num,
00141                         double tmout)
00142 {
00143    OperList lst(num, isput, addr, value);
00144 
00145    int res = operGen(lst, tmout);
00146 
00147    for (int n=0;n<num;n++)
00148       if (!isput[n]) value[n] = lst.oper(n).value;
00149 
00150    return res;
00151 }
00152 
00153 
00154 int base::Board::put(uint32_t addr, uint32_t value, double tmout)
00155 {
00156    bool isput = true;
00157 
00158    return operGen(&isput, &addr, &value, 1, tmout);
00159 }
00160 
00161 int base::Board::get(uint32_t addr, uint32_t& value, double tmout)
00162 {
00163    bool isput = false;
00164 
00165    return operGen(&isput, &addr, &value, 1, tmout);
00166 }
00167 
00168 
00169 //----------------------------------------------------------------------------
00171 
00183 int base::Board::operPP(uint32_t addr0, uint32_t  val0p,
00184                        uint32_t addr1, uint32_t  val1p,
00185                        double tmout)
00186 {
00187   bool isput[2];
00188   uint32_t addr[2];
00189   uint32_t data[2];
00190 
00191   isput[0] = true;  addr[0] = addr0;    data[0] = val0p;
00192   isput[1] = true;  addr[1] = addr1;    data[1] = val1p;
00193 
00194   int rc = operGen(isput, addr, data, 2, tmout);
00195   return rc;
00196 }
00197 
00198 //----------------------------------------------------------------------------
00200 
00212 int base::Board::operPG(uint32_t addr0, uint32_t  val0p,
00213                        uint32_t addr1, uint32_t& val1g,
00214                        double tmout)
00215 {
00216   bool isput[2];
00217   uint32_t addr[2];
00218   uint32_t data[2];
00219 
00220   isput[0] = true;  addr[0] = addr0;    data[0] = val0p;
00221   isput[1] = false; addr[1] = addr1;
00222 
00223   int rc = operGen(isput, addr, data, 2, tmout);
00224   val1g = data[1];
00225   return rc;
00226 }
00227 
00228 //----------------------------------------------------------------------------
00230 
00244 int base::Board::operPPP(uint32_t addr0, uint32_t  val0p,
00245                         uint32_t addr1, uint32_t  val1p,
00246                         uint32_t addr2, uint32_t  val2p,
00247                         double tmout)
00248 {
00249   bool isput[3];
00250   uint32_t addr[3];
00251   uint32_t data[3];
00252 
00253   isput[0] = true;  addr[0] = addr0;    data[0] = val0p;
00254   isput[1] = true;  addr[1] = addr1;    data[1] = val1p;
00255   isput[2] = true;  addr[2] = addr2;    data[2] = val2p;
00256 
00257   int rc = operGen(isput, addr, data, 3, tmout);
00258   return rc;
00259 }
00260 
00261 //----------------------------------------------------------------------------
00263 
00277 int base::Board::operGGG(uint32_t addr0, uint32_t&  val0p,
00278                         uint32_t addr1, uint32_t&  val1p,
00279                         uint32_t addr2, uint32_t&  val2p,
00280                         double tmout)
00281 {
00282   bool isput[3];
00283   uint32_t addr[3];
00284   uint32_t data[3];
00285 
00286   isput[0] = false;  addr[0] = addr0;
00287   isput[1] = false;  addr[1] = addr1;
00288   isput[2] = false;  addr[2] = addr2;
00289 
00290   int rc = operGen(isput, addr, data, 3, tmout);
00291 
00292   val0p = data[0];
00293   val1p = data[1];
00294   val2p = data[2];
00295 
00296   return rc;
00297 }
00298 
00299 //----------------------------------------------------------------------------
00301 
00317 int base::Board::operPPPP(uint32_t addr0, uint32_t  val0p,
00318                          uint32_t addr1, uint32_t  val1p,
00319                          uint32_t addr2, uint32_t  val2p,
00320                          uint32_t addr3, uint32_t  val3p,
00321                          double tmout)
00322 {
00323   bool isput[4];
00324   uint32_t addr[4];
00325   uint32_t data[4];
00326 
00327   isput[0] = true;  addr[0] = addr0;    data[0] = val0p;
00328   isput[1] = true;  addr[1] = addr1;    data[1] = val1p;
00329   isput[2] = true;  addr[2] = addr2;    data[2] = val2p;
00330   isput[3] = true;  addr[3] = addr3;    data[3] = val3p;
00331 
00332   int rc = operGen(isput, addr, data, 4, tmout);
00333   return rc;
00334 }
00335 
00336 //----------------------------------------------------------------------------
00338 
00343 const char* base::Board::operErrCodeName(int rc)
00344 {
00345    switch(operErrCode(rc)) {
00346       case kOperSuccess:    return "success";
00347       case kOperAddrErr:    return "invalid address";
00348       case kOperValueErr:   return "value not allowed";
00349       case kOperStateErr:   return "operation not allowed";
00350       case kOperNetworkErr: return "communication error";
00351       case kOperVerifyErr:  return "readback verify error";
00352       case kOperBusErr:     return "secondary bus error";
00353    }
00354   return "";
00355 }
00356 
00357 //----------------------------------------------------------------------------
00359 
00376 std::string base::Board::operErrToString(int rc)
00377 {
00378   char buf[32];
00379   if (rc <0) {
00380     snprintf(buf, sizeof(buf), "rc = %d", rc);
00381     return std::string(buf);
00382   }
00383 
00384   snprintf(buf, sizeof(buf), "rc = %4d,%2d -> ",
00385            operErrIndex(rc), operErrCode(rc));
00386   std::string str(buf);
00387   return str+operErrCodeName(rc);
00388 }
00389 
00390 
00391 //----------------------------------------------------------------------------
00393 
00399 void base::Board::addRegAddrMapping(const char* name, uint32_t addr)
00400 {
00401   std::string sname(name);
00402   fMapName2Addr[sname] = addr;
00403   fMapAddr2Name[addr]  = sname;
00404 }
00405 
00406 //----------------------------------------------------------------------------
00408 
00417 uint32_t base::Board::findRegAddressByName(const char* name)
00418 {
00419   mapn2a_t::iterator it = fMapName2Addr.find(std::string(name));
00420   if (it != fMapName2Addr.end())
00421     return it->second;
00422   return kAddrError;
00423 }
00424 
00425 
00426 //----------------------------------------------------------------------------
00428 
00436 const char* base::Board::findRegNameByAddress(uint32_t addr)
00437 {
00438    if (addr==kAddrError) return 0;
00439    mapa2n_t::iterator it = fMapAddr2Name.find(addr);
00440    if (it != fMapAddr2Name.end())
00441      return it->second.c_str();            // ok because entries never deleted
00442    return 0;
00443 }
00444 
00445 //----------------------------------------------------------------------------
00446 
00447 void base::Board::printRegAddressMap(std::ostream& os, bool byname)
00448 {
00449    char sbuf[1000];
00450 
00451    if (byname) {
00452       for (mapn2a_t::iterator it=fMapName2Addr.begin(); it!=fMapName2Addr.end(); it++) {
00453          snprintf(sbuf, sizeof(sbuf), "0x08x : %s", (unsigned) it->second, (const char*) (it->first.c_str()));
00454          os << sbuf << std::endl;
00455       }
00456    } else {
00457       for (mapa2n_t::iterator it=fMapAddr2Name.begin(); it!=fMapAddr2Name.end(); it++) {
00458          snprintf(sbuf, sizeof(sbuf), "0x08x : %s", (unsigned) it->first, (const char*) (it->second.c_str()));
00459          os << sbuf << std::endl;
00460       }
00461    }
00462 }
00463 
00464 //----------------------------------------------------------------------------
00465 void base::Board::fillRegAddrNames(std::list<std::string>& lst)
00466 {
00467    for (mapn2a_t::iterator it=fMapName2Addr.begin(); it!=fMapName2Addr.end(); it++)
00468       lst.push_back(it->first);
00469 }
00470 
00471 
00472 
00473 //----------------------------------------------------------------------------
00475 
00476 const char* base::Board::versionToString(uint32_t ver)
00477 {
00478    static char sbuf[100];
00479    snprintf(sbuf, sizeof(sbuf), "%u.%u.%u.%u",
00480            (ver >> 24),
00481            (ver >> 16) & 0xff,
00482            (ver >> 8) & 0xff,
00483            ver & 0xff);
00484    return sbuf;
00485 }
00486 
00487 
00488 base::Board* base::Board::Connect(const char* url, ClientRole role)
00489 {
00490    return base::BoardFactory::CreateBoard(url, role);
00491 }
00492 
00493 bool base::Board::Close(Board* brd)
00494 {
00495    return base::BoardFactory::DestroyBoard(brd);
00496 }
00497 
00498 
00499 //----------------------------------------------------------------------------
00501 
00502 uint32_t base::Board::getHardwareVersion()
00503 {
00504    uint32_t val = 0;
00505    get(base::addr_HardwareVersion, val);
00506    return val;
00507 }
00508 
00509 //----------------------------------------------------------------------------
00511 
00512 uint32_t base::Board::getHardwareType()
00513 {
00514    uint32_t val = 0;
00515    get(base::addr_HardwareType, val);
00516    return val;
00517 }
00518 
00519 
00520 //----------------------------------------------------------------------------
00522 
00523 uint32_t base::Board::initBoard(const char* name, uint32_t minversion)
00524 {
00525    base::OperList lst;
00526    lst.addGet(base::addr_BoardId);
00527    lst.addGet(base::addr_HardwareVersion);
00528    lst.addGet(base::addr_HardwareType);
00529    if (operGen(lst)!=0) return 0;
00530 
00531    fBrdNumber          = lst.oper(0).value;
00532    uint32_t roc_hw_ver = lst.oper(1).value;
00533    uint32_t roc_typ    = lst.oper(2).value;
00534 
00535    if(roc_hw_ver < minversion) {
00536       Debug(-1, "The %s you want to access has hardware version %s", name, versionToString(roc_hw_ver));
00537       Debug(-1, "Please update your hardware to version %s", versionToString(minversion));
00538    }
00539 
00540    const char* fe_typ = "<unknown>";
00541    switch (roc_typ >> 16) {
00542       case base::kind_nXYTER:  fe_typ = "nXYTER"; break;
00543       case base::kind_oldFEET: fe_typ = "FEET 0.1"; break;
00544       case base::kind_FEET:    fe_typ = "FEET"; break;
00545       case base::kind_newNX:   fe_typ = "nXYTER 2.0"; break;
00546       case base::kind_SPADIC:  fe_typ = "SPADIC"; break;
00547    }
00548 
00549    const char* be_typ = "<unknown>";
00550    switch (roc_typ & 0xffff) {
00551       case base::kind_Optic: be_typ = "Optic"; break;
00552       case base::kind_FX20:  be_typ = "Eth-FX20"; break;
00553       case base::kind_FX40:  be_typ = "Eth-FX40"; break;
00554       case base::kind_FX60:  be_typ = "Eth-FX60"; break;
00555       case base::kind_newOptic: be_typ = "Optic2"; break;
00556    }
00557 
00558    Debug(0, "BRD%u %s HW version: %s; front:%s; back:%s",
00559          fBrdNumber, name, versionToString(roc_hw_ver), fe_typ, be_typ);
00560 
00561    return roc_hw_ver;
00562 }
00563 
00564 
00565 //----------------------------------------------------------------------------
00567 
00568 uint32_t base::Board::getBoardNumber()
00569 {
00570    uint32_t num = 0;
00571    if (get(base::addr_BoardId, num)==0)
00572       fBrdNumber = num;
00573    return num;
00574 }
00575 
00576 
00577 //----------------------------------------------------------------------------
00579 
00580 void base::Board::setBoardNumber(uint32_t num)
00581 {
00582    put(base::addr_BoardId, num);
00583 }
00584 
00585 
00586 
00587 // =============================================================================
00588 
00589 base::BoardFactory* base::BoardFactory::gArr[base::BoardFactory::MaxNumFactories] =
00590                    { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };
00591 
00592 //----------------------------------------------------------------------------
00593 
00594 base::BoardFactory::BoardFactory()
00595 {
00596    for (int n=0;n<MaxNumFactories;n++)
00597      if (gArr[n]==0) {
00598         gArr[n] = this;
00599         break;
00600      }
00601 }
00602 
00603 //----------------------------------------------------------------------------
00604 
00605 base::BoardFactory::~BoardFactory()
00606 {
00607    for (int n=0;n<MaxNumFactories;n++)
00608      if (gArr[n]==this) gArr[n] = 0;
00609 }
00610 
00611 //----------------------------------------------------------------------------
00612 
00613 
00614 base::Board* base::BoardFactory::CreateBoard(const char* url, ClientRole role)
00615 {
00616    if ((url==0) || (strlen(url)==0)) return 0;
00617 
00618    // first check
00619    for (int n=0;n<MaxNumFactories;n++) {
00620      if (gArr[n]==0) continue;
00621      if (!gArr[n]->IsFactoryFor(url)) continue;
00622 
00623      base::Board* brd = gArr[n]->DoConnect(url, role);
00624 
00625      if (brd==0) {
00626         fprintf(stderr,"Fail to create board with url %s\n", url);
00627         return 0;
00628      }
00629 
00630      brd->fBrdFactory = gArr[n];
00631 
00632      return brd;
00633    }
00634 
00635    fprintf(stderr,"Cannot create board with url %s - no proper factory found\n", url);
00636 
00637    return 0;
00638 }
00639 
00640 bool base::BoardFactory::DestroyBoard(base::Board* brd)
00641 {
00642    if (brd==0) return true;
00643 
00644    BoardFactory* fact = brd->fBrdFactory;
00645 
00646    if (fact==0) return false;
00647 
00648    return fact->DoClose(brd);
00649 }
00650 
00651 
00652 void base::BoardFactory::ShowDebug(int lvl, const char* msg)
00653 {
00654    if (msg!=0) fprintf(lvl<0 ? stderr : stdout, "%s\n", msg);
00655 }

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