Four things the adversarial review of #1049 turned up that were out of scope for it.
<object data="x.js"> and <embed src="x.js"> are now inlined as JavaScript. The old scanner's table allowed only images on those two attributes; the deny-list that replaced it classifies by MIME, so the type widened. Harmless in practice, but whether object and embed should carry a per-tag class restriction is a design call rather than a bug fix.
sf_parse_mark rejects a <len> over SF_MAX_REF (4096), and the emitter can exceed it: tempo is 2048 bytes, and escape_for_html_print_full turns & into & and a high byte into six characters. A reference near the limit would emit a mark that parses as nothing and stays in the page as literal text. Savenames arrive percent-escaped so it is unreachable today, but the cap should match the emitter's worst case, or singlefile_mark should refuse to write a mark it cannot read back.
singlefile_may_mark hand-rolls a bounded substring search that hts_memstr (htstools.c:281) already provides, with the same NUL-safe contract.
Two cases in tests/94_local-single-file.test assert nothing. The --changes case builds its command from common, which points at $out and not $chg, so $chgpage never exists and the test ! -f "$chgpage" || guard short-circuits to a pass. The charset case uses grep -q 'charset=127' ... || true as its non-vacuity floor, which passes on a build that emits no charset meta at all.
Four things the adversarial review of #1049 turned up that were out of scope for it.
<object data="x.js">and<embed src="x.js">are now inlined as JavaScript. The old scanner's table allowed only images on those two attributes; the deny-list that replaced it classifies by MIME, so the type widened. Harmless in practice, but whether object and embed should carry a per-tag class restriction is a design call rather than a bug fix.sf_parse_markrejects a<len>overSF_MAX_REF(4096), and the emitter can exceed it:tempois 2048 bytes, andescape_for_html_print_fullturns&into&and a high byte into six characters. A reference near the limit would emit a mark that parses as nothing and stays in the page as literal text. Savenames arrive percent-escaped so it is unreachable today, but the cap should match the emitter's worst case, orsinglefile_markshould refuse to write a mark it cannot read back.singlefile_may_markhand-rolls a bounded substring search thathts_memstr(htstools.c:281) already provides, with the same NUL-safe contract.Two cases in
tests/94_local-single-file.testassert nothing. The--changescase builds its command fromcommon, which points at$outand not$chg, so$chgpagenever exists and thetest ! -f "$chgpage" ||guard short-circuits to a pass. The charset case usesgrep -q 'charset=127' ... || trueas its non-vacuity floor, which passes on a build that emits no charset meta at all.