调试程序的时候 经常要查看内存数据 孤陋寡闻,不知道有什么API可以直接把内存数据以文本的形式写出来 索性自己写了一个函数 ,从中学到不少东西 共享出来,给有和我同样需要的朋友


invoke _MemToStr,40001000h,30h
invoke  MessageBox,NULL,eax,$CTA0("TEST"),MB_OK


;invoke _MemToStr,lpDate,DateLen    lpDate 想读取的内存地址 读取长度  返回EAX为文本指针
;invoke  _DwToStr,lpStr,Date

_DwToStr  proc uses edx ebx ecx edi esi  lpStr,Date
      Local @szTMP:DWORD
      Local @szBuffer[512]:Byte
      invoke  RtlZeroMemory,addr @szBuffer,sizeof @szBuffer
      mov  esi,lpStr
      lea  edi,@szTMP
      mov  ebx,Date
      mov  ax,bx
      shr  ebx,16
      shl  eax,16
      add  eax,ebx
      mov  @szTMP,eax
      mov  ecx,4
      @@:
      mov  eax,0
      mov  al,[edi]
      shl  ax,4
      shr  al,4
      .if ah<0ah 
        add ah,30h
      .else
        add ah,37h
      .endif
  
      .if al<0ah 
        add al,30h
      .else
        add al,37h
      .endif
        mov  dh,al
        mov  dl,ah
        mov  word ptr [esi],dx
      add  edi,1
      add  esi,2
  loop @b
  lea eax,@szBuffer
  ret
_DwToStr  endp



_MemToStr  proc  uses ebx edx ecx edi esi lpDate,DateLen
  Local @szAddrTmpHex:Byte
  Local @szBuffer[2048]:Byte
  local  @i:byte
  invoke  RtlZeroMemory,addr @szBuffer,sizeof @szBuffer
  mov  edi,lpDate
  lea  esi,@szBuffer
  mov  ecx,6
  mov  @i,0
  mov  eax,2020h
  init:
  mov  dword ptr [esi],eax
  add  esi,2
  loop init
  
  mov  ecx,10
  mov  bx,30h
  init2:
  mov  word ptr [esi],bx
  mov  dword ptr [esi+1],eax
  add  bx,1
  add  esi,3
  loop init2
  
  mov  ecx,6
  mov  bx,41h
  init3:
  mov  word ptr [esi],bx
  mov  dword ptr [esi+1],eax
  add  bx,1
  add  esi,3
  loop init3
  
  mov  dx,0d0ah
  mov  word ptr [esi],dx
  add  esi,2
  
  mov  ecx,DateLen
  @@:  
    .if @i==0    ;新行
      mov  dx,7830h
      mov  word ptr [esi],dx
      add  esi,2
      invoke _DwToStr,esi,edi
      mov  dl,20h
      mov  byte ptr [esi+8],dl
      add  esi,9
    .endif
    
  add @i,1
  mov  eax,0
  mov  al,[edi]
  shl  ax,4
  shr  al,4
  .if ah<0ah 
    add ah,30h
  
  .else
    add ah,37h
  .endif
  
  .if al<0ah 
    add al,30h
  
  .else
    add al,37h
  .endif
  mov  dh,al
  mov  dl,ah
  mov  word ptr [esi],dx
  mov  dl,20h
  mov  byte ptr [esi+2],dl
  .if  @i<16
    add  esi,3
    

  .else
    
    mov  dx,0d0ah
    mov  word ptr [esi+3],dx
    add  esi,5
    mov  @i,0
    
  .endif

  add  edi,1
  loop @b
  
  lea eax,@szBuffer
  ret
_MemToStr  endp
  

其中有一个似乎可以用递归的地方,结果试了N次都调试不成功  总返回 jmp too far

  • 标 题:答复
  • 作 者:mmhkh
  • 时 间:2009-02-15 10:07

刚看了 书呆老大 给昨天的一个问题的回复
发现这个函数写的有问题。
不要返回栈上的数据 这是基本常识。汗现在我总算知道了。。
疑似应该是 不要返回 局部变量的地址吧。上面的程序用内部变量做字符缓冲区
函数直接返回 字符串在堆栈上的地址。。。。。。
有问题。。。各位想用的话 最好自己修改下吧。。。给_MemToStr加一个输入参数 指向 调用者自己定义的缓冲区