Masterbelt

masterbelt/masterbelt

Built-Ins

Synced from main@9490864MarkdownSource

#Built-Ins

This document defines the currently implemented Masterbelt built-in types, values, functions, and operators.

The built-in set is intentionally minimal at this stage. Future built-in additions must extend this document before or together with implementation changes.

#Built-In Types

The implemented built-in primitive types are:

  • null: the type of the null literal.
  • bool: the type of boolean literals.
  • string: the type of string literals.

The implemented built-in numeric types are:

MasterbeltSignednessWidth
intsignednative (host language's natural width)
int8signed8 bits
int16signed16 bits
int32signed32 bits
int64signed64 bits
uintunsignednative (host language's natural width)
uint8unsigned8 bits
uint16unsigned16 bits
uint32unsigned32 bits
uint64unsigned64 bits

The default type of an integer literal that has no type annotation, pushdown target, or cast prefix is int.

Built-in type names are written in lowercase.

#Numeric Type Classes

The language distinguishes three internal numeric type classes. These classes are not types in their own right: they cannot appear in a type expression position and they do not name a binding. They exist to let the checker describe operations that require a numeric operand or target.

  • numeric: the union of every built-in numeric type listed above.
  • snumeric: the union of every signed built-in numeric type (int, int8, int16, int32, int64).
  • unumeric: the union of every unsigned built-in numeric type (uint, uint8, uint16, uint32, uint64).

An alias whose target resolves to a numeric type belongs to the same class as the resolved target.

The implemented built-in generic type constructors are:

  • list<T>: a homogeneous sequence of values of element type T.
  • map<K, V>: an associative mapping from key type K to value type V.

Generic type constructors take their type arguments between < and > separated by ,. Each type argument is itself a type expression.

The number of type arguments must match the constructor:

  • list takes exactly one type argument.
  • map takes exactly two type arguments.

Built-in type names and generic type constructor names are available only in type expression positions. They do not introduce value bindings.

#Built-In Product Types

Error is the built-in product type used to represent a recoverable failure produced by a failable function.

Masterbelt
type Error = { message: string }

The Error name is reserved at the type binding space: declaring a type, enum, or master named Error is a type checking error reported through the standard reserved-name diagnostic. The only surface use of Error is as the argument to fail (fail Error { message: "..." }); it does not appear in function return types or in user-visible unions. See syntax.md and semantics.md for the integration with fail.

#Built-In Values

The implemented built-in values are the literal words null, true, and false.

#Built-In Functions and Operators

The implemented built-in free functions are:

  • fn range(start: int, end: int): list<int> — yields the integers start, start + 1, ..., end - 1 in ascending order. When start >= end the result is empty. The function is total: every input produces a value of list<int> without effects.

range is exposed as a value binding in the same module-scope name space as user-declared functions. The name range cannot be redeclared (a user declaration of const range = ... or fn range(...) is rejected through the reserved built-in names rule extended to value-position built-ins).

Although range(start, end) returns a list<int> at the type level, every supported codegen target recognises a for i in range(a, b) { ... } source form and emits a counted loop instead of materializing the list (see codegen/golang.md, codegen/typescript.md, and codegen/csharp.md). The optimization is a target-emission concern; the language semantics treat range as returning a regular list.

#Operator Methods

Every unary or binary operator in syntax.md is defined as a method on the operand (for unary) or the left operand (for binary). The surface form a OP b is equivalent to the method call a.METHOD(b); the unary form OP a is equivalent to a.METHOD().

The complete operator-to-method mapping is:

SurfaceMethodArity
!anotunary
+aplusunary
-aminusunary
a + baddbinary
a - bsubbinary
a * bmulbinary
a / bdivbinary
a % bmodbinary
a == beqlbinary
a != bneqbinary
a < bltbinary
a <= blteqbinary
a > bgtbinary
a >= bgteqbinary
a & bandbinary
`ab`or
a ^ bxorbinary
a << blshiftbinary
a >> brshiftbinary

The method must exist on the operand's type. Type checking of an operator expression follows the same overload resolution rules used for any other method call (see types.md). A user product type may declare any subset of these methods to opt that operator in; declaring a method whose name is not in this table is permitted but has no operator interpretation.

#Built-In Fields on Primitive and Generic Types

A few built-in types expose readonly fields that record a side-effect-free property of the value. The fields are not method calls — they participate in the regular value.field member-access form defined in syntax.md — so the surface form has no parentheses.

  • string.length: int — the number of Unicode codepoints in the string (rune count, not byte count). The value matches Go's utf8.RuneCountInString; each codepoint counts as one regardless of its UTF-8 byte size.
  • list<T>.size: int — the number of elements in the list.
  • map<K, V>.size: int — the number of entries in the map.

The fields are not visible as free identifiers and cannot be redefined; they exist on every value of the corresponding type. An alias whose target resolves to one of these types inherits the same fields.

#Built-In Operator Methods on Primitive Types

For every built-in primitive type listed earlier in this document, the language exposes a fixed set of operator methods as if the type carried them in its method list. These methods are not visible as free identifiers and cannot be redefined; they exist only to make operator expressions on primitive operands type-check.

The intrinsic operator methods provided for each primitive type are:

  • Every numeric type N (int, int8, ..., uint64):
    • fn add(other: N): N, fn sub(other: N): N, fn mul(other: N): N, fn div(other: N): N, fn mod(other: N): N
    • fn eql(other: N): bool, fn neq(other: N): bool, fn lt(other: N): bool, fn lteq(other: N): bool, fn gt(other: N): bool, fn gteq(other: N): bool
    • fn and(other: N): N, fn or(other: N): N, fn xor(other: N): N
    • fn lshift(other: N): N, fn rshift(other: N): N
    • fn plus(): N (unary +)
    • fn minus(): N (unary -; provided on signed numeric types only)
  • bool:
    • fn eql(other: bool): bool, fn neq(other: bool): bool
    • fn and(other: bool): bool, fn or(other: bool): bool, fn xor(other: bool): bool
    • fn not(): bool (unary !)
  • string:
    • fn eql(other: string): bool, fn neq(other: string): bool
    • fn lt(other: string): bool, fn lteq(other: string): bool, fn gt(other: string): bool, fn gteq(other: string): bool
    • fn add(other: string): string (concatenation)
  • null:
    • fn eql(other: null): bool, fn neq(other: null): bool

The built-in generic constructors expose operator methods as well:

  • list<T>:
    • fn add(other: list<T>): list<T> — element-wise concatenation; the result lists the receiver's elements followed by the argument's elements.
  • map<K, V>:
    • fn add(other: map<K, V>): map<K, V> — last-wins merge; the result contains every entry of the receiver and every entry of the argument, with a key present in both taking the argument's value.

An alias whose target resolves to a primitive type or a built-in generic application inherits the corresponding intrinsic operator method set.

Operator method calls on primitive operands are emitted by every supported target as that target's native operator. Operator method calls on built-in generic operands (list, map) are emitted as a call into the target's runtime helper file; see each target's specification for the surface translation and runtime file emission.

Specification