原:http://www.cnblogs.com/developersupport/p/windbgcommand-u.html

在调试过程中难免会遇到须要反编译代码来分析逻辑的时候。在windbg中,须要反编译代码就要用到u/ub/uf这三个命令。本文这里分别介绍这三个命令各自的用途。

下面是一个quick sort的实例代码,将其编译成可运行文件,然后通过windbg运行。

#include <stdio.h>
#include <string.h> #define MAXLINES 5000
#define MAXLEN 1000
#define ALLOCSIZE 10000 static char allocbuf[ALLOCSIZE];
static char *allocp = allocbuf;
char *lineptr[MAXLINES]; int readlines(char *lineptr[], int nlines);
void writelines(char *lineptr[], int nlines); void qsort(void *lineptr[], int left, int right, int(*comp)(void *, void *));
int numcmp(char *, char *); main(int argc, int *argv[])
{
int nlines;
int numeric = 0; if((argc > 1) && strcmp(argv[1], "-n")==0)
numeric = 1;
if((nlines = readlines(lineptr, MAXLINES)) >= 0){
qsort((void **) lineptr, 0, nlines-1,
(int (*)(void*, void*))(numeric ? numcmp : strcmp));
writelines(lineptr, nlines);
return 0;
} else {
printf("input too big to sort\n");
return 1;
}
} void qsort(void *v[], int left, int right,
int (*comp)(void *, void *))
{
int i, last;
void swap(void *v[], int, int); if(left >= right)
return;
swap(v, left, (left+right)/2);
last = left;
for( i = left+1; i <= right; i++)
if((*comp)(v[i], v[left]) < 0)
swap(v, ++last, i);
swap(v, left, last);
qsort(v, left, last-1, comp);
qsort(v, last+1, right, comp);
} char *alloc(int n)
{
if(allocbuf + ALLOCSIZE - allocp >= n){
allocp += n;
return allocp - n;
} else
return 0;
} int getline(char s[], int lim)
{
int c, i;
i = 0;
while(--lim > 0 && (c=getchar()) != EOF && c != '\n')
s[i++] = c;
if(c == '\n')
s[i++] = c;
s[i] = '\0';
return i;
} int readlines(char *lineptr[], int maxlines)
{
int len, nlines;
char *p, line[MAXLEN];
nlines = 0;
while((len = getline(line, MAXLEN)) > 0)
if((nlines >= maxlines || (p = alloc(len)) == NULL))
return -1;
else{
line[len-1] = '\0';
strcpy(p, line);
lineptr[nlines++] = p;
}
return nlines;
} void writelines(char *lineptr[], int nlines)
{
int i; for(i = 0; i < nlines; i++)
printf("%s\n", lineptr[i]);
} int numcmp(char *s1, char *s2)
{
double v1, v2; v1 = atof(s1);
v2 = atof(s2);
if(v1 < v2)
return -1;
else if(v1 > v2)
return 1;
else
return 0;
} void swap(void *v[], int i, int j)
{
void *temp; temp = v[i];
v[i] = v[j];
v[j] = temp;
}

u命令

u命令的作用就是反编译指定地址參数之后的代码,假设不指定地址參数,即仅仅输入u命令运行,那么默认就是反编译当前线程的当前指令

我们来做个实验。在运行起实例代码之后,在main函数上设断点,然后通过u命令来反编译eip(instruction pointer)中的地址指向的方法地址。即当前函数的运行地址。能够查看接下来当前线程要运行的汇编代码。

关于x86各个寄存器的含义能够參考x86 Architecture

