无法使用在 Solaris 上运行的代码在 Linux 上从 `siginfo_t` 检索 PID

标签 c linux unix signals pid

我需要从 siginfo_t 结构中检索子进程的 PID。此代码适用于 Solaris:

siginfo_t *info; 
//
// siginfo is initialized with proper data here
//
pid = info->__data.__proc.__pid;

但是当我尝试将代码移植到 Linux 时,出现编译错误:

error: ‘siginfo_t’ has no member named ‘__data’
pid = info->__data.__proc.__pid;

这是 Solaris 上 siginfo_t 的定义(来自 signal.h):

typedef struct {
    int             si_signo;
    int             si_code;
    int             si_errno;
    union {
        int             __pad[7];
        struct {
            pid_t           __pid;
            union {
                struct {
                    uid_t           __uid;
                    union sigval    __value;
                } __kill;     /* si_code <= 0 SI_FROMUSER */
                struct {
                    _CSTD clock_t   __utime;
                    int             __status; /* CLD_EXITED status, else signo */
                    _CSTD clock_t   __stime;
                } __chld; /* si_signo=SIGCHLD si_code=CLD_* */
            } __pdata;
        } __proc;
        struct {
            int             __fltno;
            void            *__fltip;   
            void            *__addr;    
            int             __bdslot;
        } __fault;                /* si_signo=SIGSEGV,ILL,FPE,TRAP,BUS */
    } __data;
} siginfo_t;

但是,Linux signal.h 有完全不同的定义。我不明白如何编写使用 siginfo_t 但同时适用于 Linux 和 Solaris 的代码,请解释一下。

最佳答案

The official specification of siginfo_t (您必须搜索“siginfo_t”,抱歉,没有片段 anchor )没有显示您引用的任何结构。这是一个内部实现细节,您不应该直接使用。

(根据一般经验,您不应该在名称以两个下划线开头的系统 header 中直接使用任何内容。)

更改您的代码以读取

pid = info->si_pid;

并且它可以在 Solaris 和 Linux 上正常工作。如果您还没有,添加其中一个也是一个好主意

#define _POSIX_C_SOURCE 200809L

#define _XOPEN_SOURCE 700

到每个源文件的最顶部(它需要位于所有 #include 之前,否则将不起作用)(选择其中一个,而不是两者,具体取决于您是否需要 XSI 功能)。当前版本的 Solaris 和 Linux 默认为(大约)此模式,但显式激活它可以防止出现意外,尤其是对于较旧的系统。

对于siginfo_t中的所有其他有用字段,还有以si_开头的其他名称;我链接到的规范列出了普遍可用的规范。如果您需要使用特定于操作系统的字段,请在您找到 siginfo_t 的同一 header 中查找表单的 #define

#define si_pid    __data.__proc.__pid

并使用si_名称。

关于无法使用在 Solaris 上运行的代码在 Linux 上从 `siginfo_t` 检索 PID,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41937595/

相关文章:

c - 第三个函数不会运行 scanf

c - 使用 strcpy 从整数生成指针,无需进行强制转换

c - 简单 OpenGL 应用程序中的 “Access violation reading location 0x000000000”

java - 将 jar 部署到 unix 服务器

python - 在 UNIX 上执行 Python 代码

c++ - 对 __cdecl 和 __stdcall 调用约定感到困惑

python - Ansible,检查库存组和主机

c++ - 指针如何引用硬盘中的一个段

计算 C 程序中耗时(以毫秒为单位)

linux - Bash 脚本 Unix。模式匹配