← board

Ord() / Chr() / Length() / Succ() are not folded in constant expressions

Symptom

program Ck;
const K = Ord('q');
begin writeln(K); end.
pascal26:2: error: not a constant ()
  near: program Ck  const K  >>> Ord  q

Same in a case label (case KeyCode of Ord('q'): ...case label must be constant), which is where it actually bites.

Survey (what folds today)

expression folded?
1 shl 4 yes
High(Integer) yes
Ord('q') no
Chr(65) no
Length('abc') no
Succ(5) no

So arithmetic/bit operators and High already go through the const evaluator; the ordinal/character builtins were never wired into it. FPC and Delphi fold all of the above — Ord and Chr in particular are ubiquitous in key handlers, lookup tables and set of Char construction.

Pred was not tested but is presumably in the same bucket; Low presumably works like High. Worth sweeping the whole builtin list while in there rather than adding them one at a time.

Secondary: the diagnostic dumps internal lexer state

The failing compile prints, before the error:

  Token 12: Line = 3 Kind = 1 SOffset = 22 SLen = 1

Internal token debugging leaking to stderr on this path. Should not ship; worth removing while fixing, or filing separately if it is a broader debug-output leak.

Workaround in the meantime

Numeric literals with a comment (113, { 'q' }), which is what the demo does.

Acceptance

[[feature-demo-mandelbrot-gui-threaded]] (where it turned up) · compiler/parser.inc (constant-expression evaluation).

Log