You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
A Tcl / iRules braced value scores one operand when the grammar
models the command that takes it, and one per word inside when only
the command's name would identify it. set x {a b} and lappend x {a b} are the same value in the same language and score
differently.
#1318 fixed the operator half of this — lappend x {a b} no longer
reports a {} block that is not there — and deliberately stopped
short of the operand half. This issue is the remainder.
$ printf 'set x {a b}\nlappend y {a b}\n' > two.tcl
$ bca ops --no-config -p two.tcl
|- operators
| `- set
`- operands
|- x
|- {a b} <- `set` takes a `braced_word_simple`: one operand
|- lappend
|- y
|- a <- `lappend` takes a `braced_word`: one per word
`- b
n2 = 6 where the two lines describe two identical values.
The two roles share one kind (braced_word), so the only signal is the
enclosing command's name, and that signal is absent for every command
outside a small core list — including every user proc. Suppressing a
value word's contents on that guess was built and measured, then
rejected: a braced argument to an unrecognised command is as often real
code as a list. On this file —
oo::class create Counter {
variable n
constructor {} { set n 0 }
method bump {} { incr n }
}
test counter-1.1 {bump increments} -body {
set c [Counter new]
$c bump
} -result 1
set f [apply {{x} { expr {$x + 1} }} 2]
n1
N1
n2
N2
contents kept (shipped)
5
8
25
32
contents suppressed
2
2
15
15
The class body, the test body and the lambda each collapsed into a
single operand, taking halstead.effort — a gated threshold metric —
down with them. So #1318's rule only ever withdraws a claim the classifier cannot support
(the block), and never discards code the walk has already read.
The reasoning is recorded on Getter::braced_word_op_type in src/getter.rs.
What would actually close this
Nothing available from the grammar alone. Options worth weighing:
Leave it, and document it as the contract. A braced argument to
an unrecognised command is treated as code because it as often is;
the set / lappend asymmetry is then the grammar's, not the
classifier's. Cheapest, and arguably correct.
Widen the braced_word_simple treatment to a command allowlist.
The mirror of fix(getter): Tcl/iRules braced literals still fabricate a block outside special-cased commands #1318's list: lappend, puts, list, lset, string map, regsub, array set, … A value word passed to one of
those is one operand. Bounded and safe for the listed commands,
incomplete by construction for everything else — and it would make three behaviours where there are now two.
Read the contents. A braced word holding no variable_substitution,
no command_substitution and no nested block is more list-like than
script-like. A heuristic on top of a heuristic; would need measuring
against a real Tcl corpus before anyone believed it.
Whichever way it lands, .claude/rules/testing.md applies: assert n1 andN1and the operand vocabulary, and mirror every row across
both dialects.
Prerequisite
There is no Tcl or iRules source in the integration corpora
(fd -e tcl -e irule tests/repositories returns nothing), so no
snapshot would move for any of these options and the whole question
rests on unit fixtures. Adding a real Tcl corpus is worth doing before
option 2 or 3, and would also give #1318 the coverage it currently
lacks.
Summary
A Tcl / iRules braced value scores one operand when the grammar
models the command that takes it, and one per word inside when only
the command's name would identify it.
set x {a b}andlappend x {a b}are the same value in the same language and scoredifferently.
#1318 fixed the operator half of this —
lappend x {a b}no longerreports a
{}block that is not there — and deliberately stoppedshort of the operand half. This issue is the remainder.
Evidence
At the pinned grammars, after #1318:
n2 = 6 where the two lines describe two identical values.
Why #1318 did not fix it
The two roles share one kind (
braced_word), so the only signal is theenclosing command's name, and that signal is absent for every command
outside a small core list — including every user proc. Suppressing a
value word's contents on that guess was built and measured, then
rejected: a braced argument to an unrecognised command is as often real
code as a list. On this file —
oo::class create Counter { variable n constructor {} { set n 0 } method bump {} { incr n } } test counter-1.1 {bump increments} -body { set c [Counter new] $c bump } -result 1 set f [apply {{x} { expr {$x + 1} }} 2]The class body, the test body and the lambda each collapsed into a
single operand, taking
halstead.effort— a gated threshold metric —down with them. So
#1318's rule only ever withdraws a claim the classifier cannot support
(the block), and never discards code the walk has already read.
The reasoning is recorded on
Getter::braced_word_op_typeinsrc/getter.rs.What would actually close this
Nothing available from the grammar alone. Options worth weighing:
an unrecognised command is treated as code because it as often is;
the
set/lappendasymmetry is then the grammar's, not theclassifier's. Cheapest, and arguably correct.
braced_word_simpletreatment to a command allowlist.The mirror of fix(getter): Tcl/iRules braced literals still fabricate a block outside special-cased commands #1318's list:
lappend,puts,list,lset,string map,regsub,array set, … A value word passed to one ofthose is one operand. Bounded and safe for the listed commands,
incomplete by construction for everything else — and it would make
three behaviours where there are now two.
variable_substitution,no
command_substitutionand no nested block is more list-like thanscript-like. A heuristic on top of a heuristic; would need measuring
against a real Tcl corpus before anyone believed it.
Whichever way it lands,
.claude/rules/testing.mdapplies: assertn1and
N1and the operand vocabulary, and mirror every row acrossboth dialects.
Prerequisite
There is no Tcl or iRules source in the integration corpora
(
fd -e tcl -e irule tests/repositoriesreturns nothing), so nosnapshot would move for any of these options and the whole question
rests on unit fixtures. Adding a real Tcl corpus is worth doing before
option 2 or 3, and would also give #1318 the coverage it currently
lacks.
Related
Checker::is_stringcalls a script body a string literal.