diff options
Diffstat (limited to 'modules')
38 files changed, 307 insertions, 116 deletions
diff --git a/modules/basis_universal/SCsub b/modules/basis_universal/SCsub index 351628a0e3..1f9fde966d 100644 --- a/modules/basis_universal/SCsub +++ b/modules/basis_universal/SCsub @@ -11,40 +11,45 @@ thirdparty_obj = [] # Not unbundled so far since not widespread as shared library thirdparty_dir = "#thirdparty/basis_universal/" -tool_sources = [ +# Sync list with upstream CMakeLists.txt +encoder_sources = [ + "apg_bmp.c", "basisu_astc_decomp.cpp", "basisu_backend.cpp", "basisu_basis_file.cpp", + "basisu_bc7enc.cpp", "basisu_comp.cpp", "basisu_enc.cpp", "basisu_etc.cpp", "basisu_frontend.cpp", "basisu_global_selector_palette_helpers.cpp", "basisu_gpu_texture.cpp", + "basisu_kernels_sse.cpp", "basisu_pvrtc1_4.cpp", - "basisu_resample_filters.cpp", "basisu_resampler.cpp", + "basisu_resample_filters.cpp", "basisu_ssim.cpp", + "basisu_uastc_enc.cpp", + "jpgd.cpp", "lodepng.cpp", ] -tool_sources = [thirdparty_dir + file for file in tool_sources] +encoder_sources = [thirdparty_dir + "encoder/" + file for file in encoder_sources] transcoder_sources = [thirdparty_dir + "transcoder/basisu_transcoder.cpp"] # Treat Basis headers as system headers to avoid raising warnings. Not supported on MSVC. if not env.msvc: - env_basisu.Append( - CPPFLAGS=["-isystem", Dir(thirdparty_dir).path, "-isystem", Dir(thirdparty_dir + "transcoder").path] - ) + env_basisu.Append(CPPFLAGS=["-isystem", Dir(thirdparty_dir).path]) else: - env_basisu.Prepend(CPPPATH=[thirdparty_dir, thirdparty_dir + "transcoder"]) + env_basisu.Prepend(CPPPATH=[thirdparty_dir]) if env["target"] == "debug": - env_basisu.Append(CPPFLAGS=["-DBASISU_DEVEL_MESSAGES=1", "-DBASISD_ENABLE_DEBUG_FLAGS=1"]) + env_basisu.Append(CPPDEFINES=[("BASISU_DEVEL_MESSAGES", 1), ("BASISD_ENABLE_DEBUG_FLAGS", 1)]) env_thirdparty = env_basisu.Clone() env_thirdparty.disable_warnings() if env["tools"]: - env_thirdparty.add_source_files(thirdparty_obj, tool_sources) + env_thirdparty.Append(CPPDEFINES=["BASISU_NO_IMG_LOADERS"]) + env_thirdparty.add_source_files(thirdparty_obj, encoder_sources) env_thirdparty.add_source_files(thirdparty_obj, transcoder_sources) env.modules_sources += thirdparty_obj diff --git a/modules/basis_universal/register_types.cpp b/modules/basis_universal/register_types.cpp index cf5581265b..772ac87dbf 100644 --- a/modules/basis_universal/register_types.cpp +++ b/modules/basis_universal/register_types.cpp @@ -35,7 +35,7 @@ #include "texture_basisu.h" #ifdef TOOLS_ENABLED -#include <basisu_comp.h> +#include <encoder/basisu_comp.h> #endif #include <transcoder/basisu_transcoder.h> @@ -233,7 +233,7 @@ static Ref<Image> basis_universal_unpacker(const Vector<uint8_t> &p_buffer) { basist::basisu_image_info info; tr.get_image_info(ptr, size, info, 0); - int block_size = basist::basis_get_bytes_per_block(format); + int block_size = basist::basis_get_bytes_per_block_or_pixel(format); Vector<uint8_t> gpudata; gpudata.resize(info.m_total_blocks * block_size); diff --git a/modules/basis_universal/texture_basisu.cpp b/modules/basis_universal/texture_basisu.cpp index 92882a1cc8..6a5f6313c4 100644 --- a/modules/basis_universal/texture_basisu.cpp +++ b/modules/basis_universal/texture_basisu.cpp @@ -33,7 +33,7 @@ #include "core/os/os.h" #ifdef TOOLS_ENABLED -#include <basisu_comp.h> +#include <encoder/basisu_comp.h> #endif #include <transcoder/basisu_transcoder.h> diff --git a/modules/basis_universal/texture_basisu.h b/modules/basis_universal/texture_basisu.h index 282a0dfc8a..3316035404 100644 --- a/modules/basis_universal/texture_basisu.h +++ b/modules/basis_universal/texture_basisu.h @@ -34,7 +34,7 @@ #include "scene/resources/texture.h" #ifdef TOOLS_ENABLED -#include <basisu_comp.h> +#include <encoder/basisu_comp.h> #endif #include <transcoder/basisu_transcoder.h> diff --git a/modules/bmp/image_loader_bmp.cpp b/modules/bmp/image_loader_bmp.cpp index c7fdf56af4..f22e74cafb 100644 --- a/modules/bmp/image_loader_bmp.cpp +++ b/modules/bmp/image_loader_bmp.cpp @@ -130,23 +130,19 @@ Error ImageLoaderBMP::convert_to_image(Ref<Image> p_image, line_ptr += 1; } break; case 24: { - uint32_t color = *((uint32_t *)line_ptr); - - write_buffer[index + 2] = color & 0xff; - write_buffer[index + 1] = (color >> 8) & 0xff; - write_buffer[index + 0] = (color >> 16) & 0xff; + write_buffer[index + 2] = line_ptr[0]; + write_buffer[index + 1] = line_ptr[1]; + write_buffer[index + 0] = line_ptr[2]; write_buffer[index + 3] = 0xff; index += 4; line_ptr += 3; } break; case 32: { - uint32_t color = *((uint32_t *)line_ptr); - - write_buffer[index + 2] = color & 0xff; - write_buffer[index + 1] = (color >> 8) & 0xff; - write_buffer[index + 0] = (color >> 16) & 0xff; - write_buffer[index + 3] = color >> 24; + write_buffer[index + 2] = line_ptr[0]; + write_buffer[index + 1] = line_ptr[1]; + write_buffer[index + 0] = line_ptr[2]; + write_buffer[index + 3] = line_ptr[3]; index += 4; line_ptr += 4; @@ -172,11 +168,9 @@ Error ImageLoaderBMP::convert_to_image(Ref<Image> p_image, const uint8_t *cb = p_color_buffer; for (unsigned int i = 0; i < color_table_size; ++i) { - uint32_t color = *((uint32_t *)cb); - - pal[i * 4 + 0] = (color >> 16) & 0xff; - pal[i * 4 + 1] = (color >> 8) & 0xff; - pal[i * 4 + 2] = (color)&0xff; + pal[i * 4 + 0] = cb[2]; + pal[i * 4 + 1] = cb[1]; + pal[i * 4 + 2] = cb[0]; pal[i * 4 + 3] = 0xff; cb += 4; diff --git a/modules/gdnative/include/gdnative/callable.h b/modules/gdnative/include/gdnative/callable.h index b84b0c1f1f..1d52ca7a68 100644 --- a/modules/gdnative/include/gdnative/callable.h +++ b/modules/gdnative/include/gdnative/callable.h @@ -37,6 +37,7 @@ extern "C" { #include <stdint.h> +// Alignment hardcoded in `core/variant/callable.h`. #define GODOT_CALLABLE_SIZE (16) #ifndef GODOT_CORE_API_GODOT_CALLABLE_TYPE_DEFINED diff --git a/modules/gdnative/include/gdnative/signal.h b/modules/gdnative/include/gdnative/signal.h index f4dc17e089..41a76d0510 100644 --- a/modules/gdnative/include/gdnative/signal.h +++ b/modules/gdnative/include/gdnative/signal.h @@ -37,6 +37,7 @@ extern "C" { #include <stdint.h> +// Alignment hardcoded in `core/variant/callable.h`. #define GODOT_SIGNAL_SIZE (16) #ifndef GODOT_CORE_API_GODOT_SIGNAL_TYPE_DEFINED diff --git a/modules/gdnative/pluginscript/pluginscript_script.cpp b/modules/gdnative/pluginscript/pluginscript_script.cpp index 31e6a81975..a0d7fbf726 100644 --- a/modules/gdnative/pluginscript/pluginscript_script.cpp +++ b/modules/gdnative/pluginscript/pluginscript_script.cpp @@ -441,10 +441,10 @@ Error PluginScript::load_source_code(const String &p_path) { FileAccess *f = FileAccess::open(p_path, FileAccess::READ, &err); ERR_FAIL_COND_V_MSG(err, err, "Cannot open file '" + p_path + "'."); - int len = f->get_len(); + uint64_t len = f->get_len(); sourcef.resize(len + 1); uint8_t *w = sourcef.ptrw(); - int r = f->get_buffer(w, len); + uint64_t r = f->get_buffer(w, len); f->close(); memdelete(f); ERR_FAIL_COND_V(r != len, ERR_CANT_OPEN); diff --git a/modules/gdnative/videodecoder/video_stream_gdnative.cpp b/modules/gdnative/videodecoder/video_stream_gdnative.cpp index f2fb0a2fdc..1b7838846f 100644 --- a/modules/gdnative/videodecoder/video_stream_gdnative.cpp +++ b/modules/gdnative/videodecoder/video_stream_gdnative.cpp @@ -47,11 +47,7 @@ godot_int GDAPI godot_videodecoder_file_read(void *ptr, uint8_t *buf, int buf_si // if file exists if (file) { - long bytes_read = file->get_buffer(buf, buf_size); - // No bytes to read => EOF - if (bytes_read == 0) { - return 0; - } + int64_t bytes_read = file->get_buffer(buf, buf_size); return bytes_read; } return -1; @@ -62,41 +58,35 @@ int64_t GDAPI godot_videodecoder_file_seek(void *ptr, int64_t pos, int whence) { FileAccess *file = reinterpret_cast<FileAccess *>(ptr); if (file) { - size_t len = file->get_len(); + int64_t len = file->get_len(); switch (whence) { case SEEK_SET: { - // Just for explicitness - size_t new_pos = static_cast<size_t>(pos); - if (new_pos > len) { + if (pos > len) { return -1; } - file->seek(new_pos); - pos = static_cast<int64_t>(file->get_position()); - return pos; + file->seek(pos); + return file->get_position(); } break; case SEEK_CUR: { // Just in case it doesn't exist - if (pos < 0 && (size_t)-pos > file->get_position()) { + if (pos < 0 && -pos > (int64_t)file->get_position()) { return -1; } - pos = pos + static_cast<int>(file->get_position()); - file->seek(pos); - pos = static_cast<int64_t>(file->get_position()); - return pos; + file->seek(file->get_position() + pos); + return file->get_position(); } break; case SEEK_END: { // Just in case something goes wrong - if ((size_t)-pos > len) { + if (-pos > len) { return -1; } file->seek_end(pos); - pos = static_cast<int64_t>(file->get_position()); - return pos; + return file->get_position(); } break; default: { // Only 4 possible options, hence default = AVSEEK_SIZE // Asks to return the length of file - return static_cast<int64_t>(len); + return len; } break; } } diff --git a/modules/gdscript/gdscript.cpp b/modules/gdscript/gdscript.cpp index 859c1acde9..9206f4095a 100644 --- a/modules/gdscript/gdscript.cpp +++ b/modules/gdscript/gdscript.cpp @@ -1045,10 +1045,10 @@ Error GDScript::load_source_code(const String &p_path) { ERR_FAIL_COND_V(err, err); } - int len = f->get_len(); + uint64_t len = f->get_len(); sourcef.resize(len + 1); uint8_t *w = sourcef.ptrw(); - int r = f->get_buffer(w, len); + uint64_t r = f->get_buffer(w, len); f->close(); memdelete(f); ERR_FAIL_COND_V(r != len, ERR_CANT_OPEN); diff --git a/modules/gdscript/gdscript_analyzer.cpp b/modules/gdscript/gdscript_analyzer.cpp index 17ae52f3ab..7b04959227 100644 --- a/modules/gdscript/gdscript_analyzer.cpp +++ b/modules/gdscript/gdscript_analyzer.cpp @@ -2078,9 +2078,23 @@ void GDScriptAnalyzer::reduce_call(GDScriptParser::CallNode *p_call, bool is_awa mark_node_unsafe(p_call); return; } - reduce_expression(subscript->base); + if (subscript->attribute == nullptr) { + // Invalid call. Error already sent in parser. + p_call->set_datatype(call_type); + mark_node_unsafe(p_call); + return; + } - base_type = subscript->base->get_datatype(); + GDScriptParser::IdentifierNode *base_id = nullptr; + if (subscript->base->type == GDScriptParser::Node::IDENTIFIER) { + base_id = static_cast<GDScriptParser::IdentifierNode *>(subscript->base); + } + if (base_id && GDScriptParser::get_builtin_type(base_id->name) < Variant::VARIANT_MAX) { + base_type = make_builtin_meta_type(GDScriptParser::get_builtin_type(base_id->name)); + } else { + reduce_expression(subscript->base); + base_type = subscript->base->get_datatype(); + } } else { // Invalid call. Error already sent in parser. // TODO: Could check if Callable here too. diff --git a/modules/gdscript/gdscript_byte_codegen.cpp b/modules/gdscript/gdscript_byte_codegen.cpp index 0da99ccee3..ea34a2ca2d 100644 --- a/modules/gdscript/gdscript_byte_codegen.cpp +++ b/modules/gdscript/gdscript_byte_codegen.cpp @@ -129,12 +129,6 @@ uint32_t GDScriptByteCodeGenerator::add_temporary(const GDScriptDataType &p_type int idx = temporaries.size(); pool.push_back(idx); temporaries.push_back(new_temp); - - // First time using this, so adjust to the proper type. - if (temp_type != Variant::NIL) { - Address addr(Address::TEMPORARY, idx, p_type); - write_type_adjust(addr, temp_type); - } } int slot = pool.front()->get(); pool.pop_front(); @@ -189,8 +183,12 @@ GDScriptFunction *GDScriptByteCodeGenerator::write_end() { append(GDScriptFunction::OPCODE_END, 0); for (int i = 0; i < temporaries.size(); i++) { + int stack_index = i + max_locals + RESERVED_STACK; for (int j = 0; j < temporaries[i].bytecode_indices.size(); j++) { - opcodes.write[temporaries[i].bytecode_indices[j]] = (i + max_locals + RESERVED_STACK) | (GDScriptFunction::ADDR_TYPE_STACK << GDScriptFunction::ADDR_BITS); + opcodes.write[temporaries[i].bytecode_indices[j]] = stack_index | (GDScriptFunction::ADDR_TYPE_STACK << GDScriptFunction::ADDR_BITS); + } + if (temporaries[i].type != Variant::NIL) { + function->temporary_slots[stack_index] = temporaries[i].type; } } @@ -1017,6 +1015,56 @@ void GDScriptByteCodeGenerator::write_call_builtin_type(const Address &p_target, append(Variant::get_validated_builtin_method(p_type, p_method)); } +void GDScriptByteCodeGenerator::write_call_builtin_type_static(const Address &p_target, Variant::Type p_type, const StringName &p_method, const Vector<Address> &p_arguments) { + bool is_validated = false; + + // Check if all types are correct. + if (Variant::is_builtin_method_vararg(p_type, p_method)) { + is_validated = true; // Vararg works fine with any argument, since they can be any type. + } else if (p_arguments.size() == Variant::get_builtin_method_argument_count(p_type, p_method)) { + bool all_types_exact = true; + for (int i = 0; i < p_arguments.size(); i++) { + if (!IS_BUILTIN_TYPE(p_arguments[i], Variant::get_builtin_method_argument_type(p_type, p_method, i))) { + all_types_exact = false; + break; + } + } + + is_validated = all_types_exact; + } + + if (!is_validated) { + // Perform regular call. + append(GDScriptFunction::OPCODE_CALL_BUILTIN_STATIC, p_arguments.size() + 1); + for (int i = 0; i < p_arguments.size(); i++) { + append(p_arguments[i]); + } + append(p_target); + append(p_type); + append(p_method); + append(p_arguments.size()); + return; + } + + if (p_target.mode == Address::TEMPORARY) { + Variant::Type result_type = Variant::get_builtin_method_return_type(p_type, p_method); + Variant::Type temp_type = temporaries[p_target.address].type; + if (result_type != temp_type) { + write_type_adjust(p_target, result_type); + } + } + + append(GDScriptFunction::OPCODE_CALL_BUILTIN_TYPE_VALIDATED, 2 + p_arguments.size()); + + for (int i = 0; i < p_arguments.size(); i++) { + append(p_arguments[i]); + } + append(Address()); // No base since it's static. + append(p_target); + append(p_arguments.size()); + append(Variant::get_validated_builtin_method(p_type, p_method)); +} + void GDScriptByteCodeGenerator::write_call_method_bind(const Address &p_target, const Address &p_base, MethodBind *p_method, const Vector<Address> &p_arguments) { append(p_target.mode == Address::NIL ? GDScriptFunction::OPCODE_CALL_METHOD_BIND : GDScriptFunction::OPCODE_CALL_METHOD_BIND_RET, 2 + p_arguments.size()); for (int i = 0; i < p_arguments.size(); i++) { diff --git a/modules/gdscript/gdscript_byte_codegen.h b/modules/gdscript/gdscript_byte_codegen.h index c060476f39..f8c05fea83 100644 --- a/modules/gdscript/gdscript_byte_codegen.h +++ b/modules/gdscript/gdscript_byte_codegen.h @@ -461,6 +461,7 @@ public: virtual void write_call_utility(const Address &p_target, const StringName &p_function, const Vector<Address> &p_arguments) override; virtual void write_call_gdscript_utility(const Address &p_target, GDScriptUtilityFunctions::FunctionPtr p_function, const Vector<Address> &p_arguments) override; virtual void write_call_builtin_type(const Address &p_target, const Address &p_base, Variant::Type p_type, const StringName &p_method, const Vector<Address> &p_arguments) override; + virtual void write_call_builtin_type_static(const Address &p_target, Variant::Type p_type, const StringName &p_method, const Vector<Address> &p_arguments) override; virtual void write_call_method_bind(const Address &p_target, const Address &p_base, MethodBind *p_method, const Vector<Address> &p_arguments) override; virtual void write_call_ptrcall(const Address &p_target, const Address &p_base, MethodBind *p_method, const Vector<Address> &p_arguments) override; virtual void write_call_self(const Address &p_target, const StringName &p_function_name, const Vector<Address> &p_arguments) override; diff --git a/modules/gdscript/gdscript_cache.cpp b/modules/gdscript/gdscript_cache.cpp index 113d36be98..6aa76703f1 100644 --- a/modules/gdscript/gdscript_cache.cpp +++ b/modules/gdscript/gdscript_cache.cpp @@ -153,9 +153,9 @@ String GDScriptCache::get_source_code(const String &p_path) { ERR_FAIL_COND_V(err, ""); } - int len = f->get_len(); + uint64_t len = f->get_len(); source_file.resize(len + 1); - int r = f->get_buffer(source_file.ptrw(), len); + uint64_t r = f->get_buffer(source_file.ptrw(), len); f->close(); ERR_FAIL_COND_V(r != len, ""); source_file.write[len] = 0; diff --git a/modules/gdscript/gdscript_codegen.h b/modules/gdscript/gdscript_codegen.h index ae9a8ede5e..399c9d6de7 100644 --- a/modules/gdscript/gdscript_codegen.h +++ b/modules/gdscript/gdscript_codegen.h @@ -122,6 +122,7 @@ public: virtual void write_call_utility(const Address &p_target, const StringName &p_function, const Vector<Address> &p_arguments) = 0; virtual void write_call_gdscript_utility(const Address &p_target, GDScriptUtilityFunctions::FunctionPtr p_function, const Vector<Address> &p_arguments) = 0; virtual void write_call_builtin_type(const Address &p_target, const Address &p_base, Variant::Type p_type, const StringName &p_method, const Vector<Address> &p_arguments) = 0; + virtual void write_call_builtin_type_static(const Address &p_target, Variant::Type p_type, const StringName &p_method, const Vector<Address> &p_arguments) = 0; virtual void write_call_method_bind(const Address &p_target, const Address &p_base, MethodBind *p_method, const Vector<Address> &p_arguments) = 0; virtual void write_call_ptrcall(const Address &p_target, const Address &p_base, MethodBind *p_method, const Vector<Address> &p_arguments) = 0; virtual void write_call_self(const Address &p_target, const StringName &p_function_name, const Vector<Address> &p_arguments) = 0; diff --git a/modules/gdscript/gdscript_compiler.cpp b/modules/gdscript/gdscript_compiler.cpp index 37ce8ae2cb..f495b0d787 100644 --- a/modules/gdscript/gdscript_compiler.cpp +++ b/modules/gdscript/gdscript_compiler.cpp @@ -537,39 +537,44 @@ GDScriptCodeGenerator::Address GDScriptCompiler::_parse_expression(CodeGen &code const GDScriptParser::SubscriptNode *subscript = static_cast<const GDScriptParser::SubscriptNode *>(call->callee); if (subscript->is_attribute) { - GDScriptCodeGenerator::Address base = _parse_expression(codegen, r_error, subscript->base); - if (r_error) { - return GDScriptCodeGenerator::Address(); - } - if (within_await) { - gen->write_call_async(result, base, call->function_name, arguments); - } else if (base.type.has_type && base.type.kind != GDScriptDataType::BUILTIN) { - // Native method, use faster path. - StringName class_name; - if (base.type.kind == GDScriptDataType::NATIVE) { - class_name = base.type.native_type; - } else { - class_name = base.type.native_type == StringName() ? base.type.script_type->get_instance_base_type() : base.type.native_type; + // May be static built-in method call. + if (!call->is_super && subscript->base->type == GDScriptParser::Node::IDENTIFIER && GDScriptParser::get_builtin_type(static_cast<GDScriptParser::IdentifierNode *>(subscript->base)->name) < Variant::VARIANT_MAX) { + gen->write_call_builtin_type_static(result, GDScriptParser::get_builtin_type(static_cast<GDScriptParser::IdentifierNode *>(subscript->base)->name), subscript->attribute->name, arguments); + } else { + GDScriptCodeGenerator::Address base = _parse_expression(codegen, r_error, subscript->base); + if (r_error) { + return GDScriptCodeGenerator::Address(); } - if (ClassDB::class_exists(class_name) && ClassDB::has_method(class_name, call->function_name)) { - MethodBind *method = ClassDB::get_method(class_name, call->function_name); - if (_have_exact_arguments(method, arguments)) { - // Exact arguments, use ptrcall. - gen->write_call_ptrcall(result, base, method, arguments); + if (within_await) { + gen->write_call_async(result, base, call->function_name, arguments); + } else if (base.type.has_type && base.type.kind != GDScriptDataType::BUILTIN) { + // Native method, use faster path. + StringName class_name; + if (base.type.kind == GDScriptDataType::NATIVE) { + class_name = base.type.native_type; } else { - // Not exact arguments, but still can use method bind call. - gen->write_call_method_bind(result, base, method, arguments); + class_name = base.type.native_type == StringName() ? base.type.script_type->get_instance_base_type() : base.type.native_type; } + if (ClassDB::class_exists(class_name) && ClassDB::has_method(class_name, call->function_name)) { + MethodBind *method = ClassDB::get_method(class_name, call->function_name); + if (_have_exact_arguments(method, arguments)) { + // Exact arguments, use ptrcall. + gen->write_call_ptrcall(result, base, method, arguments); + } else { + // Not exact arguments, but still can use method bind call. + gen->write_call_method_bind(result, base, method, arguments); + } + } else { + gen->write_call(result, base, call->function_name, arguments); + } + } else if (base.type.has_type && base.type.kind == GDScriptDataType::BUILTIN) { + gen->write_call_builtin_type(result, base, base.type.builtin_type, call->function_name, arguments); } else { gen->write_call(result, base, call->function_name, arguments); } - } else if (base.type.has_type && base.type.kind == GDScriptDataType::BUILTIN) { - gen->write_call_builtin_type(result, base, base.type.builtin_type, call->function_name, arguments); - } else { - gen->write_call(result, base, call->function_name, arguments); - } - if (base.mode == GDScriptCodeGenerator::Address::TEMPORARY) { - gen->pop_temporary(); + if (base.mode == GDScriptCodeGenerator::Address::TEMPORARY) { + gen->pop_temporary(); + } } } else { _set_error("Cannot call something that isn't a function.", call->callee); diff --git a/modules/gdscript/gdscript_disassembler.cpp b/modules/gdscript/gdscript_disassembler.cpp index 789af57b4c..8a6ac04539 100644 --- a/modules/gdscript/gdscript_disassembler.cpp +++ b/modules/gdscript/gdscript_disassembler.cpp @@ -542,6 +542,28 @@ void GDScriptFunction::disassemble(const Vector<String> &p_code_lines) const { incr = 5 + argc; } break; + case OPCODE_CALL_BUILTIN_STATIC: { + Variant::Type type = (Variant::Type)_code_ptr[ip + 1 + instr_var_args]; + int argc = _code_ptr[ip + 3 + instr_var_args]; + + text += "call built-in method static "; + text += DADDR(1 + argc); + text += " = "; + text += Variant::get_type_name(type); + text += "."; + text += _global_names_ptr[_code_ptr[ip + 2 + instr_var_args]].operator String(); + text += "("; + + for (int i = 0; i < argc; i++) { + if (i > 0) { + text += ", "; + } + text += DADDR(1 + i); + } + text += ")"; + + incr += 5 + argc; + } break; case OPCODE_CALL_PTRCALL_NO_RETURN: { text += "call-ptrcall (no return) "; diff --git a/modules/gdscript/gdscript_function.h b/modules/gdscript/gdscript_function.h index 70b62ced6d..26b8809337 100644 --- a/modules/gdscript/gdscript_function.h +++ b/modules/gdscript/gdscript_function.h @@ -263,6 +263,7 @@ public: OPCODE_CALL_SELF_BASE, OPCODE_CALL_METHOD_BIND, OPCODE_CALL_METHOD_BIND_RET, + OPCODE_CALL_BUILTIN_STATIC, // ptrcall have one instruction per return type. OPCODE_CALL_PTRCALL_NO_RETURN, OPCODE_CALL_PTRCALL_BOOL, @@ -496,6 +497,8 @@ private: Vector<GDScriptDataType> argument_types; GDScriptDataType return_type; + Map<int, Variant::Type> temporary_slots; + #ifdef TOOLS_ENABLED Vector<StringName> arg_names; Vector<Variant> default_arg_values; diff --git a/modules/gdscript/gdscript_vm.cpp b/modules/gdscript/gdscript_vm.cpp index 4757ec6ca9..d9fc54c9d4 100644 --- a/modules/gdscript/gdscript_vm.cpp +++ b/modules/gdscript/gdscript_vm.cpp @@ -152,6 +152,44 @@ String GDScriptFunction::_get_call_error(const Callable::CallError &p_err, const return err_text; } +void (*type_init_function_table[])(Variant *) = { + nullptr, // NIL (shouldn't be called). + &VariantInitializer<bool>::init, // BOOL. + &VariantInitializer<int64_t>::init, // INT. + &VariantInitializer<double>::init, // FLOAT. + &VariantInitializer<String>::init, // STRING. + &VariantInitializer<Vector2>::init, // VECTOR2. + &VariantInitializer<Vector2i>::init, // VECTOR2I. + &VariantInitializer<Rect2>::init, // RECT2. + &VariantInitializer<Rect2i>::init, // RECT2I. + &VariantInitializer<Vector3>::init, // VECTOR3. + &VariantInitializer<Vector3i>::init, // VECTOR3I. + &VariantInitializer<Transform2D>::init, // TRANSFORM2D. + &VariantInitializer<Plane>::init, // PLANE. + &VariantInitializer<Quat>::init, // QUAT. + &VariantInitializer<AABB>::init, // AABB. + &VariantInitializer<Basis>::init, // BASIS. + &VariantInitializer<Transform>::init, // TRANSFORM. + &VariantInitializer<Color>::init, // COLOR. + &VariantInitializer<StringName>::init, // STRING_NAME. + &VariantInitializer<NodePath>::init, // NODE_PATH. + &VariantInitializer<RID>::init, // RID. + &VariantTypeAdjust<Object *>::adjust, // OBJECT. + &VariantInitializer<Callable>::init, // CALLABLE. + &VariantInitializer<Signal>::init, // SIGNAL. + &VariantInitializer<Dictionary>::init, // DICTIONARY. + &VariantInitializer<Array>::init, // ARRAY. + &VariantInitializer<PackedByteArray>::init, // PACKED_BYTE_ARRAY. + &VariantInitializer<PackedInt32Array>::init, // PACKED_INT32_ARRAY. + &VariantInitializer<PackedInt64Array>::init, // PACKED_INT64_ARRAY. + &VariantInitializer<PackedFloat32Array>::init, // PACKED_FLOAT32_ARRAY. + &VariantInitializer<PackedFloat64Array>::init, // PACKED_FLOAT64_ARRAY. + &VariantInitializer<PackedStringArray>::init, // PACKED_STRING_ARRAY. + &VariantInitializer<PackedVector2Array>::init, // PACKED_VECTOR2_ARRAY. + &VariantInitializer<PackedVector3Array>::init, // PACKED_VECTOR3_ARRAY. + &VariantInitializer<PackedColorArray>::init, // PACKED_COLOR_ARRAY. +}; + #if defined(__GNUC__) #define OPCODES_TABLE \ static const void *switch_table_ops[] = { \ @@ -196,6 +234,7 @@ String GDScriptFunction::_get_call_error(const Callable::CallError &p_err, const &&OPCODE_CALL_SELF_BASE, \ &&OPCODE_CALL_METHOD_BIND, \ &&OPCODE_CALL_METHOD_BIND_RET, \ + &&OPCODE_CALL_BUILTIN_STATIC, \ &&OPCODE_CALL_PTRCALL_NO_RETURN, \ &&OPCODE_CALL_PTRCALL_BOOL, \ &&OPCODE_CALL_PTRCALL_INT, \ @@ -491,6 +530,10 @@ Variant GDScriptFunction::call(GDScriptInstance *p_instance, const Variant **p_a memnew_placement(&stack[ADDR_STACK_CLASS], Variant(script)); + for (const Map<int, Variant::Type>::Element *E = temporary_slots.front(); E; E = E->next()) { + type_init_function_table[E->get()](&stack[E->key()]); + } + String err_text; #ifdef DEBUG_ENABLED @@ -1573,6 +1616,51 @@ Variant GDScriptFunction::call(GDScriptInstance *p_instance, const Variant **p_a } DISPATCH_OPCODE; + OPCODE(OPCODE_CALL_BUILTIN_STATIC) { + CHECK_SPACE(4 + instr_arg_count); + + ip += instr_arg_count; + + GD_ERR_BREAK(_code_ptr[ip + 1] < 0 || _code_ptr[ip + 1] >= Variant::VARIANT_MAX); + Variant::Type builtin_type = (Variant::Type)_code_ptr[ip + 1]; + + int methodname_idx = _code_ptr[ip + 2]; + GD_ERR_BREAK(methodname_idx < 0 || methodname_idx >= _global_names_count); + const StringName *methodname = &_global_names_ptr[methodname_idx]; + + int argc = _code_ptr[ip + 3]; + GD_ERR_BREAK(argc < 0); + + GET_INSTRUCTION_ARG(ret, argc); + + const Variant **argptrs = const_cast<const Variant **>(instruction_args); + +#ifdef DEBUG_ENABLED + uint64_t call_time = 0; + + if (GDScriptLanguage::get_singleton()->profiling) { + call_time = OS::get_singleton()->get_ticks_usec(); + } +#endif + + Callable::CallError err; + Variant::call_static(builtin_type, *methodname, argptrs, argc, *ret, err); + +#ifdef DEBUG_ENABLED + if (GDScriptLanguage::get_singleton()->profiling) { + function_call_time += OS::get_singleton()->get_ticks_usec() - call_time; + } + + if (err.error != Callable::CallError::CALL_OK) { + err_text = _get_call_error(err, "static function '" + methodname->operator String() + "' in type '" + Variant::get_type_name(builtin_type) + "'", argptrs); + OPCODE_BREAK; + } +#endif + + ip += 4; + } + DISPATCH_OPCODE; + #ifdef DEBUG_ENABLED #define OPCODE_CALL_PTR(m_type) \ OPCODE(OPCODE_CALL_PTRCALL_##m_type) { \ diff --git a/modules/gdscript/tests/test_gdscript.cpp b/modules/gdscript/tests/test_gdscript.cpp index 36da64bbaa..8ad5cdacad 100644 --- a/modules/gdscript/tests/test_gdscript.cpp +++ b/modules/gdscript/tests/test_gdscript.cpp @@ -215,7 +215,7 @@ void test(TestType p_type) { init_language(fa->get_path_absolute().get_base_dir()); Vector<uint8_t> buf; - int flen = fa->get_len(); + uint64_t flen = fa->get_len(); buf.resize(fa->get_len() + 1); fa->get_buffer(buf.ptrw(), flen); buf.write[flen] = 0; diff --git a/modules/jpg/image_loader_jpegd.cpp b/modules/jpg/image_loader_jpegd.cpp index 7daf6a3a57..18beff41d8 100644 --- a/modules/jpg/image_loader_jpegd.cpp +++ b/modules/jpg/image_loader_jpegd.cpp @@ -105,7 +105,7 @@ Error jpeg_load_image_from_buffer(Image *p_image, const uint8_t *p_buffer, int p Error ImageLoaderJPG::load_image(Ref<Image> p_image, FileAccess *f, bool p_force_linear, float p_scale) { Vector<uint8_t> src_image; - int src_image_len = f->get_len(); + uint64_t src_image_len = f->get_len(); ERR_FAIL_COND_V(src_image_len == 0, ERR_FILE_CORRUPT); src_image.resize(src_image_len); diff --git a/modules/mbedtls/crypto_mbedtls.cpp b/modules/mbedtls/crypto_mbedtls.cpp index 987306af2a..4a42e9af0d 100644 --- a/modules/mbedtls/crypto_mbedtls.cpp +++ b/modules/mbedtls/crypto_mbedtls.cpp @@ -58,7 +58,7 @@ Error CryptoKeyMbedTLS::load(String p_path, bool p_public_only) { FileAccess *f = FileAccess::open(p_path, FileAccess::READ); ERR_FAIL_COND_V_MSG(!f, ERR_INVALID_PARAMETER, "Cannot open CryptoKeyMbedTLS file '" + p_path + "'."); - int flen = f->get_len(); + uint64_t flen = f->get_len(); out.resize(flen + 1); f->get_buffer(out.ptrw(), flen); out.write[flen] = 0; // string terminator @@ -146,7 +146,7 @@ Error X509CertificateMbedTLS::load(String p_path) { FileAccess *f = FileAccess::open(p_path, FileAccess::READ); ERR_FAIL_COND_V_MSG(!f, ERR_INVALID_PARAMETER, "Cannot open X509CertificateMbedTLS file '" + p_path + "'."); - int flen = f->get_len(); + uint64_t flen = f->get_len(); out.resize(flen + 1); f->get_buffer(out.ptrw(), flen); out.write[flen] = 0; // string terminator diff --git a/modules/minimp3/resource_importer_mp3.cpp b/modules/minimp3/resource_importer_mp3.cpp index afd26fb79e..96cce49c86 100644 --- a/modules/minimp3/resource_importer_mp3.cpp +++ b/modules/minimp3/resource_importer_mp3.cpp @@ -79,7 +79,7 @@ Error ResourceImporterMP3::import(const String &p_source_file, const String &p_s ERR_FAIL_COND_V(!f, ERR_CANT_OPEN); - size_t len = f->get_len(); + uint64_t len = f->get_len(); Vector<uint8_t> data; data.resize(len); diff --git a/modules/mono/utils/string_utils.cpp b/modules/mono/utils/string_utils.cpp index 43de77005e..5d53394658 100644 --- a/modules/mono/utils/string_utils.cpp +++ b/modules/mono/utils/string_utils.cpp @@ -170,10 +170,10 @@ Error read_all_file_utf8(const String &p_path, String &r_content) { FileAccess *f = FileAccess::open(p_path, FileAccess::READ, &err); ERR_FAIL_COND_V_MSG(err != OK, err, "Cannot open file '" + p_path + "'."); - int len = f->get_len(); + uint64_t len = f->get_len(); sourcef.resize(len + 1); uint8_t *w = sourcef.ptrw(); - int r = f->get_buffer(w, len); + uint64_t r = f->get_buffer(w, len); f->close(); memdelete(f); ERR_FAIL_COND_V(r != len, ERR_CANT_OPEN); diff --git a/modules/raycast/config.py b/modules/raycast/config.py index 26493da41b..3da9ace9d8 100644 --- a/modules/raycast/config.py +++ b/modules/raycast/config.py @@ -1,10 +1,16 @@ def can_build(env, platform): + # Depends on Embree library, which supports only x86_64 (originally) + # and aarch64 (thanks to the embree-aarch64 fork). + if platform == "android": - return env["android_arch"] in ["arm64v8", "x86", "x86_64"] + return env["android_arch"] in ["arm64v8", "x86_64"] if platform == "javascript": return False # No SIMD support yet + if env["bits"] == "32": + return False + return True diff --git a/modules/raycast/lightmap_raycaster.cpp b/modules/raycast/lightmap_raycaster.cpp index 56bdb5900b..0583acc119 100644 --- a/modules/raycast/lightmap_raycaster.cpp +++ b/modules/raycast/lightmap_raycaster.cpp @@ -32,7 +32,9 @@ #include "lightmap_raycaster.h" +#ifdef __SSE2__ #include <pmmintrin.h> +#endif LightmapRaycaster *LightmapRaycasterEmbree::create_embree_raycaster() { return memnew(LightmapRaycasterEmbree); @@ -171,8 +173,10 @@ void embree_error_handler(void *p_user_data, RTCError p_code, const char *p_str) } LightmapRaycasterEmbree::LightmapRaycasterEmbree() { +#ifdef __SSE2__ _MM_SET_FLUSH_ZERO_MODE(_MM_FLUSH_ZERO_ON); _MM_SET_DENORMALS_ZERO_MODE(_MM_DENORMALS_ZERO_ON); +#endif embree_device = rtcNewDevice(nullptr); rtcSetDeviceErrorFunction(embree_device, &embree_error_handler, nullptr); @@ -180,8 +184,10 @@ LightmapRaycasterEmbree::LightmapRaycasterEmbree() { } LightmapRaycasterEmbree::~LightmapRaycasterEmbree() { +#ifdef __SSE2__ _MM_SET_FLUSH_ZERO_MODE(_MM_FLUSH_ZERO_OFF); _MM_SET_DENORMALS_ZERO_MODE(_MM_DENORMALS_ZERO_OFF); +#endif if (embree_scene != nullptr) { rtcReleaseScene(embree_scene); diff --git a/modules/stb_vorbis/resource_importer_ogg_vorbis.cpp b/modules/stb_vorbis/resource_importer_ogg_vorbis.cpp index ec1c30783a..17380001f5 100644 --- a/modules/stb_vorbis/resource_importer_ogg_vorbis.cpp +++ b/modules/stb_vorbis/resource_importer_ogg_vorbis.cpp @@ -79,7 +79,7 @@ Error ResourceImporterOGGVorbis::import(const String &p_source_file, const Strin ERR_FAIL_COND_V_MSG(!f, ERR_CANT_OPEN, "Cannot open file '" + p_source_file + "'."); - size_t len = f->get_len(); + uint64_t len = f->get_len(); Vector<uint8_t> data; data.resize(len); diff --git a/modules/svg/image_loader_svg.cpp b/modules/svg/image_loader_svg.cpp index 6ce3e4b4b3..24fe654946 100644 --- a/modules/svg/image_loader_svg.cpp +++ b/modules/svg/image_loader_svg.cpp @@ -140,7 +140,7 @@ Error ImageLoaderSVG::create_image_from_string(Ref<Image> p_image, const char *p } Error ImageLoaderSVG::load_image(Ref<Image> p_image, FileAccess *f, bool p_force_linear, float p_scale) { - uint32_t size = f->get_len(); + uint64_t size = f->get_len(); Vector<uint8_t> src_image; src_image.resize(size + 1); uint8_t *src_w = src_image.ptrw(); diff --git a/modules/text_server_adv/dynamic_font_adv.cpp b/modules/text_server_adv/dynamic_font_adv.cpp index 326af7f0ee..faeb83f920 100644 --- a/modules/text_server_adv/dynamic_font_adv.cpp +++ b/modules/text_server_adv/dynamic_font_adv.cpp @@ -66,7 +66,7 @@ DynamicFontDataAdvanced::DataAtSize *DynamicFontDataAdvanced::get_data_for_size( ERR_FAIL_V_MSG(nullptr, "Cannot open font file '" + font_path + "'."); } - size_t len = f->get_len(); + uint64_t len = f->get_len(); font_mem_cache.resize(len); f->get_buffer(font_mem_cache.ptrw(), len); font_mem = font_mem_cache.ptr(); diff --git a/modules/text_server_adv/text_server_adv.cpp b/modules/text_server_adv/text_server_adv.cpp index 8b8b6b7cd3..361852547f 100644 --- a/modules/text_server_adv/text_server_adv.cpp +++ b/modules/text_server_adv/text_server_adv.cpp @@ -181,7 +181,7 @@ bool TextServerAdvanced::load_support_data(const String &p_filename) { UErrorCode err = U_ZERO_ERROR; // ICU data found. - size_t len = f->get_len(); + uint64_t len = f->get_len(); icu_data = (uint8_t *)memalloc(len); f->get_buffer(icu_data, len); f->close(); diff --git a/modules/text_server_fb/dynamic_font_fb.cpp b/modules/text_server_fb/dynamic_font_fb.cpp index dec1d6f83f..406f60b6f5 100644 --- a/modules/text_server_fb/dynamic_font_fb.cpp +++ b/modules/text_server_fb/dynamic_font_fb.cpp @@ -65,7 +65,7 @@ DynamicFontDataFallback::DataAtSize *DynamicFontDataFallback::get_data_for_size( ERR_FAIL_V_MSG(nullptr, "Cannot open font file '" + font_path + "'."); } - size_t len = f->get_len(); + uint64_t len = f->get_len(); font_mem_cache.resize(len); f->get_buffer(font_mem_cache.ptrw(), len); font_mem = font_mem_cache.ptr(); diff --git a/modules/tga/image_loader_tga.cpp b/modules/tga/image_loader_tga.cpp index ef53661557..52b92ee930 100644 --- a/modules/tga/image_loader_tga.cpp +++ b/modules/tga/image_loader_tga.cpp @@ -226,9 +226,9 @@ Error ImageLoaderTGA::convert_to_image(Ref<Image> p_image, const uint8_t *p_buff Error ImageLoaderTGA::load_image(Ref<Image> p_image, FileAccess *f, bool p_force_linear, float p_scale) { Vector<uint8_t> src_image; - int src_image_len = f->get_len(); + uint64_t src_image_len = f->get_len(); ERR_FAIL_COND_V(src_image_len == 0, ERR_FILE_CORRUPT); - ERR_FAIL_COND_V(src_image_len < (int)sizeof(tga_header_s), ERR_FILE_CORRUPT); + ERR_FAIL_COND_V(src_image_len < (int64_t)sizeof(tga_header_s), ERR_FILE_CORRUPT); src_image.resize(src_image_len); Error err = OK; diff --git a/modules/theora/video_stream_theora.cpp b/modules/theora/video_stream_theora.cpp index 54f5b3f424..7b421bdc16 100644 --- a/modules/theora/video_stream_theora.cpp +++ b/modules/theora/video_stream_theora.cpp @@ -58,7 +58,7 @@ int VideoStreamPlaybackTheora::buffer_data() { #else - int bytes = file->get_buffer((uint8_t *)buffer, 4096); + uint64_t bytes = file->get_buffer((uint8_t *)buffer, 4096); ogg_sync_wrote(&oy, bytes); return (bytes); @@ -176,7 +176,7 @@ void VideoStreamPlaybackTheora::set_file(const String &p_file) { thread_eof = false; //pre-fill buffer int to_read = ring_buffer.space_left(); - int read = file->get_buffer(read_buffer.ptr(), to_read); + uint64_t read = file->get_buffer(read_buffer.ptr(), to_read); ring_buffer.write(read_buffer.ptr(), read); thread.start(_streaming_thread, this); @@ -632,8 +632,8 @@ void VideoStreamPlaybackTheora::_streaming_thread(void *ud) { //just fill back the buffer if (!vs->thread_eof) { int to_read = vs->ring_buffer.space_left(); - if (to_read) { - int read = vs->file->get_buffer(vs->read_buffer.ptr(), to_read); + if (to_read > 0) { + uint64_t read = vs->file->get_buffer(vs->read_buffer.ptr(), to_read); vs->ring_buffer.write(vs->read_buffer.ptr(), read); vs->thread_eof = vs->file->eof_reached(); } diff --git a/modules/tinyexr/image_loader_tinyexr.cpp b/modules/tinyexr/image_loader_tinyexr.cpp index 47214e6974..cfb75fb93b 100644 --- a/modules/tinyexr/image_loader_tinyexr.cpp +++ b/modules/tinyexr/image_loader_tinyexr.cpp @@ -37,7 +37,7 @@ Error ImageLoaderTinyEXR::load_image(Ref<Image> p_image, FileAccess *f, bool p_force_linear, float p_scale) { Vector<uint8_t> src_image; - int src_image_len = f->get_len(); + uint64_t src_image_len = f->get_len(); ERR_FAIL_COND_V(src_image_len == 0, ERR_FILE_CORRUPT); src_image.resize(src_image_len); diff --git a/modules/visual_script/visual_script_editor.cpp b/modules/visual_script/visual_script_editor.cpp index b1a08bc732..a51369c599 100644 --- a/modules/visual_script/visual_script_editor.cpp +++ b/modules/visual_script/visual_script_editor.cpp @@ -2710,6 +2710,10 @@ void VisualScriptEditor::set_debugger_active(bool p_active) { } } +Control *VisualScriptEditor::get_base_editor() const { + return graph; +} + void VisualScriptEditor::set_tooltip_request_func(String p_method, Object *p_obj) { } diff --git a/modules/visual_script/visual_script_editor.h b/modules/visual_script/visual_script_editor.h index fc9a2df60f..ef3a5d11c0 100644 --- a/modules/visual_script/visual_script_editor.h +++ b/modules/visual_script/visual_script_editor.h @@ -320,6 +320,8 @@ public: virtual bool can_lose_focus_on_node_selection() override { return false; } virtual void validate() override; + virtual Control *get_base_editor() const override; + static void register_editor(); static void free_clipboard(); diff --git a/modules/webm/video_stream_webm.cpp b/modules/webm/video_stream_webm.cpp index a6b64b342e..15bf9dbf2d 100644 --- a/modules/webm/video_stream_webm.cpp +++ b/modules/webm/video_stream_webm.cpp @@ -62,10 +62,10 @@ public: virtual int Read(long long pos, long len, unsigned char *buf) { if (file) { - if (file->get_position() != (size_t)pos) { + if (file->get_position() != (uint64_t)pos) { file->seek(pos); } - if (file->get_buffer(buf, len) == len) { + if (file->get_buffer(buf, len) == (uint64_t)len) { return 0; } } @@ -74,7 +74,7 @@ public: virtual int Length(long long *total, long long *available) { if (file) { - const size_t len = file->get_len(); + const uint64_t len = file->get_len(); if (total) { *total = len; } diff --git a/modules/webp/image_loader_webp.cpp b/modules/webp/image_loader_webp.cpp index 6e62840a3e..d7e88d76b1 100644 --- a/modules/webp/image_loader_webp.cpp +++ b/modules/webp/image_loader_webp.cpp @@ -147,7 +147,7 @@ static Ref<Image> _webp_mem_loader_func(const uint8_t *p_png, int p_size) { Error ImageLoaderWEBP::load_image(Ref<Image> p_image, FileAccess *f, bool p_force_linear, float p_scale) { Vector<uint8_t> src_image; - int src_image_len = f->get_len(); + uint64_t src_image_len = f->get_len(); ERR_FAIL_COND_V(src_image_len == 0, ERR_FILE_CORRUPT); src_image.resize(src_image_len); |