📄 pcielink.c
字号:
argv11_r=atoi(result);
if(argv11_r<1||argv11_r>255)
{
if(echo) printf(emsg);
rtnVal=10;
}
//check negotiate link width register msb
strcpy(emsg,"Invalid Negotiate Link Width Register MSB!\n");
result=strtok(NULL,";");
argv11_m=atoi(result);
if(argv11_m<0||argv11_m>32)
{
if(echo) printf(emsg);
rtnVal=10;
}
//check negotiate link width register lsb
strcpy(emsg,"Invalid Negotiate Link Width Register LSB!\n");
result=strtok(NULL,";");
argv11_l=atoi(result);
if(argv11_l<0||argv11_l>32||argv11_l>=argv11_m)
{
if(echo) printf(emsg);
rtnVal=10;
}
//check negotiate link speed register
strcpy(emsg,"Invalid Negotiate Link Speed Register!\n");
result=strtok(argv12,";");
argv12_r=atoi(result);
if(argv12_r<1||argv12_r>255)
{
if(echo) printf(emsg);
rtnVal=11;
}
//check negotiate link speed register msb
strcpy(emsg,"Invalid Negotiate Link Speed Register MSB!\n");
result=strtok(NULL,";");
argv12_m=atoi(result);
if(argv12_m<0||argv12_m>32)
{
if(echo) printf(emsg);
rtnVal=11;
}
//check negotiate link width register lsb
strcpy(emsg,"Invalid Negotiate Link Speed Register LSB!\n");
result=strtok(NULL,";");
argv12_l=atoi(result);
if(argv12_l<0||argv12_l>32||argv12_l>=argv12_m)
{
if(echo) printf(emsg);
rtnVal=11;
}
//set device id number
inregs.x.cx=argv6;
//set vendor id number
venId=argv8;
//set subsystem vendor id
venIdS=argv9;
//detect devices by vendor ID into array
if(!userBD)
{
for(i=acount=0;i<ADAPTER_COUNT;i++)
{
inregs.h.ah=0xB1; //PCI_FUNCTION_ID;
inregs.h.al=0x02; //FIND_PCI_DEVICE;
inregs.x.dx=venId;
inregs.x.si=i;
_int86(0x1A,&inregs,&outregs);
Device_Info_Array[acount].Bus_Number=outregs.h.bh;
Device_Info_Array[acount].Device_Number=outregs.h.bl;
//if BAD VENDOR ID or DEVICE_NOT_FOUND get next
if(outregs.h.ah==0x83||outregs.h.ah==0x86) break;
//if SUCCESSFUL
if(echo && !outregs.h.ah)
{
printf("Detected BUS: %s DEV: %s\n",ltoa(outregs.h.bh,test,10),ltoa(outregs.h.bl,test1,10));
}
acount++;
}
if(!acount)
{
if(echo) printf("No devices detected for this Vendor ID..\n");
rtnVal=1;
}
}
//if any error occurred, exit
if(rtnVal) return rtnVal;
//check if PCI BIOS is present on the motherboard, does not detect missing HBA
inregs.h.ah=0xB1; // PCI_FUNCTION_ID;
inregs.h.al=0x01; // PCI_BIOS_PRESENT
_int86(0x1a,&inregs,&outregs);
if(outregs.x.cflag)
{
if(echo) printf("No PCI BIOS present in this motherboard!!\n");
return 1;
}
//set PCI READ CONFIGURATION WORD
inregs.h.ah=0xB1; // PCI_FUNCTION_ID;
inregs.h.al=0x09; // READ_CONFIG_WORD;
//inregs.h.al=0x0A; // READ_CONFIG_DWORD;
//set PCI Bus and Device numbers
if(userBD)
{
//user set values
inregs.h.bh=argv1; // bus number
inregs.h.bl=argv2; // device number
acount=1; // minimum once through next loop
}
for(tcount=0;tcount<acount;tcount++)
{
//reset doTest flag (used in autoDetect mode to test only /Device=0 for each /Bus
doTest=0;
//if not using /B or /D and we are on a /Device=0 then
if(!userBD && Device_Info_Array[tcount].Device_Number==0)
{
doTest=1;
inregs.h.bh=Device_Info_Array[tcount].Bus_Number; // bus number
inregs.h.bl=Device_Info_Array[tcount].Device_Number; // device number
if(echo) printf("Testing BUS: %s DEV: %s\n",ltoa(Device_Info_Array[tcount].Bus_Number,test,10),ltoa(Device_Info_Array[tcount].Device_Number,test1,10));
}
//show current /Bus and /Device
if(echo && userBD) printf("Testing BUS: %s DEV: %s\n",ltoa(argv1,test,10),ltoa(argv2,test1,10));
//if using /B or /D direct mode, doTest always set
if(userBD) doTest=1;
//perform testing
if(doTest)
{
//read device id
inregs.x.di=0x02;
_int86(0x1A,&inregs,&outregs);
strcpy(emsg,"02 - Device ID: ");
if(argv7==10)
{
strcat(emsg,ltoa(outregs.x.cx,test,16));
} else
{
strcat(emsg,ltoa(outregs.x.cx,test,argv7));
}
if(outregs.x.cx==0xFFFF | outregs.x.cx==0x0)
{
strcat(emsg," ** Error **");
rtnVal=1;
}
if(echo) printf("%s\n",emsg);
if(rtnVal) return rtnVal;
//read vendor id offset 00h
inregs.x.di=0x00;
_int86(0x1A,&inregs,&outregs);
strcpy(emsg,"00 - Vendor ID: ");
if(argv7==10)
{
strcat(emsg,ltoa(outregs.x.cx,test,16));
} else
{
strcat(emsg,ltoa(outregs.x.cx,test,argv7));
}
if(outregs.x.cx!=venId)
{
strcat(emsg," ** Error **");
rtnVal=7;
}
if(echo) printf("%s\n",emsg);
if(rtnVal) return rtnVal;
//read subsystem vendor id
inregs.x.di=0x2c;
_int86(0x1A,&inregs,&outregs);
strcpy(emsg,"2C - Subsystem Vendor ID: ");
if(argv7==10)
{
strcat(emsg,ltoa(outregs.x.cx,test,16));
} else
{
strcat(emsg,ltoa(outregs.x.cx,test,argv7));
}
if(outregs.x.cx!=venIdS)
{
strcat(emsg," ** Error **");
rtnVal=8;
}
if(echo) printf("%s\n",emsg);
if(rtnVal) return rtnVal;
//read link capability bits[msb:lsb] (PCIe BUS Maximum supported lane width)
shift=argv10_l;
mask=(int)(pow(2,((argv10_m-argv10_l)+1))-1);
inregs.x.di=argv10_r;
_int86(0x1A,&inregs,&outregs);
strcpy(emsg,itoa(argv10_r,test,16));
strcat(emsg," - Maximum Link Width: ");
tmpVal=((outregs.x.cx>>shift) & mask);
strcat(emsg,ltoa(tmpVal,test,argv7));
if(!argv3)
{
strcat(emsg," ** Ignored **");
rtnVal=0;
}
else if (tmpVal!=argv3)
{
strcat(emsg," ** Error **");
rtnVal=3;
}
if(echo) printf("%s\n",emsg);
if(rtnVal) return rtnVal;
//read link status bits [msb:lsb] (PCIe BUS Negotiated Link Width)
shift=argv11_l;
mask=(int)(pow(2,((argv11_m-argv11_l)+1))-1);
inregs.x.di=argv11_r;
_int86(0x1A,&inregs,&outregs);
strcpy(emsg,itoa(argv11_r,test,16));
strcat(emsg," - Negotiate Link Width: ");
tmpVal=((outregs.x.cx>>shift) & mask);
strcat(emsg,ltoa(tmpVal,test,argv7));
if(!argv4)
{
strcat(emsg," ** Ignored **");
rtnVal=0;
}
else if(tmpVal!=argv4)
{
strcat(emsg," ** Error **");
rtnVal=4;
}
if(echo) printf("%s\n",emsg);
if(rtnVal) return rtnVal;
// read link status bits [msb:lsb] (PCIe BUS Link Speed)
shift=argv12_l;
mask=(int)(pow(2,((argv12_m-argv12_l)+1))-1);
inregs.x.di=argv12_r;
_int86(0x1A,&inregs,&outregs);
strcpy(emsg,itoa(argv12_r,test,16));
strcat(emsg," - Link Speed: ");
lssVal=(outregs.x.cx>>shift & mask);
strcat(emsg,ltoa(lssVal,test,argv7));
if(!argv5)
{
strcat(emsg," ** Ignored **");
rtnVal=0;
}
else if((outregs.x.cx>>shift & mask) != argv5)
{
strcat(emsg," ** Error **");
rtnVal=5;
}
if(echo) printf("%s\n",emsg);
if(rtnVal) return rtnVal;
}
}
return rtnVal;
}
//make PCIELINK.TXT example file if not already exist in same folder
void makeTxt(void)
{
FILE *ifp;
FILE *ofp;
//exit if file already exists
if((ifp=fopen("PCIELINK.TXT","r"))!=NULL)
{
fclose(ifp);
return;
}
//not already exist, make a default version
if((ofp=fopen("PCIELINK.TXT","w"))!=NULL)
{
fputs("Examples for PCIELINK.EXE PCI EXPRESS LINK CAPABILITY TEST V2.0\n",ofp);
fputs("\n",ofp);
fputs("Created by: Jeff Fabrizio, QLogic Corporation FVT Production Test\n",ofp);
fputs("\n",ofp);
fputs(" VendorID QLOGIC 4215 0x1077 \n",ofp);
fputs(" HP 4156 0x103C \n",ofp);
fputs(" SUN 284 0x011C \n",ofp);
fputs(" NEC 4147 0x1033 \n",ofp);
fputs(" PLX 4187 0x10B5 \n",ofp);
fputs(" DeviceID ISP2432 9266 0x2432 \n",ofp);
fputs(" ISP2532 9522 0x2532 \n",ofp);
fputs(" NEC UPD720403 335 0x014F \n",ofp);
fputs(" PLX8516/1517 34070 0x4277 \n",ofp);
fputs("\n",ofp);
fputs("The /e /f /g options require three values separated by a semicolon. These\n",ofp);
fputs("options are not required for QLogic ISP devices but are required for non-\n",ofp);
fputs("QLogic devices such as the NEC or PLX PCI bridge devices. The design spec\n",ofp);
fputs("for any device is required to obtain the PCI register offset values for:\n",ofp);
fputs(" PCI Maximum Lane Width\n",ofp);
fputs(" PCI Negotiated Lane Width\n",ofp);
fputs(" PCI Negotiated Lane Speed\n",ofp);
fputs("\n",ofp);
fputs(" example:\n",ofp);
fputs(" /eRegMLW;msb;lsb\n",ofp);
fputs(" /fRegNLW;msb;lsb\n",ofp);
fputs(" /gRegNLS;msb;lsb\n",ofp);
fputs("\n",ofp);
fputs(" RegMLW = Register Maximum Link Width\n",ofp);
fputs(" RegNLW = Register Negotiated Link Width\n",ofp);
fputs(" RegNLS = Register Negotiated Link Speed\n",ofp);
fputs(" msb = most significant bit offset\n",ofp);
fputs(" lsb = least significant bit offset\n",ofp);
fputs("\n",ofp);
fputs("*QLogic 2432 (Default device only requires minimum of /i and /a)\n",ofp);
fputs("PCIELINK /v /h /i4215 /a9266 /s4215 /m4 /n4 /l1 /e88;9;4 /f94;9;4 /g94;3;0\n",ofp);
fputs("*QLogic 5432\n",ofp);
fputs("4215;21554\n",ofp);
fputs("*QLogic 6432\n",ofp);
fputs("4215;25650\n",ofp);
fputs("*QLogic 7432\n",ofp);
fputs("4215;29746\n",ofp);
fputs("*QLogic 8432\n",ofp);
fputs("4215;33842\n",ofp);
fputs("*QLogic 2532\n",ofp);
fputs("4215;9522;\n",ofp);
fputs("*QLogic 6220\n",ofp);
fputs("4215;25120\n",ofp);
fputs("*QLogic 7220\n",ofp);
fputs("4215;29216\n",ofp);
fputs("*QLogic 8000\n",ofp);
fputs("4215;32768;88;9;4;94;9;4;94;3;0\n",ofp);
fputs("*QLogic 8001\n",ofp);
fputs("4215;32769;88;9;4;94;9;4;94;3;0\n",ofp);
fputs("*NEC uPD720403 Port 0 PCI Motherboard\n",ofp);
fputs("PCIELINK /v /h /i4147 /a335 /m8 /n8 /s0 /e108;9;4 /f114;9;4 /g114;3;0\n",ofp);
fputs("*NEC uPD720403 Port 1 PCI ISP 0\n",ofp);
fputs("PCIELINK /v /h /i4147 /a336 /m8 /n8 /s0 /e108;9;4 /f114;9;4 /g114;3;0\n",ofp);
fputs("*NEC uPD720403 Port 2 PCI ISP 1\n",ofp);
fputs("PCIELINK /v /h /i4147 /a337 /m8 /n8 /s0 /e108;9;4 /f114;9;4 /g114;3;0\n",ofp);
fputs("*NEC uPD720403 Port 3 unused\n",ofp);
fputs("PCIELINK /v /h /i4147 /a338 /m8 /n8 /s0 /e108;9;4 /f114;9;4 /g114;3;0\n",ofp);
fputs("*PLX 8516/8517\n",ofp);
fputs("PCIELINK /v /h /i4277 /a34070 /s0 /m8 /n8 /e116;9;4 /f122;9;4 /g122;3;0\n",ofp);
fputs("\n",ofp);
fputs("<end of file>\n",ofp);
fclose(ofp);
}
}
//trim leading and trailing spaces from string
void trimSpace(char *trimStr, char *trimmedStr, int newLine)
{
//local vars
int lineLen=0, count=0, nonSpace=0, i=0, nextChar=0;
char aline[255];
char bline[255];
memset(aline,'\0',255);
memset(bline,'\0',255);
//copy temp vars
strcpy(aline,trimStr);
lineLen=strlen(aline);
//trim leading spaces
for (count=0;count<lineLen;count++)
{
nextChar=aline[count];
if(isspace(nextChar)==0 && nonSpace==0) nonSpace=1; //not a space/tab/ff/nl
if(nonSpace==1)
{
bline[i]=nextChar;
i++;
}
}
//trim trailing spaces
count=0;
lineLen=strlen(bline);
for(count=strlen(bline)-1;count>=0;count--)
{
if(isspace(bline[count])==0) break; //found first char not a space/tab/ff/nl
bline[count]='\0';
}
strcpy(trimmedStr,bline);
if(newLine) strcat(trimmedStr,"\n");
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -