Commit Graph
100 Commits
Author SHA1 Message Date
dimgigov 2259567ac2 docs: add Drop trait implementation plan 2026-06-11 01:08:27 +03:00
dimgigov f4f09602c6 docs: add Drop trait / destructors design document 2026-06-11 01:07:34 +03:00
dimgigov ef4aa42b0b feat: add web playground with Docker sandbox
- playground/backend/main.go — Go HTTP server with /compile endpoint
- playground/frontend/index.html — Monaco Editor with 8 code examples
- playground/sandbox/Dockerfile — isolated Docker container with buxc2
- playground/docker-compose.yml — orchestrates backend + sandbox
- playground/Makefile — build and run targets
- playground/README.md — deployment guide for VPS with nginx + SSL
2026-06-10 20:33:26 +03:00
dimgigov 8f68a9da1a docs: document --target cross-compilation flag
- Add cross-compilation to README.md features and quick start
- Add cross-compilation section to docs/BuildAndTest.md
2026-06-10 20:26:31 +03:00
dimgigov e4e4e0d8ef feat: add --target <triple> cross-compilation flag
- Parse --target flag in Cli_Run before command dispatch
- Pass targetTriple through Cli_Build, Cli_BuildProject, Cli_RunProject
- Use clang with -target when cross-compiling, cc otherwise
- Selfhost loop: C output identical
2026-06-10 20:24:46 +03:00
dimgigov 18aa232b1c docs: add cross-compilation design document 2026-06-10 20:19:17 +03:00
dimgigov c6bae8b9ee feat(diag): add parser severity filtering and source map heuristic for bux build 2026-06-10 20:15:57 +03:00
dimgigov aef0cd7936 docs: add source location error fixes design 2026-06-10 20:12:20 +03:00
dimgigov 62d92b0aa6 test: add error snippet formatting test 2026-06-10 20:08:24 +03:00
dimgigov 9a63dcca11 fix(diag): remove parser diag printing, fix String_CharAt and sourceName issues 2026-06-10 20:08:20 +03:00
dimgigov 10a2b64ac4 feat(diag): print parser diagnostics in Parser_Parse 2026-06-10 20:04:31 +03:00
dimgigov 92962fa1b0 feat(diag): format all lexer and sema errors with Diagnostic_Print 2026-06-10 20:03:56 +03:00
dimgigov b971775baf feat(diag): add Diagnostic struct and Rust-style formatter 2026-06-10 20:02:33 +03:00
dimgigov 85d15cd16d docs: add source location error messages implementation plan 2026-06-10 20:00:09 +03:00
dimgigov de3ac76581 docs: add source location error messages design document 2026-06-10 19:56:55 +03:00
dimgigov 2824d25369 test: add green thread integration test
Also fix runtime scheduler bugs:
- g_task_creating was thread-local but set on main thread and read on worker
- g_scheduler_context was global shared by all workers instead of per-thread
2026-06-10 19:48:47 +03:00
dimgigov 9cd0580832 feat(task): add full green thread API (Init, Wait, Yield, CurrentId, Shutdown) 2026-06-10 19:45:24 +03:00
dimgigov 9e547f123a fix(scheduler): make Task_Sleep yield instead of block (MVP) 2026-06-10 19:44:55 +03:00
dimgigov 211a811f32 feat(scheduler): implement green thread scheduler with work-stealing 2026-06-10 19:43:31 +03:00
dimgigov 4456bb00af docs: add green threads implementation plan 2026-06-10 19:38:24 +03:00
dimgigov 6a0a0425dd docs: add green threads / task scheduler design document 2026-06-10 19:33:53 +03:00
dimgigov 9e515c157d feat(pkg): add basic package manager (add, remove, fetch, build deps)
- manifest.bux: parse [dependencies] section with up to 8 deps
- manifest.bux: Manifest_AddDep, Manifest_RemoveDep, Manifest_ToString
- cli.bux: bux add <name> <url> — adds dependency to bux.toml
- cli.bux: bux remove <name> — removes dependency from bux.toml
- cli.bux: bux fetch — git clone/pull dependencies into deps/
- cli.bux: Cli_BuildProject now merges deps/<name>/src/*.bux before user code
- Selfhost bootstrap loop verified: C output deterministic ✓
2026-06-10 19:18:36 +03:00
dimgigov 8f8708c5df feat(drop): enforce @[Drop] attribute and add basic move semantics
- Auto-drop now only triggers for user-defined types explicitly marked
  with @[Drop] on the struct declaration.
- Added move tracking in C backend to skip auto-drop for variables
  that have been moved (via let y = x, return x, or assignment).
- Prevents double-free when ownership is transferred.
- Selfhost bootstrap loop verified: C output is deterministic.
2026-06-10 19:08:15 +03:00
dimgigov 7392013301 docs: add Phase 8.7 — Optimization & Release Mode to PLAN.md
- @[Release] attribute for zero-cost abstractions
- Auto-drop inline, dead-store elimination, -O3 by default, PGO
- Milestone M15: C-speed benchmarks vs Nim/Crystal
2026-06-10 13:51:10 +03:00
dimgigov 0b887b92d3 selfhost: for-in support for Channel<T>; fix break/continue C codegen
- lib/Channel.bux: add Channel_Recv_Ok<T> for use in for-in desugaring
- hir_lower.bux: Channel for-in desugars to while+recv_ok pattern
- c_backend.bux: emit 'break;' / 'continue;' with semicolon, fix missing
  semicolon when break/continue inside if-block
- bootstrap/hir_lower.nim: skip generic methods in vtable generation to
  avoid referencing non-existent monomorphized C functions
2026-06-10 13:46:06 +03:00
dimgigov 7d6cf7f511 selfhost: add lib/Drop.bux with interface Drop; extend methods visible in scope
- lib/Drop.bux: interface Drop { func Drop(self: *Self); }
- sema.bux: define TypeName_MethodName in scope for impl block methods
  so auto-drop (Lcx_BuildAutoDropFree) can find Drop implementations
  via extend Type for Drop, not just @[Drop] or standalone functions
- Verified: extend Buffer for Drop auto-calls Buffer_Drop in @[Checked]
2026-06-10 13:37:55 +03:00
dimgigov 0a41ce85f4 selfhost: add @[Drop] attribute for user-defined structs
- ast.bux: add isDrop field to Decl
- parser.bux: parse @[Drop] attribute and attach to struct Decls
- hir_lower.bux: auto-drop now looks for TypeName_Drop for any type
- Test: _test_drop_user verifies Buffer_Drop is auto-called
2026-06-10 13:32:40 +03:00
dimgigov d6f0a30948 selfhost: add *_Drop wrappers to stdlib types; auto-drop uses _Drop instead of _Free
- Array.bux, Channel.bux, Set.bux, Map.bux: add *_Drop<T> delegating to *_Free
- hir_lower.bux: Lcx_BuildAutoDropFree searches for _Drop suffix instead of _Free
- Skip direct lowering of generic functions (only monomorphized instances)
2026-06-10 13:25:11 +03:00
dimgigov a2236de69a feat(selfhost): add operator overloading support (+,-,==,[], etc.)
- Auto-register func Type_Method(self: T, ...) as methods in sema.
- Add method table lookup for binary operators in sema.bux ekBinary.
- Add method table lookup for operator_index_get in sema.bux ekIndex.
- Add HIR lowering for binary operators to method calls in hir_lower.bux.
- Add HIR lowering for operator_index_get/set in hir_lower.bux.
- Set expr.refType for overloaded operators so chained ops work.
2026-06-10 13:11:46 +03:00
dimgigov a4e410fb30 fix(selfhost): for-in with monomorphized Array/Iter types + golden test updates + ROADMAP cleanup
- Fix hir_lower.bux to recognize Array_int/Iter_string etc. in for-in loops
  by checking Array_/Iter_ prefix outside the empty-elemTypeName branch.
- Update all golden expected.c files to include duplicate bux_bounds_check
  declaration (matches actual C codegen).
- Remove duplicate Drop trait item from ROADMAP.md.
2026-06-10 12:57:53 +03:00
dimgigov 51bd3c172b Add Slice<T> generic struct support and fix C backend generic filtering
- Add lib/Slice.bux with Slice<T> generic struct
- Fix C backend to recognize Slice/Slice* as generic types
- Use var instead of let for uninitialized Slice<T> locals
- Selfhost loop passes, tests pass
2026-06-10 12:03:31 +03:00
dimgigov 3a7b4bd5c1 selfhost: extend auto-Drop to Channel<T>, Set<T>, Map<K,V>
In @[Checked] functions, variables of type Channel<T>, Set<T>, and
Map<K,V> now automatically get defer Free_T(&var) injected.

- Added Lcx_BuildAutoDropFree helper that matches typeName prefix
  and generates the appropriate Free instance:
  - Array_<T>  → Array_Free_<T>
  - Channel_<T> → Channel_Free_<T>
  - Set_<T>    → Set_Free_<T>
  - Map_<K>_<V> → Map_Free_<K>_<V>

Selfhost loop passes, C output deterministic.
2026-06-10 11:47:50 +03:00
dimgigov a099999e02 selfhost: auto-Drop for Array<T> in @[Checked] functions
In @[Checked] functions, variables of type Array<T> automatically get
a defer Array_Free_T(&var) injected at declaration site. This ensures
Array values are freed when they go out of scope, preventing leaks.

Implementation:
- HIR lowering detects Array_<T> types in skLet statements
- Generates Array_Free_T generic instance if needed
- Builds synthetic defer node: defer Array_Free_T(&var)
- Wraps let+defer in hBlock for proper statement chaining

Also adds checkedFunc flag to HirFunc and CEmitter for future use.
2026-06-10 11:40:11 +03:00
dimgigov 5eec4328f3 docs: update ROADMAP and PHASE8 with completed features
Mark as done:
- for x in collection iterator loops
- Trait bounds (T: Comparable)
- CTFE (compile-time const evaluation)
- Selfhost bootstrap loop (deterministic C output)
- Implicit generic type argument inference
2026-06-10 11:21:04 +03:00
dimgigov c7d4c87fcf selfhost: basic CTFE — compile-time const expression evaluator
Evaluate const declarations at compile time:
- Arithmetic: +, -, *, /, %
- Comparisons: <, <=, >, >=, ==, !=
- Bitwise: &, |, ^, <<, >>
- Logical: &&, ||
- Unary: -, !, ~
- Ternary: cond ? a : b
- Cast: (T)expr (evaluates operand)
- Cross-const references: const C = A + B

Uses multi-pass evaluation to handle forward references
(caused by parser push-front ordering).
2026-06-10 11:11:52 +03:00
dimgigov d70ccba5ca selfhost: implicit generic type argument inference for Array/Iter stdlib functions
- sema: add Sema_InferGenericArg + Sema_ExtractElemType helpers
- Infers T from first argument's collection type:
  - Array_Push(&arr, 10) → Array_Push_int (from &arr's Array<int> type)
  - Iter_HasNext(&it) → Iter_HasNext_int (from &it's Iter<int> type)
- Supports both explicit generic types (Array<int>) and mangled types (Array_int)
- Works with reference expressions (&x) by unwrapping to x's type
- Selfhost loop: C output IDENTICAL
2026-06-10 10:26:08 +03:00
dimgigov 01677001c3 selfhost: for x in collection works with non-identifier expressions + buxc2 build merges stdlib
- cli: buxc2 build now delegates to Cli_BuildProject for src/Main.bux,
  enabling stdlib merging (Array_Iter, Iter_HasNext, etc. available)
- sema: set expr.refType on ekCall from function return type
  (needed for for-loop type extraction from MakeArr()-style expressions)
- hir_lower: remove ekIdent restriction on collection-based for loops
  - supports arbitrary expressions: for x in MakeArr() { ... }
  - creates temp variable __tmp_coll_N for non-identifier iterators
  - generates proper Array_T struct instances for temp variables
- Test: for x in MakeArr() sums [10,20,30] → 60
- Selfhost loop: C output IDENTICAL
2026-06-10 10:20:16 +03:00
dimgigov bb84693acb selfhost: fix extend-for method linked list + trait bounds check before indirect call return
- parser: extend-for only linked first 2 methods; now uses lastMethod pointer
- sema: trait bounds checking was after indirect-call early return (tyFunc path),
  so Max<Circle>(...) skipped bounds check when callee had tekFunc refType.
  Moved bounds check before both indirect/direct call returns.
- Negative test: Circle without Comparable impl now correctly errors.
- Selfhost loop: C output IDENTICAL.
2026-06-10 09:02:22 +03:00
dimgigov f63cbd1bf0 selfhost: trait bounds parsing, sema checks, and generic monomorphization fix
- AST: add typeParam0Bound/typeParam1Bound to Decl, strValue2 to dkImpl
- Parser: parse <T: Trait> bounds, Self type in interfaces, extend-for blocks
- Sema: add interfaceTable/methodTable, Sema_CheckTraitBounds, Sema_TypeImplements
- HIR lower: two-pass decl iteration — collect generic funcs before lowering bodies
  Fixes Max<Circle>(...) not generating Max_Circle when caller precedes callee
- C backend: skip generic funcs in emission (only emit monomorphized instances)
- Array.bux: fix for-loop over monomorphized Array types
- All debug prints removed; selfhost loop passes (C output IDENTICAL)
2026-06-10 08:48:10 +03:00
dimgigov 499b389ba8 fix(selfhost): collection-based for-in with Std::Array + monomorphization fixes
- Fix Fmt_Format name conflict between lib/Fmt.bux and src/fmt.bux
  by renaming selfhost formatter function to Fmt_FormatSource.

- Fix collection-based for-in loops to handle already-monomorphized
  types like Array_int and Iter_string (typeArgCount=0 cases).

- Fix ekSizeOf and ekCast in HIR lowering to apply Lcx_SubstituteType
  during generic monomorphization, so sizeof(T) and *T casts emit
  correct concrete types in C output.

- Fix sema to infer stmt.refStmtType from initializer expression
  when no explicit type annotation is given, ensuring C backend
  emits correct pointer types for let data = ... as *T.
2026-06-10 01:15:21 +03:00
dimgigov 632fa1535c fix(test): update wrong-args error message expectation 2026-06-10 00:28:18 +03:00
dimgigov 40bcbeb710 Fix generic struct monomorphization and C output for imports
- Fix nested Lcx_GenerateStructInstance overwriting parent slot by
  incrementing structCount BEFORE field processing
- Fix Lcx_LowerModule to skip generic structs from hm.structs (was missing
  continue due to bootstrap compiler codegen limitation)
- Fix C backend to forward-declare ALL structs at top, removing second
  generic-only forward declaration section that came too late
- Add empty-name guard in CBE_EmitStructDef
- Import system: parser supports ::* glob imports, sema two-pass resolution
2026-06-09 23:33:44 +03:00
dimgigov b36df0f5b7 feat(selfhost): generic monomorphization + collection-based for-in loops
- Add on-demand generic function/struct monomorphization in HIR lower
  - Lcx_SubstituteType: substitute type params and mangle names (e.g. Array<int> -> Array_int)
  - Lcx_GenerateFuncInstance: clone generic func with active substitution
  - Lcx_GenerateStructInstance: create concrete struct definitions
  - Detect generic calls (ekCall) and struct inits (ekStructInit)

- Parser: propagate generic type args from ident to ekStructInit node

- Fix duplicate HIR constant: hIndexPtr and hCall both had value 18,
  causing index expressions to emit as comma expressions in C backend

- Implement collection-based for-in desugaring:
  for x in arr { body } -> __iter = Array_Iter_T(&arr);
                           while Iter_HasNext_T(&__iter) { x = Iter_Next_T(&__iter); body }

Selfhost loop remains deterministic. All golden tests and examples pass.
2026-06-09 22:33:36 +03:00
dimgigov b3141dbcd5 docs: update ROADMAP + PHASE8 for for-in loops
- Mark range-based for-in as done
- Note collection-based for-in blocked by generic monomorphization
2026-06-09 21:55:40 +03:00
dimgigov 74db8a5790 feat: for-in range loops in selfhost + bootstrap
- Parser: add parseRange for selfhost (.. / ..=)
- Sema: determine loop variable type from range bounds
- HIR Lower: desugar range for-in to while loop with counter
- Bootstrap sema: fix range-based for variable type (was unknown)
- Selfhost loop remains deterministic
2026-06-09 21:53:12 +03:00
dimgigov 6414ef236b docs: update ROADMAP and PHASE8 for closures with captures 2026-06-09 21:23:58 +03:00
dimgigov 9b473c667c closures with captures: env struct + global instance + body rewriting
- AST: captureCount + captureName0..7 + captureType0..7 in Expr
- Sema: Scope_LookupUpTo + closureScope for capture analysis
- HIR Lower: env struct generation, capture assignments in skLet,
  body rewriting (ekIdent -> hFieldAccess on env instance)
- C Backend: env struct def + global instance emission for closures
- Bootstrap: full capture support in sema, hir_lower, lir_lower, lir_c_backend
- Selfhost loop remains deterministic
2026-06-09 21:23:05 +03:00
dimgigov ba54aa240e docs: update ROADMAP and LanguageRef with closures
- Mark capture-less closures as ✅ Done in ROADMAP
- Add closure syntax examples to LanguageRef.md Functions section
- Update PHASE8_STRATEGY.md Milestone A with closures
2026-06-09 20:25:34 +03:00
dimgigov c83f6d5994 feat: capture-less anonymous functions (closures)
Implement MVP closures — anonymous functions without captures.

Syntax:
  |a: int, b: int| -> int { return a + b; }

Changes:
- ast.bux + ast.nim: add ekClosure AST node
- parser.bux + parser.nim: parse |params| -> Ret { body }
- sema.bux + sema.nim: type-check closure params/body, return tyFunc
- hir_lower.bux + hir_lower.nim: generate __closure_N function + hAddrOf
- lir_c_backend.nim: fix function-pointer variable declaration (cParamDecl)
- C backend: closures compile to global functions with unique names

Test: _test_closure/src/Main.bux
- Closure as variable
- Closure passed to higher-order function
- Address of named function as function pointer

Both bootstrap and selfhost compilers build and pass the test.
2026-06-09 20:24:10 +03:00
dimgigov 34504d1647 docs: sync all docs with recent features
Updated documentation to reflect changes from the last 2 days:

ROADMAP.md:
- Mark string interpolation, named/default params, bux fmt/test/new/init,
  and basic borrow checker as ✅ Done
- Update Recommended Order (next: closures)

PHASE8_STRATEGY.md:
- Update date, achievements, and milestone statuses
- Borrow checker is now ✅ working in selfhost
- CTFE, LSP, formatter, test runner marked done where applicable

LanguageRef.md:
- Add defer, switch/case, string interpolation (f"...")
- Add &T, &mut T, own T to composite types
- Add named/default parameters and operator overloading sections
- Expand @[Checked] rules with double-mut-borrow and use-after-move
- Update keywords and operators

STRATEGY.md:
- Update date and version (0.3.0 selfhost)
- Mark 8.2 borrow checker, 8.4 CTFE, 8.7 LSP as ✅

BuildAndTest.md:
- Add bux init, bux fmt, bux test commands
- Expand test sections with golden tests and Std::Test
2026-06-09 19:19:53 +03:00
dimgigov 079b76ae71 feat(selfhost): add 'bux fmt' code formatter
Line-based indentation formatter that:
- Adjusts indentation based on { } brace depth (4 spaces)
- Preserves original line structure and comments
- Skips braces inside string/char literals and // comments
- Handles } at line start and mixed brace lines
- 'bux fmt <file>' formats a single file
- 'bux fmt <dir>' formats all .bux files in directory
2026-06-09 17:48:20 +03:00
dimgigov 3ce7ba51d2 feat(selfhost): use-after-move tracking in @[Checked] functions
- Add inline movedName0..7 fields to Sema (avoids dynamic allocation issues)
- Sema_AddMoved: track variable moves from let/var init expressions
- Sema_IsMoved: check if variable was moved before use
- Sema_RemoveMoved: clear moved status on reinitialization (x = value)
- Report 'use of moved value' error for moved variable access
2026-06-09 17:40:20 +03:00
dimgigov 41c0fb1d6f feat(selfhost): double mutable borrow detection in @[Checked] functions
Detect when the same variable is passed as &mut argument twice
in a single function call (e.g. Swap(&x, &x)) inside checked functions.
Matches bootstrap sema.nim behavior (lines 1078-1089).
2026-06-09 17:32:21 +03:00
dimgigov f809827bea feat(selfhost): add &T (shared ref) and &mut T (mutable ref) type syntax
- Add tekRef and tekMutRef to TypeExpr enum (ast.bux)
- Parse &T and &mut T in parserParseType, before *T handling (parser.bux)
- Map tekRef/tekMutRef to tyPointer in HIR lowering (hir_lower.bux)
- Both emit as T* in C backend (same as raw pointer)
- Borrow checker rejects write-through-pointer in @[Checked] functions
  for all pointer types (safe default)
2026-06-09 17:30:19 +03:00
dimgigov 81281cbb11 feat(selfhost): @[Checked] borrow checker — basic write-through-ptr detection
- Add isChecked field to Decl struct (ast.bux)
- Parse @[Checked] attribute in parserParseDecl (parser.bux)
- Add checkedFunc flag and movedVars to Sema struct (sema.bux)
- Enable borrow checking per-function in Sema_Analyze
- Reject assignment through raw pointer (*T) in @[Checked] functions
- Skip newlines between @[Checked] attribute and the declaration keyword
  to avoid parser seeing the attribute and function as separate decls
2026-06-09 17:25:28 +03:00
dimgigov c14578d9dd feat(selfhost): add 'bux test' command
- 'bux test [dir]' builds the project and runs the resulting binary,
  reporting 'Tests passed' or 'Tests failed (exit code N)'.
- Builds on existing Cli_BuildProject pipeline — test code goes in
  src/ alongside production code; test assertions use lib/Test.bux.
2026-06-09 17:11:31 +03:00
dimgigov 0ac254facc feat(selfhost): add 'new' and 'init' CLI commands
- 'buxc new <name>': creates a new Bux project directory with bux.toml
  and src/Main.bux. Supports both relative names and absolute paths.
- 'buxc init': initializes a Bux project in the current directory.
- Adds extern bux_getcwd() and bux_path_parent() declarations.
- Fix mkdir return value check (bux_mkdir_if_needed returns 0 on success).
- Extract package name from path for absolute path arguments.
2026-06-09 17:09:03 +03:00
dimgigov 392dd64f97 cleanup(selfhost): remove 17 dead functions across 5 files
Remove unused helper functions, factories, accessors, and merge helpers:
- c_backend.bux: CBE_Init, CBE_ClearDefers, CBE_EmitLine, CBE_Build, CBackend_Free
- hir_lower.bux: Lcx_FreshName, Lcx_LowerType, HirLower_Free
- lexer.bux: Lexer_Init, lexIsIdentKind, Lexer_TokenCount, Lexer_GetToken
- parser.bux: parserIsBinaryOp, parserPrevious, parserMergeAddDecl,
  Parser_DiagCount, Parser_Free, Parser_MergeModules
- sema.bux: Sema_TypeName

None of these functions are referenced anywhere in src/.
2026-06-09 16:14:31 +03:00
dimgigov 90e67079f4 cleanup(selfhost): remove unused Print/PrintLine externs + dead debug comments from sema.bux 2026-06-09 15:59:57 +03:00
dimgigov 265bda850d test: expand golden C-codegen tests from 2 to 8 examples
Add golden tests for: structs, generics, algebraic_enums, enums,
methods, strings. Each test captures the expected C output from the
bootstrap compiler for regression detection.

Also remove leftover 'PARSER FIX V2 ACTIVE' debug print from parser.bux.
2026-06-09 15:58:44 +03:00
dimgigov 3ed5891de2 fix(selfhost): block scoping for if/while/loop/match bodies
- Create child scope in Sema_CheckBlock for every block, matching
  bootstrap sema.nim behavior (newScope for ekBlock).
- Fixes "var scoping bug in selfhost sema" where variables declared
  with var inside if/while blocks shared parent function scope, causing
  duplicate-definition errors between sibling if/else blocks, and C
  scoping mismatch between user variables and compiled output.
- Remove stale workaround comments from lib/Json.bux (let instead of
  var inside if blocks — no longer needed).
- Update sema.bux TODO comment for type table.
2026-06-09 15:56:16 +03:00
dimgigov 64bd41067a cleanup(selfhost): remove 24 DEBUG prints + stale parser HACK
- Remove DEBUG prints from c_backend.bux, hir_lower.bux, lexer.bux, parser.bux
- Remove HACK for stray } in parserParseFuncDecl (no longer needed after
  Decl refactor in 4a86009)
- Clean selfhost check/build output
2026-06-09 15:48:38 +03:00
dimgigov 4a860095fd fix(selfhost): resolve segfault in buxc2 compiling src/
- Replace Decl's 256 inline struct fields with dynamic fields: *StructField
  array to avoid parser field limit truncation and name shifts.
- Update parser.bux and hir_lower.bux to use decl.fields[i].
- Fix uninitialized Symbol.refType in three stack-allocated Symbol sites:
  loopSym (for-loop iterator), vSym (enum variants), and HIR param sym.
  Garbage refType values (e.g. 0xFF) were leaking into scope tables,
  later copied to expr->refType, causing SIGSEGV in Lcx_LowerExpr.
2026-06-09 15:03:45 +03:00
dimgigov 0c41c7bb25 feat(selfhost): function types (func(Params) -> Ret)
- Add tekFunc AST node and TypeExprList linked list for params
- Parse func(T, U) -> R syntax in parser.bux
- Resolve tekFunc to tyFunc in sema.bux
- Track original TypeExpr via Symbol.refType for params/lets/consts/funcs
- Build C function-pointer type names in hir_lower.bux (Ret (*)(Params))
- Lower indirect calls through function-typed values as hCallIndirect
- Add CBE_CParamDecl helper in c_backend.bux to embed name inside (*)
- Emit hCallIndirect and function-pointer variable declarations
- _test_funcptr now builds and runs with selfhost buxc2
2026-06-08 23:39:15 +03:00
dimgigov 2e536488e6 feat(bootstrap): function pointer types + C emission
- Add tekFunc AST node and parser support for func(Params) -> Ret
- Add tkFunc type resolution in sema and hir_lower
- Add &FuncName address-taking yielding tkMutRef(tkFunc)
- Fix C emission: function pointer params use Ret (*name)(Params) syntax
  via cParamDecl helper that embeds the name inside (*)
- Fix forward declarations and temp declarations for function pointers
- Add funcPtrTypes table in C backend so &Fn temps get proper type
- Add _test_funcptr integration test
2026-06-08 22:31:32 +03:00
dimgigov 3f0a3901ca feat: named and default parameters
Bootstrap compiler:
- ast.nim: add exprCallArgNames to ekCall for named arg tracking
- parser.nim: detect name: value syntax in call args
- sema.nim: add resolveCallArgs helper that injects default values
  for missing params and reorders named args into param order.
  Parser already parsed default param values; sema now uses them.

Selfhost compiler:
- ast.bux: add defaultExpr to Param, argName to ExprList
- parser.bux: parse = defaultExpr in param list, detect name: value
  syntax in call arguments
- sema.bux: add Sema_ResolveCallArgs with same logic as bootstrap

Tests:
- _test_named_params verifies defaults, named args, mixed positional+named,
  and named args with defaults in both compilers.

All verifications pass: build, selfhost-loop, test-examples, test-golden.
2026-06-08 22:02:19 +03:00
dimgigov 17c896c4dc feat: string interpolation via f"..." syntax
Bootstrap compiler:
- Add ekStringInterp AST node with text/expr parts
- Lexer: recognize f"..." prefix for interpolation strings
- Parser: split f"..." into ekStringInterp, parse inner expressions
  via sub-lexer/sub-parser. Supports escaped braces \{ and \}.
- Sema: type-check interpolated expressions, return String type
- HIR lowerer: desugar ekStringInterp to chained String_Concat
  calls with automatic type conversions:
  - int/uint types -> String_FromInt
  - float types -> String_FromFloat
  - bool -> String_FromBool
  - String -> as-is

Selfhost compiler:
- ast.bux: add ekStringInterp constant (reserved for future)
- lexer.bux: accept f" prefix, treat as plain string literal
  (selfhost parser does not implement interpolation yet)

Tests:
- _test_string_interp verifies int, float, bool, String,
  multiple interpolations, plain strings, and Fmt-style {0} templates
2026-06-08 21:48:10 +03:00
dimgigov cfce2a93e5 feat: operator overloading in bootstrap compiler
- Add operatorMethodName mapping (tkPlus -> operator_add, etc.)
- Add tryLowerOperatorCall / tryLowerIndexCall in HIR lowerer
- Modify ekBinary lowering to check method table before builtins
- Modify ekAssign lowering to detect ekIndex target and emit
  operator_index_set method call when available
- Add sema type-checking for operator overloads in ekBinary
  and ekIndex paths (method-table lookup before builtin rules)
- Fix sema compile errors: minfo.params[N].typ -> minfo.params[N]
- Fix hir_lower forward decl ordering for resolveExprType
- Update golden test expected.c files for current C backend
- Update ROADMAP.md and PHASE8_STRATEGY.md status
2026-06-08 21:31:42 +03:00
dimgigov d9aceeac6e feat: switch/case statement
- Add  syntax
- Desugars to if-else chain in HIR lowering (both compilers)
- No new HIR/C backend nodes needed — reuses hIf/hBinary/hBlock
- Supports integer, char, and enum tag dispatch
- Case body can be single statement (no braces required)
2026-06-08 21:08:55 +03:00
dimgigov a67271b08c feat: defer statement support in both compilers
- Add  statement for function-level deferred execution
- Deferred expressions run in LIFO order on function exit (return or implicit)
- Bootstrap: desugar defers in hir_lower.nim (inject before return + end of func)
- Selfhost: emit defers in c_backend.bux via CEmitter defer stack
- Both: add tkDefer token, skDefer AST node, hDefer HIR node
- Parser, lexer, sema, token files updated in both bootstrap/ and src/
2026-06-08 20:59:27 +03:00
dimgigov cf92b63ba6 fix: bootstrap parser newline skipping + nexus compile errors
- Add tkNewLine skipping in bootstrap parser parsePrimary, parseUnary, parsePostfix
- Fix nexus: req.String_Len(path) -> String_Len(req.path)
- Fix nexus: bux_sb_append_char with char literal -> bux_sb_append with string
2026-06-08 20:28:37 +03:00
dimgigov 9c3d6dc723 fix: EVP_SignFinal unsigned int* type mismatch in OpenSSL calls 2026-06-08 20:24:47 +03:00
dimgigov 7d1d722cba fix: String_IsNull/String_Offset helpers + remove pointer-to-int casts
- Add String_IsNull and String_Offset wrappers in lib/String.bux
- Add bux_str_is_null and bux_str_offset runtime functions in rt/runtime.c
- Update String_Replace to use String_IsNull instead of String_Len(pos)==0
- Replace pointer-to-uint casts (as uint == 0, pointer arithmetic) across apps/
- Parser newline skipping fixes in src/parser.bux
2026-06-08 20:23:30 +03:00
dimgigov 3c7938163c fix(runtime): detach StringBuilder buffer on build to prevent use-after-free
bux_sb_build returned sb->buf and then bux_sb_free freed it,
causing dangling pointers in all callers of StringBuilder_Build
followed by StringBuilder_Free (e.g. JsonParser_ParseString, Fmt).

Fix: bux_sb_build now detaches the buffer (sets sb->buf = NULL)
before returning it, so bux_sb_free only frees the sb struct.
This transfers buffer ownership to the caller.
2026-06-08 20:10:30 +03:00
dimgigov c4e3f80405 fix(selfhost/c_backend): handle backtick raw string literals
Backtick strings were emitted directly into C code without
stripping the backticks or escaping the content, causing C syntax errors.

Fix: detect backtick-wrapped literals in CBE_EmitExpr, strip
the backticks, escape inner content, and wrap in double quotes.
2026-06-08 20:03:33 +03:00
dimgigov d253a01aa9 fix(selfhost/c_backend): emit _Tag + struct wrapper for all enums
Simple enums were emitted as plain C enums, but the rest of the codegen
(and source code) expected them to have a .tag field like algebraic enums.
This caused C compilation errors:
- 'request for member tag in something not a structure or union'
- 'field name not in record or union initializer'

Fix: always emit the _Tag typedef + struct wrapper for every enum.
For simple enums, the struct only contains the tag (no _Data union).
For algebraic enums, keep the existing _Data union + struct behavior.

This matches the bootstrap compiler's enum codegen.
2026-06-08 20:00:58 +03:00
dimgigov 2cb971a483 fix(selfhost/parser): skip newlines inside expressions
The selfhost parser did not skip tkNewLine tokens inside expression parsing,
causing multi-line expressions (e.g. if conditions spanning lines with ||)
to be truncated. When parserParseBinaryPrec hit a newline it treated it as
an invalid primary, returning a malformed literal and leaving p.pos at the
newline. parserParseBlock then failed to find '{' and its depth-counter
fallback consumed far too many tokens, causing subsequent function bodies
to be parsed into the wrong AST nodes.

Fix: add newline skipping in parserParsePrimary, parserParseUnary, and
parserParseBinaryPrec, matching the bootstrap parser's skipNewlines() calls
in parseAnd/parseOr.

Also complete the variant cap raise from 8->9 in src/sema.bux (was already
done in ast.bux, parser.bux, hir_lower.bux).
2026-06-08 19:45:05 +03:00
dimgigov b1deff7fd5 fix(selfhost/parser): skip newlines inside multi-import brace blocks
parserParseImportDecl now skips tkNewLine tokens inside {..} blocks,
matching the bootstrap parser behavior. This fixes parsing of imports
with names on separate lines, e.g.:

  import Std::String::{
      String_Eq,
      String_Len
  };

Previously the parser failed because it expected tkIdent immediately
after { but encountered tkNewLine instead.
2026-06-08 18:56:43 +03:00
dimgigov 38bc469be7 fix(bootstrap): resolve algebraic enum _Data union field types in HIR lowering
hir_lower.resolveExprType for ekField now correctly resolves variant
positional/named fields (e.g., r.data.Ok_0, r.data.Err_0) on _Data
union types, matching the existing logic in sema.checkExpr.

This fixes the runtime segfault in examples/algebraic_enums.bux where
the C backend emitted an int temporary for a String field, causing
PrintLine to dereference a garbage pointer.
2026-06-08 18:48:30 +03:00
dimgigov bebc362ae6 fix(bootstrap): simple enum codegen, crypto parser compatibility, import ordering
- Fix bootstrap sema to type simple enum variants as the enum itself
  (not _Tag), and .tag access returns the enum type.
- Fix hir_lower to lower simple enum .tag as no-op and Enum{tag:X}
  init as X directly.
- Fix sema collectGlobals to register imports AFTER real declarations,
  preventing duplicate-symbol errors when stdlib files import symbols
  defined in later files (e.g. jwt.bux importing rsa.bux).
- Rewrite lib/crypto/*.bux as single-line to work around bootstrap
  parser limitations with multi-line function calls.
- Rename 'pub' -> 'pubBuf' in ed25519.bux and jwt-pitbul/Main.bux
  to avoid reserved keyword collision.
- Remove algTag:int workaround from jwt-pitbul/Main.bux; enum
  comparisons now type-check without manual casts.
- Update .gitignore to exclude _test_*/ and backup files.
- Delete accidentally-committed _test_array/ directory.
2026-06-08 18:43:26 +03:00
dimgigov a7a1b45588 chore: add MIT license 2026-06-08 14:44:05 +03:00
dimgigov a13cee8a0f feat(simpledb): file-backed key-value database with CLI
- Add SimpleDB: plain-text key=value store with get/set/del/has/keys/count
- Fix lib/Fmt.bux: replace *(ptr+N) pointer arithmetic with ptr[N] indexing
- Fix lib/crypto/jwt.bux: use alg.tag directly instead of int-comparison
2026-06-08 12:26:24 +03:00
dimgigov 3b7fc455b0 fix(parser): infinite loop on newlines in multi-import, multi-line params, type args, struct patterns
Parser would hang (infinite loop) when encountering newline tokens
inside certain constructs because expect() returns without advancing
position when the expected token doesn't match.

Fixed 5 places in parseBaseType, parsePrimaryPattern, parseTypeParams,
parseParamList, and parseUseDecl by adding newline-skipping at the
start of each iteration.

Verified: compiler no longer hangs/crashes on all 3 real-world apps
from apps/ (boko-framework, jwt-pitbul, nexus).
2026-06-07 23:02:43 +03:00
dimgigov e7e900973f feat: crypto library, Nexus HTTP server, JWT CLI, Boko web framework
- lib/crypto/: 9-module crypto library (Hash, HMAC, Base64/URL, Random, AES, RSA, ECDSA, Ed25519, JWT)
- rt/runtime.c: +346 lines OpenSSL crypto primitives (SHA-1/384/512, HMAC, Base64URL, AES-CBC/GCM, RSA, ECDSA, Ed25519)
- apps/nexus/: multi-threaded HTTP/1.1 + HTTP/2 detect + WebSocket server
- apps/jwt-pitbul/: JWT CLI tool (sign, verify, decode, keygen)
- apps/boko-framework/: FastAPI-inspired async web framework
- test_crypto/: crypto library test suite (23 tests)
2026-06-07 22:15:00 +03:00
dimgigov a2617e9954 feat: VS Code extension, web playground, LSP server 2026-06-07 18:34:41 +03:00
dimgigov 3ffa9f7d54 feat: web playground + LSP server + docs update 2026-06-07 18:29:05 +03:00
dimgigov b3af1208e8 feat(lsp): add LSP server with completion, definition, hover, diagnostics 2026-06-07 18:20:35 +03:00
dimgigov 0d7a30835f feat: borrow expr, parser fix, borrow tests, borrow example 2026-06-07 18:09:40 +03:00
dimgigov adca52b269 docs: update README v0.4.0, update stdlib docs to 23 modules
- README: bump version to v0.4.0, add selfhost loop & borrow/shared
- Stdlib.md: update sections 1-4, add String_Chars, FromBool, Fmt, Iter
- BuildAndTest.md: add make selfhost-loop and make test-golden targets
- Standard library list updated to all 23 modules
2026-06-07 18:08:34 +03:00
dimgigov 04be9eb400 feat(stdlib): add String_Chars, String_FromBool, fix Fmt and Net
- String.bux: add String_Chars(s, index) for char-at-index access
- String.bux: add String_FromBool(b) conversion
- Fmt.bux: rewrite with correct stdlib imports (was using non-existent names)
- Net.bux: fix String_Len -> bux_strlen (String_Len not imported)
- All lib modules compile successfully
2026-06-07 18:05:04 +03:00
dimgigov bfe87a8acb feat: add borrow test example, fix borrow &mut parsing order
- examples/borrow.bux: working borrow expression example
- tests/borrow_test.nim: add 4 new tests for borrow & @[Shared]
- parser.nim: fix borrow parsing order (& before mut)
- Build verified: example compiles and runs
2026-06-07 17:50:27 +03:00
dimgigov 46814b2abc feat: selfhost-loop determinism, golden tests, sema diagnostics 2026-06-07 17:37:22 +03:00
dimgigov 9758b17b1a fix(parser): add stray } workaround in parserParseFuncDecl, enable selfhost build
This workaround consumes a stray } that parserParseBlock sometimes leaves
behind, which was causing the module handler to exit early. With this fix,
the selfhost compiler (buxc2) can now compile the entire src/ project.

- buxc2 project build: 491 user + 310 stdlib = 801 decls, no sema errors
- make selfhost-loop: builds and runs both passes
- C compilation succeeds, resulting binary works
2026-06-07 17:33:17 +03:00
dimgigov 8347599d23 fix(parser): save/restore + depth counter for reliable } consumption 2026-06-07 17:25:30 +03:00
dimgigov 4794335673 chore: clean up experimental changes, keep core parser improvements 2026-06-07 17:11:45 +03:00
dimgigov 134e8e877d fix(parser): depth counter in module handler, stray } cleanup, token count debug 2026-06-07 17:06:36 +03:00
dimgigov 88af8b09d4 fix(parser): improve parserParseBlock infinite-loop safeguard for stuck at } 2026-06-07 17:01:15 +03:00
dimgigov e41a8d31df fix(parser): use parserExpect for module closing brace 2026-06-07 16:43:14 +03:00
dimgigov a11071ab95 fix(parser): skip newlines before checking decl kind 2026-06-07 16:38:42 +03:00
dimgigov 093e08a2b9 chore(cli): remove diagnostic scan, keep FIFO merge and per-file counts 2026-06-07 16:25:23 +03:00