NBPR.Buildroot.Defconfig (NBPR v0.4.0)

Copy Markdown View Source

Generates a per-build Buildroot defconfig that layers nbpr-specific settings on top of the active Nerves system's defconfig.

Layered on top in order:

  1. The system's defconfig verbatim (e.g. nerves_system_rpi4/nerves_defconfig).
  2. BR2_PER_PACKAGE_DIRECTORIES=y so per-package builds don't contend.
  3. BR2_PACKAGE_BUSYBOX_SHOW_OTHERS=y so packages overlapping busybox applets (e.g. kmod's tools) aren't dropped as unmet dependencies.
  4. BR2_PRIMARY_SITE pointing at Buildroot's source archive — see below.
  5. One line per kconfig symbol gating a nested package — see below.
  6. BR2_PACKAGE_<UPPER_BR_NAME>=y to enable the target package.
  7. One line per resolved build_opt whose schema declared a :br_flag extension, formatted as <br_flag>=<value> with BR-style boolean, string, and integer encoding. A :br_flag naming a list of symbols emits one line each, all carrying the same value — which is what Buildroot's virtual packages need, where enabling a feature means setting both the virtual symbol and a provider from the choice beneath it.

The result is a defconfig file ready to be loaded with make defconfig — but typically we'd write it to O=<dir>/.config directly and follow with make olddefconfig to resolve any dependencies.

Nested packages and their gating symbols

Most Buildroot packages live at package/<name>/, and BR2_PACKAGE_<NAME>=y is all it takes to select one. Some live one level deeper, at package/<parent>/<name>/, and their Config.in is sourced from the parent's inside an if block — fftw-single under fftw, every xlib_* and xdriver_* under x11r7, the qt5*/qt6* and gst1-* families.

For those, BR2_PACKAGE_<NAME>=y on its own is silently discarded by make olddefconfig: the symbol's dependencies aren't met, so kconfig drops it, the package never builds, and the failure only surfaces later as a missing per-package output directory.

The gating symbols can't be derived from the parent directory's name — package/x11r7/ is gated by BR2_PACKAGE_XORG7, not BR2_PACKAGE_X11R7, and package/opengl/ sources its children with no gate at all. Nor can the directory be trusted to hold the declaration: package/jpeg-turbo/ ships only a .mk and a Config.in.options, while BR2_PACKAGE_JPEG_TURBO itself is declared inside the choice in package/jpeg/Config.in, under if BR2_PACKAGE_JPEG.

So the gates are read from the tree, starting from wherever the symbol is actually declared:

  1. the if blocks wrapping the config stanza in its own file, then
  2. the if blocks wrapping each source line on the chain from that file up to package/Config.in.

Outermost first. Both halves are real: the modular Xorg drivers sit inside if BR2_PACKAGE_XORG7 and if BR2_PACKAGE_XSERVER_XORG_SERVER_MODULAR by inclusion, while jpeg-turbo is gated by its declaring stanza alone. choice/endchoice is not a gate — it groups alternatives, and setting a member to y is how you pick one.

Only bare symbol conditions are emitted. A compound condition (Buildroot has one, an || over two freescale-imx platform choices) is a choice between alternatives that nbpr has no basis to make, so it's left alone.

Top-level packages are deliberately excluded from this lookup even though package/Config.in has if blocks of its own: they already build, and re-deriving their gates would change what every existing package's build sees for no benefit.

Why the primary site is set

BR2_BACKUP_SITE defaults to Buildroot's own source archive, which mirrors every tarball mainline Buildroot references. Nerves systems override it to https://dl.nerves-project.org, which only carries what a Nerves system itself builds — reasonable for them, useless here, because nbpr's whole purpose is building packages Nerves systems don't include.

Left alone, an nbpr build's only real source is the package's own upstream site, and some of those are unreliable: gpsd's is a Savannah mirror over plain HTTP, which times out often enough from CI runners to fail roughly half a nine-target matrix, with dl.nerves-project.org then returning 403.

Setting BR2_PRIMARY_SITE to the archive fixes that without touching the system's backup choice. Buildroot tries the primary site first and falls back to the package's own site, so downloads get faster and more reliable at the same time, and upstreams see less traffic — which is what Buildroot recommends the option for.

Summary

Functions

Returns the kconfig symbols that must be y for br_package to be selectable, outermost first.

Returns the defconfig text for the given inputs as a binary.

Functions

gating_symbols(br_tree, br_package)

@spec gating_symbols(Path.t(), String.t()) :: [String.t()]

Returns the kconfig symbols that must be y for br_package to be selectable, outermost first.

Empty for a package whose symbol is declared at the top level of its own Config.in and sourced unconditionally.

render!(package, system_defconfig_path, br_tree, build_opts)

@spec render!(NBPR.Package.t(), Path.t(), Path.t(), keyword()) :: String.t()

Returns the defconfig text for the given inputs as a binary.

package is an NBPR.Package.t(). br_tree is an extracted Buildroot source tree (from NBPR.Buildroot.Source.ensure!/2), read to derive the gating symbols of a nested package. build_opts is the resolved keyword list (defaults applied) — typically the validated output of NimbleOptions.validate!/2 on the package's build_opts schema.