88import tempfile
99import urllib .request
1010import zipfile
11- from typing import Optional
11+ from typing import Dict , List , Optional , Tuple
1212
1313from tqdm import tqdm
1414
@@ -156,7 +156,7 @@ def _extract_tar(archive_path: pathlib.Path, prefix: str, target_dir: pathlib.Pa
156156LLVM_VERSION = "14.0.0"
157157LIBCXX_BASE_NAME = f"clang+llvm-{ LLVM_VERSION } -x86_64-linux-gnu-ubuntu-18.04"
158158LLVM_URL = f"https://github.com/llvm/llvm-project/releases/download/llvmorg-{ LLVM_VERSION } /{ LIBCXX_BASE_NAME } .tar.xz"
159- REQUIRED_LIBS = [
159+ REQUIRED_LIBC_LIBS = [
160160 "libc++.so.1.0" ,
161161 "libc++abi.so.1.0" ,
162162 "libunwind.so.1" ,
@@ -168,7 +168,7 @@ def _extract_tar(archive_path: pathlib.Path, prefix: str, target_dir: pathlib.Pa
168168def _stage_libcxx (target_dir : pathlib .Path ):
169169 target_dir .mkdir (parents = True , exist_ok = True )
170170
171- if all ((target_dir / libname ).exists () for libname in REQUIRED_LIBS ):
171+ if all ((target_dir / libname ).exists () for libname in REQUIRED_LIBC_LIBS ):
172172 print (f"[libcxx] Already staged at { target_dir } , skipping download" )
173173 return
174174
@@ -184,7 +184,7 @@ def _stage_libcxx(target_dir: pathlib.Path):
184184 tar .extractall (temp_extract .parent )
185185
186186 lib_src = temp_extract / "lib"
187- for fname in REQUIRED_LIBS :
187+ for fname in REQUIRED_LIBC_LIBS :
188188 src_path = lib_src / fname
189189 if not src_path .exists ():
190190 print (f"[libcxx] Warning: { fname } not found in extracted LLVM" )
@@ -203,6 +203,37 @@ def _stage_libcxx(target_dir: pathlib.Path):
203203 print (f"[libcxx] Staged libc++ to { target_dir } " )
204204
205205
206+ REQUIRED_LIBS : List [str ] = [
207+ "libQnnHtp.so" ,
208+ ] + REQUIRED_LIBC_LIBS
209+
210+
211+ def _ld_library_paths () -> List [pathlib .Path ]:
212+ raw = os .environ .get ("LD_LIBRARY_PATH" , "" )
213+ return [pathlib .Path (p ) for p in raw .split (":" ) if p .strip ()]
214+
215+
216+ def _find_lib_in_ld_paths (
217+ libname : str , ld_dirs : Optional [List [pathlib .Path ]] = None
218+ ) -> Optional [pathlib .Path ]:
219+ if ld_dirs is None :
220+ ld_dirs = _ld_library_paths ()
221+ for d in ld_dirs :
222+ candidate = d / libname
223+ if candidate .exists ():
224+ return candidate .resolve ()
225+ return None
226+
227+
228+ def _check_required_libs_in_ld () -> Tuple [bool , Dict [str , Optional [pathlib .Path ]]]:
229+ ld_dirs = _ld_library_paths ()
230+ locations : Dict [str , Optional [pathlib .Path ]] = {}
231+ for lib in REQUIRED_LIBS :
232+ locations [lib ] = _find_lib_in_ld_paths (lib , ld_dirs )
233+ all_present = all (locations [lib ] is not None for lib in REQUIRED_LIBS )
234+ return all_present , locations
235+
236+
206237def _load_libcxx_libs (lib_path ):
207238 candidates = list (lib_path .glob ("*.so*" ))
208239 priority = ["libc++abi" , "libc++" ]
@@ -220,6 +251,13 @@ def _load_libcxx_libs(lib_path):
220251
221252
222253def install_qnn_sdk (force_download : bool = True ) -> bool :
254+ all_present , locations = _check_required_libs_in_ld ()
255+ if all_present and not force_download :
256+ print ("[INIT] All required libraries already present in LD_LIBRARY_PATH:" )
257+ for lib , path in locations .items ():
258+ print (f" - { lib } : { path } " )
259+ return True
260+
223261 print (f"[INIT] SDK_DIR: { SDK_DIR } " )
224262 if not SDK_DIR .exists ():
225263 print ("[INIT] Qualcomm SDK not found. Downloading..." )
0 commit comments