Skip to content

Quiet GNU Make 4.4 peer-target warnings in noweb.mk and tex.mk - #84

Open
dbosk wants to merge 13 commits into
masterfrom
fix/texmk-peer-target-warnings
Open

dbosk wants to merge 13 commits into
masterfrom
fix/texmk-peer-target-warnings

Conversation

@dbosk

@dbosk dbosk commented Aug 25, 2026

Copy link
Copy Markdown
Owner

Fixes #83.

Three commits (the branch contains fix/noweb-peer-target-warnings):

  • noweb.mk: the multi-target pattern rule tangling supported suffixes from a
    plain .nw was one grouped rule to GNU Make 4.4+, warning "pattern recipe
    did not update peer target" for every suffix not written (a dozen+ warnings
    per built file in nytid). Replaced with one single-target rule per suffix
    via the same define/foreach/eval idiom used two rules above. (dbosk/nytid
    already pins this commit via its submodule gitlink.)
  • tex.mk.nw: restore parity with the generated tex.mk — tex.mk: unbounded rerun loop in COMPILE.tex never terminates when labels oscillate #73's bounded rerun
    loops had been applied to the generated file only, so any regeneration
    (which noweb.mk's %.mk: %.mk.nw rule makes automatic) would have silently
    reverted tex.mk: unbounded rerun loop in COMPILE.tex never terminates when labels oscillate #73. tex.mk is byte-identical after tangling.
  • tex.mk: split the grouped %.pytxmcr pattern rule into per-target rules
    (terminal :: semantics verified empirically; TEX_OUTDIR set/./empty cases
    tested and documented in the literate source). Last remaining peer-target
    warning in a full nytid doc build: 1 → 0.

🤖 Generated with Claude Code

https://claude.ai/code/session_01AhWZp3q1126cvw9bW8VBB5

dbosk and others added 13 commits June 12, 2026 09:04
The prose examples like [[<<module_name.py>>=]] made noweave parse the
inner <<...>> as a real chunk reference: the raw underscore in the
chunk name reached LaTeX unescaped (breaking compilation with "Missing
$ inserted") and the reference linked to a never-defined chunk.
Examples quoting the [[...]] notation itself, like [[[[...]]]],
truncated at the first ]] and left stray bracket text in the PDF.

Literal chunk syntax is now written with noweb's @<<...@>> escape
inside [[...]], and literal double brackets with \texttt and split
brackets, so the document compiles again and the examples render as
intended.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
NOWEAVE.tex now weaves through noweb's autolang and tominted filters
(dbosk noweb fork): each chunk is syntax-highlighted with minted using
a per-chunk lexer, and -autodefs python3 fills the identifier index
with -autolang gating the autodefs filters so chunks in other
languages stay out of the index.  The chunk-name-equals-filename
convention our tangling rules already enforce is what drives the
language inference.

The bundled Pygments lexer keeps chunk references hyperlinked inside
Python strings; noweb.mk provides a rule copying it from noweb's
library directory (read from the LIB= line of the noweave script),
and documents declare a dependency on it, as makefiles.pdf now does.
Documents must load minted and compile with -shell-escape, which our
own build already did.

