首页 > 解决方案 > C++ 程序错误:malloc():内存损坏

问题描述

C++ 新手,一直在编写 C++ 程序,但它最终在从 ctime 调用 lib 函数调用时中断。

错误显示如下信息:
malloc(): memory corruption

AFAIK,此错误(内存损坏)应该是由于对越界内存地址进行操作而导致的。并且打印格式代表YYYY-MM-DD-HH-MM,这里列出,表示长度肯定小于100。

附加信息:
- 程序使用标志编译:“-O3 -g -Wall -Wextra -Werror -std=c++17”
- 编译器:g++ 7.4.0
- 系统:WSL Ubuntu-18

注意:此代码不能编译,也不能重现问题,请参阅下面的更新

/** class file **/
#include <sys/wait.h>
#include <sys/types.h>  
#include <unistd.h>
#include <errno.h>
#include <cstdlib>
#include <iostream>
#include <sstream>
#include <string>
#include <ios>
#include <fcntl.h>
#include <algorithm>
#include <cctype>
#include <ctime>
#include <limits>
#include "cache-proxy.hpp"

static int PROXY_CONFIG = 0;

void get_timestamp(char *buffer, int len);
std::string get_cwd(void);

CacheProxy::CacheProxy(__attribute__((unused)) const std::string& node)
{ 
    curr_dir = fs::get_cwd();
    Logger::get().info("curr_dir " + curr_dir);
    proxy_path = "/usr/sbin/squid";
    std::string squid("squid");

    char buff[200];
    get_timestamp(buff, 200);    // error pops
    std::string proxy_config_path;

    /** plenty of codes following, but commented**/
}

void ~CacheProxy(){}

void get_timestamp(char *buffer, int len)
{
    time_t raw_time;
    struct tm *time_info;
    time(&raw_time);
    time_info = std::localtime(&raw_time);
    std::strftime(buffer, len, "%F-%H-%M", time_info);
    return;
}

// originally from other files, for convenient to be moved into this file 
std::string get_cwd(void)
{
    char path[PATH_MAX];
    std::string retval;
    if (getcwd(path, sizeof(path)) != NULL) {
        retval = std::string(path);
    } else {
        Logger::get().err("current_path", errno);
    }
    return retval;
}


/** header file **/ 
#pragma once
#include <string>

class CacheProxy:
{
private:
    int server_pid;
    std::string proxy_path;
    std::string curr_dir;
    std::string squid_pid_path;
    ;

public:
    CacheProxy(const std::string&);
    ~CacheProxy() override;

};

/** main file **/
int main(){
    Node node(); // the parameter is never used in the CacheProxy constructor though
    CacheProxy proxy(node); // error pops
    proxy.init();
}

感谢您的任何建议或想法。


更新:
代码更新如上,有三个主要文件。该代码通过省略不相关的代码(我在遇到错误时将它们注释掉)显示了与我原始代码库的逻辑完全相同的序列,但请原谅我给出如此粗略的代码。

基本上,在对象初始化期间会弹出错误,我目前认为问题出在 get_cwd 或本地时间。

请指出您是否需要更多信息,尽管我认为其他代码确实不相关。


12 月 21 日更新:
在注释掉原始代码的不同部分后,我设法找到了错误部分,但无法修复错误。评论中的意见确实是真的,内存损坏错误应该事先来自某个地方,但是,我要解决这个问题的方法与其他答案有些不同,因为我在我的程序中使用了 setcap 并且在这种情况下不能使用 valgrind .

我使用了另一个名为 ASan( Address Sanitizer ) 的工具来进行内存检查。使用该工具很容易找出内存损坏的根源,并且在运行时发生错误时具有全面的分析。我在编译器中添加了支持,发现我的主要问题是 CacheProxy 类中字符串变量的内存分配。

到目前为止,已经证明是另一个问题,即“为什么在调用此类的构造函数时为字符串对象分配内存会导致间接内存泄漏”,我不会在此问题中折叠。

但对我来说确实是一个很好的教训,内存问题实际上有各种类型和原因,你不能盯着源代码来解决不是“索引越界”或“非法地址访问”(segfault)问题的问题。许多工具非常方便并且专门用于处理这些事情,所以去拿你的工具吧。

标签: c++memory-managementctimememory-corruption

解决方案


malloc 或 free 内的任何崩溃都可能是早期堆损坏的原因。

您的内存可能较早损坏。

如果您使用的是 Linux,请尝试在 valgrind 下运行您的程序。Valgrind 可以帮助你找出这种错误。


推荐阅读