Skip to content

Makefile: allow using BUILD_DIR for outputs#536

Merged
robertswiecki merged 1 commit into
google:masterfrom
PaulGrandperrin:master
Apr 13, 2026
Merged

Makefile: allow using BUILD_DIR for outputs#536
robertswiecki merged 1 commit into
google:masterfrom
PaulGrandperrin:master

Conversation

@PaulGrandperrin
Copy link
Copy Markdown
Contributor

Hi!

We recently got an issue (rust-fuzz/honggfuzz-rs#116) with honggfuzz-rs when building honggfuzz from a read-only directory. This happens for example when using Nix as a build system.

Rust's cargo usually writes all its artifacts in a target directory but until now my honggfuzz-rs project didn't respect that and built honggfuzz's objects files directly in the source directory.

This violates cargo's mechanism and breaks Nix builds.

One easy solution is to copy the whole honggfuzz project in the target directory each time and build from here. I think this is not great as honggfuzz is a hundred or so MBs and cargo will duplicate it as many times as there will be build configurations.

We could avoid copying the examples dir or using symlinks/hardlinks but I think the best solution would be have the Makefile be able to use a separate output directory, similarly to cmake.

To illustrate the idea I send you this PR but don't hesitate to reject it, I didn't even write it as I only know the basics of Makefiles. This code was written by Claude Opus 4.6 and I don't fully understand it. It seems to work fine though.

Summary of Changes (written by Claude)

The Makefile now supports an optional BUILD_DIR variable for out-of-tree builds. When not set, it builds in-tree exactly as before.

Key mechanisms:

  1. SRCDIR — automatically derived from the Makefile's own location using $(abspath $(lastword $(MAKEFILE_LIST))), so it always points to the source tree regardless of where make is invoked from.

  2. BUILD_DIR — user-supplied, optional. When set, all build artifacts (.o, .a, .so, binaries) go there instead of the source tree.

  3. _OBJDIR — internal variable that equals BUILD_DIR when set, or SRCDIR when not (backward compat).

  4. VPATH := $(SRCDIR) — lets Make find .c source files in the source tree when building from a different directory.

  5. -I$(SRCDIR) — replaces the old -I. so header includes always resolve against the source tree.

  6. .SECONDEXPANSION: with | $$(dir $$@) order-only prerequisites — ensures build subdirectories (linux/, libhfcommon/, etc.) are created in BUILD_DIR before compilation.

  7. All output paths (OBJS, BIN, HFUZZ_CC_BIN, LHFUZZ_ARCH, LCOMMON_ARCH, LNETDRIVER_ARCH, etc.) are prefixed with $(_OBJDIR)/.

The Makefile now supports an optional `BUILD_DIR` variable for out-of-tree builds. When not set, it builds in-tree exactly as before.

Key mechanisms:

`SRCDIR` — automatically derived from the Makefile's own location using `$(abspath $(lastword $(MAKEFILE_LIST)))`, so it always points to the source tree regardless of where `make` is invoked from.
`BUILD_DIR` — user-supplied, optional. When set, all build artifacts (`.o`, `.a`, `.so`, binaries) go there instead of the source tree.
`_OBJDIR` — internal variable that equals `BUILD_DIR` when set, or `SRCDIR` when not (backward compat).
`VPATH := $(SRCDIR)` — lets Make find `.c` source files in the source tree when building from a different directory.
`-I$(SRCDIR)` — replaces the old `-I.` so header includes always resolve against the source tree.
`.SECONDEXPANSION:` with `| $$(dir $$@)` order-only prerequisites — ensures build subdirectories (`linux/`, `libhfcommon/`, etc.) are created in `BUILD_DIR` before compilation.

All output paths (`OBJS`, `BIN`, `HFUZZ_CC_BIN`, `LHFUZZ_ARCH`, `LCOMMON_ARCH`, `LNETDRIVER_ARCH`, etc.) are prefixed with `$(_OBJDIR)/`.
@robertswiecki
Copy link
Copy Markdown
Collaborator

Thank you Paul!

@robertswiecki robertswiecki marked this pull request as ready for review April 13, 2026 06:34
@robertswiecki robertswiecki merged commit 48790f7 into google:master Apr 13, 2026
1 check passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants