Checker Agent Guide
Use this file for work under checker/ together with the repository-level AGENTS.md.
| Attribute |
Value |
| Name |
Checker |
| Purpose |
Performs semantic analysis on the bound AST: type checking, type inference, conversions and type relations, and ETS-specific semantics (reachability, assignment, boxing, etc.), and reports semantic errors and warnings. Day-to-day work is limited to ETSChecker and ETS semantics. |
| Primary Language |
C++ |
In-Scope (Primary Modification Target)
- Only ETSChecker: The only checker entry modified in practice is ETSChecker; TSChecker, JSChecker, ASchecker are out of scope.
- Only ETS semantics: Semantic and type-related changes apply to the ETS path only; TS semantics and the corresponding files/directories are out of scope.
- The checker must not transform the AST tree (no add/remove/replace/reparent).
- The checker must not allocate new AST nodes.
- Checker updates are limited to semantic metadata: set node type info and resolved variable references.
- Legacy code in the checker that mutates the AST tree is scheduled for refactor/removal. Do not add or keep AST tree transformations in the checker.
Type-Checking Rules (Spec-Aligned)
- Use
TypeRelation APIs (IsSupertypeOf, IsIdenticalTo, ...) for subtyping/compatibility/conversion logic.
- Do not hardcode type names (for example
"escompat.Record") and do not compare types by pointer identity.
- Avoid
Is<SomeType> checks when subtype semantics are involved; express the rule through TypeRelation.
- Avoid hard-coded AST-shape checks with
Is<SomeExpression>/Is<SomeStatement> as semantic shortcuts.
- Limited accepted patterns are context-specific and rare (for example call-site
a.b() member-call shape, numeric operand handling where required by semantics).
- Do not introduce new checker state flags (
CheckerStatus, AstNodeFlags, ETSObjectFlags, similar) as workaround logic; prefer relation/lowering-based designs.
- If spec and implementation/tests diverge for type compatibility, report the mismatch and keep behavior spec-first.
Directory Layout
checker/
├── ETSchecker.* # [in scope] ETS checker entry
├── ETSAnalyzer.cpp, ETSAnalyzer.h # [in scope] Per-node Check(...) entry; traverses via child Check() calls
├── ETSAnalyzerHelpers.* # [in scope] ETSAnalyzer helpers
├── ETSAnalyzerUnreachable.cpp # [in scope] Unreachable code analysis
├── ets/ # [in scope] ETS-specific submodules (see ets/ list below)
├── types/ # Type representation and relations (ETS types in scope only)
│ ├── type.*, typeRelation.*, typeFlag.h, typeFacts.h, typeError.h, typeMapping.h
│ ├── ets/ # [in scope] ETS types (primitive, object, union, tuple, function, etc.)
│ ├── ts/ # Rarely modified
│ └── globalTypesHolder.*, signature.*
├── checkerContext.* # Shared checker context
├── typeChecker/ # Type-checking core (TypeChecker)
├── checker.* # Base (Checker abstraction)
├── *checker*.cpp (non-ETS) # TSChecker, JSchecker, ASchecker — out of scope
├── *Analyzer*.cpp (TS) # TSAnalyzer, TSAnalyzerUnreachable — out of scope
├── ts/ # TS-specific — out of scope
└── resolveResult.h, SemanticAnalyzer.h
ets/ Submodule Summary (In Scope)
| File |
Role |
function.cpp |
Function calls, overload/signature selection |
arithmetic.* |
Arithmetic expressions and operation types |
assignAnalyzer.* |
Assignment semantics and liveness |
aliveAnalyzer.* |
Liveness / reachability |
boxingConverter.*, unboxingConverter.*, wideningConverter.* |
Boxing, unboxing, widening |
typeConverter.*, conversion.*, typeCreation.* |
Type conversion and creation |
castingContext.*, typeRelationContext.* |
Cast and type-relation context |
object.cpp |
Object type / literal checking |
etsWarningAnalyzer.* |
ETS warning analysis |
helpers.cpp, typeCheckingHelpers.cpp, validateHelpers.cpp |
General / type-check / validation helpers |
utilityTypeHandlers.cpp |
Utility types (e.g. Partial, ReturnType) |
Check Flow and Entry Points
- Per-node entry: Each AST node is checked from ETSAnalyzer.cpp; the tree is traversed by calling the Check method on child nodes.
- Function-related logic: Files under
ets/ named *function* (e.g. function.cpp) handle function calls and call signature selection.
Responsibilities
- Type system: ETS type hierarchy and relations in
types/; ETS-related subtyping and assignment compatibility in typeRelation.
- Type checking:
typeChecker/ and ETSChecker validate and infer types for expressions, statements, and declarations; checker writes semantic metadata but does not transform AST shape.
- ETS semantics: Boxing/unboxing, widening, arithmetic, assignment analysis, reachability, warnings in
ets/; keep implementations relation-based and avoid AST rewrites.
Dependencies
- Used by: compiler (lowering, core).
- Depends on: varbinder (binding results), parser/ir (AST), util.
Extending or Modifying
- New ETS type: Add the type class under
types/ets/, wire it into typeRelation and ETSChecker/ETS analysis.
- New ETS check rule: Add branches in ETSAnalyzer/ETSChecker or
ets/ visitors and report diagnostics. Checker-side updates must stay metadata-only (types/variables), with no AST shape changes.
- New AST node kind: In ETSAnalyzer.h declare
Check(ir::NodeType *node) via AST_NODE_MAPPING; implement the check in ETSAnalyzer.cpp and recurse via the node’s Check(checker).