Skip to content

v3.ssa

fn build #

fn build(a_ &flat.FlatAst) &Module

fn build_with_options #

fn build_with_options(a_ &flat.FlatAst, used_fns map[string]bool, tc &types.TypeChecker, opts BuildOptions) &Module

fn build_with_used #

fn build_with_used(a_ &flat.FlatAst, used_fns map[string]bool, tc &types.TypeChecker) &Module

fn AtomicOrdering.from #

fn AtomicOrdering.from[W](input W) !AtomicOrdering

fn CallConv.from #

fn CallConv.from[W](input W) !CallConv

fn InlineHint.from #

fn InlineHint.from[W](input W) !InlineHint

fn Linkage.from #

fn Linkage.from[W](input W) !Linkage

fn Module.new #

fn Module.new() &Module

fn OpCode.from #

fn OpCode.from[W](input W) !OpCode

fn TypeKind.from #

fn TypeKind.from[W](input W) !TypeKind

fn TypeStore.new #

fn TypeStore.new() TypeStore

fn ValueKind.from #

fn ValueKind.from[W](input W) !ValueKind

type BlockID #

type BlockID = int

type TypeID #

type TypeID = int

type ValueID #

type ValueID = int

enum AtomicOrdering #

enum AtomicOrdering {
	not_atomic
	unordered
	monotonic
	acquire
	release
	acq_rel
	seq_cst
}

enum CallConv #

enum CallConv {
	c_decl
	fast_call
	wasm_std
}

enum InlineHint #

enum InlineHint {
	none_  // No hint, let optimizer decide
	always // Always inline (e.g. V's [inline] attribute)
	never  // Never inline (e.g. V's [noinline] attribute)
	hint   // Suggest inlining (optimizer may ignore)
}

enum Linkage #

enum Linkage {
	external
	private
	internal
}

enum OpCode #

enum OpCode {
	// Terminators
	ret
	br
	jmp
	switch_ // Multi-way branch: switch_ %val, default_block, [case_val, block]...
	unreachable
	// Binary (integer)
	add
	sub
	mul
	sdiv
	srem
	udiv
	urem
	// Binary (float)
	fadd
	fsub
	fmul
	fdiv
	frem
	// Bitwise
	shl
	ashr
	lshr
	and_
	or_
	xor
	// Memory
	alloca
	load
	store
	get_element_ptr
	heap_alloc // Heap allocate memory for a type (malloc+zero): returns ptr
	fence      // Memory ordering barrier
	cmpxchg    // Atomic compare-exchange
	atomicrmw  // Atomic read-modify-write
	// Comparisons
	lt
	gt
	le
	ge
	ult
	ugt
	ule
	uge
	eq
	ne
	// Other
	call
	call_indirect // Indirect call through function pointer
	call_sret     // Call with struct return (x8 indirect return on ARM64)
	neg
	trunc
	sext
	zext
	fptoui
	fptosi
	uitofp
	sitofp
	bitcast
	phi
	select
	assign             // Copy op used during phi elimination
	inline_string_init // Build a string struct by value: (string){str, len}
	// Concurrency
	go_call    // Launch goroutine: go_call fn_ref, args...
	spawn_call // Launch OS thread: spawn_call fn_ref, args...
	// Aggregate (struct/tuple) operations
	extractvalue
	insertvalue
	struct_init
}

enum TypeKind #

enum TypeKind {
	void_t
	int_t
	float_t
	ptr_t
	array_t
	struct_t
	func_t
	label_t
	metadata_t
}

enum ValueKind #

enum ValueKind {
	unknown
	constant
	argument
	global
	instruction
	basic_block
	string_literal   // V string struct literal (by value)
	c_string_literal // C string literal (raw char pointer)
	func_ref
}

struct BasicBlock #

struct BasicBlock {
pub mut:
	id     BlockID
	val_id ValueID // SSA value representing the block (0 in v3's raw-block-id model)
	name   string
	parent int
	instrs []ValueID
	preds  []BlockID
	succs  []BlockID
	// Dominators
	idom     BlockID
	dom_tree []BlockID
}

struct BuildOptions #

struct BuildOptions {
pub:
	hot_fn         string   // build only this function's body (hot reload)
	skip_fn_bodies bool     // register signatures only, mark them prototypes
	skip_modules   []string // skip all functions declared in these modules
}

BuildOptions controls which functions a build materializes. The zero value reproduces the default whole-program build.

