11import os
2+ import textwrap
23
34from conan import ConanFile
45from conan .errors import ConanInvalidConfiguration
56from conan .tools .apple import is_apple_os
67from conan .tools .build import check_min_cppstd
78from conan .tools .cmake import CMake , CMakeDeps , CMakeToolchain , cmake_layout
8- from conan .tools .files import apply_conandata_patches , copy , export_conandata_patches , get , rm
9+ from conan .tools .files import copy , apply_conandata_patches , export_conandata_patches , get , rm , save
910from conan .tools .scm import Version
1011
1112required_conan_version = ">=2.1"
@@ -36,6 +37,7 @@ class WhisperCppConan(ConanFile):
3637 "coreml_allow_fallback" : [True , False ],
3738 "with_blas" : [True , False ],
3839 "with_openvino" : [True , False ],
40+ "with_cuda" : [True , False ],
3941 }
4042 default_options = {
4143 "shared" : False ,
@@ -54,6 +56,7 @@ class WhisperCppConan(ConanFile):
5456 "coreml_allow_fallback" : False ,
5557 "with_blas" : False ,
5658 "with_openvino" : False ,
59+ "with_cuda" : False ,
5760 }
5861 package_type = "library"
5962
@@ -74,12 +77,23 @@ def _compilers_minimum_version(self):
7477 }.get (self ._min_cppstd , {})
7578
7679 @property
77- def _is_openvino_option_available (self ):
78- return Version (self .version ) >= "1.5.2"
80+ def _cuda_build_module (self ):
81+ # Adding this to the package info is necessary if we want consumers of whisper to link correctly when
82+ # they activate the CUDA option. In the future, when we have a CUDA recipe this could be removed.
83+ return textwrap .dedent ("""\
84+ find_dependency(CUDAToolkit REQUIRED)
85+ if (WIN32)
86+ # As of CUDA 12.3.1, Windows does not offer a static cublas library
87+ target_link_libraries(whisper-cpp::whisper-cpp INTERFACE CUDA::cudart_static CUDA::cublas CUDA::cublasLt CUDA::cuda_driver)
88+ else ()
89+ target_link_libraries(whisper-cpp::whisper-cpp INTERFACE CUDA::cudart_static CUDA::cublas_static CUDA::cublasLt_static CUDA::cuda_driver)
90+ endif()
91+ """ )
7992
8093 def config_options (self ):
8194 if is_apple_os (self ):
8295 del self .options .with_blas
96+ del self .options .with_cuda
8397 else :
8498 del self .options .metal
8599 del self .options .metal_ndebug
@@ -90,9 +104,6 @@ def config_options(self):
90104 if self .settings .os == "Windows" :
91105 del self .options .fPIC
92106
93- if not self ._is_openvino_option_available :
94- del self .options .with_openvino
95-
96107 def configure (self ):
97108 if self .options .shared :
98109 self .options .rm_safe ("fPIC" )
@@ -112,7 +123,7 @@ def validate(self):
112123
113124 def requirements (self ):
114125 if not is_apple_os (self ):
115- if self .options .with_blas :
126+ if self .options .get_safe ( " with_blas" ) :
116127 self .requires ("openblas/0.3.24" )
117128 if self .options .get_safe ("with_openvino" ):
118129 self .requires ("openvino/2023.2.0" )
@@ -155,6 +166,12 @@ def generate(self):
155166 # TODO: Implement OpenMP support
156167 tc .variables ["GGML_OPENMP" ] = False
157168
169+ tc .variables ["GGML_CUDA" ] = bool (self .options .get_safe ("with_cuda" , False ))
170+
171+ tc .variables ["GGML_BLAS" ] = bool (self .options .get_safe ("with_blas" , False ))
172+ if self .options .get_safe ("with_blas" ):
173+ tc .variables ["GGML_BLAS_VENDOR" ] = "OpenBLAS"
174+
158175 if self .options .get_safe ("with_openvino" ):
159176 tc .variables ["WHISPER_OPENVINO" ] = True
160177 # TODO: remove with Conan 1.x support
@@ -169,16 +186,7 @@ def generate(self):
169186 tc .variables ["WHISPER_COREML" ] = True
170187 if self .options .coreml_allow_fallback :
171188 tc .variables ["WHISPER_COREML_ALLOW_FALLBACK" ] = True
172- if Version (self .version ) >= "1.7.0" :
173- tc .variables ["GGML_METAL" ] = self .options .metal
174- else :
175- tc .variables ["WHISPER_METAL" ] = self .options .metal
176- else :
177- if self .options .with_blas :
178- if Version (self .version ) >= "1.4.2" :
179- tc .variables ["WHISPER_OPENBLAS" ] = True
180- else :
181- tc .variables ["WHISPER_SUPPORT_OPENBLAS" ] = True
189+ tc .variables ["GGML_METAL" ] = bool (self .options .get_safe ("metal" , False ))
182190
183191 tc .generate ()
184192
@@ -195,21 +203,20 @@ def package(self):
195203 rm (self , "*.cmake" , self .package_folder , recursive = True )
196204 rm (self , "*.pc" , self .package_folder , recursive = True )
197205 copy (self , "*" , os .path .join (self .source_folder , "models" ), os .path .join (self .package_folder , "res" , "models" ))
206+ if self .options .get_safe ("with_cuda" ) and not self .options .shared :
207+ save (self , os .path .join (self .package_folder , "lib" , "cmake" , "whisper-cpp-cuda-static.cmake" ), self ._cuda_build_module )
198208
199209 def package_info (self ):
200210 self .cpp_info .libs = ["whisper" ]
201- if Version (self .version ) >= "1.7.0" :
202- self .cpp_info .libs .append ("ggml" )
203- if Version (self .version ) >= "1.7.3" :
204- self .cpp_info .libs .extend (["ggml-base" , "ggml-cpu" ])
211+ self .cpp_info .libs .extend (["ggml" , "ggml-base" , "ggml-cpu" ])
212+ if self .options .get_safe ("with_cuda" ):
213+ self .cpp_info .libs .append ("ggml-cuda" )
205214 self .cpp_info .resdirs = ["res" ]
206- if Version (self .version ) < "1.7.0" :
207- self .cpp_info .libdirs = ["lib" , "lib/static" ]
208215
209216 if self .options .get_safe ("with_blas" ):
210- self .cpp_info .requires = ["ggml-blas" ]
217+ self .cpp_info .libs . extend ( ["ggml-blas" ])
211218 if self .options .get_safe ("with_openvino" ):
212- self .cpp_info .requires = [ "openvino::Runtime" ]
219+ self .cpp_info .requires . append ( "openvino::Runtime" )
213220
214221 if is_apple_os (self ):
215222 if not self .options .no_accelerate :
@@ -218,7 +225,11 @@ def package_info(self):
218225 self .cpp_info .frameworks .append ("CoreML" )
219226 if self .options .get_safe ("metal" ):
220227 self .cpp_info .frameworks .extend (["CoreFoundation" , "Foundation" , "Metal" , "MetalKit" ])
221- if Version (self .version ) >= "1.7.3" :
222- self .cpp_info .libs .extend (["ggml-metal" , "ggml-blas" ])
228+ self .cpp_info .libs .extend (["ggml-metal" ])
223229 elif self .settings .os in ("Linux" , "FreeBSD" ):
224230 self .cpp_info .system_libs .extend (["dl" , "m" , "pthread" ])
231+
232+ if self .options .get_safe ("with_cuda" ) and not self .options .shared :
233+ self .cpp_info .builddirs .append (os .path .join ("lib" , "cmake" ))
234+ module_path = os .path .join ("lib" , "cmake" , "whisper-cpp-cuda-static.cmake" )
235+ self .cpp_info .set_property ("cmake_build_modules" , [module_path ])
0 commit comments