pcc created this revision. pcc added reviewers: bkramer, aaron.ballman. Herald added subscribers: mikhail.ramalho, arphaman. Herald added a project: All. pcc requested review of this revision. Herald added a project: clang.
Various driver features, such as the sysroot path detection for Android targets, rely on being able to find the Clang install directory (look for callers of `getDriver().getInstalledDir()`). However, the install directory isn't currently being plumbed through to the driver, which is conventionally done via the argv[0] passed to the Driver constructor. It looks like D14695 <https://reviews.llvm.org/D14695> attempted to fix this by adding another API that allows specifying the argv[0]. However, rather than requiring every user of libclang to switch to this API for correct behavior, let's have the other existing APIs work by default, by using the existing logic in libclang for finding the install directory. Repository: rG LLVM Github Monorepo https://reviews.llvm.org/D146497 Files: clang/include/clang-c/Index.h clang/test/Index/record-completion-invocation.c clang/test/Index/record-parsing-invocation.c clang/tools/libclang/CIndex.cpp Index: clang/tools/libclang/CIndex.cpp =================================================================== --- clang/tools/libclang/CIndex.cpp +++ clang/tools/libclang/CIndex.cpp @@ -4013,8 +4013,16 @@ struct CXUnsavedFile *unsaved_files, unsigned num_unsaved_files, unsigned options, CXTranslationUnit *out_TU) { noteBottomOfStack(); + + if (!CIdx) + return CXError_InvalidArguments; + SmallString<64> ClangPath( + static_cast<CIndexer *>(CIdx)->getClangToolchainPath()); + llvm::sys::path::append(ClangPath, "bin"); + llvm::sys::path::append(ClangPath, "clang"); + SmallVector<const char *, 4> Args; - Args.push_back("clang"); + Args.push_back(ClangPath.c_str()); Args.append(command_line_args, command_line_args + num_command_line_args); return clang_parseTranslationUnit2FullArgv( CIdx, source_filename, Args.data(), Args.size(), unsaved_files, Index: clang/test/Index/record-parsing-invocation.c =================================================================== --- clang/test/Index/record-parsing-invocation.c +++ clang/test/Index/record-parsing-invocation.c @@ -25,5 +25,5 @@ # pragma clang __debug parser_crash #endif -// CHECK: {"toolchain":"{{.*}}","libclang.operation":"parse","libclang.opts":1,"args":["clang","-fno-spell-checking","{{.*}}record-parsing-invocation.c","-Xclang","-detailed-preprocessing-record","-fallow-editor-placeholders"]} -// CHECK-UNSAVED: {"toolchain":"{{.*}}","libclang.operation":"parse","libclang.opts":1,"args":["clang","-fno-spell-checking","{{.*}}record-parsing-invocation.c","-Xclang","-detailed-preprocessing-record","-fallow-editor-placeholders"],"unsaved_file_hashes":[{"name":"{{.*}}record-parsing-invocation.c","md5":"aee23773de90e665992b48209351d70e"}]} +// CHECK: {"toolchain":"{{.*}}","libclang.operation":"parse","libclang.opts":1,"args":["{{.*}}bin{{.*}}clang","-fno-spell-checking","{{.*}}record-parsing-invocation.c","-Xclang","-detailed-preprocessing-record","-fallow-editor-placeholders"]} +// CHECK-UNSAVED: {"toolchain":"{{.*}}","libclang.operation":"parse","libclang.opts":1,"args":["{{.*}}bin{{.*}}clang","-fno-spell-checking","{{.*}}record-parsing-invocation.c","-Xclang","-detailed-preprocessing-record","-fallow-editor-placeholders"],"unsaved_file_hashes":[{"name":"{{.*}}record-parsing-invocation.c","md5":"aee23773de90e665992b48209351d70e"}]} Index: clang/test/Index/record-completion-invocation.c =================================================================== --- clang/test/Index/record-completion-invocation.c +++ clang/test/Index/record-completion-invocation.c @@ -9,4 +9,4 @@ // RUN: env LIBCLANG_DISABLE_CRASH_RECOVERY=1 CINDEXTEST_INVOCATION_EMISSION_PATH=%t not --crash c-index-test -code-completion-at=%s:10:1 "-remap-file=%s,%S/Inputs/record-parsing-invocation-remap.c" %s // RUN: cat %t/libclang-* | FileCheck %s -// CHECK: {"toolchain":"{{.*}}","libclang.operation":"complete","libclang.opts":1,"args":["clang","-fno-spell-checking","{{.*}}record-completion-invocation.c","-Xclang","-detailed-preprocessing-record","-fallow-editor-placeholders"],"invocation-args":["-code-completion-at={{.*}}record-completion-invocation.c:10:1"],"unsaved_file_hashes":[{"name":"{{.*}}record-completion-invocation.c","md5":"aee23773de90e665992b48209351d70e"}]} +// CHECK: {"toolchain":"{{.*}}","libclang.operation":"complete","libclang.opts":1,"args":["{{.*}}bin{{.*}}clang","-fno-spell-checking","{{.*}}record-completion-invocation.c","-Xclang","-detailed-preprocessing-record","-fallow-editor-placeholders"],"invocation-args":["-code-completion-at={{.*}}record-completion-invocation.c:10:1"],"unsaved_file_hashes":[{"name":"{{.*}}record-completion-invocation.c","md5":"aee23773de90e665992b48209351d70e"}]} Index: clang/include/clang-c/Index.h =================================================================== --- clang/include/clang-c/Index.h +++ clang/include/clang-c/Index.h @@ -899,8 +899,13 @@ /** * Same as clang_parseTranslationUnit2 but requires a full command line - * for \c command_line_args including argv[0]. This is useful if the standard - * library paths are relative to the binary. + * for \c command_line_args including argv[0]. + * + * This is useful if the driver uses paths relative to the binary and either + * you are targeting libclang versions older than Clang 17, or libclang is + * installed to a non-standard location. Clang 17 and newer will automatically + * use the correct argv[0] if libclang is installed in the lib directory + * parallel to the bin directory where the clang binary is installed. */ CINDEX_LINKAGE enum CXErrorCode clang_parseTranslationUnit2FullArgv( CXIndex CIdx, const char *source_filename,
Index: clang/tools/libclang/CIndex.cpp =================================================================== --- clang/tools/libclang/CIndex.cpp +++ clang/tools/libclang/CIndex.cpp @@ -4013,8 +4013,16 @@ struct CXUnsavedFile *unsaved_files, unsigned num_unsaved_files, unsigned options, CXTranslationUnit *out_TU) { noteBottomOfStack(); + + if (!CIdx) + return CXError_InvalidArguments; + SmallString<64> ClangPath( + static_cast<CIndexer *>(CIdx)->getClangToolchainPath()); + llvm::sys::path::append(ClangPath, "bin"); + llvm::sys::path::append(ClangPath, "clang"); + SmallVector<const char *, 4> Args; - Args.push_back("clang"); + Args.push_back(ClangPath.c_str()); Args.append(command_line_args, command_line_args + num_command_line_args); return clang_parseTranslationUnit2FullArgv( CIdx, source_filename, Args.data(), Args.size(), unsaved_files, Index: clang/test/Index/record-parsing-invocation.c =================================================================== --- clang/test/Index/record-parsing-invocation.c +++ clang/test/Index/record-parsing-invocation.c @@ -25,5 +25,5 @@ # pragma clang __debug parser_crash #endif -// CHECK: {"toolchain":"{{.*}}","libclang.operation":"parse","libclang.opts":1,"args":["clang","-fno-spell-checking","{{.*}}record-parsing-invocation.c","-Xclang","-detailed-preprocessing-record","-fallow-editor-placeholders"]} -// CHECK-UNSAVED: {"toolchain":"{{.*}}","libclang.operation":"parse","libclang.opts":1,"args":["clang","-fno-spell-checking","{{.*}}record-parsing-invocation.c","-Xclang","-detailed-preprocessing-record","-fallow-editor-placeholders"],"unsaved_file_hashes":[{"name":"{{.*}}record-parsing-invocation.c","md5":"aee23773de90e665992b48209351d70e"}]} +// CHECK: {"toolchain":"{{.*}}","libclang.operation":"parse","libclang.opts":1,"args":["{{.*}}bin{{.*}}clang","-fno-spell-checking","{{.*}}record-parsing-invocation.c","-Xclang","-detailed-preprocessing-record","-fallow-editor-placeholders"]} +// CHECK-UNSAVED: {"toolchain":"{{.*}}","libclang.operation":"parse","libclang.opts":1,"args":["{{.*}}bin{{.*}}clang","-fno-spell-checking","{{.*}}record-parsing-invocation.c","-Xclang","-detailed-preprocessing-record","-fallow-editor-placeholders"],"unsaved_file_hashes":[{"name":"{{.*}}record-parsing-invocation.c","md5":"aee23773de90e665992b48209351d70e"}]} Index: clang/test/Index/record-completion-invocation.c =================================================================== --- clang/test/Index/record-completion-invocation.c +++ clang/test/Index/record-completion-invocation.c @@ -9,4 +9,4 @@ // RUN: env LIBCLANG_DISABLE_CRASH_RECOVERY=1 CINDEXTEST_INVOCATION_EMISSION_PATH=%t not --crash c-index-test -code-completion-at=%s:10:1 "-remap-file=%s,%S/Inputs/record-parsing-invocation-remap.c" %s // RUN: cat %t/libclang-* | FileCheck %s -// CHECK: {"toolchain":"{{.*}}","libclang.operation":"complete","libclang.opts":1,"args":["clang","-fno-spell-checking","{{.*}}record-completion-invocation.c","-Xclang","-detailed-preprocessing-record","-fallow-editor-placeholders"],"invocation-args":["-code-completion-at={{.*}}record-completion-invocation.c:10:1"],"unsaved_file_hashes":[{"name":"{{.*}}record-completion-invocation.c","md5":"aee23773de90e665992b48209351d70e"}]} +// CHECK: {"toolchain":"{{.*}}","libclang.operation":"complete","libclang.opts":1,"args":["{{.*}}bin{{.*}}clang","-fno-spell-checking","{{.*}}record-completion-invocation.c","-Xclang","-detailed-preprocessing-record","-fallow-editor-placeholders"],"invocation-args":["-code-completion-at={{.*}}record-completion-invocation.c:10:1"],"unsaved_file_hashes":[{"name":"{{.*}}record-completion-invocation.c","md5":"aee23773de90e665992b48209351d70e"}]} Index: clang/include/clang-c/Index.h =================================================================== --- clang/include/clang-c/Index.h +++ clang/include/clang-c/Index.h @@ -899,8 +899,13 @@ /** * Same as clang_parseTranslationUnit2 but requires a full command line - * for \c command_line_args including argv[0]. This is useful if the standard - * library paths are relative to the binary. + * for \c command_line_args including argv[0]. + * + * This is useful if the driver uses paths relative to the binary and either + * you are targeting libclang versions older than Clang 17, or libclang is + * installed to a non-standard location. Clang 17 and newer will automatically + * use the correct argv[0] if libclang is installed in the lib directory + * parallel to the bin directory where the clang binary is installed. */ CINDEX_LINKAGE enum CXErrorCode clang_parseTranslationUnit2FullArgv( CXIndex CIdx, const char *source_filename,
_______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits