ichabod
驱动牛犊
驱动牛犊
  • 注册日期2004-12-08
  • 最后登录2007-08-09
  • 粉丝0
  • 关注0
  • 积分10分
  • 威望1点
  • 贡献值0点
  • 好评度1点
  • 原创分0分
  • 专家分0分
阅读:1625回复:10

谁能提供一个win2k下访问PCI配置空间的驱动?

楼主#
更多 发布于:2004-12-16 10:57
rt,访问PCI配置空间需要访问0xCF8和0xCFC端口,这两个端口都需要按4字节访问。我写了一个在win2k下访问端口的驱动,但是按字节访问是可以的(通过读CMOS验证),但是按4字节访问总是出错,推测原因一是Win2k把这种访问PCI配置空间的方式给禁了,再就是我的驱动写的有问题。有哪位达人可指教,在此先谢过了(最好能提供源码)
我的驱动的源码如下:
#include <ntddk.h>
#include "portaccess.h"

#define    IOPM_SIZE    0x2000

typedef UCHAR IOPM[IOPM_SIZE];

IOPM *IOPM_local = 0;

void Ke386SetIoAccessMap(int, IOPM *);
void Ke386QueryIoAccessMap(int, IOPM *);
void Ke386IoSetAccessProcess(PEPROCESS, int);

NTSTATUS PortAccessDeviceControl(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp);
VOID PortAccessUnload(IN PDRIVER_OBJECT DriverObject);

NTSTATUS PortAccessCreateDispatch(
    IN PDEVICE_OBJECT DeviceObject,
    IN PIRP Irp
    )
{
    Irp->IoStatus.Information = 0;
    Irp->IoStatus.Status = STATUS_SUCCESS;
    IoCompleteRequest(Irp, IO_NO_INCREMENT);
    return STATUS_SUCCESS;
}

NTSTATUS
PortAccessDeviceControl(
    IN PDEVICE_OBJECT DeviceObject,
    IN PIRP pIrp
    )

{
    PIO_STACK_LOCATION  irpSp;
    NTSTATUS            ntStatus = STATUS_SUCCESS;  

    ULONG               inBufLength;   /* Input buffer length */
    ULONG               outBufLength;  /* Output buffer length */
    ULONG               inBuf;         /* Pointer to Input and output buffer */

    PUCHAR              CharBuffer;
    PUSHORT             ShortBuffer;
    PULONG              LongBuffer;
    PVOID               ioBuffer;

    USHORT Offset;
    ULONG Value;
 
    ULONG ProcessID;    
    struct _EPROCESS *Process;

    irpSp = IoGetCurrentIrpStackLocation( pIrp );
    inBufLength = irpSp->Parameters.DeviceIoControl.InputBufferLength;
    outBufLength = irpSp->Parameters.DeviceIoControl.OutputBufferLength;

    ioBuffer    = pIrp->AssociatedIrp.SystemBuffer;

    CharBuffer  = (PUCHAR) ioBuffer;
    ShortBuffer = (PUSHORT) ioBuffer;
    LongBuffer  = (PULONG) ioBuffer;

    switch ( irpSp->Parameters.DeviceIoControl.IoControlCode )
     {
    
      case IOCTL_READ_PORT_BYTE:
 
            if ((inBufLength >= 2) && (outBufLength >= 1)) {
               // KdPrint( ("PORTACCESS: IOCTL_READ_PORT_UCHAR 0x%X",ShortBuffer[0]) );
                (UCHAR)Value = READ_PORT_UCHAR((PUCHAR)ShortBuffer[0]);
            /*  __asm {
               mov dx,word ptr CharBuffer[0] ;
               in al,dx
     mov byte ptr Value,al
         }
            */   // KdPrint( ("PORTACCESS: Value Read %X",Value) );
                CharBuffer[0] = Value;
            } else ntStatus = STATUS_BUFFER_TOO_SMALL;
            pIrp->IoStatus.Information = 1; /* Output Buffer Size */
            ntStatus = STATUS_SUCCESS;
            break;

      case IOCTL_WRITE_PORT_BYTE:
            if (inBufLength >= 3) {
               // KdPrint( ("PORTACCESS: IOCTL_WRITE_PORT_UCHAR(0x%X,0x%X)",ShortBuffer[0], CharBuffer[2]) );
                WRITE_PORT_UCHAR((PUCHAR)ShortBuffer[0], CharBuffer[2]);
           /*    __asm {
               mov dx,word ptr CharBuffer[0];
               mov al,byte ptr Value;
               out dx,al
         }
        */    } else ntStatus = STATUS_BUFFER_TOO_SMALL;
            pIrp->IoStatus.Information = 0; /* Output Buffer Size */
            ntStatus = STATUS_SUCCESS;
            break;
            
      case IOCTL_READ_PORT_WORD:
 
            if ((inBufLength >= 1) && (outBufLength >= 1)) {
               // KdPrint( ("PORTACCESS: IOCTL_READ_PORT_UCHAR 0x%X",ShortBuffer[0]) );
                (USHORT)Value = READ_PORT_USHORT((PUSHORT)ShortBuffer[0]);
               // KdPrint( ("PORTACCESS: Value Read %X",Value) );
                ShortBuffer[0] = Value;
            } else ntStatus = STATUS_BUFFER_TOO_SMALL;
            pIrp->IoStatus.Information = 1; /* Output Buffer Size */
            ntStatus = STATUS_SUCCESS;
            break;

      case IOCTL_WRITE_PORT_WORD:
            if (inBufLength >= 3) {
               // KdPrint( ("PORTACCESS: IOCTL_WRITE_PORT_UCHAR(0x%X,0x%X)",ShortBuffer[0], CharBuffer[2]) );
                WRITE_PORT_USHORT((PUSHORT)ShortBuffer[0], ShortBuffer[2]);
            } else ntStatus = STATUS_BUFFER_TOO_SMALL;
            pIrp->IoStatus.Information = 0; /* Output Buffer Size */
            ntStatus = STATUS_SUCCESS;
            break;
            
      case IOCTL_READ_PORT_DWORD:
 
            if ((inBufLength >= 2) && (outBufLength >= 1)) {
               // KdPrint( ("PORTACCESS: IOCTL_READ_PORT_UCHAR 0x%X",ShortBuffer[0]) );
                (ULONG)Value = READ_PORT_ULONG((PULONG)ShortBuffer[0]);
               // KdPrint( ("PORTACCESS: Value Read %X",Value) );
                LongBuffer[0] = Value;
            } else ntStatus = STATUS_BUFFER_TOO_SMALL;
            pIrp->IoStatus.Information = 1; /* Output Buffer Size */
            ntStatus = STATUS_SUCCESS;
            break;

      case IOCTL_WRITE_PORT_DWORD:
            if (inBufLength >= 3) {
               // KdPrint( ("PORTACCESS: IOCTL_WRITE_PORT_UCHAR(0x%X,0x%X)",ShortBuffer[0], CharBuffer[2]) );
                WRITE_PORT_ULONG((PULONG)ShortBuffer[0], LongBuffer[2]);
            } else ntStatus = STATUS_BUFFER_TOO_SMALL;
            pIrp->IoStatus.Information = 0; /* Output Buffer Size */
            ntStatus = STATUS_SUCCESS;
            break;

      default:
            KdPrint( ("PORTACCESS: Unsupported IOCTL Call\n") );
            ntStatus = STATUS_UNSUCCESSFUL;
            pIrp->IoStatus.Information = 0;
            break;

    }
    pIrp->IoStatus.Status = ntStatus;
    IoCompleteRequest( pIrp, IO_NO_INCREMENT );
    return ntStatus;
}

VOID PortAccessUnload(IN PDRIVER_OBJECT DriverObject)
{
    WCHAR DOSNameBuffer[] = L"\\DosDevices\\PortAccess";
    UNICODE_STRING uniDOSString;

    KdPrint( ("PORTAccess: PortAccess is Unloading . .\n") );

    if(IOPM_local) MmFreeNonCachedMemory(IOPM_local, sizeof(IOPM));
    RtlInitUnicodeString(&uniDOSString, DOSNameBuffer);
    IoDeleteSymbolicLink (&uniDOSString);
    IoDeleteDevice(DriverObject->DeviceObject);
}

NTSTATUS DriverEntry(
    IN PDRIVER_OBJECT DriverObject,
    IN PUNICODE_STRING RegistryPath
    )
{
    PDEVICE_OBJECT deviceObject;
    NTSTATUS status;
    WCHAR NameBuffer[] = L"\\Device\\PortAccess";
    WCHAR DOSNameBuffer[] = L"\\DosDevices\\PortAccess";
    UNICODE_STRING uniNameString, uniDOSString;

    KdPrint( ("PORTACCESS: PortAccess has Loaded") );

    IOPM_local = MmAllocateNonCachedMemory(sizeof(IOPM));
    if(IOPM_local == 0) return STATUS_INSUFFICIENT_RESOURCES;

    RtlFillMemory(IOPM_local, sizeof(IOPM), 0xFF);

    RtlInitUnicodeString(&uniNameString, NameBuffer);
    RtlInitUnicodeString(&uniDOSString, DOSNameBuffer);

    status = IoCreateDevice(DriverObject,
                            0,
                            &uniNameString,
                            FILE_DEVICE_UNKNOWN,
                            0,
                            FALSE,
                            &deviceObject);

    if(!NT_SUCCESS(status))
        return status;

    status = IoCreateSymbolicLink (&uniDOSString, &uniNameString);

    if (!NT_SUCCESS(status))
        return status;

    DriverObject->MajorFunction[IRP_MJ_CREATE] = PortAccessCreateDispatch;
    DriverObject->MajorFunction[IRP_MJ_DEVICE_CONTROL] = PortAccessDeviceControl;
    DriverObject->DriverUnload = PortAccessUnload;

    return STATUS_SUCCESS;
}

[编辑 -  12/16/04 by  ichabod]
AllenZh
驱动老牛
驱动老牛
  • 注册日期2001-08-19
  • 最后登录2015-11-27
  • 粉丝19
  • 关注10
  • 积分1316分
  • 威望2387点
  • 贡献值7点
  • 好评度321点
  • 原创分0分
  • 专家分0分
沙发#
发布于:2004-12-16 13:37
rt,访问PCI配置空间需要访问0xCF8和0xCFC端口,这两个端口都需要按4字节访问。我写了一个在win2k下访问端口的驱动,但是按字节访问是可以的(通过读CMOS验证),但是按4字节访问总是出错,推测原因一是Win2k把这种访问PCI配置空间的方式给禁了,再就是我的驱动写的有问题。有哪位达人可指教,在此先谢过了(最好能提供源码)
我的驱动的源码如下:
#include <ntddk.h>
#include "portaccess.h"

#define    IOPM_SIZE    0x2000

typedef UCHAR IOPM[IOPM_SIZE];

IOPM *IOPM_local = 0;

void Ke386SetIoAccessMap(int, IOPM *);
void Ke386QueryIoAccessMap(int, IOPM *);
void Ke386IoSetAccessProcess(PEPROCESS, int);

NTSTATUS PortAccessDeviceControl(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp);
VOID PortAccessUnload(IN PDRIVER_OBJECT DriverObject);

NTSTATUS PortAccessCreateDispatch(
    IN PDEVICE_OBJECT DeviceObject,
    IN PIRP Irp
    )
{
    Irp->IoStatus.Information = 0;
    Irp->IoStatus.Status = STATUS_SUCCESS;
    IoCompleteRequest(Irp, IO_NO_INCREMENT);
    return STATUS_SUCCESS;
}

NTSTATUS
PortAccessDeviceControl(
    IN PDEVICE_OBJECT DeviceObject,
    IN PIRP pIrp
    )

