Propagate global --cache_dir to continuous batching pipeline (#4230)#4329
Propagate global --cache_dir to continuous batching pipeline (#4230)#4329exzile wants to merge 6 commits into
Conversation
End-to-end verification on GPUBeyond the unit test, I verified the actual caching behavior on an Intel Arc Pro B70 dGPU ( Run 1 (empty cache):
Run 2 (restart, populated cache):
Without the change the cache directory stays empty on the CB path and every restart recompiles. With it, blobs persist and are reused across restarts as intended. |
The continuous batching servable initializer constructs the GenAI ContinuousBatchingPipeline directly and never applied the server-level --cache_dir (ServerSettings.cacheDir). Unlike the non-CB path, which applies it via ModelInstance::setCacheOptions, the CB path left model compilation caching disabled unless the user duplicated the value into the node's plugin_config as CACHE_DIR. As a result, .blob/.cl_cache artifacts were never persisted and every restart fully recompiled the model. Inject the global cache_dir into the pipeline plugin config before constructing the pipeline. An explicit CACHE_DIR in the node's plugin_config remains authoritative. Adds a regression test (LLMNodeOptionsCacheDirPropagation) covering both propagation of the global value and precedence of an explicit node value. Fixes openvinotoolkit#4230 Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
6fd48db to
c45573c
Compare
LLMNodeOptionsCacheDirPropagation only asserts that --cache_dir lands in properties->pluginConfig, which doesn't prove OpenVINO Core actually persists compiled-model cache artifacts -- the actual symptom in openvinotoolkit#4230 (log said "cache enabled", nothing was ever written to disk). Addresses feedback on the issue: openvinotoolkit#4230 (comment) LLMNodeOptionsCacheDirWritesCacheArtifacts constructs a real ContinuousBatchingPipeline against a temp --cache_dir and asserts at least one cache file actually lands there. Verified locally on Windows (MSVC) against facebook/opt-125m: [ OK ] LLMOptionsHttpTest.LLMNodeOptionsCacheDirWritesCacheArtifacts (707 ms)
Extract the global --cache_dir propagation into a shared GenAiServableInitializer::applyGlobalCacheDir helper and call it from all GenAI initializers. The continuous batching path already applied it (and VLM_CB shares that same initializer), but the legacy LM and legacy VLM paths construct their pipelines directly and never applied the server-level cache_dir. Routing every path through one helper covers all four pipeline types (LM/VLM x CB/legacy) and removes the duplicated inline block from the CB initializer. In the cache_dir tests, replace the manual end-of-test Config restore with a GlobalCacheDirGuard RAII helper so a failed ASSERT mid-test can no longer leak the modified --cache_dir singleton into subsequent tests in the suite. The guard also removes the temporary cache directory on scope exit. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
There was a problem hiding this comment.
Pull request overview
This PR restores the server-level --cache_dir behavior for GenAI servables by propagating it into the OpenVINO GenAI pipeline pluginConfig (unless explicitly overridden by node plugin_config), ensuring compiled-model cache artifacts can persist across restarts for LLM/VLM pipelines.
Changes:
- Add
GenAiServableInitializer::applyGlobalCacheDir()to inject the global--cache_dirinto GenAI pipeline plugin properties whenCACHE_DIRis not explicitly set per node. - Call
applyGlobalCacheDir()from LM/VLM initializers (legacy + continuous batching) before constructing GenAI pipelines. - Add regression tests for cache-dir propagation (and an end-to-end cache artifact write check), plus documentation clarifying behavior.
Reviewed changes
Copilot reviewed 7 out of 7 changed files in this pull request and generated 3 comments.
Show a summary per file
| File | Description |
|---|---|
| src/test/llm/llmnode_test.cpp | Adds tests verifying --cache_dir propagation and precedence, plus an end-to-end artifact write assertion. |
| src/llm/visual_language_model/legacy/servable_initializer.cpp | Applies global cache dir before creating ov::genai::VLMPipeline. |
| src/llm/servable_initializer.hpp | Declares applyGlobalCacheDir() helper on the shared initializer base. |
| src/llm/servable_initializer.cpp | Implements applyGlobalCacheDir() using Config::instance().cacheDir() and ov::cache_dir.name(). |
| src/llm/language_model/legacy/servable_initializer.cpp | Applies global cache dir before creating ov::genai::LLMPipeline. |
| src/llm/language_model/continuous_batching/servable_initializer.cpp | Applies global cache dir before creating ov::genai::ContinuousBatchingPipeline. |
| docs/model_cache.md | Documents cache-dir behavior for GenAI/LLM pipelines and precedence rules. |
Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com>
Summary
Fixes #4230.
The continuous batching servable initializer constructs the GenAI
ContinuousBatchingPipelinedirectly and never applied the server-level--cache_dir(ServerSettings.cacheDir). Unlike the non-CB path — which applies it viaModelInstance::setCacheOptions(ieCore.set_property(ov::cache_dir(...))) — the CB path left model-compilation caching disabled unless the user manually duplicated the value into the node'splugin_configasCACHE_DIR. As a result,.blob/.cl_cacheartifacts were never persisted and every server restart fully recompiled the model.Fix
In
ContinuousBatchingServableInitializer::initialize, inject the globalcache_dirinto the pipelinepluginConfig(keyed byov::cache_dir.name()==CACHE_DIR) right after parsing the nodeplugin_configand before constructing the pipeline. An explicitCACHE_DIRin the node'splugin_configremains authoritative.This also applies to the VLM continuous-batching servable, which reuses this initializer.
Testing
Added a regression test
LLMNodeOptionsCacheDirPropagation(run for both the CB and VLM fixtures) covering:--cache_diris propagated intopluginConfig["CACHE_DIR"]when the node does not set it.CACHE_DIRin the nodeplugin_configtakes precedence over the global value.Built and ran locally on Windows (MSVC) against a real
facebook/opt-125mcontinuous-batching pipeline:🤖 Generated with Claude Code