From 498039038b621cb80fd0a9b920ff9522423a2392 Mon Sep 17 00:00:00 2001
From: past-due <30942300+past-due@users.noreply.github.com>
Date: Sun, 15 Oct 2023 16:42:45 -0400
Subject: [PATCH] vk_mem_alloc.h: Patch for C++14 compilation on Linux, BSDs

---
 lib/ivis_opengl/3rdparty/vk_mem_alloc.cpp | 47 +++++++++++++++++++++++
 lib/ivis_opengl/3rdparty/vk_mem_alloc.h   |  1 +
 2 files changed, 48 insertions(+)

diff --git a/lib/ivis_opengl/3rdparty/vk_mem_alloc.cpp b/lib/ivis_opengl/3rdparty/vk_mem_alloc.cpp
index dad4a116e39..1e845de0388 100644
--- a/lib/ivis_opengl/3rdparty/vk_mem_alloc.cpp
+++ b/lib/ivis_opengl/3rdparty/vk_mem_alloc.cpp
@@ -27,6 +27,7 @@
 # pragma clang diagnostic ignored "-Wmissing-field-initializers"
 # pragma clang diagnostic ignored "-Wunused-private-field"
 # pragma clang diagnostic ignored "-Wcast-align"
+# pragma clang diagnostic ignored "-Wunused-function"
 #  if defined(__APPLE__)
 #    pragma clang diagnostic ignored "-Wnullability-completeness" // Warning triggered on newer Xcode
 #  endif
@@ -45,17 +46,63 @@
 # pragma GCC diagnostic ignored "-Wmissing-field-initializers"
 # pragma GCC diagnostic ignored "-Wmissing-noreturn"
 # pragma GCC diagnostic ignored "-Wcast-align"
+# pragma GCC diagnostic ignored "-Wunused-function"
 #elif defined(_MSC_VER)
 # pragma warning( push )
 # pragma warning( disable : 4189 ) // warning C4189: 'identifier' : local variable is initialized but not referenced
 # pragma warning( disable : 4324 ) // warning C4324: 'struct_name' : structure was padded due to alignment specifier
 # pragma warning( disable : 4127 ) // warning C4127: conditional expression is constant
+# pragma warning( disable : 4505 ) // warning C4505: unreferenced function with internal linkage has been removed
 #endif
 
 #define VMA_IMPLEMENTATION
 #define VMA_STATIC_VULKAN_FUNCTIONS 0
 #define VMA_DYNAMIC_VULKAN_FUNCTIONS 0
 #define VMA_ASSERT(expr) ASSERT(expr, "VMA_ASSERT failed")
+#include <cstdio>
+
+// The VMA_NULLABLE macro is defined to be _Nullable when compiling with Clang.
+// see: https://clang.llvm.org/docs/AttributeReference.html#nullable
+#ifndef VMA_NULLABLE
+	#ifdef __clang__
+		#define VMA_NULLABLE _Nullable
+	#else
+		#define VMA_NULLABLE
+	#endif
+#endif
+
+// WZ Patch for C++14 compilation
+#if (__cplusplus >= 201402L && __cplusplus < 201703L)
+# if defined(__ANDROID_API__) && (__ANDROID_API__ < 16)
+	// do not do anything - is handled by vk_mem_alloc
+# elif defined(__APPLE__) || defined(__ANDROID__)
+	// do not do anything - is handled by vk_mem_alloc
+# elif defined(__linux__) || defined(__FreeBSD__) || defined(__DragonFly__) || defined(__OpenBSD__) || defined(__NetBSD__)
+	// On C++14, implement for Linux + BSDs (until we can require C++17)
+	// Reference: https://github.com/GPUOpen-LibrariesAndSDKs/VulkanMemoryAllocator/issues/332
+	#include <cstdlib>
+	static void* wz_vma_aligned_alloc(size_t alignment, size_t size)
+	{
+		// alignment must be >= sizeof(void*)
+		if(alignment < sizeof(void*))
+		{
+			alignment = sizeof(void*);
+		}
+
+		void *pointer;
+		if(posix_memalign(&pointer, alignment, size) == 0)
+			return pointer;
+		return nullptr;
+	}
+	static void wz_vma_aligned_free(void* VMA_NULLABLE ptr)
+	{
+		free(ptr);
+	}
+#  define VMA_SYSTEM_ALIGNED_MALLOC(size, alignment)	wz_vma_aligned_alloc((alignment), (size))
+#  define VMA_SYSTEM_ALIGNED_FREE(ptr)					wz_vma_aligned_free(ptr)
+# endif
+#endif
+
 #include "vk_mem_alloc.h"
 
 #if defined(__clang__)
diff --git a/lib/ivis_opengl/3rdparty/vk_mem_alloc.h b/lib/ivis_opengl/3rdparty/vk_mem_alloc.h
index 3cc5880d160..bbd8d06641f 100644
--- a/lib/ivis_opengl/3rdparty/vk_mem_alloc.h
+++ b/lib/ivis_opengl/3rdparty/vk_mem_alloc.h
@@ -2813,6 +2813,7 @@ static void* vma_aligned_alloc(size_t alignment, size_t size)
 #else
 static void* vma_aligned_alloc(size_t alignment, size_t size)
 {
+    #error No available implementation for vma_aligned_alloc
     VMA_ASSERT(0 && "Could not implement aligned_alloc automatically. Please enable C++17 or later in your compiler or provide custom implementation of macro VMA_SYSTEM_ALIGNED_MALLOC (and VMA_SYSTEM_ALIGNED_FREE if needed) using the API of your system.");
     return VMA_NULL;
 }