[PATCH] D130303: Handle template parameter-dependent bit field widths in libclang
collinbaker added a comment. Pinging this Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D130303/new/ https://reviews.llvm.org/D130303 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[PATCH] D130303: Handle template parameter-dependent bit field widths in libclang
collinbaker created this revision. collinbaker added a reviewer: rnk. Herald added a subscriber: arphaman. Herald added a project: All. collinbaker requested review of this revision. Herald added a project: clang. Herald added a subscriber: cfe-commits. In a class template, a bit field's width may depend on a template parameter. In this case the width expression cannot be evaluated. Previously clang_getFieldDeclBitWidth() would assert, or cause memory unsafety and return an invalid result if assertions are disabled. This adds a check for this case which returns an error code. An additional function clang_isFieldDeclBitWidthDependent() as added for users to check for this case. Repository: rG LLVM Github Monorepo https://reviews.llvm.org/D130303 Files: clang/include/clang-c/Index.h clang/tools/libclang/CXType.cpp Index: clang/tools/libclang/CXType.cpp === --- clang/tools/libclang/CXType.cpp +++ clang/tools/libclang/CXType.cpp @@ -15,6 +15,7 @@ #include "CXString.h" #include "CXTranslationUnit.h" #include "CXType.h" +#include "clang-c/Index.h" #include "clang/AST/Decl.h" #include "clang/AST/DeclObjC.h" #include "clang/AST/DeclTemplate.h" @@ -377,6 +378,21 @@ return ULLONG_MAX; } +unsigned clang_isFieldDeclBitWidthDependent(CXCursor C) { + using namespace cxcursor; + + if (clang_isDeclaration(C.kind)) { +const Decl *D = getCursorDecl(C); + +if (const FieldDecl *FD = dyn_cast_or_null(D)) { + if (FD->isBitField() && FD->getBitWidth()->isValueDependent()) +return 1; +} + } + + return 0; +} + int clang_getFieldDeclBitWidth(CXCursor C) { using namespace cxcursor; @@ -384,7 +400,7 @@ const Decl *D = getCursorDecl(C); if (const FieldDecl *FD = dyn_cast_or_null(D)) { - if (FD->isBitField()) + if (FD->isBitField() && !FD->getBitWidth()->isValueDependent()) return FD->getBitWidthValue(getCursorContext(C)); } } Index: clang/include/clang-c/Index.h === --- clang/include/clang-c/Index.h +++ clang/include/clang-c/Index.h @@ -3545,10 +3545,19 @@ CINDEX_LINKAGE unsigned long long clang_getEnumConstantDeclUnsignedValue(CXCursor C); +/** + * Returns non-zero if a bit field's width depends on template parameters. + * + * If the cursor does not reference a bit field declaration or if the bit + * field's width does not depend on template parameters, 0 is returned. + */ +CINDEX_LINKAGE unsigned clang_isFieldDeclBitWidthDependent(CXCursor C); + /** * Retrieve the bit width of a bit field declaration as an integer. * - * If a cursor that is not a bit field declaration is passed in, -1 is returned. + * If a cursor that is not a bit field declaration is passed in, or if the bit + * field's width expression cannot be evaluated, -1 is returned. */ CINDEX_LINKAGE int clang_getFieldDeclBitWidth(CXCursor C); Index: clang/tools/libclang/CXType.cpp === --- clang/tools/libclang/CXType.cpp +++ clang/tools/libclang/CXType.cpp @@ -15,6 +15,7 @@ #include "CXString.h" #include "CXTranslationUnit.h" #include "CXType.h" +#include "clang-c/Index.h" #include "clang/AST/Decl.h" #include "clang/AST/DeclObjC.h" #include "clang/AST/DeclTemplate.h" @@ -377,6 +378,21 @@ return ULLONG_MAX; } +unsigned clang_isFieldDeclBitWidthDependent(CXCursor C) { + using namespace cxcursor; + + if (clang_isDeclaration(C.kind)) { +const Decl *D = getCursorDecl(C); + +if (const FieldDecl *FD = dyn_cast_or_null(D)) { + if (FD->isBitField() && FD->getBitWidth()->isValueDependent()) +return 1; +} + } + + return 0; +} + int clang_getFieldDeclBitWidth(CXCursor C) { using namespace cxcursor; @@ -384,7 +400,7 @@ const Decl *D = getCursorDecl(C); if (const FieldDecl *FD = dyn_cast_or_null(D)) { - if (FD->isBitField()) + if (FD->isBitField() && !FD->getBitWidth()->isValueDependent()) return FD->getBitWidthValue(getCursorContext(C)); } } Index: clang/include/clang-c/Index.h === --- clang/include/clang-c/Index.h +++ clang/include/clang-c/Index.h @@ -3545,10 +3545,19 @@ CINDEX_LINKAGE unsigned long long clang_getEnumConstantDeclUnsignedValue(CXCursor C); +/** + * Returns non-zero if a bit field's width depends on template parameters. + * + * If the cursor does not reference a bit field declaration or if the bit + * field's width does not depend on template parameters, 0 is returned. + */ +CINDEX_LINKAGE unsigned clang_isFieldDeclBitWidthDependent(CXCursor C); + /** * Retrieve the bit width of a bit field declaration as an integer. * - * If a cursor that is not a bit field declaration is passed in, -1 is returned. + * If a cursor that is not a bit field declaration is passed in, or if the bit + * field's width expression canno
[PATCH] D115049: Fall back on Android triple w/o API level for runtimes search
collinbaker created this revision. Herald added subscribers: abrachet, danielkiss, kristof.beyls. collinbaker requested review of this revision. Herald added a project: clang. Herald added a subscriber: cfe-commits. Clang searches for runtimes (e.g. libclang_rt*) first in a subdirectory named for the target triple (corresponding to LLVM_ENABLE_PER_TARGET_RUNTIME_DIR=ON), then if it's not found uses .../lib//libclang_rt* with a suffix corresponding to the arch and environment name. Android triples optionally include an API level indicating the minimum Android version to be run on (e.g. aarch64-unknown-linux-android21). When compiler-rt is built with LLVM_ENABLE_PER_TARGET_RUNTIME_DIR=ON this API level is part of the output path. Linking code built for a later API level against a runtime built for an earlier one is safe. In projects with several API level targets this is desireable to avoid re-building the same runtimes many times. This is difficult with the current runtime search method: if the API levels don't exactly match Clang gives up on the per-target runtime directory path. To enable this more simply, this change tries target triple without the API level before falling back on the old layout. Another option would be to try every API level in the triple, e.g. check aarch-64-unknown-linux-android21, then ...20, then ...19, etc. Repository: rG LLVM Github Monorepo https://reviews.llvm.org/D115049 Files: clang/include/clang/Driver/ToolChain.h clang/lib/Driver/Driver.cpp clang/lib/Driver/ToolChain.cpp clang/lib/Driver/ToolChains/Fuchsia.cpp clang/test/Driver/Inputs/resource_dir_with_per_target_subdir/lib/aarch64-unknown-linux-android/.keep clang/test/Driver/Inputs/resource_dir_with_per_target_subdir/lib/aarch64-unknown-linux-android/libclang_rt.builtins.a clang/test/Driver/Inputs/resource_dir_with_per_target_subdir/lib/aarch64-unknown-linux-android21/.keep clang/test/Driver/Inputs/resource_dir_with_per_target_subdir/lib/aarch64-unknown-linux-android21/libclang_rt.builtins.a clang/test/Driver/linux-per-target-runtime-dir.c Index: clang/test/Driver/linux-per-target-runtime-dir.c === --- clang/test/Driver/linux-per-target-runtime-dir.c +++ clang/test/Driver/linux-per-target-runtime-dir.c @@ -25,3 +25,21 @@ // RUN: -resource-dir=%S/Inputs/resource_dir_with_per_target_subdir \ // RUN: | FileCheck --check-prefix=CHECK-FILE-NAME-X8664 %s // CHECK-FILE-NAME-X8664: lib{{/|\\}}x86_64-unknown-linux-gnu{{/|\\}}libclang_rt.builtins.a + +// RUN: %clang -rtlib=compiler-rt -print-file-name=libclang_rt.builtins.a 2>&1 \ +// RUN: --target=aarch64-unknown-linux-android21 \ +// RUN: -resource-dir=%S/Inputs/resource_dir_with_per_target_subdir \ +// RUN: | FileCheck --check-prefix=CHECK-FILE-NAME-ANDROID21 %s +// CHECK-FILE-NAME-ANDROID21: lib{{/|\\}}aarch64-unknown-linux-android21{{/|\\}}libclang_rt.builtins.a + +// RUN: %clang -rtlib=compiler-rt -print-file-name=libclang_rt.builtins.a 2>&1 \ +// RUN: --target=aarch64-unknown-linux-android23 \ +// RUN: -resource-dir=%S/Inputs/resource_dir_with_per_target_subdir \ +// RUN: | FileCheck --check-prefix=CHECK-FILE-NAME-ANDROID23 %s +// CHECK-FILE-NAME-ANDROID23: lib{{/|\\}}aarch64-unknown-linux-android{{/|\\}}libclang_rt.builtins.a + +// RUN: %clang -rtlib=compiler-rt -print-file-name=libclang_rt.builtins.a 2>&1 \ +// RUN: --target=aarch64-unknown-linux-android \ +// RUN: -resource-dir=%S/Inputs/resource_dir_with_per_target_subdir \ +// RUN: | FileCheck --check-prefix=CHECK-FILE-NAME-ANDROID %s +// CHECK-FILE-NAME-ANDROID: lib{{/|\\}}aarch64-unknown-linux-android{{/|\\}}libclang_rt.builtins.a Index: clang/lib/Driver/ToolChains/Fuchsia.cpp === --- clang/lib/Driver/ToolChains/Fuchsia.cpp +++ clang/lib/Driver/ToolChains/Fuchsia.cpp @@ -191,9 +191,11 @@ auto FilePaths = [&](const Multilib &M) -> std::vector { std::vector FP; -SmallString<128> P(getStdlibPath()); -llvm::sys::path::append(P, M.gccSuffix()); -FP.push_back(std::string(P.str())); +for (const std::string &Path : getStdlibPaths()) { + SmallString<128> P(Path); + llvm::sys::path::append(P, M.gccSuffix()); + FP.push_back(std::string(P.str())); +} return FP; }; Index: clang/lib/Driver/ToolChain.cpp === --- clang/lib/Driver/ToolChain.cpp +++ clang/lib/Driver/ToolChain.cpp @@ -75,17 +75,16 @@ const ArgList &Args) : D(D), Triple(T), Args(Args), CachedRTTIArg(GetRTTIArgument(Args)), CachedRTTIMode(CalculateRTTIMode(Args, Triple, CachedRTTIArg)) { - std::string RuntimePath = getRuntimePath(); - if (getVFS().exists(RuntimePath)) -getLibraryPaths().push_back(RuntimePath); - - std::string StdlibPath = getStdlibPath(); - if (getVFS().exists(StdlibPath)) -getFilePaths().push_bac
[PATCH] D115049: Fall back on Android triple w/o API level for runtimes search
collinbaker updated this revision to Diff 391661. collinbaker added a comment. Fix variable name style Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D115049/new/ https://reviews.llvm.org/D115049 Files: clang/include/clang/Driver/ToolChain.h clang/lib/Driver/Driver.cpp clang/lib/Driver/ToolChain.cpp clang/lib/Driver/ToolChains/Fuchsia.cpp clang/test/Driver/Inputs/resource_dir_with_per_target_subdir/lib/aarch64-unknown-linux-android/.keep clang/test/Driver/Inputs/resource_dir_with_per_target_subdir/lib/aarch64-unknown-linux-android/libclang_rt.builtins.a clang/test/Driver/Inputs/resource_dir_with_per_target_subdir/lib/aarch64-unknown-linux-android21/.keep clang/test/Driver/Inputs/resource_dir_with_per_target_subdir/lib/aarch64-unknown-linux-android21/libclang_rt.builtins.a clang/test/Driver/linux-per-target-runtime-dir.c Index: clang/test/Driver/linux-per-target-runtime-dir.c === --- clang/test/Driver/linux-per-target-runtime-dir.c +++ clang/test/Driver/linux-per-target-runtime-dir.c @@ -25,3 +25,21 @@ // RUN: -resource-dir=%S/Inputs/resource_dir_with_per_target_subdir \ // RUN: | FileCheck --check-prefix=CHECK-FILE-NAME-X8664 %s // CHECK-FILE-NAME-X8664: lib{{/|\\}}x86_64-unknown-linux-gnu{{/|\\}}libclang_rt.builtins.a + +// RUN: %clang -rtlib=compiler-rt -print-file-name=libclang_rt.builtins.a 2>&1 \ +// RUN: --target=aarch64-unknown-linux-android21 \ +// RUN: -resource-dir=%S/Inputs/resource_dir_with_per_target_subdir \ +// RUN: | FileCheck --check-prefix=CHECK-FILE-NAME-ANDROID21 %s +// CHECK-FILE-NAME-ANDROID21: lib{{/|\\}}aarch64-unknown-linux-android21{{/|\\}}libclang_rt.builtins.a + +// RUN: %clang -rtlib=compiler-rt -print-file-name=libclang_rt.builtins.a 2>&1 \ +// RUN: --target=aarch64-unknown-linux-android23 \ +// RUN: -resource-dir=%S/Inputs/resource_dir_with_per_target_subdir \ +// RUN: | FileCheck --check-prefix=CHECK-FILE-NAME-ANDROID23 %s +// CHECK-FILE-NAME-ANDROID23: lib{{/|\\}}aarch64-unknown-linux-android{{/|\\}}libclang_rt.builtins.a + +// RUN: %clang -rtlib=compiler-rt -print-file-name=libclang_rt.builtins.a 2>&1 \ +// RUN: --target=aarch64-unknown-linux-android \ +// RUN: -resource-dir=%S/Inputs/resource_dir_with_per_target_subdir \ +// RUN: | FileCheck --check-prefix=CHECK-FILE-NAME-ANDROID %s +// CHECK-FILE-NAME-ANDROID: lib{{/|\\}}aarch64-unknown-linux-android{{/|\\}}libclang_rt.builtins.a Index: clang/lib/Driver/ToolChains/Fuchsia.cpp === --- clang/lib/Driver/ToolChains/Fuchsia.cpp +++ clang/lib/Driver/ToolChains/Fuchsia.cpp @@ -191,9 +191,11 @@ auto FilePaths = [&](const Multilib &M) -> std::vector { std::vector FP; -SmallString<128> P(getStdlibPath()); -llvm::sys::path::append(P, M.gccSuffix()); -FP.push_back(std::string(P.str())); +for (const std::string &Path : getStdlibPaths()) { + SmallString<128> P(Path); + llvm::sys::path::append(P, M.gccSuffix()); + FP.push_back(std::string(P.str())); +} return FP; }; Index: clang/lib/Driver/ToolChain.cpp === --- clang/lib/Driver/ToolChain.cpp +++ clang/lib/Driver/ToolChain.cpp @@ -75,17 +75,16 @@ const ArgList &Args) : D(D), Triple(T), Args(Args), CachedRTTIArg(GetRTTIArgument(Args)), CachedRTTIMode(CalculateRTTIMode(Args, Triple, CachedRTTIArg)) { - std::string RuntimePath = getRuntimePath(); - if (getVFS().exists(RuntimePath)) -getLibraryPaths().push_back(RuntimePath); - - std::string StdlibPath = getStdlibPath(); - if (getVFS().exists(StdlibPath)) -getFilePaths().push_back(StdlibPath); + auto addIfExists = [this](path_list &List, const std::string &Path) { +if (getVFS().exists(Path)) + List.push_back(Path); + }; - std::string CandidateLibPath = getArchSpecificLibPath(); - if (getVFS().exists(CandidateLibPath)) -getFilePaths().push_back(CandidateLibPath); + for (const auto &Path : getRuntimePaths()) +addIfExists(getLibraryPaths(), Path); + for (const auto &Path : getStdlibPaths()) +addIfExists(getFilePaths(), Path); + addIfExists(getFilePaths(), getArchSpecificLibPath()); } void ToolChain::setTripleEnvironment(llvm::Triple::EnvironmentType Env) { @@ -485,16 +484,36 @@ return Args.MakeArgString(getCompilerRT(Args, Component, Type)); } -std::string ToolChain::getRuntimePath() const { - SmallString<128> P(D.ResourceDir); - llvm::sys::path::append(P, "lib", getTripleString()); - return std::string(P.str()); +ToolChain::path_list ToolChain::getRuntimePaths() const { + path_list Paths; + auto addPathForTriple = [this, &Paths](const llvm::Triple &Triple) { +SmallString<128> P(D.ResourceDir); +llvm::sys::path::append(P, "lib", Triple.str()); +Paths.push_back(std::string(P.str())); + }; +
[PATCH] D130303: Handle template parameter-dependent bit field widths in libclang
collinbaker updated this revision to Diff 502758. collinbaker added a comment. Sync with upstream changes Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D130303/new/ https://reviews.llvm.org/D130303 Files: clang/include/clang-c/Index.h clang/tools/libclang/CXType.cpp Index: clang/tools/libclang/CXType.cpp === --- clang/tools/libclang/CXType.cpp +++ clang/tools/libclang/CXType.cpp @@ -10,11 +10,12 @@ // //======// +#include "CXType.h" #include "CIndexer.h" #include "CXCursor.h" #include "CXString.h" #include "CXTranslationUnit.h" -#include "CXType.h" +#include "clang-c/Index.h" #include "clang/AST/Decl.h" #include "clang/AST/DeclObjC.h" #include "clang/AST/DeclTemplate.h" @@ -371,6 +372,21 @@ return ULLONG_MAX; } +unsigned clang_isFieldDeclBitWidthDependent(CXCursor C) { + using namespace cxcursor; + + if (clang_isDeclaration(C.kind)) { +const Decl *D = getCursorDecl(C); + +if (const FieldDecl *FD = dyn_cast_or_null(D)) { + if (FD->isBitField() && FD->getBitWidth()->isValueDependent()) +return 1; +} + } + + return 0; +} + int clang_getFieldDeclBitWidth(CXCursor C) { using namespace cxcursor; @@ -378,7 +394,7 @@ const Decl *D = getCursorDecl(C); if (const FieldDecl *FD = dyn_cast_or_null(D)) { - if (FD->isBitField()) + if (FD->isBitField() && !FD->getBitWidth()->isValueDependent()) return FD->getBitWidthValue(getCursorContext(C)); } } Index: clang/include/clang-c/Index.h === --- clang/include/clang-c/Index.h +++ clang/include/clang-c/Index.h @@ -2887,10 +2887,19 @@ CINDEX_LINKAGE unsigned long long clang_getEnumConstantDeclUnsignedValue(CXCursor C); +/** + * Returns non-zero if a bit field's width depends on template parameters. + * + * If the cursor does not reference a bit field declaration or if the bit + * field's width does not depend on template parameters, 0 is returned. + */ +CINDEX_LINKAGE unsigned clang_isFieldDeclBitWidthDependent(CXCursor C); + /** * Retrieve the bit width of a bit field declaration as an integer. * - * If a cursor that is not a bit field declaration is passed in, -1 is returned. + * If a cursor that is not a bit field declaration is passed in, or if the bit + * field's width expression cannot be evaluated, -1 is returned. */ CINDEX_LINKAGE int clang_getFieldDeclBitWidth(CXCursor C); Index: clang/tools/libclang/CXType.cpp === --- clang/tools/libclang/CXType.cpp +++ clang/tools/libclang/CXType.cpp @@ -10,11 +10,12 @@ // //======// +#include "CXType.h" #include "CIndexer.h" #include "CXCursor.h" #include "CXString.h" #include "CXTranslationUnit.h" -#include "CXType.h" +#include "clang-c/Index.h" #include "clang/AST/Decl.h" #include "clang/AST/DeclObjC.h" #include "clang/AST/DeclTemplate.h" @@ -371,6 +372,21 @@ return ULLONG_MAX; } +unsigned clang_isFieldDeclBitWidthDependent(CXCursor C) { + using namespace cxcursor; + + if (clang_isDeclaration(C.kind)) { +const Decl *D = getCursorDecl(C); + +if (const FieldDecl *FD = dyn_cast_or_null(D)) { + if (FD->isBitField() && FD->getBitWidth()->isValueDependent()) +return 1; +} + } + + return 0; +} + int clang_getFieldDeclBitWidth(CXCursor C) { using namespace cxcursor; @@ -378,7 +394,7 @@ const Decl *D = getCursorDecl(C); if (const FieldDecl *FD = dyn_cast_or_null(D)) { - if (FD->isBitField()) + if (FD->isBitField() && !FD->getBitWidth()->isValueDependent()) return FD->getBitWidthValue(getCursorContext(C)); } } Index: clang/include/clang-c/Index.h === --- clang/include/clang-c/Index.h +++ clang/include/clang-c/Index.h @@ -2887,10 +2887,19 @@ CINDEX_LINKAGE unsigned long long clang_getEnumConstantDeclUnsignedValue(CXCursor C); +/** + * Returns non-zero if a bit field's width depends on template parameters. + * + * If the cursor does not reference a bit field declaration or if the bit + * field's width does not depend on template parameters, 0 is returned. + */ +CINDEX_LINKAGE unsigned clang_isFieldDeclBitWidthDependent(CXCursor C); + /** * Retrieve the bit width of a bit field declaration as an integer. * - * If a cursor that is not a bit field declaration is passed in, -1 is returned. + * If a cursor that is not a bit field declaration is passed in, or if the bit + * field's width expression cannot be evaluated, -1 is returned. */ CINDEX_LINKAGE int clang_getFieldDeclBitWidth(CXCursor C); ___ cfe-commits mailing list cfe-commits@lists.llvm.org https:
[PATCH] D130303: Handle template parameter-dependent bit field widths in libclang
collinbaker updated this revision to Diff 502762. collinbaker added a comment. Add release notes and remove unneeded include Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D130303/new/ https://reviews.llvm.org/D130303 Files: clang/docs/ReleaseNotes.rst clang/include/clang-c/Index.h clang/tools/libclang/CXType.cpp Index: clang/tools/libclang/CXType.cpp === --- clang/tools/libclang/CXType.cpp +++ clang/tools/libclang/CXType.cpp @@ -10,11 +10,11 @@ // //======// +#include "CXType.h" #include "CIndexer.h" #include "CXCursor.h" #include "CXString.h" #include "CXTranslationUnit.h" -#include "CXType.h" #include "clang/AST/Decl.h" #include "clang/AST/DeclObjC.h" #include "clang/AST/DeclTemplate.h" @@ -371,6 +371,21 @@ return ULLONG_MAX; } +unsigned clang_isFieldDeclBitWidthDependent(CXCursor C) { + using namespace cxcursor; + + if (clang_isDeclaration(C.kind)) { +const Decl *D = getCursorDecl(C); + +if (const FieldDecl *FD = dyn_cast_or_null(D)) { + if (FD->isBitField() && FD->getBitWidth()->isValueDependent()) +return 1; +} + } + + return 0; +} + int clang_getFieldDeclBitWidth(CXCursor C) { using namespace cxcursor; @@ -378,7 +393,7 @@ const Decl *D = getCursorDecl(C); if (const FieldDecl *FD = dyn_cast_or_null(D)) { - if (FD->isBitField()) + if (FD->isBitField() && !FD->getBitWidth()->isValueDependent()) return FD->getBitWidthValue(getCursorContext(C)); } } Index: clang/include/clang-c/Index.h === --- clang/include/clang-c/Index.h +++ clang/include/clang-c/Index.h @@ -2887,10 +2887,19 @@ CINDEX_LINKAGE unsigned long long clang_getEnumConstantDeclUnsignedValue(CXCursor C); +/** + * Returns non-zero if a bit field's width depends on template parameters. + * + * If the cursor does not reference a bit field declaration or if the bit + * field's width does not depend on template parameters, 0 is returned. + */ +CINDEX_LINKAGE unsigned clang_isFieldDeclBitWidthDependent(CXCursor C); + /** * Retrieve the bit width of a bit field declaration as an integer. * - * If a cursor that is not a bit field declaration is passed in, -1 is returned. + * If a cursor that is not a bit field declaration is passed in, or if the bit + * field's width expression cannot be evaluated, -1 is returned. */ CINDEX_LINKAGE int clang_getFieldDeclBitWidth(CXCursor C); Index: clang/docs/ReleaseNotes.rst === --- clang/docs/ReleaseNotes.rst +++ clang/docs/ReleaseNotes.rst @@ -290,6 +290,11 @@ - Introduced the new function ``clang_CXXMethod_isExplicit``, which identifies whether a constructor or conversion function cursor was marked with the explicit identifier. +- Added check in ``clang_getFieldDeclBitWidth`` for whether a bit field + has an evaluable bit width. Fixes undefined behavior when called on a + bit field whose width depends on a template paramter. +- Added function ``clang_isFieldDeclBitWidthDependent`` to check if a + bit field's width depends on a template parameter. Static Analyzer --- Index: clang/tools/libclang/CXType.cpp === --- clang/tools/libclang/CXType.cpp +++ clang/tools/libclang/CXType.cpp @@ -10,11 +10,11 @@ // //======// +#include "CXType.h" #include "CIndexer.h" #include "CXCursor.h" #include "CXString.h" #include "CXTranslationUnit.h" -#include "CXType.h" #include "clang/AST/Decl.h" #include "clang/AST/DeclObjC.h" #include "clang/AST/DeclTemplate.h" @@ -371,6 +371,21 @@ return ULLONG_MAX; } +unsigned clang_isFieldDeclBitWidthDependent(CXCursor C) { + using namespace cxcursor; + + if (clang_isDeclaration(C.kind)) { +const Decl *D = getCursorDecl(C); + +if (const FieldDecl *FD = dyn_cast_or_null(D)) { + if (FD->isBitField() && FD->getBitWidth()->isValueDependent()) +return 1; +} + } + + return 0; +} + int clang_getFieldDeclBitWidth(CXCursor C) { using namespace cxcursor; @@ -378,7 +393,7 @@ const Decl *D = getCursorDecl(C); if (const FieldDecl *FD = dyn_cast_or_null(D)) { - if (FD->isBitField()) + if (FD->isBitField() && !FD->getBitWidth()->isValueDependent()) return FD->getBitWidthValue(getCursorContext(C)); } } Index: clang/include/clang-c/Index.h === --- clang/include/clang-c/Index.h +++ clang/include/clang-c/Index.h @@ -2887,10 +2887,19 @@ CINDEX_LINKAGE unsigned long long clang_getEnumConstantDeclUnsignedValue(CXCursor C); +/** + * Returns non-zero if a bit field's width depends on template
[PATCH] D130303: Handle template parameter-dependent bit field widths in libclang
collinbaker added inline comments. Comment at: clang/include/clang-c/Index.h:3552 + * If the cursor does not reference a bit field declaration or if the bit + * field's width does not depend on template parameters, 0 is returned. + */ vedgy wrote: > I just thought how the new API could be used in KDevelop. Currently when > `clang_getFieldDeclBitWidth()` is positive, e.g. 2, KDevelop shows ` : 2` > after the data member name in a tooltip. Ideally a template-param-dependent > expression (actual code) would be displayed after the colon. If that's > difficult to implement, `: [tparam-dependent]` or `: ?` could be displayed > instead. But it would be more convenient and efficient to get this > information by a single call to `clang_getFieldDeclBitWidth()` instead of > calling `clang_isFieldDeclBitWidthDependent()` each time > `clang_getFieldDeclBitWidth()` returns `-1`. So how about returning `-2` or > `0` from `clang_getFieldDeclBitWidth()` instead of adding this new API? I understand the motivation but I don't think requiring an extra call is asking too much of libclang clients, and it's one extra call that doesn't do much work and will be called rarely so I don't see efficiency concerns. Without strong reasons otherwise I think it's better to be explicit here. Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D130303/new/ https://reviews.llvm.org/D130303 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[PATCH] D130303: Handle template parameter-dependent bit field widths in libclang
collinbaker updated this revision to Diff 502763. collinbaker added a comment. Add symbol to version map Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D130303/new/ https://reviews.llvm.org/D130303 Files: clang/docs/ReleaseNotes.rst clang/include/clang-c/Index.h clang/tools/libclang/CXType.cpp clang/tools/libclang/libclang.map Index: clang/tools/libclang/libclang.map === --- clang/tools/libclang/libclang.map +++ clang/tools/libclang/libclang.map @@ -421,6 +421,7 @@ LLVM_17 { global: clang_CXXMethod_isExplicit; +clang_isFieldDeclBitWidthDependent; }; # Example of how to add a new symbol version entry. If you do add a new symbol Index: clang/tools/libclang/CXType.cpp === --- clang/tools/libclang/CXType.cpp +++ clang/tools/libclang/CXType.cpp @@ -10,11 +10,11 @@ // //======// +#include "CXType.h" #include "CIndexer.h" #include "CXCursor.h" #include "CXString.h" #include "CXTranslationUnit.h" -#include "CXType.h" #include "clang/AST/Decl.h" #include "clang/AST/DeclObjC.h" #include "clang/AST/DeclTemplate.h" @@ -371,6 +371,21 @@ return ULLONG_MAX; } +unsigned clang_isFieldDeclBitWidthDependent(CXCursor C) { + using namespace cxcursor; + + if (clang_isDeclaration(C.kind)) { +const Decl *D = getCursorDecl(C); + +if (const FieldDecl *FD = dyn_cast_or_null(D)) { + if (FD->isBitField() && FD->getBitWidth()->isValueDependent()) +return 1; +} + } + + return 0; +} + int clang_getFieldDeclBitWidth(CXCursor C) { using namespace cxcursor; @@ -378,7 +393,7 @@ const Decl *D = getCursorDecl(C); if (const FieldDecl *FD = dyn_cast_or_null(D)) { - if (FD->isBitField()) + if (FD->isBitField() && !FD->getBitWidth()->isValueDependent()) return FD->getBitWidthValue(getCursorContext(C)); } } Index: clang/include/clang-c/Index.h === --- clang/include/clang-c/Index.h +++ clang/include/clang-c/Index.h @@ -2887,10 +2887,19 @@ CINDEX_LINKAGE unsigned long long clang_getEnumConstantDeclUnsignedValue(CXCursor C); +/** + * Returns non-zero if a bit field's width depends on template parameters. + * + * If the cursor does not reference a bit field declaration or if the bit + * field's width does not depend on template parameters, 0 is returned. + */ +CINDEX_LINKAGE unsigned clang_isFieldDeclBitWidthDependent(CXCursor C); + /** * Retrieve the bit width of a bit field declaration as an integer. * - * If a cursor that is not a bit field declaration is passed in, -1 is returned. + * If a cursor that is not a bit field declaration is passed in, or if the bit + * field's width expression cannot be evaluated, -1 is returned. */ CINDEX_LINKAGE int clang_getFieldDeclBitWidth(CXCursor C); Index: clang/docs/ReleaseNotes.rst === --- clang/docs/ReleaseNotes.rst +++ clang/docs/ReleaseNotes.rst @@ -290,6 +290,11 @@ - Introduced the new function ``clang_CXXMethod_isExplicit``, which identifies whether a constructor or conversion function cursor was marked with the explicit identifier. +- Added check in ``clang_getFieldDeclBitWidth`` for whether a bit field + has an evaluable bit width. Fixes undefined behavior when called on a + bit field whose width depends on a template paramter. +- Added function ``clang_isFieldDeclBitWidthDependent`` to check if a + bit field's width depends on a template parameter. Static Analyzer --- ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[PATCH] D130303: Handle template parameter-dependent bit field widths in libclang
collinbaker marked 3 inline comments as done. collinbaker added a comment. Thanks for the review. Someone else will need to commit since I don't have permission. Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D130303/new/ https://reviews.llvm.org/D130303 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[PATCH] D130303: Handle template parameter-dependent bit field widths in libclang
collinbaker added a comment. @dexonsmith can you weigh in? Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D130303/new/ https://reviews.llvm.org/D130303 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[PATCH] D130303: Handle template parameter-dependent bit field widths in libclang
collinbaker updated this revision to Diff 503570. collinbaker edited the summary of this revision. collinbaker added a comment. Requested changes Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D130303/new/ https://reviews.llvm.org/D130303 Files: clang/docs/ReleaseNotes.rst clang/include/clang-c/Index.h clang/tools/libclang/CXType.cpp clang/tools/libclang/libclang.map Index: clang/tools/libclang/libclang.map === --- clang/tools/libclang/libclang.map +++ clang/tools/libclang/libclang.map @@ -421,6 +421,7 @@ LLVM_17 { global: clang_CXXMethod_isExplicit; +clang_isBitFieldDecl; }; # Example of how to add a new symbol version entry. If you do add a new symbol Index: clang/tools/libclang/CXType.cpp === --- clang/tools/libclang/CXType.cpp +++ clang/tools/libclang/CXType.cpp @@ -10,11 +10,11 @@ // //======// +#include "CXType.h" #include "CIndexer.h" #include "CXCursor.h" #include "CXString.h" #include "CXTranslationUnit.h" -#include "CXType.h" #include "clang/AST/Decl.h" #include "clang/AST/DeclObjC.h" #include "clang/AST/DeclTemplate.h" @@ -371,7 +371,7 @@ return ULLONG_MAX; } -int clang_getFieldDeclBitWidth(CXCursor C) { +unsigned clang_isBitFieldDecl(CXCursor C) { using namespace cxcursor; if (clang_isDeclaration(C.kind)) { @@ -379,6 +379,21 @@ if (const FieldDecl *FD = dyn_cast_or_null(D)) { if (FD->isBitField()) +return 1; +} + } + + return 0; +} + +int clang_getFieldDeclBitWidth(CXCursor C) { + using namespace cxcursor; + + if (clang_isDeclaration(C.kind)) { +const Decl *D = getCursorDecl(C); + +if (const FieldDecl *FD = dyn_cast_or_null(D)) { + if (FD->isBitField() && !FD->getBitWidth()->isValueDependent()) return FD->getBitWidthValue(getCursorContext(C)); } } Index: clang/include/clang-c/Index.h === --- clang/include/clang-c/Index.h +++ clang/include/clang-c/Index.h @@ -2887,10 +2887,18 @@ CINDEX_LINKAGE unsigned long long clang_getEnumConstantDeclUnsignedValue(CXCursor C); +/** + * Returns non-zero if a field declaration has a bit width expression. + * + * If the cursor does not reference a bit field declaration 0 is returned. + */ +CINDEX_LINKAGE unsigned clang_isBitFieldDecl(CXCursor C); + /** * Retrieve the bit width of a bit field declaration as an integer. * - * If a cursor that is not a bit field declaration is passed in, -1 is returned. + * If the cursor does not reference a bit field, or if the bit field's width + * expression cannot be evaluated, -1 is returned. */ CINDEX_LINKAGE int clang_getFieldDeclBitWidth(CXCursor C); Index: clang/docs/ReleaseNotes.rst === --- clang/docs/ReleaseNotes.rst +++ clang/docs/ReleaseNotes.rst @@ -290,6 +290,11 @@ - Introduced the new function ``clang_CXXMethod_isExplicit``, which identifies whether a constructor or conversion function cursor was marked with the explicit identifier. +- Added check in ``clang_getFieldDeclBitWidth`` for whether a bit field + has an evaluable bit width. Fixes undefined behavior when called on a + bit field whose width depends on a template paramter. +- Added function ``clang_isBitFieldDecl`` to check if a struct/class field is a + bit field. Static Analyzer --- Index: clang/tools/libclang/libclang.map === --- clang/tools/libclang/libclang.map +++ clang/tools/libclang/libclang.map @@ -421,6 +421,7 @@ LLVM_17 { global: clang_CXXMethod_isExplicit; +clang_isBitFieldDecl; }; # Example of how to add a new symbol version entry. If you do add a new symbol Index: clang/tools/libclang/CXType.cpp === --- clang/tools/libclang/CXType.cpp +++ clang/tools/libclang/CXType.cpp @@ -10,11 +10,11 @@ // //======// +#include "CXType.h" #include "CIndexer.h" #include "CXCursor.h" #include "CXString.h" #include "CXTranslationUnit.h" -#include "CXType.h" #include "clang/AST/Decl.h" #include "clang/AST/DeclObjC.h" #include "clang/AST/DeclTemplate.h" @@ -371,7 +371,7 @@ return ULLONG_MAX; } -int clang_getFieldDeclBitWidth(CXCursor C) { +unsigned clang_isBitFieldDecl(CXCursor C) { using namespace cxcursor; if (clang_isDeclaration(C.kind)) { @@ -379,6 +379,21 @@ if (const FieldDecl *FD = dyn_cast_or_null(D)) { if (FD->isBitField()) +return 1; +} + } + + return 0; +} + +int clang_getFieldDeclBitWidth(CXCursor C) { + using namespace cxcursor; + + if (clang_isDeclaration(C.kind)) { +
[PATCH] D130303: Handle template parameter-dependent bit field widths in libclang
collinbaker marked 5 inline comments as done. collinbaker added a comment. Changed as requested. Again leaving it up to a committer to commit this Comment at: clang/include/clang-c/Index.h:3552 + * If the cursor does not reference a bit field declaration or if the bit + * field's width does not depend on template parameters, 0 is returned. + */ vedgy wrote: > vedgy wrote: > > collinbaker wrote: > > > vedgy wrote: > > > > I just thought how the new API could be used in KDevelop. Currently > > > > when `clang_getFieldDeclBitWidth()` is positive, e.g. 2, KDevelop shows > > > > ` : 2` after the data member name in a tooltip. Ideally a > > > > template-param-dependent expression (actual code) would be displayed > > > > after the colon. If that's difficult to implement, `: > > > > [tparam-dependent]` or `: ?` could be displayed instead. But it would > > > > be more convenient and efficient to get this information by a single > > > > call to `clang_getFieldDeclBitWidth()` instead of calling > > > > `clang_isFieldDeclBitWidthDependent()` each time > > > > `clang_getFieldDeclBitWidth()` returns `-1`. So how about returning > > > > `-2` or `0` from `clang_getFieldDeclBitWidth()` instead of adding this > > > > new API? > > > I understand the motivation but I don't think requiring an extra call is > > > asking too much of libclang clients, and it's one extra call that doesn't > > > do much work and will be called rarely so I don't see efficiency > > > concerns. Without strong reasons otherwise I think it's better to be > > > explicit here. > > KDevelop calls `clang_getFieldDeclBitWidth()` for each encountered class > > member declaration. `clang_isFieldDeclBitWidthDependent()` would have to be > > called each time `clang_getFieldDeclBitWidth()` returns `-1`, which would > > be most of the time, because few class members are bit-fields. The work > > this new function does is the same as that of > > `clang_getFieldDeclBitWidth()` (repeated). > > > > If the concern about returning `-2` from `clang_getFieldDeclBitWidth()` is > > cryptic return codes, an `enum` with named constants can be introduced. > > > > If the concern is breaking backward compatibility for users that relied on > > the returned value being positive or `-1`, then a replacement for > > `clang_getFieldDeclBitWidth()` with the most convenient API should be > > introduced and `clang_getFieldDeclBitWidth()` itself - deprecated. > > > > KDevelop simply stores the value returned by `clang_getFieldDeclBitWidth()` > > in an `int16_t m_bitWidth` data member and uses it later. So if `-2` is > > returned, the only place in code to adjust would be the use of this data > > member. With the current `clang_isFieldDeclBitWidthDependent()` > > implementation, this function would have to be called, `-2` explicitly > > stored in `m_bitWidth` and the use of `m_bitWidth` would have to be > > adjusted just the same. > > > > Have you considered potential usage of the added API in your project? Which > > alternative would be more convenient to use? > One more API alternative is to replace `clang_isFieldDeclBitWidthDependent()` > with `clang_isBitFieldDecl()`. The usage would be more straightforward and > efficient: first call `clang_isBitFieldDecl()`; if it returns true (should be > rare enough), call `clang_getFieldDeclBitWidth()`; if that returns `-1`, then > the bit-field width must be unknown (dependent on template parameters). Such > usage would still be less convenient and efficient compared to > `clang_getFieldDeclBitWidth()` returning `-2` though. Implemented as `clang_isBitFieldDecl` rather than magic return value Comment at: clang/tools/libclang/CXType.cpp:13 +#include "CXType.h" #include "CIndexer.h" vedgy wrote: > I guess //clang-format// did this include reordering. But it certainly looks > out of place and the include order becomes wrong. So I think it should be > reverted. I don't agree, it's pretty standard for a source file to have its associated header include at the top. Comment at: clang/tools/libclang/CXType.cpp:404 + if (FD->isBitField() && !FD->getBitWidth()->isValueDependent()) return FD->getBitWidthValue(getCursorContext(C)); } vedgy wrote: > I thought of the same fix while analyzing the assertion failure here: > https://bugs.kde.org/show_bug.cgi?id=438249#c19 > > An alternative implementation is to place this same check in > `clang::FieldDecl::getBitWidthValue()`. This looks like a general issue that > could affect non-libclang users of `clang::FieldDecl::getBitWidthValue()`. > But apparently no one else has stumbled upon it. > > `clang::FieldDecl::getBitWidthValue()` returns `unsigned` and has no > error-reporting mechanism yet. It could return > `std::numeric_limits::max()` (or `0` if that's an invalid bit width > value) in case of the value dependence. This would be
[PATCH] D130303: Handle template parameter-dependent bit field widths in libclang
collinbaker updated this revision to Diff 503950. collinbaker marked 3 inline comments as done. collinbaker edited the summary of this revision. collinbaker added a comment. Cleanups and split header order change to separate commit Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D130303/new/ https://reviews.llvm.org/D130303 Files: clang/docs/ReleaseNotes.rst clang/include/clang-c/Index.h clang/tools/libclang/CXType.cpp clang/tools/libclang/libclang.map Index: clang/tools/libclang/libclang.map === --- clang/tools/libclang/libclang.map +++ clang/tools/libclang/libclang.map @@ -421,6 +421,7 @@ LLVM_17 { global: clang_CXXMethod_isExplicit; +clang_isBitFieldDecl; }; # Example of how to add a new symbol version entry. If you do add a new symbol Index: clang/tools/libclang/CXType.cpp === --- clang/tools/libclang/CXType.cpp +++ clang/tools/libclang/CXType.cpp @@ -371,14 +371,27 @@ return ULLONG_MAX; } +unsigned clang_isBitFieldDecl(CXCursor C) { + using namespace cxcursor; + + if (clang_isDeclaration(C.kind)) { +const Decl *D = getCursorDecl(C); + +if (const auto *FD = dyn_cast_or_null(D)) + return FD->isBitField(); + } + + return 0; +} + int clang_getFieldDeclBitWidth(CXCursor C) { using namespace cxcursor; if (clang_isDeclaration(C.kind)) { const Decl *D = getCursorDecl(C); -if (const FieldDecl *FD = dyn_cast_or_null(D)) { - if (FD->isBitField()) +if (const auto *FD = dyn_cast_or_null(D)) { + if (FD->isBitField() && !FD->getBitWidth()->isValueDependent()) return FD->getBitWidthValue(getCursorContext(C)); } } Index: clang/include/clang-c/Index.h === --- clang/include/clang-c/Index.h +++ clang/include/clang-c/Index.h @@ -2887,10 +2887,18 @@ CINDEX_LINKAGE unsigned long long clang_getEnumConstantDeclUnsignedValue(CXCursor C); +/** + * Returns non-zero if a field declaration has a bit width expression. + * + * If the cursor does not reference a bit field declaration 0 is returned. + */ +CINDEX_LINKAGE unsigned clang_isBitFieldDecl(CXCursor C); + /** * Retrieve the bit width of a bit field declaration as an integer. * - * If a cursor that is not a bit field declaration is passed in, -1 is returned. + * If the cursor does not reference a bit field, or if the bit field's width + * expression cannot be evaluated, -1 is returned. */ CINDEX_LINKAGE int clang_getFieldDeclBitWidth(CXCursor C); Index: clang/docs/ReleaseNotes.rst === --- clang/docs/ReleaseNotes.rst +++ clang/docs/ReleaseNotes.rst @@ -290,6 +290,11 @@ - Introduced the new function ``clang_CXXMethod_isExplicit``, which identifies whether a constructor or conversion function cursor was marked with the explicit identifier. +- Added check in ``clang_getFieldDeclBitWidth`` for whether a bit field + has an evaluable bit width. Fixes undefined behavior when called on a + bit field whose width depends on a template paramter. +- Added function ``clang_isBitFieldDecl`` to check if a struct/class field is a + bit field. Static Analyzer --- Index: clang/tools/libclang/libclang.map === --- clang/tools/libclang/libclang.map +++ clang/tools/libclang/libclang.map @@ -421,6 +421,7 @@ LLVM_17 { global: clang_CXXMethod_isExplicit; +clang_isBitFieldDecl; }; # Example of how to add a new symbol version entry. If you do add a new symbol Index: clang/tools/libclang/CXType.cpp === --- clang/tools/libclang/CXType.cpp +++ clang/tools/libclang/CXType.cpp @@ -371,14 +371,27 @@ return ULLONG_MAX; } +unsigned clang_isBitFieldDecl(CXCursor C) { + using namespace cxcursor; + + if (clang_isDeclaration(C.kind)) { +const Decl *D = getCursorDecl(C); + +if (const auto *FD = dyn_cast_or_null(D)) + return FD->isBitField(); + } + + return 0; +} + int clang_getFieldDeclBitWidth(CXCursor C) { using namespace cxcursor; if (clang_isDeclaration(C.kind)) { const Decl *D = getCursorDecl(C); -if (const FieldDecl *FD = dyn_cast_or_null(D)) { - if (FD->isBitField()) +if (const auto *FD = dyn_cast_or_null(D)) { + if (FD->isBitField() && !FD->getBitWidth()->isValueDependent()) return FD->getBitWidthValue(getCursorContext(C)); } } Index: clang/include/clang-c/Index.h === --- clang/include/clang-c/Index.h +++ clang/include/clang-c/Index.h @@ -2887,10 +2887,18 @@ CINDEX_LINKAGE unsigned long long clang_getEnumConstantDeclUnsignedValue(CXCursor C); +/** + * Returns non-zero if a field declar
[PATCH] D130303: Handle template parameter-dependent bit field widths in libclang
collinbaker updated this revision to Diff 503952. collinbaker added a comment. Missed commit Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D130303/new/ https://reviews.llvm.org/D130303 Files: clang/docs/ReleaseNotes.rst clang/include/clang-c/Index.h clang/tools/libclang/CXType.cpp clang/tools/libclang/libclang.map Index: clang/tools/libclang/libclang.map === --- clang/tools/libclang/libclang.map +++ clang/tools/libclang/libclang.map @@ -421,6 +421,7 @@ LLVM_17 { global: clang_CXXMethod_isExplicit; +clang_isBitFieldDecl; }; # Example of how to add a new symbol version entry. If you do add a new symbol Index: clang/tools/libclang/CXType.cpp === --- clang/tools/libclang/CXType.cpp +++ clang/tools/libclang/CXType.cpp @@ -10,11 +10,11 @@ // //======// +#include "CXType.h" #include "CIndexer.h" #include "CXCursor.h" #include "CXString.h" #include "CXTranslationUnit.h" -#include "CXType.h" #include "clang/AST/Decl.h" #include "clang/AST/DeclObjC.h" #include "clang/AST/DeclTemplate.h" @@ -371,14 +371,27 @@ return ULLONG_MAX; } +unsigned clang_isBitFieldDecl(CXCursor C) { + using namespace cxcursor; + + if (clang_isDeclaration(C.kind)) { +const Decl *D = getCursorDecl(C); + +if (const auto *FD = dyn_cast_or_null(D)) + return FD->isBitField(); + } + + return 0; +} + int clang_getFieldDeclBitWidth(CXCursor C) { using namespace cxcursor; if (clang_isDeclaration(C.kind)) { const Decl *D = getCursorDecl(C); -if (const FieldDecl *FD = dyn_cast_or_null(D)) { - if (FD->isBitField()) +if (const auto *FD = dyn_cast_or_null(D)) { + if (FD->isBitField() && !FD->getBitWidth()->isValueDependent()) return FD->getBitWidthValue(getCursorContext(C)); } } Index: clang/include/clang-c/Index.h === --- clang/include/clang-c/Index.h +++ clang/include/clang-c/Index.h @@ -2887,10 +2887,18 @@ CINDEX_LINKAGE unsigned long long clang_getEnumConstantDeclUnsignedValue(CXCursor C); +/** + * Returns non-zero if a field declaration has a bit width expression. + * + * If the cursor does not reference a bit field declaration 0 is returned. + */ +CINDEX_LINKAGE unsigned clang_isBitFieldDecl(CXCursor C); + /** * Retrieve the bit width of a bit field declaration as an integer. * - * If a cursor that is not a bit field declaration is passed in, -1 is returned. + * If the cursor does not reference a bit field, or if the bit field's width + * expression cannot be evaluated, -1 is returned. */ CINDEX_LINKAGE int clang_getFieldDeclBitWidth(CXCursor C); Index: clang/docs/ReleaseNotes.rst === --- clang/docs/ReleaseNotes.rst +++ clang/docs/ReleaseNotes.rst @@ -290,6 +290,11 @@ - Introduced the new function ``clang_CXXMethod_isExplicit``, which identifies whether a constructor or conversion function cursor was marked with the explicit identifier. +- Added check in ``clang_getFieldDeclBitWidth`` for whether a bit field + has an evaluable bit width. Fixes undefined behavior when called on a + bit field whose width depends on a template paramter. +- Added function ``clang_isBitFieldDecl`` to check if a struct/class field is a + bit field. Static Analyzer --- Index: clang/tools/libclang/libclang.map === --- clang/tools/libclang/libclang.map +++ clang/tools/libclang/libclang.map @@ -421,6 +421,7 @@ LLVM_17 { global: clang_CXXMethod_isExplicit; +clang_isBitFieldDecl; }; # Example of how to add a new symbol version entry. If you do add a new symbol Index: clang/tools/libclang/CXType.cpp === --- clang/tools/libclang/CXType.cpp +++ clang/tools/libclang/CXType.cpp @@ -10,11 +10,11 @@ // //======// +#include "CXType.h" #include "CIndexer.h" #include "CXCursor.h" #include "CXString.h" #include "CXTranslationUnit.h" -#include "CXType.h" #include "clang/AST/Decl.h" #include "clang/AST/DeclObjC.h" #include "clang/AST/DeclTemplate.h" @@ -371,14 +371,27 @@ return ULLONG_MAX; } +unsigned clang_isBitFieldDecl(CXCursor C) { + using namespace cxcursor; + + if (clang_isDeclaration(C.kind)) { +const Decl *D = getCursorDecl(C); + +if (const auto *FD = dyn_cast_or_null(D)) + return FD->isBitField(); + } + + return 0; +} + int clang_getFieldDeclBitWidth(CXCursor C) { using namespace cxcursor; if (clang_isDeclaration(C.kind)) { const Decl *D = getCursorDecl(C); -if (const FieldDecl *FD = dyn_cast_or_null
[PATCH] D130303: Fix include order in CXType.cpp
collinbaker updated this revision to Diff 503953. collinbaker retitled this revision from "Handle template parameter-dependent bit field widths in libclang" to "Fix include order in CXType.cpp". collinbaker edited the summary of this revision. collinbaker added a comment. Re-add "Fixes" commit message footer Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D130303/new/ https://reviews.llvm.org/D130303 Files: clang/docs/ReleaseNotes.rst clang/include/clang-c/Index.h clang/tools/libclang/CXType.cpp clang/tools/libclang/libclang.map Index: clang/tools/libclang/libclang.map === --- clang/tools/libclang/libclang.map +++ clang/tools/libclang/libclang.map @@ -421,6 +421,7 @@ LLVM_17 { global: clang_CXXMethod_isExplicit; +clang_isBitFieldDecl; }; # Example of how to add a new symbol version entry. If you do add a new symbol Index: clang/tools/libclang/CXType.cpp === --- clang/tools/libclang/CXType.cpp +++ clang/tools/libclang/CXType.cpp @@ -10,11 +10,11 @@ // //======// +#include "CXType.h" #include "CIndexer.h" #include "CXCursor.h" #include "CXString.h" #include "CXTranslationUnit.h" -#include "CXType.h" #include "clang/AST/Decl.h" #include "clang/AST/DeclObjC.h" #include "clang/AST/DeclTemplate.h" @@ -371,14 +371,27 @@ return ULLONG_MAX; } +unsigned clang_isBitFieldDecl(CXCursor C) { + using namespace cxcursor; + + if (clang_isDeclaration(C.kind)) { +const Decl *D = getCursorDecl(C); + +if (const auto *FD = dyn_cast_or_null(D)) + return FD->isBitField(); + } + + return 0; +} + int clang_getFieldDeclBitWidth(CXCursor C) { using namespace cxcursor; if (clang_isDeclaration(C.kind)) { const Decl *D = getCursorDecl(C); -if (const FieldDecl *FD = dyn_cast_or_null(D)) { - if (FD->isBitField()) +if (const auto *FD = dyn_cast_or_null(D)) { + if (FD->isBitField() && !FD->getBitWidth()->isValueDependent()) return FD->getBitWidthValue(getCursorContext(C)); } } Index: clang/include/clang-c/Index.h === --- clang/include/clang-c/Index.h +++ clang/include/clang-c/Index.h @@ -2887,10 +2887,18 @@ CINDEX_LINKAGE unsigned long long clang_getEnumConstantDeclUnsignedValue(CXCursor C); +/** + * Returns non-zero if a field declaration has a bit width expression. + * + * If the cursor does not reference a bit field declaration 0 is returned. + */ +CINDEX_LINKAGE unsigned clang_isBitFieldDecl(CXCursor C); + /** * Retrieve the bit width of a bit field declaration as an integer. * - * If a cursor that is not a bit field declaration is passed in, -1 is returned. + * If the cursor does not reference a bit field, or if the bit field's width + * expression cannot be evaluated, -1 is returned. */ CINDEX_LINKAGE int clang_getFieldDeclBitWidth(CXCursor C); Index: clang/docs/ReleaseNotes.rst === --- clang/docs/ReleaseNotes.rst +++ clang/docs/ReleaseNotes.rst @@ -290,6 +290,11 @@ - Introduced the new function ``clang_CXXMethod_isExplicit``, which identifies whether a constructor or conversion function cursor was marked with the explicit identifier. +- Added check in ``clang_getFieldDeclBitWidth`` for whether a bit field + has an evaluable bit width. Fixes undefined behavior when called on a + bit field whose width depends on a template paramter. +- Added function ``clang_isBitFieldDecl`` to check if a struct/class field is a + bit field. Static Analyzer --- Index: clang/tools/libclang/libclang.map === --- clang/tools/libclang/libclang.map +++ clang/tools/libclang/libclang.map @@ -421,6 +421,7 @@ LLVM_17 { global: clang_CXXMethod_isExplicit; +clang_isBitFieldDecl; }; # Example of how to add a new symbol version entry. If you do add a new symbol Index: clang/tools/libclang/CXType.cpp === --- clang/tools/libclang/CXType.cpp +++ clang/tools/libclang/CXType.cpp @@ -10,11 +10,11 @@ // //======// +#include "CXType.h" #include "CIndexer.h" #include "CXCursor.h" #include "CXString.h" #include "CXTranslationUnit.h" -#include "CXType.h" #include "clang/AST/Decl.h" #include "clang/AST/DeclObjC.h" #include "clang/AST/DeclTemplate.h" @@ -371,14 +371,27 @@ return ULLONG_MAX; } +unsigned clang_isBitFieldDecl(CXCursor C) { + using namespace cxcursor; + + if (clang_isDeclaration(C.kind)) { +const Decl *D = getCursorDecl(C); + +if (const auto *FD = dyn_cast_or_null(D)) + return FD->isBitField(); + } + +
[PATCH] D130303: Fix include order in CXType.cpp
collinbaker marked 5 inline comments as done. collinbaker added a comment. I am very bad at using differential Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D130303/new/ https://reviews.llvm.org/D130303 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[PATCH] D130303: Fix include order in CXType.cpp
collinbaker updated this revision to Diff 503954. collinbaker added a comment. Rebase w/ conflict in libclang.map Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D130303/new/ https://reviews.llvm.org/D130303 Files: clang/docs/ReleaseNotes.rst clang/include/clang-c/Index.h clang/tools/libclang/CXType.cpp clang/tools/libclang/libclang.map Index: clang/tools/libclang/libclang.map === --- clang/tools/libclang/libclang.map +++ clang/tools/libclang/libclang.map @@ -422,6 +422,7 @@ global: clang_CXXMethod_isExplicit; clang_createIndexWithOptions; +clang_isBitFieldDecl; }; # Example of how to add a new symbol version entry. If you do add a new symbol Index: clang/tools/libclang/CXType.cpp === --- clang/tools/libclang/CXType.cpp +++ clang/tools/libclang/CXType.cpp @@ -10,11 +10,11 @@ // //======// +#include "CXType.h" #include "CIndexer.h" #include "CXCursor.h" #include "CXString.h" #include "CXTranslationUnit.h" -#include "CXType.h" #include "clang/AST/Decl.h" #include "clang/AST/DeclObjC.h" #include "clang/AST/DeclTemplate.h" @@ -371,14 +371,27 @@ return ULLONG_MAX; } +unsigned clang_isBitFieldDecl(CXCursor C) { + using namespace cxcursor; + + if (clang_isDeclaration(C.kind)) { +const Decl *D = getCursorDecl(C); + +if (const auto *FD = dyn_cast_or_null(D)) + return FD->isBitField(); + } + + return 0; +} + int clang_getFieldDeclBitWidth(CXCursor C) { using namespace cxcursor; if (clang_isDeclaration(C.kind)) { const Decl *D = getCursorDecl(C); -if (const FieldDecl *FD = dyn_cast_or_null(D)) { - if (FD->isBitField()) +if (const auto *FD = dyn_cast_or_null(D)) { + if (FD->isBitField() && !FD->getBitWidth()->isValueDependent()) return FD->getBitWidthValue(getCursorContext(C)); } } Index: clang/include/clang-c/Index.h === --- clang/include/clang-c/Index.h +++ clang/include/clang-c/Index.h @@ -3016,10 +3016,18 @@ CINDEX_LINKAGE unsigned long long clang_getEnumConstantDeclUnsignedValue(CXCursor C); +/** + * Returns non-zero if a field declaration has a bit width expression. + * + * If the cursor does not reference a bit field declaration 0 is returned. + */ +CINDEX_LINKAGE unsigned clang_isBitFieldDecl(CXCursor C); + /** * Retrieve the bit width of a bit field declaration as an integer. * - * If a cursor that is not a bit field declaration is passed in, -1 is returned. + * If the cursor does not reference a bit field, or if the bit field's width + * expression cannot be evaluated, -1 is returned. */ CINDEX_LINKAGE int clang_getFieldDeclBitWidth(CXCursor C); Index: clang/docs/ReleaseNotes.rst === --- clang/docs/ReleaseNotes.rst +++ clang/docs/ReleaseNotes.rst @@ -295,6 +295,11 @@ - Introduced the new function ``clang_CXXMethod_isExplicit``, which identifies whether a constructor or conversion function cursor was marked with the explicit identifier. +- Added check in ``clang_getFieldDeclBitWidth`` for whether a bit field + has an evaluable bit width. Fixes undefined behavior when called on a + bit field whose width depends on a template paramter. +- Added function ``clang_isBitFieldDecl`` to check if a struct/class field is a + bit field. - Introduced the new ``CXIndex`` constructor function ``clang_createIndexWithOptions``, which allows overriding precompiled preamble Index: clang/tools/libclang/libclang.map === --- clang/tools/libclang/libclang.map +++ clang/tools/libclang/libclang.map @@ -422,6 +422,7 @@ global: clang_CXXMethod_isExplicit; clang_createIndexWithOptions; +clang_isBitFieldDecl; }; # Example of how to add a new symbol version entry. If you do add a new symbol Index: clang/tools/libclang/CXType.cpp === --- clang/tools/libclang/CXType.cpp +++ clang/tools/libclang/CXType.cpp @@ -10,11 +10,11 @@ // //======// +#include "CXType.h" #include "CIndexer.h" #include "CXCursor.h" #include "CXString.h" #include "CXTranslationUnit.h" -#include "CXType.h" #include "clang/AST/Decl.h" #include "clang/AST/DeclObjC.h" #include "clang/AST/DeclTemplate.h" @@ -371,14 +371,27 @@ return ULLONG_MAX; } +unsigned clang_isBitFieldDecl(CXCursor C) { + using namespace cxcursor; + + if (clang_isDeclaration(C.kind)) { +const Decl *D = getCursorDecl(C); + +if (const auto *FD = dyn_cast_or_null(D)) + return FD->isBitField(); + } + + return 0; +} + int clang_getFieldDeclBitWidt
[PATCH] D130303: Fix include order in CXType.cpp
collinbaker added a comment. All done. Again, I don't have commit access so someone else will need to land this. Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D130303/new/ https://reviews.llvm.org/D130303 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[PATCH] D130303: Fix include order in CXType.cpp
collinbaker added a comment. Collin Baker collinba...@chromium.org This should also be in the author field of the commits Thanks! Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D130303/new/ https://reviews.llvm.org/D130303 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[PATCH] D115049: Fall back on Android triple w/o API level for runtimes search
collinbaker updated this revision to Diff 397394. collinbaker added a comment. Rebase Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D115049/new/ https://reviews.llvm.org/D115049 Files: clang/include/clang/Driver/ToolChain.h clang/lib/Driver/Driver.cpp clang/lib/Driver/ToolChain.cpp clang/lib/Driver/ToolChains/Fuchsia.cpp clang/lib/Driver/ToolChains/VEToolchain.cpp clang/test/Driver/Inputs/resource_dir_with_per_target_subdir/lib/aarch64-unknown-linux-android/.keep clang/test/Driver/Inputs/resource_dir_with_per_target_subdir/lib/aarch64-unknown-linux-android/libclang_rt.builtins.a clang/test/Driver/Inputs/resource_dir_with_per_target_subdir/lib/aarch64-unknown-linux-android21/.keep clang/test/Driver/Inputs/resource_dir_with_per_target_subdir/lib/aarch64-unknown-linux-android21/libclang_rt.builtins.a clang/test/Driver/linux-per-target-runtime-dir.c Index: clang/test/Driver/linux-per-target-runtime-dir.c === --- clang/test/Driver/linux-per-target-runtime-dir.c +++ clang/test/Driver/linux-per-target-runtime-dir.c @@ -25,3 +25,21 @@ // RUN: -resource-dir=%S/Inputs/resource_dir_with_per_target_subdir \ // RUN: | FileCheck --check-prefix=CHECK-FILE-NAME-X8664 %s // CHECK-FILE-NAME-X8664: lib{{/|\\}}x86_64-unknown-linux-gnu{{/|\\}}libclang_rt.builtins.a + +// RUN: %clang -rtlib=compiler-rt -print-file-name=libclang_rt.builtins.a 2>&1 \ +// RUN: --target=aarch64-unknown-linux-android21 \ +// RUN: -resource-dir=%S/Inputs/resource_dir_with_per_target_subdir \ +// RUN: | FileCheck --check-prefix=CHECK-FILE-NAME-ANDROID21 %s +// CHECK-FILE-NAME-ANDROID21: lib{{/|\\}}aarch64-unknown-linux-android21{{/|\\}}libclang_rt.builtins.a + +// RUN: %clang -rtlib=compiler-rt -print-file-name=libclang_rt.builtins.a 2>&1 \ +// RUN: --target=aarch64-unknown-linux-android23 \ +// RUN: -resource-dir=%S/Inputs/resource_dir_with_per_target_subdir \ +// RUN: | FileCheck --check-prefix=CHECK-FILE-NAME-ANDROID23 %s +// CHECK-FILE-NAME-ANDROID23: lib{{/|\\}}aarch64-unknown-linux-android{{/|\\}}libclang_rt.builtins.a + +// RUN: %clang -rtlib=compiler-rt -print-file-name=libclang_rt.builtins.a 2>&1 \ +// RUN: --target=aarch64-unknown-linux-android \ +// RUN: -resource-dir=%S/Inputs/resource_dir_with_per_target_subdir \ +// RUN: | FileCheck --check-prefix=CHECK-FILE-NAME-ANDROID %s +// CHECK-FILE-NAME-ANDROID: lib{{/|\\}}aarch64-unknown-linux-android{{/|\\}}libclang_rt.builtins.a Index: clang/lib/Driver/ToolChains/VEToolchain.cpp === --- clang/lib/Driver/ToolChains/VEToolchain.cpp +++ clang/lib/Driver/ToolChains/VEToolchain.cpp @@ -48,7 +48,8 @@ // ${BINPATH}/../lib/ve-unknown-linux-gnu, (== getStdlibPath) // ${RESOURCEDIR}/lib/linux/ve, (== getArchSpecificLibPath) // ${SYSROOT}/opt/nec/ve/lib, - getFilePaths().push_back(getStdlibPath()); + for (auto &Path : getStdlibPaths()) +getFilePaths().push_back(std::move(Path)); getFilePaths().push_back(getArchSpecificLibPath()); getFilePaths().push_back(computeSysRoot() + "/opt/nec/ve/lib"); } Index: clang/lib/Driver/ToolChains/Fuchsia.cpp === --- clang/lib/Driver/ToolChains/Fuchsia.cpp +++ clang/lib/Driver/ToolChains/Fuchsia.cpp @@ -191,9 +191,11 @@ auto FilePaths = [&](const Multilib &M) -> std::vector { std::vector FP; -SmallString<128> P(getStdlibPath()); -llvm::sys::path::append(P, M.gccSuffix()); -FP.push_back(std::string(P.str())); +for (const std::string &Path : getStdlibPaths()) { + SmallString<128> P(Path); + llvm::sys::path::append(P, M.gccSuffix()); + FP.push_back(std::string(P.str())); +} return FP; }; Index: clang/lib/Driver/ToolChain.cpp === --- clang/lib/Driver/ToolChain.cpp +++ clang/lib/Driver/ToolChain.cpp @@ -75,17 +75,16 @@ const ArgList &Args) : D(D), Triple(T), Args(Args), CachedRTTIArg(GetRTTIArgument(Args)), CachedRTTIMode(CalculateRTTIMode(Args, Triple, CachedRTTIArg)) { - std::string RuntimePath = getRuntimePath(); - if (getVFS().exists(RuntimePath)) -getLibraryPaths().push_back(RuntimePath); - - std::string StdlibPath = getStdlibPath(); - if (getVFS().exists(StdlibPath)) -getFilePaths().push_back(StdlibPath); + auto addIfExists = [this](path_list &List, const std::string &Path) { +if (getVFS().exists(Path)) + List.push_back(Path); + }; - std::string CandidateLibPath = getArchSpecificLibPath(); - if (getVFS().exists(CandidateLibPath)) -getFilePaths().push_back(CandidateLibPath); + for (const auto &Path : getRuntimePaths()) +addIfExists(getLibraryPaths(), Path); + for (const auto &Path : getStdlibPaths()) +addIfExists(getFilePaths(), Path); + addIfExists(getF
[PATCH] D115049: Fall back on Android triple w/o API level for runtimes search
collinbaker updated this revision to Diff 393978. collinbaker added a comment. - Address comments - Fix VEToolchain build error - Rebase Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D115049/new/ https://reviews.llvm.org/D115049 Files: clang/include/clang/Driver/ToolChain.h clang/lib/Driver/Driver.cpp clang/lib/Driver/ToolChain.cpp clang/lib/Driver/ToolChains/Fuchsia.cpp clang/lib/Driver/ToolChains/VEToolchain.cpp clang/test/Driver/Inputs/resource_dir_with_per_target_subdir/lib/aarch64-unknown-linux-android/.keep clang/test/Driver/Inputs/resource_dir_with_per_target_subdir/lib/aarch64-unknown-linux-android/libclang_rt.builtins.a clang/test/Driver/Inputs/resource_dir_with_per_target_subdir/lib/aarch64-unknown-linux-android21/.keep clang/test/Driver/Inputs/resource_dir_with_per_target_subdir/lib/aarch64-unknown-linux-android21/libclang_rt.builtins.a clang/test/Driver/linux-per-target-runtime-dir.c Index: clang/test/Driver/linux-per-target-runtime-dir.c === --- clang/test/Driver/linux-per-target-runtime-dir.c +++ clang/test/Driver/linux-per-target-runtime-dir.c @@ -25,3 +25,21 @@ // RUN: -resource-dir=%S/Inputs/resource_dir_with_per_target_subdir \ // RUN: | FileCheck --check-prefix=CHECK-FILE-NAME-X8664 %s // CHECK-FILE-NAME-X8664: lib{{/|\\}}x86_64-unknown-linux-gnu{{/|\\}}libclang_rt.builtins.a + +// RUN: %clang -rtlib=compiler-rt -print-file-name=libclang_rt.builtins.a 2>&1 \ +// RUN: --target=aarch64-unknown-linux-android21 \ +// RUN: -resource-dir=%S/Inputs/resource_dir_with_per_target_subdir \ +// RUN: | FileCheck --check-prefix=CHECK-FILE-NAME-ANDROID21 %s +// CHECK-FILE-NAME-ANDROID21: lib{{/|\\}}aarch64-unknown-linux-android21{{/|\\}}libclang_rt.builtins.a + +// RUN: %clang -rtlib=compiler-rt -print-file-name=libclang_rt.builtins.a 2>&1 \ +// RUN: --target=aarch64-unknown-linux-android23 \ +// RUN: -resource-dir=%S/Inputs/resource_dir_with_per_target_subdir \ +// RUN: | FileCheck --check-prefix=CHECK-FILE-NAME-ANDROID23 %s +// CHECK-FILE-NAME-ANDROID23: lib{{/|\\}}aarch64-unknown-linux-android{{/|\\}}libclang_rt.builtins.a + +// RUN: %clang -rtlib=compiler-rt -print-file-name=libclang_rt.builtins.a 2>&1 \ +// RUN: --target=aarch64-unknown-linux-android \ +// RUN: -resource-dir=%S/Inputs/resource_dir_with_per_target_subdir \ +// RUN: | FileCheck --check-prefix=CHECK-FILE-NAME-ANDROID %s +// CHECK-FILE-NAME-ANDROID: lib{{/|\\}}aarch64-unknown-linux-android{{/|\\}}libclang_rt.builtins.a Index: clang/lib/Driver/ToolChains/VEToolchain.cpp === --- clang/lib/Driver/ToolChains/VEToolchain.cpp +++ clang/lib/Driver/ToolChains/VEToolchain.cpp @@ -48,7 +48,8 @@ // ${BINPATH}/../lib/ve-unknown-linux-gnu, (== getStdlibPath) // ${RESOURCEDIR}/lib/linux/ve, (== getArchSpecificLibPath) // ${SYSROOT}/opt/nec/ve/lib, - getFilePaths().push_back(getStdlibPath()); + for (auto &Path : getStdlibPaths()) +getFilePaths().push_back(std::move(Path)); getFilePaths().push_back(getArchSpecificLibPath()); getFilePaths().push_back(computeSysRoot() + "/opt/nec/ve/lib"); } Index: clang/lib/Driver/ToolChains/Fuchsia.cpp === --- clang/lib/Driver/ToolChains/Fuchsia.cpp +++ clang/lib/Driver/ToolChains/Fuchsia.cpp @@ -191,9 +191,11 @@ auto FilePaths = [&](const Multilib &M) -> std::vector { std::vector FP; -SmallString<128> P(getStdlibPath()); -llvm::sys::path::append(P, M.gccSuffix()); -FP.push_back(std::string(P.str())); +for (const std::string &Path : getStdlibPaths()) { + SmallString<128> P(Path); + llvm::sys::path::append(P, M.gccSuffix()); + FP.push_back(std::string(P.str())); +} return FP; }; Index: clang/lib/Driver/ToolChain.cpp === --- clang/lib/Driver/ToolChain.cpp +++ clang/lib/Driver/ToolChain.cpp @@ -75,17 +75,16 @@ const ArgList &Args) : D(D), Triple(T), Args(Args), CachedRTTIArg(GetRTTIArgument(Args)), CachedRTTIMode(CalculateRTTIMode(Args, Triple, CachedRTTIArg)) { - std::string RuntimePath = getRuntimePath(); - if (getVFS().exists(RuntimePath)) -getLibraryPaths().push_back(RuntimePath); - - std::string StdlibPath = getStdlibPath(); - if (getVFS().exists(StdlibPath)) -getFilePaths().push_back(StdlibPath); + auto addIfExists = [this](path_list &List, const std::string &Path) { +if (getVFS().exists(Path)) + List.push_back(Path); + }; - std::string CandidateLibPath = getArchSpecificLibPath(); - if (getVFS().exists(CandidateLibPath)) -getFilePaths().push_back(CandidateLibPath); + for (const auto &Path : getRuntimePaths()) +addIfExists(getLibraryPaths(), Path); + for (const auto &Path : getStdlibPaths()) +add
[PATCH] D115049: Fall back on Android triple w/o API level for runtimes search
collinbaker marked 2 inline comments as done. collinbaker added inline comments. Comment at: clang/lib/Driver/ToolChain.cpp:500 + if (getTriple().isAndroid() && + getTriple().getEnvironmentName() != "android") { +llvm::outs() << getTriple().getEnvironmentName() << "\n"; thakis wrote: > Why do you need the environment check? This skips adding an extra path if the triple doesn't have an Android API level. E.g. for the target triple aarch64-unknown-linux-android23, the environment name will be "android23". The condition will be true since "android23" != "android", and the extra path will be appended. If it had just been "android" it'll skip this step. Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D115049/new/ https://reviews.llvm.org/D115049 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits