阅读:1576回复:5
怎么会没人回答呢
我想在驱动中分配10k的内存然后映射到应用程序,可是不知为什么得到的数据却不对,而在驱动中看到数据是对的,不明白怎么回事?
我的应用程序映射部分如下所示: if (!DeviceIoControl(hDevice,P9054_IOCTL_801, bufInput, IOCTL_INBUF_SIZE, &DataBuf, sizeof(DataBuf), &nOutput, NULL) ) { printf("ERROR: DeviceIoControl returns %0x.", GetLastError()); Exit(1); } if((fp=fopen("data","a+"))==NULL) { printf("file not open"); Exit(1); } iNum=fwrite(&DataBuf,4,1024,fp); fclose(fp); 驱动部分如下所示: m_pBuffer = new (NonPagedPool) long [BUFFER_SIZE]; m_pBuffer= (LONG *)((LONG)m_pBuffer&0xfffff000 + 0x1000); m_Mdl = new (NonPagedPool) KMemory(m_pBuffer, BUFFER_SIZE*4,FALSE, FALSE, NULL); UserSpaceAddress=m_Mdl->MapUserSpaceAddress(dMdl, UserMode); I.UserBuffer()=UserSpaceAddress; |
|
沙发#
发布于:2004-09-26 09:44
I.UserBuffer()=UserSpaceAddress;
可能有问题: I.UserBuffer()是个指针,你应该将UserSpaceAddress的值copy到该指针,还有I.Information()应该设置为sizeof(UserSpaceAddress); |
|
|
板凳#
发布于:2004-09-26 23:17
抄别人的 !!
inputBuffer = curIRPStack->Parameters.DeviceIoControl.Type3InputBuffer; outputBuffer = Irp->UserBuffer; inputBufferLength = curIRPStack->Parameters.DeviceIoControl.InputBufferLength; outputBufferLength = curIRPStack->Parameters.DeviceIoControl.OutputBufferLength; if ( !status ) // status == 0 -> OK { NextState(); status = MapGuiView( outputBuffer, outputBufferLength, Irp ); if ( status == STATUS_SUCCESS ) { SetGuiView( Irp, (PVOID)*(PULONG)outputBuffer ); DbgPrint("GetGuiView after Map = %x\n", GetGuiView(Irp)); } } extern void SetGuiView( IN PIRP pIrp, IN PVOID value ) { PFILE_OBJECT pFile = pIrp->Tail.Overlay.OriginalFileObject; pFile->FsContext = (PVOID)value; } NTSTATUS MapGuiView( IN OUT PVOID outputBuffer, IN DWORD outputBufferLength, IN PIRP pIrp ) { NTSTATUS status = STATUS_UNSUCCESSFUL; // Anything to do? if ( GetGuiView(pIrp) != NULL) { return STATUS_SUCCESS; } // Do we have good parameters? status = ValidateBuffer( outputBuffer, outputBufferLength, sizeof(DWORD) ); if ( status != STATUS_SUCCESS ) { return status; } _try { DWORD size = MmSizeOfMdl(pHeader,bufferSize); // map pHeader to user pMdl = (PMDL)ExAllocatePool( NonPagedPool, size ); pMdl = MmCreateMdl( pMdl, pHeader, bufferSize); if ( (pMdl->MdlFlags & (MDL_PAGES_LOCKED | MDL_SOURCE_IS_NONPAGED_POOL | MDL_MAPPED_TO_SYSTEM_VA | MDL_PARTIAL) ) == 0) MmBuildMdlForNonPagedPool(pMdl); PVOID ptr = MmMapLockedPages(pMdl, UserMode); if ( ptr == NULL ) *(PDBGTRAP_HEADER*)outputBuffer = NULL; else *(PDBGTRAP_HEADER*)outputBuffer = (PDBGTRAP_HEADER) (ULONG(ptr) | MmGetMdlByteOffset(pMdl)); DbgPrint("Pointer %x + Offset %x \n", ptr, MmGetMdlByteOffset(pMdl)); } __except (EXCEPTION_EXECUTE_HANDLER) { return STATUS_ACCESS_VIOLATION; } DbgPrint("MapGuiView success ! \n"); return status; } |
|
地板#
发布于:2004-09-27 14:54
AllenZh :
I.UserBuffer()是个指针我将它的地址指向UserSpaceAddress不对么,我在程序中这样写: *((PVOID *)(I.UserBuffer()))=UserSpaceAddress; 如果像你说的将UserSpaceAddress的数据copy到I.UserBuffer,I.UserBuffer是个指针,这能copy么? 我一直有点不明白,我是startdevice函数中分配的内存 m_pBuffer = new (NonPagedPool) long [BUFFER_SIZE]; m_Mdl = new (NonPagedPool) KMemory(m_pBuffer, BUFFER_SIZE*4,FALSE, FALSE, NULL); 然后我在dma回调函数中 RtlCopyMemory(m_pBuffer,SystemVirtualAddress,2048*4); 用到了这块地址,然后我再映射,不知道这块地址是否变了,是否是一块地址? KMK: 这块程序你试过了么,可是我到*(PDBGTRAP_HEADER*)outputBuffer = (PDBGTRAP_HEADER) (ULONG(ptr) | MmGetMdlByteOffset(pMdl)); 时却兰屏了? 这个PDBGTRAP_HEADER 是什么定义呢? |
|
地下室#
发布于:2004-09-27 15:13
试过了,可用的 !
PDBGTRAP_HEADER pHeader; pHeader = (PDBGTRAP_HEADER) ExAllocatePool( NonPagedPool, bufferSize ); 是这定义 typedef struct DBGTRAP_HEADER { SHORT size; // size in bytes of this header SHORT version; // current version of the driver ULONG sig; // Our signature...should be 'MVOF' ULONG numEntries; // Max # of entries this buffer can hold ULONG index; // Current index into the buffer // The shared event buffer immediately follows this header struct DBGTRAP_EVENT eb[0]; // <- ( disable: 4200 ) } DBGTRAP_HEADER, *PDBGTRAP_HEADER; MmSizeOfMdl The MmSizeOfMdl routine returns the number of bytes to allocate for an MDL describing a given address range. ULONG MmSizeOfMdl( IN PVOID Base, IN SIZE_T Length ); Parameters Base Pointer to the base virtual address for the range. Length Supplies the size, in bytes, of the range. Return Value MmSizeOfMdl returns the number of bytes required to contain the MDL. Headers Declared in wdm.h and ntddk.h. Include wdm.h or ntddk.h. Comments The given address range must be locked down if it will be accessed at raised IRQL. Memory for the MDL itself must be allocated from nonpaged pool if the caller subsequently passes a pointer to the MDL while running at IRQL >= DISPATCH_LEVEL. Callers of MmSizeOfMdl run at any IRQL. |
|
5楼#
发布于:2004-09-28 10:50
KMK: 谢谢!!! 我试试。你用的什么工具开发的,是kerneldriver么还是ddk? 我用的是ds不知道行不行?我分配内存和用内存,还有映射内存不是在一起做的,不知道有没有区别? |
|