From 16d9d5cd6c04aaddf3b53f161f346fdee2faa21e Mon Sep 17 00:00:00 2001
From: Arina Neshlyaeva <arina.neshlyaeva@intel.com>
Date: Tue, 23 Aug 2022 15:20:18 -0700
Subject: [PATCH] Added CMake flag and ISPC definition to enable/disable opaque
 pointers mode

---
 CMakeLists.txt               | 30 ++++++++++++++++++++++++++++++
 cmake/GenerateBuiltins.cmake |  2 +-
 src/ispc.cpp                 | 19 +++++++++++++++++++
 3 files changed, 50 insertions(+), 1 deletion(-)

diff --git a/CMakeLists.txt b/CMakeLists.txt
index 32d8b3e8c..1176f96aa 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -62,6 +62,8 @@ option(ISPC_INCLUDE_UTILS "Generate build targets for the utils." ON)
 option(ISPC_PREPARE_PACKAGE "Generate build targets for ispc package" OFF)
 option(ISPC_NO_DUMPS "Turn off functionality, which requires LLVM dump() functions" OFF)
 
+option(ISPC_OPAQUE_PTR_MODE "Build ISPC with usage of opaque pointers" OFF)
+
 option(ISPC_CROSS "Build ISPC with cross compilation support" OFF)
 # Default settings for cross compilation
 if (ISPC_CROSS)
@@ -288,6 +290,9 @@ if (WASM_ENABLED)
 endif()
 
 set(CLANG_LIBRARY_LIST clangFrontend clangDriver clangSerialization clangParse clangSema clangAnalysis clangAST clangBasic clangEdit clangLex)
+if (${LLVM_VERSION_NUMBER} VERSION_GREATER_EQUAL "15.0.0")
+    list(APPEND CLANG_LIBRARY_LIST clangSupport)
+endif()
 set(LLVM_COMPONENTS engine ipo bitreader bitwriter instrumentation linker option frontendopenmp)
 
 if (X86_ENABLED)
@@ -312,6 +317,25 @@ if (XE_ENABLED)
     list(APPEND XE_LIBRARY_LIST LLVMGenXIntrinsics LLVMSPIRVLib)
 endif()
 
+# Set the flag responsible for generation of opaque pointers in builtins
+set(ISPC_OPAQUE_FLAGS)
+if (ISPC_OPAQUE_PTR_MODE)
+    if (${LLVM_VERSION_NUMBER} VERSION_GREATER_EQUAL "15.0.0")
+    # Do nothing, opaque pointers mode is default
+    elseif (${LLVM_VERSION_NUMBER} VERSION_EQUAL "14.0.0")
+    # Explicitly enable opaque pointers for LLVM 14.0
+        set(ISPC_OPAQUE_FLAGS "-Xclang" "-opaque-pointers")
+    else()
+        message(FATAL_ERROR "ISPC opaque pointers mode is not supported with LLVM " ${LLVM_VERSION_NUMBER})
+    endif()
+else()
+    # Explicitly disable opaque pointers starting LLVM 15.0
+    if (${LLVM_VERSION_NUMBER} VERSION_GREATER_EQUAL "15.0.0")
+        set(ISPC_OPAQUE_FLAGS "-Xclang" "-no-opaque-pointers")
+    endif()
+endif()
+message(STATUS "ISPC opaque pointers mode is " ${ISPC_OPAQUE_PTR_MODE})
+
 get_llvm_libfiles(LLVM_LIBRARY_LIST ${LLVM_COMPONENTS})
 get_llvm_cppflags(LLVM_CPP_FLAGS)
 
@@ -395,6 +419,7 @@ endif()
 if (ARM_ENABLED)
     target_compile_definitions(${PROJECT_NAME} PRIVATE ISPC_ARM_ENABLED)
 endif()
+
 if (XE_ENABLED)
     target_compile_definitions(${PROJECT_NAME} PRIVATE ISPC_XE_ENABLED)
 endif()
@@ -430,6 +455,11 @@ if (NOT ISPC_PS_TARGET)
     target_compile_definitions(${PROJECT_NAME} PRIVATE ISPC_PS_TARGET_OFF)
 endif()
 
+# Compile definition for opaque pointers mode
+if (ISPC_OPAQUE_PTR_MODE)
+    target_compile_definitions(${PROJECT_NAME} PRIVATE ISPC_OPAQUE_PTR_MODE)
+endif()
+
 # Include directories
 target_include_directories(${PROJECT_NAME} PRIVATE
                            ${LLVM_INCLUDE_DIRS}
diff --git a/cmake/GenerateBuiltins.cmake b/cmake/GenerateBuiltins.cmake
index 77393a62d..602b9bde6 100644
--- a/cmake/GenerateBuiltins.cmake
+++ b/cmake/GenerateBuiltins.cmake
@@ -293,7 +293,7 @@ function(builtin_to_cpp bit os_name arch supported_archs supported_oses resultFi
     else()
         add_custom_command(
             OUTPUT ${output}
-            COMMAND ${CLANGPP_EXECUTABLE} ${target_flags} -I${CMAKE_SOURCE_DIR} -m${bit} -emit-llvm --std=gnu++17 -c ${inputFilePath} -o - | (\"${LLVM_DIS_EXECUTABLE}\" - || echo "builtins-c-*.cpp compile error")
+            COMMAND ${CLANGPP_EXECUTABLE} ${target_flags} -I${CMAKE_SOURCE_DIR} -m${bit} -emit-llvm ${ISPC_OPAQUE_FLAGS} --std=gnu++17 -c ${inputFilePath} -o - | (\"${LLVM_DIS_EXECUTABLE}\" - || echo "builtins-c-*.cpp compile error")
                 | \"${Python3_EXECUTABLE}\" bitcode2cpp.py c --type=builtins-c --runtime=${bit} --os=${os_name} --arch=${target_arch} --llvm_as ${LLVM_AS_EXECUTABLE}
                 > ${output}
             DEPENDS ${inputFilePath} bitcode2cpp.py
diff --git a/src/ispc.cpp b/src/ispc.cpp
index 4fd7322fe..b0602b433 100644
--- a/src/ispc.cpp
+++ b/src/ispc.cpp
@@ -1995,6 +1995,25 @@ Globals::Globals() {
     timeTraceGranularity = 500;
     target = NULL;
     ctx = new llvm::LLVMContext;
+
+// Opaque pointers mode is supported starting from LLVM 14,
+// became default in LLVM 15
+#ifdef ISPC_OPAQUE_PTR_MODE
+#if ISPC_LLVM_VERSION >= ISPC_LLVM_15_0
+// Do nothing, opaque pointers mode is default
+#elif ISPC_LLVM_VERSION == ISPC_LLVM_14_0
+    // Explicitly enable opaque pointers mode for LLVM 14.0
+    ctx->setOpaquePointers(true);
+#else
+    FATAL("Opaque pointers mode is not supported with this LLVM version!");
+#endif
+#else
+#if ISPC_LLVM_VERSION >= ISPC_LLVM_15_0
+    // Explicitly disable opaque pointers starting LLVM 15.0
+    ctx->setOpaquePointers(false);
+#endif
+#endif
+
 #ifdef ISPC_XE_ENABLED
     stackMemSize = 0;
 #endif
