3.4 KiB

Jai Developer Agent Guidelines

These guidelines apply to any agent working with the Jai programming language.

1. Syntax & Core Idioms

  • Declarations: Use := for type inference, : Type = for explicit types, and :: for compile-time constants (functions, structs, constants).
  • Procedures: Declare procedures as name :: (params) -> return_type { ... }. Use #expand for macros that compile into the caller's scope and access caller variables using backticks (e.g., `x).
  • Memory Management: Jai does not have RAII or garbage collection. Memory is managed manually, typically using defer to clean up resources right after allocation:
    data := alloc(size);
    defer free(data);
    
  • Context Allocators: Jai uses an implicit context parameter containing the current allocator (context.allocator).
    • Use context.allocator = temp_allocator; for temporary/arena allocations that don't need manual freeing (cleared at the end of the frame/loop iteration via reset_temporary_storage()).
    • When writing reusable libraries or procedures, accept an optional allocator parameter or use context.allocator by default.

2. Standard Libraries & Imports

  • Anonymous Imports: Use #import "Basic"; anonymously to bring standard utilities like print, alloc, free, tprint directly into the scope.
  • Named Imports: Use named imports String :: #import "String"; to namespace helper libraries, which keeps the scope clean. Note that operator overloads do not automatically propagate through namespaces.
  • No Package Manager: Since Jai does not have a package manager, vendor any external libraries directly into the project's modules/ folder or implement them yourself.

3. Platform Bindings & Win32 API

  • Windows Bindings: The standard Windows module (#import "Windows";) provides native bindings to Win32 APIs.
  • Wide Strings: Many Windows APIs require wide UTF-16 strings (e.g., LPCWSTR). Use helper utilities to convert Jai UTF-8 strings (string) to UTF-16 wide strings when calling Windows APIs (e.g. using utf8_to_wide or similar functions in the runtime or writing a custom converter using MultiByteToWideChar).
  • Callback Conventions: When defining callbacks for Win32 API (such as Window Procedures or Thread Procedures), you must mark the procedure with #c_call calling convention and usually #no_context to prevent context mismatches when called from OS threads:
    window_proc :: (hwnd: HWND, msg: u32, wparam: WPARAM, lparam: LPARAM) -> LRESULT #c_call {
        // If context is needed inside the callback, re-push it:
        ctx: Context; // or get from global/user data
        push_context ctx {
            // Jai code here
        }
    }
    

4. Code Quality & Compilation

  • No Compiler Warnings: Always ensure the code compiles without warnings or errors.
  • Compile-Time Execution: Utilize #run blocks to execute code at compile-time for code generation, building lookups, or validating configurations.
  • Linting & Safety: Avoid using uninitialized variables unless performance-critical (explicitly mark as --- if needed).

5. Process Management Warning (VPN Connectivity)

  • CRITICAL WARNING: Do NOT kill, terminate, or stop the sing-box or singbox_tray processes during runtime unless explicitly instructed by the user. The agent's own network connection and container/sandbox internet access might be routed through this active VPN. Killing it will sever the agent's connection.