下面的内容在崩溃时崩溃:(有使用void *的理由)。
bool s = true;
void* arg = &s;
argument = malloc(sizeof(arg));
memcpy(argument,arg,sizeof(arg));
free(argument);
这里的参数是一个空白*
为什么免费崩溃应用程序?
由于
答案 0 :(得分:8)
你的问题最有可能发生在其他地方。
由于您对sizeof (pointer)
有一些误解我怀疑您的程序中的其他位置存在缓冲区溢出/下溢导致堆头损坏,然后free
在尝试迭代时崩溃腐败的堆。
当其他人指出你从一个只有sizeof (void*)
的变量中读取sizeof (bool)
时,其他人都是正确的,但由于它在堆栈上,因此s
以外的内存几乎可以肯定有效(它可能包含其他局部变量,函数参数或返回地址,如果无意中读取它们,则不会导致程序崩溃)。
memcpy
可以很好地读取未对齐的数据,因此即使您在未对齐访问时崩溃的架构上,这也不是问题。
检查其他动态分配的缓冲区是否溢出。
编辑:我也想回应米洛对一个现已删除的问题的评论:我需要获得可以分配的任何类型的对象 - Milo
C ++无法正常工作。 malloc
只能为POD类型分配内存,这些内存必须满足一些非常强大的限制。完全没有符合标准的方法来克隆完全任意类型的实例。
在某些类型上可靠运行的一些方法是:
Clone
功能,请多态调用Clone
new char[]
和memcpy
答案 1 :(得分:2)
arg指向一个bool,你要记住它的4个字节!这就是崩溃的原因。布尔只有一个字节。
答案 2 :(得分:2)
#include <string>
int main(void)
{
void* argument;
bool s = true;
void* arg = &s;
argument = malloc(sizeof(arg));
memcpy(argument,arg,sizeof(arg));
free(argument);
return 0;
}
此代码在VS 2010中不会崩溃。事实上,就内存管理而言,此代码没有任何违法行为。但是,它没有按预期运行,因为它复制了垃圾。假设有32位环境,则分配4个字节并将“argument”设置为指向这4个字节。然后,您将从“arg”指向的内存中复制4个字节到“参数”指向的4个字节。是的,arg指向的4个字节中有3个是垃圾,但它们就在那里。编译器将在堆栈上为bool s分配4个字节,而不是1.堆栈需要以4个字节的块分配。所以内存就在那里,虽然有3个字节里面有垃圾。
我怀疑你的其他地方有一个损坏的堆,并且由于这个原因,对free的调用恰好在这里崩溃。
答案 3 :(得分:0)
您确定free()
崩溃了吗?看起来更有可能是memcpy()
电话。你是盲目地复制X字节,其中X是指针的大小,从arg
到argument
。但是你不知道arg
指向的数据大小是什么。
答案 4 :(得分:0)
根据您的评论判断,您认为sizeof(arg)
正在返回arg
指向的实际大小。这是错的。它返回void*
指针的大小。
您的memcpy
正在从源的有效端之外复制数据,但这极不可能导致崩溃。
如果free
在为其指定有效指针时崩溃,则表示已删除堆。由于示例中没有代码表明会使指针无效或者使堆丢弃,因此在得到此代码之前,我必须在其他地方得出结论。