mirror of
https://github.com/ggml-org/llama.cpp.git
synced 2025-10-28 08:31:25 +00:00
* metal : improve naming * metal : refactor device ggml-ci * cont : props ggml-ci * metal : apply ggml_mem_ranges_t ggml-ci * metal : remove GGML_METAL_USE_BF16 ggml-ci * metal : refactor device buffer ggml-ci * cont : fix naming * metal : sync before destroying the backend ggml-ci * metal : refactor context ggml-ci * metal : migrate ggml-metal.m to ggml-metal.cpp ggml-ci * metal : adjust ops API ggml-ci * metal : use C++ to store piplienes ggml-ci * metal : migrate ops to separate functions ggml-ci * metal : add ggml_metal_library_t ggml-ci * metal : improve naming ggml-ci * metal : cleanp ggml-ci * metal : add support for GGML_OP_LOG ggml-ci * metal : fix error handling ggml-ci
125 lines
5.6 KiB
CMake
125 lines
5.6 KiB
CMake
find_library(FOUNDATION_LIBRARY Foundation REQUIRED)
|
|
find_library(METAL_FRAMEWORK Metal REQUIRED)
|
|
find_library(METALKIT_FRAMEWORK MetalKit REQUIRED)
|
|
|
|
message(STATUS "Metal framework found")
|
|
|
|
ggml_add_backend_library(ggml-metal
|
|
ggml-metal.cpp
|
|
ggml-metal-device.m
|
|
ggml-metal-device.cpp
|
|
ggml-metal-common.cpp
|
|
ggml-metal-context.m
|
|
ggml-metal-ops.cpp
|
|
)
|
|
|
|
target_link_libraries(ggml-metal PRIVATE
|
|
${FOUNDATION_LIBRARY}
|
|
${METAL_FRAMEWORK}
|
|
${METALKIT_FRAMEWORK}
|
|
)
|
|
|
|
if (GGML_METAL_NDEBUG)
|
|
add_compile_definitions(GGML_METAL_NDEBUG)
|
|
endif()
|
|
|
|
# copy metal files to bin directory
|
|
configure_file(../ggml-common.h ${CMAKE_RUNTIME_OUTPUT_DIRECTORY}/ggml-common.h COPYONLY)
|
|
configure_file(ggml-metal.metal ${CMAKE_RUNTIME_OUTPUT_DIRECTORY}/ggml-metal.metal COPYONLY)
|
|
configure_file(ggml-metal-impl.h ${CMAKE_RUNTIME_OUTPUT_DIRECTORY}/ggml-metal-impl.h COPYONLY)
|
|
|
|
set(METALLIB_COMMON "${CMAKE_CURRENT_SOURCE_DIR}/../ggml-common.h")
|
|
if (GGML_METAL_EMBED_LIBRARY)
|
|
enable_language(ASM)
|
|
|
|
add_compile_definitions(GGML_METAL_EMBED_LIBRARY)
|
|
|
|
set(METALLIB_SOURCE "${CMAKE_CURRENT_SOURCE_DIR}/ggml-metal.metal")
|
|
set(METALLIB_IMPL "${CMAKE_CURRENT_SOURCE_DIR}/ggml-metal-impl.h")
|
|
|
|
file(MAKE_DIRECTORY "${CMAKE_BINARY_DIR}/autogenerated")
|
|
|
|
# merge ggml-common.h and ggml-metal.metal into a single file
|
|
set(METALLIB_EMBED_ASM "${CMAKE_BINARY_DIR}/autogenerated/ggml-metal-embed.s")
|
|
set(METALLIB_SOURCE_EMBED "${CMAKE_BINARY_DIR}/autogenerated/ggml-metal-embed.metal")
|
|
set(METALLIB_SOURCE_EMBED_TMP "${CMAKE_BINARY_DIR}/autogenerated/ggml-metal-embed.metal.tmp")
|
|
|
|
add_custom_command(
|
|
OUTPUT "${METALLIB_EMBED_ASM}"
|
|
COMMAND echo "Embedding Metal library"
|
|
COMMAND sed -e "/__embed_ggml-common.h__/r ${METALLIB_COMMON}" -e "/__embed_ggml-common.h__/d" < "${METALLIB_SOURCE}" > "${METALLIB_SOURCE_EMBED_TMP}"
|
|
COMMAND sed -e "/\#include \"ggml-metal-impl.h\"/r ${METALLIB_IMPL}" -e "/\#include \"ggml-metal-impl.h\"/d" < "${METALLIB_SOURCE_EMBED_TMP}" > "${METALLIB_SOURCE_EMBED}"
|
|
COMMAND echo ".section __DATA,__ggml_metallib" > "${METALLIB_EMBED_ASM}"
|
|
COMMAND echo ".globl _ggml_metallib_start" >> "${METALLIB_EMBED_ASM}"
|
|
COMMAND echo "_ggml_metallib_start:" >> "${METALLIB_EMBED_ASM}"
|
|
COMMAND echo .incbin "\"${METALLIB_SOURCE_EMBED}\"" >> "${METALLIB_EMBED_ASM}"
|
|
COMMAND echo ".globl _ggml_metallib_end" >> "${METALLIB_EMBED_ASM}"
|
|
COMMAND echo "_ggml_metallib_end:" >> "${METALLIB_EMBED_ASM}"
|
|
DEPENDS ../ggml-common.h ggml-metal.metal ggml-metal-impl.h
|
|
COMMENT "Generate assembly for embedded Metal library"
|
|
VERBATIM
|
|
)
|
|
|
|
target_sources(ggml-metal PRIVATE "${METALLIB_EMBED_ASM}")
|
|
else()
|
|
if (GGML_METAL_SHADER_DEBUG)
|
|
# custom command to do the following:
|
|
# xcrun -sdk macosx metal -fno-fast-math -c ggml-metal.metal -o ggml-metal.air
|
|
# xcrun -sdk macosx metallib ggml-metal.air -o default.metallib
|
|
#
|
|
# note: this is the only way I found to disable fast-math in Metal. it's ugly, but at least it works
|
|
# disabling fast math is needed in order to pass tests/test-backend-ops
|
|
# note: adding -fno-inline fixes the tests when using MTL_SHADER_VALIDATION=1
|
|
# note: unfortunately, we have to call it default.metallib instead of ggml.metallib
|
|
# ref: https://github.com/ggerganov/whisper.cpp/issues/1720
|
|
# note: adding -g causes segmentation fault during compile
|
|
#set(XC_FLAGS -fno-fast-math -fno-inline -g)
|
|
set(XC_FLAGS -fno-fast-math -fno-inline)
|
|
else()
|
|
set(XC_FLAGS -O3)
|
|
endif()
|
|
|
|
# Append macOS metal versioning flags
|
|
if (GGML_METAL_MACOSX_VERSION_MIN)
|
|
message(STATUS "Adding -mmacosx-version-min=${GGML_METAL_MACOSX_VERSION_MIN} flag to metal compilation")
|
|
list (APPEND XC_FLAGS -mmacosx-version-min=${GGML_METAL_MACOSX_VERSION_MIN})
|
|
endif()
|
|
|
|
if (GGML_METAL_STD)
|
|
message(STATUS "Adding -std=${GGML_METAL_STD} flag to metal compilation")
|
|
list (APPEND XC_FLAGS -std=${GGML_METAL_STD})
|
|
endif()
|
|
|
|
add_custom_command(
|
|
OUTPUT ${CMAKE_RUNTIME_OUTPUT_DIRECTORY}/default.metallib
|
|
COMMAND xcrun -sdk macosx metal ${XC_FLAGS} -c ${CMAKE_RUNTIME_OUTPUT_DIRECTORY}/ggml-metal.metal -o - |
|
|
xcrun -sdk macosx metallib - -o ${CMAKE_RUNTIME_OUTPUT_DIRECTORY}/default.metallib
|
|
COMMAND rm -f ${CMAKE_RUNTIME_OUTPUT_DIRECTORY}/ggml-common.h
|
|
COMMAND rm -f ${CMAKE_RUNTIME_OUTPUT_DIRECTORY}/ggml-metal.metal
|
|
DEPENDS ggml-metal.metal ${METALLIB_COMMON}
|
|
COMMENT "Compiling Metal kernels"
|
|
)
|
|
|
|
# FIXME: only add to the ggml-metal target?
|
|
add_custom_target(
|
|
ggml-metal-lib ALL
|
|
DEPENDS ${CMAKE_RUNTIME_OUTPUT_DIRECTORY}/default.metallib
|
|
)
|
|
endif() # GGML_METAL_EMBED_LIBRARY
|
|
|
|
if (NOT GGML_METAL_EMBED_LIBRARY)
|
|
install(
|
|
FILES src/ggml-metal/ggml-metal.metal
|
|
PERMISSIONS
|
|
OWNER_READ
|
|
OWNER_WRITE
|
|
GROUP_READ
|
|
WORLD_READ
|
|
DESTINATION ${CMAKE_INSTALL_BINDIR})
|
|
|
|
install(
|
|
FILES ${CMAKE_RUNTIME_OUTPUT_DIRECTORY}/default.metallib
|
|
DESTINATION ${CMAKE_INSTALL_BINDIR}
|
|
)
|
|
endif()
|