共享内存指针分段错误

Ser*_*yan 7 c++ shared-memory

嘿我正在尝试在两个进程之间创建一个共享对象.并尝试读取和更改每个进程中的值.这是我的简单结构.

编辑:我在我的结构中添加了一个构造函数.

struct shared{
    shared(){
        value = 10;
        name = "AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA";
    }
    int value;
    string name;
};
Run Code Online (Sandbox Code Playgroud)

我试过在调用fork()之前和之后调用shmat()但是没有任何改变它仍然给出了分段错误.

编辑:并在shmat()后添加一个检查,看看它是否失败.

#include <unistd.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <iostream>
#include <sys/shm.h>
#include <string.h>

using namespace std;

struct shared{
    shared(){
        value = 10;
        name = "AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA";
    }
    int value;
    string name;
};

int main(){
    int shm_id = shmget(IPC_PRIVATE,sizeof(shared),0);

    if(shm_id == -1){
        cout<<"shmget() failed "<<endl;
        return -1;
    }
    pid_t pid = fork();
    if(pid == -1){
        cout<<"fork() failed "<<endl;
        return -2;
    }

    shared* sharedPtr = (shared*)shmat(shm_id,0,0);


    if(sharedPtr == 0){
        cout<<"shmat() failed "<<endl;
    }

    cout<<"Setting up the object: "<<endl;
    sharedPtr->value = 5;
    sharedPtr->name = "aaaaaa: ";

    if(pid == 0){       //Child process

        cout<<"Child process: "<<endl;
        sharedPtr->value = 10;
        sharedPtr->name  = "bbbbbbb: ";
        cout<<"Changed the object "<<endl;
        return 0;
    }
    if(pid != 0){ //Parent process
        sleep(1);
        cout<<"Parent process: "<<endl;
        cout<< sharedPtr->name << sharedPtr->value<<endl;

    }

    return 0;
}
Run Code Online (Sandbox Code Playgroud)

但我仍然遇到分段错误.

Fan*_*Fox 4

指针 () 的有效性检查if(sharedPtr == 0){发生在指针已在 中取消引用之后sharedPtr->value。因此,您可能会出现此行为,因为您正在取消引用空指针。在使用指针之前进行此项检查。

此外,您不能那样使用共享内存。您将获得一个静态大小的共享内存指针,它表示相当于未初始化的字符串和 int 的内存,考虑一下这一点。你基本上有这个:

int : size -> 4 bytes
empty string : size -> 32 bytes
Run Code Online (Sandbox Code Playgroud)

从这里开始取决于系统)。然后,当您执行 this(shared*)shmat(shm_id,0,0)和 this时sharedPtr->name = "aaaaaa: "string您在此结构中创建的构造函数从未被调用,因此未正确创建。当您执行此操作时,operator=您正在尝试使用任何地方都不存在的函数,因为您调用它的对象未正确构造。如果您使用原始共享内存,则需要非常小心如何使用它以及占用多少大小。您还可以考虑使用内存控制器来帮助您,例如boost::interprocess.

  • 不,当你执行“sharedPtr-&gt;name = ...”时,你已经输了,因为“name”是一个字符串,其构造函数从未运行过。这是一个无效的对象,而不是一个空字符串。 (2认同)