Introduce a memory safe compilation mode inspired by Fil-C

mpweiher1 pts0 comments

#36237 - introduce an actually memory safe (unlike Rust) compilation mode inspired by Fil-C - ziglang/zig - Codeberg.org

This website requires JavaScript.

ziglang/zig

Watch

270

Star

6.1k

Fork

800

Code

Issues

734

Pull requests

317

Activity

Actions

19

introduce an actually memory safe (unlike Rust) compilation mode inspired by Fil-C #36237

New issue

Open

opened 2026-07-20 04:58:59 +02:00 by andrewrk

3 comments

andrewrk

commented 2026-07-20 04:58:59 +02:00

Owner

Copy link

Based on prior art: Fil-C

Currently Zig has:

pub const Optimize = enum {<br>/// Safety checks enabled. Optimize for bug detection, accurate debug info,<br>/// and compilation speed (in that order).<br>debug,<br>/// Safety checks enabled. Optimize for runtime performance.<br>safe,<br>/// Safety checks disabled. Optimize for runtime performance.<br>fast,<br>/// Safety checks disabled. Optimize for machine code size, then performance.<br>small,<br>};<br>This proposal is to keep the existing optimization modes , while introducing an additional ABI ("fil") alongside musl, gnu, msvc, etc.

Related: RFC/Proposal: Turning Zig target triples into quadruples

TODO: contact Fil and ask if he wants make Fil-C ABI stable, versioned, or otherwise. Zig project would prefer to adhere to a standard, if possible.

This ABI has limitations:

incompatible with the other ABIs. All objects must be compiled with fil ABI or linking cannot succeed. Zig linkers must identify incompatible objects and refuse to link.

mainly it is expected to combine this ABI with Optimize.safe or Optimize.debug. However, the other modes can also work, but for example invisicaps would still be implemented (i.e. runtime pointer provenance checks) because that is needed by the ABI.

currently it is only defined for x86_64-linux, however, support for other targets could be expanded over time.

When using this ABI, Zig compiler would implement the same techniques from the Fil-C project. That is, invisicaps combined with a tight coupling with the target OS in order to wrap all syscalls. No dependency on the Fil-C project; an alternative implementation.

One opportunity to diverge here is garbage collection. Fil pointed out to me that GC (see FUGC) is just one way to implement this technique. Another one would be automatic insertion of unique type ids into invisicaps metadata, ensuring that if UAF does occur, type confusion is still prevented. Unique type IDs are already a necessary ingredient for the accepted proposal add safety checks for pointer casting.

The main challenge to solve is that Zig needs to intercept all syscalls (and in fact all inline assembly), just like Fil-C currently does today. Allocator interface is OK, but mmap has to be replaced with wrapper code. I don't think this requires any language changes however. I think it can be done via compiler and standard library changes alone.

By doing this, Zig can offer its users an option to compile their projects, including entire tree of C/C++ dependencies, into an executable that is fully memory safe, with no escape hatch , at a ~1-6x performance penalty (depending on prevalence of pointer chasing).

Once this is implemented then, in a twist of fate, Zig will become one of the only toolchains capable of producing actually memory safe executables, especially when you consider that real world applications tend to have C/C++ dependencies and, in the case of Rust, additional use of unsafe beyond FFI.

Based on prior art: [Fil-C](https://fil-c.org/)

Currently Zig has:

```zig<br>pub const Optimize = enum {<br>/// Safety checks enabled. Optimize for bug detection, accurate debug info,<br>/// and compilation speed (in that order).<br>debug,<br>/// Safety checks enabled. Optimize for runtime performance.<br>safe,<br>/// Safety checks disabled. Optimize for runtime performance.<br>fast,<br>/// Safety checks disabled. Optimize for machine code size, then performance.<br>small,<br>};<br>```

This proposal is to **keep the existing optimization modes**, while introducing an additional ABI ("fil") alongside musl, gnu, msvc, etc.

Related: [RFC/Proposal: Turning Zig target triples into quadruples](https://github.com/ziglang/zig/issues/20690)

TODO: contact Fil and ask if he wants make Fil-C ABI stable, versioned, or otherwise. Zig project would prefer to adhere to a standard, if possible.

This ABI has limitations:<br>- incompatible with the other ABIs. All objects must be compiled with fil ABI or linking cannot succeed. Zig linkers must identify incompatible objects and refuse to link.<br>- mainly it is expected to combine this ABI with `Optimize.safe` or `Optimize.debug`. However, the other modes can also work, but for example invisicaps would still be implemented (i.e. runtime pointer provenance checks) because that is needed by the ABI.<br>- currently it is only defined for x86_64-linux, however, support for other targets could be expanded over time.

When using this ABI, Zig compiler would implement the same techniques from the Fil-C project. That is,...

optimize checks safe safety performance debug

Related Articles