| 2363 | } |
| 2364 | |
| 2365 | CSharpInstance *CSharpScript::_create_instance(const Variant **p_args, int p_argcount, Object *p_owner, bool p_is_ref_counted, Callable::CallError &r_error) { |
| 2366 | ERR_FAIL_COND_V_MSG(!type_info.can_instantiate(), nullptr, "Cannot instantiate C# script. Script: '" + get_path() + "'."); |
| 2367 | |
| 2368 | /* STEP 1, CREATE */ |
| 2369 | |
| 2370 | Ref<RefCounted> ref; |
| 2371 | if (p_is_ref_counted) { |
| 2372 | // Hold it alive. Important if we have to dispose a script instance binding before creating the CSharpInstance. |
| 2373 | ref = Ref<RefCounted>(static_cast<RefCounted *>(p_owner)); |
| 2374 | } |
| 2375 | |
| 2376 | // If the object had a script instance binding, dispose it before adding the CSharpInstance |
| 2377 | if (CSharpLanguage::has_instance_binding(p_owner)) { |
| 2378 | void *data = CSharpLanguage::get_existing_instance_binding(p_owner); |
| 2379 | CRASH_COND(data == nullptr); |
| 2380 | |
| 2381 | CSharpScriptBinding &script_binding = ((RBMap<Object *, CSharpScriptBinding>::Element *)data)->get(); |
| 2382 | if (script_binding.inited && !script_binding.gchandle.is_released()) { |
| 2383 | GDMonoCache::managed_callbacks.CSharpInstanceBridge_CallDispose( |
| 2384 | script_binding.gchandle.get_intptr(), /* okIfNull */ true); |
| 2385 | |
| 2386 | script_binding.gchandle.release(); // Just in case |
| 2387 | script_binding.inited = false; |
| 2388 | } |
| 2389 | } |
| 2390 | |
| 2391 | CSharpInstance *instance = memnew(CSharpInstance(Ref<CSharpScript>(this))); |
| 2392 | instance->base_ref_counted = p_is_ref_counted; |
| 2393 | instance->owner = p_owner; |
| 2394 | instance->owner->set_script_instance(instance); |
| 2395 | |
| 2396 | /* STEP 2, INITIALIZE AND CONSTRUCT */ |
| 2397 | |
| 2398 | bool ok = GDMonoCache::managed_callbacks.ScriptManagerBridge_CreateManagedForGodotObjectScriptInstance( |
| 2399 | this, p_owner, p_args, p_argcount); |
| 2400 | |
| 2401 | if (!ok) { |
| 2402 | // Important to clear this before destroying the script instance here |
| 2403 | instance->script = Ref<CSharpScript>(); |
| 2404 | p_owner->set_script_instance(nullptr); |
| 2405 | instance->owner = nullptr; |
| 2406 | |
| 2407 | return nullptr; |
| 2408 | } |
| 2409 | |
| 2410 | CRASH_COND(instance->gchandle.is_released()); |
| 2411 | |
| 2412 | /* STEP 3, PARTY */ |
| 2413 | |
| 2414 | /// @todo Make thread safe |
| 2415 | return instance; |
| 2416 | } |
| 2417 | |
| 2418 | Variant CSharpScript::_new(const Variant **p_args, int p_argcount, Callable::CallError &r_error) { |
| 2419 | if (!valid) { |
nothing calls this directly
no test coverage detected