{
    PIO_STACK_LOCATION  irpSp;
    NTSTATUS            ntStatus = STATUS_SUCCESS;  

    ULONG               inBufLength;   /* Input buffer length */
    ULONG               outBufLength;  /* Output buffer length */
    ULONG               inBuf;         /* Pointer to Input and output buffer */

    PUCHAR              CharBuffer;
    PUSHORT             ShortBuffer;
    PULONG              LongBuffer;
    PVOID               ioBuffer;

    USHORT Offset;
    ULONG Value;
 
    ULONG ProcessID;    
    struct _EPROCESS *Process;

    irpSp = IoGetCurrentIrpStackLocation( pIrp );
    inBufLength = irpSp->Parameters.DeviceIoControl.InputBufferLength;
    outBufLength = irpSp->Parameters.DeviceIoControl.OutputBufferLength;

    ioBuffer    = pIrp->AssociatedIrp.SystemBuffer;

    CharBuffer  = (PUCHAR) ioBuffer;
    ShortBuffer = (PUSHORT) ioBuffer;
    LongBuffer  = (PULONG) ioBuffer;

    switch ( irpSp->Parameters.DeviceIoControl.IoControlCode )
     {
    
      case IOCTL_READ_PORT_BYTE:
 
            if ((inBufLength >= 2) && (outBufLength >= 1)) {
               // KdPrint( ("PORTACCESS: IOCTL_READ_PORT_UCHAR 0x%X",ShortBuffer[0]) );
                (UCHAR)Value = READ_PORT_UCHAR((PUCHAR)ShortBuffer[0]);
            /*  __asm {
               mov dx,word ptr CharBuffer[0] ;
               in al,dx
     mov byte ptr Value,al
         }
            */   // KdPrint( ("PORTACCESS: Value Read %X",Value) );
                CharBuffer[0] = Value;
            } else ntStatus = STATUS_BUFFER_TOO_SMALL;
            pIrp->IoStatus.Information = 1; /* Output Buffer Size */
            ntStatus = STATUS_SUCCESS;
            break;

      case IOCTL_WRITE_PORT_BYTE:
            if (inBufLength >= 3) {
               // KdPrint( ("PORTACCESS: IOCTL_WRITE_PORT_UCHAR(0x%X,0x%X)",ShortBuffer[0], CharBuffer[2]) );
                WRITE_PORT_UCHAR((PUCHAR)ShortBuffer[0], CharBuffer[2]);
           /*    __asm {
               mov dx,word ptr CharBuffer[0];
               mov al,byte ptr Value;
               out dx,al
         }
        */    } else ntStatus = STATUS_BUFFER_TOO_SMALL;
            pIrp->IoStatus.Information = 0; /* Output Buffer Size */
            ntStatus = STATUS_SUCCESS;
            break;
            
      case IOCTL_READ_PORT_WORD:
 
            if ((inBufLength >= 1) && (outBufLength >= 1)) {
               // KdPrint( ("PORTACCESS: IOCTL_READ_PORT_UCHAR 0x%X",ShortBuffer[0]) );
                (USHORT)Value = READ_PORT_USHORT((PUSHORT)ShortBuffer[0]);
               // KdPrint( ("PORTACCESS: Value Read %X",Value) );
                ShortBuffer[0] = Value;
            } else ntStatus = STATUS_BUFFER_TOO_SMALL;
            pIrp->IoStatus.Information = 1; /* Output Buffer Size */
            ntStatus = STATUS_SUCCESS;
            break;

      case IOCTL_WRITE_PORT_WORD:
            if (inBufLength >= 3) {
               // KdPrint( ("PORTACCESS: IOCTL_WRITE_PORT_UCHAR(0x%X,0x%X)",ShortBuffer[0], CharBuffer[2]) );
                WRITE_PORT_USHORT((PUSHORT)ShortBuffer[0], ShortBuffer[2]);
            } else ntStatus = STATUS_BUFFER_TOO_SMALL;
            pIrp->IoStatus.Information = 0; /* Output Buffer Size */
            ntStatus = STATUS_SUCCESS;
            break;
            
      case IOCTL_READ_PORT_DWORD:
 
            if ((inBufLength >= 2) && (outBufLength >= 1)) {
               // KdPrint( ("PORTACCESS: IOCTL_READ_PORT_UCHAR 0x%X",ShortBuffer[0]) );
                (ULONG)Value = READ_PORT_ULONG((PULONG)ShortBuffer[0]);
               // KdPrint( ("PORTACCESS: Value Read %X",Value) );
                LongBuffer[0] = Value;
            } else ntStatus = STATUS_BUFFER_TOO_SMALL;
            pIrp->IoStatus.Information = 1; /* Output Buffer Size */
            ntStatus = STATUS_SUCCESS;
            break;

      case IOCTL_WRITE_PORT_DWORD:
            if (inBufLength >= 3) {
               // KdPrint( ("PORTACCESS: IOCTL_WRITE_PORT_UCHAR(0x%X,0x%X)",ShortBuffer[0], CharBuffer[2]) );
                WRITE_PORT_ULONG((PULONG)ShortBuffer[0], LongBuffer[2]);
            } else ntStatus = STATUS_BUFFER_TOO_SMALL;
            pIrp->IoStatus.Information = 0; /* Output Buffer Size */
            ntStatus = STATUS_SUCCESS;
            break;

      default:
            KdPrint( ("PORTACCESS: Unsupported IOCTL Calln") );
            ntStatus = STATUS_UNSUCCESSFUL;
            pIrp->IoStatus.Information = 0;
            break;

    }
    pIrp->IoStatus.Status = ntStatus;
    IoCompleteRequest( pIrp, IO_NO_INCREMENT );
    return ntStatus;
}

