Add version API, pkg-config, SPDX headers, SECURITY.md, CHANGELOG.md

Project-hygiene pass toward being a properly citable, embeddable,
professionally-packaged C library rather than just working code:

- PACKFS_VERSION_MAJOR/MINOR/PATCH/STRING in include/packfs.h, the single
  source of truth for the project's version, plus a runtime pfs_version()
  (src/vfs.c, next to vfs_new/vfs_free) so a dynamically-linked consumer
  can check ABI/API compatibility without recompiling. Covered by a new
  assertion in tests/test_mem.c that the macro and the runtime function
  never disagree.
- packfs.pc.in + a `make install` rule that generates packfs.pc with its
  Version: field derived from PACKFS_VERSION_STRING via a Makefile-level
  grep/sed, never hand-maintained separately -- verified end-to-end with a
  scratch `make install PREFIX=...` + `pkg-config --cflags --libs packfs`
  + `make uninstall`, not just by reading the rule.
- SPDX-License-Identifier: MIT added to every src/*.c and src/internal.h
  (include/packfs.h already had one); the whole distributed source tree
  now carries consistent machine-readable license metadata.
- SECURITY.md, stating precisely what this project's containment and pack-
  integrity code actually claims as a security boundary (concept.md
  Section 6/7) versus what it explicitly does not (unenforced `mode`, no
  cross-process concurrency) -- not generic boilerplate -- with a real
  reporting contact rather than a placeholder.
- CHANGELOG.md (Keep a Changelog format), summarizing the real history in
  git log to date; explicitly notes no version is tagged yet.

Verified: clean `make all` + `make test` (all 6 binaries, including the
new version-check assertion), and a full ASan/UBSan sweep of all 6
binaries with zero real findings (one run hit the already-documented
DEADLYSIGNAL sandbox flake on test_pack_write_perf across all 3 retries;
re-verified directly afterward with 5/5 additional clean passes and timing
well under any plausible timeout, confirming it was the flake, not a
regression, before treating this as done).

Deliberately not done here, by the user's explicit choice: no
CODE_OF_CONDUCT.md, and no git remote/publishing -- this repository still
has neither, and both are decisions left to the maintainer.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01UqJpkdJ6Njnt1pw3CbghzB
This commit is contained in:
2026-09-14 10:58:35 +00:00
co-authored by Claude Sonnet 5
parent 529935deb4
commit 419182bb05
17 changed files with 317 additions and 6 deletions
+21
View File
@@ -15,6 +15,20 @@
#include <stddef.h>
#include <stdint.h>
/* Semantic versioning (semver.org). 0.x per semver's own definition means
* the public API may still change between minor versions without a major
* bump — consistent with this codebase's own "v0" status (README.md
* "Status"): an initial, partial implementation of concept.md, not a
* completed one. PACKFS_VERSION_STRING and pfs_version() always agree
* (the latter is generated from the former's components, not maintained
* separately) and both come from this header, so a statically-linked
* consumer's PACKFS_VERSION_* macros and a dynamically-linked consumer's
* pfs_version() call always describe the same build. */
#define PACKFS_VERSION_MAJOR 0
#define PACKFS_VERSION_MINOR 1
#define PACKFS_VERSION_PATCH 0
#define PACKFS_VERSION_STRING "0.1.0"
#ifdef __cplusplus
extern "C" {
#endif
@@ -86,6 +100,13 @@ typedef struct VfsDir {
Vfs *vfs_new(void);
void vfs_free(Vfs *v);
/* Returns PACKFS_VERSION_STRING of the linked library (not necessarily the
* header a caller compiled against, for a dynamically-linked consumer) —
* an ABI/API compatibility check available at runtime, not just compile
* time. Always non-NULL, always a byte-identical string literal, never
* allocated: never free() the result. */
const char *pfs_version(void);
/* --- Backend constructors -------------------------------------------
*
* Every backend is a Backend* handed to vfs_mount. Backends not currently