diff options
Diffstat (limited to 'modules')
-rw-r--r-- | modules/gdscript/gdscript_functions.cpp | 57 | ||||
-rw-r--r-- | modules/gdscript/gdscript_tokenizer.cpp | 8 | ||||
-rw-r--r-- | modules/mono/glue/Managed/Files/GD.cs | 12 | ||||
-rw-r--r-- | modules/mono/glue/gd_glue.cpp | 10 | ||||
-rw-r--r-- | modules/mono/glue/gd_glue.h | 4 | ||||
-rw-r--r-- | modules/visual_script/visual_script_builtin_funcs.cpp | 43 |
6 files changed, 100 insertions, 34 deletions
diff --git a/modules/gdscript/gdscript_functions.cpp b/modules/gdscript/gdscript_functions.cpp index 44d44462ca..46c9efd54f 100644 --- a/modules/gdscript/gdscript_functions.cpp +++ b/modules/gdscript/gdscript_functions.cpp @@ -768,11 +768,30 @@ void GDScriptFunctions::call(Function p_func, const Variant **p_args, int p_arg_ (void)VariantParser::parse(&ss, r_ret, errs, line); } break; case VAR_TO_BYTES: { - VALIDATE_ARG_COUNT(1); + bool full_objects = false; + if (p_arg_count < 1) { + r_error.error = Variant::CallError::CALL_ERROR_TOO_FEW_ARGUMENTS; + r_error.argument = 1; + r_ret = Variant(); + return; + } else if (p_arg_count > 2) { + r_error.error = Variant::CallError::CALL_ERROR_TOO_MANY_ARGUMENTS; + r_error.argument = 2; + r_ret = Variant(); + } else if (p_arg_count == 2) { + if (p_args[1]->get_type() != Variant::BOOL) { + r_error.error = Variant::CallError::CALL_ERROR_INVALID_ARGUMENT; + r_error.argument = 1; + r_error.expected = Variant::BOOL; + r_ret = Variant(); + return; + } + full_objects = *p_args[1]; + } PoolByteArray barr; int len; - Error err = encode_variant(*p_args[0], NULL, len); + Error err = encode_variant(*p_args[0], NULL, len, full_objects); if (err) { r_error.error = Variant::CallError::CALL_ERROR_INVALID_ARGUMENT; r_error.argument = 0; @@ -784,15 +803,35 @@ void GDScriptFunctions::call(Function p_func, const Variant **p_args, int p_arg_ barr.resize(len); { PoolByteArray::Write w = barr.write(); - encode_variant(*p_args[0], w.ptr(), len); + encode_variant(*p_args[0], w.ptr(), len, full_objects); } r_ret = barr; } break; case BYTES_TO_VAR: { - VALIDATE_ARG_COUNT(1); + bool allow_objects = false; + if (p_arg_count < 1) { + r_error.error = Variant::CallError::CALL_ERROR_TOO_FEW_ARGUMENTS; + r_error.argument = 1; + r_ret = Variant(); + return; + } else if (p_arg_count > 2) { + r_error.error = Variant::CallError::CALL_ERROR_TOO_MANY_ARGUMENTS; + r_error.argument = 2; + r_ret = Variant(); + } else if (p_arg_count == 2) { + if (p_args[1]->get_type() != Variant::BOOL) { + r_error.error = Variant::CallError::CALL_ERROR_INVALID_ARGUMENT; + r_error.argument = 1; + r_error.expected = Variant::BOOL; + r_ret = Variant(); + return; + } + allow_objects = *p_args[1]; + } + if (p_args[0]->get_type() != Variant::POOL_BYTE_ARRAY) { r_error.error = Variant::CallError::CALL_ERROR_INVALID_ARGUMENT; - r_error.argument = 0; + r_error.argument = 1; r_error.expected = Variant::POOL_BYTE_ARRAY; r_ret = Variant(); return; @@ -802,7 +841,7 @@ void GDScriptFunctions::call(Function p_func, const Variant **p_args, int p_arg_ Variant ret; { PoolByteArray::Read r = varr.read(); - Error err = decode_variant(ret, r.ptr(), varr.size(), NULL); + Error err = decode_variant(ret, r.ptr(), varr.size(), NULL, allow_objects); if (err != OK) { r_ret = RTR("Not enough bytes for decoding bytes, or invalid format."); r_error.error = Variant::CallError::CALL_ERROR_INVALID_ARGUMENT; @@ -1805,13 +1844,15 @@ MethodInfo GDScriptFunctions::get_info(Function p_func) { } break; case VAR_TO_BYTES: { - MethodInfo mi("var2bytes", PropertyInfo(Variant::NIL, "var", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_DEFAULT | PROPERTY_USAGE_NIL_IS_VARIANT)); + MethodInfo mi("var2bytes", PropertyInfo(Variant::NIL, "var", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_DEFAULT | PROPERTY_USAGE_NIL_IS_VARIANT), PropertyInfo(Variant::BOOL, "full_objects")); + mi.default_arguments.push_back(false); mi.return_val.type = Variant::POOL_BYTE_ARRAY; return mi; } break; case BYTES_TO_VAR: { - MethodInfo mi(Variant::NIL, "bytes2var", PropertyInfo(Variant::POOL_BYTE_ARRAY, "bytes")); + MethodInfo mi(Variant::NIL, "bytes2var", PropertyInfo(Variant::POOL_BYTE_ARRAY, "bytes"), PropertyInfo(Variant::BOOL, "allow_objects")); + mi.default_arguments.push_back(false); mi.return_val.type = Variant::NIL; mi.return_val.usage |= PROPERTY_USAGE_NIL_IS_VARIANT; return mi; diff --git a/modules/gdscript/gdscript_tokenizer.cpp b/modules/gdscript/gdscript_tokenizer.cpp index 8b22d6f085..8962e3bb34 100644 --- a/modules/gdscript/gdscript_tokenizer.cpp +++ b/modules/gdscript/gdscript_tokenizer.cpp @@ -1199,7 +1199,8 @@ Error GDScriptTokenizerBuffer::set_code_buffer(const Vector<uint8_t> &p_buffer) Variant v; int len; - Error err = decode_variant(v, b, total_len, &len); + // An object cannot be constant, never decode objects + Error err = decode_variant(v, b, total_len, &len, false); if (err) return err; b += len; @@ -1367,11 +1368,12 @@ Vector<uint8_t> GDScriptTokenizerBuffer::parse_code_string(const String &p_code) for (Map<int, Variant>::Element *E = rev_constant_map.front(); E; E = E->next()) { int len; - Error err = encode_variant(E->get(), NULL, len); + // Objects cannot be constant, never encode objects + Error err = encode_variant(E->get(), NULL, len, false); ERR_FAIL_COND_V(err != OK, Vector<uint8_t>()); int pos = buf.size(); buf.resize(pos + len); - encode_variant(E->get(), &buf.write[pos], len); + encode_variant(E->get(), &buf.write[pos], len, false); } for (Map<int, uint32_t>::Element *E = rev_line_map.front(); E; E = E->next()) { diff --git a/modules/mono/glue/Managed/Files/GD.cs b/modules/mono/glue/Managed/Files/GD.cs index 3afaf5d08b..aaae72fbe3 100644 --- a/modules/mono/glue/Managed/Files/GD.cs +++ b/modules/mono/glue/Managed/Files/GD.cs @@ -13,9 +13,9 @@ namespace Godot { public static partial class GD { - public static object Bytes2Var(byte[] bytes) + public static object Bytes2Var(byte[] bytes, bool allow_objects = false) { - return godot_icall_GD_bytes2var(bytes); + return godot_icall_GD_bytes2var(bytes, allow_objects); } public static object Convert(object what, int type) @@ -186,9 +186,9 @@ namespace Godot return godot_icall_GD_type_exists(type); } - public static byte[] Var2Bytes(object var) + public static byte[] Var2Bytes(object var, bool full_objects = false) { - return godot_icall_GD_var2bytes(var); + return godot_icall_GD_var2bytes(var, full_objects); } public static string Var2Str(object var) @@ -197,7 +197,7 @@ namespace Godot } [MethodImpl(MethodImplOptions.InternalCall)] - internal extern static object godot_icall_GD_bytes2var(byte[] bytes); + internal extern static object godot_icall_GD_bytes2var(byte[] bytes, bool allow_objects); [MethodImpl(MethodImplOptions.InternalCall)] internal extern static object godot_icall_GD_convert(object what, int type); @@ -251,7 +251,7 @@ namespace Godot internal extern static bool godot_icall_GD_type_exists(string type); [MethodImpl(MethodImplOptions.InternalCall)] - internal extern static byte[] godot_icall_GD_var2bytes(object what); + internal extern static byte[] godot_icall_GD_var2bytes(object what, bool full_objects); [MethodImpl(MethodImplOptions.InternalCall)] internal extern static string godot_icall_GD_var2str(object var); diff --git a/modules/mono/glue/gd_glue.cpp b/modules/mono/glue/gd_glue.cpp index af022dae81..d756131ac9 100644 --- a/modules/mono/glue/gd_glue.cpp +++ b/modules/mono/glue/gd_glue.cpp @@ -41,11 +41,11 @@ #include "../mono_gd/gd_mono_utils.h" -MonoObject *godot_icall_GD_bytes2var(MonoArray *p_bytes) { +MonoObject *godot_icall_GD_bytes2var(MonoArray *p_bytes, MonoBoolean p_allow_objects) { Variant ret; PoolByteArray varr = GDMonoMarshal::mono_array_to_PoolByteArray(p_bytes); PoolByteArray::Read r = varr.read(); - Error err = decode_variant(ret, r.ptr(), varr.size(), NULL); + Error err = decode_variant(ret, r.ptr(), varr.size(), NULL, p_allow_objects); if (err != OK) { ret = RTR("Not enough bytes for decoding bytes, or invalid format."); } @@ -187,19 +187,19 @@ void godot_icall_GD_pushwarning(MonoString *p_str) { WARN_PRINTS(GDMonoMarshal::mono_string_to_godot(p_str)); } -MonoArray *godot_icall_GD_var2bytes(MonoObject *p_var) { +MonoArray *godot_icall_GD_var2bytes(MonoObject *p_var, MonoBoolean p_full_objects) { Variant var = GDMonoMarshal::mono_object_to_variant(p_var); PoolByteArray barr; int len; - Error err = encode_variant(var, NULL, len); + Error err = encode_variant(var, NULL, len, p_full_objects); ERR_EXPLAIN("Unexpected error encoding variable to bytes, likely unserializable type found (Object or RID)."); ERR_FAIL_COND_V(err != OK, NULL); barr.resize(len); { PoolByteArray::Write w = barr.write(); - encode_variant(var, w.ptr(), len); + encode_variant(var, w.ptr(), len, p_full_objects); } return GDMonoMarshal::PoolByteArray_to_mono_array(barr); diff --git a/modules/mono/glue/gd_glue.h b/modules/mono/glue/gd_glue.h index 2632639169..910979aae3 100644 --- a/modules/mono/glue/gd_glue.h +++ b/modules/mono/glue/gd_glue.h @@ -35,7 +35,7 @@ #include "../mono_gd/gd_mono_marshal.h" -MonoObject *godot_icall_GD_bytes2var(MonoArray *p_bytes); +MonoObject *godot_icall_GD_bytes2var(MonoArray *p_bytes, MonoBoolean p_allow_objects); MonoObject *godot_icall_GD_convert(MonoObject *p_what, int32_t p_type); @@ -71,7 +71,7 @@ MonoObject *godot_icall_GD_str2var(MonoString *p_str); MonoBoolean godot_icall_GD_type_exists(MonoString *p_type); -MonoArray *godot_icall_GD_var2bytes(MonoObject *p_var); +MonoArray *godot_icall_GD_var2bytes(MonoObject *p_var, MonoBoolean p_full_objects); MonoString *godot_icall_GD_var2str(MonoObject *p_var); diff --git a/modules/visual_script/visual_script_builtin_funcs.cpp b/modules/visual_script/visual_script_builtin_funcs.cpp index 9f2d1a49c0..0d379205e4 100644 --- a/modules/visual_script/visual_script_builtin_funcs.cpp +++ b/modules/visual_script/visual_script_builtin_funcs.cpp @@ -183,10 +183,10 @@ int VisualScriptBuiltinFunc::get_func_argument_count(BuiltinFunc p_func) { case TEXT_PRINTRAW: case VAR_TO_STR: case STR_TO_VAR: - case VAR_TO_BYTES: - case BYTES_TO_VAR: case TYPE_EXISTS: return 1; + case VAR_TO_BYTES: + case BYTES_TO_VAR: case MATH_ATAN2: case MATH_FMOD: case MATH_FPOSMOD: @@ -491,12 +491,18 @@ PropertyInfo VisualScriptBuiltinFunc::get_input_value_port_info(int p_idx) const return PropertyInfo(Variant::STRING, "string"); } break; case VAR_TO_BYTES: { - return PropertyInfo(Variant::NIL, "var"); + if (p_idx == 0) + return PropertyInfo(Variant::NIL, "var"); + else + return PropertyInfo(Variant::BOOL, "full_objects"); } break; case BYTES_TO_VAR: { - return PropertyInfo(Variant::POOL_BYTE_ARRAY, "bytes"); + if (p_idx == 0) + return PropertyInfo(Variant::POOL_BYTE_ARRAY, "bytes"); + else + return PropertyInfo(Variant::BOOL, "allow_objects"); } break; case COLORN: { @@ -655,11 +661,15 @@ PropertyInfo VisualScriptBuiltinFunc::get_output_value_port_info(int p_idx) cons } break; case VAR_TO_BYTES: { - t = Variant::POOL_BYTE_ARRAY; + if (p_idx == 0) + t = Variant::POOL_BYTE_ARRAY; + else + t = Variant::BOOL; } break; case BYTES_TO_VAR: { - + if (p_idx == 1) + t = Variant::BOOL; } break; case COLORN: { t = Variant::COLOR; @@ -1192,9 +1202,16 @@ void VisualScriptBuiltinFunc::exec_func(BuiltinFunc p_func, const Variant **p_in } break; case VisualScriptBuiltinFunc::VAR_TO_BYTES: { + if (p_inputs[1]->get_type() != Variant::BOOL) { + r_error.error = Variant::CallError::CALL_ERROR_INVALID_ARGUMENT; + r_error.argument = 1; + r_error.expected = Variant::BOOL; + return; + } PoolByteArray barr; int len; - Error err = encode_variant(*p_inputs[0], NULL, len); + bool full_objects = *p_inputs[1]; + Error err = encode_variant(*p_inputs[0], NULL, len, full_objects); if (err) { r_error.error = Variant::CallError::CALL_ERROR_INVALID_ARGUMENT; r_error.argument = 0; @@ -1206,7 +1223,7 @@ void VisualScriptBuiltinFunc::exec_func(BuiltinFunc p_func, const Variant **p_in barr.resize(len); { PoolByteArray::Write w = barr.write(); - encode_variant(*p_inputs[0], w.ptr(), len); + encode_variant(*p_inputs[0], w.ptr(), len, full_objects); } *r_return = barr; } break; @@ -1216,15 +1233,21 @@ void VisualScriptBuiltinFunc::exec_func(BuiltinFunc p_func, const Variant **p_in r_error.error = Variant::CallError::CALL_ERROR_INVALID_ARGUMENT; r_error.argument = 0; r_error.expected = Variant::POOL_BYTE_ARRAY; - + return; + } + if (p_inputs[1]->get_type() != Variant::BOOL) { + r_error.error = Variant::CallError::CALL_ERROR_INVALID_ARGUMENT; + r_error.argument = 1; + r_error.expected = Variant::BOOL; return; } PoolByteArray varr = *p_inputs[0]; + bool allow_objects = *p_inputs[1]; Variant ret; { PoolByteArray::Read r = varr.read(); - Error err = decode_variant(ret, r.ptr(), varr.size(), NULL); + Error err = decode_variant(ret, r.ptr(), varr.size(), NULL, allow_objects); if (err != OK) { r_error_str = RTR("Not enough bytes for decoding bytes, or invalid format."); r_error.error = Variant::CallError::CALL_ERROR_INVALID_ARGUMENT; |