VOID PortAccessUnload(IN PDRIVER_OBJECT DriverObject)
{
    WCHAR DOSNameBuffer[] = L"\DosDevices\PortAccess";
    UNICODE_STRING uniDOSString;

    KdPrint( ("PORTAccess: PortAccess is Unloading . .n") );

    if(IOPM_local) MmFreeNonCachedMemory(IOPM_local, sizeof(IOPM));
    RtlInitUnicodeString(&uniDOSString, DOSNameBuffer);
    IoDeleteSymbolicLink (&uniDOSString);
    IoDeleteDevice(DriverObject->DeviceObject);
}

NTSTATUS DriverEntry(
    IN PDRIVER_OBJECT DriverObject,
    IN PUNICODE_STRING RegistryPath
    )
{
    PDEVICE_OBJECT deviceObject;
    NTSTATUS status;
    WCHAR NameBuffer[] = L"\Device\PortAccess";
    WCHAR DOSNameBuffer[] = L"\DosDevices\PortAccess";
    UNICODE_STRING uniNameString, uniDOSString;

    KdPrint( ("PORTACCESS: PortAccess has Loaded") );

    IOPM_local = MmAllocateNonCachedMemory(sizeof(IOPM));
    if(IOPM_local == 0) return STATUS_INSUFFICIENT_RESOURCES;

    RtlFillMemory(IOPM_local, sizeof(IOPM), 0xFF);

    RtlInitUnicodeString(&uniNameString, NameBuffer);
    RtlInitUnicodeString(&uniDOSString, DOSNameBuffer);

    status = IoCreateDevice(DriverObject,
                            0,
                            &uniNameString,
                            FILE_DEVICE_UNKNOWN,
                            0,
                            FALSE,
                            &deviceObject);

    if(!NT_SUCCESS(status))
        return status;

    status = IoCreateSymbolicLink (&uniDOSString, &uniNameString);

    if (!NT_SUCCESS(status))
        return status;

    DriverObject->MajorFunction[IRP_MJ_CREATE] = PortAccessCreateDispatch;
    DriverObject->MajorFunction[IRP_MJ_DEVICE_CONTROL] = PortAccessDeviceControl;
    DriverObject->DriverUnload = PortAccessUnload;

    return STATUS_SUCCESS;
}

[编辑 -  12/16/04 by  ichabod]

留下Mail地址,我发给你修改后的代码
1,承接Windows下驱动/应用开发 2,本人原创虚拟鼠标/键盘,触摸屏,虚拟显卡,Mirror驱动,XP无盘的SCSI虚拟磁盘驱动等 3,windows下有尝技术服务(包括BUG调试,员工培训等) 欢迎深圳和海外企业联系.msn:mfczmh@sina.com
ichabod
驱动牛犊
驱动牛犊
  • 注册日期2004-12-08
  • 最后登录2007-08-09
  • 粉丝0
  • 关注0
  • 积分10分
  • 威望1点
  • 贡献值0点
  • 好评度1点
  • 原创分0分
  • 专家分0分
板凳#
发布于:2004-12-16 18:23
mhx011052@yahoo.com.cn
多谢多谢
AllenZh
驱动老牛
驱动老牛
  • 注册日期2001-08-19
  • 最后登录2015-11-27
  • 粉丝19
  • 关注10
  • 积分1316分
  • 威望2387点
  • 贡献值7点
  • 好评度321点
  • 原创分0分
  • 专家分0分
地板#
发布于:2004-12-16 20:57
mhx011052@yahoo.com.cn
多谢多谢

mail已经发送,请查收
1,承接Windows下驱动/应用开发 2,本人原创虚拟鼠标/键盘,触摸屏,虚拟显卡,Mirror驱动,XP无盘的SCSI虚拟磁盘驱动等 3,windows下有尝技术服务(包括BUG调试,员工培训等) 欢迎深圳和海外企业联系.msn:mfczmh@sina.com
ichabod
驱动牛犊
驱动牛犊
  • 注册日期2004-12-08
  • 最后登录2007-08-09
  • 粉丝0
  • 关注0
  • 积分10分
  • 威望1点
  • 贡献值0点
  • 好评度1点
  • 原创分0分
  • 专家分0分
