📄 svf2vme.c
字号:
}
fDelayTime += 0x8000;
}
write( WAIT );
ConvNumber( fDelayTime );
}
break;
case 3: /*element 3 is; or ENDSTATE*/
if ( 0 == stricmp( SVF_string, "ENDSTATE" ) ) { /*use STATE for ENDSTATE*/
STATECom();
}
break;
default:
rcode = FILE_ERROR;
break;
}
}
return rcode;
}
/******************************************************************************
* *
* ExeFREQUENCYCommand() *
* *
* The frequency is expressed in 16 bits integer in KHZ or MHZ *
******************************************************************************/
short int FREQUENCYCom()
{
int rcode;
float freq;
rcode = Token(";");
freq =(float)atof(SVF_string);
/* tnt 10/21/02: added to support frequency option at commandline. */
if (!frequency)
frequency =(long)(freq/1000); /*convert it to KHZ*/
if(frequency == 0) {
frequency = (unsigned int)freq;
}
write(FREQUENCY); /* support frequency statement to delay the clock for 3K devices*/
ConvNumber(frequency);
return rcode;
}
/******************************************************************************************
* *
* Execute the Shift Data Register *
* *
* syntax: SDR or SIR 128[SMASK - Optional][TDI Optional][SMASK - Optional] *
*[TDO - optional] *
* *
* Howard Tang 02/02/2000 When encounter SDR > 64000, split the SDR into *
* mulitple SDR with 64000 bits maximum per each shift *
* Example: *
* SDR 84000 TDI(); *
* is splitted up into: *
* SDR 64000 TDI ........ SDR 20000 TDI ........ *
* Howard Tang 03/07/2000 Give special treatment to a 1 bit long SDR, i.e. SDR 1(0); *
* It shows up primarily for an auto address increment. It is *
* converted blindly into STATE SHIFTDR; STATE PAUSEDR; *
* To achieve minimum file size, the TDO stream is compared with the*
* the TDI stream of the previous DRSCAN, if it is the same, *
* opcode XSDR is used to launch simultaneous shift in and out *
* *
*******************************************************************************************/
short int ScanCom( char scan_type, char options )
{
int rcode = 0;
long int DR_Length;
/* Read the TDI data */
rcode = Token( " (" );
/* Read the number of bits for SDR */
DR_Length = atoi( SVF_string );
if ( DR_Length == 0 ) {
return UNKNOWN_CHIP;
}
/*10/26/01 tnt store numbits in array to process with data later */
if ( scan_type && allocateFlag ) {
numBitArray = ( int * ) calloc( 100, sizeof( int ) );
allocateFlag = 0;
}
if ( DR_Length > ( long int ) ScanMax ) {
/* 1/14/04 Put the device into DRPAUSE before processing cascading frames */
if ( scan_type ) {
write( STATE );
write( DRPAUSE );
}
}
/* Read the TDI and TDO data from the SVF file and convert */
rcode = TDIToken( DR_Length, scan_type, options );
/* TDO may exist and compression turns on */
if ( ( scan_type ) && ( DR_Length > ( long int ) ScanMax ) ) {
/* 1/14/04 Put the device into ENDDR after processing cascading frames */
write( STATE );
write( ( char ) CurEndDR );
}
return ( rcode );
}
/***********************************************************************
* *
* Generic routine to read data from the SVF file. *
* *
* Parses the SVF command token "TDI(11223344)" *
* *
* SDR 128 TDI(00302043003010430030304300308043); Program *
* *
* SDR 128 TDI(ffffffffffffffffffffffffffffffff) *
* TDO(00302043003010430030304300308043); Verify *
* *
* Var *
* numbits The number of bits of data to be processed. *
* SVF_string The string contains the whole or part of the data read *
* from SVF *
* sdr 0 is sir. 1,2 is sdr 3 is hir,hdr,tir,tdr *
* compress 0 = no compress by default. e.g. SIR data *
* 1 = compress *
************************************************************************/
short int TDIToken(long int numbits, char sdr, char compress)
{
int i;
int y= 0;
int rcode = 0;
int bits, bit;
long int MultipleScan = 0; /*default is single SDR or SIR */
char Nodes[4]= {SIR, SDR, XSDR, HIR};
char option = 0, Done = 0;
char ioshift = 0; /*simutaneously shift in and out*/
/* unsigned char char_val; */
char opcode;
/*check if SDR need to be splited.*/
MultipleScan = ( long int ) numbits / ScanMax; /* split a SDR into multiple SDR */
if ( MultipleScan == 0 )
option = compress + 1;
if ((sdr<3)&&(scanNodes[sdr].numbits != numbits))
{
/*void old mask if size changes*/
if (scanNodes[sdr].mask != NULL)
{
free(scanNodes[sdr].mask);
scanNodes[sdr].mask = NULL;
}
}
else if ((sdr==1) && (scanNodes[sdr].tdi != NULL))
{
/*if SDR and length is the same*/
if (scanNodes[2].tdi != NULL)
free(scanNodes[2].tdi);
if ((scanNodes[2].tdi =(unsigned char *)malloc(numbits/8 + 2)) == NULL)
return OUT_OF_MEMORY;
/*copy the previous TDI data in*/
for (i = 0; i < numbits/8 + 1; i++) {
scanNodes[2].tdi[i] = scanNodes[1].tdi[i];
scanNodes[2].numbits = numbits;
}
}
scanNodes[sdr].numbits = numbits;
Done = 0;
/*read one SDR or SIR loop and convert TDI, TDO, MASK into binary stream*/
while ((!Done) && (rcode == 0))
{
rcode = Token(" "); /*fetch the next token*/
for (i = 0; i < ScanTokenMax; i++)
if (stricmp(scanTokens[i].text, SVF_string) == 0)
break;
opcode = scanTokens[i].token;
switch (opcode)
{
case TDI:
if (numBitArray && sdr) {
numBitArray[globalBitArrayCounter] = numbits;
globalBitArrayCounter++;
}
if (scanNodes[sdr].tdi != NULL)
free(scanNodes[sdr].tdi);
if ((scanNodes[sdr].tdi =(unsigned char *)malloc(numbits/8 + 2)) == NULL)
return OUT_OF_MEMORY;
rcode = ConvertFromHexString(numbits, scanNodes[sdr].tdi, &Done, 1, sdr);
break;
case SMASK: /*read and throw away*/
rcode = ConvertFromHexString(numbits, NULL, &Done, 0, sdr);
break;
case TDO:
if (numBitArray && sdr) {
numBitArray[globalBitArrayCounter] = numbits;
globalBitArrayCounter++;
}
if ((scanNodes[sdr].tdo =(unsigned char *)malloc(numbits/8 + 2)) == NULL)
return OUT_OF_MEMORY;
rcode = ConvertFromHexString(numbits, scanNodes[sdr].tdo, &Done, 1, sdr);
if ((sdr==1) && (scanNodes[2].numbits == scanNodes[1].numbits)&&
(scanNodes[2].tdi != NULL) && !iLoopVMEOption) /* tnt 5/22/02: if looping then
do not allow for XSDR, XTDO */
{
/*check if previous tdi same as current tdo*/
for (i = 0; i < numbits/8 + 1; i++) {
if (scanNodes[2].tdi[i] != scanNodes[sdr].tdo[i]) {
break;
}
}
if (i == numbits/8 + 1)
ioshift= 1; /*tdi and tdo the same*/
}
break;
case MASK:
if (numBitArray && sdr) {
numBitArray[globalBitArrayCounter] = numbits;
globalBitArrayCounter++;
}
if (scanNodes[sdr].mask == NULL)
{
if ((scanNodes[sdr].mask =
(unsigned char *)malloc(numbits/8 + 2)) == NULL)
return OUT_OF_MEMORY;
}
rcode = ConvertFromHexString(numbits, scanNodes[sdr].mask, &Done, 1, sdr);
break;
/* 05/27/03 Nguyen added to support Dynamic IO */
case DMASK:
if (numBitArray && sdr) {
numBitArray[globalBitArrayCounter] = numbits;
globalBitArrayCounter++;
}
if (scanNodes[sdr].dmask == NULL)
{
if ((scanNodes[sdr].dmask = (unsigned char *)malloc(numbits/8 + 2)) == NULL)
return OUT_OF_MEMORY;
}
rcode = ConvertFromHexString(numbits, scanNodes[sdr].dmask, &Done, 1, sdr);
break;
case ENDDATA: /*found ';' */
default: Done = 1;
break;
}
}
/*write the current SDR or SIR stream into VME file format*/
/*split them into multiple SDR stream if necessary*/
bit = 0; /*the first position of data to be fetched*/
option = compress + 1;
do {
if ( numbits > (long int) ScanMax ) {
/* 1/15/04 Turn on cascading */
write( SETFLOW );
ConvNumber( CASCADE );
bits =(int)ScanMax;
}
else {
bits =(int)numbits;
}
if (ioshift) {
write(Nodes[2]); /*write XSDR */
}
else if (sdr<3) {
if (shiftsize) {
if (!strcmp(shiftdirection, "SHR")) {
write(SHR);
}
else if (!strcmp(shiftdirection, "SHL")) {
write(SHL);
}
ConvNumber(shiftsize);
shiftsize = 0;
}
write(Nodes[sdr]); /*regular SDR*/
}
/*8/28/01 ht convert to VME1.1 format*/
ConvNumber(bits);
/*01/02/2001 ht fix the memory problem by dividing bit by 8*/
if (scanNodes[sdr].tdi != NULL)
{
write(TDI);
rcode = convertToispSTREAM(bits, &scanNodes[sdr].tdi[bit/8], option, 0);
}
if (scanNodes[sdr].tdo != NULL)
{
if (ioshift) {
write(XTDO); /*get TDO data from previous TDI*/
}
else
{
write(TDO); /*regular TDO with data follows immediately*/
rcode = convertToispSTREAM(bits, &scanNodes[sdr].tdo[bit/8], option, 0);
}
}
if ((scanNodes[sdr].tdo != NULL) && (scanNodes[sdr].mask != NULL))
{
/* remember SIR and SDR mask for altera devices */
if (vendor == ALTERA) {
if (sdr) {
SDRMask = &scanNodes[sdr].mask[bit/8];
previousSDRbits = numbits;
}
else {
SIRMask = &scanNodes[sdr].mask[bit/8];
previousSIRbits = numbits;
}
}
write(MASK);
rcode = convertToispSTREAM(bits, &scanNodes[sdr].mask[bit/8], option, 0);
}
else {
if (sdr && (bits == previousSDRbits) && (vendor == ALTERA)) {
write(MASK);
rcode = convertToispSTREAM(bits, SDRMask, option, 0);
}
else if (!sdr && (bits == previousSIRbits) && (vendor == ALTERA)) {
write(MASK);
rcode = convertToispSTREAM(bits, SIRMask, option, 0);
}
}
/* 05/27/03 Nguyen added to support Dynamic IO */
if (scanNodes[sdr].dmask != NULL)
{
write(DMASK);
rcode = convertToispSTREAM(bits, &scanNodes[sdr].dmask[bit/8], option, 0);
}
write(CONTINUE); /*terminator*/
bit +=(long int)ScanMax; /*if multiple loop, the next starting point is*/
if ( numbits > (long int) ScanMax ) {
/* 1/15/04 Turn off cascading */
write( RESETFLOW );
ConvNumber( CASCADE );
}
} while ((rcode == 0) && ((numbits -=(long int)ScanMax) > 0)); /*process 64000 bits each time */
if ( scanNodes[ sdr ].tdo != NULL ) {
free( scanNodes[ sdr ].tdo );
scanNodes[ sdr ].tdo = NULL;
}
if ( scanNodes[ sdr ].tdi != NULL ) {
free( scanNodes[ sdr ].tdi);
scanNodes[ sdr ].tdi = NULL;
}
if ( scanNodes[ sdr ].mask != NULL ) {
free( scanNodes[ sdr ].mask );
scanNodes[ sdr ].mask = NULL;
}
/* 05/27/03 Nguyen added to support Dynamic IO */
if ( scanNodes[ sdr ].dmask != NULL ) {
free( scanNodes[ sdr ].dmask );
scanNodes[ sdr ].dmask = NULL;
}
return ( rcode );
}
/******************************************************************************
* *
* ConvertFromHexString *
* *
* Converts the Hex String[00302043003010430030304300308043] into *
* binary bits. *
* It start by searching for open '(' and terminate only by seeing a *
* close ')'. It will read another string in from the file if necessary. *
* The binary order is exactly the reverse of the SVF Hex format. *
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -