aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorgingerBill <bill@gingerbill.org>2022-05-25 21:29:45 +0100
committergingerBill <bill@gingerbill.org>2022-05-25 21:29:45 +0100
commit63cc8a80a045d48960d85640d11f39237c2f8ca4 (patch)
tree270f01c9c64ef01b7c4cc140f2c5e311e9c3f4d9 /src
parent1549d01bf76e8c5e13626e57b1f976330a9cdd50 (diff)
Correct parapoly for #simd
Diffstat (limited to 'src')
-rw-r--r--src/check_expr.cpp13
-rw-r--r--src/check_type.cpp4
-rw-r--r--src/types.cpp9
3 files changed, 23 insertions, 3 deletions
diff --git a/src/check_expr.cpp b/src/check_expr.cpp
index a30f83e7e..fcd7818bc 100644
--- a/src/check_expr.cpp
+++ b/src/check_expr.cpp
@@ -1328,6 +1328,19 @@ bool is_polymorphic_type_assignable(CheckerContext *c, Type *poly, Type *source,
}
}
return false;
+
+ case Type_SimdVector:
+ if (source->kind == Type_SimdVector) {
+ if (poly->SimdVector.generic_count != nullptr) {
+ if (!polymorphic_assign_index(&poly->SimdVector.generic_count, &poly->SimdVector.count, source->SimdVector.count)) {
+ return false;
+ }
+ }
+ if (poly->SimdVector.count == source->SimdVector.count) {
+ return is_polymorphic_type_assignable(c, poly->SimdVector.elem, source->SimdVector.elem, true, modify_type);
+ }
+ }
+ return false;
}
return false;
}
diff --git a/src/check_type.cpp b/src/check_type.cpp
index 088853810..354ab6e94 100644
--- a/src/check_type.cpp
+++ b/src/check_type.cpp
@@ -2803,14 +2803,14 @@ bool check_type_internal(CheckerContext *ctx, Ast *e, Type **type, Type *named_t
goto array_end;
}
if (is_type_polymorphic(elem)) {
- count = 1;
+ // Ignore
} else if (count < 1 || !is_power_of_two(count)) {
error(at->count, "Invalid length for 'intrinsics.simd_vector', expected a power of two length, got '%lld'", cast(long long)count);
*type = alloc_type_array(elem, count, generic_type);
goto array_end;
}
- *type = alloc_type_simd_vector(count, elem);
+ *type = alloc_type_simd_vector(count, elem, generic_type);
} else {
error(at->tag, "Invalid tag applied to array, got #%.*s", LIT(name));
*type = alloc_type_array(elem, count, generic_type);
diff --git a/src/types.cpp b/src/types.cpp
index 755f78f1c..2d5709b19 100644
--- a/src/types.cpp
+++ b/src/types.cpp
@@ -261,6 +261,7 @@ struct TypeProc {
TYPE_KIND(SimdVector, struct { \
i64 count; \
Type *elem; \
+ Type *generic_count; \
}) \
TYPE_KIND(RelativePointer, struct { \
Type *pointer_type; \
@@ -1085,10 +1086,11 @@ Type *alloc_type_bit_set() {
-Type *alloc_type_simd_vector(i64 count, Type *elem) {
+Type *alloc_type_simd_vector(i64 count, Type *elem, Type *generic_count=nullptr) {
Type *t = alloc_type(Type_SimdVector);
t->SimdVector.count = count;
t->SimdVector.elem = elem;
+ t->SimdVector.generic_count = generic_count;
return t;
}
@@ -2078,6 +2080,11 @@ bool is_type_polymorphic(Type *t, bool or_specialized=false) {
return true;
}
return is_type_polymorphic(t->Array.elem, or_specialized);
+ case Type_SimdVector:
+ if (t->SimdVector.generic_count != nullptr) {
+ return true;
+ }
+ return is_type_polymorphic(t->SimdVector.elem, or_specialized);
case Type_DynamicArray:
return is_type_polymorphic(t->DynamicArray.elem, or_specialized);
case Type_Slice: