Browse Source

Vulkan/RD rasterizer now does clean exit.

Juan Linietsky 6 years ago
parent
commit
dc3b47f3ab

+ 22 - 3
core/rid_owner.h

@@ -4,7 +4,7 @@
 #include "core/print_string.h"
 #include "core/rid.h"
 #include "core/spin_lock.h"
-
+#include <stdio.h>
 #include <typeinfo>
 
 class RID_AllocBase {
@@ -189,7 +189,7 @@ public:
 		return alloc_count;
 	}
 
-	_FORCE_INLINE_ T *get_rid_by_index(uint32_t p_index) {
+	_FORCE_INLINE_ T *get_ptr_by_index(uint32_t p_index) {
 		ERR_FAIL_INDEX_V(p_index, alloc_count, NULL);
 		if (THREAD_SAFE) {
 			spin_lock.lock();
@@ -202,6 +202,21 @@ public:
 		return ptr;
 	}
 
+	_FORCE_INLINE_ RID get_rid_by_index(uint32_t p_index) {
+		ERR_FAIL_INDEX_V(p_index, alloc_count, RID());
+		if (THREAD_SAFE) {
+			spin_lock.lock();
+		}
+		uint64_t idx = free_list_chunks[p_index / elements_in_chunk][p_index % elements_in_chunk];
+		uint64_t validator = validator_chunks[idx / elements_in_chunk][idx % elements_in_chunk];
+
+		RID rid = _make_from_id((validator << 32) | idx);
+		if (THREAD_SAFE) {
+			spin_lock.unlock();
+		}
+		return rid;
+	}
+
 	void get_owned_list(List<RID> *p_owned) {
 		for (size_t i = 0; i < alloc_count; i++) {
 			uint64_t idx = free_list_chunks[i / elements_in_chunk][i % elements_in_chunk];
@@ -315,10 +330,14 @@ public:
 		return alloc.get_rid_count();
 	}
 
-	_FORCE_INLINE_ T *get_rid_by_index(uint32_t p_index) {
+	_FORCE_INLINE_ RID get_rid_by_index(uint32_t p_index) {
 		return alloc.get_rid_by_index(p_index);
 	}
 
+	_FORCE_INLINE_ T *get_ptr_by_index(uint32_t p_index) {
+		return alloc.get_ptr_by_index(p_index);
+	}
+
 	_FORCE_INLINE_ void get_owned_list(List<RID> *p_owned) {
 		return alloc.get_owned_list(p_owned);
 	}

+ 3 - 2
scene/main/viewport.cpp

@@ -147,7 +147,6 @@ ViewportTexture::ViewportTexture() {
 
 	vp = NULL;
 	set_local_to_scene(true);
-	proxy = VS::get_singleton()->texture_2d_placeholder_create();
 }
 
 ViewportTexture::~ViewportTexture() {
@@ -159,7 +158,9 @@ ViewportTexture::~ViewportTexture() {
 	if (proxy_ph.is_valid()) {
 		VS::get_singleton()->free(proxy_ph);
 	}
-	VS::get_singleton()->free(proxy);
+	if (proxy.is_valid()) {
+		VS::get_singleton()->free(proxy);
+	}
 }
 
 /////////////////////////////////////

+ 3 - 0
servers/visual/rasterizer_rd/effects_rd.cpp

@@ -139,4 +139,7 @@ EffectsRD::EffectsRD() {
 }
 
 EffectsRD::~EffectsRD() {
+	RD::get_singleton()->free(default_sampler);
+	blur.shader.version_free(blur.shader_version);
+	RD::get_singleton()->free(index_buffer); //array gets freed as dependency
 }

+ 25 - 4
servers/visual/rasterizer_rd/rasterizer_canvas_rd.cpp

@@ -2559,10 +2559,24 @@ RasterizerCanvasRD::~RasterizerCanvasRD() {
 
 	//canvas state
 
-	if (state.canvas_state_buffer.is_valid()) {
-		RD::get_singleton()->free(state.canvas_state_buffer);
+	{
+		if (state.canvas_state_buffer.is_valid()) {
+			RD::get_singleton()->free(state.canvas_state_buffer);
+		}
+
+		memdelete_arr(state.light_uniforms);
+		RD::get_singleton()->free(state.lights_uniform_buffer);
+		RD::get_singleton()->free(shader.default_skeleton_uniform_buffer);
+		RD::get_singleton()->free(shader.default_skeleton_texture_buffer);
 	}
 
+	//shadow rendering
+	{
+
+		shadow_render.shader.version_free(shadow_render.shader_version);
+		//this will also automatically clear all pipelines
+		RD::get_singleton()->free(state.shadow_sampler);
+	}
 	//bindings
 	{
 
@@ -2589,8 +2603,15 @@ RasterizerCanvasRD::~RasterizerCanvasRD() {
 	shader.canvas_shader.version_free(shader.default_version);
 
 	//buffers
-	RD::get_singleton()->free(shader.quad_index_array);
-	RD::get_singleton()->free(shader.quad_index_buffer);
+	{
+		RD::get_singleton()->free(shader.quad_index_array);
+		RD::get_singleton()->free(shader.quad_index_buffer);
+		RD::get_singleton()->free(polygon_buffers.default_bone_buffer);
+		RD::get_singleton()->free(polygon_buffers.default_weight_buffer);
+		RD::get_singleton()->free(polygon_buffers.default_color_buffer);
+		RD::get_singleton()->free(polygon_buffers.default_uv_buffer);
+		//primitives are erase by dependency
+	}
 
 	//pipelines don't need freeing, they are all gone after shaders are gone
 }

+ 8 - 5
servers/visual/rasterizer_rd/rasterizer_storage_rd.cpp

@@ -573,9 +573,7 @@ RID RasterizerStorageRD::texture_2d_create(const Ref<Image> &p_image) {
 	texture.is_render_target = false;
 	texture.rd_view = rd_view;
 	texture.is_proxy = false;
-#ifndef _MSC_VER
-#warning texture owner needs a spinlock to make this really callable from any thread
-#endif
+
 	return texture_owner.make_rid(texture);
 }
 
@@ -607,6 +605,7 @@ RID RasterizerStorageRD::texture_proxy_create(RID p_base) {
 	RID rid = texture_owner.make_rid(proxy_tex);
 
 	tex->proxies.push_back(rid);
+
 	return rid;
 }
 
@@ -2045,11 +2044,13 @@ bool RasterizerStorageRD::free(RID p_rid) {
 
 		ERR_FAIL_COND_V(t->is_render_target, false);
 
-		if (t->rd_texture_srgb.is_valid()) {
+		if (RD::get_singleton()->texture_is_valid(t->rd_texture_srgb)) {
 			//erase this first, as it's a dependency of the one below
 			RD::get_singleton()->free(t->rd_texture_srgb);
 		}
-		RD::get_singleton()->free(t->rd_texture);
+		if (RD::get_singleton()->texture_is_valid(t->rd_texture)) {
+			RD::get_singleton()->free(t->rd_texture);
+		}
 
 		for (int i = 0; i < t->proxies.size(); i++) {
 			Texture *p = texture_owner.getornull(t->proxies[i]);
@@ -2079,6 +2080,7 @@ bool RasterizerStorageRD::free(RID p_rid) {
 		}
 		material_set_shader(p_rid, RID()); //clean up shader
 		material->instance_dependency.instance_notify_deleted(p_rid);
+		material_owner.free(p_rid);
 	} else if (render_target_owner.owns(p_rid)) {
 		RenderTarget *rt = render_target_owner.getornull(p_rid);
 
@@ -2252,6 +2254,7 @@ RasterizerStorageRD::RasterizerStorageRD() {
 }
 
 RasterizerStorageRD::~RasterizerStorageRD() {
+
 	//def textures
 	for (int i = 0; i < DEFAULT_RD_TEXTURE_MAX; i++) {
 		RD::get_singleton()->free(default_rd_textures[i]);