尝试异步执行带有 pkexec 的进程并得到“拒绝向死去的父母提供服务”

尝试异步执行带有 pkexec 的进程并得到“拒绝向死去的父母提供服务”

我正在尝试从使用常规权限运行的应用程序以 root 身份执行一个进程pkexec

当我pkexec同步调用时一切都很好但是当我使用以下代码异步运行它时:

    private void execute_process_async () {

        if (permission.allowed ) {
            ...

            Pid child_pid;
            var cli = "%s/my_exec".printf (Build.PKGDATADIR);
            try {

                Process.spawn_async (null,
                    {   "pkexec", cli,
                        settings.scrollbar_width.to_string (),
                        settings.scrollbar_button_radius.to_string (),
                        settings.active_tab_underline_color
                    },
                    Environ.get (),
                    SpawnFlags.SEARCH_PATH,
                    null,
                    out child_pid);
            } catch (SpawnError e) {
                report_error ("error while executing '%s'. Message: '%s'.".printf (cli, e.message)) ;
            }
        }
    }

我收到一条相当严重的错误信息:

Refusing to render service to dead parents.

你知道发生什么事了吗?

答案1

不允许pkexec通过 fork 和 exec 在后台运行,然后终止父进程。该进程将成为孤儿进程,属于init(ppid == 1)。请参阅https://lists.ubuntu.com/archives/foundations-bugs/2012-July/100103.html

您正在将应用程序的控制权交给另一个用户(通常是 root)。默认方式是以 root 身份从 shell 脚本运行应用程序pkexec。这样,父级就是 shell,而不是init

例如 GParted ( /usr/bin/gparted-pkexec) 和 GameConqueror ( /usr/bin/gameconqueror) 就是这样做的,如下所示:

  1. 创建一个 shell 脚本如下/usr/local/bin/foo.sh

    #!/bin/sh
    pkexec "/usr/sbin/foo" "$@"
    
  2. 赋予上述脚本可执行权限:

    chmod +x /usr/local/bin/foo.sh
    
  3. 如果您使用.desktop文件,请将Exec值更改为:

    Exec=/usr/local/bin/foo.sh
    
  4. 确保您的策略文件中/usr/share/polkit-1/actions/有以下条目以允许 GUI:

    <annotate key="org.freedesktop.policykit.exec.allow_gui">TRUE</annotate>
    

就是这样!

答案2

看看这个关联它对我有用。

  • 它解释了如何安装提供 pkexec 的 policykit-1。
  • 解释 gui su 快速权限提升的用法
  • Bash 别名设置,使用别名运行程序,无需输入

    pkexec application-name
    
  • 相反,它变成别名(应用程序名称):

    application-name
    

相关内容