阅读:1609回复:9
在2k和xp下,如何通过给定的物理地址访问内存?
怎么编写这种驱动呢?
这种驱动怎么加载呢? 有点迷惑。。。。。。 望高手指点一下,可以看哪些文档? |
|
沙发#
发布于:2004-11-24 22:13
这个好像有个函数有这个功能
|
|
板凳#
发布于:2004-11-25 01:15
1. Read !ptov and !vtop in WinDbg help. And I knew there's a chapter in SoftIce manual to talking about physical and virtual address translate. They are talking about translate from virtual address to physical address, but you can get a sense of it.
You might want to download Volumn 3 of Intel IA-32 manual (system programming) from Intel website. 2. Why do you need to have this feature? Generally, this shouldn't be useful in device driver, especially for pnp device. So you might need to think hard before following this design. |
|
地板#
发布于:2004-11-25 02:44
You might also try MmGetVirtualForPhysical, which is reserved for system use. But it seems to work for the current process address space.
|
|
地下室#
发布于:2004-11-25 13:11
1. Read !ptov and !vtop in WinDbg help. And I knew there's a chapter in SoftIce manual to talking about physical and virtual address translate. They are talking about translate from virtual address to physical address, but you can get a sense of it. What I exactly need is to access a specific range of physical memory in user level, but the user level doesn't have enough previlege, and I think driver must be used to help me. I don't know how to write such kind of driver, can u give me some hints? Thk u very much :cool: |
|
5楼#
发布于:2004-11-25 13:24
ZwMapViewOfSection
|
|
|
6楼#
发布于:2004-11-25 13:54
ZwMapViewOfSection 这个函数是在用户级调用还是在驱动中调用呢? |
|
7楼#
发布于:2004-11-25 13:59
在驱动中用,应用层的方法可以参考我的方法,在GDT中通过CALLGATE进RING0来获得MBR的部分.
.686p .model flat, stdcall option casemap :none ; case sensitive ; ######################################################################### include \masm32\include\windows.inc include \masm32\include\user32.inc include \masm32\include\kernel32.inc include \masm32\include\advapi32.inc includelib \masm32\lib\user32.lib includelib \masm32\lib\kernel32.lib includelib \masm32\lib\advapi32.lib DEBUG = TRUE HMODULE typedef dword NTSTATUS typedef dword PACL typedef dword PSECURITY_DESCRIPTOR typedef dword OBJ_INHERIT=2 OBJ_PERMANENT=10h OBJ_EXCLUSIVE=20h OBJ_CASE_INSENSITIVE=40h OBJ_OPENIF=80h OBJ_OPENLINK =100h OBJ_KERNEL_HANDLE=200 OBJ_VALID_ATTRIBUTES=3F2h SE_KERNEL_OBJECT = 6 GRANT_ACCESS =1 NO_INHERITANCE =0 TRUSTEE_IS_NAME=1 TRUSTEE_IS_USER=1 STATUS_SUCCESS =0 STATUS_ACCESS_DENIED =0C0000022h STATUS_ACCESS_VIOLATION equ 0C0000005h STATUS_INFO_LENGTH_MISMATCH equ 0C0000004h SystemModuleInformation equ 11 PVOID TYPEDEF DWORD UNLONG TYPEDEF DWORD CHAR TYPEDEF BYTE UNICODE_STRING struct nLength word ? MaximumLength word ? Buffer dword ? UNICODE_STRING ends OBJECT_ATTRIBUTES struct nLength dword ? RootDirectory HANDLE ? ObjectName dword ?;PUNICODE_STRING Attributes dword ?; SecurityDescriptor dword ?; PVOID // Points to type SECURITY_DESCRIPTOR SecurityQualityOfService dword ?;PVOID // Points to type SECURITY_QUALITY_OF_SERVICE OBJECT_ATTRIBUTES ends TRUSTEE struct pMultipleTrustee dword ?;PTRUSTEE MultipleTrusteeOperation dword ?; MULTIPLE_TRUSTEE_OPERATION TrusteeForm dword ?;TRUSTEE_FORM TrusteeType dword ?;TRUSTEE_TYPE ptstrName dword ?;LPTSTR TRUSTEE ends EXPLICIT_ACCESS struct grfAccessPermissions DWORD ? grfAccessMode dword ? ;ACCESS_MODE grfInheritance DWORD ? ; Trustee TRUSTEE <> ; EXPLICIT_ACCESS ends MyGATE struct ;门结构类型定义 OFFSETL WORD ? ;32位偏移的低16位 SELECTOR WORd ? ;选择子 DCOUNT BYTE ? ;双字计数字段 GTYPE BYTE ? ;类型 OFFSETH WORD ? ;32位偏移的高16位 MyGATE ends SetPhyscialMemorySectionCanBeWrited proto :dword MiniMmGetPhysicalAddress proto :dword ENTERRING0 macro pushad pushfd cli mov eax,cr0 ;get rid off readonly protect and eax,0fffeffffh mov cr0,eax endm LEAVERING0 macro mov eax,cr0 ;restore readonly protect or eax,10000h mov cr0,eax sti popfd popad retf endm UNICODE_STR macro str irpc _c,<str> db '&_c' db 0 endm endm .data? GdtLimit dw ? GdtAddr dd ? mapAddr dd ? OldEsp dd ? readed dw ? buffer db 512 dup(?) ShowText db 512*3 dup (?) .data align 4 objname dw objnamestr_size,objnamestr_size+2 objnameptr dd 0 objnamestr equ this byte UNICODE_STR <\Device\PhysicalMemory> objnamestr_size equ $-objnamestr align 4 ObjAttr db 24 dup (0) IsIdtFlag dd 0 Callgt dq 0 ;call gate's sel:off Caption db 'Windows XP绝对磁盘读写--MBR',0 Digit db '0123456789ABCDEF',0 .code _Ring0Proc PROC ; Ring0 code here.. ENTERRING0 mov dx,1f6h ;Drive and head port mov al,0a0h ;Drive 0,Head 0 out dx,al mov dx,1f2h ;Sector count port mov al,1 ;Read One Sector out dx,al mov dx,1f3h ;Sector number port mov al,1 ;Read One Sector out dx,al mov dx,1f4h ;Cylinder low port xor al,al ;Cylinder 0 out dx,al mov dx,1f5h ;Cylinder high port xor al,al ;The rest of Cylinder 0 out dx,al mov dx,1f7h ;Command port mov al,20h ;Read with Entry out dx,al Still_going: in al,dx test al,8 ;This means the sector buffer requires servcing jz Still_going;do not continue until the sector buffer is ready xor ecx,ecx mov cx,512/2 ;one sector/2 mov edi,offset buffer mov dx,1f0h ;data port - data comes in and out here cli cld rep insw sti LEAVERING0 _Ring0Proc ENDP Ring0CodeLen=$-_Ring0Proc _ShowBuffer proc ;显示所读出的信息 ;把数据转换成16进制的形式 mov [readed],512 mov esi,offset buffer ;数据 mov edi,offset ShowText ;转换后的数据 mov ebx,offset Digit xor ecx,ecx xor eax,eax computeAgain: cmp [readed],0 jz endCompute dec [readed] lodsb push eax shr eax,4 ;高4位 xlatb stosb pop eax and eax,0fH ;低4位 xlatb stosb mov byte ptr[edi],' ' ;空格 inc edi inc ecx cmp ecx,16 jnz computeAgain xor ecx,ecx mov byte ptr[edi-1],13 ;回车 jmp computeAgain endCompute: ;显示 invoke MessageBoxA,NULL,offset ShowText,offset Caption,MB_OK ret _ShowBuffer endp SetPhyscialMemorySectionCanBeWrited proc uses ebx esi edi hSection:HANDLE local pDacl: PACL local pNewDacl:PACL local pSD :PSECURITY_DESCRIPTOR local dwRes:DWORD ; local ea:EXPLICIT_ACCESS ; invoke GetSecurityInfo,hSection,SE_KERNEL_OBJECT,DACL_SECURITY_INFORMATION,\ NULL,NULL, addr pDacl,NULL, addr pSD cmp eax,ERROR_SUCCESS jz @f jmp OutSet @@: mov dwRes,eax mov ea.grfAccessPermissions ,SECTION_MAP_WRITE;2 mov ea.grfAccessMode ,GRANT_ACCESS;1 mov ea.grfInheritance,NO_INHERITANCE;0 mov ea.Trustee.pMultipleTrustee,0 mov ea.Trustee.MultipleTrusteeOperation,0 mov ea.Trustee.TrusteeForm,TRUSTEE_IS_NAME;1 mov ea.Trustee.TrusteeType,TRUSTEE_IS_USER;1 call @f db "CURRENT_USER",0 @@: pop edx mov ea.Trustee.ptstrName,edx invoke SetEntriesInAcl,1,addr ea,pDacl,addr pNewDacl cmp eax,ERROR_SUCCESS jz @f jmp OutSet @@: invoke SetSecurityInfo,hSection,SE_KERNEL_OBJECT,DACL_SECURITY_INFORMATION,\ NULL,NULL,pNewDacl,NULL OutSet: cmp pSD,0 jz @f invoke LocalFree,pSD @@: cmp pNewDacl,0 jz @f invoke LocalFree,pNewDacl @@: ret SetPhyscialMemorySectionCanBeWrited endp MiniMmGetPhysicalAddress proc virtualaddress:dword mov eax,virtualaddress cmp eax,80000000h jb @f cmp eax,0a0000000h jae @f and eax,1FFFF000h ret @@: mov eax,0 ret MiniMmGetPhysicalAddress endp ExecRing0Proc proc Entry:ULONG,seglen:ULONG local tmpSel:dword local setcg:dword local BaseAddress:dword local NtdllMod :dword local hSection:HANDLE local status:NTSTATUS local objectAttributes:OBJECT_ATTRIBUTES local objName:UNICODE_STRING mov status,STATUS_SUCCESS; sgdt GdtLimit invoke MiniMmGetPhysicalAddress,GdtAddr mov mapAddr,eax test eax,eax jz Exit1 call @f db "Ntdll.dll",0 @@: call LoadLibraryA mov NtdllMod,eax lea edx,objnamestr mov objnameptr,edx lea edi,ObjAttr and di,0fffch ;align to 4 bytes,or ZwOpenSection will fail push edi ;edi->ObjAttr push 24 ;length of <\Device\PhysicalMemory> pop ecx push ecx xor eax,eax rep stosb ;put ObjAttr with 0 pop ecx pop edi mov esi,edi stosd mov dword ptr[esi],ecx stosd lea eax,[edx-8] ;eax->objname stosd ;ObjAddr(18h,00,00,00,00,00,00,00,offset objname,40,02,00,00,dd 2 dup(0) mov dword ptr [edi],240h call @f db "ZwOpenSection",0 @@: push NtdllMod call GetProcAddress mov ebx,eax ;ebx=ZwOpenSection push esi ;esi->ObjAttr push SECTION_MAP_READ or SECTION_MAP_WRITE lea edi,hSection push edi ;edi->hSection call eax ;ZwOpenSection(&hSection,SECTION_MAP_READ or SECTION_MAP_WRITE,ObjAttr) mov status,eax cmp status,STATUS_ACCESS_DENIED jnz AccessPermit mov eax,ebx push esi push READ_CONTROL or WRITE_DAC push edi call eax mov status,eax invoke SetPhyscialMemorySectionCanBeWrited,hSection call @f db "ZwClose",0 @@: push NtdllMod call GetProcAddress push hSection call eax ;zwClose hSection mov eax,ebx push esi push SECTION_MAP_READ or SECTION_MAP_WRITE lea edi,hSection push edi call eax mov status ,eax ;status =ZwOpenSection(&hSection,SECTION_MAP_WRITE|SECTION_MAP_WRITE,&objectAttributes); AccessPermit: cmp status ,STATUS_SUCCESS jz @f ;printf("Error Open PhysicalMemory Section Object,Status:%08X\n",status); ;return 0; mov eax,0 ret @@: movzx eax,word ptr[GdtLimit] inc eax invoke MapViewOfFile,hSection, FILE_MAP_READ or FILE_MAP_WRITE, 0, mapAddr, \ eax mov BaseAddress,eax cmp BaseAddress,0 jnz @f ;printf("Error MapViewOfFile:"); ;PrintWin32Error(GetLastError()); return 0; mov eax,0 ret @@: mov esi,eax ;esi->gdt base movzx eax,word ptr GdtLimit ;eax=gdt limit mov IsIdtFlag,0 call Search_XDT mov tmpSel,eax mov setcg,FALSE; mov esi,BaseAddress mov ebx,eax add ebx,esi assume ebx:ptr MyGATE mov edx,Entry mov [ebx].OFFSETL,dx mov [ebx].SELECTOR ,8 mov [ebx].DCOUNT ,0 mov [ebx].GTYPE,0ech shr edx,16 mov [ebx].OFFSETH,dx mov setcg,TRUE cmp setcg,0 jnz ChangeOK call @f db "ZwClose",0 @@: push NtdllMod call GetProcAddress push hSection call eax xor eax,eax ret ChangeOK: and dword ptr Callgt,0 or al,3h mov word ptr [Callgt+4],ax ;farcall[2]=((short)((ULONG)cg-(ULONG)BaseAddress))|3; //Ring 3 callgate; invoke VirtualLock,Entry,seglen test eax,eax jnz @f xor eax,eax ret @@: invoke GetCurrentThread invoke SetThreadPriority,eax,THREAD_PRIORITY_TIME_CRITICAL invoke Sleep,0 call fword ptr [Callgt] ;use callgate to Ring0! ;_asm call fword ptr [farcall] invoke GetCurrentThread invoke SetThreadPriority,eax,THREAD_PRIORITY_NORMAL invoke VirtualUnlock,Entry,seglen ;//Clear callgate ;*(ULONG *)cg=0; ;*((ULONG *)cg+1)=0; mov esi,BaseAddress mov eax,tmpSel add eax,esi mov dword ptr[eax],0 mov dword ptr[eax+4],0 ;ZwClose(hSection); call @f db "ZwClose",0 @@: push NtdllMod call GetProcAddress push hSection call eax mov eax,TRUE ret ExecRing0Proc endp Search_XDT proc near ;entry esi==Base of Idt or GDT ;Eax==Limit pushad mov ebx,eax ;ebx=limit mov eax,8 ; skipping null selector @@1: cmp IsIdtFlag,1 jz IsIdt cmp dword ptr [esi+eax+0],0 ;gdt jnz @@2 cmp dword ptr [esi+eax+4],0 jz @@3 jmp @@2 IsIdt: cmp dword ptr [esi+eax+0],80000h ;idt jnz @@2 cmp dword ptr [esi+eax+4],0 jz @@3 @@2: add eax,8 cmp eax,ebx jb @@1 ;if we haven't found any free GDT entry, ;lets use the last two entries mov eax,ebx sub eax,7 @@3: mov [esp+4*7],eax ; return off in eax popad ; eax=free GDT or IDT entry selector ret Search_XDT endp main: assume fs:nothing push offset MySEH push fs:[0] mov fs:[0],esp mov OldEsp,esp mov ax,ds ;if Win9x? test ax,4 jnz Exit1 invoke VirtualLock,offset _Ring0Proc,Ring0CodeLen ;invoke VirtualLock,offset r0Data,sizeof(RING0DATA) invoke ExecRing0Proc,offset _Ring0Proc,Ring0CodeLen ;invoke VirtualUnlock,offset r0Data,sizeof(RING0DATA) invoke VirtualUnlock,offset _Ring0Proc,Ring0CodeLen call _ShowBuffer Exit1: pop fs:[0] add esp,4 invoke ExitProcess,0 MySEH : mov esp,OldEsp pop fs:[0] add esp,4 invoke ExitProcess,-1 end main |
|
|
8楼#
发布于:2004-11-25 14:20
怎么编写这种驱动呢? 如果编写驱动的话,实际上就比较容易了,你可以直接使用相关内核函数(ntdll.dll中的ZwOpenSection,ZwMapViewofFile)来进行访问,因为驱动程序工作在RING0级. 这样的驱动也比较容易写,你可以自定义IRP通过你的设备专门读写物理内存,其他的IRP只简单的往设备栈下层传就可以了. 用调用门也是一种方法,它提供了一种在RING3下调用RING0几代码的方式. |
|
9楼#
发布于:2004-11-25 22:05
kernel 的其实用这个MmMapIoSpace就可以了
user的可以读PhysicalMemory这个section完成...这个代码到google上搜索一片一片的 |
|