Skip to content

Commit

Permalink
Work on reflection data
Browse files Browse the repository at this point in the history
  • Loading branch information
Victorious3 committed Sep 29, 2024
1 parent 2e8f433 commit 7ca22e1
Show file tree
Hide file tree
Showing 3 changed files with 51 additions and 39 deletions.
37 changes: 21 additions & 16 deletions src/compiler.pr
Original file line number Diff line number Diff line change
Expand Up @@ -9124,6 +9124,10 @@ def push_structural_members(tpe: &typechecking::Type, global: Value, module: &to
}

def do_create_type(tpe: &typechecking::Type, svalue: &scope::Value, module: &toolchain::Module, cache: &Vector(TypeEntry)) -> &Value {
if not is_stub(tpe) {
all_types.add(tpe)
}

if toolchain::no_stdlib { return NO_VALUE }

if tpe.kind == typechecking::TypeKind::BOX {
Expand Down Expand Up @@ -9489,24 +9493,24 @@ def make_global_data(name: Str, value: size_t, state: &State) {
state.module.imported.add(name)
}

export let all_types = set::make(type &typechecking::Type)

export def generate_reflection_data() {
let data = io::make_stream()
let strings = [ strings = io::make_stream(), map = map::make(size_t) ] !&UniquedStrings

for var key in @types_to_resolve.keys() {
let to_resolve = types_to_resolve(key)
generate_reflection_data_1(to_resolve.tpe, data, strings)
for var tpe in @all_types.keys() {
generate_reflection_data_1(tpe, data, strings)
}

for var key in @types_to_resolve.keys() {
let to_resolve = types_to_resolve(key)
generate_reflection_data_2(to_resolve.tpe, data, strings)
for var tpe in @all_types.keys() {
generate_reflection_data_2(tpe, data, strings)
}

make_global_data("__reflection_data", data, toolchain::types_state)
make_global_data("__reflection_data_size", data.data().size, toolchain::types_state)
make_global_data("__reflection_strings", strings.strings, toolchain::types_state)
make_global_data("__reflection_num_types", types_to_resolve.size, toolchain::types_state)
make_global_data("__reflection_num_types", all_types.size, toolchain::types_state)
}

type UniquedStrings = struct {
Expand All @@ -9524,8 +9528,6 @@ def write_zt(uniqued: &UniquedStrings, s: Str) -> int {
}

def generate_reflection_data_2(tpe: &typechecking::Type, data: &ByteStream, strings: &UniquedStrings) {
if tpe.kind == typechecking::TypeKind::STUB { return }

// Collect type members
let type_members = vector::make(typechecking::TypeEntryMember)
for var member in typechecking::iterate_member_functions(tpe) {
Expand All @@ -9541,7 +9543,7 @@ def generate_reflection_data_2(tpe: &typechecking::Type, data: &ByteStream, stri

data.write(member.function.parameter_t.length !int)
for var arg in member.function.parameter_t {
data.write(arg.tpe.hash) // TODO Do we want function argument names maybe?
data.write(arg.tpe.hash if arg.tpe else 0) // TODO Do we want function argument names maybe?
}
data.write(member.function.return_t.length !int)
for var t in member.function.return_t {
Expand All @@ -9566,7 +9568,7 @@ def generate_reflection_data_2(tpe: &typechecking::Type, data: &ByteStream, stri
case typechecking::TypeKind::POINTER, typechecking::TypeKind::REFERENCE,
typechecking::TypeKind::WEAK_REF, typechecking::TypeKind::ARRAY,
typechecking::TypeKind::STATIC_ARRAY
data.write(tpe.tpe.hash)
data.write(tpe.tpe.hash if tpe.tpe else 0)
case typechecking::TypeKind::TUPLE
for var t in tpe.return_t {
data.write(t.hash)
Expand All @@ -9586,12 +9588,12 @@ def generate_reflection_data_2(tpe: &typechecking::Type, data: &ByteStream, stri
}

def generate_reflection_data_1(tpe: &typechecking::Type, data: &ByteStream, strings: &UniquedStrings) {
if tpe.kind == typechecking::TypeKind::STUB { return }

data.write(tpe.kind) // This does rely on the values beind the same
data.write(strings.write_zt(tpe.name))
data.write(strings.write_zt(tpe.module.module))
data.write(strings.write_zt(tpe.module.module if tpe.module else to_str("")))
data.write(tpe.hash)

print(tpe.kind, " ", tpe.name, " ", (tpe.module.module if tpe.module else to_str("")), " ", tpe.hash, "\n")

switch tpe.kind {
case typechecking::TypeKind::WORD
Expand All @@ -9604,12 +9606,15 @@ def generate_reflection_data_1(tpe: &typechecking::Type, data: &ByteStream, stri
case typechecking::TypeKind::STRUCT, typechecking::TypeKind::UNION
data.write(tpe.size !int)
data.write(tpe.align !int)
data.write(tpe.fields.size)
data.write(tpe.fields.size !int)

print("\tsize: ", tpe.size, " align: ", tpe.align, " members: ", tpe.fields.size, "\n")
for var i in 0..tpe.fields.size {
let field = tpe.fields(i)
let member = tpe.field_types(field.index)
data.write(strings.write_zt(field.name))
data.write(member.offset !int)
print("\tname: ", field.name, " offset: ", member.offset, "\n")
}
case typechecking::TypeKind::STATIC_ARRAY
data.write(tpe.size)
Expand All @@ -9623,7 +9628,7 @@ def generate_reflection_data_1(tpe: &typechecking::Type, data: &ByteStream, stri
data.write(tpe.align !int)
data.write(not tpe.unsig)
case typechecking::TypeKind::STRUCTURAL
data.write(tpe.members.length)
data.write(tpe.members.length !int)
for var member in tpe.members {
data.write(strings.write_zt(member.name))
data.write(member.parameter_t.length !int)
Expand Down
2 changes: 1 addition & 1 deletion src/toolchain.pr
Original file line number Diff line number Diff line change
Expand Up @@ -840,8 +840,8 @@ export def compile_main_file(filename: String) {
}

debug::trace("Resolving types")
compiler::generate_reflection_data()
compiler::resolve_types() // TODO Remove this function
compiler::generate_reflection_data()
debug::trace("Creating builtin functions")
compiler::create_builtin_functions()

Expand Down
51 changes: 29 additions & 22 deletions std/reflection.pr
Original file line number Diff line number Diff line change
Expand Up @@ -192,7 +192,7 @@ import io
import map
import std

var types: &Map(size_t, Type)
var types: &Map(uint64, Type)

load_types(__reflection_data, @__reflection_data_size, @__reflection_num_types, __reflection_strings)

Expand All @@ -206,15 +206,17 @@ def load_types(input: *uint8, size: size_t, num: size_t, strings: *char) {
defer close(fp)

if not types {
types = map::make(size_t, Type)
types = map::make(uint64, Type)
}

var index = 0
while index < num {
let kind = fp.read(TypeKind)
let name = make_slice(strings, fp.read(int))
let module = make_slice(strings, fp.read(int))
let id = fp.read(size_t)
let id = fp.read(uint64)

print(kind, " ", name, " ", module, " ", id, "\n")

switch kind {
case TypeKind::BOOL
Expand All @@ -234,8 +236,13 @@ def load_types(input: *uint8, size: size_t, num: size_t, strings: *char) {
let size = fp.read(int)
let align = fp.read(int)
let members = zero_allocate(Field, fp.read(int))

print("\tsize: ", size, " align: ", align, " members: ", members.size, "\n")

for var i in 0..members.size {
members(i) = [ name = make_slice(strings, fp.read(int)), offset = fp.read(int) ] !Field
let field = [ name = make_slice(strings, fp.read(int)), offset = fp.read(int) ] !Field
members(i) = field
print("\tname: ", field.name, " offset: ", field.offset, "\n")
}

if kind == TypeKind::STRUCT {
Expand Down Expand Up @@ -320,11 +327,11 @@ def load_types(input: *uint8, size: size_t, num: size_t, strings: *char) {

let arguments = allocate_ref(type weak Type, fp.read(int))
for var i in 0..arguments.size {
arguments(i) = type_id(fp.read(size_t))
arguments(i) = type_id(fp.read(uint64))
}
let returns = allocate_ref(type weak Type, fp.read(int))
for var i in 0..returns.size {
returns(i) = type_id(fp.read(size_t))
returns(i) = type_id(fp.read(uint64))
}

member.arguments = arguments
Expand All @@ -336,65 +343,65 @@ def load_types(input: *uint8, size: size_t, num: size_t, strings: *char) {
let rec = tpe !StructT
for var i in 0..rec.members.size {
let f = *rec.members(i)
f.tpe = type_id(fp.read(size_t))
f.tpe = type_id(fp.read(uint64))
}
} else if tpe.type == UnionT {
let rec = tpe !UnionT
for var i in 0..rec.members.size {
let f = *rec.members(i)
f.tpe = type_id(fp.read(size_t))
f.tpe = type_id(fp.read(uint64))
}
} else if tpe.type == InterfaceT {
let intf = tpe !InterfaceT
for var i in 0..intf.members.size {
let m = *intf.members(i)
for var i in 0..m.arguments.size {
m.arguments(i) = type_id(fp.read(size_t))
m.arguments(i) = type_id(fp.read(uint64))
}
for var i in 0..m.returns.size {
m.returns(i) = type_id(fp.read(size_t))
m.returns(i) = type_id(fp.read(uint64))
}
}
} else if tpe.type == PointerT {
(tpe !PointerT).tpe = type_id(fp.read(size_t))
(tpe !PointerT).tpe = type_id(fp.read(uint64))
} else if tpe.type == ReferenceT {
(tpe !ReferenceT).tpe = type_id(fp.read(size_t))
(tpe !ReferenceT).tpe = type_id(fp.read(uint64))
} else if tpe.type == WeakReferenceT {
(tpe !WeakReferenceT).tpe = type_id(fp.read(size_t))
(tpe !WeakReferenceT).tpe = type_id(fp.read(uint64))
} else if tpe.type == ArrayT {
(tpe !ArrayT).tpe = type_id(fp.read(size_t))
(tpe !ArrayT).tpe = type_id(fp.read(uint64))
} else if tpe.type == StaticArrayT {
(tpe !StaticArrayT).tpe = type_id(fp.read(size_t))
(tpe !StaticArrayT).tpe = type_id(fp.read(uint64))
} else if (tpe.type == VariantT) {
let vnt = tpe !VariantT
for var i in 0..vnt.variants.size {
vnt.variants(i) = type_id(fp.read(size_t))
vnt.variants(i) = type_id(fp.read(uint64))
}
} else if (tpe.type == TupleT) {
let tuple = tpe !TupleT
for var i in 0..tuple.elements.size {
tuple.elements(i) = type_id(fp.read(size_t))
tuple.elements(i) = type_id(fp.read(uint64))
}
} else if (tpe.type == FunctionT) {
let fun = tpe !FunctionT
for var i in 0..fun.arguments.size {
fun.arguments(i) = type_id(fp.read(size_t))
fun.arguments(i) = type_id(fp.read(uint64))
}
for var i in 0..fun.returns.size {
fun.returns(i) = type_id(fp.read(size_t))
fun.returns(i) = type_id(fp.read(uint64))
}
} else if (tpe.type == ClosureT) {
let fun = tpe !ClosureT
for var i in 0..fun.arguments.size {
fun.arguments(i) = type_id(fp.read(size_t))
fun.arguments(i) = type_id(fp.read(uint64))
}
for var i in 0..fun.returns.size {
fun.returns(i) = type_id(fp.read(size_t))
fun.returns(i) = type_id(fp.read(uint64))
}
}
}
}

def type_id(index: size_t) -> Type {
def type_id(index: uint64) -> Type {
return types(index)
}

0 comments on commit 7ca22e1

Please sign in to comment.