那些编译器和操作系统(os)钟情的填充字节——0xCD/0XDD/0XFD

来源:互联网 发布:算法导论视频 百度云 编辑:程序博客网 时间:2024/05/21 16:55

在利用VS提供的反汇编IDE工具查看内存内容的时候,常常会看到一些似曾相识但却无法知道其出处的内容。下面是我从一个MSDN下面的论坛上看到的一片文章,希望通过此篇文章能够解开大家的疑惑,今后对那些似曾相识的内存内容有所了解,并渐渐的开始喜欢上他们。

 

Value     Name           Description  
------   --------        ------------------------- 
0xCD     Clean Memory    Allocated memory via malloc or new but never  
                                              written by the application.  (注释:编译器新开辟的堆(heapk)空间,即使用new运算符的结果)。
 
0xDD     Dead Memory     Memory that has been released with delete or free.  
                                              Used to detect writing through dangling pointers.  
                                             (注释:已收回的堆(heap)空间,即利用delete操作符的结果) 

0xFD     Fence Memory    Also known as "no mans land." This is used to wrap  
                                              the allocated memory (surrounding it with a fence)  
                                             and is used to detect indexing arrays out of  
                                              bounds or other accesses (especially writes) past 
                                              the end (or start) of an allocated block. 
                                           (注释:可以理解为隔离(栅栏字节)字节,主要出现在分配的各个堆栈空间之间,用来隔离作用的,例如可以识别数组的下标是否越界。)

0xCC                                  When the code is compiled with the /GZ option, 
                                               uninitialized variables are automatically assigned  
                                                to this value (at byte level).  
                                            (注释:在编译器选择/GZ选项HOU ,未初始化的变量都用此内容填充,0xCC同时也是INT 3软中断的机器码,如果在程序中使用了未初始化的内存空间,就会触发相应的软中断,终止程序运行)。
 
// the following magic values are done by the OS, not the C runtime: 
 
0xAB                   (Allocated Block?)            Memory allocated by LocalAlloc().  
 
0xBAADF00D   Bad Food                            Memory allocated by LocalAlloc() with LMEM_FIXED,but  
                                                                         not yet written to.  
 
0xFEEEFEEE                                                OS fill heap memory, which was marked for usage,  
                                                                          but wasn't allocated by HeapAlloc() or LocalAlloc().  
                                                                         Or that memory just has been freed by HeapFree(). 
下面就让我们利用VS2008中自带的IDE反汇编工具,来真实体验一下编译器和操作系统填充的字节内容。

让我们新建一个工程文件,例如命名为PaddingByte.cpp,代码如下:

#include "stdafx.h"


int _tmain(int argc, _TCHAR* argv[])
{
 int notInit;
 int isInit=100;
 
 char *pNChar;
 char *pChar=NULL;
 
int* pArr=new int[4];
 delete []pArr;

 

 return 0;
}

调试截图:

未初始化的两个变量:notInit为整型,占用4字节,pArr指针类型,占用4字节,其各自的地址如下:

各自的内存内容如下:

接下来看pArr指针,指向new操作符动态分配的4元素的整型数组。(此块内存在堆中分配)

看一下刚开始pArr的地址,和其内存中的内容:

0x003984b8是堆中的空间,其内容如下:

可以看到new申请的堆空间,初始化时CD字节填充,并且在分配空间的前后各有4字节的fd隔离字节。

进行了delete操作后,变化如下:

这个就是最后的有操作系统OS来填充的0xfeeefeee字节。

详细的内容可参见:《Debugging Windows Programs》一书。

原创粉丝点击