struct Builder #

struct Builder {
mut:
	m                  &Module            = unsafe { nil }
	a                  &flat.FlatAst      = unsafe { nil }
	tc                 &types.TypeChecker = unsafe { nil }
	used_fns           map[string]bool
	cur_module         string
	cur_func           int
	cur_block          BlockID
	vars               map[string]ValueID
	var_type_names     map[string]string
	i64_type           TypeID
	i32_type           TypeID
	i8_type            TypeID
	i1_type            TypeID
	u64_type           TypeID
	u32_type           TypeID
	u16_type           TypeID
	u8_type            TypeID
	f32_type           TypeID
	f64_type           TypeID
	void_type          TypeID
	str_type           TypeID
	array_type         TypeID
	map_type           TypeID
	map_state_type     TypeID
	fn_types           map[string]TypeID
	fn_ids             map[string]int
	const_exprs        map[string]flat.NodeId
	struct_types       map[string]TypeID
	struct_field_types map[string]string
	option_types       map[string]TypeID
	sum_type_variants  map[string][]string
	sum_type_canonical map[string]string
	enum_types         map[string]bool
	flag_enum_types    map[string]bool
	enum_values        map[string]int
	enum_member_values map[string]int
	enum_member_dupes  map[string]bool
	c_fn_ids           map[string]int
	c_fn_types         map[string]TypeID
	label_blocks       map[string]BlockID
	defer_body_ids     []flat.NodeId
	break_targets      []BlockID
	continue_targets   []BlockID
	top_level_main     bool
	// --- Build-control machinery (ported from v2 build_all) ---
	// When set, build_functions only materializes this one function body (hot reload).
	hot_fn string
	// When set, build_functions registers signatures only and marks them prototypes.
	skip_fn_bodies bool
	// When non-empty, all functions declared in these modules are skipped (dead
	// code elimination for unused backends/modules).
	skip_modules map[string]bool
	// SSA-level type alias name -> resolved base TypeID. Supplements the checker's
	// alias map (used when building without a checker).
	type_aliases map[string]TypeID
}

struct ConstantData #

struct ConstantData {
pub:
	int_val   i64
	float_val f64
	str_val   string
}

ConstantData carries the typed payload of a constant value. It mirrors v2's representation so backends can recover the original int/float/string value instead of re-parsing Value.name.

struct Function #

struct Function {
pub mut:
	id           int
	name         string
	typ          TypeID
	blocks       []BlockID
	params       []ValueID
	is_c_extern  bool // C-language extern function (no V body)
	is_prototype bool // Registered declaration/signature whose body is not materialized yet
	linkage      Linkage
	call_conv    CallConv
}

struct GlobalVar #

struct GlobalVar {
pub mut:
	name          string
	typ           TypeID
	linkage       Linkage
	alignment     int
	is_constant   bool
	initial_value i64  // For constants/enums, the initial integer value
	initial_data  []u8 // For constant arrays: serialized element data
}

struct Instruction #

struct Instruction {
pub mut:
	op         OpCode
	operands   []ValueID
	block      BlockID
	typ        TypeID
	pos        token.Pos
	atomic_ord AtomicOrdering
	inline     InlineHint // Inline hint for call instructions
}

fn (Instruction) value_operands #

fn (i &Instruction) value_operands() []ValueID

struct Module #

@[heap]
struct Module {
pub mut:
	name       string
	target     TargetData
	type_store TypeStore
	values     []Value
	instrs     []Instruction
	blocks     []BasicBlock
	funcs      []Function
	globals    []GlobalVar
	// C struct names: TypeID -> C struct name (e.g. for `struct stat`). Used by
	// codegen to emit `typedef struct <name> ...;` and preserve the C layout.
	c_struct_names map[int]string
	// C structs marked @[typedef] — already a C typedef, not a struct tag.
	c_typedef_structs map[int]bool
	// Constant cache: "type:name" -> ValueID for deduplication.
	const_cache map[string]ValueID
}

fn (Module) add_value #

fn (mut m Module) add_value(kind ValueKind, typ TypeID, name string, index int) ValueID

fn (Module) add_instr #

fn (mut m Module) add_instr(op OpCode, block BlockID, typ TypeID, operands []ValueID) ValueID

fn (Module) add_instr_front #

fn (mut m Module) add_instr_front(op OpCode, block BlockID, typ TypeID, operands []ValueID) ValueID

