diff options
Diffstat (limited to 'core/variant')
| -rw-r--r-- | core/variant/array.cpp | 6 | ||||
| -rw-r--r-- | core/variant/callable.cpp | 9 | ||||
| -rw-r--r-- | core/variant/callable.h | 7 | ||||
| -rw-r--r-- | core/variant/variant_call.cpp | 3 | ||||
| -rw-r--r-- | core/variant/variant_internal.h | 17 |
5 files changed, 31 insertions, 11 deletions
diff --git a/core/variant/array.cpp b/core/variant/array.cpp index 3c7e2a0719..09cf785390 100644 --- a/core/variant/array.cpp +++ b/core/variant/array.cpp @@ -366,8 +366,8 @@ Array Array::filter(const Callable &p_callable) const { new_arr.resize(size()); int accepted_count = 0; + const Variant *argptrs[1]; for (int i = 0; i < size(); i++) { - const Variant **argptrs = (const Variant **)alloca(sizeof(Variant *)); argptrs[0] = &get(i); Variant result; @@ -392,8 +392,8 @@ Array Array::map(const Callable &p_callable) const { Array new_arr; new_arr.resize(size()); + const Variant *argptrs[1]; for (int i = 0; i < size(); i++) { - const Variant **argptrs = (const Variant **)alloca(sizeof(Variant *)); argptrs[0] = &get(i); Variant result; @@ -417,8 +417,8 @@ Variant Array::reduce(const Callable &p_callable, const Variant &p_accum) const start = 1; } + const Variant *argptrs[2]; for (int i = start; i < size(); i++) { - const Variant **argptrs = (const Variant **)alloca(sizeof(Variant *) * 2); argptrs[0] = &ret; argptrs[1] = &get(i); diff --git a/core/variant/callable.cpp b/core/variant/callable.cpp index e06b3e07ef..5c87042f6b 100644 --- a/core/variant/callable.cpp +++ b/core/variant/callable.cpp @@ -50,6 +50,15 @@ void Callable::call(const Variant **p_arguments, int p_argcount, Variant &r_retu custom->call(p_arguments, p_argcount, r_return_value, r_call_error); } else { Object *obj = ObjectDB::get_instance(ObjectID(object)); +#ifdef DEBUG_ENABLED + if (!obj) { + r_call_error.error = CallError::CALL_ERROR_INSTANCE_IS_NULL; + r_call_error.argument = 0; + r_call_error.expected = 0; + r_return_value = Variant(); + return; + } +#endif r_return_value = obj->call(method, p_arguments, p_argcount, r_call_error); } } diff --git a/core/variant/callable.h b/core/variant/callable.h index d91bebfa5f..20d0804292 100644 --- a/core/variant/callable.h +++ b/core/variant/callable.h @@ -44,9 +44,9 @@ class CallableCustom; // is required. It is designed for the standard case (object and method) // but can be optimized or customized. +// Enforce 16 bytes with `alignas` to avoid arch-specific alignment issues on x86 vs armv7. class Callable { - //needs to be max 16 bytes in 64 bits - StringName method; + alignas(8) StringName method; union { uint64_t object = 0; CallableCustom *custom; @@ -138,8 +138,9 @@ public: // be put inside a Variant, but it is not // used by the engine itself. +// Enforce 16 bytes with `alignas` to avoid arch-specific alignment issues on x86 vs armv7. class Signal { - StringName name; + alignas(8) StringName name; ObjectID object; public: diff --git a/core/variant/variant_call.cpp b/core/variant/variant_call.cpp index efaaa8cd19..063611d415 100644 --- a/core/variant/variant_call.cpp +++ b/core/variant/variant_call.cpp @@ -611,6 +611,9 @@ struct _VariantCall { if (buffer_size <= 0) { ERR_FAIL_V_MSG(decompressed, "Decompression buffer size must be greater than zero."); } + if (p_instance->size() == 0) { + ERR_FAIL_V_MSG(decompressed, "Compressed buffer size must be greater than zero."); + } decompressed.resize(buffer_size); int result = Compression::decompress(decompressed.ptrw(), buffer_size, p_instance->ptr(), p_instance->size(), mode); diff --git a/core/variant/variant_internal.h b/core/variant/variant_internal.h index 7d33d85cd6..fb791f8c0c 100644 --- a/core/variant/variant_internal.h +++ b/core/variant/variant_internal.h @@ -43,18 +43,21 @@ public: v->type = p_type; switch (p_type) { - case Variant::AABB: - init_aabb(v); + case Variant::STRING: + init_string(v); break; case Variant::TRANSFORM2D: init_transform2d(v); break; + case Variant::AABB: + init_aabb(v); + break; + case Variant::BASIS: + init_basis(v); + break; case Variant::TRANSFORM: init_transform(v); break; - case Variant::STRING: - init_string(v); - break; case Variant::STRING_NAME: init_string_name(v); break; @@ -192,6 +195,10 @@ public: v->type = GetTypeInfo<T>::VARIANT_TYPE; } + // Should be in the same order as Variant::Type for consistency. + // Those primitive and vector types don't need an `init_` method: + // Nil, bool, float, Vector2/i, Rect2/i, Vector3/i, Plane, Quat, Color, RID. + // Object is a special case, handled via `object_assign_null`. _FORCE_INLINE_ static void init_string(Variant *v) { memnew_placement(v->_data._mem, String); v->type = Variant::STRING; |