我看很多资料上都说:PCI的地址端口是CF8h,数据端口是CFCh,
可是我在取配置空间的数据时,老是取出的Vendor ID都是FFFFh,
就是说取不到数据(我的总线地址应该没有问题),
请问:PCI的地址端口和数据端口有问题吗?
哪位有去PCI配置空间数据的代码?
------解决方案--------------------------------------------------------
这个是DOS里面妹举PCI设备的代码
- Assembly code
.386PDSEG SEGMENT USE16 ;16位数据段CfgSpace DB 256 DUP(0) ;PCI设备的256字节配置空间bus DW 0 ;bus号,0~255dev DW 0 ;dev号,0~31func DW 0 ;func号,0~7index DW 0 ;index,0~63DSEG ENDS ;数据段结束 SSEG SEGMENT PARA STACK ;堆栈段 DB 512 DUP (0)SSEG ENDS ;堆栈段结束 ;字符显示宏指令的定义EchoCh MACRO ascii mov ah,2 mov dl,ascii int 21h ENDM CSEG SEGMENT USE16 ;1代码段 ASSUME CS:CSEG,DS:DSEG; 搜索PCI-IDE设备, 获取PCI配置空间FindPCIIDE PROC ; bus号从0循环到255 mov bus, 0loop_bus: ; dev号从0循环到31 mov dev, 0loop_dev: ; func号从0循环到7 mov func, 0loop_func: ; index号从0循环到63 mov index, 0loop_index: ;构造eax为一个32位双字, 写入0cf8h端口 ;(1 << 31)|(bus << 16)|(dev << 11)|(func << 8)|(index << 2) movzx eax,bus ;eax=bus movzx ebx,dev ;ebx=dev movzx ecx,func ;ecx=func movzx edx,index ;dex=index shl eax,16 ;eax=(bus<<16) shl ebx,11 ;ebx=(dev<<11) shl ecx,8 ;ecx=(func<<8) shl edx,2 ;edx=(index<<2) or eax,80000000h ;eax=(1<<31)||(bus<<16) or eax,ebx ;eax=..||(dev << 11) or eax,ecx ;eax=..||(func << 8) or eax,edx ;eax=..||(index << 2) ;从0cf8h端口读取的配置寄存器将保存在CfgSpace[index*4]中 lea edi,CfgSpace[edx] mov dx,0cf8h out dx,eax ;eax写入到0cf8h端口 mov dx,0cfch in eax,dx ;从0cfch端口读入 cld stosd ;配置寄存器保存在CfgSpace中 inc index cmp index, 64 jb loop_index ;index=0~63 cmp WORD PTR CfgSpace[0ah],0101h ;检查类代码寄存器 jz FindValidOne ;BaseClass=01h,Sub-Class=01h cmp func,0 ;func=0时,检查为多功能设备 jnz NotFunc0 ;func=1时,不检查 test CfgSpace[0eh],80h ;Bit7=1,<bus,dev>是多功能设备 jz NotMultiFunc ;Bit7=0,不是NotFunc0: inc func cmp func, 8 jb loop_func ;index=0~7NotMultiFunc: inc dev cmp dev, 32 jb loop_dev ;dev=0~31 inc bus cmp bus, 256 jb loop_bus ;bus=0~255 FindValidOne: retFindPCIIDE ENDP Start PROC mov ax,DSEG mov ds,ax ;ds指向数据段 mov es,ax ;es指向数据段 call FindPCIIDE ;搜索PCI-IDE设备 lea si,CfgSpace ;显示配置空间中的256字节数据 cld mov bp,256/16NextLine: mov cx,16NextCh: lodsb push ax shr al,4 call ToASCII EchoCh al pop ax call ToASCII EchoCh al EchoCh ' ' loop NextCh EchoCh 0dh EchoCh 0ah dec bp jnz NextLine mov ax,4c00h int 21hStart ENDP ToASCII PROC and al,0fh cmp al,10 jae Over10 add al,'0' retOver10: add al,'A'-10 retToASCII ENDP CSEG ENDS ;代码段结束 END Start