aboutsummaryrefslogtreecommitdiff
path: root/AGENTS
diff options
context:
space:
mode:
Diffstat (limited to 'AGENTS')
-rw-r--r--AGENTS/ARCH.md1
-rw-r--r--AGENTS/CONVENTIONS.md17
-rw-r--r--AGENTS/PITFALLS.md10
-rw-r--r--AGENTS/SUBSYSTEMS.md12
4 files changed, 36 insertions, 4 deletions
diff --git a/AGENTS/ARCH.md b/AGENTS/ARCH.md
index 0ffe875..16456e2 100644
--- a/AGENTS/ARCH.md
+++ b/AGENTS/ARCH.md
@@ -315,6 +315,7 @@ do not modify the real release for local verification.
| `lib/Parser/ParserType.cc` | Type names, variable/array/constant declarations, TYPE/ENDTYPE and CLASS/ENDCLASS declarations, shared field and method parsing, SET/DEFINE reserved stubs |
| `lib/CodeGen/CodeGen.cc` | Initialization, symbols, call arguments and main() compilation |
| `lib/CodeGen/ExpressionGen.cc`, `StatementGen.cc`, `ControlFlowGen.cc` | Expression/statement dispatch and control-flow emission |
+| `lib/CodeGen/OperatorGen.cc`, `include/cps/Operator.h` | Exact global/member operator selection, calls and temporary receivers; shared operator spellings |
| `lib/CodeGen/GlobalGen.cc` | Primitive GLOBAL declaration and constant-initializer passes |
| `lib/CodeGen/ConstantGen.cc` | Literal constants, declaration conflicts and lexical binding restoration |
| `lib/CodeGen/ValueTypeGen.cc`, `OutputGen.cc`, `Builtins.h` | Expression typing, coercion/declarations, scalar output and the shared builtin table |
diff --git a/AGENTS/CONVENTIONS.md b/AGENTS/CONVENTIONS.md
index 5ab7459..d1f018d 100644
--- a/AGENTS/CONVENTIONS.md
+++ b/AGENTS/CONVENTIONS.md
@@ -83,8 +83,8 @@ pseudocode types *backwards* from LLVM types (`getExprTypeInfo`'s fallback,
only explicitly declared pointer types compare addresses. STRING's six comparison
operators use `strcmp` in `StringHandler`, dispatched by pseudocode type in CodeGen
before ArithmeticHandler. Ordering is case-sensitive byte lexicographic order;
-mixed STRING/non-STRING comparisons are errors. Whole-array and record comparisons
-remain unsupported.
+mixed STRING/non-STRING comparisons are errors. Whole-array comparisons remain unsupported; records/classes require an explicit
+operator overload for comparisons.
**Strings are malloc'd and never freed — by design.** Every string-producing operation
(`&`, MID/LEFT/RIGHT/LCASE/UCASE, NUM_TO_STR, CHR, READFILE, CHAR/number→STRING
@@ -152,6 +152,19 @@ declaration spelling for LLVM lookup, independently of call-site casing. Methods
`Class.Method` names and a hidden leading receiver address; their FuncSig parameters
contain only explicit source parameters. Method prototypes are pre-registered too.
+**Operator overloads share static selection.** OPERATOR is a reserved keyword;
+`OVERLOAD FUNCTION OPERATOR+(...)` records the token on PrototypeAST. Canonical
+names contain a space (`OPERATOR +`, `Class.OPERATOR AND`) to avoid collisions with
+ordinary identifiers. `OperatorGen.cc` probes visible global and left-class member
+signatures without emitting diagnostics or evaluating operands. Matching is exact;
+member/global ties are ambiguous and access is checked only after selection.
+Both getExprTypeInfo and emission must consult this resolver before hardcoded
+builtin result types. Returns may be any supported function result, including
+non-BOOLEAN comparisons/logic. emitCoercedExpr rejects implicit STRING to BOOLEAN;
+CASE separately requires BOOLEAN comparisons. Operators use shared argument
+marshalling and exception-aware calls. Member lvalues keep their original address;
+rvalues are materialized and registered for the existing function-scoped cleanup.
+
**Parameter modes are sticky and BYREF is procedure-only (guide §8.3).** In
`(BYREF a : T, b : T)` the `b` is BYREF too; unannotated parameters default to
BYVAL (§8.1). A BYREF parameter in a FUNCTION is a parse error. **Array
diff --git a/AGENTS/PITFALLS.md b/AGENTS/PITFALLS.md
index 3198852..4059767 100644
--- a/AGENTS/PITFALLS.md
+++ b/AGENTS/PITFALLS.md
@@ -46,7 +46,7 @@ test programs.
at any new call site) and internally defaults to INTEGER for unclassified arithmetic expressions; unknown or unmatched calls now diagnose and return nullptr.
OUTPUT reports an error for a nullptr result.
- **CONSTANT** accepts only literals (including negative numeric literals), never expressions or other names. Constants have lexical block scope and may shadow outer names; bindings hiding constants are restored on block exit too. Functions inherit previously declared constants from their own unit and all visible imported top-level constants. Constants have no writable storage: assignment, INPUT, READFILE targets, FOR variables, BYREF and address-of are rejected.
-- **CASE OF** reads its selector once and tests expression labels in source order, with inclusive TO ranges and an optional final OTHERWISE. Label headers occupy their own source line; bodies may begin after the colon or on subsequent lines. Comparisons reuse ordinary operator rules; records and whole arrays are unsupported.
+- **CASE OF** reads its selector once and tests expression labels in source order, with inclusive TO ranges and an optional final OTHERWISE. Label headers occupy their own source line; bodies may begin after the colon or on subsequent lines. Comparisons reuse ordinary operator rules; records/classes need BOOLEAN-returning comparison overloads, and whole arrays are unsupported.
- The lexer emits no newline tokens; most grammar is keyword-delimited, while CASE
uses token line information to recognize labels. Bare `RETURN` is recognized
before block terminators and the next CASE label.
@@ -93,6 +93,14 @@ test programs.
inputs. MAIN and builtins cannot be overloaded. NEW supports overloads; DECLARE,
fields and arrays needing default construction require a matching no-argument NEW.
Private access is checked after selection, never used to select a public fallback.
+- **OPERATOR extension.** Requires OVERLOAD FUNCTION, with supported unary/binary
+ arity and at least one record/class/enum operand. Pointer aliases alone do not
+ qualify. Exact matching considers visible globals and left-class members
+ together; ties are errors, including private/public ties. Comparison and logic
+ result types are declared, not assumed BOOLEAN; implicit STRING to BOOLEAN is
+ rejected. CASE comparisons must return BOOLEAN. AND/OR overloads evaluate both
+ operands. Temporary member receivers have function-scoped cleanup, not C++
+ full-expression lifetimes. Explicit calls use OPERATOR+(a,b) or a.OPERATOR+(b).
- **CLASS subset (§10).** `CLASS`/`ENDCLASS`/`PUBLIC`/`PRIVATE` are reserved.
CLASS is a top-level record-derived value type with optional per-member access
keywords (no DECLARE). Omitting access defaults to public, per the guide.
diff --git a/AGENTS/SUBSYSTEMS.md b/AGENTS/SUBSYSTEMS.md
index ac31cde..be20bc3 100644
--- a/AGENTS/SUBSYSTEMS.md
+++ b/AGENTS/SUBSYSTEMS.md
@@ -43,6 +43,16 @@ compile error (no extern is fabricated). Functions inherit visible GLOBAL storag
`StmtEmitter` callback, and must restore its own insert point (and the exchanged
ArrayTable) afterwards.
+**Operator overloads** (`OperatorGen.cc`): PrototypeAST retains the operator token;
+FunctionGen validates operand count and requires a record/class/enum operand.
+Global signatures and left-class methods share exact-type selection, used by
+ValueTypeGen and ExpressionGen before builtin operations. Missing candidates leave
+builtin rules intact; ties are errors. Member access is checked after selection.
+The raw-expression argument-marshalling overload borrows AST pointers for operator
+calls; ordinary calls adapt their unique_ptr lists into it. Member receivers use
+lvalue storage or a materialized, Alive-tracked temporary. CASE calls the value
+entry point with its already captured selector and requires BOOLEAN results.
+
**EXTERN "C"** (`ExternDeclAST`, `IncludeObjStmtAST`): the parser builds a body-less
`PrototypeAST` (IsExternal, IsVariadic, unnamed `argN` params). `FunctionGen::emitExternPrototype`
validates C types, records a `FuncSig` with `IsExternal`, the declared `FunctionType` and
@@ -71,7 +81,7 @@ constants live in a TypeSystem-owned table, resolved in `emitExpr`'s
`VariableExprAST` branch after `Symbols` misses. The lvalue layer
(`emitLValue`/`loadFromLValue`) resolves designator chains to `{address, type name}`;
`emitCoercedExpr` is the single name-level admission gate; `emitUserKindBinaryOp`
-intercepts binary operators ahead of ArithmeticHandler (which, like StringHandler and
+intercepts built-in binary operators ahead of ArithmeticHandler (which, like StringHandler and
FileHandler, is deliberately ignorant of user kinds). The enum range check after
`E ± INTEGER` is the only site that can produce an invalid ordinal — every other
producer (constants, same-name copies, zero-init, memset-0 arrays) is valid by