0:000> x qsort!main
000c12e0 qsort!main (int, int **)
0:000> bp 000c12e0 
0:000> g
Breakpoint 0 hit
eax=004e8228 ebx=00000000 ecx=00000001 edx=00000000 esi=00000000 edi=00000000
eip=000c12e0 esp=0027f7d4 ebp=0027f818 iopl=0 nv up ei pl zr na pe nc
cs=0023 ss=002b ds=002b es=002b fs=0053 gs=002b efl=00000246
qsort!main:
000c12e0 55 push ebp
0:000> u @eip
qsort!main [c:\qsort.c @ 19]:
000c12e0 55 push ebp
000c12e1 8bec mov ebp,esp
000c12e3 83ec0c sub esp,0Ch
000c12e6 c745f800000000 mov dword ptr [ebp-8],0
000c12ed 837d0801 cmp dword ptr [ebp+8],1
000c12f1 7e27 jle qsort!main+0x3a (000c131a)
000c12f3 6804b00e00 push offset qsort!allocp+0x4 (000eb004)
000c12f8 b804000000 mov eax,4

uf命令

uf命令是用来反编译整个函数的汇编代码,

比方我希望反编译整个main函数,能够通过uf函数。

0:000> uf @eip
qsort!main [c:\qsort.c @ 19]:
19 000c12e0 55 push ebp
19 000c12e1 8bec mov ebp,esp
19 000c12e3 83ec0c sub esp,0Ch
21 000c12e6 c745f800000000 mov dword ptr [ebp-8],0
23 000c12ed 837d0801 cmp dword ptr [ebp+8],1
23 000c12f1 7e27 jle qsort!main+0x3a (000c131a)

qsort!main+0x13 [c:\qsort.c @ 23]:
23 000c12f3 6804b00e00 push offset qsort!allocp+0x4 (000eb004)
23 000c12f8 b804000000 mov eax,4
23 000c12fd c1e000 shl eax,0
23 000c1300 8b4d0c mov ecx,dword ptr [ebp+0Ch]
23 000c1303 8b1401 mov edx,dword ptr [ecx+eax]
23 000c1306 52 push edx
23 000c1307 e854080000 call qsort!strcmp (000c1b60)
23 000c130c 83c408 add esp,8
23 000c130f 85c0 test eax,eax
23 000c1311 7507 jne qsort!main+0x3a (000c131a)

qsort!main+0x33 [c:\qsort.c @ 24]:
24 000c1313 c745f801000000 mov dword ptr [ebp-8],1

qsort!main+0x3a [c:\qsort.c @ 25]:
25 000c131a 6888130000 push 1388h
25 000c131f 68e0020f00 push offset qsort!lineptr (000f02e0)
25 000c1324 e8f5fcffff call qsort!ILT+25(_readlines) (000c101e)
25 000c1329 83c408 add esp,8
25 000c132c 8945fc mov dword ptr [ebp-4],eax
25 000c132f 837dfc00 cmp dword ptr [ebp-4],0
25 000c1333 7c47 jl qsort!main+0x9c (000c137c)

qsort!main+0x55 [c:\qsort.c @ 27]:
27 000c1335 837df800 cmp dword ptr [ebp-8],0
27 000c1339 7409 je qsort!main+0x64 (000c1344)

qsort!main+0x5b [c:\qsort.c @ 27]:
27 000c133b c745f414100c00 mov dword ptr [ebp-0Ch],offset qsort!ILT+15(_numcmp) (000c1014)
27 000c1342 eb07 jmp qsort!main+0x6b (000c134b)

qsort!main+0x64 [c:\qsort.c @ 27]:
27 000c1344 c745f4601b0c00 mov dword ptr [ebp-0Ch],offset qsort!strcmp (000c1b60)

qsort!main+0x6b [c:\qsort.c @ 27]:
27 000c134b 8b45f4 mov eax,dword ptr [ebp-0Ch]
27 000c134e 50 push eax
27 000c134f 8b4dfc mov ecx,dword ptr [ebp-4]
27 000c1352 83e901 sub ecx,1
27 000c1355 51 push ecx
27 000c1356 6a00 push 0
27 000c1358 68e0020f00 push offset qsort!lineptr (000f02e0)
27 000c135d e8adfcffff call qsort!ILT+10(_qsort) (000c100f)
27 000c1362 83c410 add esp,10h
28 000c1365 8b55fc mov edx,dword ptr [ebp-4]
28 000c1368 52 push edx
28 000c1369 68e0020f00 push offset qsort!lineptr (000f02e0)
28 000c136e e8bafcffff call qsort!ILT+40(_writelines) (000c102d)
28 000c1373 83c408 add esp,8
29 000c1376 33c0 xor eax,eax
29 000c1378 eb14 jmp qsort!main+0xae (000c138e)

