我目前正在学习Linux操作系统下的C语言信号. 我有一个父进程,它希望将一个名为struct Data的整值 struct 发送到它Forking 的子进程-使用siginfo_t struct ,当我们使用sigcation定义信号处理程序时,它是信号处理程序的参数:void handler(int, siginfo_t*, void*)

父进程定义union sigval,并将联合中的sival_ptr字段设置为 (void*) data,其中数据是包含两个整数的struct Data. 然后家长使用sigqueue(child_pid, SIGUSR1, my_sigval)

子进程使用我前面提到的sigaction,并且它使用标志SA_SIGINFO为SIGUSR 1信号设置信号处理程序.

在子代码的信号处理程序内部,我定义了指针struct Data* data 并做这行:data = (struct Data*) (si->si_value.sival_ptr) 然后我try 打印我从父母发送的数据.

我得到的行为是,子进程在打印struct Data data内的值之前退出,并且该行之前的所有内容都会按照预期执行并打印在屏幕上.

我哪里做错了?我是否没有正确地从家长那里传递指针到struct Data

或者我在子信号处理器功能内的铸造过程中做错了什么?

以下是代码:

父母 :


#include <stdio.h>
#include <signal.h>
#include <unistd.h>
#include <stdlib.h>
#include <sys/wait.h>

#define MY_SIGNAL SIGUSR1

// Define a structure to hold two integers
struct Data {
    int value1;
    int value2;
};

int main() {
    // Prepare data structure
    struct Data* data = (struct Data*) malloc(sizeof(struct Data));
    data->value1 = 10;
    data->value2 = 20;

    // Fork a child process
    pid_t pid = fork();

    if (pid == -1) {
        perror("fork failed");
        return 1;
    } else if (pid == 0) { // Child process
        // Child process logic
        execlp("./c2","c2",  NULL);
                  //
    } else { // Parent process
        // Sending the signal with a pointer to the data structure
        union sigval value;
        value.sival_ptr = (void*) data;
//        value.sival_int = 7;
        sleep(1);
        sigqueue(pid, MY_SIGNAL, value);
        sleep(1);
    }

    wait(NULL);
    return 0;
}

子元素:

#include <stdio.h>
#include <signal.h>
#include <unistd.h>
#include <stdlib.h>
#include <string.h>

#define MY_SIGNAL SIGUSR1

// Define a structure to hold two integers
struct Data {
    int value1;
    int value2;
};

// Function to handle the signal
void handler(int sig, siginfo_t *si, void *unused) {
    printf("Received signal: %d\n", sig);
//    printf("Received signal value: %d\n", si->si_value.sival_int);
    struct Data* data;
    data = (struct Data*)(si->si_value.sival_ptr);
    printf("Received values: %d, %d\n", data->value1, data->value2);
    // Copy the received data into the allocated memory
}

int main() {
    // Set up signal handler
    struct sigaction sa;
    sa.sa_sigaction = handler;
    sa.sa_flags = SA_SIGINFO;
    sigemptyset(&sa.sa_mask);
    sigaction(MY_SIGNAL, &sa, NULL);

    
    pause();

    return 0;
}

推荐答案

您的计划不可能起作用,因为指针仅在进程中有效,因 for each 进程都有自己的地址空间.

即使您的内存在两个进程之间共享,也可能无法在两个进程中的同一地址找到该块.


由于这里存在父子关系,因此您可以在Forking 之前设置一些共享内存,并使用该内存来交换数据.确保一个进程不能在读取的同时写入内存,反之亦然.

C++相关问答推荐

C指针地址和转换

编译SDL 2时缺少SDL_ttf

手动矢量化性能差异较大

如果包含路径不存在,我的编译器可以被配置为出错吗?(GCC、MSVC)

ARM64 ASIMD固有的加载uint8_t* 到uint16x8(x3)?

我无法让LLDB正确运行我的可执行文件

如何在C中通过套接字自定义数据类型读取原始变量?

C语言编译阶段与翻译阶段的关系

`#if`条件中是否允许`sizeof`?

Clang警告称,`ffi_type`与`sizeof`不兼容

从uint8_t*转换为char*可接受

为什么我从CSV文件中进行排序和搜索的代码没有显示数据的所有结果?

在C语言中,指针指向一个数组

不同原型的危险C函数是可能的

如何确保我将使用C标准库函数的函数版本,如&getc";,而不是类似函数的宏版本?

表达式x&;&;(~x)应该返回1还是0?它依赖于编译器吗?

为什么会出现此错误?二进制表达式的操作数无效

即使客户端不发送数据,也会发生UNIX套接字读取

一元运算符

C/C++编译器可以在编译过程中通过按引用传递来优化按值传递吗?