2014-02-24 48 views
0

嗨我正在开发一个项目,我需要将文件打包到PFS映像中。我正在使用ANSI C语言编写一个应用程序。我得到每个文件Hexdump和其他属性并存储内部变量。C内存分配错误

一旦收集到关于被打包文件的所有信息,我需要为每个文件的信息创建一个输出文件。

由于我这样做,我有内存分配问题。输出错误的代码如下。

for (Counter = 0; Counter < PackingCount; Counter ++) 
{ 
    PFSEntry Packed; 

    Packed.HexEquivalent = DumpHex(FileNames[Counter]); 

    strncpy(Packed.Filename, FileNames[Counter], NAME_BLOCK); 

    Packed.Offset = OffsetCounter; 

    OffsetCounter += FileSize; 

    Packed.FileSize = FileSize; 

    Packed.Timestamp = 2999606509; // For the Sake of Diffing 

    Packer[Counter] = Packed; 


} 

其上面的环填充的结构如下所示

typedef struct 
{ 
char Filename [NAME_BLOCK]; 
u_int32_t Timestamp; 
u_int32_t Offset; 
u_int32_t FileSize; 
char * HexEquivalent; 
} PFSEntry; 

和DumpHex功能如下:

char * DumpHex(char * FileName) 
{ 
    FILE * File = FileOpener(FileName, "rb"); 

    printf("%s is of Size %ld\r\n\r\n", FileName, FileSize); 

    fseek(File, 0L, SEEK_END); 

    FileSize = ftell(File); 

    fseek(File, 0L, SEEK_SET); 

    char * HexArray = malloc(FileSize); 

    unsigned char Character; 

    int Counter = 0; 

    while (Counter < FileSize) 
    { 
     Character = fgetc(File);  
     sprintf(HexArray + Counter, "%c", Character);  
     Counter++; 
    } 

    return HexArray; 
} 

的作用DumpHex,它返回的十六进制输出给定文件正在输出以下错误。

的a.out:malloc.c:2369:SYSMALLOC:断言`(old_top ==(((mbinptr) (((字符*)&((AV) - >仓[((1) - 1)* 2]))__builtin_offsetof(struct malloc_chunk,fd))))& & old_size == 0)|| ((无符号长)(old_size)

=(无符号长整数)((((__ builtin_offsetof(结构个malloc_chunk,fd_nextsize))+((2 *(的sizeof(为size_t))) - 1))&〜( (2 *(的sizeof(为size_t))) - 1)))& &((old_top) - >大小为0x1 &)& &((无符号长整数)OLD_END & pagemask)== 0)”失败。中止(核心转储)

下面是添加到可以在发现解决方案帮助应用程序的一些调试信息。

Total Files to Pack 38 
Size of Packed Structure 80 
Packing File 0 of size 9319 Bytes 
Packing File 1 of size 1459 Bytes 
Packing File 2 of size 844 Bytes 
Packing File 3 of size 4396 Bytes 
Packing File 4 of size 270250 Bytes 
Packing File 5 of size 656800 Bytes 
Packing File 6 of size 0 Bytes 
Packing File 7 of size 322744 Bytes 
Packing File 8 of size 1278114 Bytes 
Packing File 9 of size 12473 Bytes 
Packing File 10 of size 13791 Bytes 
Packing File 11 of size 14158899 Bytes 
Packing File 12 of size 343051 Bytes 
Packing File 13 of size 599051 Bytes 
Packing File 14 of size 505867 Bytes 
Packing File 15 of size 10138349 Bytes 
Packing File 16 of size 17481 Bytes 
Packing File 17 of size 4900 Bytes 
Packing File 18 of size 9000 Bytes 
Packing File 19 of size 343 Bytes 
Packing File 20 of size 6888 Bytes 
Packing File 21 of size 13992 Bytes 
Packing File 22 of size 916222 Bytes 
Packing File 23 of size 2048 Bytes 
Packing File 24 of size 7776 Bytes 
Packing File 25 of size 13884 Bytes 
Packing File 26 of size 10787 Bytes 
Packing File 27 of size 12747 Bytes 

a.out: malloc.c:2369: sysmalloc: Assertion `(old_top == (((mbinptr) (((char *) 
&((av)->bins[((1) - 1) * 2])) - __builtin_offsetof (struct malloc_chunk, fd)))) && 
old_size == 0) || ((unsigned long) (old_size) >= (unsigned long)((((__builtin_offsetof 
(struct malloc_chunk, fd_nextsize))+((2 * (sizeof(size_t))) - 1)) & ~((2 * 
(sizeof(size_t))) - 1))) && ((old_top)->size & 0x1) && ((unsigned long)old_end & 
pagemask) == 0)' failed. 

中止(核心转储)

我是新来的语言,我不太了解内存的分配和自由法的概念。

+0

什么是“PFSEntry”?什么类型是'PFSEntry.Filename'? (顺便说一句,很抱歉听说你的不幸同化。) –

+0

PFSEntry.Filename是一个字符文件名,发贴 – Andrew

+0

'Packed.HexEquivalent = DumpHex(FileNames [Counter]);'听起来很危险,因为'HexEquivalent'是一个指针。 'DumpHex'是否动态分配内存?或者它是否返回一个指向局部变量的指针?或者到一个静态缓冲区?或者......嗯,也许你应该展示它。你的问题到底是什么? “我在内存分配方面遇到问题”究竟意味着什么? –

回答

1

从这里显示的代码,并给出错误,它看起来像你有一个越界数组访问的地方是破坏malloc自己的数据结构。

它与一些文件一起工作的事实纯属运气,这就是未定义行为的问题 - 行为像预期的那样是一种未定义行为的形式,这使得像这样的错误难以跟踪。

从我所看到的,这是错误的:

while (Counter < FileSize) 
    { 
     Character = fgetc(File);  
     sprintf(HexArray + Counter, "%c", Character);  
     Counter++; 
    } 

HexArrayFileSize字节动态分配的数组。但是请注意,sprintf()总是以空字节结束输出字符串。因此,对于每次迭代,HexArray[Counter]被设置为Character,并且HexArray[Counter+1]被设置为空字节。除了最后一次迭代之外,这里没有任何伤害。当CounterFileSize-1(最后一次迭代)时,sprintf()将写入空字节到HexArray[FileSize]-出界限存取。这是未定义的行为,很可能会破坏malloc数据结构,从而在程序后期产生隐蔽错误。

如果你想要做的就是写一个字符到每个位置HexArray,可以使用更有效,更不容易出错的形式:

while (Counter < FileSize) 
    { 
     Character = fgetc(File); 
     HexArray[Counter++] = Character; 
    } 

而且,由于Characterunsigned char,你应该将HexArraychar *更改为unsigned char *

想想大文件会发生什么(如果你的程序应该被这些文件调用)。内存耗尽是一个现实,特别是如果你正在开发一个嵌入式系统(这似乎是这种情况)。

+0

非常感谢。错误正是你指出的地方。那么应用程序是用每个迭代文件的空字节覆盖堆栈的权利?如果是这样,这就解释了为什么我有时会堆栈砸错误。再次感谢Filipe。 – Andrew

+0

@Andrew很高兴知道。的确,非常微妙的错误! –