Main Page   Class Hierarchy   Alphabetical List   Compound List   File List   Compound Members   File Members   Related Pages  

LOW_linkDS2490.cpp

Go to the documentation of this file.
00001 /***************************************************************************
00002                           LOW_linkDS2490.cpp  -  description
00003                              -------------------
00004     begin                : Sun Oct 12 2003
00005     copyright            : (C) 2003 by Harald Roelle
00006     email                : roelle@informatik.uni-muenchen.de
00007  ***************************************************************************/
00008 
00009 /***************************************************************************
00010  *                                                                         *
00011  *   This program is free software; you can redistribute it and/or modify  *
00012  *   it under the terms of the GNU General Public License as published by  *
00013  *   the Free Software Foundation; either version 2 of the License, or     *
00014  *   (at your option) any later version.                                   *
00015  *                                                                         *
00016  ***************************************************************************/
00017 
00018 
00019 #include "LOW_linkDS2490.h"
00020 #include "LOW_device.h"
00021 
00022 
00023 
00024 //=====================================================================================
00025 //
00026 // constructors
00027 //
00028 
00029 LOW_linkDS2490::LOW_linkDS2490( const LOW_portUsb_Factory::usbDeviceSpecifier_t inUsbDevSpec,
00030                                 const bool inHasExternalPower, const bool inAllowProgPulse) :
00031   LOW_link( true, inHasExternalPower, inAllowProgPulse),
00032   LOW_linkFlexibleSpeed( normal_speed, pdSlewRate_1_37, w1LowTime_11, soW0RecTime_10) // use normal speed, but preconfigure the recommeded optimal parameters as of app note #148
00033 {
00034   usbDevice = LOW_portUsb_Factory::new_portUsbDevice( inUsbDevSpec);
00035 
00036   if ( usbDevice->getVendorID() != usbVendorID || usbDevice->getProductID() != usbProductID )
00037     throw link_error( "Requested device has wrong vendor/product ID", __FILE__, __LINE__);
00038 
00039   commonConstructorActions();
00040 }
00041 
00042 
00043 LOW_linkDS2490::LOW_linkDS2490( const bool inHasExternalPower, const bool inAllowProgPulse) :
00044   LOW_link( true, inHasExternalPower, inAllowProgPulse),
00045   LOW_linkFlexibleSpeed( normal_speed, pdSlewRate_1_37, w1LowTime_11, soW0RecTime_10) // use normal speed, but preconfigure the recommeded optimal parameters as of app note #148
00046 {
00047   usbDevice = LOW_portUsb_Factory::new_portUsbDevice( usbVendorID, usbProductID);
00048 
00049   commonConstructorActions();
00050 }
00051 
00052 
00053 LOW_linkDS2490::~LOW_linkDS2490()
00054 {
00055   ctlCmd_resetDevice();
00056   usbDevice->releaseInterface( usbDefaultInterface);
00057   delete usbDevice;
00058 }
00059 
00060 
00061 //=====================================================================================
00062 //
00063 // Standard methods required by LOW_link
00064 //
00065 
00066 //-------------------------------------------------------------------------------------
00067 //
00068 // Bus touch (write/read) methods required by LOW_link
00069 //
00070 
00071 bool LOW_linkDS2490::touchBit( const bool inSendBit, const strongPullup_t inPullup)
00072 {
00073   commLock lock( *this);
00074 
00075   if ( inPullup != pullUp_NONE ) {
00076     comCmd_setDuration( strongPullup_2_spFactor( inPullup), // inTimeFactor
00077                         false,                              // inSpecifyProgPulse
00078                         resultOnError_rsltHdl,              // inResultHandling
00079                         false);                             // inImmediateExec
00080   }
00081 
00082   comCmd_bitIO( inSendBit,                        // inWriteBit
00083                 inPullup==pullUp_NONE?false:true, // inDoStrongPullup
00084                 false,                            // inSuppressPullupOnRead1
00085                 resultOnError_rsltHdl,            // inResultHandling, resultOnError_rsltHdl is necessary to get response byte
00086                 false);                           // inImmediateExec
00087 
00088   ctlCmd_startExecution();
00089 
00090   deviceFeedback_t  deviceFeedback;
00091   resultCodeVec_t   resultCodeVec;
00092   waitUntilIdle( deviceFeedback, resultCodeVec, 1000);
00093 
00094   if ( deviceFeedback.dataInBufferUsage != 1 )
00095     throw comm_error( "Unexpected data amount in IN buffer", __FILE__, __LINE__);
00096 
00097   uint8_t      readByte;
00098   unsigned int readSize = usbDevice->bulkRead( usbDataInEP, 1, &readByte, 1000);
00099   if ( readSize != 1 )
00100     throw comm_error( "Short read from IN buffer", __FILE__, __LINE__);
00101   
00102   return (readByte&0x01)==0x01;
00103 }
00104 
00105 
00106 uint8_t LOW_linkDS2490::touchByte( const uint8_t inSendByte, const strongPullup_t inPullup)
00107 {
00108   commLock lock( *this);
00109 
00110   if ( inPullup != pullUp_NONE ) {
00111     comCmd_setDuration( strongPullup_2_spFactor( inPullup), // inTimeFactor
00112                         false,                              // inSpecifyProgPulse
00113                         resultOnError_rsltHdl,              // inResultHandling
00114                         false);                             // inImmediateExec
00115   }
00116 
00117   comCmd_byteIO( inSendByte,                       // inWriteByte
00118                  inPullup==pullUp_NONE?false:true, // inDoStrongPullup
00119                  resultOnError_rsltHdl,            // inResultHandling, resultOnError_rsltHdl is necessary to get response byte
00120                  false);                           // inImmediateExec
00121 
00122   ctlCmd_startExecution();
00123 
00124   deviceFeedback_t  deviceFeedback;
00125   resultCodeVec_t   resultCodeVec;
00126   waitUntilIdle( deviceFeedback, resultCodeVec, 1000);
00127 
00128   if ( deviceFeedback.dataInBufferUsage != 1 )
00129     throw comm_error( "Unexpected data amount in IN buffer", __FILE__, __LINE__);
00130 
00131   uint8_t      readByte;
00132   unsigned int readSize = usbDevice->bulkRead( usbDataInEP, 1, &readByte, 1000);
00133   if ( readSize != 1 )
00134     throw comm_error( "Short read from IN buffer", __FILE__, __LINE__);
00135 
00136   return readByte;
00137 }
00138 
00139 
00140 byteVec_t LOW_linkDS2490::touchBlock( const byteVec_t &inBytes, const strongPullup_t inPullup)
00141 {
00142   commLock lock( *this);
00143   
00144   const unsigned int  maxBlockSize = (usbDataOutEP_FIFOsize < usbDataInEP_FIFOsize) ? usbDataOutEP_FIFOsize-1 : usbDataInEP_FIFOsize-1;
00145   const unsigned int  total        = inBytes.size();
00146   uint8_t             *writeBuffer = new uint8_t[total];
00147   uint8_t             *readBuffer  = new uint8_t[maxBlockSize];
00148   byteVec_t           retVec       = byteVec_t( total);
00149   
00150   if ( inPullup != pullUp_NONE ) {
00151     comCmd_setDuration( strongPullup_2_spFactor( inPullup), // inTimeFactor
00152                         false,                              // inSpecifyProgPulse
00153                         resultOnError_rsltHdl,              // inResultHandling
00154                         false);                             // inImmediateExec
00155   }
00156 
00157   try {
00158     std::copy( inBytes.begin(), inBytes.end(), writeBuffer);
00159     
00160     unsigned int  written   = 0;
00161     unsigned int  remaining = total;
00162     unsigned int  totalRead = 0;
00163     unsigned int  read      = 0;
00164     uint8_t       *writePtr = writeBuffer;
00165     do {
00166       const unsigned int blockSize = (remaining < maxBlockSize) ? remaining : maxBlockSize;
00167       
00168       written = usbDevice->bulkWrite( usbDataOutEP, blockSize, writePtr, 1000);
00169       remaining -= written;
00170       writePtr  += written;
00171     
00172       comCmd_blockIO( written,                                 // inWriteSize
00173                       false,                                   // inBusResetBefore
00174                       (remaining==0) ? (inPullup==pullUp_NONE?false:true) : false, // inDoStrongPullup
00175                       resultOnError_rsltHdl,                   // inResultHandling,
00176                       false);                                  // inImmediateExec
00177    
00178       ctlCmd_startExecution();
00179 
00180       deviceFeedback_t  deviceFeedback;
00181       resultCodeVec_t   resultCodeVec;
00182       waitUntilIdle( deviceFeedback, resultCodeVec, 1000);
00183    
00184       read = usbDevice->bulkRead( usbDataInEP, written, readBuffer, 1000);
00185       if ( read != written )
00186         throw comm_error( "Short read from IN buffer", __FILE__, __LINE__);
00187       std::copy( readBuffer, readBuffer+read, retVec.begin()+totalRead);
00188       totalRead += read;
00189     }
00190     while ( remaining != 0);
00191   }
00192   catch( ... ) {
00193     delete[] writeBuffer;
00194     delete[] readBuffer;
00195     throw;
00196   }
00197   
00198   delete[] writeBuffer;
00199   delete[] readBuffer;
00200   
00201   return retVec;
00202   
00203   
00204   byteVec_t retBytes = byteVec_t( inBytes.size());
00205   for( unsigned int a=0; a<inBytes.size()-1; ++a) {
00206     retBytes[a] = touchByte( inBytes[a], pullUp_NONE);
00207   }
00208   retBytes[inBytes.size()-1] = touchByte( inBytes[inBytes.size()-1], inPullup);
00209 
00210   return retBytes;
00211 }
00212 
00213 
00214 //-------------------------------------------------------------------------------------
00215 //
00216 // Higher level methods by LOW_link
00217   
00218 LOW_deviceID::deviceIDVec_t LOW_linkDS2490::searchDevices( const bool inOnlyAlarm, const LOW_deviceIDRaw inPreload,
00219                                                            const LOW_deviceIDRaw::devFamCode_t inFamCode, const bool inDoReset)
00220 {
00221   commLock lock( *this);
00222 
00223   const uint8_t                maxDevs = usbDataInEP_FIFOsize/sizeof( LOW_deviceIDRaw::devRomID_t) - 1;  // FIFO_size / ID_size - place_for_discr_vec
00224   LOW_deviceID::deviceIDVec_t  returnIDs;
00225   
00226   LOW_deviceIDRaw preloadVec = inPreload;
00227   
00228   // preload family type
00229   if ( inFamCode != LOW_device::anyDev_famCode )
00230     preloadVec.setFamilyCode( inFamCode);
00231 
00232   if ( resetBus() == false )
00233     return returnIDs;
00234 
00235   bool searchRunning = true;
00236   while ( searchRunning ) {
00237     
00238     unsigned int writeSize = usbDevice->bulkWrite( usbDataOutEP, preloadVec.getRomIDVec(), 1000);
00239     if ( writeSize != preloadVec.getRomIDVec().size() )
00240       throw comm_error( "Short write to OUT buffer", __FILE__, __LINE__);
00241 
00242     comCmd_searchAccess( maxDevs,              // inMaxDevNum
00243                          inOnlyAlarm ? LOW_device::SearchAlarmROM_COMMAND : LOW_device::SearchROM_COMMAND, // inSearchCommand
00244                          true,                 // inSearchWithoutFullAccess
00245                          true,                 // inReturnDiscrepancyInfo
00246                          true,                 // inBusResetBefore
00247                          true,                 // inFlushBuffersOnErr
00248                          resultAlways_rsltHdl, // inResultHandling
00249                          false);               // inImmediateExec
00250   
00251     ctlCmd_startExecution();
00252   
00253     deviceFeedback_t  deviceFeedback;
00254     resultCodeVec_t   resultCodeVec;
00255     waitUntilIdle( deviceFeedback, resultCodeVec, 30000);
00256   
00257     if ( (deviceFeedback.dataInBufferUsage % sizeof( LOW_deviceIDRaw::devRomID_t)) != 0 )
00258       throw comm_error( "Illegal byte count in IN buffer", __FILE__, __LINE__);
00259       
00260     unsigned int rawDevCnt = deviceFeedback.dataInBufferUsage / sizeof( LOW_deviceIDRaw::devRomID_t);
00261     LOW_deviceIDRaw::devRomID_t *readRawIDs = new LOW_deviceIDRaw::devRomID_t[rawDevCnt];
00262     
00263     try {
00264       unsigned int readSize = usbDevice->bulkRead( usbDataInEP, deviceFeedback.dataInBufferUsage, reinterpret_cast<LOW_portUsbDevice::msgData_t>(readRawIDs), 1000);
00265       if ( readSize != deviceFeedback.dataInBufferUsage )
00266         throw comm_error( "Short read from IN buffer", __FILE__, __LINE__);
00267   
00268       unsigned int realIDCnt = rawDevCnt<=maxDevs ? rawDevCnt : maxDevs;
00269       for( unsigned int a=0; a<realIDCnt; ++a) {
00270         LOW_deviceID newID = LOW_deviceID( readRawIDs[a]);
00271         if ( inFamCode!=LOW_device::anyDev_famCode && newID.getFamilyCode()!=inFamCode ) {
00272           searchRunning = false;
00273           break;
00274         }
00275         else
00276           returnIDs.push_back( newID);
00277       }
00278   
00279       if ( rawDevCnt <= maxDevs )
00280         searchRunning = false;
00281       else
00282         preloadVec = readRawIDs[rawDevCnt-1];
00283     }
00284     catch ( ... ) {
00285       delete[] readRawIDs;
00286       throw;
00287     }
00288   
00289     delete[] readRawIDs;
00290   }
00291 
00292   if ( inDoReset )
00293     resetBus();
00294   
00295   return returnIDs;
00296 }
00297 
00298 
00299                                                      
00300 //-------------------------------------------------------------------------------------
00301 //
00302 // Misc methods required by LOW_link
00303 //
00304 
00305 void LOW_linkDS2490::resetLinkAdapter()
00306 {
00307   commLock lock( *this);
00308 
00309   // reset device
00310   ctlCmd_resetDevice();
00311   
00312   modCmd_setEnablePulse( true, allowProgPulse);
00313   modCmd_setEnableSpeedChange( false);
00314   
00315   // restore former settings
00316   setWireSpeed( wireSpeed);
00317   if ( wireSpeed == flexible_speed ) {
00318     setPullDownSlewRate( pdSlewRate);
00319     setWrite1LowTime( w1LowTime);
00320     setSampleOffsetWrite0Rec( soW0RecTime);
00321   }
00322   
00323   deviceFeedback_t devFeedback;
00324   resultCodeVec_t  resultCodeVec;
00325   readDeviceStatus( devFeedback, resultCodeVec);
00326   hasProgramPulse = devFeedback.progVoltagePresent;
00327 }
00328 
00329 
00330 bool LOW_linkDS2490::resetBus()
00331 {
00332   commLock lock( *this);
00333   
00334   comCmd_oneWireReset( false,                // inLoopUntilPresenceDetect
00335                        false,                // inEnableSpeedChange
00336                        normal_OWSPEED,       // inSpeedSelector
00337                        true,                 // inFlushBuffersOnErr
00338                        resultAlways_rsltHdl, // inResultHandling
00339                        false);               // inImmediateExec
00340   ctlCmd_startExecution();
00341   
00342   deviceFeedback_t  deviceFeedback;
00343   resultCodeVec_t   resultCodeVec;
00344   waitUntilIdle( deviceFeedback, resultCodeVec, 1000);
00345 
00346 //  printf( " isStrongPullupEnabled       = %d\n", deviceFeedback.isStrongPullupEnabled);
00347 //  printf( " isProgPulseEnabled          = %d\n", deviceFeedback.isProgPulseEnabled);
00348 //  printf( " isDynSpeedChangeEnabled     = %d\n", deviceFeedback.isDynSpeedChangeEnabled);
00349 //  printf( " oneWireSpeed;               = %d\n", deviceFeedback.oneWireSpeed);
00350 //  printf( " strongPullupDurationFactor; = %d\n", deviceFeedback.strongPullupDurationFactor);
00351 //  printf( " progPulseDurationFactor;    = %d\n", deviceFeedback.progPulseDurationFactor);
00352 //  printf( " pulldownSlewRate;           = %d\n", deviceFeedback.pulldownSlewRate);
00353 //  printf( " write1LowTime;              = %d\n", deviceFeedback.write1LowTime);
00354 //  printf( " dsow0RecTime;               = %d\n", deviceFeedback.dsow0RecTime);
00355 //  printf( " strongPullupCurrentActive;  = %d\n", deviceFeedback.strongPullupCurrentActive);
00356 //  printf( " progPulseCurrentActive;     = %d\n", deviceFeedback.progPulseCurrentActive);
00357 //  printf( " progVoltagePresent;         = %d\n", deviceFeedback.progVoltagePresent);
00358 //  printf( " deviceExternalPowered;      = %d\n", deviceFeedback.deviceExternalPowered);
00359 //  printf( " deviceHalted;               = %d\n", deviceFeedback.deviceHalted);
00360 //  printf( " deviceIdle;                 = %d\n", deviceFeedback.deviceIdle);
00361 //  printf( " ep0FifoOverflowError;       = %d\n", deviceFeedback.ep0FifoOverflowError);
00362 //  printf( " currentCommCmd;             = %d\n", deviceFeedback.currentCommCmd);
00363 //  printf( " commCmdBufferUsage;         = %d\n", deviceFeedback.commCmdBufferUsage);
00364 //  printf( " dataOutBufferUsage;         = %d\n", deviceFeedback.dataOutBufferUsage);
00365 //  printf( " dataInBufferUsage;          = %d\n", deviceFeedback.dataInBufferUsage);
00366 //  printf( " resultCount;                = %d\n", deviceFeedback.resultCount);
00367 //  printf( " resultCodeVec.size()        = %d\n", resultCodeVec.size());
00368   
00369   if ( resultCodeVec.size() == 0)
00370     throw comm_error( "Expected answer not found", __FILE__, __LINE__);
00371 
00372     /** @todo Check if and how "alarming presence pulse" response works. */
00373   if ( resultCodeVec.back().alarmingPresencePulse )  return true;
00374   if ( resultCodeVec.back().noPresencePulse )        return false;
00375   if ( resultCodeVec.back().shortToGround )          throw comm_error( "Short to ground detected", __FILE__, __LINE__);
00376 
00377   return true;
00378 }
00379 
00380 
00381 void LOW_linkDS2490::strongPullup( const unsigned long inMilliSecs)
00382 {
00383   commLock lock( *this);
00384 
00385   if ( inMilliSecs>=16 && inMilliSecs<=4064 && (inMilliSecs%16)==0 ) {  // 16ms <= length <= 4096ms AND dividable by 16ms
00386     strongPullupInternal( inMilliSecs/16);
00387     return;
00388   }
00389 
00390   comCmd_setDuration( 0x00,                  // inTimeFactor = infinite
00391                       false,                 // inSpecifyProgPulse
00392                       resultOnError_rsltHdl, // inResultHandling
00393                       true);                 // inImmediateExec
00394 
00395   comCmd_pulse( false,                  // inSpecifyProgPulse
00396                 true,                   // inFlushBuffersOnErr,
00397                 resultOnError_rsltHdl,  // inResultHandling
00398                 true);                  // inImmediateExec
00399 
00400   LOW_platformMisc::milliSleep( inMilliSecs);
00401   ctlCmd_haltExecutionWhenDone();  // stop the pullup
00402   ctlCmd_resumeExecution();
00403 
00404   deviceFeedback_t  deviceFeedback;
00405   resultCodeVec_t   resultCodeVec;
00406   readDeviceStatus( deviceFeedback, resultCodeVec);
00407 
00408   if ( resultCodeVec.size() != 0)
00409     throw comm_error( "Unexpected error reply found", __FILE__, __LINE__);
00410 }
00411 
00412 
00413 void LOW_linkDS2490::strongPullup( const strongPullup_t inPullupTimes)
00414 {
00415   commLock lock( *this);
00416 
00417   strongPullupInternal( strongPullup_2_spFactor( inPullupTimes));
00418 }
00419 
00420 
00421 void LOW_linkDS2490::programPulse( const unsigned long inMicroSecs)
00422 {
00423   commLock lock( *this);
00424 
00425   if ( ! allowProgPulse )
00426     throw notAllowed_error( "Program pulse not allowed", __FILE__, __LINE__);
00427 
00428   if ( ! hasProgramPulse )
00429     throw illegalLevel_error( "Program pulse not available", __FILE__, __LINE__);
00430 
00431   if ( inMicroSecs>=8 && inMicroSecs<=2032 && (inMicroSecs%8)==0 ) { // 8us <= length <= 2032us AND dividable by 8us
00432     progPulseInternal( inMicroSecs/8);
00433     return;
00434   }
00435 
00436   comCmd_setDuration( 0x00,                  // inTimeFactor = infinite
00437                       true,                  // inSpecifyProgPulse
00438                       resultOnError_rsltHdl, // inResultHandling
00439                       true);                 // inImmediateExec
00440 
00441   comCmd_pulse( true,                  // inSpecifyProgPulse
00442                 true,                  // inFlushBuffersOnErr,
00443                 resultAlways_rsltHdl,  // inResultHandling
00444                 true);                 // inImmediateExec
00445 
00446   LOW_platformMisc::microSleep( inMicroSecs);;
00447   ctlCmd_haltExecutionWhenDone();  // stop the pulse
00448   ctlCmd_resumeExecution();
00449 
00450   deviceFeedback_t  deviceFeedback;
00451   resultCodeVec_t   resultCodeVec;
00452   readDeviceStatus( deviceFeedback, resultCodeVec);
00453 
00454   if ( resultCodeVec.size() == 0)
00455     throw comm_error( "Expected answer not found", __FILE__, __LINE__);
00456 
00457   if ( resultCodeVec.back().progVoltageMissingOnBus )
00458     throw comm_error( "12V program pulse not detected on bus", __FILE__, __LINE__);
00459 }
00460 
00461 
00462 void LOW_linkDS2490::programPulse( const progPulse_t inPulseTime)
00463 {
00464   commLock lock( *this);
00465 
00466   if ( ! allowProgPulse )
00467     throw notAllowed_error( "Program pulse not allowed", __FILE__, __LINE__);
00468 
00469   if ( ! hasProgramPulse )
00470     throw illegalLevel_error( "Program pulse not available", __FILE__, __LINE__);
00471 
00472   progPulseInternal( progPulse_2_ppFactor( inPulseTime));
00473 }
00474 
00475 
00476 void LOW_linkDS2490::doSearchSequence( const LOW_deviceIDRaw& /*inBranchVector*/,
00477                                        LOW_deviceIDRaw& /*outFoundID*/, LOW_deviceIDRaw& /*outDiscrVec*/)
00478 {
00479   throw internal_error( "doSearchSequence() not implemented. Should never be called as searchDevices() is overloaded.", __FILE__, __LINE__);
00480 } 
00481 
00482 
00483 
00484 //=====================================================================================
00485 //
00486 // Standard methods required by LOW_linkFlexibleSpeed
00487 //
00488 
00489 void LOW_linkDS2490::setWireSpeed( const wireSpeed_t inWireSpeed)
00490 {
00491   commLock lock( *this);
00492 
00493   LOW_linkFlexibleSpeed::setWireSpeed( inWireSpeed); // conserve the setting via superclass
00494 
00495   modCmd_setOneWireSpeed( wireSpeed_2_OWSPEED_val( inWireSpeed));
00496 
00497   // restore former settings
00498   if ( wireSpeed == flexible_speed ) {
00499     setPullDownSlewRate( pdSlewRate);
00500     setWrite1LowTime( w1LowTime);
00501     setSampleOffsetWrite0Rec( soW0RecTime);
00502   }
00503 }
00504 
00505 
00506 LOW_linkDS2490::wireSpeed_t LOW_linkDS2490::getWireSpeed()
00507 {
00508   commLock lock( *this);
00509 
00510   deviceFeedback_t devFeedback;
00511   resultCodeVec_t  resultCodeVec;
00512   readDeviceStatus( devFeedback, resultCodeVec);
00513   return OWSPEED_val_2_wireSpeed( devFeedback.oneWireSpeed);
00514 }
00515 
00516 
00517 void LOW_linkDS2490::setPullDownSlewRate( const pdSlewRate_t inPDSR)
00518 {
00519   commLock lock( *this);
00520 
00521   LOW_linkFlexibleSpeed::setPullDownSlewRate( inPDSR);  // conserve the setting via superclass
00522 
00523   modCmd_setPulldownSlewRate( pdSlewRate_2_PDSR_val( inPDSR));
00524 }
00525 
00526 
00527 LOW_linkDS2490::pdSlewRate_t LOW_linkDS2490::getPullDownSlewRate()
00528 {
00529   commLock lock( *this);
00530 
00531   LOW_linkFlexibleSpeed::getPullDownSlewRate();  // sanity checking in superclass
00532 
00533   deviceFeedback_t devFeedback;
00534   resultCodeVec_t  resultCodeVec;
00535   readDeviceStatus( devFeedback, resultCodeVec);
00536   return PDSR_val_2_pdSlewRate( devFeedback.pulldownSlewRate);
00537 }
00538 
00539 
00540 void LOW_linkDS2490::setWrite1LowTime( const w1LowTime_t inW1LT)
00541 {
00542   commLock lock( *this);
00543 
00544   LOW_linkFlexibleSpeed::setWrite1LowTime( inW1LT);  // conserve the setting via superclass
00545 
00546   modCmd_setWrite1LowTime( w1LowTime_2_W1LT_val( inW1LT));
00547 }
00548 
00549 
00550 LOW_linkDS2490::w1LowTime_t LOW_linkDS2490::getWrite1LowTime()
00551 {
00552   commLock lock( *this);
00553 
00554   LOW_linkFlexibleSpeed::getWrite1LowTime();  // sanity checking in superclass
00555 
00556   deviceFeedback_t devFeedback;
00557   resultCodeVec_t  resultCodeVec;
00558   readDeviceStatus( devFeedback, resultCodeVec);
00559   return W1LT_val_2_w1LowTime( devFeedback.write1LowTime);
00560 }
00561 
00562 
00563 void LOW_linkDS2490::setSampleOffsetWrite0Rec( const soW0RecTime_t inSOW0RT)
00564 {
00565   commLock lock( *this);
00566 
00567   LOW_linkFlexibleSpeed::setSampleOffsetWrite0Rec( inSOW0RT);  // conserve the setting via superclass
00568 
00569   modCmd_setDsoW0RecoveryTime( soW0RecTime_2_SOW0RT_val( inSOW0RT));
00570 }
00571 
00572 
00573 LOW_linkDS2490::soW0RecTime_t LOW_linkDS2490::getSampleOffsetWrite0Rec()
00574 {
00575   commLock lock( *this);
00576 
00577   LOW_linkFlexibleSpeed::getSampleOffsetWrite0Rec();  // sanity checking in superclass
00578 
00579   deviceFeedback_t devFeedback;
00580   resultCodeVec_t  resultCodeVec;
00581   readDeviceStatus( devFeedback, resultCodeVec);
00582   return SOW0RT_val_2_soW0RecTime( devFeedback.dsow0RecTime);
00583 }
00584 
00585 
00586 
00587 
00588 //=====================================================================================
00589 //
00590 // private methods
00591 //
00592 
00593 
00594 //-------------------------------------------------------------------------------------
00595 //
00596 // Mid-layer methods.
00597 //
00598 
00599 void LOW_linkDS2490::commonConstructorActions()
00600 {
00601   // locking done in publicly accessible methods
00602 
00603   usbDevice->claimInterface( usbDefaultInterface);
00604   
00605   resetLinkAdapter();
00606 }
00607 
00608 
00609 void LOW_linkDS2490::readDeviceStatus( deviceFeedback_t &outDevFeedback, resultCodeVec_t &outResultCodeVec)
00610 {
00611   // locking done in publicly accessible methods
00612 
00613   deviceFeedbackRaw_t  feedbackData;
00614 
00615   unsigned int readBytes = usbDevice->bulkRead( usbStatusInEP, sizeof( feedbackData),
00616                                                 reinterpret_cast<LOW_portUsbDevice::msgData_t>(&feedbackData), 500);
00617   if ( readBytes < 16 )
00618     throw comm_error( "Short read from status endpoint", __FILE__, __LINE__);
00619 
00620   // analyze standard data
00621   outDevFeedback.isStrongPullupEnabled      = feedbackData.enableFlags & SPUE_bitmask;
00622   outDevFeedback.isProgPulseEnabled         = feedbackData.enableFlags & PRGE_bitmask;
00623   outDevFeedback.isDynSpeedChangeEnabled    = feedbackData.enableFlags & SPCE_bitmask;
00624   outDevFeedback.oneWireSpeed               = static_cast<OWSPEED_val_t>(feedbackData.oneWireSpeed);
00625   outDevFeedback.strongPullupDurationFactor = feedbackData.strongPullupDuration;
00626   outDevFeedback.progPulseDurationFactor    = feedbackData.progPulseDuration;
00627   outDevFeedback.pulldownSlewRate           = static_cast<PDSR_val_t>(feedbackData.pulldownSlewRate);
00628   outDevFeedback.write1LowTime              = static_cast<W1LT_val_t>(feedbackData.write1LowTime);
00629   outDevFeedback.dsow0RecTime               = static_cast<SOW0RT_val_t>(feedbackData.dsow0RecTime);
00630   outDevFeedback.strongPullupCurrentActive  = feedbackData.deviceStatusFlags & SPUA_bitmask;
00631   outDevFeedback.progPulseCurrentActive     = feedbackData.deviceStatusFlags & PRGA_bitmask;
00632   outDevFeedback.progVoltagePresent         = feedbackData.deviceStatusFlags & VP12_bitmask;
00633   outDevFeedback.deviceExternalPowered      = feedbackData.deviceStatusFlags & PMOD_bitmask;
00634   outDevFeedback.deviceHalted               = feedbackData.deviceStatusFlags & HALT_bitmask;
00635   outDevFeedback.deviceIdle                 = feedbackData.deviceStatusFlags & IDLE_bitmask;
00636   outDevFeedback.ep0FifoOverflowError       = feedbackData.deviceStatusFlags & EP0F_bitmask;
00637   outDevFeedback.currentCommCmd             = (feedbackData.commCmdHI<<8) | feedbackData.commCmdLO;
00638   outDevFeedback.commCmdBufferUsage         = feedbackData.commCmdBufferStatus;
00639   outDevFeedback.dataOutBufferUsage         = feedbackData.dataOutBufferStatus;
00640   outDevFeedback.dataInBufferUsage          = feedbackData.dataInBufferStatus;
00641   outDevFeedback.resultCount                = readBytes - 16;
00642   outDevFeedback.compoundResults.deviceDetected             = false;
00643   outDevFeedback.compoundResults.searchAccessDeviceUnderrun = false;
00644   outDevFeedback.compoundResults.pageIsRedirected           = false;
00645   outDevFeedback.compoundResults.crcError                   = false;
00646   outDevFeedback.compoundResults.compareError               = false;
00647   outDevFeedback.compoundResults.progVoltageMissingOnBus    = false;
00648   outDevFeedback.compoundResults.alarmingPresencePulse      = false;
00649   outDevFeedback.compoundResults.shortToGround              = false;
00650   outDevFeedback.compoundResults.noPresencePulse            = false;
00651   
00652   // analyze extra result codes and calc compound results
00653   for( int a=0; a<outDevFeedback.resultCount; a++) {
00654     resultCode_t theResult = { false, false, false, false, false, false, false, false, false};
00655 
00656     if ( feedbackData.resultCode[a] == devDetect_code ) {
00657       theResult.deviceDetected             = true;
00658     }
00659     else {
00660       theResult.searchAccessDeviceUnderrun = feedbackData.resultCode[a] & EOS_bitmask;
00661       theResult.pageIsRedirected           = feedbackData.resultCode[a] & RDP_bitmask;
00662       theResult.crcError                   = feedbackData.resultCode[a] & CRC_bitmask;
00663       theResult.compareError               = feedbackData.resultCode[a] & CMP_bitmask;
00664       theResult.progVoltageMissingOnBus    = feedbackData.resultCode[a] & VPP_bitmask;
00665       theResult.alarmingPresencePulse      = feedbackData.resultCode[a] & APP_bitmask;
00666       theResult.shortToGround              = feedbackData.resultCode[a] & SH_bitmask;
00667       theResult.noPresencePulse            = feedbackData.resultCode[a] & NRS_bitmask;
00668     }
00669 
00670     outDevFeedback.compoundResults.deviceDetected             |= theResult.deviceDetected;
00671     outDevFeedback.compoundResults.searchAccessDeviceUnderrun |= theResult.searchAccessDeviceUnderrun;
00672     outDevFeedback.compoundResults.pageIsRedirected           |= theResult.pageIsRedirected;
00673     outDevFeedback.compoundResults.crcError                   |= theResult.crcError;
00674     outDevFeedback.compoundResults.compareError               |= theResult.compareError;
00675     outDevFeedback.compoundResults.progVoltageMissingOnBus    |= theResult.progVoltageMissingOnBus;
00676     outDevFeedback.compoundResults.alarmingPresencePulse      |= theResult.alarmingPresencePulse;
00677     outDevFeedback.compoundResults.shortToGround              |= theResult.shortToGround;
00678     outDevFeedback.compoundResults.noPresencePulse            |= theResult.noPresencePulse;
00679 
00680     outResultCodeVec.push_back( theResult);
00681   }
00682 
00683   // ep0 fifo overrun makes the device unusable anyway so we handle it here centrally
00684   if ( outDevFeedback.ep0FifoOverflowError ) {
00685     ctlCmd_resetDevice();
00686     throw comm_error( "EP0 FIFO overrund. Reset command was sent to device.", __FILE__, __LINE__);
00687   }
00688 }
00689 
00690 
00691 void LOW_linkDS2490::waitUntilIdle( deviceFeedback_t &outDeviceFeedback, resultCodeVec_t &outResultCodeVec,
00692                                     const LOW_portUsbDevice::usbTimeout_t inTimeout)
00693 {
00694   // locking done in publicly accessible methods
00695 
00696   static const unsigned long sleepTime_ms = 1;
00697 
00698   resultCode_t cmpdResults = { false, false, false, false, false, false, false, false, false};
00699   
00700   for ( unsigned int a=0; a<(inTimeout/sleepTime_ms)+1; ++a) {
00701     deviceFeedback_t  feedbackData;
00702     readDeviceStatus( feedbackData, outResultCodeVec);
00703     
00704     cmpdResults.deviceDetected             |= feedbackData.compoundResults.deviceDetected;
00705     cmpdResults.searchAccessDeviceUnderrun |= feedbackData.compoundResults.searchAccessDeviceUnderrun;
00706     cmpdResults.pageIsRedirected           |= feedbackData.compoundResults.pageIsRedirected;
00707     cmpdResults.crcError                   |= feedbackData.compoundResults.crcError;
00708     cmpdResults.compareError               |= feedbackData.compoundResults.compareError;
00709     cmpdResults.progVoltageMissingOnBus    |= feedbackData.compoundResults.progVoltageMissingOnBus;
00710     cmpdResults.alarmingPresencePulse      |= feedbackData.compoundResults.alarmingPresencePulse;
00711     cmpdResults.shortToGround              |= feedbackData.compoundResults.shortToGround;
00712     cmpdResults.noPresencePulse            |= feedbackData.compoundResults.noPresencePulse;
00713     
00714     if ( feedbackData.deviceIdle && feedbackData.commCmdBufferUsage==0 ) {
00715       outDeviceFeedback = feedbackData;
00716       outDeviceFeedback.compoundResults = cmpdResults;
00717       return;
00718     }
00719 
00720     LOW_platformMisc::milliSleep( sleepTime_ms);
00721   }
00722   throw comm_error( "Timeout waiting for device to become idle.", __FILE__, __LINE__);
00723 }
00724 
00725 
00726 void LOW_linkDS2490::strongPullupInternal( const unsigned int inPullupFactor)
00727 {
00728   // locking done in publicly accessible methods
00729 
00730   comCmd_setDuration( inPullupFactor,          // inTimeFactor
00731                       false,                   // inSpecifyProgPulse
00732                       resultOnError_rsltHdl,   // inResultHandling
00733                       true);                   // inImmediateExec
00734 
00735   comCmd_pulse( false,                 // inSpecifyProgPulse
00736                 true,                  // inFlushBuffersOnErr,
00737                 resultOnError_rsltHdl, // inResultHandling
00738                 true);                 // inImmediateExec
00739 
00740   deviceFeedback_t  deviceFeedback;
00741   resultCodeVec_t   resultCodeVec;
00742   waitUntilIdle( deviceFeedback, resultCodeVec, (16*inPullupFactor) + 1000);  // (16ms * factor) + 1s
00743 
00744   if ( resultCodeVec.size() != 0)
00745     throw comm_error( "Unexpected error reply found", __FILE__, __LINE__);
00746 }
00747 
00748 
00749 void LOW_linkDS2490::progPulseInternal( const unsigned int inPulseFactor)
00750 {
00751   // locking done in publicly accessible methods
00752 
00753   comCmd_setDuration( inPulseFactor,           // inTimeFactor
00754                       true,                    // inSpecifyProgPulse
00755                       resultOnError_rsltHdl,   // inResultHandling
00756                       true);                   // inImmediateExec
00757 
00758   comCmd_pulse( true,                  // inSpecifyProgPulse
00759                 true,                  // inFlushBuffersOnErr,
00760                 resultAlways_rsltHdl,  // inResultHandling
00761                 true);                 // inImmediateExec
00762 
00763   deviceFeedback_t  deviceFeedback;
00764   resultCodeVec_t   resultCodeVec;
00765   waitUntilIdle( deviceFeedback, resultCodeVec, (8*inPulseFactor)/1000 + 1000);  // (8us * factor)/1000us + 1s
00766 
00767   if ( resultCodeVec.size() == 0)
00768     throw comm_error( "Expected answer not found", __FILE__, __LINE__);
00769 
00770   if ( resultCodeVec.back().progVoltageMissingOnBus )
00771     throw comm_error( "12V program pulse not detected on bus", __FILE__, __LINE__);
00772 }
00773 
00774 
00775 
00776 //-------------------------------------------------------------------------------------
00777 //
00778 // Control command methods.
00779 //
00780 
00781 void LOW_linkDS2490::ctlCmd_resetDevice()
00782 {
00783   // locking done in publicly accessible methods
00784 
00785   usbDevice->controlMsg( vendorCmd_requestType, control_cmdType, resetDevice_ctlCmd,
00786                          0x0000, 0x0000, 0, ctlCmd_usbTimeout);
00787 }
00788 
00789 
00790 void LOW_linkDS2490::ctlCmd_startExecution()
00791 {
00792   // locking done in publicly accessible methods
00793 
00794   usbDevice->controlMsg( vendorCmd_requestType, control_cmdType, startExe_ctlCmd,
00795                          0x0000, 0x0000, 0, ctlCmd_usbTimeout);
00796 }
00797 
00798 
00799 void LOW_linkDS2490::ctlCmd_resumeExecution()
00800 {
00801   // locking done in publicly accessible methods
00802 
00803   usbDevice->controlMsg( vendorCmd_requestType, control_cmdType, resumeExe_ctlCmd,
00804                          0x0000, 0x0000, 0, ctlCmd_usbTimeout);
00805 }
00806 
00807 
00808 void LOW_linkDS2490::ctlCmd_haltExecutionWhenIdle()
00809 {
00810   // locking done in publicly accessible methods
00811 
00812   usbDevice->controlMsg( vendorCmd_requestType, control_cmdType, haltExeIdle_ctlCmd,
00813                          0x0000, 0x0000, 0, ctlCmd_usbTimeout);
00814 }
00815 
00816 
00817 void LOW_linkDS2490::ctlCmd_haltExecutionWhenDone()
00818 {
00819   // locking done in publicly accessible methods
00820 
00821   usbDevice->controlMsg( vendorCmd_requestType, control_cmdType, haltExeDone_ctlCmd,
00822                          0x0000, 0x0000, 0, ctlCmd_usbTimeout);
00823 }
00824 
00825 
00826 void LOW_linkDS2490::ctlCmd_flushCommCmds()
00827 {
00828   // locking done in publicly accessible methods
00829 
00830   usbDevice->controlMsg( vendorCmd_requestType, control_cmdType, flushCommCmds_ctlCmd,
00831                          0x0000, 0x0000, 0, ctlCmd_usbTimeout);
00832 }
00833 
00834 
00835 void LOW_linkDS2490::ctlCmd_flushDataRcvBuffer()
00836 {
00837   // locking done in publicly accessible methods
00838 
00839   usbDevice->controlMsg( vendorCmd_requestType, control_cmdType, flushRcvBuffer_ctlCmd,
00840                          0x0000, 0x0000, 0, ctlCmd_usbTimeout);
00841 }
00842 
00843 
00844 void LOW_linkDS2490::ctlCmd_flushDataXmtBuffer()
00845 {
00846   // locking done in publicly accessible methods
00847 
00848   usbDevice->controlMsg( vendorCmd_requestType, control_cmdType, flushXmtBuffer_ctlCmd,
00849                          0x0000, 0x0000, 0, ctlCmd_usbTimeout);
00850 }
00851 
00852 
00853 void LOW_linkDS2490::ctlCmd_getCommCmds( byteVec_t &outBytes)
00854 {
00855   // locking done in publicly accessible methods
00856 
00857   usbDevice->controlMsg( vendorCmd_requestType, control_cmdType, getCommCmds_ctlCmd,
00858                          0x0000, outBytes, ctlCmd_usbTimeout);
00859 }
00860 
00861 
00862 
00863 //-------------------------------------------------------------------------------------
00864 //
00865 // Mode command methods.
00866 //
00867   
00868 void LOW_linkDS2490::modCmd_setEnablePulse( const bool inEnableStrongPullup, const bool inEnableProgPulse)
00869 {
00870   // locking done in publicly accessible methods
00871 
00872   LOW_portUsbDevice::wIndex_t indexVal = 0x0000;
00873   
00874   if ( inEnableStrongPullup ) indexVal |= 0x0002;
00875   if ( inEnableProgPulse )    indexVal |= 0x0001;
00876   
00877   usbDevice->controlMsg( vendorCmd_requestType, mode_cmdType, pulseEn_modCmd,
00878                          indexVal, 0x0000, 0, modCmd_usbTimeout);
00879 }
00880 
00881   
00882 void LOW_linkDS2490::modCmd_setEnableSpeedChange( const bool inEnableSpeedChange)
00883 {
00884   // locking done in publicly accessible methods
00885 
00886   LOW_portUsbDevice::wIndex_t indexVal = 0x0000;
00887   
00888   if ( inEnableSpeedChange ) indexVal |= 0x0001;
00889   
00890   usbDevice->controlMsg( vendorCmd_requestType, mode_cmdType, speedChangeEn_modCmd,
00891                          indexVal, 0x0000, 0, modCmd_usbTimeout);
00892 }
00893 
00894   
00895 void LOW_linkDS2490::modCmd_setOneWireSpeed( const OWSPEED_val_t inWireSpeed)
00896 {
00897   // locking done in publicly accessible methods
00898 
00899   LOW_portUsbDevice::wIndex_t indexVal = 0x0000 | inWireSpeed;
00900   
00901   usbDevice->controlMsg( vendorCmd_requestType, mode_cmdType, oneWireSpeed_modCmd,
00902                          indexVal, 0x0000, 0, modCmd_usbTimeout);
00903 }
00904 
00905   
00906 void LOW_linkDS2490::modCmd_setStrongPullupDuration( const uint8_t inSpuDurationFactor)
00907 {
00908   // locking done in publicly accessible methods
00909 
00910   LOW_portUsbDevice::wIndex_t indexVal = 0x0000 | inSpuDurationFactor;
00911   
00912   usbDevice->controlMsg( vendorCmd_requestType, mode_cmdType, strongPuDuration_modCmd,
00913                          indexVal, 0x0000, 0, modCmd_usbTimeout);
00914 }
00915 
00916   
00917 void LOW_linkDS2490::modCmd_setProgPulseDuration( const uint8_t inPpDurationFactor)
00918 {
00919   // locking done in publicly accessible methods
00920 
00921   LOW_portUsbDevice::wIndex_t indexVal = 0x0000 | inPpDurationFactor;
00922   
00923   usbDevice->controlMsg( vendorCmd_requestType, mode_cmdType, progPulseDuration_modCmd,
00924                          indexVal, 0x0000, 0, modCmd_usbTimeout);
00925 }
00926 
00927   
00928 void LOW_linkDS2490::modCmd_setPulldownSlewRate( const PDSR_val_t inPDSR)
00929 {
00930   // locking done in publicly accessible methods
00931 
00932   LOW_portUsbDevice::wIndex_t indexVal = 0x0000 | inPDSR;
00933   
00934   usbDevice->controlMsg( vendorCmd_requestType, mode_cmdType, pulldownSlewRate_modCmd,
00935                          indexVal, 0x0000, 0, modCmd_usbTimeout);
00936 }
00937 
00938   
00939 void LOW_linkDS2490::modCmd_setWrite1LowTime( const W1LT_val_t inW1LT)
00940 {
00941   // locking done in publicly accessible methods
00942 
00943   LOW_portUsbDevice::wIndex_t indexVal = 0x0000 | inW1LT;
00944   
00945   usbDevice->controlMsg( vendorCmd_requestType, mode_cmdType, write1LowTime_modCmd,
00946                          indexVal, 0x0000, 0, modCmd_usbTimeout);
00947 }
00948 
00949   
00950 void LOW_linkDS2490::modCmd_setDsoW0RecoveryTime( const SOW0RT_val_t inSOW0RT)
00951 {
00952   // locking done in publicly accessible methods
00953 
00954   LOW_portUsbDevice::wIndex_t indexVal = 0x0000 | inSOW0RT;
00955   
00956   usbDevice->controlMsg( vendorCmd_requestType, mode_cmdType, dsow0Trec_modCmd,
00957                          indexVal, 0x0000, 0, modCmd_usbTimeout);
00958 }
00959 
00960 
00961 
00962 //-------------------------------------------------------------------------------------
00963 //
00964 // Communication command methods.
00965 //
00966 
00967 void LOW_linkDS2490::comCmd_setDuration( const uint8_t inTimeFactor,
00968                                          const bool inSpecifyProgPulse,
00969                                          const resultHandling_t inResultHandling,
00970                                          const bool inImmediateExec)
00971 {
00972   // locking done in publicly accessible methods
00973 
00974   LOW_portUsbDevice::wValue_t valueCmd = setDuration_comCmdBase;
00975   if ( inSpecifyProgPulse ) valueCmd |= TYPE_bitmask;
00976   handleCommonComCmdBits( valueCmd, inResultHandling, inImmediateExec);
00977 
00978   LOW_portUsbDevice::wIndex_t indexVal = 0x0000 | inTimeFactor;
00979 
00980   usbDevice->controlMsg( vendorCmd_requestType, comm_cmdType, valueCmd,
00981                          indexVal, 0x0000, 0, comCmd_usbTimeout);
00982 }
00983 
00984 
00985 void LOW_linkDS2490::comCmd_pulse( const bool inSpecifyProgPulse,
00986                                    const bool inFlushBuffersOnErr,
00987                                    const resultHandling_t inResultHandling,
00988                                    const bool inImmediateExec)
00989 {
00990   // locking done in publicly accessible methods
00991 
00992   LOW_portUsbDevice::wValue_t valueCmd = pulse_comCmdBase;
00993   if ( inSpecifyProgPulse )  valueCmd |= TYPE_bitmask;
00994   if ( inFlushBuffersOnErr ) valueCmd |= F_bitmask;
00995   handleCommonComCmdBits( valueCmd, inResultHandling, inImmediateExec);
00996 
00997   usbDevice->controlMsg( vendorCmd_requestType, comm_cmdType, valueCmd,
00998                          0x0000, 0x0000, 0, comCmd_usbTimeout);
00999 }
01000 
01001 
01002 void LOW_linkDS2490::comCmd_oneWireReset( const bool inLoopUntilPresenceDetect,
01003                                           const bool inEnableSpeedChange,
01004                                           const OWSPEED_val_t inSpeedSelector,
01005                                           const bool inFlushBuffersOnErr,
01006                                           const resultHandling_t inResultHandling,
01007                                           const bool inImmediateExec)
01008 {
01009   // locking done in publicly accessible methods
01010 
01011   LOW_portUsbDevice::wValue_t valueCmd = oneWireReset_comCmdBase;
01012   if ( inLoopUntilPresenceDetect ) valueCmd |= PST_bitmask;
01013   if ( inEnableSpeedChange )       valueCmd |= SE_bitmask;
01014   if ( inFlushBuffersOnErr )       valueCmd |= F_bitmask;
01015   handleCommonComCmdBits( valueCmd, inResultHandling, inImmediateExec);
01016 
01017   LOW_portUsbDevice::wIndex_t indexVal = 0x0000 | inSpeedSelector;
01018 
01019   usbDevice->controlMsg( vendorCmd_requestType, comm_cmdType, valueCmd,
01020                          indexVal, 0x0000, 0, comCmd_usbTimeout);
01021 }
01022 
01023 
01024 void LOW_linkDS2490::comCmd_bitIO( const bool inWriteBit,
01025                                    const bool inDoStrongPullup,
01026                                    const bool inSuppressPullupOnRead1,
01027                                    const resultHandling_t inResultHandling,
01028                                    const bool inImmediateExec)
01029 {
01030   // locking done in publicly accessible methods
01031 
01032   LOW_portUsbDevice::wValue_t valueCmd = bitIO_comCmdBase;
01033   if ( inWriteBit )              valueCmd |= D_bitmask;
01034   if ( inDoStrongPullup )        valueCmd |= SPU_bitmask;
01035   if ( inSuppressPullupOnRead1 ) valueCmd |= CIB_bitmask;
01036   handleCommonComCmdBits( valueCmd, inResultHandling, inImmediateExec);
01037 
01038   usbDevice->controlMsg( vendorCmd_requestType, comm_cmdType, valueCmd,
01039                          0x0000, 0x0000, 0, comCmd_usbTimeout);
01040 }
01041 
01042 
01043 void LOW_linkDS2490::comCmd_byteIO( const uint8_t inWriteByte,
01044                                     const bool inDoStrongPullup,
01045                                     const resultHandling_t inResultHandling,
01046                                     const bool inImmediateExec)
01047 {
01048   // locking done in publicly accessible methods
01049 
01050   LOW_portUsbDevice::wValue_t valueCmd = byteIO_comCmdBase;
01051   if ( inDoStrongPullup ) valueCmd |= SPU_bitmask;
01052   handleCommonComCmdBits( valueCmd, inResultHandling, inImmediateExec);
01053 
01054   LOW_portUsbDevice::wIndex_t indexVal = 0x0000 | inWriteByte;
01055 
01056   usbDevice->controlMsg( vendorCmd_requestType, comm_cmdType, valueCmd,
01057                          indexVal, 0x0000, 0, comCmd_usbTimeout);
01058 }
01059 
01060 
01061 void LOW_linkDS2490::comCmd_blockIO( const uint16_t inWriteSize,
01062                                      const bool inBusResetBefore,
01063                                      const bool inDoStrongPullup,
01064                                      const resultHandling_t inResultHandling,
01065                                      const bool inImmediateExec)
01066 {
01067   // locking done in publicly accessible methods
01068 
01069   LOW_portUsbDevice::wValue_t valueCmd = blockIO_comCmdBase;
01070   if ( inBusResetBefore ) valueCmd |= RST_bitmask;
01071   if ( inDoStrongPullup ) valueCmd |= SPU_bitmask;
01072   handleCommonComCmdBits( valueCmd, inResultHandling, inImmediateExec);
01073 
01074   LOW_portUsbDevice::wIndex_t indexVal = inWriteSize;
01075 
01076   usbDevice->controlMsg( vendorCmd_requestType, comm_cmdType, valueCmd,
01077                          indexVal, 0x0000, 0, comCmd_usbTimeout);
01078 }
01079 
01080 
01081 void LOW_linkDS2490::comCmd_matchAccess( const uint8_t inMatchCommand,
01082                                          const bool inBusResetBefore,
01083                                          const bool inEnableSpeedChange,
01084                                          const OWSPEED_val_t inSpeedSelector,
01085                                          const resultHandling_t inResultHandling,
01086                                          const bool inImmediateExec)
01087 {
01088   // locking done in publicly accessible methods
01089 
01090   LOW_portUsbDevice::wValue_t valueCmd = matchAccess_comCmdBase;
01091   if ( inBusResetBefore )    valueCmd |= RST_bitmask;
01092   if ( inEnableSpeedChange ) valueCmd |= SE_bitmask;
01093   handleCommonComCmdBits( valueCmd, inResultHandling, inImmediateExec);
01094 
01095   LOW_portUsbDevice::wIndex_t indexVal = ((inSpeedSelector&0xff)<<8) | (inMatchCommand&0xff);
01096 
01097   usbDevice->controlMsg( vendorCmd_requestType, comm_cmdType, valueCmd,
01098                          indexVal, 0x0000, 0, comCmd_usbTimeout);
01099 }
01100 
01101 
01102 void LOW_linkDS2490::comCmd_readStraight( const uint8_t inWritePreambleSize,
01103                                           const uint16_t inReadSize,
01104                                           const bool inBusResetBefore,
01105                                           const resultHandling_t inResultHandling,
01106                                           const bool inImmediateExec)
01107 {
01108   // locking done in publicly accessible methods
01109 
01110   LOW_portUsbDevice::wValue_t valueCmd = readStraight_comCmdBase;
01111   if ( inBusResetBefore ) valueCmd = 0x0000 | ((inWritePreambleSize&0xff)<<8);
01112 
01113   // special bit positions for this command
01114   switch ( inResultHandling ) {
01115     case noResult_rsltHdl:      valueCmd |= 0x0004; break;  // NTF=x  ICP=1
01116     case resultOnError_rsltHdl:                     break;  // NTF=0  ICP=0
01117     case resultAlways_rsltHdl:  valueCmd |= 0x0008; break;  // NTF=1  ICP=0
01118     default :                   throw internal_error( "Unknown resultHandling_t value detected", __FILE__, __LINE__);
01119   }
01120   if ( inBusResetBefore )       valueCmd |= 0x0002;  // RST=1
01121   if ( inImmediateExec )        valueCmd |= 0x0001;  // IM=1
01122   
01123   LOW_portUsbDevice::wIndex_t indexVal = inReadSize;
01124 
01125   LOW_portUsbDevice::wLength_t lengthVal = 0x0000 | inWritePreambleSize;
01126 
01127   usbDevice->controlMsg( vendorCmd_requestType, comm_cmdType, valueCmd,
01128                          indexVal, lengthVal, 0, comCmd_usbTimeout);
01129 }
01130 
01131 
01132 void LOW_linkDS2490::comCmd_doAndRelease( const uint8_t inWritePreambleSize,
01133                                           const bool inDoReadOperation,
01134                                           const bool inDoStrongPullup,
01135                                           const bool inFlushBuffersOnErr,
01136                                           const resultHandling_t inResultHandling,
01137                                           const bool inImmediateExec)
01138 {
01139   // locking done in publicly accessible methods
01140 
01141   LOW_portUsbDevice::wValue_t valueCmd = doAndRelease_comCmdBase;
01142   if ( inDoReadOperation )   valueCmd |= R_bitmask;
01143   if ( inDoStrongPullup )    valueCmd |= SPU_bitmask;
01144   if ( inFlushBuffersOnErr ) valueCmd |= F_bitmask;
01145   handleCommonComCmdBits( valueCmd, inResultHandling, inImmediateExec);
01146 
01147   LOW_portUsbDevice::wIndex_t indexVal = 0x0000 | inWritePreambleSize;
01148 
01149   usbDevice->controlMsg( vendorCmd_requestType, comm_cmdType, valueCmd,
01150                          indexVal, 0x0000, 0, comCmd_usbTimeout);
01151 }
01152 
01153 
01154 void LOW_linkDS2490::comCmd_setPath( const uint8_t inPreloadPathSize,
01155                                      const bool inBusResetBefore,
01156                                      const bool inFlushBuffersOnErr,
01157                                      const resultHandling_t inResultHandling,
01158                                      const bool inImmediateExec)
01159 {
01160   // locking done in publicly accessible methods
01161 
01162   LOW_portUsbDevice::wValue_t valueCmd = setPath_comCmdBase;
01163   if ( inBusResetBefore )    valueCmd |= RST_bitmask;
01164   if ( inFlushBuffersOnErr ) valueCmd |= F_bitmask;
01165   handleCommonComCmdBits( valueCmd, inResultHandling, inImmediateExec);
01166 
01167   LOW_portUsbDevice::wIndex_t indexVal = 0x0000 | inPreloadPathSize;
01168 
01169   usbDevice->controlMsg( vendorCmd_requestType, comm_cmdType, valueCmd,
01170                          indexVal, 0x0000, 0, comCmd_usbTimeout);
01171 }
01172 
01173 
01174 void LOW_linkDS2490::comCmd_writeSramPage( const uint8_t inWriteSize,
01175                                            const bool inShortPreambleSize,
01176                                            const bool inActivateCrc16,
01177                                            const bool inFlushBuffersOnErr,
01178                                            const resultHandling_t inResultHandling,
01179                                            const bool inImmediateExec)
01180 {
01181   // locking done in publicly accessible methods
01182 
01183   LOW_portUsbDevice::wValue_t valueCmd = writeSramPage_comCmdBase;
01184   if ( inShortPreambleSize ) valueCmd |= PS_bitmask;
01185   if ( inActivateCrc16 )     valueCmd |= DT_bitmask;
01186   if ( inFlushBuffersOnErr ) valueCmd |= F_bitmask;
01187   handleCommonComCmdBits( valueCmd, inResultHandling, inImmediateExec);
01188 
01189   LOW_portUsbDevice::wIndex_t indexVal = 0x0000 | inWriteSize;
01190 
01191   usbDevice->controlMsg( vendorCmd_requestType, comm_cmdType, valueCmd,
01192                          indexVal, 0x0000, 0, comCmd_usbTimeout);
01193 }
01194 
01195 
01196 void LOW_linkDS2490::comCmd_writeEprom( const uint16_t inWriteSize,
01197                                         const bool inActivateCrc16,
01198                                         const bool inCheck0BitsOnly,
01199                                         const bool inFlushBuffersOnErr,
01200                                         const resultHandling_t inResultHandling,
01201                                         const bool inImmediateExec)
01202 {
01203   // locking done in publicly accessible methods
01204 
01205   LOW_portUsbDevice::wValue_t valueCmd = writeEprom_comCmdBase;
01206   if ( inActivateCrc16 )     valueCmd |= DT_bitmask;
01207   if ( inCheck0BitsOnly )    valueCmd |= Z_bitmask;
01208   if ( inFlushBuffersOnErr ) valueCmd |= F_bitmask;
01209   handleCommonComCmdBits( valueCmd, inResultHandling, inImmediateExec);
01210 
01211   LOW_portUsbDevice::wIndex_t indexVal = inWriteSize;
01212 
01213   usbDevice->controlMsg( vendorCmd_requestType, comm_cmdType, valueCmd,
01214                          indexVal, 0x0000, 0, comCmd_usbTimeout);
01215 }
01216 
01217 
01218 void LOW_linkDS2490::comCmd_readCrcProtPage( const uint8_t inPageCount,
01219                                              const uint8_t inPageSizeLog2,
01220                                              const bool inShortPreambleSize,
01221                                              const bool inActivateCrc16,
01222                                              const bool inFlushBuffersOnErr,
01223                                              const resultHandling_t inResultHandling,
01224                                              const bool inImmediateExec)
01225 {
01226   // locking done in publicly accessible methods
01227 
01228   LOW_portUsbDevice::wValue_t valueCmd = readCrcProtPage_comCmdBase;
01229   if ( inShortPreambleSize ) valueCmd |= PS_bitmask;
01230   if ( inActivateCrc16 )     valueCmd |= DT_bitmask;
01231   if ( inFlushBuffersOnErr ) valueCmd |= F_bitmask;
01232   handleCommonComCmdBits( valueCmd, inResultHandling, inImmediateExec);
01233 
01234   LOW_portUsbDevice::wIndex_t indexVal = ((inPageCount&0xff)<<8) | (inPageSizeLog2&0xff);
01235 
01236   usbDevice->controlMsg( vendorCmd_requestType, comm_cmdType, valueCmd,
01237                          indexVal, 0x0000, 0, comCmd_usbTimeout);
01238 }
01239 
01240 
01241 void LOW_linkDS2490::comCmd_readRedirectPageCrc( const uint8_t inPageNumber,
01242                                                  const uint8_t inPageSize,
01243                                                  const bool inFollowRedirect,
01244                                                  const bool inFlushBuffersOnErr,
01245                                                  const resultHandling_t inResultHandling,
01246                                                  const bool inImmediateExec)
01247 {
01248   // locking done in publicly accessible methods
01249 
01250   LOW_portUsbDevice::wValue_t valueCmd = readRedirectPageCrc_comCmdBase;
01251   if ( inFollowRedirect )    valueCmd |= CH_bitmask;
01252   if ( inFlushBuffersOnErr ) valueCmd |= F_bitmask;
01253   handleCommonComCmdBits( valueCmd, inResultHandling, inImmediateExec);
01254 
01255   LOW_portUsbDevice::wIndex_t indexVal = ((inPageNumber&0xff)<<8) | (inPageSize&0xff);
01256 
01257   usbDevice->controlMsg( vendorCmd_requestType, comm_cmdType, valueCmd,
01258                          indexVal, 0x0000, 0, comCmd_usbTimeout);
01259 }
01260 
01261 
01262 void LOW_linkDS2490::comCmd_searchAccess( const uint8_t inMaxDevNum,
01263                                           const uint8_t inSearchCommand,
01264                                           const bool inSearchWithoutFullAccess,
01265                                           const bool inReturnDiscrepancyInfo,
01266                                           const bool inBusResetBefore,
01267                                           const bool inFlushBuffersOnErr,
01268                                           const resultHandling_t inResultHandling,
01269                                           const bool inImmediateExec)
01270 {
01271   // locking done in publicly accessible methods
01272 
01273   LOW_portUsbDevice::wValue_t valueCmd = searchAccess_comCmdBase;
01274   if ( inSearchWithoutFullAccess ) valueCmd |= SM_bitmask;
01275   if ( inReturnDiscrepancyInfo )   valueCmd |= RTS_bitmask;
01276   if ( inBusResetBefore )          valueCmd |= RST_bitmask;
01277   if ( inFlushBuffersOnErr )       valueCmd |= F_bitmask;
01278   handleCommonComCmdBits( valueCmd, inResultHandling, inImmediateExec);
01279 
01280   LOW_portUsbDevice::wIndex_t indexVal = ((inMaxDevNum&0xff)<<8) | (inSearchCommand&0xff);
01281 
01282   usbDevice->controlMsg( vendorCmd_requestType, comm_cmdType, valueCmd,
01283                          indexVal, 0x0000, 0, comCmd_usbTimeout);
01284 }
01285 
01286 
01287 void LOW_linkDS2490::handleCommonComCmdBits( LOW_portUsbDevice::wValue_t &inOutValueCmd,
01288                                              const resultHandling_t inResultHandling, const bool inImmediateExec)
01289 {
01290   // locking done in publicly accessible methods
01291 
01292   // special bit positions for this command
01293   switch ( inResultHandling ) {
01294     case noResult_rsltHdl:      inOutValueCmd |= ICP_bitmask; break;  // NTF=x  ICP=1
01295     case resultOnError_rsltHdl:                               break;  // NTF=0  ICP=0
01296     case resultAlways_rsltHdl:  inOutValueCmd |= NTF_bitmask; break;  // NTF=1  ICP=0
01297     default :                   throw internal_error( "Unknown resultHandling_t value detected", __FILE__, __LINE__);
01298   }
01299   if ( inImmediateExec )        inOutValueCmd |= IM_bitmask;  // IM=1
01300 }
01301 
01302 
01303 
01304 
01305 //-------------------------------------------------------------------------------------
01306 //
01307 // Enumeration type conversion methods
01308 //
01309 
01310 const LOW_linkDS2490::pdSlewRate_t LOW_linkDS2490::PDSR_val_2_pdSlewRate( const PDSR_val_t inPDSR_val) const
01311 {
01312   // fully const, no locking necessary
01313 
01314   switch( inPDSR_val ) {
01315     case PDSR_15:   return pdSlewRate_15;
01316     case PDSR_2_2:  return pdSlewRate_2_2;
01317     case PDSR_1_65: return pdSlewRate_1_65;
01318     case PDSR_1_37: return pdSlewRate_1_37;
01319     case PDSR_1_1:  return pdSlewRate_1_1;
01320     case PDSR_0_83: return pdSlewRate_0_83;
01321     case PDSR_0_7:  return pdSlewRate_0_7;
01322     case PDSR_0_55: return pdSlewRate_0_55;
01323     default:           throw internal_error( "Unknown PDSR_val_t value detected", __FILE__, __LINE__);
01324   }
01325 }
01326 
01327 const LOW_linkDS2490::PDSR_val_t LOW_linkDS2490::pdSlewRate_2_PDSR_val( const pdSlewRate_t inPdSlewRate_t) const
01328 {
01329   // fully const, no locking necessary
01330 
01331   switch( inPdSlewRate_t ) {
01332     case pdSlewRate_15:    return PDSR_15;
01333     case pdSlewRate_2_2:   return PDSR_2_2;
01334     case pdSlewRate_1_65:  return PDSR_1_65;
01335     case pdSlewRate_1_37:  return PDSR_1_37;
01336     case pdSlewRate_1_1:   return PDSR_1_1;
01337     case pdSlewRate_0_83:  return PDSR_0_83;
01338     case pdSlewRate_0_7:   return PDSR_0_7;
01339     case pdSlewRate_0_55:  return PDSR_0_55;
01340     default:           throw internal_error( "Unknown pdSlewRate_t value detected", __FILE__, __LINE__);
01341   }
01342 }
01343 
01344 
01345 const LOW_linkDS2490::w1LowTime_t LOW_linkDS2490::W1LT_val_2_w1LowTime( const W1LT_val_t inW1LT_val) const
01346 {
01347   // fully const, no locking necessary
01348 
01349   switch( inW1LT_val ) {
01350     case W1LT_8:  return w1LowTime_8;
01351     case W1LT_9:  return w1LowTime_9;
01352     case W1LT_10: return w1LowTime_10;
01353     case W1LT_11: return w1LowTime_11;
01354     case W1LT_12: return w1LowTime_12;
01355     case W1LT_13: return w1LowTime_13;
01356     case W1LT_14: return w1LowTime_14;
01357     case W1LT_15: return w1LowTime_15;
01358     default:      throw internal_error( "Unknown W1LT_val_t value detected", __FILE__, __LINE__);
01359   }
01360 }
01361 
01362 const LOW_linkDS2490::W1LT_val_t LOW_linkDS2490::w1LowTime_2_W1LT_val( const w1LowTime_t inW1LowTime) const
01363 {
01364   // fully const, no locking necessary
01365 
01366   switch( inW1LowTime ) {
01367     case w1LowTime_8:  return W1LT_8;
01368     case w1LowTime_9:  return W1LT_9;
01369     case w1LowTime_10: return W1LT_10;
01370     case w1LowTime_11: return W1LT_11;
01371     case w1LowTime_12: return W1LT_12;
01372     case w1LowTime_13: return W1LT_13;
01373     case w1LowTime_14: return W1LT_14;
01374     case w1LowTime_15: return W1LT_15;
01375     default:           throw internal_error( "Unknown w1LowTime_t value detected", __FILE__, __LINE__);
01376   }
01377 }
01378 
01379 
01380 const LOW_linkDS2490::soW0RecTime_t LOW_linkDS2490::SOW0RT_val_2_soW0RecTime( const SOW0RT_val_t inSOW0RT_val) const
01381 {
01382   // fully const, no locking necessary
01383 
01384   switch( inSOW0RT_val ) {
01385     case SOW0RT_3:  return soW0RecTime_3;
01386     case SOW0RT_4:  return soW0RecTime_4;
01387     case SOW0RT_5:  return soW0RecTime_5;
01388     case SOW0RT_6:  return soW0RecTime_6;
01389     case SOW0RT_7:  return soW0RecTime_7;
01390     case SOW0RT_8:  return soW0RecTime_8;
01391     case SOW0RT_9:  return soW0RecTime_9;
01392     case SOW0RT_10: return soW0RecTime_10;
01393     default:        throw internal_error( "Unknown SOW0RT_val_t value detected", __FILE__, __LINE__);
01394   }
01395 }
01396 
01397 const LOW_linkDS2490::SOW0RT_val_t LOW_linkDS2490::soW0RecTime_2_SOW0RT_val( const soW0RecTime_t inSoW0RecTime) const
01398 {
01399   // fully const, no locking necessary
01400 
01401   switch( inSoW0RecTime ) {
01402     case soW0RecTime_3:  return SOW0RT_3;
01403     case soW0RecTime_4:  return SOW0RT_4;
01404     case soW0RecTime_5:  return SOW0RT_5;
01405     case soW0RecTime_6:  return SOW0RT_6;
01406     case soW0RecTime_7:  return SOW0RT_7;
01407     case soW0RecTime_8:  return SOW0RT_8;
01408     case soW0RecTime_9:  return SOW0RT_9;
01409     case soW0RecTime_10: return SOW0RT_10;
01410     default:             throw internal_error( "Unknown soW0RecTime_t value detected", __FILE__, __LINE__);
01411   }
01412 }
01413 
01414 
01415 const LOW_linkDS2490::wireSpeed_t LOW_linkDS2490::OWSPEED_val_2_wireSpeed( const OWSPEED_val_t inOWSPEED_val) const
01416 {
01417   // fully const, no locking necessary
01418 
01419   switch( inOWSPEED_val ) {
01420     case normal_OWSPEED:    return normal_speed;
01421     case flexible_OWSPEED:  return flexible_speed;
01422     case overdrive_OWSPEED: return overdrive_speed;
01423     default:                throw internal_error( "Unknown OWSPEED_val_t value detected", __FILE__, __LINE__);
01424   }
01425 }
01426 
01427 const LOW_linkDS2490::OWSPEED_val_t LOW_linkDS2490::wireSpeed_2_OWSPEED_val( const wireSpeed_t inWireSpeed) const
01428 {
01429   // fully const, no locking necessary
01430 
01431   switch( inWireSpeed ) {
01432     case normal_speed:    return normal_OWSPEED;
01433     case flexible_speed:  return flexible_OWSPEED;
01434     case overdrive_speed: return overdrive_OWSPEED;
01435     default:              throw internal_error( "Unknown wireSpeed_t value detected", __FILE__, __LINE__);
01436   }
01437 }
01438 
01439 
01440 const uint8_t LOW_linkDS2490::strongPullup_2_spFactor( const strongPullup_t inPullup) const
01441 {
01442   // fully const, no locking necessary
01443 
01444   switch( inPullup ) {
01445     case pullUp_16_4:  return  1;
01446     case pullUp_65_5:  return  4;
01447     case pullUp_131:   return  8;
01448     case pullUp_262:   return 16;
01449     case pullUp_524:   return 32;
01450     case pullUp_1048:  return 64;
01451     default:           throw internal_error( "Unknown strongPullup_t value detected", __FILE__, __LINE__);
01452   }
01453 }
01454 
01455 
01456 const uint8_t LOW_linkDS2490::progPulse_2_ppFactor( const progPulse_t inPulse) const
01457 {
01458   // fully const, no locking necessary
01459 
01460   switch( inPulse ) {
01461     case progPulse_32:   return   4;
01462     case progPulse_64:   return   8;
01463     case progPulse_128:  return  16;
01464     case progPulse_256:  return  32;
01465     case progPulse_512:  return  64;
01466     case progPulse_1024: return 128;
01467     case progPulse_2048: return 254;
01468     default:             throw internal_error( "Unknown progPulse_t value detected", __FILE__, __LINE__);
01469   }
01470 }
01471 

Generated on Mon Oct 27 22:56:08 2003 by doxygen1.2.13.1 written by Dimitri van Heesch, © 1997-2001