NOWEAVE.pdf keeps the classic rendering: its preamble is generated by
noweave and cannot load minted.  Everything is set with ?=, so
projects without the fork override NOWEAVEFLAGS.tex.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
The autodefs filters now index make targets such as upload and
autocommit, which turns every [[...]] quote of those names into a
hyperlinked identifier use --- including the ones in section
headings, where hyperref cannot survive a link inside the moving
argument (the PDF bookmark breaks with "Undefined control sequence
\hyper@@link").  Headings now write \texttt where body prose keeps
the quoted, linked form.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
noweb now ships autodefs filters for shell and make (and Haskell,
Rust and Java), gated by the same @language annotations -autolang
provides, so stacking them indexes every chunk by exactly the filter
that understands it.  The default stack --- Python, shell, make ---
covers what our projects mix into one document: program modules,
helper scripts and their build files; our own woven documentation
now indexes its make variables and targets.

The stack stays at three because noweave has seven filter slots and
-autolang, each -autodefs and tominted occupy one each; the default
leaves two slots free for project filters, and other languages
remain a one-line NOWEAVEFLAGS.tex override.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
The caution claimed the default stack leaves two of noweave's seven
filter slots free.  It missed that -index inserts two filters
(finduses + noidx); with -autolang and tominted also taking one each,
the three-autodefs default fills all seven exactly.  Adding a fourth
-autodefs or a project -filter overflows unless something is dropped.

Prose-only change in a documentation chunk; the tangled noweb.mk is
unchanged.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
- Replace the seven-filter-slot caution with the dbosk fork's unbounded
  pipeline; keep the old ceiling only as a note for pre-fork noweave.
- Note that the preamble loads minted through the noweb package
  (\usepackage[minted]{noweb}) rather than a hand-added \usepackage{minted}.
- Record that noweave -minted can load minted into the generated preamble,
  so the standalone .pdf weave stays classic by choice, not necessity.

Documentation only; the tangled noweb.mk is unchanged.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Replace the hand-added \usepackage{minted} (plus a separate
\usepackage{noweb}) with \usepackage[minted]{noweb}, so the minted
dependency rides the noweb package the way tominted weaves expect.
\setminted{autogobble} still applies, as minted is loaded (via
\AtEndOfPackage) before it runs.

Requires the noweb fork whose noweb.sty declares the minted option;
to pass minted options such as outputdir, load minted directly before
\usepackage{noweb} instead.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
The dbosk fork's noweave, with -index, runs -autolang's inference as a
pre-pass to discover which languages a document contains and stacks the
matching autodefs filter for each. The default weave therefore no
longer lists -autodefs python3/sh/make: discovery covers them, and an
explicit -autodefs is still merged without duplication for chunks whose
language the name does not reveal.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Test chunks follow the convention <<test [[foo.py]]>>, labelling the
file rather than being it, and autolang deliberately does not infer a
language from such a labelled name. Left unclassified, a test chunk is
scanned by every autodefs filter and salts the index with
cross-language false matches. Add one -langrule per supported language
(python, shell, make) so each test chunk is classified, and hence
indexed, by the same filter as the module it exercises.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
The rule tangling a supported suffix from a plain .nw source listed
every suffix as targets of a single pattern rule. That is not shorthand
for several rules: make reads it as one recipe that produces all of
them, and since GNU Make 4.4 it says so, warning "pattern recipe did
not update peer target" for every suffix the recipe did not write. A
source that tangles one .py module reported the .c, .hs, .sty and the
rest it was never going to create -- more than a dozen warnings per
built file, enough to bury real diagnostics.

Generate one single-target pattern rule per suffix instead, with the
same define/foreach/eval idiom already used for the rules that carry
the suffix in the source name. The set of rules make ends up with is
the same; only the grouping claim goes away.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Commit e82e304 capped the LaTeX rerun loops at five extra passes, but it
edited the generated tex.mk only and left tex.mk.nw with the original
unbounded while-grep loops.  Every other .mk here tangles byte-for-byte
from its .nw, so tex.mk was the one file whose generated form no longer
matched its source.  That is a trap rather than a cosmetic drift:
noweb.mk supplies a %.mk: %.mk.nw rule and make remakes included
makefiles by itself, so the next build that touched tex.mk.nw would have
regenerated tex.mk and silently reverted #73.

Move the loop, and the comment explaining why it is bounded, into the
chunks they belong to.  tex.mk itself is unchanged: tangling tex.mk.nw
now reproduces the committed file exactly.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
The rules producing a .pytxmcr, a .pdf and a .dvi each listed the plain
name and the ${TEX_OUTDIR}/ one as targets of a single pattern rule.
Those two names are alternatives -- two ways of asking for the same
output -- but that is not how make reads them: a pattern rule with
several targets means one recipe that produces all of them (GNU Make
manual, Sect. 10.5.1).  Since GNU Make 4.4 it says so, with
a "pattern recipe did not update peer target" warning for every listed
target the recipe did not write.  Building nytid's documentation hit it
once per build, from the PythonTeX rule, whose recipe only ever writes
inside ${TEX_OUTDIR}.

Write one single-target rule per name instead, sharing each recipe
through a chunk so the two copies cannot drift.  The .pytxmcr rules keep
their double colon: on a pattern rule that marks the rule terminal, and
splitting the targets must not quietly change that.

The rules make ends up with are the same in every configuration.  Where
TEX_OUTDIR names a separate directory -- the ltxobj default -- the two
patterns stay distinct and each name selects its own rule.  Where it is
set to ".", they coincide; since the recipes are identical the behaviour
is unchanged, just as before, when make saw the same pattern listed
twice within one rule.

Fixes #83.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
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.

tex.mk grouped pattern rules trigger GNU Make 4.4 peer-target warnings

1 participant