トランジスタ技術2011年9月号「mbed30分クッキング」のプログラムです。

Dependencies:   mbed TextLCD SDFileSystem

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers micro.c Source File

micro.c

00001 /*****************************************************************************
00002 * file:         micro.c
00003 * abstract:     This file contains the function, xsvfExecute(),
00004 *               call for interpreting the XSVF commands.
00005 * Usage:        Call xsvfExecute() to process XSVF data.
00006 *               The XSVF data is retrieved by readByte() in ports.c
00007 *               Remove the main function if you already have one.
00008 * Options:      XSVF_SUPPORT_COMPRESSION
00009 *                   This define supports the XC9500/XL compression scheme.
00010 *                   This define adds support for XSDRINC and XSETSDRMASKS.
00011 *               XSVF_SUPPORT_ERRORCODES
00012 *                   This define causes the xsvfExecute function to return
00013 *                   an error code for specific errors.  See error codes below.
00014 *                   If this is not defined, the return value defaults to the
00015 *                   legacy values for backward compatibility:
00016 *                   1 = success;  0 = failure.
00017 * Debugging:    DEBUG_MODE (Legacy name)
00018 *               Define DEBUG_MODE to compile with debugging features.
00019 *               Both micro.c and ports.c must be compiled with the DEBUG_MODE
00020 *               defined to enable the standalone main implementation in
00021 *               micro.c that reads XSVF from a file.
00022 * History:      v2.00   - Original XSVF implementation.
00023 *               v4.04   - Added delay at end of XSIR for XC18v00 support.
00024 *                         Added new commands for CoolRunner support:
00025 *                         XSTATE, XENDIR, XENDDR
00026 *               v4.05   - Cleanup micro.c but leave ports.c intact.
00027 *               v4.06   - Fix xsvfGotoTapState for retry transition.
00028 *               v4.07   - Update example waitTime implementations for
00029 *                         compatibility with Virtex-II.
00030 *               v4.10   - Add new XSIR2 command that supports a 2-byte
00031 *                         IR-length parameter for IR shifts > 255 bits.
00032 *               v4.11   - No change.  Update version to match SVF2XSVF xlator.
00033 *               v4.14   - Added XCOMMENT.
00034 *               v5.00   - Improve XSTATE support.
00035 *                         Added XWAIT.
00036 *               v5.01   - make sure that TCK is low during RUNTEST wait for
00037 *                         XC18V00/XCF00 support.  Only change is in PORTS.C
00038 *                         waitTime() function for implementations that do NOT
00039 *                         pulse TCK during the waitTime.
00040 *****************************************************************************/
00041 
00042 /*============================================================================
00043 * #include files
00044 ============================================================================*/
00045 #include "micro.h"
00046 #include "lenval.h"
00047 #include "ports.h"
00048 #include "mbed.h"
00049 
00050 /*============================================================================
00051 * XSVF #define
00052 ============================================================================*/
00053 
00054 #define XSVF_VERSION    "5.01"
00055 
00056 /*****************************************************************************
00057 * Define:       XSVF_SUPPORT_COMPRESSION
00058 * Description:  Define this to support the XC9500/XL XSVF data compression
00059 *               scheme.
00060 *               Code size can be reduced by NOT supporting this feature.
00061 *               However, you must use the -nc (no compress) option when
00062 *               translating SVF to XSVF using the SVF2XSVF translator.
00063 *               Corresponding, uncompressed XSVF may be larger.
00064 *****************************************************************************/
00065 #ifndef XSVF_SUPPORT_COMPRESSION
00066 #define XSVF_SUPPORT_COMPRESSION    1
00067 #endif
00068 
00069 /*****************************************************************************
00070 * Define:       XSVF_SUPPORT_ERRORCODES
00071 * Description:  Define this to support the new XSVF error codes.
00072 *               (The original XSVF player just returned 1 for success and
00073 *               0 for an unspecified failure.)
00074 *****************************************************************************/
00075 #ifndef XSVF_SUPPORT_ERRORCODES
00076 #define XSVF_SUPPORT_ERRORCODES     1
00077 #endif
00078 
00079 #ifdef  XSVF_SUPPORT_ERRORCODES
00080 #define XSVF_ERRORCODE(errorCode)   errorCode
00081 #else   /* Use legacy error code */
00082 #define XSVF_ERRORCODE(errorCode)   ((errorCode==XSVF_ERROR_NONE)?1:0)
00083 #endif  /* XSVF_SUPPORT_ERRORCODES */
00084 
00085 /*============================================================================
00086 * DEBUG_MODE #define
00087 ============================================================================*/
00088 
00089 #if 0
00090 
00091 #define XSVFDBG_PRINTF(iDebugLevel,pzFormat) \
00092                 {                    printf( pzFormat ); }
00093 #define XSVFDBG_PRINTF1(iDebugLevel,pzFormat,arg1) \
00094                 {                    printf( pzFormat, arg1 ); }
00095 #define XSVFDBG_PRINTF2(iDebugLevel,pzFormat,arg1,arg2) \
00096                 {                    printf( pzFormat, arg1, arg2 ); }
00097 #define XSVFDBG_PRINTF3(iDebugLevel,pzFormat,arg1,arg2,arg3) \
00098                 {                    printf( pzFormat, arg1, arg2, arg3 ); }
00099 #define XSVFDBG_PRINTLENVAL(iDebugLevel,plenVal) \
00100                 {                    xsvfPrintLenVal(plenVal); }
00101 
00102 #else
00103 
00104 #define XSVFDBG_PRINTF(iDebugLevel,pzFormat)
00105 #define XSVFDBG_PRINTF1(iDebugLevel,pzFormat,arg1)
00106 #define XSVFDBG_PRINTF2(iDebugLevel,pzFormat,arg1,arg2)
00107 #define XSVFDBG_PRINTF3(iDebugLevel,pzFormat,arg1,arg2,arg3)
00108 #define XSVFDBG_PRINTLENVAL(iDebugLevel,plenVal)
00109 
00110 #endif
00111 
00112 /*============================================================================
00113 * XSVF Type Declarations
00114 ============================================================================*/
00115 
00116 /*****************************************************************************
00117 * Struct:       SXsvfInfo
00118 * Description:  This structure contains all of the data used during the
00119 *               execution of the XSVF.  Some data is persistent, predefined
00120 *               information (e.g. lRunTestTime).  The bulk of this struct's
00121 *               size is due to the lenVal structs (defined in lenval.h)
00122 *               which contain buffers for the active shift data.  The MAX_LEN
00123 *               #define in lenval.h defines the size of these buffers.
00124 *               These buffers must be large enough to store the longest
00125 *               shift data in your XSVF file.  For example:
00126 *                   MAX_LEN >= ( longest_shift_data_in_bits / 8 )
00127 *               Because the lenVal struct dominates the space usage of this
00128 *               struct, the rough size of this struct is:
00129 *                   sizeof( SXsvfInfo ) ~= MAX_LEN * 7 (number of lenVals)
00130 *               xsvfInitialize() contains initialization code for the data
00131 *               in this struct.
00132 *               xsvfCleanup() contains cleanup code for the data in this
00133 *               struct.
00134 *****************************************************************************/
00135 typedef struct tagSXsvfInfo {
00136     /* XSVF status information */
00137     unsigned char   ucComplete;         /* 0 = running; 1 = complete */
00138     unsigned char   ucCommand;          /* Current XSVF command byte */
00139     long            lCommandCount;      /* Number of commands processed */
00140     int             iErrorCode;         /* An error code. 0 = no error. */
00141 
00142     /* TAP state/sequencing information */
00143     unsigned char   ucTapState;         /* Current TAP state */
00144     unsigned char   ucEndIR;            /* ENDIR TAP state (See SVF) */
00145     unsigned char   ucEndDR;            /* ENDDR TAP state (See SVF) */
00146 
00147     /* RUNTEST information */
00148     unsigned char   ucMaxRepeat;        /* Max repeat loops (for xc9500/xl) */
00149     long            lRunTestTime;       /* Pre-specified RUNTEST time (usec) */
00150 
00151     /* Shift Data Info and Buffers */
00152     long            lShiftLengthBits;   /* Len. current shift data in bits */
00153     short           sShiftLengthBytes;  /* Len. current shift data in bytes */
00154 
00155     lenVal          lvTdi;              /* Current TDI shift data */
00156     lenVal          lvTdoExpected;      /* Expected TDO shift data */
00157     lenVal          lvTdoCaptured;      /* Captured TDO shift data */
00158     lenVal          lvTdoMask;          /* TDO mask: 0=dontcare; 1=compare */
00159 
00160 #ifdef  XSVF_SUPPORT_COMPRESSION
00161     /* XSDRINC Data Buffers */
00162     lenVal          lvAddressMask;      /* Address mask for XSDRINC */
00163     lenVal          lvDataMask;         /* Data mask for XSDRINC */
00164     lenVal          lvNextData;         /* Next data for XSDRINC */
00165 #endif  /* XSVF_SUPPORT_COMPRESSION */
00166 } SXsvfInfo;
00167 
00168 /* Declare pointer to functions that perform XSVF commands */
00169 typedef int (*TXsvfDoCmdFuncPtr)( SXsvfInfo* );
00170 
00171 
00172 /*============================================================================
00173 * XSVF Command Bytes
00174 ============================================================================*/
00175 
00176 /* encodings of xsvf instructions */
00177 #define XCOMPLETE        0
00178 #define XTDOMASK         1
00179 #define XSIR             2
00180 #define XSDR             3
00181 #define XRUNTEST         4
00182 /* Reserved              5 */
00183 /* Reserved              6 */
00184 #define XREPEAT          7
00185 #define XSDRSIZE         8
00186 #define XSDRTDO          9
00187 #define XSETSDRMASKS     10
00188 #define XSDRINC          11
00189 #define XSDRB            12
00190 #define XSDRC            13
00191 #define XSDRE            14
00192 #define XSDRTDOB         15
00193 #define XSDRTDOC         16
00194 #define XSDRTDOE         17
00195 #define XSTATE           18         /* 4.00 */
00196 #define XENDIR           19         /* 4.04 */
00197 #define XENDDR           20         /* 4.04 */
00198 #define XSIR2            21         /* 4.10 */
00199 #define XCOMMENT         22         /* 4.14 */
00200 #define XWAIT            23         /* 5.00 */
00201 /* Insert new commands here */
00202 /* and add corresponding xsvfDoCmd function to xsvf_pfDoCmd below. */
00203 #define XLASTCMD         24         /* Last command marker */
00204 
00205 
00206 /*============================================================================
00207 * XSVF Command Parameter Values
00208 ============================================================================*/
00209 
00210 #define XSTATE_RESET     0          /* 4.00 parameter for XSTATE */
00211 #define XSTATE_RUNTEST   1          /* 4.00 parameter for XSTATE */
00212 
00213 #define XENDXR_RUNTEST   0          /* 4.04 parameter for XENDIR/DR */
00214 #define XENDXR_PAUSE     1          /* 4.04 parameter for XENDIR/DR */
00215 
00216 /* TAP states */
00217 #define XTAPSTATE_RESET     0x00
00218 #define XTAPSTATE_RUNTEST   0x01    /* a.k.a. IDLE */
00219 #define XTAPSTATE_SELECTDR  0x02
00220 #define XTAPSTATE_CAPTUREDR 0x03
00221 #define XTAPSTATE_SHIFTDR   0x04
00222 #define XTAPSTATE_EXIT1DR   0x05
00223 #define XTAPSTATE_PAUSEDR   0x06
00224 #define XTAPSTATE_EXIT2DR   0x07
00225 #define XTAPSTATE_UPDATEDR  0x08
00226 #define XTAPSTATE_IRSTATES  0x09    /* All IR states begin here */
00227 #define XTAPSTATE_SELECTIR  0x09
00228 #define XTAPSTATE_CAPTUREIR 0x0A
00229 #define XTAPSTATE_SHIFTIR   0x0B
00230 #define XTAPSTATE_EXIT1IR   0x0C
00231 #define XTAPSTATE_PAUSEIR   0x0D
00232 #define XTAPSTATE_EXIT2IR   0x0E
00233 #define XTAPSTATE_UPDATEIR  0x0F
00234 
00235 /*============================================================================
00236 * XSVF Function Prototypes
00237 ============================================================================*/
00238 
00239 int xsvfDoIllegalCmd( SXsvfInfo* pXsvfInfo );   /* Illegal command function */
00240 int xsvfDoXCOMPLETE( SXsvfInfo* pXsvfInfo );
00241 int xsvfDoXTDOMASK( SXsvfInfo* pXsvfInfo );
00242 int xsvfDoXSIR( SXsvfInfo* pXsvfInfo );
00243 int xsvfDoXSIR2( SXsvfInfo* pXsvfInfo );
00244 int xsvfDoXSDR( SXsvfInfo* pXsvfInfo );
00245 int xsvfDoXRUNTEST( SXsvfInfo* pXsvfInfo );
00246 int xsvfDoXREPEAT( SXsvfInfo* pXsvfInfo );
00247 int xsvfDoXSDRSIZE( SXsvfInfo* pXsvfInfo );
00248 int xsvfDoXSDRTDO( SXsvfInfo* pXsvfInfo );
00249 int xsvfDoXSETSDRMASKS( SXsvfInfo* pXsvfInfo );
00250 int xsvfDoXSDRINC( SXsvfInfo* pXsvfInfo );
00251 int xsvfDoXSDRBCE( SXsvfInfo* pXsvfInfo );
00252 int xsvfDoXSDRTDOBCE( SXsvfInfo* pXsvfInfo );
00253 int xsvfDoXSTATE( SXsvfInfo* pXsvfInfo );
00254 int xsvfDoXENDXR( SXsvfInfo* pXsvfInfo );
00255 int xsvfDoXCOMMENT( SXsvfInfo* pXsvfInfo );
00256 int xsvfDoXWAIT( SXsvfInfo* pXsvfInfo );
00257 /* Insert new command functions here */
00258 int xsvfExecute();
00259 
00260 /*============================================================================
00261 * XSVF Global Variables
00262 ============================================================================*/
00263 
00264 /* Array of XSVF command functions.  Must follow command byte value order! */
00265 /* If your compiler cannot take this form, then convert to a switch statement*/
00266 TXsvfDoCmdFuncPtr   xsvf_pfDoCmd[]  = {
00267     xsvfDoXCOMPLETE,        /*  0 */
00268     xsvfDoXTDOMASK,         /*  1 */
00269     xsvfDoXSIR,             /*  2 */
00270     xsvfDoXSDR,             /*  3 */
00271     xsvfDoXRUNTEST,         /*  4 */
00272     xsvfDoIllegalCmd,       /*  5 */
00273     xsvfDoIllegalCmd,       /*  6 */
00274     xsvfDoXREPEAT,          /*  7 */
00275     xsvfDoXSDRSIZE,         /*  8 */
00276     xsvfDoXSDRTDO,          /*  9 */
00277 #ifdef  XSVF_SUPPORT_COMPRESSION
00278     xsvfDoXSETSDRMASKS,     /* 10 */
00279     xsvfDoXSDRINC,          /* 11 */
00280 #else
00281     xsvfDoIllegalCmd,       /* 10 */
00282     xsvfDoIllegalCmd,       /* 11 */
00283 #endif  /* XSVF_SUPPORT_COMPRESSION */
00284     xsvfDoXSDRBCE,          /* 12 */
00285     xsvfDoXSDRBCE,          /* 13 */
00286     xsvfDoXSDRBCE,          /* 14 */
00287     xsvfDoXSDRTDOBCE,       /* 15 */
00288     xsvfDoXSDRTDOBCE,       /* 16 */
00289     xsvfDoXSDRTDOBCE,       /* 17 */
00290     xsvfDoXSTATE,           /* 18 */
00291     xsvfDoXENDXR,           /* 19 */
00292     xsvfDoXENDXR,           /* 20 */
00293     xsvfDoXSIR2,            /* 21 */
00294     xsvfDoXCOMMENT,         /* 22 */
00295     xsvfDoXWAIT             /* 23 */
00296     /* Insert new command functions here */
00297 };
00298 
00299 char* xsvf_pzCommandName[]  = {
00300     "XCOMPLETE",
00301     "XTDOMASK",
00302     "XSIR",
00303     "XSDR",
00304     "XRUNTEST",
00305     "Reserved5",
00306     "Reserved6",
00307     "XREPEAT",
00308     "XSDRSIZE",
00309     "XSDRTDO",
00310     "XSETSDRMASKS",
00311     "XSDRINC",
00312     "XSDRB",
00313     "XSDRC",
00314     "XSDRE",
00315     "XSDRTDOB",
00316     "XSDRTDOC",
00317     "XSDRTDOE",
00318     "XSTATE",
00319     "XENDIR",
00320     "XENDDR",
00321     "XSIR2",
00322     "XCOMMENT",
00323     "XWAIT"
00324 };
00325 
00326 char*   xsvf_pzErrorName[]  = {
00327     "No error",
00328     "ERROR:  Unknown",
00329     "ERROR:  TDO mismatch",
00330     "ERROR:  TDO mismatch and exceeded max retries",
00331     "ERROR:  Unsupported XSVF command",
00332     "ERROR:  Illegal state specification",
00333     "ERROR:  Data overflows allocated MAX_LEN buffer size"
00334 };
00335 
00336 char*   xsvf_pzTapState[] = {
00337     "RESET",        /* 0x00 */
00338     "RUNTEST/IDLE", /* 0x01 */
00339     "DRSELECT",     /* 0x02 */
00340     "DRCAPTURE",    /* 0x03 */
00341     "DRSHIFT",      /* 0x04 */
00342     "DREXIT1",      /* 0x05 */
00343     "DRPAUSE",      /* 0x06 */
00344     "DREXIT2",      /* 0x07 */
00345     "DRUPDATE",     /* 0x08 */
00346     "IRSELECT",     /* 0x09 */
00347     "IRCAPTURE",    /* 0x0A */
00348     "IRSHIFT",      /* 0x0B */
00349     "IREXIT1",      /* 0x0C */
00350     "IRPAUSE",      /* 0x0D */
00351     "IREXIT2",      /* 0x0E */
00352     "IRUPDATE"      /* 0x0F */
00353 };
00354 
00355 /*============================================================================
00356 * Utility Functions
00357 ============================================================================*/
00358 
00359 /*****************************************************************************
00360 * Function:     xsvfPrintLenVal
00361 * Description:  Print the lenval value in hex.
00362 * Parameters:   plv     - ptr to lenval.
00363 * Returns:      void.
00364 *****************************************************************************/
00365 void xsvfPrintLenVal( lenVal *plv ) {
00366     int i;
00367 
00368     if ( plv ) {
00369         printf( "0x" );
00370         for ( i = 0; i < plv->len; ++i ) {
00371             printf( "%02x", ((unsigned int)(plv->val[ i ])) );
00372         }
00373     }
00374 }
00375 
00376 /*****************************************************************************
00377 * Function:     xsvfInfoInit
00378 * Description:  Initialize the xsvfInfo data.
00379 * Parameters:   pXsvfInfo   - ptr to the XSVF info structure.
00380 * Returns:      int         - 0 = success; otherwise error.
00381 *****************************************************************************/
00382 int xsvfInfoInit( SXsvfInfo* pXsvfInfo ) {
00383     XSVFDBG_PRINTF1( 4, "    sizeof( SXsvfInfo ) = %d bytes\n",
00384                      sizeof( SXsvfInfo ) );
00385 
00386     pXsvfInfo->ucComplete       = 0;
00387     pXsvfInfo->ucCommand        = XCOMPLETE;
00388     pXsvfInfo->lCommandCount    = 0;
00389     pXsvfInfo->iErrorCode       = XSVF_ERROR_NONE;
00390     pXsvfInfo->ucMaxRepeat      = 0;
00391     pXsvfInfo->ucTapState       = XTAPSTATE_RESET;
00392     pXsvfInfo->ucEndIR          = XTAPSTATE_RUNTEST;
00393     pXsvfInfo->ucEndDR          = XTAPSTATE_RUNTEST;
00394     pXsvfInfo->lShiftLengthBits = 0L;
00395     pXsvfInfo->sShiftLengthBytes= 0;
00396     pXsvfInfo->lRunTestTime     = 0L;
00397 
00398     return( 0 );
00399 }
00400 
00401 /*****************************************************************************
00402 * Function:     xsvfInfoCleanup
00403 * Description:  Cleanup the xsvfInfo data.
00404 * Parameters:   pXsvfInfo   - ptr to the XSVF info structure.
00405 * Returns:      void.
00406 *****************************************************************************/
00407 void xsvfInfoCleanup( SXsvfInfo* pXsvfInfo ) {
00408 }
00409 
00410 /*****************************************************************************
00411 * Function:     xsvfGetAsNumBytes
00412 * Description:  Calculate the number of bytes the given number of bits
00413 *               consumes.
00414 * Parameters:   lNumBits    - the number of bits.
00415 * Returns:      short       - the number of bytes to store the number of bits.
00416 *****************************************************************************/
00417 short xsvfGetAsNumBytes( long lNumBits ) {
00418     return( (short)( ( lNumBits + 7L ) / 8L ) );
00419 }
00420 
00421 /*****************************************************************************
00422 * Function:     xsvfTmsTransition
00423 * Description:  Apply TMS and transition TAP controller by applying one TCK
00424 *               cycle.
00425 * Parameters:   sTms    - new TMS value.
00426 * Returns:      void.
00427 *****************************************************************************/
00428 void xsvfTmsTransition( short sTms ) {
00429     setPort( TMS, sTms );
00430     setPort( TCK, 0 );
00431     setPort( TCK, 1 );
00432 }
00433 
00434 /*****************************************************************************
00435 * Function:     xsvfGotoTapState
00436 * Description:  From the current TAP state, go to the named TAP state.
00437 *               A target state of RESET ALWAYS causes TMS reset sequence.
00438 *               All SVF standard stable state paths are supported.
00439 *               All state transitions are supported except for the following
00440 *               which cause an XSVF_ERROR_ILLEGALSTATE:
00441 *                   - Target==DREXIT2;  Start!=DRPAUSE
00442 *                   - Target==IREXIT2;  Start!=IRPAUSE
00443 * Parameters:   pucTapState     - Current TAP state; returns final TAP state.
00444 *               ucTargetState   - New target TAP state.
00445 * Returns:      int             - 0 = success; otherwise error.
00446 *****************************************************************************/
00447 int xsvfGotoTapState( unsigned char*   pucTapState,
00448                       unsigned char    ucTargetState ) {
00449     int i;
00450     int iErrorCode;
00451 
00452     iErrorCode  = XSVF_ERROR_NONE;
00453     if ( ucTargetState == XTAPSTATE_RESET ) {
00454         /* If RESET, always perform TMS reset sequence to reset/sync TAPs */
00455         xsvfTmsTransition( 1 );
00456         for ( i = 0; i < 5; ++i ) {
00457             setPort( TCK, 0 );
00458             setPort( TCK, 1 );
00459         }
00460         *pucTapState    = XTAPSTATE_RESET;
00461         XSVFDBG_PRINTF( 3, "   TMS Reset Sequence -> Test-Logic-Reset\n" );
00462         XSVFDBG_PRINTF1( 3, "   TAP State = %s\n",
00463                          xsvf_pzTapState[ *pucTapState ] );
00464     } else if ( ( ucTargetState != *pucTapState ) &&
00465                 ( ( ( ucTargetState == XTAPSTATE_EXIT2DR ) && ( *pucTapState != XTAPSTATE_PAUSEDR ) ) ||
00466                   ( ( ucTargetState == XTAPSTATE_EXIT2IR ) && ( *pucTapState != XTAPSTATE_PAUSEIR ) ) ) ) {
00467         /* Trap illegal TAP state path specification */
00468         iErrorCode      = XSVF_ERROR_ILLEGALSTATE;
00469     } else {
00470         if ( ucTargetState == *pucTapState ) {
00471             /* Already in target state.  Do nothing except when in DRPAUSE
00472                or in IRPAUSE to comply with SVF standard */
00473             if ( ucTargetState == XTAPSTATE_PAUSEDR ) {
00474                 xsvfTmsTransition( 1 );
00475                 *pucTapState    = XTAPSTATE_EXIT2DR;
00476                 XSVFDBG_PRINTF1( 3, "   TAP State = %s\n",
00477                                  xsvf_pzTapState[ *pucTapState ] );
00478             } else if ( ucTargetState == XTAPSTATE_PAUSEIR ) {
00479                 xsvfTmsTransition( 1 );
00480                 *pucTapState    = XTAPSTATE_EXIT2IR;
00481                 XSVFDBG_PRINTF1( 3, "   TAP State = %s\n",
00482                                  xsvf_pzTapState[ *pucTapState ] );
00483             }
00484         }
00485 
00486         /* Perform TAP state transitions to get to the target state */
00487         while ( ucTargetState != *pucTapState ) {
00488             switch ( *pucTapState ) {
00489                 case XTAPSTATE_RESET:
00490                     xsvfTmsTransition( 0 );
00491                     *pucTapState    = XTAPSTATE_RUNTEST;
00492                     break;
00493                 case XTAPSTATE_RUNTEST:
00494                     xsvfTmsTransition( 1 );
00495                     *pucTapState    = XTAPSTATE_SELECTDR;
00496                     break;
00497                 case XTAPSTATE_SELECTDR:
00498                     if ( ucTargetState >= XTAPSTATE_IRSTATES ) {
00499                         xsvfTmsTransition( 1 );
00500                         *pucTapState    = XTAPSTATE_SELECTIR;
00501                     } else {
00502                         xsvfTmsTransition( 0 );
00503                         *pucTapState    = XTAPSTATE_CAPTUREDR;
00504                     }
00505                     break;
00506                 case XTAPSTATE_CAPTUREDR:
00507                     if ( ucTargetState == XTAPSTATE_SHIFTDR ) {
00508                         xsvfTmsTransition( 0 );
00509                         *pucTapState    = XTAPSTATE_SHIFTDR;
00510                     } else {
00511                         xsvfTmsTransition( 1 );
00512                         *pucTapState    = XTAPSTATE_EXIT1DR;
00513                     }
00514                     break;
00515                 case XTAPSTATE_SHIFTDR:
00516                     xsvfTmsTransition( 1 );
00517                     *pucTapState    = XTAPSTATE_EXIT1DR;
00518                     break;
00519                 case XTAPSTATE_EXIT1DR:
00520                     if ( ucTargetState == XTAPSTATE_PAUSEDR ) {
00521                         xsvfTmsTransition( 0 );
00522                         *pucTapState    = XTAPSTATE_PAUSEDR;
00523                     } else {
00524                         xsvfTmsTransition( 1 );
00525                         *pucTapState    = XTAPSTATE_UPDATEDR;
00526                     }
00527                     break;
00528                 case XTAPSTATE_PAUSEDR:
00529                     xsvfTmsTransition( 1 );
00530                     *pucTapState    = XTAPSTATE_EXIT2DR;
00531                     break;
00532                 case XTAPSTATE_EXIT2DR:
00533                     if ( ucTargetState == XTAPSTATE_SHIFTDR ) {
00534                         xsvfTmsTransition( 0 );
00535                         *pucTapState    = XTAPSTATE_SHIFTDR;
00536                     } else {
00537                         xsvfTmsTransition( 1 );
00538                         *pucTapState    = XTAPSTATE_UPDATEDR;
00539                     }
00540                     break;
00541                 case XTAPSTATE_UPDATEDR:
00542                     if ( ucTargetState == XTAPSTATE_RUNTEST ) {
00543                         xsvfTmsTransition( 0 );
00544                         *pucTapState    = XTAPSTATE_RUNTEST;
00545                     } else {
00546                         xsvfTmsTransition( 1 );
00547                         *pucTapState    = XTAPSTATE_SELECTDR;
00548                     }
00549                     break;
00550                 case XTAPSTATE_SELECTIR:
00551                     xsvfTmsTransition( 0 );
00552                     *pucTapState    = XTAPSTATE_CAPTUREIR;
00553                     break;
00554                 case XTAPSTATE_CAPTUREIR:
00555                     if ( ucTargetState == XTAPSTATE_SHIFTIR ) {
00556                         xsvfTmsTransition( 0 );
00557                         *pucTapState    = XTAPSTATE_SHIFTIR;
00558                     } else {
00559                         xsvfTmsTransition( 1 );
00560                         *pucTapState    = XTAPSTATE_EXIT1IR;
00561                     }
00562                     break;
00563                 case XTAPSTATE_SHIFTIR:
00564                     xsvfTmsTransition( 1 );
00565                     *pucTapState    = XTAPSTATE_EXIT1IR;
00566                     break;
00567                 case XTAPSTATE_EXIT1IR:
00568                     if ( ucTargetState == XTAPSTATE_PAUSEIR ) {
00569                         xsvfTmsTransition( 0 );
00570                         *pucTapState    = XTAPSTATE_PAUSEIR;
00571                     } else {
00572                         xsvfTmsTransition( 1 );
00573                         *pucTapState    = XTAPSTATE_UPDATEIR;
00574                     }
00575                     break;
00576                 case XTAPSTATE_PAUSEIR:
00577                     xsvfTmsTransition( 1 );
00578                     *pucTapState    = XTAPSTATE_EXIT2IR;
00579                     break;
00580                 case XTAPSTATE_EXIT2IR:
00581                     if ( ucTargetState == XTAPSTATE_SHIFTIR ) {
00582                         xsvfTmsTransition( 0 );
00583                         *pucTapState    = XTAPSTATE_SHIFTIR;
00584                     } else {
00585                         xsvfTmsTransition( 1 );
00586                         *pucTapState    = XTAPSTATE_UPDATEIR;
00587                     }
00588                     break;
00589                 case XTAPSTATE_UPDATEIR:
00590                     if ( ucTargetState == XTAPSTATE_RUNTEST ) {
00591                         xsvfTmsTransition( 0 );
00592                         *pucTapState    = XTAPSTATE_RUNTEST;
00593                     } else {
00594                         xsvfTmsTransition( 1 );
00595                         *pucTapState    = XTAPSTATE_SELECTDR;
00596                     }
00597                     break;
00598                 default:
00599                     iErrorCode      = XSVF_ERROR_ILLEGALSTATE;
00600                     *pucTapState    = ucTargetState;    /* Exit while loop */
00601                     break;
00602             }
00603             XSVFDBG_PRINTF1( 3, "   TAP State = %s\n",
00604                              xsvf_pzTapState[ *pucTapState ] );
00605         }
00606     }
00607 
00608     return( iErrorCode );
00609 }
00610 
00611 /*****************************************************************************
00612 * Function:     xsvfShiftOnly
00613 * Description:  Assumes that starting TAP state is SHIFT-DR or SHIFT-IR.
00614 *               Shift the given TDI data into the JTAG scan chain.
00615 *               Optionally, save the TDO data shifted out of the scan chain.
00616 *               Last shift cycle is special:  capture last TDO, set last TDI,
00617 *               but does not pulse TCK.  Caller must pulse TCK and optionally
00618 *               set TMS=1 to exit shift state.
00619 * Parameters:   lNumBits        - number of bits to shift.
00620 *               plvTdi          - ptr to lenval for TDI data.
00621 *               plvTdoCaptured  - ptr to lenval for storing captured TDO data.
00622 *               iExitShift      - 1=exit at end of shift; 0=stay in Shift-DR.
00623 * Returns:      void.
00624 *****************************************************************************/
00625 void xsvfShiftOnly( long    lNumBits,
00626                     lenVal* plvTdi,
00627                     lenVal* plvTdoCaptured,
00628                     int     iExitShift ) {
00629     unsigned char*  pucTdi;
00630     unsigned char*  pucTdo;
00631     unsigned char   ucTdiByte;
00632     unsigned char   ucTdoByte;
00633     unsigned char   ucTdoBit;
00634     int             i;
00635 
00636     /* assert( ( ( lNumBits + 7 ) / 8 ) == plvTdi->len ); */
00637 
00638     /* Initialize TDO storage len == TDI len */
00639     pucTdo  = 0;
00640     if ( plvTdoCaptured ) {
00641         plvTdoCaptured->len = plvTdi->len;
00642         pucTdo              = plvTdoCaptured->val + plvTdi->len;
00643     }
00644 
00645     /* Shift LSB first.  val[N-1] == LSB.  val[0] == MSB. */
00646     pucTdi  = plvTdi->val + plvTdi->len;
00647     while ( lNumBits ) {
00648         /* Process on a byte-basis */
00649         ucTdiByte   = (*(--pucTdi));
00650         ucTdoByte   = 0;
00651         for ( i = 0; ( lNumBits && ( i < 8 ) ); ++i ) {
00652             --lNumBits;
00653             if ( iExitShift && !lNumBits ) {
00654                 /* Exit Shift-DR state */
00655                 setPort( TMS, 1 );
00656             }
00657 
00658             /* Set the new TDI value */
00659             setPort( TDI, (short)(ucTdiByte & 1) );
00660             ucTdiByte   >>= 1;
00661 
00662             /* Set TCK low */
00663             setPort( TCK, 0 );
00664 
00665             if ( pucTdo ) {
00666                 /* Save the TDO value */
00667                 ucTdoBit    = readTDOBit();
00668                 ucTdoByte   |= ( ucTdoBit << i );
00669             }
00670 
00671             /* Set TCK high */
00672             setPort( TCK, 1 );
00673         }
00674 
00675         /* Save the TDO byte value */
00676         if ( pucTdo ) {
00677             (*(--pucTdo))   = ucTdoByte;
00678         }
00679     }
00680 }
00681 
00682 /*****************************************************************************
00683 * Function:     xsvfShift
00684 * Description:  Goes to the given starting TAP state.
00685 *               Calls xsvfShiftOnly to shift in the given TDI data and
00686 *               optionally capture the TDO data.
00687 *               Compares the TDO captured data against the TDO expected
00688 *               data.
00689 *               If a data mismatch occurs, then executes the exception
00690 *               handling loop upto ucMaxRepeat times.
00691 * Parameters:   pucTapState     - Ptr to current TAP state.
00692 *               ucStartState    - Starting shift state: Shift-DR or Shift-IR.
00693 *               lNumBits        - number of bits to shift.
00694 *               plvTdi          - ptr to lenval for TDI data.
00695 *               plvTdoCaptured  - ptr to lenval for storing TDO data.
00696 *               plvTdoExpected  - ptr to expected TDO data.
00697 *               plvTdoMask      - ptr to TDO mask.
00698 *               ucEndState      - state in which to end the shift.
00699 *               lRunTestTime    - amount of time to wait after the shift.
00700 *               ucMaxRepeat     - Maximum number of retries on TDO mismatch.
00701 * Returns:      int             - 0 = success; otherwise TDO mismatch.
00702 * Notes:        XC9500XL-only Optimization:
00703 *               Skip the waitTime() if plvTdoMask->val[0:plvTdoMask->len-1]
00704 *               is NOT all zeros and sMatch==1.
00705 *****************************************************************************/
00706 int xsvfShift( unsigned char*   pucTapState,
00707                unsigned char    ucStartState,
00708                long             lNumBits,
00709                lenVal*          plvTdi,
00710                lenVal*          plvTdoCaptured,
00711                lenVal*          plvTdoExpected,
00712                lenVal*          plvTdoMask,
00713                unsigned char    ucEndState,
00714                long             lRunTestTime,
00715                unsigned char    ucMaxRepeat ) {
00716     int             iErrorCode;
00717     int             iMismatch;
00718     unsigned char   ucRepeat;
00719     int             iExitShift;
00720 
00721     iErrorCode  = XSVF_ERROR_NONE;
00722     iMismatch   = 0;
00723     ucRepeat    = 0;
00724     iExitShift  = ( ucStartState != ucEndState );
00725 
00726     XSVFDBG_PRINTF1( 3, "   Shift Length = %ld\n", lNumBits );
00727     XSVFDBG_PRINTF( 4, "    TDI          = ");
00728     XSVFDBG_PRINTLENVAL( 4, plvTdi );
00729     XSVFDBG_PRINTF( 4, "\n");
00730     XSVFDBG_PRINTF( 4, "    TDO Expected = ");
00731     XSVFDBG_PRINTLENVAL( 4, plvTdoExpected );
00732     XSVFDBG_PRINTF( 4, "\n");
00733 
00734     if ( !lNumBits ) {
00735         /* Compatibility with XSVF2.00:  XSDR 0 = no shift, but wait in RTI */
00736         if ( lRunTestTime ) {
00737             /* Wait for prespecified XRUNTEST time */
00738             xsvfGotoTapState( pucTapState, XTAPSTATE_RUNTEST );
00739             XSVFDBG_PRINTF1( 3, "   Wait = %ld usec\n", lRunTestTime );
00740             waitTime( lRunTestTime );
00741         }
00742     } else {
00743         do {
00744             /* Goto Shift-DR or Shift-IR */
00745             xsvfGotoTapState( pucTapState, ucStartState );
00746 
00747             /* Shift TDI and capture TDO */
00748             xsvfShiftOnly( lNumBits, plvTdi, plvTdoCaptured, iExitShift );
00749 
00750             if ( plvTdoExpected ) {
00751                 /* Compare TDO data to expected TDO data */
00752                 iMismatch   = !EqualLenVal( plvTdoExpected,
00753                                             plvTdoCaptured,
00754                                             plvTdoMask );
00755             }
00756 
00757             if ( iExitShift ) {
00758                 /* Update TAP state:  Shift->Exit */
00759                 ++(*pucTapState);
00760                 XSVFDBG_PRINTF1( 3, "   TAP State = %s\n",
00761                                  xsvf_pzTapState[ *pucTapState ] );
00762 
00763                 if ( iMismatch && lRunTestTime && ( ucRepeat < ucMaxRepeat ) ) {
00764                     XSVFDBG_PRINTF( 4, "    TDO Expected = ");
00765                     XSVFDBG_PRINTLENVAL( 4, plvTdoExpected );
00766                     XSVFDBG_PRINTF( 4, "\n");
00767                     XSVFDBG_PRINTF( 4, "    TDO Captured = ");
00768                     XSVFDBG_PRINTLENVAL( 4, plvTdoCaptured );
00769                     XSVFDBG_PRINTF( 4, "\n");
00770                     XSVFDBG_PRINTF( 4, "    TDO Mask     = ");
00771                     XSVFDBG_PRINTLENVAL( 4, plvTdoMask );
00772                     XSVFDBG_PRINTF( 4, "\n");
00773                     XSVFDBG_PRINTF1( 3, "   Retry #%d\n", ( ucRepeat + 1 ) );
00774                     /* Do exception handling retry - ShiftDR only */
00775                     xsvfGotoTapState( pucTapState, XTAPSTATE_PAUSEDR );
00776                     /* Shift 1 extra bit */
00777                     xsvfGotoTapState( pucTapState, XTAPSTATE_SHIFTDR );
00778                     /* Increment RUNTEST time by an additional 25% */
00779                     lRunTestTime    += ( lRunTestTime >> 2 );
00780                 } else {
00781                     /* Do normal exit from Shift-XR */
00782                     xsvfGotoTapState( pucTapState, ucEndState );
00783                 }
00784 
00785                 if ( lRunTestTime ) {
00786                     /* Wait for prespecified XRUNTEST time */
00787                     xsvfGotoTapState( pucTapState, XTAPSTATE_RUNTEST );
00788                     XSVFDBG_PRINTF1( 3, "   Wait = %ld usec\n", lRunTestTime );
00789                     waitTime( lRunTestTime );
00790                 }
00791             }
00792         } while ( iMismatch && ( ucRepeat++ < ucMaxRepeat ) );
00793     }
00794 
00795     if ( iMismatch ) {
00796         XSVFDBG_PRINTF( 1, " TDO Expected = ");
00797         XSVFDBG_PRINTLENVAL( 1, plvTdoExpected );
00798         XSVFDBG_PRINTF( 1, "\n");
00799         XSVFDBG_PRINTF( 1, " TDO Captured = ");
00800         XSVFDBG_PRINTLENVAL( 1, plvTdoCaptured );
00801         XSVFDBG_PRINTF( 1, "\n");
00802         XSVFDBG_PRINTF( 1, " TDO Mask     = ");
00803         XSVFDBG_PRINTLENVAL( 1, plvTdoMask );
00804         XSVFDBG_PRINTF( 1, "\n");
00805         if ( ucMaxRepeat && ( ucRepeat > ucMaxRepeat ) ) {
00806             iErrorCode  = XSVF_ERROR_MAXRETRIES;
00807         } else {
00808             iErrorCode  = XSVF_ERROR_TDOMISMATCH;
00809         }
00810     }
00811 
00812     return( iErrorCode );
00813 }
00814 
00815 /*****************************************************************************
00816 * Function:     xsvfBasicXSDRTDO
00817 * Description:  Get the XSDRTDO parameters and execute the XSDRTDO command.
00818 *               This is the common function for all XSDRTDO commands.
00819 * Parameters:   pucTapState         - Current TAP state.
00820 *               lShiftLengthBits    - number of bits to shift.
00821 *               sShiftLengthBytes   - number of bytes to read.
00822 *               plvTdi              - ptr to lenval for TDI data.
00823 *               lvTdoCaptured       - ptr to lenval for storing TDO data.
00824 *               iEndState           - state in which to end the shift.
00825 *               lRunTestTime        - amount of time to wait after the shift.
00826 *               ucMaxRepeat         - maximum xc9500/xl retries.
00827 * Returns:      int                 - 0 = success; otherwise TDO mismatch.
00828 *****************************************************************************/
00829 int xsvfBasicXSDRTDO( unsigned char*    pucTapState,
00830                       long              lShiftLengthBits,
00831                       short             sShiftLengthBytes,
00832                       lenVal*           plvTdi,
00833                       lenVal*           plvTdoCaptured,
00834                       lenVal*           plvTdoExpected,
00835                       lenVal*           plvTdoMask,
00836                       unsigned char     ucEndState,
00837                       long              lRunTestTime,
00838                       unsigned char     ucMaxRepeat ) {
00839     readVal( plvTdi, sShiftLengthBytes );
00840     if ( plvTdoExpected ) {
00841         readVal( plvTdoExpected, sShiftLengthBytes );
00842     }
00843     return( xsvfShift( pucTapState, XTAPSTATE_SHIFTDR, lShiftLengthBits,
00844                        plvTdi, plvTdoCaptured, plvTdoExpected, plvTdoMask,
00845                        ucEndState, lRunTestTime, ucMaxRepeat ) );
00846 }
00847 
00848 /*****************************************************************************
00849 * Function:     xsvfDoSDRMasking
00850 * Description:  Update the data value with the next XSDRINC data and address.
00851 * Example:      dataVal=0x01ff, nextData=0xab, addressMask=0x0100,
00852 *               dataMask=0x00ff, should set dataVal to 0x02ab
00853 * Parameters:   plvTdi          - The current TDI value.
00854 *               plvNextData     - the next data value.
00855 *               plvAddressMask  - the address mask.
00856 *               plvDataMask     - the data mask.
00857 * Returns:      void.
00858 *****************************************************************************/
00859 #ifdef  XSVF_SUPPORT_COMPRESSION
00860 void xsvfDoSDRMasking( lenVal*  plvTdi,
00861                        lenVal*  plvNextData,
00862                        lenVal*  plvAddressMask,
00863                        lenVal*  plvDataMask ) {
00864     int             i;
00865     unsigned char   ucTdi;
00866     unsigned char   ucTdiMask;
00867     unsigned char   ucDataMask;
00868     unsigned char   ucNextData;
00869     unsigned char   ucNextMask;
00870     short           sNextData;
00871 
00872     /* add the address Mask to dataVal and return as a new dataVal */
00873     addVal( plvTdi, plvTdi, plvAddressMask );
00874 
00875     ucNextData  = 0;
00876     ucNextMask  = 0;
00877     sNextData   = plvNextData->len;
00878     for ( i = plvDataMask->len - 1; i >= 0; --i ) {
00879         /* Go through data mask in reverse order looking for mask (1) bits */
00880         ucDataMask  = plvDataMask->val[ i ];
00881         if ( ucDataMask ) {
00882             /* Retrieve the corresponding TDI byte value */
00883             ucTdi       = plvTdi->val[ i ];
00884 
00885             /* For each bit in the data mask byte, look for 1's */
00886             ucTdiMask   = 1;
00887             while ( ucDataMask ) {
00888                 if ( ucDataMask & 1 ) {
00889                     if ( !ucNextMask ) {
00890                         /* Get the next data byte */
00891                         ucNextData  = plvNextData->val[ --sNextData ];
00892                         ucNextMask  = 1;
00893                     }
00894 
00895                     /* Set or clear the data bit according to the next data */
00896                     if ( ucNextData & ucNextMask ) {
00897                         ucTdi   |= ucTdiMask;       /* Set bit */
00898                     } else {
00899                         ucTdi   &= ( ~ucTdiMask );  /* Clear bit */
00900                     }
00901 
00902                     /* Update the next data */
00903                     ucNextMask  <<= 1;
00904                 }
00905                 ucTdiMask   <<= 1;
00906                 ucDataMask  >>= 1;
00907             }
00908 
00909             /* Update the TDI value */
00910             plvTdi->val[ i ]    = ucTdi;
00911         }
00912     }
00913 }
00914 #endif  /* XSVF_SUPPORT_COMPRESSION */
00915 
00916 /*============================================================================
00917 * XSVF Command Functions (type = TXsvfDoCmdFuncPtr)
00918 * These functions update pXsvfInfo->iErrorCode only on an error.
00919 * Otherwise, the error code is left alone.
00920 * The function returns the error code from the function.
00921 ============================================================================*/
00922 
00923 /*****************************************************************************
00924 * Function:     xsvfDoIllegalCmd
00925 * Description:  Function place holder for illegal/unsupported commands.
00926 * Parameters:   pXsvfInfo   - XSVF information pointer.
00927 * Returns:      int         - 0 = success;  non-zero = error.
00928 *****************************************************************************/
00929 int xsvfDoIllegalCmd( SXsvfInfo* pXsvfInfo ) {
00930     XSVFDBG_PRINTF2( 0, "ERROR:  Encountered unsupported command #%d (%s)\n",
00931                      ((unsigned int)(pXsvfInfo->ucCommand)),
00932                      ((pXsvfInfo->ucCommand < XLASTCMD)
00933                       ? (xsvf_pzCommandName[pXsvfInfo->ucCommand])
00934                       : "Unknown") );
00935     pXsvfInfo->iErrorCode   = XSVF_ERROR_ILLEGALCMD;
00936     return( pXsvfInfo->iErrorCode );
00937 }
00938 
00939 /*****************************************************************************
00940 * Function:     xsvfDoXCOMPLETE
00941 * Description:  XCOMPLETE (no parameters)
00942 *               Update complete status for XSVF player.
00943 * Parameters:   pXsvfInfo   - XSVF information pointer.
00944 * Returns:      int         - 0 = success;  non-zero = error.
00945 *****************************************************************************/
00946 int xsvfDoXCOMPLETE( SXsvfInfo* pXsvfInfo ) {
00947     pXsvfInfo->ucComplete   = 1;
00948     return( XSVF_ERROR_NONE );
00949 }
00950 
00951 /*****************************************************************************
00952 * Function:     xsvfDoXTDOMASK
00953 * Description:  XTDOMASK <lenVal.TdoMask[XSDRSIZE]>
00954 *               Prespecify the TDO compare mask.
00955 * Parameters:   pXsvfInfo   - XSVF information pointer.
00956 * Returns:      int         - 0 = success;  non-zero = error.
00957 *****************************************************************************/
00958 int xsvfDoXTDOMASK( SXsvfInfo* pXsvfInfo ) {
00959     readVal( &(pXsvfInfo->lvTdoMask), pXsvfInfo->sShiftLengthBytes );
00960     XSVFDBG_PRINTF( 4, "    TDO Mask     = ");
00961     XSVFDBG_PRINTLENVAL( 4, &(pXsvfInfo->lvTdoMask) );
00962     XSVFDBG_PRINTF( 4, "\n");
00963     return( XSVF_ERROR_NONE );
00964 }
00965 
00966 /*****************************************************************************
00967 * Function:     xsvfDoXSIR
00968 * Description:  XSIR <(byte)shiftlen> <lenVal.TDI[shiftlen]>
00969 *               Get the instruction and shift the instruction into the TAP.
00970 *               If prespecified XRUNTEST!=0, goto RUNTEST and wait after
00971 *               the shift for XRUNTEST usec.
00972 * Parameters:   pXsvfInfo   - XSVF information pointer.
00973 * Returns:      int         - 0 = success;  non-zero = error.
00974 *****************************************************************************/
00975 int xsvfDoXSIR( SXsvfInfo* pXsvfInfo ) {
00976     unsigned char   ucShiftIrBits;
00977     short           sShiftIrBytes;
00978     int             iErrorCode;
00979 
00980     /* Get the shift length and store */
00981     readByte( &ucShiftIrBits );
00982     sShiftIrBytes   = xsvfGetAsNumBytes( ucShiftIrBits );
00983     XSVFDBG_PRINTF1( 3, "   XSIR length = %d\n",
00984                      ((unsigned int)ucShiftIrBits) );
00985 
00986     if ( sShiftIrBytes > MAX_LEN ) {
00987         iErrorCode  = XSVF_ERROR_DATAOVERFLOW;
00988     } else {
00989         /* Get and store instruction to shift in */
00990         readVal( &(pXsvfInfo->lvTdi), xsvfGetAsNumBytes( ucShiftIrBits ) );
00991 
00992         /* Shift the data */
00993         iErrorCode  = xsvfShift( &(pXsvfInfo->ucTapState), XTAPSTATE_SHIFTIR,
00994                                  ucShiftIrBits, &(pXsvfInfo->lvTdi),
00995                                  /*plvTdoCaptured*/0, /*plvTdoExpected*/0,
00996                                  /*plvTdoMask*/0, pXsvfInfo->ucEndIR,
00997                                  pXsvfInfo->lRunTestTime, /*ucMaxRepeat*/0 );
00998     }
00999 
01000     if ( iErrorCode != XSVF_ERROR_NONE ) {
01001         pXsvfInfo->iErrorCode   = iErrorCode;
01002     }
01003     return( iErrorCode );
01004 }
01005 
01006 /*****************************************************************************
01007 * Function:     xsvfDoXSIR2
01008 * Description:  XSIR <(2-byte)shiftlen> <lenVal.TDI[shiftlen]>
01009 *               Get the instruction and shift the instruction into the TAP.
01010 *               If prespecified XRUNTEST!=0, goto RUNTEST and wait after
01011 *               the shift for XRUNTEST usec.
01012 * Parameters:   pXsvfInfo   - XSVF information pointer.
01013 * Returns:      int         - 0 = success;  non-zero = error.
01014 *****************************************************************************/
01015 int xsvfDoXSIR2( SXsvfInfo* pXsvfInfo ) {
01016     long            lShiftIrBits;
01017     short           sShiftIrBytes;
01018     int             iErrorCode;
01019 
01020     /* Get the shift length and store */
01021     readVal( &(pXsvfInfo->lvTdi), 2 );
01022     lShiftIrBits    = value( &(pXsvfInfo->lvTdi) );
01023     sShiftIrBytes   = xsvfGetAsNumBytes( lShiftIrBits );
01024     XSVFDBG_PRINTF1( 3, "   XSIR2 length = %d\n", lShiftIrBits);
01025 
01026     if ( sShiftIrBytes > MAX_LEN ) {
01027         iErrorCode  = XSVF_ERROR_DATAOVERFLOW;
01028     } else {
01029         /* Get and store instruction to shift in */
01030         readVal( &(pXsvfInfo->lvTdi), xsvfGetAsNumBytes( lShiftIrBits ) );
01031 
01032         /* Shift the data */
01033         iErrorCode  = xsvfShift( &(pXsvfInfo->ucTapState), XTAPSTATE_SHIFTIR,
01034                                  lShiftIrBits, &(pXsvfInfo->lvTdi),
01035                                  /*plvTdoCaptured*/0, /*plvTdoExpected*/0,
01036                                  /*plvTdoMask*/0, pXsvfInfo->ucEndIR,
01037                                  pXsvfInfo->lRunTestTime, /*ucMaxRepeat*/0 );
01038     }
01039 
01040     if ( iErrorCode != XSVF_ERROR_NONE ) {
01041         pXsvfInfo->iErrorCode   = iErrorCode;
01042     }
01043     return( iErrorCode );
01044 }
01045 
01046 /*****************************************************************************
01047 * Function:     xsvfDoXSDR
01048 * Description:  XSDR <lenVal.TDI[XSDRSIZE]>
01049 *               Shift the given TDI data into the JTAG scan chain.
01050 *               Compare the captured TDO with the expected TDO from the
01051 *               previous XSDRTDO command using the previously specified
01052 *               XTDOMASK.
01053 * Parameters:   pXsvfInfo   - XSVF information pointer.
01054 * Returns:      int         - 0 = success;  non-zero = error.
01055 *****************************************************************************/
01056 int xsvfDoXSDR( SXsvfInfo* pXsvfInfo ) {
01057     int iErrorCode;
01058     readVal( &(pXsvfInfo->lvTdi), pXsvfInfo->sShiftLengthBytes );
01059     /* use TDOExpected from last XSDRTDO instruction */
01060     iErrorCode  = xsvfShift( &(pXsvfInfo->ucTapState), XTAPSTATE_SHIFTDR,
01061                              pXsvfInfo->lShiftLengthBits, &(pXsvfInfo->lvTdi),
01062                              &(pXsvfInfo->lvTdoCaptured),
01063                              &(pXsvfInfo->lvTdoExpected),
01064                              &(pXsvfInfo->lvTdoMask), pXsvfInfo->ucEndDR,
01065                              pXsvfInfo->lRunTestTime, pXsvfInfo->ucMaxRepeat );
01066     if ( iErrorCode != XSVF_ERROR_NONE ) {
01067         pXsvfInfo->iErrorCode   = iErrorCode;
01068     }
01069     return( iErrorCode );
01070 }
01071 
01072 /*****************************************************************************
01073 * Function:     xsvfDoXRUNTEST
01074 * Description:  XRUNTEST <uint32>
01075 *               Prespecify the XRUNTEST wait time for shift operations.
01076 * Parameters:   pXsvfInfo   - XSVF information pointer.
01077 * Returns:      int         - 0 = success;  non-zero = error.
01078 *****************************************************************************/
01079 int xsvfDoXRUNTEST( SXsvfInfo* pXsvfInfo ) {
01080     readVal( &(pXsvfInfo->lvTdi), 4 );
01081     pXsvfInfo->lRunTestTime = value( &(pXsvfInfo->lvTdi) );
01082     XSVFDBG_PRINTF1( 3, "   XRUNTEST = %ld\n", pXsvfInfo->lRunTestTime );
01083     return( XSVF_ERROR_NONE );
01084 }
01085 
01086 /*****************************************************************************
01087 * Function:     xsvfDoXREPEAT
01088 * Description:  XREPEAT <byte>
01089 *               Prespecify the maximum number of XC9500/XL retries.
01090 * Parameters:   pXsvfInfo   - XSVF information pointer.
01091 * Returns:      int         - 0 = success;  non-zero = error.
01092 *****************************************************************************/
01093 int xsvfDoXREPEAT( SXsvfInfo* pXsvfInfo ) {
01094     readByte( &(pXsvfInfo->ucMaxRepeat) );
01095     XSVFDBG_PRINTF1( 3, "   XREPEAT = %d\n",
01096                      ((unsigned int)(pXsvfInfo->ucMaxRepeat)) );
01097     return( XSVF_ERROR_NONE );
01098 }
01099 
01100 /*****************************************************************************
01101 * Function:     xsvfDoXSDRSIZE
01102 * Description:  XSDRSIZE <uint32>
01103 *               Prespecify the XRUNTEST wait time for shift operations.
01104 * Parameters:   pXsvfInfo   - XSVF information pointer.
01105 * Returns:      int         - 0 = success;  non-zero = error.
01106 *****************************************************************************/
01107 int xsvfDoXSDRSIZE( SXsvfInfo* pXsvfInfo ) {
01108     int iErrorCode;
01109     iErrorCode  = XSVF_ERROR_NONE;
01110     readVal( &(pXsvfInfo->lvTdi), 4 );
01111     pXsvfInfo->lShiftLengthBits = value( &(pXsvfInfo->lvTdi) );
01112     pXsvfInfo->sShiftLengthBytes= xsvfGetAsNumBytes( pXsvfInfo->lShiftLengthBits );
01113     XSVFDBG_PRINTF1( 3, "   XSDRSIZE = %ld\n", pXsvfInfo->lShiftLengthBits );
01114     if ( pXsvfInfo->sShiftLengthBytes > MAX_LEN ) {
01115         iErrorCode  = XSVF_ERROR_DATAOVERFLOW;
01116         pXsvfInfo->iErrorCode   = iErrorCode;
01117     }
01118     return( iErrorCode );
01119 }
01120 
01121 /*****************************************************************************
01122 * Function:     xsvfDoXSDRTDO
01123 * Description:  XSDRTDO <lenVal.TDI[XSDRSIZE]> <lenVal.TDO[XSDRSIZE]>
01124 *               Get the TDI and expected TDO values.  Then, shift.
01125 *               Compare the expected TDO with the captured TDO using the
01126 *               prespecified XTDOMASK.
01127 * Parameters:   pXsvfInfo   - XSVF information pointer.
01128 * Returns:      int         - 0 = success;  non-zero = error.
01129 *****************************************************************************/
01130 int xsvfDoXSDRTDO( SXsvfInfo* pXsvfInfo ) {
01131     int iErrorCode;
01132     iErrorCode  = xsvfBasicXSDRTDO( &(pXsvfInfo->ucTapState),
01133                                     pXsvfInfo->lShiftLengthBits,
01134                                     pXsvfInfo->sShiftLengthBytes,
01135                                     &(pXsvfInfo->lvTdi),
01136                                     &(pXsvfInfo->lvTdoCaptured),
01137                                     &(pXsvfInfo->lvTdoExpected),
01138                                     &(pXsvfInfo->lvTdoMask),
01139                                     pXsvfInfo->ucEndDR,
01140                                     pXsvfInfo->lRunTestTime,
01141                                     pXsvfInfo->ucMaxRepeat );
01142     if ( iErrorCode != XSVF_ERROR_NONE ) {
01143         pXsvfInfo->iErrorCode   = iErrorCode;
01144     }
01145     return( iErrorCode );
01146 }
01147 
01148 /*****************************************************************************
01149 * Function:     xsvfDoXSETSDRMASKS
01150 * Description:  XSETSDRMASKS <lenVal.AddressMask[XSDRSIZE]>
01151 *                            <lenVal.DataMask[XSDRSIZE]>
01152 *               Get the prespecified address and data mask for the XSDRINC
01153 *               command.
01154 *               Used for xc9500/xl compressed XSVF data.
01155 * Parameters:   pXsvfInfo   - XSVF information pointer.
01156 * Returns:      int         - 0 = success;  non-zero = error.
01157 *****************************************************************************/
01158 #ifdef  XSVF_SUPPORT_COMPRESSION
01159 int xsvfDoXSETSDRMASKS( SXsvfInfo* pXsvfInfo ) {
01160     /* read the addressMask */
01161     readVal( &(pXsvfInfo->lvAddressMask), pXsvfInfo->sShiftLengthBytes );
01162     /* read the dataMask    */
01163     readVal( &(pXsvfInfo->lvDataMask), pXsvfInfo->sShiftLengthBytes );
01164 
01165     XSVFDBG_PRINTF( 4, "    Address Mask = " );
01166     XSVFDBG_PRINTLENVAL( 4, &(pXsvfInfo->lvAddressMask) );
01167     XSVFDBG_PRINTF( 4, "\n" );
01168     XSVFDBG_PRINTF( 4, "    Data Mask    = " );
01169     XSVFDBG_PRINTLENVAL( 4, &(pXsvfInfo->lvDataMask) );
01170     XSVFDBG_PRINTF( 4, "\n" );
01171 
01172     return( XSVF_ERROR_NONE );
01173 }
01174 #endif  /* XSVF_SUPPORT_COMPRESSION */
01175 
01176 /*****************************************************************************
01177 * Function:     xsvfDoXSDRINC
01178 * Description:  XSDRINC <lenVal.firstTDI[XSDRSIZE]> <byte(numTimes)>
01179 *                       <lenVal.data[XSETSDRMASKS.dataMask.len]> ...
01180 *               Get the XSDRINC parameters and execute the XSDRINC command.
01181 *               XSDRINC starts by loading the first TDI shift value.
01182 *               Then, for numTimes, XSDRINC gets the next piece of data,
01183 *               replaces the bits from the starting TDI as defined by the
01184 *               XSETSDRMASKS.dataMask, adds the address mask from
01185 *               XSETSDRMASKS.addressMask, shifts the new TDI value,
01186 *               and compares the TDO to the expected TDO from the previous
01187 *               XSDRTDO command using the XTDOMASK.
01188 *               Used for xc9500/xl compressed XSVF data.
01189 * Parameters:   pXsvfInfo   - XSVF information pointer.
01190 * Returns:      int         - 0 = success;  non-zero = error.
01191 *****************************************************************************/
01192 #ifdef  XSVF_SUPPORT_COMPRESSION
01193 int xsvfDoXSDRINC( SXsvfInfo* pXsvfInfo ) {
01194     int             iErrorCode;
01195     int             iDataMaskLen;
01196     unsigned char   ucDataMask;
01197     unsigned char   ucNumTimes;
01198     unsigned char   i;
01199 
01200     readVal( &(pXsvfInfo->lvTdi), pXsvfInfo->sShiftLengthBytes );
01201     iErrorCode  = xsvfShift( &(pXsvfInfo->ucTapState), XTAPSTATE_SHIFTDR,
01202                              pXsvfInfo->lShiftLengthBits,
01203                              &(pXsvfInfo->lvTdi), &(pXsvfInfo->lvTdoCaptured),
01204                              &(pXsvfInfo->lvTdoExpected),
01205                              &(pXsvfInfo->lvTdoMask), pXsvfInfo->ucEndDR,
01206                              pXsvfInfo->lRunTestTime, pXsvfInfo->ucMaxRepeat );
01207     if ( !iErrorCode ) {
01208         /* Calculate number of data mask bits */
01209         iDataMaskLen    = 0;
01210         for ( i = 0; i < pXsvfInfo->lvDataMask.len; ++i ) {
01211             ucDataMask  = pXsvfInfo->lvDataMask.val[ i ];
01212             while ( ucDataMask ) {
01213                 iDataMaskLen    += ( ucDataMask & 1 );
01214                 ucDataMask      >>= 1;
01215             }
01216         }
01217 
01218         /* Get the number of data pieces, i.e. number of times to shift */
01219         readByte( &ucNumTimes );
01220 
01221         /* For numTimes, get data, fix TDI, and shift */
01222         for ( i = 0; !iErrorCode && ( i < ucNumTimes ); ++i ) {
01223             readVal( &(pXsvfInfo->lvNextData),
01224                      xsvfGetAsNumBytes( iDataMaskLen ) );
01225             xsvfDoSDRMasking( &(pXsvfInfo->lvTdi),
01226                               &(pXsvfInfo->lvNextData),
01227                               &(pXsvfInfo->lvAddressMask),
01228                               &(pXsvfInfo->lvDataMask) );
01229             iErrorCode  = xsvfShift( &(pXsvfInfo->ucTapState),
01230                                      XTAPSTATE_SHIFTDR,
01231                                      pXsvfInfo->lShiftLengthBits,
01232                                      &(pXsvfInfo->lvTdi),
01233                                      &(pXsvfInfo->lvTdoCaptured),
01234                                      &(pXsvfInfo->lvTdoExpected),
01235                                      &(pXsvfInfo->lvTdoMask),
01236                                      pXsvfInfo->ucEndDR,
01237                                      pXsvfInfo->lRunTestTime,
01238                                      pXsvfInfo->ucMaxRepeat );
01239         }
01240     }
01241     if ( iErrorCode != XSVF_ERROR_NONE ) {
01242         pXsvfInfo->iErrorCode   = iErrorCode;
01243     }
01244     return( iErrorCode );
01245 }
01246 #endif  /* XSVF_SUPPORT_COMPRESSION */
01247 
01248 /*****************************************************************************
01249 * Function:     xsvfDoXSDRBCE
01250 * Description:  XSDRB/XSDRC/XSDRE <lenVal.TDI[XSDRSIZE]>
01251 *               If not already in SHIFTDR, goto SHIFTDR.
01252 *               Shift the given TDI data into the JTAG scan chain.
01253 *               Ignore TDO.
01254 *               If cmd==XSDRE, then goto ENDDR.  Otherwise, stay in ShiftDR.
01255 *               XSDRB, XSDRC, and XSDRE are the same implementation.
01256 * Parameters:   pXsvfInfo   - XSVF information pointer.
01257 * Returns:      int         - 0 = success;  non-zero = error.
01258 *****************************************************************************/
01259 int xsvfDoXSDRBCE( SXsvfInfo* pXsvfInfo ) {
01260     unsigned char   ucEndDR;
01261     int             iErrorCode;
01262     ucEndDR = (unsigned char)(( pXsvfInfo->ucCommand == XSDRE ) ?
01263                               pXsvfInfo->ucEndDR : XTAPSTATE_SHIFTDR);
01264     iErrorCode  = xsvfBasicXSDRTDO( &(pXsvfInfo->ucTapState),
01265                                     pXsvfInfo->lShiftLengthBits,
01266                                     pXsvfInfo->sShiftLengthBytes,
01267                                     &(pXsvfInfo->lvTdi),
01268                                     /*plvTdoCaptured*/0, /*plvTdoExpected*/0,
01269                                     /*plvTdoMask*/0, ucEndDR,
01270                                     /*lRunTestTime*/0, /*ucMaxRepeat*/0 );
01271     if ( iErrorCode != XSVF_ERROR_NONE ) {
01272         pXsvfInfo->iErrorCode   = iErrorCode;
01273     }
01274     return( iErrorCode );
01275 }
01276 
01277 /*****************************************************************************
01278 * Function:     xsvfDoXSDRTDOBCE
01279 * Description:  XSDRB/XSDRC/XSDRE <lenVal.TDI[XSDRSIZE]> <lenVal.TDO[XSDRSIZE]>
01280 *               If not already in SHIFTDR, goto SHIFTDR.
01281 *               Shift the given TDI data into the JTAG scan chain.
01282 *               Compare TDO, but do NOT use XTDOMASK.
01283 *               If cmd==XSDRTDOE, then goto ENDDR.  Otherwise, stay in ShiftDR.
01284 *               XSDRTDOB, XSDRTDOC, and XSDRTDOE are the same implementation.
01285 * Parameters:   pXsvfInfo   - XSVF information pointer.
01286 * Returns:      int         - 0 = success;  non-zero = error.
01287 *****************************************************************************/
01288 int xsvfDoXSDRTDOBCE( SXsvfInfo* pXsvfInfo ) {
01289     unsigned char   ucEndDR;
01290     int             iErrorCode;
01291     ucEndDR = (unsigned char)(( pXsvfInfo->ucCommand == XSDRTDOE ) ?
01292                               pXsvfInfo->ucEndDR : XTAPSTATE_SHIFTDR);
01293     iErrorCode  = xsvfBasicXSDRTDO( &(pXsvfInfo->ucTapState),
01294                                     pXsvfInfo->lShiftLengthBits,
01295                                     pXsvfInfo->sShiftLengthBytes,
01296                                     &(pXsvfInfo->lvTdi),
01297                                     &(pXsvfInfo->lvTdoCaptured),
01298                                     &(pXsvfInfo->lvTdoExpected),
01299                                     /*plvTdoMask*/0, ucEndDR,
01300                                     /*lRunTestTime*/0, /*ucMaxRepeat*/0 );
01301     if ( iErrorCode != XSVF_ERROR_NONE ) {
01302         pXsvfInfo->iErrorCode   = iErrorCode;
01303     }
01304     return( iErrorCode );
01305 }
01306 
01307 /*****************************************************************************
01308 * Function:     xsvfDoXSTATE
01309 * Description:  XSTATE <byte>
01310 *               <byte> == XTAPSTATE;
01311 *               Get the state parameter and transition the TAP to that state.
01312 * Parameters:   pXsvfInfo   - XSVF information pointer.
01313 * Returns:      int         - 0 = success;  non-zero = error.
01314 *****************************************************************************/
01315 int xsvfDoXSTATE( SXsvfInfo* pXsvfInfo ) {
01316     unsigned char   ucNextState;
01317     int             iErrorCode;
01318     readByte( &ucNextState );
01319     iErrorCode  = xsvfGotoTapState( &(pXsvfInfo->ucTapState), ucNextState );
01320     if ( iErrorCode != XSVF_ERROR_NONE ) {
01321         pXsvfInfo->iErrorCode   = iErrorCode;
01322     }
01323     return( iErrorCode );
01324 }
01325 
01326 /*****************************************************************************
01327 * Function:     xsvfDoXENDXR
01328 * Description:  XENDIR/XENDDR <byte>
01329 *               <byte>:  0 = RUNTEST;  1 = PAUSE.
01330 *               Get the prespecified XENDIR or XENDDR.
01331 *               Both XENDIR and XENDDR use the same implementation.
01332 * Parameters:   pXsvfInfo   - XSVF information pointer.
01333 * Returns:      int         - 0 = success;  non-zero = error.
01334 *****************************************************************************/
01335 int xsvfDoXENDXR( SXsvfInfo* pXsvfInfo ) {
01336     int             iErrorCode;
01337     unsigned char   ucEndState;
01338 
01339     iErrorCode  = XSVF_ERROR_NONE;
01340     readByte( &ucEndState );
01341     if ( ( ucEndState != XENDXR_RUNTEST ) && ( ucEndState != XENDXR_PAUSE ) ) {
01342         iErrorCode  = XSVF_ERROR_ILLEGALSTATE;
01343     } else {
01344 
01345         if ( pXsvfInfo->ucCommand == XENDIR ) {
01346             if ( ucEndState == XENDXR_RUNTEST ) {
01347                 pXsvfInfo->ucEndIR  = XTAPSTATE_RUNTEST;
01348             } else {
01349                 pXsvfInfo->ucEndIR  = XTAPSTATE_PAUSEIR;
01350             }
01351             XSVFDBG_PRINTF1( 3, "   ENDIR State = %s\n",
01352                              xsvf_pzTapState[ pXsvfInfo->ucEndIR ] );
01353         } else { /* XENDDR */
01354             if ( ucEndState == XENDXR_RUNTEST ) {
01355                 pXsvfInfo->ucEndDR  = XTAPSTATE_RUNTEST;
01356             } else {
01357                 pXsvfInfo->ucEndDR  = XTAPSTATE_PAUSEDR;
01358             }
01359             XSVFDBG_PRINTF1( 3, "   ENDDR State = %s\n",
01360                              xsvf_pzTapState[ pXsvfInfo->ucEndDR ] );
01361         }
01362     }
01363 
01364     if ( iErrorCode != XSVF_ERROR_NONE ) {
01365         pXsvfInfo->iErrorCode   = iErrorCode;
01366     }
01367     return( iErrorCode );
01368 }
01369 
01370 /*****************************************************************************
01371 * Function:     xsvfDoXCOMMENT
01372 * Description:  XCOMMENT <text string ending in \0>
01373 *               <text string ending in \0> == text comment;
01374 *               Arbitrary comment embedded in the XSVF.
01375 * Parameters:   pXsvfInfo   - XSVF information pointer.
01376 * Returns:      int         - 0 = success;  non-zero = error.
01377 *****************************************************************************/
01378 int xsvfDoXCOMMENT( SXsvfInfo* pXsvfInfo ) {
01379     /* Use the comment for debugging */
01380     /* Otherwise, read through the comment to the end '\0' and ignore */
01381     unsigned char   ucText;
01382 
01383     putchar( ' ' );
01384 
01385     do {
01386         readByte( &ucText );
01387         putchar( ucText ? ucText : '\n' );
01388     } while ( ucText );
01389 
01390     pXsvfInfo->iErrorCode   = XSVF_ERROR_NONE;
01391 
01392     return( pXsvfInfo->iErrorCode );
01393 }
01394 
01395 /*****************************************************************************
01396 * Function:     xsvfDoXWAIT
01397 * Description:  XWAIT <wait_state> <end_state> <wait_time>
01398 *               If not already in <wait_state>, then go to <wait_state>.
01399 *               Wait in <wait_state> for <wait_time> microseconds.
01400 *               Finally, if not already in <end_state>, then goto <end_state>.
01401 * Parameters:   pXsvfInfo   - XSVF information pointer.
01402 * Returns:      int         - 0 = success;  non-zero = error.
01403 *****************************************************************************/
01404 int xsvfDoXWAIT( SXsvfInfo* pXsvfInfo ) {
01405     unsigned char   ucWaitState;
01406     unsigned char   ucEndState;
01407     long            lWaitTime;
01408 
01409     /* Get Parameters */
01410     /* <wait_state> */
01411     readVal( &(pXsvfInfo->lvTdi), 1 );
01412     ucWaitState = pXsvfInfo->lvTdi.val[0];
01413 
01414     /* <end_state> */
01415     readVal( &(pXsvfInfo->lvTdi), 1 );
01416     ucEndState = pXsvfInfo->lvTdi.val[0];
01417 
01418     /* <wait_time> */
01419     readVal( &(pXsvfInfo->lvTdi), 4 );
01420     lWaitTime = value( &(pXsvfInfo->lvTdi) );
01421     XSVFDBG_PRINTF2( 3, "   XWAIT:  state = %s; time = %ld\n",
01422                      xsvf_pzTapState[ ucWaitState ], lWaitTime );
01423 
01424     /* If not already in <wait_state>, go to <wait_state> */
01425     if ( pXsvfInfo->ucTapState != ucWaitState ) {
01426         xsvfGotoTapState( &(pXsvfInfo->ucTapState), ucWaitState );
01427     }
01428 
01429     /* Wait for <wait_time> microseconds */
01430     waitTime( lWaitTime );
01431 
01432     /* If not already in <end_state>, go to <end_state> */
01433     if ( pXsvfInfo->ucTapState != ucEndState ) {
01434         xsvfGotoTapState( &(pXsvfInfo->ucTapState), ucEndState );
01435     }
01436 
01437     return( XSVF_ERROR_NONE );
01438 }
01439 
01440 
01441 /*============================================================================
01442 * Execution Control Functions
01443 ============================================================================*/
01444 
01445 /*****************************************************************************
01446 * Function:     xsvfInitialize
01447 * Description:  Initialize the xsvf player.
01448 *               Call this before running the player to initialize the data
01449 *               in the SXsvfInfo struct.
01450 *               xsvfCleanup is called to clean up the data in SXsvfInfo
01451 *               after the XSVF is played.
01452 * Parameters:   pXsvfInfo   - ptr to the XSVF information.
01453 * Returns:      int - 0 = success; otherwise error.
01454 *****************************************************************************/
01455 int xsvfInitialize( SXsvfInfo* pXsvfInfo ) {
01456     /* Initialize values */
01457     pXsvfInfo->iErrorCode   = xsvfInfoInit( pXsvfInfo );
01458 
01459     if ( !pXsvfInfo->iErrorCode ) {
01460         /* Initialize the TAPs */
01461         pXsvfInfo->iErrorCode   = xsvfGotoTapState( &(pXsvfInfo->ucTapState),
01462                                   XTAPSTATE_RESET );
01463     }
01464 
01465     return( pXsvfInfo->iErrorCode );
01466 }
01467 
01468 /*****************************************************************************
01469 * Function:     xsvfRun
01470 * Description:  Run the xsvf player for a single command and return.
01471 *               First, call xsvfInitialize.
01472 *               Then, repeatedly call this function until an error is detected
01473 *               or until the pXsvfInfo->ucComplete variable is non-zero.
01474 *               Finally, call xsvfCleanup to cleanup any remnants.
01475 * Parameters:   pXsvfInfo   - ptr to the XSVF information.
01476 * Returns:      int         - 0 = success; otherwise error.
01477 *****************************************************************************/
01478 int xsvfRun( SXsvfInfo* pXsvfInfo ) {
01479     /* Process the XSVF commands */
01480     if ( (!pXsvfInfo->iErrorCode) && (!pXsvfInfo->ucComplete) ) {
01481         /* read 1 byte for the instruction */
01482         readByte( &(pXsvfInfo->ucCommand) );
01483         ++(pXsvfInfo->lCommandCount);
01484 
01485         if ( pXsvfInfo->ucCommand < XLASTCMD ) {
01486             /* Execute the command.  Func sets error code. */
01487             XSVFDBG_PRINTF1( 2, "  %s\n",
01488                              xsvf_pzCommandName[pXsvfInfo->ucCommand] );
01489             /* If your compiler cannot take this form,
01490                then convert to a switch statement */
01491             xsvf_pfDoCmd[ pXsvfInfo->ucCommand ]( pXsvfInfo );
01492         } else {
01493             /* Illegal command value.  Func sets error code. */
01494             xsvfDoIllegalCmd( pXsvfInfo );
01495         }
01496     }
01497 
01498     return( pXsvfInfo->iErrorCode );
01499 }
01500 
01501 /*****************************************************************************
01502 * Function:     xsvfCleanup
01503 * Description:  cleanup remnants of the xsvf player.
01504 * Parameters:   pXsvfInfo   - ptr to the XSVF information.
01505 * Returns:      void.
01506 *****************************************************************************/
01507 void xsvfCleanup( SXsvfInfo* pXsvfInfo ) {
01508     xsvfInfoCleanup( pXsvfInfo );
01509 }
01510 
01511 
01512 /*============================================================================
01513 * xsvfExecute() - The primary entry point to the XSVF player
01514 ============================================================================*/
01515 
01516 /*****************************************************************************
01517 * Function:     xsvfExecute
01518 * Description:  Process, interpret, and apply the XSVF commands.
01519 *               See port.c:readByte for source of XSVF data.
01520 * Parameters:   none.
01521 * Returns:      int - Legacy result values:  1 == success;  0 == failed.
01522 *****************************************************************************/
01523 int xsvfExecute() {
01524     SXsvfInfo   xsvfInfo;
01525     xsvfInitialize( &xsvfInfo );
01526 
01527     while ( !xsvfInfo.iErrorCode && (!xsvfInfo.ucComplete) ) {
01528         xsvfRun( &xsvfInfo );
01529     }
01530 
01531     if ( xsvfInfo.iErrorCode ) {
01532         XSVFDBG_PRINTF1( 0, "%s\n", xsvf_pzErrorName[
01533                              ( xsvfInfo.iErrorCode < XSVF_ERROR_LAST )
01534                              ? xsvfInfo.iErrorCode : XSVF_ERROR_UNKNOWN ] );
01535         XSVFDBG_PRINTF2( 0, "ERROR at or near XSVF command #%ld.  See line #%ld in the XSVF ASCII file.\n",
01536                          xsvfInfo.lCommandCount, xsvfInfo.lCommandCount );
01537     } else {
01538         XSVFDBG_PRINTF( 0, "SUCCESS - Completed XSVF execution.\n" );
01539     }
01540 
01541     xsvfCleanup( &xsvfInfo );
01542 
01543     return( XSVF_ERRORCODE(xsvfInfo.iErrorCode) );
01544 }
01545 
01546 
01547 /*============================================================================
01548 * main
01549 ============================================================================*/
01550 
01551 /*****************************************************************************
01552 * Function:     main
01553 * Description:  main function.
01554 *               Specified here for creating stand-alone debug executable.
01555 *               Embedded users should call xsvfExecute() directly.
01556 * Parameters:   iArgc    - number of command-line arguments.
01557 *               ppzArgv  - array of ptrs to strings (command-line arguments).
01558 * Returns:      int      - Legacy return value:  1 = success; 0 = error.
01559 *****************************************************************************/
01560 int execute_micro(char *filename, void (*cbfunc_progress)(int done, int total), void (*cbfunc_waittime)(int microsec)) {
01561     int     iErrorCode;
01562     char*   pzXsvfFileName;
01563     clock_t startClock;
01564     clock_t endClock;
01565 
01566     iErrorCode          = XSVF_ERRORCODE( XSVF_ERROR_NONE );
01567     pzXsvfFileName      = 0;
01568 
01569     printf( "XSVF Player v%s, Xilinx, Inc.\n", XSVF_VERSION );
01570 
01571     pzXsvfFileName  = filename;
01572     printf( "XSVF file = %s\n", pzXsvfFileName );
01573 
01574     /* read from the XSVF file instead of a real prom */
01575     FILE* in = fopen( pzXsvfFileName, "rb" );
01576     if ( !in ) {
01577         printf( "ERROR:  Cannot open file %s\n", pzXsvfFileName );
01578         iErrorCode  = XSVF_ERRORCODE( XSVF_ERROR_UNKNOWN );
01579     } else {
01580         initPort(in, cbfunc_progress, cbfunc_waittime);
01581         /* Initialize the I/O.  SetPort initializes I/O on first call */
01582         setPort( TMS, 1 );
01583         /* Execute the XSVF in the file */
01584         startClock  = clock();
01585         iErrorCode  = xsvfExecute();
01586         endClock    = clock();
01587         fclose( in );
01588         printf( "Execution Time = %.3f seconds\n",
01589                 (((double)(endClock - startClock)) / CLOCKS_PER_SEC) );
01590     }
01591 
01592     return( iErrorCode );
01593 }