Skip to content

Commit c9d1460

Browse files
authored
goalc: add offset-of (#4081)
<img width="1015" height="1441" alt="image" src="https://github.com/user-attachments/assets/841f1885-d438-4baf-ad92-f5996d2f4788" />
1 parent 1f8362d commit c9d1460

File tree

3 files changed

+22
-0
lines changed

3 files changed

+22
-0
lines changed

goalc/compiler/Compiler.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -730,6 +730,7 @@ class Compiler {
730730
Val* compile_size_of(const goos::Object& form, const goos::Object& rest, Env* env);
731731
ConstPropResult const_prop_size_of(const goos::Object& form, const goos::Object& rest, Env* env);
732732
Val* compile_psize_of(const goos::Object& form, const goos::Object& rest, Env* env);
733+
Val* compile_offset_of(const goos::Object& form, const goos::Object& rest, Env* env);
733734
Val* compile_current_method_id(const goos::Object& form, const goos::Object& rest, Env* env);
734735
Val* compile_current_method_type(const goos::Object& form, const goos::Object& rest, Env* env);
735736
Val* compile_cast_to_method_type(const goos::Object& form, const goos::Object& rest, Env* env);

goalc/compiler/compilation/Atoms.cpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -221,6 +221,7 @@ const std::unordered_map<std::string, GoalCompilerForm> g_goal_forms = {
221221
{"none", {.form_function = &Compiler::compile_none}},
222222
{"size-of", {.form_function = &Compiler::compile_size_of}},
223223
{"psize-of", {.form_function = &Compiler::compile_psize_of}},
224+
{"offset-of", {.form_function = &Compiler::compile_offset_of}},
224225
{"current-method-id", {.form_function = &Compiler::compile_current_method_id}},
225226
{"cast-to-method-type", {.form_function = &Compiler::compile_cast_to_method_type}},
226227

goalc/compiler/compilation/Type.cpp

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1614,6 +1614,26 @@ Val* Compiler::compile_psize_of(const goos::Object& form, const goos::Object& re
16141614
return compile_integer((get_size_for_size_of(form, rest) + 0xf) & ~0xf, env);
16151615
}
16161616

1617+
Val* Compiler::compile_offset_of(const goos::Object& form, const goos::Object& rest, Env* env) {
1618+
auto args = get_va(form, rest);
1619+
va_check(form, args, {goos::ObjectType::SYMBOL, goos::ObjectType::SYMBOL}, {});
1620+
auto type_to_look_for = args.unnamed.at(0).as_symbol();
1621+
if (!m_ts.fully_defined_type_exists(type_to_look_for.name_ptr)) {
1622+
throw_compiler_error(form, "The type {} could not be found or was not fully defined.",
1623+
args.unnamed.at(0).print());
1624+
}
1625+
auto type = m_ts.lookup_type(type_to_look_for.name_ptr);
1626+
auto field_name = args.unnamed.at(1).as_symbol().name_ptr;
1627+
auto as_struct = dynamic_cast<StructureType*>(type);
1628+
if (as_struct) {
1629+
auto info = m_ts.lookup_field_info(type->get_name(), field_name);
1630+
auto off = as_struct->is_boxed() ? info.field.offset() - 4 : info.field.offset();
1631+
return compile_integer(off, env);
1632+
} else {
1633+
throw_compiler_error(form, "The type {} is not a reference type.", args.unnamed.at(0).print());
1634+
}
1635+
}
1636+
16171637
Val* Compiler::compile_current_method_id(const goos::Object& form,
16181638
const goos::Object& rest,
16191639
Env* env) {

0 commit comments

Comments
 (0)