Skip to content

Commit 4449ade

Browse files
authored
feat: check for invalid assoc with fields (#232)
1 parent 1f75356 commit 4449ade

File tree

5 files changed

+65
-2
lines changed

5 files changed

+65
-2
lines changed

ecsact/interpret/eval.cc

Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1171,6 +1171,28 @@ static auto get_with_field_ids(
11711171
return with_field_ids;
11721172
}
11731173

1174+
static auto find_capabilities_for( //
1175+
auto sys_like_id,
1176+
auto id
1177+
) -> std::optional<ecsact_system_capability> {
1178+
for(auto&& [comp_id, caps] : ecsact::meta::system_capabilities(sys_like_id)) {
1179+
if(ecsact_id_cast<decltype(id)>(comp_id) == id) {
1180+
return caps;
1181+
}
1182+
}
1183+
1184+
auto parent = ecsact::meta::get_parent_system_id(
1185+
// NOTE: this cast only works because we wrote the meta runtime for the
1186+
// interpreter. This is bad practice.
1187+
static_cast<ecsact_system_id>(sys_like_id)
1188+
);
1189+
if(parent) {
1190+
return find_capabilities_for(*parent, id);
1191+
}
1192+
1193+
return {};
1194+
}
1195+
11741196
static auto eval_system_with_statement_data_common(
11751197
ecsact_system_like_id sys_like_id,
11761198
ecsact_component_like_id comp_like_id,
@@ -1201,6 +1223,23 @@ static auto eval_system_with_statement_data_common(
12011223
};
12021224
}
12031225

1226+
auto field_type =
1227+
ecsact::meta::get_field_type(comp_like_id, *assoc_field_id);
1228+
1229+
if(field_type.kind == ECSACT_TYPE_KIND_BUILTIN) {
1230+
if(field_type.type.builtin != ECSACT_ENTITY_TYPE) {
1231+
return ecsact_eval_error{
1232+
.code = ECSACT_EVAL_ERR_INVALID_ASSOC_FIELD_TYPE,
1233+
.relevant_content = fields[i],
1234+
};
1235+
}
1236+
} else if(field_type.kind != ECSACT_TYPE_KIND_FIELD_INDEX) {
1237+
return ecsact_eval_error{
1238+
.code = ECSACT_EVAL_ERR_INVALID_ASSOC_FIELD_TYPE,
1239+
.relevant_content = fields[i],
1240+
};
1241+
}
1242+
12041243
with_field_ids.emplace_back(*assoc_field_id);
12051244
}
12061245

ecsact/interpret/eval_error.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -88,6 +88,9 @@ typedef enum ecsact_eval_error_code {
8888
/// Statement supports the given parameter name but the value is invalid
8989
ECSACT_EVAL_ERR_INVALID_PARAMETER_VALUE,
9090

91+
/// Field type is not allowed in 'with' statement
92+
ECSACT_EVAL_ERR_INVALID_ASSOC_FIELD_TYPE,
93+
9194
/// Internal error. Should not happen and is an indiciation of a bug.
9295
ECSACT_EVAL_ERR_INTERNAL = 999,
9396

test/errors/BUILD.bazel

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ load("@rules_cc//cc:defs.bzl", "cc_test")
44
# buildifier: keep sorted
55
_TESTS = [
66
"duplicate_notice_components",
7+
"invalid_assoc_field",
78
"invalid_notify_settings",
89
"no_capabilities",
910
"no_package_statement_first",
@@ -15,9 +16,9 @@ _TESTS = [
1516
[cc_test(
1617
name = test,
1718
srcs = ["{}.cc".format(test)],
19+
args = ["--gtest_catch_exceptions=0"],
1820
copts = copts,
1921
data = ["{}.ecsact".format(test)],
20-
args = ["--gtest_catch_exceptions=0"],
2122
deps = [
2223
"//:test_lib",
2324
"@ecsact_interpret",
@@ -29,12 +30,12 @@ _TESTS = [
2930
cc_test(
3031
name = "ambiguous_field_type",
3132
srcs = ["ambiguous_field_type.cc"],
33+
args = ["--gtest_catch_exceptions=0"],
3234
copts = copts,
3335
data = [
3436
"ambiguous_field_type.ecsact",
3537
"ambiguous_field_type_import.ecsact",
3638
],
37-
args = ["--gtest_catch_exceptions=0"],
3839
deps = [
3940
"//:test_lib",
4041
"@ecsact_interpret",

test/errors/invalid_assoc_field.cc

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
#include "gtest/gtest.h"
2+
#include "ecsact/interpret/eval.h"
3+
4+
#include "test_lib.hh"
5+
6+
TEST(InvalidAssocField, NonEntityBuiltin) {
7+
auto errs =
8+
ecsact_interpret_test_files({"errors/invalid_assoc_field.ecsact"});
9+
ASSERT_EQ(errs.size(), 1);
10+
ASSERT_EQ(errs[0].eval_error, ECSACT_EVAL_ERR_INVALID_ASSOC_FIELD_TYPE);
11+
}
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
main package invalid_assoc_field;
2+
3+
component A { i32 num; }
4+
5+
system S {
6+
readwrite A with num {
7+
readwrite A;
8+
}
9+
}

0 commit comments

Comments
 (0)