From 8361c880c4fc32d3cd3607619a0aca867c291f81 Mon Sep 17 00:00:00 2001
From: Joseph Walton-Rivers <joseph@walton-rivers.uk>
Date: Fri, 22 Jul 2022 02:20:52 +0100
Subject: [PATCH] fix one possible ODR violation that caused release builds to
 go bang

---
 CMakeLists.txt                         |  5 +-
 build.sh                               |  2 +-
 demo/demo/main.cpp                     |  1 +
 fggl/app.cpp                           |  1 +
 include/fggl/ecs/component.hpp         |  8 +--
 include/fggl/ecs/component_fwd.hpp     | 68 ++++++++++++++++++++++++++
 include/fggl/ecs3/prototype/loader.hpp | 18 +------
 7 files changed, 80 insertions(+), 23 deletions(-)
 create mode 100644 include/fggl/ecs/component_fwd.hpp

diff --git a/CMakeLists.txt b/CMakeLists.txt
index 49718b8..f1687da 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -64,12 +64,15 @@ add_subdirectory( integrations/bullet )
 
 
 ## G++ enable insane checks
-target_compile_options( ${PROJECT_NAME} PRIVATE -Wall -fno-strict-aliasing -fno-strict-overflow )
+target_compile_options( ${PROJECT_NAME} PRIVATE -Wall -Wpedantic -Wextra -Wodr -fno-strict-aliasing -fno-strict-overflow )
+set_property(TARGET fggl PROPERTY INTERPROCEDURAL_OPTIMIZATION True)
 
 # extras
 #add_subdirectory(tests)
 if (FGGL_EXAMPLES)
   add_subdirectory(demo)
+  target_compile_options( demo PRIVATE -Wall -Wextra -Wodr -Wdouble-promotion -fno-strict-aliasing -fno-strict-overflow )
+  set_property(TARGET demo PROPERTY INTERPROCEDURAL_OPTIMIZATION True)
 endif()
 
 ##
diff --git a/build.sh b/build.sh
index 2bfd804..11bce74 100755
--- a/build.sh
+++ b/build.sh
@@ -20,7 +20,7 @@ rm -rf $CACHE
 #
 # build step
 #
-cmake -S . -B $BUILD_PATH -DCMAKE_BUILD_TYPE=debug
+cmake -S . -B $BUILD_PATH -DCMAKE_BUILD_TYPE=RelWithDebInfo
 cmake --build $BUILD_PATH
 cmake --install $BUILD_PATH --prefix /tmp/fggl-lib
 
diff --git a/demo/demo/main.cpp b/demo/demo/main.cpp
index 2783ab2..a09e849 100644
--- a/demo/demo/main.cpp
+++ b/demo/demo/main.cpp
@@ -26,6 +26,7 @@
 #endif
 
 #include "fggl/fggl.hpp"
+#include "fggl/ecs/component_fwd.hpp"
 
 #include "fggl/audio/openal/audio.hpp"
 
diff --git a/fggl/app.cpp b/fggl/app.cpp
index 63f078f..5e70f94 100644
--- a/fggl/app.cpp
+++ b/fggl/app.cpp
@@ -19,6 +19,7 @@
 
 #include <fggl/app.hpp>
 #include <fggl/ecs3/types.hpp>
+#include "fggl/ecs/component_fwd.hpp"
 #include "fggl/ecs3/module/module.hpp"
 #include <fggl/util/service.hpp>
 
diff --git a/include/fggl/ecs/component.hpp b/include/fggl/ecs/component.hpp
index 5ae0dfd..46c382c 100644
--- a/include/fggl/ecs/component.hpp
+++ b/include/fggl/ecs/component.hpp
@@ -25,6 +25,8 @@
 #include <utility>
 #include <iostream>
 
+#include <typeinfo>
+
 #include <vector>
 #include <unordered_map>
 #include "yaml-cpp/yaml.h"
