Structured concurrency for processes?

This isn't really rust specific, it's just a general systems programming thing, but this forum seems like a good place for it.

I have a problem which requires several different processes to interact. As I die hard proponent of structured concurrency, I want to make sure that processes are properly linked to each other, such that, if a parent process dies, the child is terminated automatically. I want this to work even if the parent is killed abruptly (so, just child.kill(); child.wait() in Drop is not good enough for me).

My understanding is that this problem isn't solvable in the general case. While on windows a solution is possible via job objects, on Linux you can only get a one-level-deep solution via process group, and that level is already occupied by the shell (duct.py/gotchas.md at master · oconnor663/duct.py · GitHub).

However, my case is not general -- the processes are cooperative, I am the author of both the parent and the child.

So, one idea I had is to set child's stdin to a pipe, and than, in the child, treat pipe's closure as a signal that the parent is dead. I think this should cover all cases, as the OS is going to close the pipe when the parent exits, right?

Is there a better pattern here? Perhaps some blog-post surveying the design space?

2 Likes

Off the top of my head, could you maybe use dbus for this?

  1. When spawning the parent, you attribute it a unique name
  2. When spawning a child, you tell it the unique name of the parent
  3. In a thread of the child, you maintain a dbus connection to periodically poll for the unique name of the parent. If missing (parent died abruptly), you exit the child (edit: you might even be able to listen for NameOwnerChanged events, sparing you from actively polling)
  4. If the parent exits cleany, you can also use dbus to send a message asking for the child to terminate.

Rust has a dbus implementation called zbus.

2 Likes

Idea; start a supervisor process that listens on a (unix?) socket, and each child have a thread that connects to it, and then keeps the connection open (or a heartbeat, or something) and terminates when supervisor is gone. Supervisor would track workers processes and terminate when something happened.

Not that you don't have to touch useful stdio fd's. You can open any FDs (some fixed magic number should be fine) before exec-ing and the new process can use that FD.

2 Likes

Yeah, the only reason to cannibalize stdin here is to avoid writing any cross-platform code and get windows compat for free.

This topic was automatically closed 90 days after the last reply. We invite you to open a new topic if you have further questions or comments.