From 24181d10552e3bedca05f1f0a470eb29a2d93975 Mon Sep 17 00:00:00 2001 From: 20kdc Date: Fri, 8 Dec 2023 12:26:44 +0000 Subject: [PATCH] GDScript: Adjust STATIC_CALLED_ON_INSTANCE warning to not default to the native type, and to not trigger on self-calls Not defaulting to the native type rationale: Defaulting to the native type is less than useful, as: * There are very few native types that are extensible and have static methods. * Defaulting to the native type does not account for a method being script-defined. While the "real fix" would be to carefully track the source of the method, the get_function_signature method is already complicated enough. This will at least ensure the resulting code should always be valid. Not triggering on self-calls rationale: Found in PR comment https://github.com/godotengine/godot/pull/85918#issuecomment-1935864459 ``` static func example(): pass func example2(): example() # self-call on static function ``` Disabling this warning on self-calls is: * Consistent with other languages * Important for anonymous classes (where the output code is unusable) --- modules/gdscript/gdscript_analyzer.cpp | 8 ++---- .../warnings/static_called_on_instance.gd | 28 +++++++++++++------ .../warnings/static_called_on_instance.out | 10 ++++++- 3 files changed, 31 insertions(+), 15 deletions(-) diff --git a/modules/gdscript/gdscript_analyzer.cpp b/modules/gdscript/gdscript_analyzer.cpp index 98d4a19a8796..3ec5098c21ef 100644 --- a/modules/gdscript/gdscript_analyzer.cpp +++ b/modules/gdscript/gdscript_analyzer.cpp @@ -3360,12 +3360,8 @@ void GDScriptAnalyzer::reduce_call(GDScriptParser::CallNode *p_call, bool p_is_a parser->push_warning(p_call, GDScriptWarning::RETURN_VALUE_DISCARDED, p_call->function_name); } - if (method_flags.has_flag(METHOD_FLAG_STATIC) && !is_constructor && !base_type.is_meta_type && !(is_self && static_context)) { - String caller_type = String(base_type.native_type); - - if (caller_type.is_empty()) { - caller_type = base_type.to_string(); - } + if (method_flags.has_flag(METHOD_FLAG_STATIC) && !is_constructor && !base_type.is_meta_type && !is_self) { + String caller_type = base_type.to_string(); parser->push_warning(p_call, GDScriptWarning::STATIC_CALLED_ON_INSTANCE, p_call->function_name, caller_type); } diff --git a/modules/gdscript/tests/scripts/parser/warnings/static_called_on_instance.gd b/modules/gdscript/tests/scripts/parser/warnings/static_called_on_instance.gd index 29d8501b7894..193faab5d0a5 100644 --- a/modules/gdscript/tests/scripts/parser/warnings/static_called_on_instance.gd +++ b/modules/gdscript/tests/scripts/parser/warnings/static_called_on_instance.gd @@ -1,11 +1,23 @@ -class Player: - var x = 3 +class_name TestStaticCalledOnInstance + +class Inner: + static func static_func(): + pass + +static func static_func(): + pass func test(): - # These should not emit a warning. - var _player = Player.new() - print(String.num_uint64(8589934592)) # 2 ^ 33 + print(String.num_uint64(8589934592)) + var some_string := String() + print(some_string.num_uint64(8589934592)) # Warning. + + TestStaticCalledOnInstance.static_func() + static_func() + self.static_func() + var other := TestStaticCalledOnInstance.new() + other.static_func() # Warning. - # This should emit a warning. - var some_string = String() - print(some_string.num_uint64(8589934592)) # 2 ^ 33 + Inner.static_func() + var inner := Inner.new() + inner.static_func() # Warning. diff --git a/modules/gdscript/tests/scripts/parser/warnings/static_called_on_instance.out b/modules/gdscript/tests/scripts/parser/warnings/static_called_on_instance.out index 77994ce9bae5..c00f3d093a1e 100644 --- a/modules/gdscript/tests/scripts/parser/warnings/static_called_on_instance.out +++ b/modules/gdscript/tests/scripts/parser/warnings/static_called_on_instance.out @@ -1,7 +1,15 @@ GDTEST_OK >> WARNING ->> Line: 11 +>> Line: 13 >> STATIC_CALLED_ON_INSTANCE >> The function "num_uint64()" is a static function but was called from an instance. Instead, it should be directly called from the type: "String.num_uint64()". +>> WARNING +>> Line: 19 +>> STATIC_CALLED_ON_INSTANCE +>> The function "static_func()" is a static function but was called from an instance. Instead, it should be directly called from the type: "TestStaticCalledOnInstance.static_func()". +>> WARNING +>> Line: 23 +>> STATIC_CALLED_ON_INSTANCE +>> The function "static_func()" is a static function but was called from an instance. Instead, it should be directly called from the type: "Inner.static_func()". 8589934592 8589934592