From 8c9f6849cd0ca2930fc541b74e4295bfff7aa38f Mon Sep 17 00:00:00 2001 From: Ivan Pleshkov Date: Mon, 9 Dec 2024 12:00:12 +0100 Subject: [PATCH] Add GPU support into Dockerfile (#5584) * gpu hnsw add gpu indexing flag add gpu vector storage time measurement add chmod flag build hnsw using gpu scoring speedup move gl_GlobalInvocationID to mains glslc with o flag fix tests use gpu atomics instead of multiple runs enable atomics add timers profile search let shader work while points collection use generations for visited flags add gpu init timer avoid entries download remove gpu call timers for a while rename to combined graph builder move gpu graph builder restore levels in link access restore links_map add gpu start condition use graph builder links memory remove mut's list point ids before processing download-upload links using methods only cpu graph builder as separate struct add cpu threads count parallel cpu build single threaded cpu preprocess try to fix glove accuracy unsafe Send and Sync for gpu builder copy graph layers builder instead of moving remove obsolete mut fix build move builders to arc fix bfb deadlock move uneccessary clear run cpu and gpu in separate threads many vectors storage buffers debug gpu vector storage fix vector storage upload bug add cpu ful graph build don't use non-ready links for point try to resolve conflicts while upsert add indexing unit test for measurements add test utilize cpu more efficient dont clear bhaep debug gpu runs try to use vec4 instead of mat4 dump scores count estimate gpu usage print usage per run start using working groups build shaders for vulkan v1.3 start shaders subgroup vk instance version 1.3 subgroup vector storage fix test nearest heap nearest heap test are you happy fmt add assert to nearest heap test are you happy fmt gpu visited flags start candidates heap candidates heap push debug nearest heap remove subgroupExclusiveMin fix build are you happy clippy remove links dependency from nearest heap provide input count to nearest test are you happy fmt provide ef to shader are you happy fmt get subgroup size move compiled shaders are you happy fmt fix workgroups count for vector storage compute test return true subgroup size do nearest heap on gpu with partial sorting remove tmp shader unite scores and indices are you happy fmt gpu nearest sorting are you happy fmt fix nearest heap test links test with subgroups gpu candidates start fix candidates sorting are you happy fmt fix candidates test on m1 chip move obsolete and test shaders start new gpu search context search context test fix links uploading debug hnsw searh on level test fix gpu hnsw search on level test move test initialization to separate function gpu greedy search shader test test heuristic shader gpu greedy search test gpu test heuristic move greedy search into searcher start insertion shader find hnsw patch on gpu fix gpu patches test start gpu graph builder equivalency test fix layers check add timers are you happy fmt quality test and fix multithreaded bug debug tests are you happy fmt fix levels count and clear links fix equivalency test remove obsolete solution trivial gpu indexing integration gpu config and skip conflicts for large hnsw glsl generic vector storage element type gpu generic vector storage enable vulkan features for f16 and u8 force_half_precision option add force f16 test fix u8 and f16 unit tests apply generic shaders in hnsw construction remove conflicts check; start cpu utilization cpu prebuild upload first point links to gpu mark all points in cpu graph as ready multithreaded cpu and gpu fix equivalency test remove cpu links copy parallel patches clearing fix multithreaded env external layers source more logs to debug cpu+gpu syncronization clear gpu processed points count remove some temp logs fix cpu stop condition bug new insert vector shader greedy search returns only ids download whole layer links apply new links on gpu directly update win shader script parallel links loading provide memory amount as setting and estimate groups count start bq gpu bq test fix tests shaders invocations refactor revert max groups settings gix build after rebase fix bug after rebase upload links to gpu in cpu thread fix greedy search iteration atomic checker for conflicts dump graph changes for debugging move iterator to separate file start combined builder refactor start cpu builder as separate struct separate gpu and cpu construction fix tests fix atomics count bug upload links to gpu as separate fn glue cpu and gpu gpu thread link points on cpu while gpu is busy fix gpu bq scoring test use xor instead of calc it reallocate with less groups if not enough gpu memory update compiled shaders don't use llvm gpu emulator debug panic if no gpu remove tmp debug dumping dockerfile for gpu customize candidates count fix gpu storage size runtime shader compilation dim as define nearest heap params as macro candidates and links capacities as macro parallel bitonic sort use bubble sort too nearest heap as shared limited shared candidates heap combine buble and bitonic sorts one-argumented similarity cache vector for scoring dont check candidates overflow do greedy before search visited hashtable Revert "visited hashtable" This reverts commit 7540d04d3859d02f17908c874927d18076f3eb8e. use less flushes bulk sum calculation Revert "bulk sum calculation" This reverts commit 6ef78ceb8d6ba7d9bf2077804548df162052c749. load vector in one read Revert "load vector in one read" This reverts commit ea980d0399b90f44638590d40fdbfb1d6ffa9504. fix build after rebase fix build after rebase sq support simplify bq uploading using constructed quantization metrics alignment depends on subgroup size are you happy fmt exact flag use lazy static for device access remove prints test reallocation factor visited flags capacity as a compile time constant build gpu hnsw for payload blocks add dynamically sized subgroup size support fix build update rust version for nvidia docker dynamically sized subgroups start device filter test device filter are you happy clippy devices manager provide device instead of flag, better locking partial cpu permit release free cpus when gpu enabled use cpu is waiting is disabled create device only when gpu is enabled cpu permit release all cases parallel indices count provide queue index small refactor of shader builder are you happy fmt quantization params as separate struct pq refactor fmt remove upload_mapped_ptr from gpu buffer refactor gpu buffer check buffer range buffer refactor refactor pipeline move shader compiler to instance refactor context more refactor no unwraps in gpu crate clippy apply pr changes are you happy fmt dont use shaderc in segment more gpu tests pq bq tests provide bq option fix bq for small dim bind pq buffers pq more complex test cover all storage types by tests test multi and vectors as iterator multivectors upload data multivectors shader fix multivector tests refactor shader builder move storage tests into separate file move quantization to separate file refactor gpu vector storage creation refactor gpu quantization api dont convert to float when unnecessary more comments small upload vectors refactor fix build after rebase fix tests after rebase different vk queue priorities capacity vectors upload stopper amd dockerfile fix build after rebase parent ec4d42e7f69a76f2dfd2e1eab6b9cf42d9e33a93 author Ivan Pleshkov 1692111338 +0200 committer Ivan Pleshkov 1732698560 +0100 gpu hnsw add gpu indexing flag add gpu vector storage time measurement add chmod flag build hnsw using gpu scoring speedup move gl_GlobalInvocationID to mains glslc with o flag fix tests use gpu atomics instead of multiple runs enable atomics add timers profile search let shader work while points collection use generations for visited flags add gpu init timer avoid entries download remove gpu call timers for a while rename to combined graph builder move gpu graph builder restore levels in link access restore links_map add gpu start condition use graph builder links memory remove mut's list point ids before processing download-upload links using methods only cpu graph builder as separate struct add cpu threads count parallel cpu build single threaded cpu preprocess try to fix glove accuracy unsafe Send and Sync for gpu builder copy graph layers builder instead of moving remove obsolete mut fix build move builders to arc fix bfb deadlock move uneccessary clear run cpu and gpu in separate threads many vectors storage buffers debug gpu vector storage fix vector storage upload bug add cpu ful graph build don't use non-ready links for point try to resolve conflicts while upsert add indexing unit test for measurements add test utilize cpu more efficient dont clear bhaep debug gpu runs try to use vec4 instead of mat4 dump scores count estimate gpu usage print usage per run start using working groups build shaders for vulkan v1.3 start shaders subgroup vk instance version 1.3 subgroup vector storage fix test nearest heap nearest heap test are you happy fmt add assert to nearest heap test are you happy fmt gpu visited flags start candidates heap candidates heap push debug nearest heap remove subgroupExclusiveMin fix build are you happy clippy remove links dependency from nearest heap provide input count to nearest test are you happy fmt provide ef to shader are you happy fmt get subgroup size move compiled shaders are you happy fmt fix workgroups count for vector storage compute test return true subgroup size do nearest heap on gpu with partial sorting remove tmp shader unite scores and indices are you happy fmt gpu nearest sorting are you happy fmt fix nearest heap test links test with subgroups gpu candidates start fix candidates sorting are you happy fmt fix candidates test on m1 chip move obsolete and test shaders start new gpu search context search context test fix links uploading debug hnsw searh on level test fix gpu hnsw search on level test move test initialization to separate function gpu greedy search shader test test heuristic shader gpu greedy search test gpu test heuristic move greedy search into searcher start insertion shader find hnsw patch on gpu fix gpu patches test start gpu graph builder equivalency test fix layers check add timers are you happy fmt quality test and fix multithreaded bug debug tests are you happy fmt fix levels count and clear links fix equivalency test remove obsolete solution trivial gpu indexing integration gpu config and skip conflicts for large hnsw glsl generic vector storage element type gpu generic vector storage enable vulkan features for f16 and u8 force_half_precision option add force f16 test fix u8 and f16 unit tests apply generic shaders in hnsw construction remove conflicts check; start cpu utilization cpu prebuild upload first point links to gpu mark all points in cpu graph as ready multithreaded cpu and gpu fix equivalency test remove cpu links copy parallel patches clearing fix multithreaded env external layers source more logs to debug cpu+gpu syncronization clear gpu processed points count remove some temp logs fix cpu stop condition bug new insert vector shader greedy search returns only ids download whole layer links apply new links on gpu directly update win shader script parallel links loading provide memory amount as setting and estimate groups count start bq gpu bq test fix tests shaders invocations refactor revert max groups settings gix build after rebase fix bug after rebase upload links to gpu in cpu thread fix greedy search iteration atomic checker for conflicts dump graph changes for debugging move iterator to separate file start combined builder refactor start cpu builder as separate struct separate gpu and cpu construction fix tests fix atomics count bug upload links to gpu as separate fn glue cpu and gpu gpu thread link points on cpu while gpu is busy fix gpu bq scoring test use xor instead of calc it reallocate with less groups if not enough gpu memory update compiled shaders don't use llvm gpu emulator debug panic if no gpu remove tmp debug dumping dockerfile for gpu customize candidates count fix gpu storage size runtime shader compilation dim as define nearest heap params as macro candidates and links capacities as macro parallel bitonic sort use bubble sort too nearest heap as shared limited shared candidates heap combine buble and bitonic sorts one-argumented similarity cache vector for scoring dont check candidates overflow do greedy before search visited hashtable Revert "visited hashtable" This reverts commit 7540d04d3859d02f17908c874927d18076f3eb8e. use less flushes bulk sum calculation Revert "bulk sum calculation" This reverts commit 6ef78ceb8d6ba7d9bf2077804548df162052c749. load vector in one read Revert "load vector in one read" This reverts commit ea980d0399b90f44638590d40fdbfb1d6ffa9504. fix build after rebase fix build after rebase sq support simplify bq uploading using constructed quantization metrics alignment depends on subgroup size are you happy fmt exact flag use lazy static for device access remove prints test reallocation factor visited flags capacity as a compile time constant build gpu hnsw for payload blocks add dynamically sized subgroup size support fix build update rust version for nvidia docker dynamically sized subgroups start device filter test device filter are you happy clippy devices manager provide device instead of flag, better locking partial cpu permit release free cpus when gpu enabled use cpu is waiting is disabled create device only when gpu is enabled cpu permit release all cases parallel indices count provide queue index small refactor of shader builder are you happy fmt quantization params as separate struct pq refactor fmt remove upload_mapped_ptr from gpu buffer refactor gpu buffer check buffer range buffer refactor refactor pipeline move shader compiler to instance refactor context more refactor no unwraps in gpu crate clippy apply pr changes are you happy fmt dont use shaderc in segment more gpu tests pq bq tests provide bq option fix bq for small dim bind pq buffers pq more complex test cover all storage types by tests test multi and vectors as iterator multivectors upload data multivectors shader fix multivector tests refactor shader builder move storage tests into separate file move quantization to separate file refactor gpu vector storage creation refactor gpu quantization api dont convert to float when unnecessary more comments small upload vectors refactor fix build after rebase fix tests after rebase different vk queue priorities capacity experiment with heaps reverse candidates heap scan only half of candidates avoid heap code duplication call subgroup elect inside bheap united nearest and candidates heaps remove cands and nearest heaps shaders fix tests start linear implementation remove nearest and candidates entities visited flags with id remap simplify cpu side move hnsw search shader into tests simplify simplify gpu links test visited flags remap remove GpuSearchContextGroupAllocation stopper and allow integrated flag add timeout comment refactor batched points refactor links and device manager are you happy clippy fix build after rebase fix build after rebase remove temp files create gpu vectors in segment constructor clean up clean up refactor gpu feature refactor gpu construction in hnsw.rs provide gpu device remove pub simplify main graph renames telemetry and settings refactor update cargo lock remove env_logger from deps update openapi gpu hnsw unit test rename test log device name while indexing * are you happy clippy * are you happy clippy * dockerfile with amd and nvidia gpu support * add gpu arg to stages * clear after rebase * Apply suggestions from code review Co-authored-by: Roman Titov * review remarks * fix CI * cnahge arg to env --------- Co-authored-by: Roman Titov --- Cargo.lock | 2 +- Dockerfile | 51 ++++++++++++++++++++++++++++++++++++++--- lib/gpu/Cargo.toml | 2 +- lib/gpu/nvidia_icd.json | 7 ++++++ 4 files changed, 57 insertions(+), 5 deletions(-) create mode 100644 lib/gpu/nvidia_icd.json diff --git a/Cargo.lock b/Cargo.lock index e7570bc020..c8306aa5ce 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -2413,7 +2413,7 @@ checksum = "d2fabcfbdc87f4758337ca535fb41a6d701b65693ce38287d856d1674551ec9b" [[package]] name = "gpu" -version = "0.0.1" +version = "0.1.0" dependencies = [ "ash", "gpu-allocator", diff --git a/Dockerfile b/Dockerfile index 4283720bb6..94c567a677 100644 --- a/Dockerfile +++ b/Dockerfile @@ -1,3 +1,8 @@ +# Enable GPU support. +# This option can be set to `nvidia` or `amd` to enable GPU support. +# This option is defined here because it is used in `FROM` instructions. +ARG GPU + # Cross-compiling using Docker multi-platform builds/images and `xx`. # # https://docs.docker.com/build/building/multi-platform/ @@ -76,6 +81,9 @@ ARG RUSTFLAGS # Select linker (e.g., `mold`, `lld` or an empty string for the default linker) ARG LINKER=mold +# Enable GPU support +ARG GPU + COPY --from=planner /qdrant/recipe.json recipe.json # `PKG_CONFIG=...` is a workaround for `xx-cargo` bug for crates using `pkg-config`! # @@ -84,7 +92,7 @@ COPY --from=planner /qdrant/recipe.json recipe.json RUN PKG_CONFIG="/usr/bin/$(xx-info)-pkg-config" \ PATH="$PATH:/opt/mold/bin" \ RUSTFLAGS="${LINKER:+-C link-arg=-fuse-ld=}$LINKER $RUSTFLAGS" \ - xx-cargo chef cook --profile $PROFILE ${FEATURES:+--features} $FEATURES --features=stacktrace --recipe-path recipe.json + xx-cargo chef cook --profile $PROFILE ${FEATURES:+--features} $FEATURES --features=stacktrace ${GPU:+--features=gpu} --recipe-path recipe.json COPY . . # Include git commit into Qdrant binary during build @@ -96,7 +104,7 @@ ARG GIT_COMMIT_ID RUN PKG_CONFIG="/usr/bin/$(xx-info)-pkg-config" \ PATH="$PATH:/opt/mold/bin" \ RUSTFLAGS="${LINKER:+-C link-arg=-fuse-ld=}$LINKER $RUSTFLAGS" \ - xx-cargo build --profile $PROFILE ${FEATURES:+--features} $FEATURES --features=stacktrace --bin qdrant \ + xx-cargo build --profile $PROFILE ${FEATURES:+--features} $FEATURES --features=stacktrace ${GPU:+--features=gpu} --bin qdrant \ && PROFILE_DIR=$(if [ "$PROFILE" = dev ]; then echo debug; else echo $PROFILE; fi) \ && mv target/$(xx-cargo --print-target-triple)/$PROFILE_DIR/qdrant /qdrant/qdrant @@ -104,10 +112,47 @@ RUN PKG_CONFIG="/usr/bin/$(xx-info)-pkg-config" \ RUN mkdir /static && STATIC_DIR=/static ./tools/sync-web-ui.sh -FROM debian:12-slim AS qdrant +# Dockerfile does not support conditional `FROM` directly. +# To workaround this limitation, we use a multi-stage build with a different base images which have equal name to ARG value. + +# Base image for Qdrant. +FROM debian:12-slim AS qdrant-cpu + + +# Base images for Qdrant with nvidia GPU support. +FROM nvidia/opengl:1.0-glvnd-devel-ubuntu22.04 AS qdrant-gpu-nvidia +# Set non-interactive mode for apt-get. +ENV DEBIAN_FRONTEND=noninteractive +# Set NVIDIA driver capabilities. By default, all capabilities are disabled. +ENV NVIDIA_DRIVER_CAPABILITIES compute,graphics,utility +# Copy Nvidia ICD loader file into the container. +COPY --from=builder /qdrant/lib/gpu/nvidia_icd.json /etc/vulkan/icd.d/ +# Override maintainer label. Nvidia base image have it's own maintainer label. +LABEL maintainer "Qdrant Team " + + +# Base images for Qdrant with amd GPU support. +FROM rocm/dev-ubuntu-22.04 AS qdrant-gpu-amd +# Set non-interactive mode for apt-get. +ENV DEBIAN_FRONTEND=noninteractive +# Override maintainer label. AMD base image have it's own maintainer label. +LABEL maintainer "Qdrant Team " + + +FROM qdrant-${GPU:+gpu-}${GPU:-cpu} AS qdrant RUN apt-get update +# Install GPU dependencies +ARG GPU + +RUN if [ -n "$GPU" ]; then \ + apt-get install -y \ + libvulkan1 \ + libvulkan-dev \ + vulkan-tools \ + ; fi + # Install additional packages into the container. # E.g., the debugger of choice: gdb/gdbserver/lldb. ARG PACKAGES diff --git a/lib/gpu/Cargo.toml b/lib/gpu/Cargo.toml index c25a7cf7a5..f2001e4e27 100644 --- a/lib/gpu/Cargo.toml +++ b/lib/gpu/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "gpu" -version = "0.0.1" +version = "0.1.0" authors = [ "Qdrant Team ", ] diff --git a/lib/gpu/nvidia_icd.json b/lib/gpu/nvidia_icd.json new file mode 100644 index 0000000000..f86d4956c9 --- /dev/null +++ b/lib/gpu/nvidia_icd.json @@ -0,0 +1,7 @@ +{ + "file_format_version" : "1.0.0", + "ICD": { + "library_path": "libGLX_nvidia.so.0", + "api_version" : "1.3" + } +}