# Tungsten: full agent reference > The Native Language of Agents. > Models write pseudocode. Tungsten runs it. This document is the comprehensive web-oriented context file for AI coding agents. For a shorter, example-first primer use: https://tungsten-lang.org/llms.txt Canonical source: https://github.com/tungsten-lang/tungsten Documentation: https://github.com/tungsten-lang/tungsten/tree/main/doc Specification: https://tungsten-lang.org/spec Status: public preview, version 2026.07.04 Targets: macOS and Linux; Windows through WSL2 File extension: `.w` ## 1. Language identity Tungsten is an indentation-based, object-oriented, multi-paradigm language with compact notation, a dynamic everyday surface, gradual native type annotations, monomorphized generics, exact domain values, and a self-hosted compiler. Ordinary compiled code follows this path: ```text Tungsten source -> lexer / parser / AST -> WIRE -> LLVM IR -> clang -> native binary ``` Typed `@gpu fn` definitions take a separate path through a multi-dialect GPU emitter: Metal Shading Language is always emitted when kernels are present, CUDA C by default, and WGSL when `TUNGSTEN_GPU_DIALECTS` includes it (e.g. `TUNGSTEN_GPU_DIALECTS=cuda,wgsl`). The GPU subset is intentionally smaller than the CPU language. The build creates a stage-one compiler and uses it to create stage two. It requires the stages to emit byte-identical LLVM IR. This is a compiler fixed-point invariant, not a proof that every compiled program is correct. ## 2. Install and orient One-line install: ```sh curl -fsSL https://tungsten-lang.org/install | sh tungsten start --agent ``` Fresh source checkout: ```sh git clone https://github.com/tungsten-lang/tungsten cd tungsten bin/tungsten bootstrap bin/tungsten start --agent ``` Run, check, inspect, and compile: ```sh bin/tungsten file.w bin/tungsten -e '<< 1 + 1' bin/tungsten -c file.w bin/tungsten --lex file.w bin/tungsten --ast file.w bin/tungsten --ll file.w bin/tungsten -o app file.w ./app ``` The quick-run path is useful for ordinary code and short feedback loops. Prefer native compilation for maximum performance, `@gpu fn`, and concurrency edge cases. Preview-era quick-run and compiled behavior are not identical in every feature. ## 3. Lexical shape - Indent with 2 spaces. - Dedent closes a block. - Identifiers are snake_case: uppercase ASCII is not valid inside an identifier (`myVar` is a lexical error — write `my_var`). PascalCase is class references; SCREAMING_SNAKE is constants. A call requires a space or a left paren after the callee. - There are no braces, block-closing `end` keywords, or required semicolons. - `#` begins a comment except where the lexer recognizes a richer literal such as a color. - Variables are created by assignment. - The last expression is the default return value. - Method calls may omit parentheses where unambiguous. - Both ASCII and selected mathematical Unicode notation are available: `π` and `τ` are bare constants, superscript powers apply to any value (`π²`, `π⁴`, `x⁷`), and `√`, `Δ`, `·`, and `∑`-style forms appear where the relevant chapters document them. - Single-quoted strings are literal; only double-quoted strings interpolate `[expr]`. ```tungsten # assignment and output name = "Tungsten" answer = 6 * 7 << "[name]: [answer]" # suffix condition << "positive" if answer > 0 ``` ### WValue: the compiler and runtime word `WValue` is Tungsten's 64-bit dynamic value representation: ```c typedef uint64_t WValue; ``` Ordinary dynamic values, runtime objects, lexical records, source locations, and packed AST references can cross the compiler/runtime boundary in one word. The high tag partitions the space: ```text 0x0000 nil, false, true, sentinels, and tagged heap pointers 0x0001..0xFFF8 biased IEEE-754 Float values 0xFFF9 String and Symbol 0xFFFA inline signed Integer; larger values promote 0xFFFB Instant 0xFFFC Token, LexChar, Slice, and Char 0xFFFD Decimal, Currency, and Quantity 0xFFFE packed values including AST Node, Rational, Date, IPv4, and Location 0xFFFF Duration ``` Only `nil` and `false` are falsy. A typed raw `i64` or `f64` is not a `WValue`; lowering boxes it when it crosses a dynamic call, collection, method-dispatch, or return boundary. Conversely, `w64` means an opaque slot containing a complete `WValue`, not an ordinary signed integer. When editing runtime or FFI code: - accept and return `WValue` at dynamic ABI boundaries; - use the `w_box_*`, `w_unbox_*`, and `w_is_*` helpers instead of duplicating masks; - do not box a helper result that is already a complete `WValue`; - in compiler internals, use `ccall_nobox` only when the C result is already tagged or is deliberately a raw machine value. The compiler accepts an exact raw-word literal for tests and low-level work: ```tungsten u0xFFFA00000000002A ``` It must contain exactly 16 hexadecimal digits. Treat this as an internal escape hatch, not an application-level serialization format. In `tungsten console`, `? expression` shows the value's runtime type, `u0x` word, binary form, and decoded fields. For exact encodings, prefer the current implementation: https://github.com/tungsten-lang/tungsten/blob/main/runtime/wvalue.h The design and value-space rationale are documented at: https://github.com/tungsten-lang/tungsten/blob/main/doc/specification/wvalue_encoding.md ### LexChar: classified Unicode input The lexer does not repeatedly ask whether each source character is a digit, identifier character, quote, or operator. `String#lchs` converts UTF-8 source into a typed array of classified characters: ```tungsten # Inside a compiler or lexer target: chars64 = source.lchs("tungsten") # i64[] LexChar values chars32 = source.lchs("tungsten", bits: 32) # u32[] compact form chars16 = source.lchs("json", bits: 16) # u16[] ASCII-hot form ``` `lchs` is a compiler/lexer intrinsic, not an ordinary application method. Native targets using it must link the generated LexChar tables (`runtime/lexchar_tables.c`); compiler and language-tool builds do this. The canonical 64-bit `LexChar` is a `0xFFFC` WValue with lexical subtype 01. It carries: ```text 21-bit Unicode codepoint 2-bit UTF-8 length minus one 5-bit Unicode category 4-bit digit value low classification flags ``` The low flags make hot tests simple masks: identifier start/continuation, whitespace, hexadecimal digit, operator, quote, and combination behavior. Language-specific tables specialize those flags. Tungsten, C, Ruby, and JSON tables live under `languages/`; their lexer implementations show complete scanners over Lex64, Lex32, and Lex16 layouts. The 16-bit form keeps an ASCII codepoint in its high byte and uses a non-ASCII placeholder when only classification is needed. Recover the actual text from the source using the token span; do not pretend the placeholder is the original codepoint. ### LexToken / Token: zero-copy source spans “LexToken” is a useful conceptual name. In the current source, search for `Token` and `W_LEXICAL_TOKEN`: the runtime subtype is Token, and the source class is `core/token.w`. A packed Token contains no copied lexeme: ```text bits 45..38 token type id bits 37..26 span length bits 25..2 source offset bit 0 first non-whitespace token on its line ``` The token type table includes broad scanner classes and parser-ready refinements: identifiers, class names, constants, literals, structural indentation, punctuation, operators, rich literal forms, superscripts, `√`, and more. `core/token.w` is the authoritative type-id map. The fast scanner first emits broad packed tokens. Materialization then refines their type and fills a parallel values array with decoded data where needed. The parser can compare a keyword or operator against the original source without copying every lexeme. Current compiler offsets and lengths index the source's Unicode codepoint array, not raw UTF-8 bytes. Parser comparisons therefore use the lexer-built character array. A raw byte slice becomes misaligned after a multibyte character. The canonical Token is a tagged `WValue`. For speed, the compiler's hot `i64[]` token stream strips the high `0xFFFC` tag and carries the complete low 46-bit payload as an inline integer. Parser hot paths shift and mask that payload directly. Do not rebox every token or dynamically dispatch Token methods inside that path. ### Indentation, spaces, and parser decisions Tungsten's lexer makes syntax-relevant whitespace explicit: - line-leading whitespace becomes `INDENT` and `DEDENT`; - mid-line spaces become `SP`; - line breaks become `NEWLINE` outside grouping delimiters; - blank and comment-only lines do not create extra statements; - `#` starts a comment, but `##` starts a type annotation and `#FF0000` can be a Color literal; - the parser skips `SP` tokens while remembering whether a space preceded the current token. That remembered space distinguishes otherwise similar forms. Important examples: ```tungsten n / 2 # arithmetic division list/sq:sum # map sq, then reduce by sum foo(x) # tight call foo (x) # space is visible to parser disambiguation ``` Identifier shape is lexical: ```text snake_case ordinary identifier Point PascalCase class reference HTTP_SERVER assignable SCREAMING_SNAKE constant WIT_keys class reference, not an assignable variable ``` Use spaces for indentation. Although tabs are scanned, mixing indentation styles makes structural tokens difficult to reason about. ### Parser, AST, and source locations The parser is recursive descent over the packed token and value arrays. Its output is already normalized in places, so the AST need not mirror the surface spelling exactly. For example: ```tungsten items -> << x² ``` parses as an `each` call with a block, and `x²` becomes a `POW` binary operation. Pipeline notation similarly becomes `map` and `calc` nodes. AST constructors return packed `W_PACKED_NODE` WValues backed by size-classed node arenas. Fields live in schema slots; selected leaf payloads live directly in the node word; uncommon metadata uses a sparse side table. Compiler passes should use: ```tungsten ast_kind(node) ast_get(node, :field) ast_set(node, :field, value) ast_children(node) is_ast_node?(value) ``` Do not assume an AST node is a Hash. Small typed-value and metadata records may still be Hashes, which is why the accessors support both shapes. Source locations are packed `W_PACKED_LOCATION` values. Per-file line and column tables turn a codepoint offset into `node.line`, `node.col`, `node.end_line`, `node.end_col`, and `node.span_length`. Preserve locations when constructing or rewriting nodes so diagnostics remain useful. ### Lexing and parsing workflow for agents ```sh tungsten --lex file.w # type-id and raw token value tungsten --ast file.w # normalized parser tree tungsten -c file.w # check without running tungsten --wire file.w # inspect post-AST WIRE tungsten --explain E_PARSE_UNEXPECTED_TOKEN ``` Use `--lex` first for unexpected characters, rich-literal boundaries, indentation, or spacing ambiguity. Token ids come from `core/token.w`. Use `--ast` when tokens are correct but precedence, block attachment, implicit `each`, pipelines, or desugaring look wrong. Compile errors expose `code`, `message`, `file`, `row`, `col`, and `span_length`. For repair loops, keep the stable error code and source span; do not scrape the decorative human rendering. Canonical implementation: - https://github.com/tungsten-lang/tungsten/blob/main/compiler/lib/lexer.w - https://github.com/tungsten-lang/tungsten/blob/main/core/token.w - https://github.com/tungsten-lang/tungsten/blob/main/compiler/lib/parser.w - https://github.com/tungsten-lang/tungsten/blob/main/compiler/lib/ast.w - https://github.com/tungsten-lang/tungsten/blob/main/doc/specification/03_grammar.md ## 4. Methods, pure functions, and lambdas `->` defines methods and lambdas. `fn` defines a pure, auto-memoized compiled function. ```tungsten -> greet(name) "hello [name]" -> add/2 @1 + @2 double = ->(x) x * 2 << double.call(21) fn fib(n) if n <= 1 n else fib(n - 1) + fib(n - 2) ``` Typed signatures put parameter types after the argument list, followed by an optional return type: ```tungsten -> add(a, b) (i64 i64) i64 a + b -> dot(xs, ys, n) (f64[] f64[] i64) f64 total = ~0.0 ## f64 i = 0 ## i64 while i < n total += xs[i] * ys[i] i += 1 total ``` Common machine types include `i64`, `u64`, `i32`, `u8`, `f64`, `f32`, and `bool`; append `[]` for typed arrays. Use explicit types in hot loops and at FFI/GPU boundaries. ## 5. Blocks and collections ```tungsten values = [1, 2, 3, 4, 5] values.each ->(x) << x doubled = values.map ->(x) x * 2 large = values.select ->(x) x > 3 total = values.reduce(0, ->(a, b) a + b) record = {name: "Ada", role: "agent"} << record[:name] << record.keys ``` `value ->` is implicit `each`: an Integer yields `0...value`, a Range yields its elements, a collection yields each element. In a bare `->` block, undeclared lowercase names bind to the yielded arguments in first-reference order (`(1..n) -> total += 1.0 / (k * k)`); names bound outside are captures. `@1`/`@2` are METHOD argument references, not block argument references. Core collection shapes include `Array`, `Hash`, `Tuple`, `Range`, `ByteArray`, `BoolArray`, typed arrays, `SmallArray`, and `StringBuffer`. `Enumerable` supplies map/select/reduce-style behavior to compatible classes. ## 6. Control flow and errors ```tungsten if score >= 90 grade = "A" elsif score >= 80 grade = "B" else grade = "C" while work? step() case value when 1 << "one" when 2, 3 << "two or three" else << "other" begin risky_operation() rescue error << "failed: [error]" ensure cleanup() ``` Errors inherit from `Error`; common subclasses include `ArgumentError`, `RangeError`, and `TypeError`. ## 7. Classes, traits, and objects `+` defines a class. Constructor arguments beginning with `@` bind directly to instance fields. A trailing `ro` or `rw` generates read-only or read-write accessors. ```tungsten + Point -> new(@x, @y, @z) ro -> distance/1 dx = x - x' dy = y - y' dz = z - z' √(dx² + dy² + dz²) origin = Point(0, 0, 0) << Point(3, 4, 0).distance(origin) ``` Inheritance and traits: ```tungsten trait Named -> label self.name + Person is Named -> new(@name) rw + Researcher < Person -> field "mathematics" ``` Tungsten is object-oriented throughout, including its numeric tower and operator dispatch. ## 8. Strings, symbols, and text ```tungsten name = "model" << "hello [name]" << "2 + 2 = [2 + 2]" kind = :agent buffer = StringBuffer() buffer.append("compact") buffer.append(" source") << buffer.to_s ``` `String` is UTF-8. `Char` represents Unicode scalar values. `Regex`, `Base64`, JSON codecs, digests, and mutable string buffers are available in core. ## 9. Rich literals Tungsten recognizes many domain values in the lexer so agents can express the value directly instead of emitting a string plus a parsing constructor. ```tungsten # exact and approximate numbers 42 # Integer 0xFF # Integer, hexadecimal 0b1010 # Integer, binary 0.1 # exact Decimal 6.626_070_15e-34 # scientific notation; _ groups digits ~0.1 # binary Float 3/4 # exact Rational # money and rates $499.99 # Currency 25¢ # Currency 15% # percentage # time 5m30s # Duration # identifiers and networks 10.0.0.0/8 # IPv4 with CIDR 2001:db8::1 # IPv6; lowercase input # colors, characters, bytes, and ranges #FF0000 # Color U+1F600 # Char: 😀 « ff 00 a5 » # ByteArray 1..10 # inclusive Range 1...10 # end-exclusive Range # compact array literals (whitespace-separated, no commas) %w[alpha beta gamma] # Array of Strings %i[read write execute] # Array of Symbols %d[1.0 2.5 3.75] # Array of exact Decimals %f64[1.5 2.5 4.0] # typed f64 buffer (raw floats) %f32[1.5 2.5] # typed f32 buffer ``` Representative arithmetic: ```tungsten << 0.1 + 0.2 # 0.3 << 3/4 + 1/4 # 1/1 << $499.99 - 15% # ≈$424.99 << $3.50 - 25¢ # $3.25 ``` The language surface also defines direct Date, Time, DateTime, and UUID literals: ```tungsten 2026-07-04 12:30:00 2026-07-04T12:30:00Z 550e8400-e29b-41d4-a716-446655440000 ``` All of these evaluate on both the quick-run and native engine paths. Dates format with `d.strftime("%Y/%m/%d")` using the standard directive set; `d.to_s(fmt)` is its alias, and bare `d.to_s` is the canonical ISO form. Date arithmetic works with ints (days), durations, and time-dimensioned quantities, in either operand order: `d + 210`, `d + 210 days`, `d - 30 days`, `d + 1mo` (calendar months, day-clamped), and datetime `+ 2h`. `"42.50".to_d` parses a String into an exact Decimal (`to_d` is identity on Decimals and exact on Integers; unparseable strings yield Decimal `0`). Equality follows exactness. Integer, Rational, and Decimal are all exact, so `==` compares them by mathematical value — `2.0 == 2`, `1/2 == 0.5`, `4/2 == 2`, and `10**20 == 1.0e20` are `true` (comparison is exact at any magnitude; nothing rounds through a double), and hash keys agree: `{2 => v}[2.0]` and `{0.5 => v}[1/2]` hit. Binary Floats are approximations, so they equal only other Float *values*: with `f = ~2.0` and `d = 2.0`, `f == d` is `false`, even though ordering still crosses the boundary (`~2.0 < 3` works). Numeric *literals* adapt (Odin-style untyped constants, gated on exactness): an int or decimal literal written directly in a comparison takes the Float side's type iff its value is exactly representable as a double. `~x == 0`, `~x == 0.5`, `~x == 2.0`, and `case ~x when 2` all work; `~x == 0.3` stays `false` because 0.3 has no exact double (2^53 adapts, 2^53 + 1 does not). Values that flowed through variables never adapt — convert explicitly (`.to_f`, `.to_d`) or use `≈`. For approximate comparison use the `≈` operator (equality precedence): every numeric coerces through one double path and passes within `|a-b| ≤ 1e-12 · max(1, |a|, |b|)` — relative above magnitude 1, absolute below it. `~0.1 + ~0.2 ≈ ~0.3` and `~2.0 ≈ 2` are `true`; `0.99971 ≈ 1` fails. Quantities convert units first (`1 km ≈ 1000 m` is `true`; a dimension mismatch is `false`, not an error). `%d[…]` is a plain Array of exact Decimals. `%f64[…]` / `%f32[…]` build real typed float buffers — the storage `f64[n]` allocates — ready for the elementwise `.+ .- .* ./` operators and numeric kernels; compiled code fills the buffer directly with no boxed intermediate. Array statistics `mean`, `variance` (Bessel-corrected), `stdev`, `median`, and `norm` (L2) work on all of these. ## 10. Units, quantities, and measurements Quantities carry dimensions through arithmetic and conversions. ```tungsten c = 299_792_458 m/s m = 1 kg planck = 6.626_070_15e-34 J·s # scientific notation + compound unit # (naming a local `h`/`m`/`s` shadows that # unit spelling in later bare pipe targets — # quote the target (`| "m"`) if you must) << m·c² # ≈8.988×10¹⁶ J << 3 ft + 12 in # 4 ft << 10 ft * 10 ft # 100 ft² << 1 cm * 1 cm * 1 cm # 1 cm³ << 9.8 m/s² * 2 s # 19.6 m/s << 1 acre | sqft # 43560 sqft << 6 ft + 2 in | cm(2) # 187.96 cm << 5 m/s | km/h # 18 km/h << 1 J | eV(3) # 6.242×10¹⁸ eV << 1 Jy | W/m²/Hz # 1e-26 W/m²/Hz << 2 m + 2 lbs # dimension mismatch ``` The conversion-pipe target is a bare unit spelling in any registry form: simple (`km`), mixed-case (`eV`, `mmHg`, `kWh`), compound with `/` and `·` (`km/h`, `W/m²/Hz`, `kg·m/s`), and superscripted (`W/m²`); `(N)` rounds the converted value to N digits. Quote the spelling only when the grammar cannot carry it bare — multi-word names (`"metric cup"`) and negative superscripts (`"cm⁻¹"`). A target component shadowed by a local variable or function keeps its expression meaning, and integer `x | y` remains bitwise-or. Conversion pipes also work inside string interpolation, the idiomatic formatting position: `"[speed | km/h(1)]"`. A quantity divided down to dimensionless (`q / (1 m)`) passes directly into `(f64)`-typed native signatures. A pipe on a bare number *attaches* the unit (`2.5 | km` → `2.5 km`), and a pipe on an array maps elementwise — decimals/ints attach, quantities convert — pairing with `%d[…]` for measurement series: ```tungsten samples = %d[1.0 2.5 4.0] | m/s # [1 m/s, 2.5 m/s, 4 m/s] << samples | km/h # [3.6 km/h, 9 km/h, 14.4 km/h] << samples.mean # 2.5 m/s << samples.stdev # sample σ in m/s ``` The Array statistics (`mean`, `variance`, `stdev`, `median`) are quantity-aware: `mean`/`median` keep the element unit, `variance` carries the squared unit, `stdev` converts elements to the first element's unit before taking σ. Quantities order across units (`1 km > 900 m` is `true`, and `<=>` works for sorting), and `q.value` / `q.unit_name` / `q.to_f` give a quantity's exact Decimal value, registry spelling, and evaluated Float. A number written against `π` (`2π`, `0.5π`, `1000000π`) is a **π-quantity**: an exact decimal multiple of π carried through the same unit machinery. ```tungsten << Math.sin(2π) # 0 — exactly << Math.sin(1000000π) # 0 — exactly, no drift at any magnitude << Math.cos(0.5π) # 0; sin(0.5π) is exactly 1 << 2π * 50 # 100 π — scalar scaling stays exact << 2π + 1 # 7.2831853071795862 — collapses to Float ``` Scaling a π-quantity by scalars keeps it exact, and `Math.sin` / `cos` / `tan` reduce the exact multiple mod 2 *before* any floating-point rounding, so whole and quarter turns are exact at any magnitude and `Math.sin(2π * f * t)` phases never drift. Evaluation boundaries — mixing with plain numbers, order comparisons, `.to_f`, other `Math.*` calls — collapse it to an imprecise Float. Bare `π` alone is a plain decimal constant. Undefined bare names in products are symbolic: `2x + 3x` is `5 x` (a 1·`x` unit factor per term), and at script level the explicit star agrees — `2 * x` is the same factor as `2x`. Defined variables keep ordinary multiplication. Core also includes `Measurement` for a scalar plus standard uncertainty and `Calibration` for polynomial measurement models with propagated uncertainty. ## 11. Types, generics, and numeric performance The everyday language is dynamically flavored. `##` annotations provide machine types and typed storage where representation and speed matter. Generics are monomorphized in compiled code. ```tungsten z = Complex.new([~3.0, ~4.0]) << z.abs # 5 m = Matrix.identity(3) v = Vec3.new([~1.0, ~2.0, ~3.0] ## f64[3]) ``` Untyped integers promote to exact big integers rather than silently overflowing. For tight loops, declare raw machine integers and floats. The numeric tower includes: - exact integers with `BigInt` promotion; - exact `Decimal`, `BigDecimal`, and decimal32/64/128 classes; - `Float16`, `Float32`, `Float64`, `Float80`, `Float128`, and `Float256` surfaces; - exact reduced `Rational` values; - interval arithmetic; - generic complex, quaternion, octonion, sedenion, and higher Cayley-Dickson algebras; - fixed and generic vectors and matrices; - dense `Tensor`, `SparseMatrix`, linear algebra, FFT, and special functions. Not every numeric class has the same degree of native/runtime maturity. Check the current core reference and tests before relying on an uncommon type. Core reference: https://github.com/tungsten-lang/tungsten/blob/main/doc/CORE.md ## 12. Scientific computing `Math` provides the native transcendental kernels on both engines: `exp`, `log`, `log2`, `log10`, `log_base`, `sqrt`, `cbrt`, `hypot`, `atan2`, the trig family with inverses, `sinh`/`cosh`/`tanh` with inverses, `trunc`, and the cancellation-safe small-argument forms `expm1` and `log1p`. Core scientific facilities include: - `Matrix`, `Vector`, `Tensor`, and dense linear algebra; - `LinAlg` for dense float work over row-major nested lists — `solve`, `det`, `cholesky`, `qr`, `charpoly`, `poly_roots`, `eigenvalues`; - `SparseMatrix` for sparse matrix algebra; - `FFT`; - `Special` transcendental and special functions; - forward and reverse automatic differentiation; - ODE initial-value solvers through `Solve`; - scalar/vector optimization and root finding through `Optim`; - interpolation and numerical quadrature; - terminal plots, sparklines, and heatmaps through `Plot`; - scientific data interchange through `SciIO`; - measurements and calibrations with uncertainty. The domain map, each autoloading on first class reference (only algebra requires its literal `use algebra` directive): | Domain | Facade | Covers | | --- | --- | --- | | `core/calculus` | `Calculus` | forward-AD derivative/gradient/jacobian/hessian, adaptive quadrature, symbolic series/limits/residues | | `core/dynamics` | `Dynamics` | flows + maps, RK4 and symplectic integration, stability, Lyapunov spectra, bifurcations, Poincaré sections, embeddings | | `core/physics` | `Physics` | CODATA constants (Quantity + `_si` float twins), ideal gas, Euler systems, finite-volume solvers | | `core/algebra` | `Algebra` | exact fields, polynomial rings, Sturm real roots, Gröbner bases, Galois theory | | `core/stats` | `Stats` | descriptive statistics, seeded RNG (`Stats.rng(seed)`); Array carries `mean`/`variance`/`stdev`/`median`/`norm` | | `core/optim` | `Optim` | root finding, least squares, minimizers | | `core/signal` | — | reserved stub; FFT lives in the `FFT` class today | ### Dynamical systems `core/dynamics` models research-grade dynamical systems. Classic systems (`Lorenz`, `Rossler`, `VanDerPol`, `Duffing`, `DoublePendulum`, `Henon`, `LogisticMap`, `StandardMap`, `HarmonicOscillator`) ship with `.classic` parameter sets; custom systems subclass `Flow` (`f(t, x)`), `MapSystem` (`step(x)`), or `HamiltonianSystem` (`accel(q)`), inheriting a finite-difference Jacobian that analytic `jac` overrides replace. ```tungsten lz = Lorenz.classic tr = Dynamics.trajectory(lz, [~1.0, ~1.0, ~1.0], ~0.0, ~50.0, ~0.01) fp = Dynamics.fixed_point_flow(lz, [~8.0, ~8.0, ~27.0]) # (√72, √72, 27) Dynamics.classify_flow(lz, fp) # :saddle sp = Dynamics.lyapunov_spectrum(lz, [~1.0, ~1.0, ~1.0], ~5.0, 3000, 5, ~0.01) Dynamics.kaplan_yorke(sp) # ≈ 2.06 pc = Dynamics.poincare(lz, [~1.0, ~1.0, ~1.0], [~0.0, ~0.0, ~1.0], ~27.0, ~5.0, ~200.0, ~0.005) d2 = Dynamics.correlation_dimension(Dynamics.orbit(Henon.classic, [~0.1, ~0.1], 1200).drop(200), ~0.01, ~0.5, 8) ``` On top of the basics: `Dynamics.trajectory_adaptive` (Dormand-Prince 5(4) via `Solve.rk45`, whose `Solve.rk45_dense` returns a `DenseSolution` you can sample at any time), `continue_equilibria` / `continue_arclength` (equilibrium branches — the arclength form rounds folds; `stability_changes` marks bifurcations, finding the Lorenz pitchfork at ρ=1 and the Hopf at ρ≈24.74), `shoot_periodic` / `shoot_periodic_multi` (periodic orbits by single/multiple shooting on the monodromy; Van der Pol μ=1 gives T = 6.66328687 with Floquet multipliers {1, 0.00086}), `basins` + `basin_counts` (basins of attraction), and `lyapunov_map` (λ over a 2-parameter grid). The basin and Lyapunov-map sweeps have `@gpu` Metal twins in `doc/examples/` verified cell-for-cell against the CPU. Validated against the literature in `spec/core/dynamics_spec.w`: logistic r=4 Lyapunov = ln 2, Hénon spectrum sums to ln b exactly with Kaplan-Yorke ≈ 1.26, the Lorenz spectrum sums to −(σ+1+β) exactly with Kaplan-Yorke ≈ 2.06, and symplectic integrators hold energy bounded where RK4 drifts. See `doc/dynamics.md` in the repository for the full API. The `wit` REPL can render mathematical expressions and plots in the terminal. ```sh tungsten console ``` Examples to enter in `wit`: ```text ? Σ(2x⁷ + 3x²) ? ∫(x², -10..10) ``` ## 13. Exact algebra Load the exact algebra stack with: ```tungsten use algebra ``` The stack includes exact coefficient domains, polynomials, ideals, orders, number fields, projective geometry, curves, divisors, and explicit certificate objects. Representative setup: ```tungsten use algebra x = Poly<ℚ>.new(:x).generator F = FiniteField.new(5) F125 = FiniteField.extension(5, 3) R = PolynomialRing.new([:t], F) t = R.generator(0) E = Algebra.extension(t**2 + t + 1, :a) K = NumberField.new(x**3 + x**2*2 - x*9 - 12, :a) ``` Implemented algebraic areas include: - rational, prime, extension finite, simple extension, finite étale, and number fields; - exact polynomial division, gcd, resultant, discriminant, factorization, monomial orders, Gröbner bases, and certified real-root isolation; - integral and maximal orders, prime decomposition, exact ideals, valuations, selected S-unit/S-class computations, and archimedean places; - replayable certificates for many finite and arithmetic computations. Searches that cannot justify a result are designed to raise or return `unknown` rather than silently changing coefficient domains or proof claims. Resource-bounded certificates prove only the statement they explicitly replay; they are not blanket theorem certificates. Detailed status: https://github.com/tungsten-lang/tungsten/blob/main/doc/algebra.md Certificate boundaries: https://github.com/tungsten-lang/tungsten/blob/main/doc/certified-mathematics.md ## 14. Geometry The current geometry surface is algebraic geometry and lives under `use algebra`. ```tungsten use algebra P2 = ProjectiveSpace<ℚ, 2>.new(:B, :S, :Z) B = P2.coords[0] S = P2.coords[1] Z = P2.coords[2] f = B**3*Z*16 + B*S**2*Z*48 - S**4*3 f += S**3*Z*8 + S**2*Z**2*162 + Z**4*729 C = Curve.new(P2, f) C.assert_homogeneous(4) ``` Implemented areas include arbitrary projective spaces, normalized points, plane curves, line intersections, rational and closed places, divisors, singular loci, local multiplicities and tangent cones, Newton polygons, selected Puiseux-sheet certificates, point counts, zeta numerators, elliptic and documented hyperelliptic arithmetic, and focused plane-quartic machinery. Important general algorithms remain incomplete, including broad function-field and divisor-class-group machinery, fast general point counting, arbitrary plane-cubic conversion, and completed generalized descent. Consult the current capability table before making a theorem-level claim. Mathematics map: https://github.com/tungsten-lang/tungsten/blob/main/doc/mathematics.md ## 15. GPU and parallel code GPU kernels stay in a `.w` source file: ```tungsten ## f32[]: x ## f32[]: y ## i32: n @gpu fn add_one(x, y, n) i = gpu.thread_position_in_grid.x ## i32 if i < n y[i] = x[i] + 1.0 ``` The compiler lowers the typed GPU subset through a multi-dialect emitter: Metal Shading Language is always emitted, CUDA C by default (`kernels.cu` beside the source; disable with `TUNGSTEN_GPU_DIALECTS=none`), and WGSL when `TUNGSTEN_GPU_DIALECTS` includes `wgsl`. Host-side runtime code builds and dispatches Metal kernels on Apple hardware; the CUDA and WGSL kernels are source sidecars for external toolchains. A few features are dialect-specific — tensor-core `gpu.wmma_*` ops are CUDA-only, and `simdgroup_*` matrices are Metal-only. Core includes threads, channels, atomics, and basic `go` concurrency. Prefer compiled execution for concurrency work and verify behavior with tests. Multi-param blocks destructure a yielded Array element (Ruby proc semantics): `pairs.each ->(freq, amp)` and `pairs.map ->(a, b) a + b` spread each pair; missing params become nil, extra elements drop, and two-arg yields (hash `each ->(k, v)`, `reduce ->(acc, x)`) are unchanged. Implicit free-var blocks bind in first-reference order and never destructure. ## 16. Systems and application library Core and shipped Bits cover: - files, paths, memory maps, processes, environment access, and threads; - JSON, Base64, digests, crypto helpers, and UUIDs; - IPv4, IPv6, CIDR, and MAC value types; - regular expressions and string/byte buffers; - dates, times, instants, durations, quantities, and currencies; - HTTP runtimes, event loops, and networking surfaces; - the Bit package manager and Bitfile dependency model. The generated core index is authoritative for registered classes: https://github.com/tungsten-lang/tungsten/blob/main/doc/CORE.md ## 17. The good Bits - Argon: manpage-driven option parsing. - Flame: profiling, interactive SVG flame graphs, diffs, and trace exports. - Forge: multi-threaded HTTP server for Tungsten and Carbide. - Hammer: M:N HTTP load and benchmark tool. - Koala: DataFrames, linear algebra, preprocessing, metrics, and ML. - wasSAT: native CDCL SAT solver with optional proof emission. - WRAT: independent streaming checker for WRAT/WRATB/LRAT/DRAT refutations. - Metaflip: exact-gated CPU and Metal search for low-rank GF(2) matrix-multiplication decompositions. Package source: https://github.com/tungsten-lang/tungsten/tree/main/bits ## 18. Agent tooling The compiler and language server expose machine-oriented feedback: ```sh tungsten start --agent tungsten -c file.w tungsten --ast file.w tungsten --lex file.w tungsten --ll file.w TUNGSTEN_ERROR_FORMAT=json tungsten -c file.w tungsten --explain E_PARSE_UNEXPECTED_TOKEN ``` Structured compile errors include a stable code, message, source position, expected/actual context where available, and an explanation pointer. The Tungsten MCP server exposes: - symbols in a file; - hover/signature information; - definition lookup; - references; - workspace symbol search; - completions; - diagnostics. MCP server: https://github.com/tungsten-lang/tungsten/blob/main/bits/tungsten-lsp/bin/mcp-server.w LSP server: https://github.com/tungsten-lang/tungsten/tree/main/bits/tungsten-lsp Editor setup: https://github.com/tungsten-lang/tungsten/blob/main/doc/editors.md ## 19. Testing and verification guidance for agents 1. Start with `tungsten start --agent`. 2. Read the nearest README, Bitfile, and specs before inventing an API. 3. Run `tungsten -c file.w` after structural edits. 4. Run the narrow affected spec before broad suites. 5. Test the quick-run and native paths when the change affects both. 6. Use JSON diagnostics when driving repair loops programmatically. 7. Do not infer theorem-level truth from a finite certificate or a healthy long-running search checkpoint. 8. Treat stage-one/stage-two identity as a compiler reproduction invariant, not a semantic proof. 9. On GPU code, test the host launch and device result, not only emitted MSL. Repository convention: use `size` rather than `length` for collection/file-like APIs, and run project-wide `rake` from the repository root. ## 20. Known boundaries - Tungsten is a public preview with a much smaller ecosystem than established languages. - macOS and Linux are primary; use WSL2 on Windows. - The quick-run and native paths do not yet have perfect feature parity. - GPU kernels emit as Metal, CUDA, and WGSL, but the built-in host launch path is Metal and requires supported Apple hardware; CUDA/WGSL sidecars need external toolchains to run. - Some advanced numerical and algebraic surfaces are intentionally resource-bounded or incomplete. ## 21. Canonical reading order 1. Short agent primer: https://tungsten-lang.org/llms.txt 2. Dense repository primer: https://github.com/tungsten-lang/tungsten/blob/main/doc/TUNGSTEN_FOR_LLMS.md 3. Getting started: https://github.com/tungsten-lang/tungsten/tree/main/doc/getting-started 4. Core library: https://github.com/tungsten-lang/tungsten/blob/main/doc/CORE.md 5. Mathematics map: https://github.com/tungsten-lang/tungsten/blob/main/doc/mathematics.md 6. Exact algebra: https://github.com/tungsten-lang/tungsten/blob/main/doc/algebra.md 7. Specification: https://tungsten-lang.org/spec 8. Curated examples: https://github.com/tungsten-lang/tungsten/tree/main/doc/examples