add_instr_front creates an instruction and prepends it to the block (used for phi insertion by mem2reg, which requires phis at the top of a block).

fn (Module) append_phi_operands #

fn (mut m Module) append_phi_operands(instr_idx int, val ValueID, block_id BlockID)

append_phi_operands appends a (val, block_id) pair to a phi instruction.

fn (Module) add_block #

fn (mut m Module) add_block(func_id int, name string) BlockID

fn (Module) new_function #

fn (mut m Module) new_function(name string, ret TypeID) int

fn (Module) func_add_param #

fn (mut m Module) func_add_param(func_id int, param_val ValueID)

--- Safe mutation helpers (avoid chained struct-array mutations) ---

fn (Module) func_set_c_extern #

fn (mut m Module) func_set_c_extern(func_id int, val bool)

fn (Module) func_set_prototype #

fn (mut m Module) func_set_prototype(func_id int, val bool)

fn (Module) block_add_succ #

fn (mut m Module) block_add_succ(from BlockID, to BlockID)

fn (Module) block_add_pred #

fn (mut m Module) block_add_pred(to BlockID, from BlockID)

fn (Module) add_global #

fn (mut m Module) add_global(name string, typ TypeID) ValueID

fn (Module) add_global_with_data #

fn (mut m Module) add_global_with_data(name string, elem_type TypeID, is_const bool, data []u8) ValueID

add_global_with_data registers a private global initialized from raw bytes (used for const arrays serialized to element data).

fn (Module) add_external_global #

fn (mut m Module) add_external_global(name string, typ TypeID) ValueID

add_external_global registers (or reuses) a global defined outside this module (e.g. C runtime globals such as __stdoutp). Returns the global pointer value.

fn (Module) get_or_add_const #

fn (mut m Module) get_or_add_const(typ TypeID, name string) ValueID

fn (Module) get_block_from_val #

fn (m &Module) get_block_from_val(val_id int) int

get_block_from_val converts a basic-block value operand to its block index.

fn (Module) type_size #

fn (m &Module) type_size(typ_id TypeID) int

type_size returns the byte size for an SSA type on the current target.

fn (Module) type_align #

fn (m &Module) type_align(typ_id TypeID) int

type_align returns the ABI alignment for an SSA type on the current target.

fn (Module) replace_uses #

fn (mut m Module) replace_uses(old_id ValueID, new_id ValueID)

fn (Module) struct_field_offset #

fn (m &Module) struct_field_offset(typ_id TypeID, field_idx int) int

struct_field_offset returns the byte offset of a field in a struct type.

fn (Module) struct_field_size #

fn (m &Module) struct_field_size(typ_id TypeID, field_idx int) int

struct_field_size returns the byte size of a field in a struct type.

struct TargetData #

struct TargetData {
pub:
	ptr_size      int  = 8
	endian_little bool = true
}

struct Type #

struct Type {
pub:
	kind        TypeKind
	width       int
	is_unsigned bool
	elem_type   TypeID // For Ptr, Array
	len         int    // For Array
	fields      []TypeID
	field_names []string
	params      []TypeID
	ret_type    TypeID
	is_c_struct bool // True for C interop structs (raw field names, typedef to C struct)
	is_union    bool // True for union types (all fields overlap at offset 0)
}

struct TypeStore #

struct TypeStore {
pub mut:
	types []Type
	cache map[string]TypeID
}

fn (TypeStore) get_int #

fn (mut ts TypeStore) get_int(width int) TypeID

fn (TypeStore) get_uint #

fn (mut ts TypeStore) get_uint(width int) TypeID

fn (TypeStore) get_float #

fn (mut ts TypeStore) get_float(width int) TypeID

fn (TypeStore) get_ptr #

fn (mut ts TypeStore) get_ptr(elem TypeID) TypeID

fn (TypeStore) get_array #

fn (mut ts TypeStore) get_array(elem TypeID, length int) TypeID

get_array returns the cached fixed-array type for (elem, length).

fn (TypeStore) get_tuple #

fn (mut ts TypeStore) get_tuple(elem_types []TypeID) TypeID

get_tuple returns a cached anonymous struct type holding the given element types.

fn (TypeStore) register #

fn (mut ts TypeStore) register(t Type) TypeID

struct Value #

struct Value {
pub mut:
	id    ValueID
	kind  ValueKind
	typ   TypeID
	name  string
	index int
	uses  []ValueID
}