@@ -32,9 +34,7 @@
 namespace fggl::ecs {
 
 	template<typename T>
-	bool restore_config(T* comp, const YAML::Node& node) {
-		return false;
-	}
+	bool restore_config(T* comp, const YAML::Node& node);
 
 	class ComponentBase {
 		public:
@@ -84,7 +84,7 @@ namespace fggl::ecs {
 				C* ptr = new C();
 				bool restored = restore_config<C>(ptr, config);
 				if ( !restored ) {
-					debug::warning("error restoring {}", C::name);
+					debug::error("error restoring {}", C::name);
 					assert( false && "failed to restore configuration when loading type!" );
 				}
 				return ptr;
diff --git a/include/fggl/ecs/component_fwd.hpp b/include/fggl/ecs/component_fwd.hpp
new file mode 100644
index 0000000..22c1daf
--- /dev/null
+++ b/include/fggl/ecs/component_fwd.hpp
@@ -0,0 +1,68 @@
+/*
+ * This file is part of FGGL.
+ *
+ * FGGL is free software: you can redistribute it and/or modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any
+ * later version.
+ *
+ * FGGL is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty
+ * of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License along with FGGL.
+ * If not, see <https://www.gnu.org/licenses/>.
+ */
+
+//
+// Created by webpigeon on 22/07/22.
+//
+
+#ifndef FGGL_ECS_COMPONENT_FWD_HPP
+#define FGGL_ECS_COMPONENT_FWD_HPP
+
+#include "fggl/ecs/component.hpp"
+
+#include "fggl/math/types.hpp"
+#include "fggl/gfx/phong.hpp"
+#include "fggl/data/model.hpp"
+#include "fggl/phys/types.hpp"
+
+#ifdef __GNUC__
+	#include <cxxabi.h>
+#endif
+
+namespace fggl::ecs {
+
+	template<typename T>
+	bool restore_config(T* comp, const YAML::Node& node) {
+		char* realName;
+
+		#ifdef __GNUC__
+		int status;
+		realName = abi::__cxa_demangle(typeid(T).name(), 0, 0, &status);
+		#endif
+
+		debug::log(debug::Level::warning, "restore_config is not implemented for {}", realName);
+		return false;
+	}
+
+	template<>
+	bool restore_config(math::Transform* comp, const YAML::Node& node);
+
+	template<>
+	bool restore_config(gfx::PhongMaterial* comp, const YAML::Node& node);
+
+	template<>
+	bool restore_config(data::StaticMesh* meshComp, const YAML::Node& node);
+
+	template<>
+	bool restore_config(phys::RigidBody* body, const YAML::Node& node);
+
+	template<>
+	bool restore_config(phys::CollisionCallbacks* callbacks, const YAML::Node& node);
+
+	template<>
+	bool restore_config(phys::CollisionCache* cache, const YAML::Node& node);
+
+} // namespace fggl::ecs
+
+#endif //FGGL_ECS_COMPONENT_FWD_HPP
diff --git a/include/fggl/ecs3/prototype/loader.hpp b/include/fggl/ecs3/prototype/loader.hpp
index d9a72d8..89fe334 100644
--- a/include/fggl/ecs3/prototype/loader.hpp
+++ b/include/fggl/ecs3/prototype/loader.hpp
@@ -30,6 +30,7 @@
 #include "fggl/data/procedural.hpp"
 
 #include "fggl/ecs3/ecs.hpp"
+#include "fggl/ecs/component_fwd.hpp"
 
 namespace fggl::ecs3 {
 
@@ -128,23 +129,6 @@ namespace fggl::ecs {
 	constexpr const char* SHAPE_BOX_VALUE{"box"};
 
 	// scene template specialisations
-	template<>
-	bool restore_config(math::Transform* comp, const YAML::Node& node);
-
-	template<>
-	bool restore_config(gfx::PhongMaterial* comp, const YAML::Node& node);
-
-	template<>
-	bool restore_config(data::StaticMesh* meshComp, const YAML::Node& node);
-
-	template<>
-	bool restore_config(phys::RigidBody* body, const YAML::Node& node);
-
-	template<>
-	bool restore_config(phys::CollisionCallbacks* callbacks, const YAML::Node& node);
-
-	template<>
-	bool restore_config(phys::CollisionCache* cache, const YAML::Node& node);
 }
 
 #endif //FGGL_ECS3_PROTOTYPE_LOADER_HPP
-- 
GitLab