Shim a missing libc header on Alpine

In an elixir:*-alpine image, mix deps.compile failed on a native dependency (picosat_elixir, the SAT-solver NIF that Ash uses for policies):

c_src/picosat.c:8150:10: fatal error: sys/unistd.h: No such file or directory

<sys/unistd.h> is a glibc quirk. All it does is include <unistd.h>. The latter is the POSIX header, so it’s the only one that musl provides.

There’s no need to fork picosat_elixir to fix this. I just added the same forwarding header to the image:

Dockerfile
RUN echo "#include <unistd.h>" > /usr/include/sys/unistd.h

The trick works for other missing glibc forwarding headers too, as long as musl has the header they forward to.

Other options:

  • Use Debian. Phoenix’s own generated Dockerfile already does.
  • For Ash specifically, replace {:picosat_elixir, "~> 0.2"} with the pure-Elixir {:simple_sat, "~> 0.1"}. It’s a bit slower but avoids NIF-compilation issues entirely.
← All notes