Brad Arant 76ea89e79c Add <try>/<catch> tag, fix a real infinite-loop bug it exposed in Tag's
split-container mechanism

<try>...container...<catch>...container2...</catch-less, matching <else>'s
own convention> intercepts any error that would otherwise propagate up and
halt the whole script - a coreutils::Exception (what every other tag
actually throws), any other std::exception (e.g. the
std::filesystem::filesystem_error <whiledir> can raise), or anything else.
Optional name=/scope= keywords bind the caught error's message to a
variable for the catch block to reference, matching <for>'s own
name=/scope= convention. New class named __trytag rather than __try: <ios>
transitively defines a preprocessor macro "#define __try try" (an SEH-
compatibility shim pulled in on this toolchain) that silently rewrites the
identifier __try to the keyword try wherever it appears, breaking
compilation - confirmed via `g++ -E -dM` before picking this name. The JET
tag name itself is still plain <try>.

Reuses the same container/container2 split mechanism <if>/<else> already
has (Tag's constructor takes an optional splitTagName), which surfaced a
real, previously-latent bug: the code that consumes the split tag's own
opening delimiter after a match was hardcoded to the literal string
"<else>" instead of being built from splitTagName. This happened to work
for every existing split-tag user (<if>, <while>, <until> all use "else"),
but for <try>'s "catch" the hardcoded ifNext("<else>") never matched, so
the cursor never advanced past <catch> and the outer scan loop matched the
same unconsumed <catch> forever - a genuine infinite loop, not just wrong
output, confirmed via a real hung jet-2.0 run before diagnosis. Fixed by
building the actual expected delimiter ("<" + splitTagName + ">")
dynamically instead.

Verified via real jet-2.0 script execution (not just compilation): a
caught <read> failure correctly binds its error text to a name= variable
and skips straight to the catch block, discarding whatever partial output
the failed attempt had already written; an untriggered <try> runs its own
content normally and skips <catch> entirely; a <try> with no <catch> at
all silently swallows the error and the script continues past it. Also
regression-tested <if>/<else> and <while> (both depend on the exact same
fixed code path) to confirm nothing broke for the existing "else" case.
2026-08-26 09:00:18 -07:00
2024-12-02 15:46:49 -08:00
2025-12-09 16:40:15 -08:00
2025-05-06 07:33:04 -07:00
2025-05-06 07:33:04 -07:00
2025-01-09 07:49:11 -08:00
2025-02-07 19:29:18 -08:00
2025-02-07 19:29:18 -08:00
2025-12-09 12:29:39 -08:00
2025-01-09 08:02:38 -08:00
2025-01-09 08:02:38 -08:00
2025-02-07 16:10:13 -08:00
2025-11-21 19:15:48 -08:00
2025-11-21 19:15:48 -08:00
2025-12-04 17:05:57 -08:00
2025-05-06 07:33:04 -07:00
2025-11-21 19:15:48 -08:00
2025-11-21 19:15:48 -08:00
2025-11-21 19:15:48 -08:00
2025-11-21 19:15:48 -08:00
2025-11-21 19:15:48 -08:00
2025-11-21 19:15:48 -08:00
S
Description
JET 2.0 core library.
40 MiB
0 Stars 0 Watchers 0 Forks
Languages
HTML 50.2%
TeX 18.7%
C++ 15%
JavaScript 7.5%
CSS 4.4%
Other 4.2%