c++ - 在 Visual C++ 中删除调用后检测到堆损坏?

标签 c++ visual-studio-2010 visual-c++ heap-memory heap-corruption

我正在尝试运行我的 c++ 代码,引入这个新代码导致了内存损坏,任何人都可以帮助我找出造成这种情况的原因。删除电话后,我面临这个问题。我还尝试在每个 strncpy 调用之后放置 newArgs[SZ] = '\0';

错误说:

HEAP CORRUPTION DETECTED after Normal Block(#274) at 0X00C09600 etc

int main(HINSTANCE hInstance, HINSTANCE hPrevInstance, char* argc, int nShowCmd){

    MyClass *obj;
    char args[] = " hello world";
    int SZ = strlen(args);
    int argsLength = 0;

    if(argc != NULL)
        argsLength=strlen(argc);
    SZ+=argsLength;
    char *newArgs = new char[SZ];
    strncpy(newArgs, "",SZ);

    if(argc != NULL)
        strncpy(newArgs, argc,argsLength);

    StrCat(newArgs,args);

    obj = new MyClass(newArgs);
    delete[] newArgs;

    return 0; 
}

最佳答案

您正在检索 argc 的字符串长度。这没有尾随的空字节:

argsLength=strlen(argc);

稍后您将 argc 复制到您的缓冲区。但是您只复制 argsLength 字符,这是没有尾随空字节的字符串。然后 strncpy 将只复制字符串内容而不添加尾随的空字节本身(参见 man strncpy)。

strncpy(newArgs, argc,argsLength);

在 strncpy 之后,您立即将另一个字符串附加到您的 newArgs。

StrCat(newArgs,args);

根据分配后 newArgs 的内容(这可能是随机的,在调试中它可能会被特殊模式填充) (直到它找到一个空字节)并将你的字符串参数附加到那里——堆中的某个地方和你分配的内存之外。这是堆损坏。

此外:

  1. 分配内存时,尾随的空字节需要多一个字节。
  2. strncpy(..., "", SZ) 有什么用?
  3. 使用 std::string,不易出错的 C 字符串。
  4. 您正在泄漏分配的 MyClass 对象。
  5. 在 C++ 中,字符串文字是常量。

我会这样重写你的程序(没有编译和测试它):

int main(HINSTANCE hInstance, HINSTANCE hPrevInstance, char* argc, int nShowCmd)
{
    const char args[] = " hello world";
    std::string newArgs;
    if(argc != NULL)
        newArgs = argc;
    newArgs += args;

    // Use the line that you prefer
    MyClass obj1(newArgs.c_str());
    std::unique_ptr<MyClass> obj2(new MyClass(newArgs.c_str()));

    return 0; 
}

关于c++ - 在 Visual C++ 中删除调用后检测到堆损坏?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/26922163/

相关文章:

c++ - 我应该如何重载模板化结构?

c# - 在设计时在 TableLayoutPanel 中插入行

c - 在 C 中,无符号和有符号字符指针之间的转换何时变得不安全?

visual-studio-2010 - 通过 Visual Studio 2010 以 .NET Framework 4.5 为目标

c++ - Visual C++ 运行时对象销毁顺序

c++ - 如果方法的调用者不需要数据的所有权,有什么好的方法可以避免复制?

c++ - 使用混淆库时 vc++ 中的链接时间错误

c++ - 将非类型参数包分布在不同的模板参数包中

c++ - 为什么有些函数分布密集,而另一些函数则用 int 3 指令对齐和填充?

c++ - 为什么更喜欢基于模板的静态断言而不是基于 typedef 的静态断言?