wfa*_*ulk 6 freebsd kill permissions signals ruby
有一个我拥有的进程,其文档声称我可以发送SIGABRT
到该进程以获取一些调试信息。但是,当我尝试发送时SIGABRT
,我得到“不允许操作”。
我还尝试向我拥有的其他进程发送相同的信号,以确保没有一些底层块阻止我SIGABRT
完全发送,但它们以适当的方式响应。这只是一个程序,但它是该程序的每个实例。进程的系统调用跟踪显示它从未收到信号。
我已经尝试/bin/kill
显式运行以排除我的 shell 的 builtin 中的任何奇怪之处kill
,并且除了一些细微的输出差异外,行为没有任何变化。
root 可以发送SIGABRT
到进程,它按我的预期工作。
我在这个游戏中已经有一段时间了,但我从未见过用户无法向他拥有的进程发送信号的情况,也没有见过用户可以发送一个信号但不是另一个。
操作系统是 FreeBSD 9.0,进程是一个 ruby 进程,它是在 Apache 下运行的 Phusion Passenger Ruby-on-Rails 应用程序的一部分。
我目前处于完全亏损状态。有谁知道发生了什么?
更新:security.bsd.conservative_signals
根据手册页,结果sysctl 被设置为 1,这阻止了许多信号被传递到 setuid 进程。将其设置为 0 可以解决问题。
虽然在进程链的某处有一个 setuid 调用——该进程是 Apache httpd 的子进程,并且 Apache 更改其 uid 以放弃 root 权限——但进程本身不是 setuid,它的 EUID、RUID 和 SVUID 都是与发送信号的用户相同。该过程的唯一检验我能找到这将表明,任何setuid的发生是P_SUGID
在标志ps
的‘标志’字段。(“自上次执行以来已设置 id 权限”)似乎不应该如此,但它是在 Apache 模块中处理的,我不知道它的确切方法。
作为记录,它是一个 ruby 进程,它作为由 mod_passenger,AKA mod_rails 处理的 Ruby on Rails 应用程序的一部分运行。
要使进程有权向 pid 指定的进程发送信号,用户必须是超级用户,或者接收进程的真实或保存的用户 ID 必须与发送进程的真实或有效用户 ID 匹配。唯一的例外是信号 SIGCONT,它可能总是被发送到与发送者具有相同会话 ID 的任何进程。另外,如果security.bsd.conservative_signals sysctl设置为1,则用户不是超级用户,接收者是set-uid,那么只能发送作业控制和终端控制信号(特别是只有SIGKILL 、SIGINT、SIGTERM、SIGALRM、SIGSTOP、SIGTTIN、SIGTTOU、SIGTSTP、SIGHUP、SIGUSR1、SIGUSR2)。
在什么意义上你拥有这个过程?与真实 uid、有效 uid、正在运行的二进制文件、该二进制文件的所有者和 setid 位等相关的进程的状态究竟是什么?