From 956870889f9025f425dadc100886ed617325433f Mon Sep 17 00:00:00 2001 From: user Date: Fri, 4 Sep 2026 11:19:45 +0000 Subject: [PATCH] Update the make variable header to match the ?= and prefix rules --- test/packaging/lint-once.test.ts | 27 +++++++++++++++++---------- 1 file changed, 17 insertions(+), 10 deletions(-) diff --git a/test/packaging/lint-once.test.ts b/test/packaging/lint-once.test.ts index 4bf4c33..cf4f26b 100644 --- a/test/packaging/lint-once.test.ts +++ b/test/packaging/lint-once.test.ts @@ -149,11 +149,15 @@ const MAKE_CONDITIONAL = /^\s*(?:ifeq|ifneq|ifdef|ifndef|else|endif)\b/; // one. `$(MAKE)` was already special-cased below, which is this same rule // half-applied to a single name; this is the general form of it. // -// Deliberately only the simple case: a name assigned a literal on one line. -// `:=` and `=` differ in when make expands them and `?=` in whether it assigns -// at all, but none of that changes the single value a literal can take, so all -// three are read the same way. What is not read is anything needing evaluation -// — a value containing another `$(...)`, a make function, or a `define` body — +// Deliberately only the simple case: a name assigned a literal on one line, +// optionally through an `export`/`override` prefix. `:=` and `=` differ in +// when make expands them, which does not change the single value a literal can +// take, so those two are read the same way and the last one wins. `?=` differs +// in whether it assigns at all — it is skipped when the name already has a +// value — so among assignments to one name the first `?=` wins, and reading it +// as last-wins would resolve a reference to the string make discards. What is +// not read is anything needing evaluation — a value containing another +// `$(...)`, a make function, or a `define` body — // because expanding those means implementing make, and a half-implementation // that resolves a variable to the wrong string would count invocations that do // not happen. An unresolved reference is left standing verbatim instead, which @@ -182,8 +186,8 @@ const makeVariables = (text: string): Map => { const assignment = MAKE_ASSIGNMENT.exec(raw.replace(/#.*$/, "").trim()); if (assignment === null) continue; const [, name, operator, value] = assignment; - if (name === undefined || operator === undefined) continue; - if (value === undefined) continue; + if (name === undefined || operator === undefined || value === undefined) + continue; // `?=` assigns only when the name has no value yet, so the first one // wins where `:=` and `=` let the last one win. Overwriting here would // resolve the reference to a string make never uses. @@ -853,9 +857,12 @@ describe("the resolver reads what the shell would run", () => { // is not read as an assignment of the empty string. expect( parseMakefile( - ["FMT := script/fmt-check", "export FMT", "check:", "\t@$(FMT)"].join( - "\n", - ), + [ + "FMT := script/fmt-check", + "export FMT", + "check:", + "\t@$(FMT)", + ].join("\n"), ).get("check")?.recipe, ).toEqual(["script/fmt-check"]); });