qsort!main+0x9c [c:\qsort.c @ 31]:
31 000c137c 6808b00e00 push offset qsort!allocp+0x8 (000eb008)
31 000c1381 e80c060000 call qsort!printf (000c1992)
31 000c1386 83c404 add esp,4
32 000c1389 b801000000 mov eax,1

qsort!main+0xae [c:\qsort.c @ 34]:
34 000c138e 8be5 mov esp,ebp
34 000c1390 5d pop ebp
34 000c1391 c3 ret

另外uf另一个比較经常使用的參数项/c,通过/c能够查看这个函数中的函数调用(call)都有哪些,当一个函数反编译代码过长的时候,我们能够通过这个參数来过滤全部的方法调用,方便查找。

0:000> uf /c @eip
qsort!main (000c12e0) [c:\qsort.c @ 19]
qsort!main+0x27 (000c1307) [c:\qsort.c @ 23]:
call to qsort!strcmp (000c1b60) [f:\dd\vctools\crt_bld\SELF_X86\crt\src\INTEL\strcmp.asm @ 65]
qsort!main+0x44 (000c1324) [c:\qsort.c @ 25]:
call to qsort!ILT+25(_readlines) (000c101e)
qsort!main+0x7d (000c135d) [c:\qsort.c @ 27]:
call to qsort!ILT+10(_qsort) (000c100f)
qsort!main+0x8e (000c136e) [c:\qsort.c @ 28]:
call to qsort!ILT+40(_writelines) (000c102d)
qsort!main+0xa1 (000c1381) [c:\qsort.c @ 31]:
call to qsort!printf (000c1992) [f:\dd\vctools\crt_bld\self_x86\crt\src\printf.c @ 49]

ub命令

ub命令与u的不同之处在于它是用来查看线程当前指令之前的汇编代码。b这里就是代表向后查看(backward)的意思。

在调用qsort!qsort方法之前设置断点,运行到这个断点的时候。假设希望看到前面运行的代码是什么样的。这时能够通过ub函数查看,通过对照就能够发现ub列出的汇编代码恰好是调用qsort!qsort方法之前的指令。

0:000> bp 000c135d 
0:000> g
Breakpoint 1 hit
eax=000c1b60 ebx=00000000 ecx=00000002 edx=00000000 esi=00000000 edi=00000000
eip=000c135d esp=0027f7b4 ebp=0027f7d0 iopl=0 nv up ei pl nz na po nc
cs=0023 ss=002b ds=002b es=002b fs=0053 gs=002b efl=00000202
qsort!main+0x7d:
000c135d e8adfcffff call qsort!ILT+10(_qsort) (000c100f)
0:000> ub 000c135d 
qsort!main+0x64 [c:\qsort.c @ 27]:
000c1344 c745f4601b0c00 mov dword ptr [ebp-0Ch],offset qsort!strcmp (000c1b60)
000c134b 8b45f4 mov eax,dword ptr [ebp-0Ch]
000c134e 50 push eax
000c134f 8b4dfc mov ecx,dword ptr [ebp-4]
000c1352 83e901 sub ecx,1
000c1355 51 push ecx
000c1356 6a00 push 0
000c1358 68e0020f00 push offset qsort!lineptr (000f02e0)

我希望对你有所帮助上述内容

Aaron Zhang

