Files
nulsl-libc/CONTRIBUTING.md
huntedbytheirsandSisyphus 5487bbc808 Add documentation
README introduces the project and build workflow; CONTRIBUTING covers the stub convention and syscall wrapper process; docs/ explains the architecture and the kernel ABI surface.

Ultraworked with [Sisyphus](https://github.com/code-yeongyu/oh-my-openagent)

Co-authored-by: Sisyphus <[email protected]>
2026-08-30 04:09:49 -04:00

2.8 KiB

Contributing to nulsl-libc

Thank you for helping Null Linux get a libc that fits in /dev/null.

Ground rules

  1. C17, and only C17. No GNU-isms in the language you write (inline asm stays in the arch files where it belongs). The build forces -std=c17 -ffreestanding -fno-builtin; make sure your code compiles clean under -Wall -Wextra -Wshadow -Wpointer-arith.
  2. Stay lean. Null Linux runs a GUI in 32 MB. If a change adds RAM per process, it needs a better justification than convenience.
  3. AI drafts, humans ship. AI-generated code is welcome as a draft, but it must be reviewed, understood, and improved by a human before it lands. If you cannot explain every line, do not open the PR.
  4. The kernel is the API. Prefer a raw syscall wrapper over inventing library machinery. syscall() is the only ABI surface — keep it that way (see docs/syscalls.md).

Structure

  • include/ — public headers. Declarations only; the struct nulsl_file layout and friends stay private in src/internal.h.
  • src/ — implementations. One file per header/domain; keep files small (a #include short of 250 lines is a good ceiling).
  • src/crt/crt0.S — the entry point. Kept out of libc.a on purpose.
  • tests/ — anything you add must be exercised (make check).
  • benchmarks/ — anything performance-relevant needs a benchmark (make bench); if it isn't memory-lean, it doesn't ship.

The stub convention

Not implemented yet? It still needs its standard signature in the public header, a documented error return, errno = ENOSYS, and a /* TODO */ comment naming what it needs. That is a feature, not a placeholder: every stub fails loudly instead of silently misbehaving.

Adding a syscall wrapper

  1. Number in include/sys/syscall.h (guarded, ABI in comment).
  2. Declaration in the right public header.
  3. Thin wrapper in the right src/ file — one syscall() call, nothing else. If it needs to be a stub, follow the stub convention.
  4. Update docs/syscalls.md (the table).
  5. Extend a test in tests/.

Workflow

./autogen.sh
make release && make check && make bench
make debug        # for actual debugging (bin/debug/, -O0 -g)
  • Style: clang-format -i on your diff (see .clang-format); keep diffs formatted, small, and single-purpose.
  • LSP: make compile_commands (needs bear) for clangd.
  • Verify: make check must pass; run make bench before and after to show you did not make anything slower.
  • Commits: small, atomic, descriptive. This project is written by humans and reviewed by humans; keep the history reviewable.
  • PRs: one idea per PR, with tests. If the change is a stub → real transition, say which roadmap item it completes.

Communication

Open an issue or a PR on https://git.spectoria.dev/The-Null-Linux-Project/nulsl-libc.