Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Crash on C# exception while reloading assemblies #65032

Closed
codecat opened this issue Aug 29, 2022 · 3 comments
Closed

Crash on C# exception while reloading assemblies #65032

codecat opened this issue Aug 29, 2022 · 3 comments

Comments

@codecat
Copy link
Contributor

codecat commented Aug 29, 2022

Godot version

v4.0.alpha.mono.custom_build [0b8a63e]

System information

Windows 11, Vulkan, 3080

Issue description

When I build a C# project that generates an exception in the editor, it crashes the editor inside of godotsharp_internal_script_debugger_send_error because EngineDebugger::get_script_debugger() returns null, and this is not checked.

image

Steps to reproduce

  1. Open the reproduction project
  2. Make sure the "crash_test" addon is enabled
  3. You should see a gizmo drawing a line in the 3D view
  4. In addons/crash_test/CrashGizmoPlugin.cs, change if (true) { to if (false) {
  5. Click "Build" in Godot

Minimal reproduction project

CrashTest20220829.zip

@raulsntos
Copy link
Member

raulsntos commented Sep 1, 2022

EngineDebugger::get_script_debugger() returns null, and this is not checked.

You are not entirely correct about this, it's true that this method can return null but we do guard calls to this method with a call to EngineDebugger::is_active() which would return false if the debugger is null so it would never call that method:

if (NativeFuncs.godotsharp_internal_script_debugger_is_active())
{
SendToScriptDebugger(e);
}

The NativeFuncs.godotsharp_internal_script_debugger_is_active method calls EngineDebugger::is_active() to check that the script debugger is not null, then we call the SendToScriptDebugger method which ends up calling EngineDebugger::get_script_debugger() but this only happens if the previous check passed.


I have been unable to reproduce the crash (with Godot built from commit 3cf16c959) but I do get an error in the console with the C# exception:

modules/mono/glue/runtime_interop.cpp:1241 - System.InvalidCastException: Unable to cast object of type 'Godot.EditorNode3DGizmoPlugin' to type 'CrashGizmoPlugin'.
     at crash_test.RestoreGodotObjectData(GodotSerializationInfo info) in /media/raulsntos/Data/GodotProjects/TESTS/CrashGizmo/Godot.SourceGenerators/Godot.SourceGenerators.ScriptSerializationGenerator/crash_test_ScriptSerialization_Generated.cs:line 15
     at Godot.Bridge.CSharpInstanceBridge.DeserializeState(IntPtr godotObjectGCHandle, godot_dictionary* propertiesState, godot_dictionary* signalEventsState) in /media/raulsntos/Data/Godot/src/godot/modules/mono/glue/GodotSharp/GodotSharp/Core/Bridge/CSharpInstanceBridge.cs:line 239

This is caused by the generated code that handles the restoring of a class when reloading assemblies. When reloading assemblies we replace script instances with placeholders to keep their state while we dispose of the old instance, when the assemblies have been reloaded we can instantiate the script again but if the class is not a [Tool] it can't be instantiated by the editor so that's probably what causes the exception here. I understand that the documentation examples are missing the [Tool] attribute so sorry about that.

@raulsntos
Copy link
Member

raulsntos commented Feb 21, 2023

@codecat Are you still able to reproduce this issue in Godot 4.0 RC2 or any later release?

@codecat
Copy link
Contributor Author

codecat commented Feb 21, 2023

I am not working on the particular project that I was anymore, but I just tested the reproduction project on RC2 and it doesn't seem to crash anymore for me. 👍

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
Archived in project
Development

No branches or pull requests

4 participants