基本调试命令 - u/ub/uf的更多相关文章

  1. 基础调试命令 - u/ub/uf

    在调试过程中难免会遇到需要反编译代码来分析逻辑的时候,在windbg中,需要反编译代码就要用到u/ub/uf这三个命令.本文这里分别介绍这三个命令各自的用途. 以下是一个quick sort的实例代码 ...

  2. WinDBG 调试命令大全

    转载收藏于:http://www.cnblogs.com/kekec/archive/2012/12/02/2798020.html  #调试命令窗口 ++++++++++++++++++++++++ ...

  3. Windbg调试命令详解

    作者:张佩][原文:http://www.yiiyee.cn/Blog] 1. 概述 用户成功安装微软Windows调试工具集后,能够在安装目录下发现四个调试器程序,分别是:cdb.exe.ntsd. ...

  4. WinDbg调试命令汇总

    一. 1. !address eax 查看对应内存页的属性 2. vertarget 显示当前进程的大致信息 3 !peb 显示process Environment Block 4. lmvm 可以 ...

  5. Windbg调试命令详解(1)

    转载注明>> [作者:张佩][镜像:http://www.yiiyee.cn/Blog] 1. 概述 用户成功安装微软Windows调试工具集后,能够在安装目录下发现四个调试器程序,分别是 ...

  6. GDB调试命令小结

    1.启动调试 前置条件:编译生成执行码时带上 -g,如果使用Makefile,通过给CFLAGS指定-g选项,否则调试时没有符号信息.gdb program //最常用的用gdb启动程序,开始调试的方 ...

  7. jdb调试命令

    常用调试命令: run GeoHashTest #带参数运行 stop at GeoHashTest:22 #断点GeoHashTest文件的22行 stop in GeoHashEncode.Enc ...

  8. 基础调试命令 - .dump/.dumpcap/.writemem/!runaway

    Windbg是windows平台上强大的调试器,它相对于其他常见的IDE集成的调试器有几个重要的优势, Windbg可以做内核态调试 Windbg可以脱离源代码进行调试 Windbg可以用来分析dum ...

  9. Windbg调试命令详解(3)

    3 进程与线程 既可以显示进程和线程列表,又可以显示指定进程或线程的详细信息.调试命令可以提供比taskmgr更详尽的进程资料,在调试过程中不可或缺. 3.1 进程命令 进程命令包括这些内容:显示进程 ...

随机推荐

  1. EditTex属性

    <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"     xmlns:tool ...

  2. IOS上怎样画出1像素的线

    #define SINGLE_LINE_WIDTH (/[UIScreen mainScreen].scale) #define SINGLE_LINE_ADJUST_OFFSET ((/[UIScr ...

  3. ACdream 1135(MST-最小生成树边上2个值,维护第一个最小的前提下让还有一个最小)

    F - MST Time Limit: 2000/1000MS (Java/Others) Memory Limit: 128000/64000KB (Java/Others) SubmitStatu ...

  4. window应用移植到Linux下(应用移植)

     配置QT的环境变量,这台电脑à属性à高级系统设置à高级à环境变量à系统变量àpathàC:\Qt\Qt5.3.0\5.3\mingw482_32\bin;C:\Qt\Qt5.3.0\Tools\ ...

  5. 在gem5的full system下运行 alpha编译的测试程序 running gem5 on ubuntu in full system mode in alpha

    背景 先需要在full system下运行gem5,通过网上查找资料以及向别人请教,终于成功运行,网上大多是关于alpha指令集的,且都是英文的,为了方便大家学习,现在总结一下,希望对大家有所帮助. ...

  6. 百度地图API相关点

    百度API接口:http://developer.baidu.com/map/jsdemo.htm#a1_1 百度地图API具体解释之地图标注:http://www.cnblogs.com/jz110 ...

  7. dell服务器各类raid 和磁盘在阵列卡上的实验

    听很多人说,做好阵列的硬盘从阵列上移除后,重新从硬盘导入阵列信息的时候不能打乱位置,昨天用两台Dell R710,四块sas 300G HP硬盘做实验,实验步骤如下: 一.dell R710首先用三块 ...

  8. hdu1042(大数模板)

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1042 在网上找了个大数模板方便以后用得到. #include<iostream> #inc ...

  9. hdu4004(二分)

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=4004 大致题意 二分最大跳跃能力,判断是否可以在m次内到达对岸! 分析:由于求青蛙最小弹跳能力,所以二 ...

  10. android获取文件getMimeType的两种方法

    方法1: import java.util.Locale; private static String getSuffix(File file) { if (file == null || !file ...