On Sat, Jan 07, 2023 at 12:12:32AM +0000, Colin Watson wrote: > On Fri, Jan 06, 2023 at 11:55:16AM +0800, Paul Wise wrote: > > * posix_spawn: this uses the appropriate mechanisms on each platform, > > glibc might be changing this to use io_uring_spawn where possible. > > I can see a few limitations here: > > * The standard API offers no way to set the working directory of the > child process, which would be needed for pipecmd_chdir and > pipecmd_fchdir. However, glibc 2.29 added > posix_spawn_file_actions_addchdir_np and > posix_spawn_file_actions_addfchdir_np as GNU extensions. > > * I'm not totally sure how to translate pipecmd_nice into > posix_spawn-speak; the documentation is, uh, opaque. It's probably > possible. > > * This wouldn't be usable for pipeline commands created using > pipecmd_new_sequence, as posix_spawn isn't guaranteed to be > async-signal-safe so can't be called between fork and exec, unlike > fork. > > However, we could always just restrict the conditions under which > posix_spawn is used, much as GLib's g_spawn_* functions do. None of the > above features are used on mandb's hot path, for instance.
On looking at this further, there is another more serious problem with using posix_spawn, despite it looking initially appealing: pipeline_install_post_fork and pipecmd_pre_exec are used heavily by man-db, and I don't see a way to implement either using posix_spawn today. The uses of pipeline_install_post_fork are mainly cleanup handlers that could perhaps mostly be avoided (though it's not clear how libpipeline could know that). However, we use pipecmd_pre_exec to load a seccomp filter and in one case to drop privileges. Privilege-dropping could perhaps be done using the POSIX_SPAWN_RESETIDS flag instead, although we'd likely need to add some way to request that explicitly via libpipeline. But I see no way to implement loading a seccomp filter for a child process using posix_spawn. If there were some way to load a seccomp filter without needing to run extra code between (v)fork and exec, then that would probably allow solving this problem. As it stands, though, I think this means that posix_spawn can't in practice be used by man-db, and that means that I have little interest in implementing it in libpipeline. (Well, I suppose it might be possible to use a helper binary to load the seccomp filter. But I suspect that this would erase any performance gains from doing the fork-and-exec more efficiently.) A shame! -- Colin Watson (he/him) [cjwat...@debian.org]