NOTE: You can&#x27;t write an init without threads in Go, as you can in C.  (I tried awhile back)<p>At least you can&#x27;t with its portable interfaces such as exec.Command() and cmd.Wait():<p><a href="http:&#x2F;&#x2F;www.mustafaak.in&#x2F;2016&#x2F;02&#x2F;09&#x2F;forking-process-in-myinit-go.html" rel="nofollow">http:&#x2F;&#x2F;www.mustafaak.in&#x2F;2016&#x2F;02&#x2F;09&#x2F;forking-process-in-myinit...</a><p>You end burning a thread <i>per process</i>, which is pretty lame for an init.  The wait() call blocks a goroutine AND OS thread, so the go runtime will have to start a new thread for the next wait().<p>Whereas in C you can do the entire thing from a simple thread (I call it &quot;async processes&quot;).  You set SIGCHLD handler and get async exit notifications, and then process those in a single-threaded loop.  I&#x27;m pretty sure there is a problem doing this in Go (besides resorting to the syscall module)... I think it has to do with the fact that Go turns signals into messages on a channel, but I don&#x27;t remember right now...<p>EDIT: Now I remember.  The problem with using the syscall module is that Go does not export Fork and Exec.  It exports ForkExec, because it needs to ensure they run on the same thread.<p><a href="https:&#x2F;&#x2F;golang.org&#x2F;pkg&#x2F;syscall&#x2F;#ForkExec" rel="nofollow">https:&#x2F;&#x2F;golang.org&#x2F;pkg&#x2F;syscall&#x2F;#ForkExec</a><p>This severely limits the usefulness of your init program, because in Unix there are all sorts of important things that happen in between.  It&#x27;s how you set the child process state.   You basically can&#x27;t do anything with file descriptors or containers at all with this model.