Verified: Ladder Diagram
Each claim the Ladder Diagram page makes, with the tests that
prove it in the last green CI run: 31 of 31 verified.
The claims live in docs/claims/ladder.yaml.
Last green CI run 16 Oct 2026, 14:48 UTC on c7618d3 · all runtime claims
LD-001 verified
A .ld file's rungs compile and run; a normally-open contact passes power when its tag is TRUE and a normally-closed contact (/Tag) when it is FALSE.
- pass
TestTranspileRungsinlang/ld - pass
TestLadderCompilesEndToEndinlang/ld - pass
TestConformance/ld-coilsinlang/conformance(11 of 11 passed)
LD-002 verified
A rising-edge contact (+Tag) passes one scan of power on Tag's 0 to 1 transition and a falling-edge contact (-Tag) one scan on 1 to 0.
- pass
TestConformance/ld-coils/+ contact passes one scan on the rise, - contact one scan on the fallinlang/conformance - pass
TestEdgeContactOneShotinlang/ld
LD-003 verified
A parallel branch [ a | b ] is the OR of its legs; each leg is a series and branches nest.
- pass
TestRungShapesinlang/ld - pass
TestConformance/ld-coils/nested branch, bare leg passes at onceinlang/conformance - pass
TestConformance/ld-coils/nested branch, FB leg is Q false at PT-1ms, true at PT, drop resetsinlang/conformance
LD-004 verified
A function contact such as EQ(P101_Mode, 0) passes power when the call returns TRUE; a leading / negates any BOOL term, including a function call or an accessor chain such as /t1.Q.
- pass
TestNegatedFunctionContactinlang/ld - pass
TestFunctionContactExpressionArgsinlang/ld - pass
TestConformance/ld-coils/negated function contact passes power when the call returns FALSEinlang/conformance - pass
TestFunctionContactPassesPowerWhenTrueinlang/ld
LD-005 verified
A block in the rung is driven by power on its power-in pin and power continues from its power-out pin; every other pin is named in the parentheses, with => capturing an output pin (BOOL or not) into a variable.
- pass
TestTranspileRungsinlang/ld - pass
TestLadderFunctionBlockRunsinlang/ld - pass
TestLadderOutputBindinginlang/ld - pass
TestConformance/ld-coils/FB-only rung (no coil) still runs, its outputs read elsewhereinlang/conformance
LD-006 verified
An output coil ( Tag ) assigns Tag the rung condition every scan; a set coil ( S Tag ) latches Tag := Tag OR condition; a reset coil ( R Tag ) unlatches Tag := Tag AND NOT condition.
- pass
TestConformance/ld-coils/S coil latches, R coil unlatches, R wins a same-scan tieinlang/conformance - pass
TestTranspileRungsinlang/ld
LD-007 verified
A P coil is TRUE for exactly one scan when the rung condition rises; an N coil for one scan when it falls; a condition already TRUE on the first scan counts as a rising edge.
- pass
TestConformance/ld-coils/P coil is TRUE for exactly one scan on the rising edgeinlang/conformance - pass
TestConformance/ld-coils/first scan with A already TRUE counts as a rising edgeinlang/conformance - pass
TestConformance/ld-coils/N coil is TRUE for exactly one scan on the falling edgeinlang/conformance
LD-008 verified
Contacts and coils take accessor references, so array elements and struct members address directly (Levels[2], PIT_001.VALUE).
LD-009 verified
A rung header carries a (* ... *) comment, and full-line // comments inside the block are diagram notes.
LD-010 verified
Series elements AND together and branch legs OR, so [ Start | Run ] /Stop ( Run ) compiles to Run := AND(OR(Start, Run), NOT Stop) (the seal-in).
- pass
TestTranspileRungsinlang/ld
LD-011 verified
A rung needs at least one coil, function block or assignment. A block can sit anywhere in the rung, power continuing from its output pin (A t1:TON(PT := T#5S) B ( Lamp ) sets Lamp to t1.Q AND B). Without a coil the rung ends at its last block: A B t1:TON(PT := T#5S) is a complete rung whose output is t1.Q read elsewhere, and anything after that block is an error.
- pass
TestFBOnlyRunginlang/ld - pass
TestRungErrorsinlang/ld - pass
TestConformance/ld-coils/FB-only rung (no coil) still runs, its outputs read elsewhereinlang/conformance - pass
TestConformance/ld-coils/block mid-rung, its Q carries power to the contact and coil after itinlang/conformance
LD-012 verified
Several coils on one rung share one condition, evaluated once and fanned out.
- pass
TestConformance/ld-coil-fanoutinlang/conformance(3 of 3 passed)
LD-013 verified
A rung with only a coil is driven by the rail, so ( AlwaysOn ) assigns TRUE.
- pass
TestRungShapesinlang/ld
LD-014 verified
Rungs evaluate top to bottom within a scan, so a coil written on one rung reads back as a contact on the next rung in the same scan.
- pass
TestConformance/ld-coils/S coil latches, R coil unlatches, R wins a same-scan tieinlang/conformance - pass
TestCoilReadsBackOnNextRungSameScaninlang/ld
LD-015 verified
Power is boolean: the six comparisons work as contacts, but a numeric function as a contact (ADD(TempC, 0.0)) is a compile error, not a pass-through.
LD-016 verified
Standard blocks use fixed power pins: TON/TOF/TP IN and Q, CTU CU, CTD CD, R_TRIG/F_TRIG CLK, SR S1/Q1, RS S/Q1.
- pass
TestConformance/fb-toninlang/conformance(7 of 7 passed) - pass
TestConformance/fb-tofinlang/conformance(8 of 8 passed) - pass
TestConformance/fb-tpinlang/conformance(9 of 9 passed) - pass
TestConformance/fb-ctdinlang/conformance(8 of 8 passed) - pass
TestConformance/fb-f-triginlang/conformance(6 of 6 passed) - pass
TestConformance/fb-srinlang/conformance(8 of 8 passed) - pass
TestConformance/fb-rsinlang/conformance(8 of 8 passed) - pass
TestConformance/ld-coils/FB-only rung (no coil) still runs, its outputs read elsewhereinlang/conformance - pass
TestLadderRTrigClockIsRungPowerinlang/ld
LD-017 verified
Passing the power pin yourself (t1:TON(IN := x)) is an error, because power owns it.
- pass
TestRungErrorsinlang/ld
LD-018 verified
Coils assign BOOL only; a timer's elapsed time or a counter's value is stored with the => output binding.
- pass
TestLadderOutputBindinginlang/ld - pass
TestConformance/ld-coils/FB-only rung (no coil) still runs, its outputs read elsewhereinlang/conformance - pass
TestCoilOnNonBoolTargetRefusedinlang/ld
LD-019 verified
Any instance output is readable as inst.Pin anywhere, including as a contact, without a => capture.
LD-020 verified
Edge contacts and coils get a stable derived instance name (from the rung, the tag and the repeat position) so the edge's retained state survives an unrelated edit.
LD-021 verified
LD transpiles in one hop to the FBD netlist, then to ST, so the built-in vocabulary, user FUNCTIONs and FUNCTION_BLOCKs from library .st files, and arrays/structs through accessors all work in ladder.
- pass
TestTranspileRungsinlang/ld - pass
TestLadderCompilesEndToEndinlang/ld - pass
TestConformance/st-case-insensitive/a FUNCTION called in another casing computes its resultinlang/conformance - pass
TestLadderLibraryProjectRunsininternal/project - pass
TestFBInstanceArrayInLadderinlang/ld - pass
TestLadderFunctionBlockInOutStructPininlang/ld
LD-022 verified
A user block drops into a rung like a TON: power lands on EN if declared, otherwise the first BOOL VAR_INPUT not bound by name, and continues from ENO or the first BOOL VAR_OUTPUT.
- pass
TestLadderFunctionBlockPowerPinsinlang/ld - pass
TestLadderLibraryProjectRunsininternal/project - pass
TestLadderFunctionBlockPowerOutOfENOinlang/ld - pass
TestLadderPowerSkipsBoundBoolInputinlang/ld
LD-023 verified
Instance state persists across scans, and an online edit carries it by name and type.
LD-024 verified
A .ld file may hold FUNCTION_BLOCKs whose bodies are rungs, and a .ld file with no PROGRAM is a project library; two instances are independent with their own state; VAR_* sections including VAR_IN_OUT (a UDT by reference) work.
- pass
TestLadderFunctionBlockLowersinlang/ld - pass
TestLadderFunctionBlockRunsinlang/ld - pass
TestLadderLibraryProjectRunsininternal/project - pass
each instance seals in and drops out on its ownintestdata/projects/ladder-subroutines - pass
each instance's TON is its own retained stateintestdata/projects/ladder-subroutines - pass
TestLadderFunctionBlockInOutStructPininlang/ld
LD-025 verified
naut check composes the line maps back through both hops, so a type error in the ST a rung produced reports at that rung's RUNG line.
LD-026 verified
Online edits treat .ld as the program source; download, diff against the controller and naut pull move the ladder text itself.
LD-027 verified
Jumps and labels (JMP, JMPC, LBL, RET) are not supported.
LD-028 verified
Master control relay zones (MCR) are not supported.
- pass
TestCheckRejects/MCRincmd/naut
LD-029 verified
Negated coils ( /Tag ) are rejected.
- pass
TestCheckRejects/negated coilincmd/naut
LD-030 verified
A coil inside a branch, or ahead of a later block, is an error: the output zone is contiguous at the rung's right end.
LD-031 verified
The ladder vocabulary is the IEC built-ins only; vendor instruction sets are not accepted.
- pass
TestCheckRejects/vendor instructionincmd/naut