地下室#
发布于:2004-12-16 22:14
信已收到,按你所说的做了修改,但结果仍然不对,还请再看一下
AllenZh
驱动老牛
驱动老牛
  • 注册日期2001-08-19
  • 最后登录2015-11-27
  • 粉丝19
  • 关注10
  • 积分1316分
  • 威望2387点
  • 贡献值7点
  • 好评度321点
  • 原创分0分
  • 专家分0分
5楼#
发布于:2004-12-17 09:19
信已收到,按你所说的做了修改,但结果仍然不对,还请再看一下
 


果然还有个低级错误
WRITE_PORT_ULONG((PULONG)ShortBuffer[0], LongBuffer[2]);
修改为
WRITE_PORT_ULONG((PULONG)(&ShortBuffer[0]), LongBuffer[2]);

WRITE_PORT_ULONG((PULONG)ShortBuffer, LongBuffer[2]);

其它的同样这样修改一下(第一个参数是指针,你将Value强制转为指针不可以)
1,承接Windows下驱动/应用开发 2,本人原创虚拟鼠标/键盘,触摸屏,虚拟显卡,Mirror驱动,XP无盘的SCSI虚拟磁盘驱动等 3,windows下有尝技术服务(包括BUG调试,员工培训等) 欢迎深圳和海外企业联系.msn:mfczmh@sina.com
ichabod
驱动牛犊
驱动牛犊
  • 注册日期2004-12-08
  • 最后登录2007-08-09
  • 粉丝0
  • 关注0
  • 积分10分
  • 威望1点
  • 贡献值0点
  • 好评度1点
  • 原创分0分
  • 专家分0分
6楼#
发布于:2004-12-18 18:38
仍然不对,两种方式都试过了,不行
AllenZh
驱动老牛
驱动老牛
  • 注册日期2001-08-19
  • 最后登录2015-11-27
  • 粉丝19
  • 关注10
  • 积分1316分
  • 威望2387点
  • 贡献值7点
  • 好评度321点
  • 原创分0分
  • 专家分0分
7楼#
发布于:2004-12-18 18:46
仍然不对,两种方式都试过了,不行

READ_PORT_USHORT和READ_PORT_ULONG等函数修改了吗?
1,承接Windows下驱动/应用开发 2,本人原创虚拟鼠标/键盘,触摸屏,虚拟显卡,Mirror驱动,XP无盘的SCSI虚拟磁盘驱动等 3,windows下有尝技术服务(包括BUG调试,员工培训等) 欢迎深圳和海外企业联系.msn:mfczmh@sina.com
ichabod
驱动牛犊
驱动牛犊
  • 注册日期2004-12-08
  • 最后登录2007-08-09
  • 粉丝0
  • 关注0
  • 积分10分
  • 威望1点
  • 贡献值0点
  • 好评度1点
  • 原创分0分
  • 专家分0分
8楼#
发布于:2004-12-19 13:21
当然都改过了,可还是不行啊
tiamo
VIP专家组
VIP专家组
  • 注册日期2002-02-26
  • 最后登录2018-01-09
  • 粉丝17
  • 关注4
  • 积分50分
  • 威望142点
  • 贡献值1点
  • 好评度40点
  • 原创分2分
  • 专家分15分
  • 原创先锋奖
  • 社区居民
9楼#
发布于:2004-12-20 05:28
我想问题出在你的exe文件中
不在这个驱动中.......

你怎么读pci config space的?
代码发上来....

或者你看看另外的那个也是读pci config space的帖子..

以上
ichabod
驱动牛犊
驱动牛犊
  • 注册日期2004-12-08
  • 最后登录2007-08-09
  • 粉丝0
  • 关注0
  • 积分10分
  • 威望1点
  • 贡献值0点
  • 好评度1点
  • 原创分0分
  • 专家分0分
10楼#
发布于:2004-12-22 16:52
多谢两位,问题已解决。用SoftICE调试发现除了达人指出的错误外,我的.exe也存在问题(ioBuffer传入的长度不对)。多谢指教。
游客

返回顶部