Skip to content

Instantly share code, notes, and snippets.

@xeechou
Created February 28, 2022 15:21
Show Gist options
  • Save xeechou/5c5ee8e7444dd35dc78e3022162d2a45 to your computer and use it in GitHub Desktop.
Save xeechou/5c5ee8e7444dd35dc78e3022162d2a45 to your computer and use it in GitHub Desktop.
include(CompileShader)
find_program(DXC_EXE NAMES dxc REQUIRED)
if (NOT DXC_EXE)
message(FATAL "The dxc executable is not available. You must install it")
endif()
################################################################################
macro(compile_hlsl_parse_options)
if(${CS_INVERT_Y})
set(ARG_INVERT_Y "-fvk-invert-y")
endif()
if(${CS_DEBUG})
set(ARG_DEBUG "-Zi")
endif()
if(${CS_WERROR})
set(ARG_WERROR "-WX")
endif()
#enable ray marching shaders
set(ARG_RT
"-fspv-extension=SPV_KHR_ray_tracing"
"-fspv-extension=SPV_KHR_multiview"
"-fspv-extension=SPV_KHR_shader_draw_parameters"
"-fspv-extension=SPV_EXT_descriptor_indexing")
endmacro()
################################################################################
macro(compile_hlsl_parse_oneargs)
if(NOT DEFINED CS_INPUT OR NOT EXISTS "${CS_INPUT}")
message(FATAL_ERROR "shader compiler requires input")
endif()
if(NOT DEFINED CS_OUTPUT)
message(FATAL_ERROR "shader compiler requires writing output")
endif()
if(NOT DEFINED CS_SMODEL)
set(CS_SMODEL "6_1") #default profile to shader model 6.1
endif()
if(DEFINED CS_STAGE)
set(ARG_PROFILE "-T" "${CS_STAGE}_${CS_SMODEL}")
else()
compile_shader_guess_stage(stage "${CS_FILE}" "hlsl")
set(ARG_PROFILE "-T" "${stage}_${CS_SMODEL}")
endif()
if(DEFINED CS_TARGET)
set(ARG_TARGET "-fspv-target-env=vulkan${CS_TARGET}")
else()
set(ARG_TARGET "-fspv-target-env=vulkan1.2")
endif()
endmacro()
################################################################################
#now you can simply add the _spirv to a custom target
function(compile_hlsl)
set(options INVERT_Y DEBUG WERROR)
set(oneValueArgs INPUT OUTPUT STAGE TARGET SMODEL)
set(multiValueArgs MACROS INCLUDES)
cmake_parse_arguments(CS "${options}" "${oneValueArgs}"
"${multiValueArgs}" ${ARGN})
set(TMPDIR $ENV{TMP})
if (NOT TMPDIR)
set(TMPDIR "${CMAKE_CURRENT_BINARY_DIR}/tmp")
endif()
get_filename_component(dir "${CS_INPUT}" DIRECTORY)
get_filename_component(infile "${CS_INPUT}" ABSOLUTE)
get_filename_component(basename "${CS_INPUT}" NAME)
set(spirv "${TMPDIR}/${basename}.spv")
set("${CS_OUTPUT}" ${spirv} PARENT_SCOPE)
set(CS_FILE "${basename}")
compile_hlsl_parse_options()
compile_hlsl_parse_oneargs()
compile_shader_parse_mulargs()
add_custom_command(
OUTPUT "${spirv}"
COMMAND ${CMAKE_COMMAND} -E make_directory ${TMPDIR}
COMMAND ${DXC_EXE} -spirv -Fo "${spirv}"
${ARG_PROFILE} ${ARG_TARGET} ${ARG_RT} "${infile}"
WORKING_DIRECTORY "${dir}"
DEPENDS "${infile}"
COMMAND_EXPAND_LISTS
VERBATIM
)
endfunction(compile_hlsl)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment