[PATCH] D30607: Replace re module by regex module in run-clang-tidy script
alexfh added a comment. https://docs.python.org/2/howto/regex.html#introduction says "The regex module was removed completely in Python 2.5.". Why would we want to switch to it? https://reviews.llvm.org/D30607 ___ cfe-commits mailing list cfe-commits@lists.llvm.org http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[PATCH] D30607: Replace re module by regex module in run-clang-tidy script
alexfh added a comment. Actually, I'm not sure why we need groups in that regex. We can instead try replacing `re.compile('(' + ')|('.join(args.files) + ')')` with `re.compile('|'.join(args.files))`. https://reviews.llvm.org/D30607 ___ cfe-commits mailing list cfe-commits@lists.llvm.org http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[PATCH] D30610: [clang-tidy] Added options to cppcoreguidelines-special-member-functions check
fgross updated this revision to Diff 90607. fgross marked an inline comment as done. fgross added a comment. reformatted https://reviews.llvm.org/D30610 Files: clang-tidy/cppcoreguidelines/SpecialMemberFunctionsCheck.cpp clang-tidy/cppcoreguidelines/SpecialMemberFunctionsCheck.h docs/clang-tidy/checks/cppcoreguidelines-special-member-functions.rst test/clang-tidy/cppcoreguidelines-special-member-functions-cxx-03.cpp test/clang-tidy/cppcoreguidelines-special-member-functions-relaxed.cpp test/clang-tidy/cppcoreguidelines-special-member-functions.cpp Index: test/clang-tidy/cppcoreguidelines-special-member-functions.cpp === --- test/clang-tidy/cppcoreguidelines-special-member-functions.cpp +++ test/clang-tidy/cppcoreguidelines-special-member-functions.cpp @@ -3,7 +3,12 @@ class DefinesDestructor { ~DefinesDestructor(); }; -// CHECK-MESSAGES: [[@LINE-3]]:7: warning: class 'DefinesDestructor' defines a destructor but does not define a copy constructor, a copy assignment operator, a move constructor or a move assignment operator [cppcoreguidelines-special-member-functions] +// CHECK-MESSAGES: [[@LINE-3]]:7: warning: class 'DefinesDestructor' defines a non-default destructor but does not define a copy constructor, a copy assignment operator, a move constructor or a move assignment operator [cppcoreguidelines-special-member-functions] + +class DefinesDefaultedDestructor { + ~DefinesDefaultedDestructor() = default; +}; +// CHECK-MESSAGES: [[@LINE-3]]:7: warning: class 'DefinesDefaultedDestructor' defines a default destructor but does not define a copy constructor, a copy assignment operator, a move constructor or a move assignment operator [cppcoreguidelines-special-member-functions] class DefinesCopyConstructor { DefinesCopyConstructor(const DefinesCopyConstructor &); Index: test/clang-tidy/cppcoreguidelines-special-member-functions-relaxed.cpp === --- test/clang-tidy/cppcoreguidelines-special-member-functions-relaxed.cpp +++ test/clang-tidy/cppcoreguidelines-special-member-functions-relaxed.cpp @@ -0,0 +1,71 @@ +// RUN: %check_clang_tidy %s cppcoreguidelines-special-member-functions %t -- -config="{CheckOptions: [{key: cppcoreguidelines-special-member-functions.AllowMissingMoveFunctions, value: 1}, {key: cppcoreguidelines-special-member-functions.AllowSoleDefaultDtor, value: 1}]}" -- + +class DefinesDestructor { + ~DefinesDestructor(); +}; +// CHECK-MESSAGES: [[@LINE-3]]:7: warning: class 'DefinesDestructor' defines a non-default destructor but does not define a copy constructor or a copy assignment operator [cppcoreguidelines-special-member-functions] + +class DefinesDefaultedDestructor { + ~DefinesDefaultedDestructor() = default; +}; + +class DefinesCopyConstructor { + DefinesCopyConstructor(const DefinesCopyConstructor &); +}; +// CHECK-MESSAGES: [[@LINE-3]]:7: warning: class 'DefinesCopyConstructor' defines a copy constructor but does not define a destructor or a copy assignment operator [cppcoreguidelines-special-member-functions] + +class DefinesCopyAssignment { + DefinesCopyAssignment &operator=(const DefinesCopyAssignment &); +}; +// CHECK-MESSAGES: [[@LINE-3]]:7: warning: class 'DefinesCopyAssignment' defines a copy assignment operator but does not define a destructor or a copy constructor [cppcoreguidelines-special-member-functions] + +class DefinesMoveConstructor { + DefinesMoveConstructor(DefinesMoveConstructor &&); +}; +// CHECK-MESSAGES: [[@LINE-3]]:7: warning: class 'DefinesMoveConstructor' defines a move constructor but does not define a destructor, a copy constructor, a copy assignment operator or a move assignment operator [cppcoreguidelines-special-member-functions] + +class DefinesMoveAssignment { + DefinesMoveAssignment &operator=(DefinesMoveAssignment &&); +}; +// CHECK-MESSAGES: [[@LINE-3]]:7: warning: class 'DefinesMoveAssignment' defines a move assignment operator but does not define a destructor, a copy constructor, a copy assignment operator or a move constructor [cppcoreguidelines-special-member-functions] +class DefinesNothing { +}; + +class DefinesEverything { + DefinesEverything(const DefinesEverything &); + DefinesEverything &operator=(const DefinesEverything &); + DefinesEverything(DefinesEverything &&); + DefinesEverything &operator=(DefinesEverything &&); + ~DefinesEverything(); +}; + +class DeletesEverything { + DeletesEverything(const DeletesEverything &) = delete; + DeletesEverything &operator=(const DeletesEverything &) = delete; + DeletesEverything(DeletesEverything &&) = delete; + DeletesEverything &operator=(DeletesEverything &&) = delete; + ~DeletesEverything() = delete; +}; + +class DeletesCopyDefaultsMove { + DeletesCopyDefaultsMove(const DeletesCopyDefaultsMove &) = delete; + DeletesCopyDefaultsMove &operator=(const DeletesCopyDefaultsMove &) = delete; + DeletesCopyDefaultsMove(DeletesCopyDefault
[libunwind] r296991 - Drop the dependency on dl_unwind_find_exidx().
Author: ed Date: Sun Mar 5 13:11:24 2017 New Revision: 296991 URL: http://llvm.org/viewvc/llvm-project?rev=296991&view=rev Log: Drop the dependency on dl_unwind_find_exidx(). While porting libunwind over to CloudABI for ARMv6, I observed that this source file doesn't build, as it depends on dl_unwind_find_exidx(), which CloudABI's C library was lacking. After I added that function, I still needed to patch up libunwind to define _Unwind_Ptr. Taking a step back, I wonder why we need to make use of this function anyway. The unwinder already has some nice code to use dl_iterate_phdr() to scan for a PT_GNU_EH_FRAME header. The dl_unwind_find_exidx() does the same thing, except matching PT_ARM_EXIDX instead. We could also do that ourselves. This change gets rid of the dl_unwind_find_exidx() call and extends the dl_iterate_phdr() loop. This approach has the advantage of getting rid of some of those OS-specific #ifdefs. This now means that if an operating system only provides dl_iterate_phdr(), it gets support for unwinding on all architectures. There is no need to add more stuff, just to get ARMv6 support. This change is identical to r295944, except that it now adds the necessary code to do bounds checking on PT_LOAD. The previous version of this change lacked this, which didn't cause any problems on CloudABI, but did break the Linux build bots. This is why I reverted it in r295948. Differential Revision: https://reviews.llvm.org/D30306 Modified: libunwind/trunk/src/AddressSpace.hpp Modified: libunwind/trunk/src/AddressSpace.hpp URL: http://llvm.org/viewvc/llvm-project/libunwind/trunk/src/AddressSpace.hpp?rev=296991&r1=296990&r2=296991&view=diff == --- libunwind/trunk/src/AddressSpace.hpp (original) +++ libunwind/trunk/src/AddressSpace.hpp Sun Mar 5 13:11:24 2017 @@ -35,29 +35,17 @@ namespace libunwind { #include "Registers.hpp" #if _LIBUNWIND_ARM_EHABI -#if defined(__FreeBSD__) || defined(__NetBSD__) || defined(__OpenBSD__) - -typedef void *_Unwind_Ptr; - -#elif defined(__linux__) - -typedef long unsigned int *_Unwind_Ptr; -extern "C" _Unwind_Ptr __gnu_Unwind_Find_exidx(_Unwind_Ptr addr, int *len); - -// Emulate the BSD dl_unwind_find_exidx API when on a GNU libdl system. -#define dl_unwind_find_exidx __gnu_Unwind_Find_exidx - -#elif !defined(_LIBUNWIND_IS_BAREMETAL) -#include -#else // !defined(_LIBUNWIND_IS_BAREMETAL) -// When statically linked on bare-metal, the symbols for the EH table are looked -// up without going through the dynamic loader. struct EHTEntry { uint32_t functionOffset; uint32_t unwindOpcodes; }; +#if defined(_LIBUNWIND_IS_BAREMETAL) +// When statically linked on bare-metal, the symbols for the EH table are looked +// up without going through the dynamic loader. extern EHTEntry __exidx_start; extern EHTEntry __exidx_end; +#else +#include #endif // !defined(_LIBUNWIND_IS_BAREMETAL) #endif // _LIBUNWIND_ARM_EHABI @@ -368,23 +356,15 @@ inline bool LocalAddressSpace::findUnwin info.compact_unwind_section_length = dyldInfo.compact_unwind_section_length; return true; } -#elif _LIBUNWIND_ARM_EHABI - #ifdef _LIBUNWIND_IS_BAREMETAL +#elif _LIBUNWIND_ARM_EHABI && defined(_LIBUNWIND_IS_BAREMETAL) // Bare metal is statically linked, so no need to ask the dynamic loader info.arm_section =(uintptr_t)(&__exidx_start); info.arm_section_length = (uintptr_t)(&__exidx_end - &__exidx_start); - #else - int length = 0; - info.arm_section = (uintptr_t) dl_unwind_find_exidx( - (_Unwind_Ptr) targetAddr, &length); - info.arm_section_length = (uintptr_t)length; - #endif _LIBUNWIND_TRACE_UNWINDING("findUnwindSections: section %X length %x", info.arm_section, info.arm_section_length); if (info.arm_section && info.arm_section_length) return true; -#elif _LIBUNWIND_SUPPORT_DWARF_UNWIND -#if _LIBUNWIND_SUPPORT_DWARF_INDEX +#elif _LIBUNWIND_ARM_EHABI || _LIBUNWIND_SUPPORT_DWARF_UNWIND struct dl_iterate_cb_data { LocalAddressSpace *addressSpace; UnwindInfoSections *sects; @@ -395,7 +375,6 @@ inline bool LocalAddressSpace::findUnwin int found = dl_iterate_phdr( [](struct dl_phdr_info *pinfo, size_t, void *data) -> int { auto cbdata = static_cast(data); -size_t object_length; bool found_obj = false; bool found_hdr = false; @@ -413,6 +392,11 @@ inline bool LocalAddressSpace::findUnwin typedef ElfW(Phdr) Elf_Phdr; #endif + #if _LIBUNWIND_SUPPORT_DWARF_UNWIND + #if !_LIBUNWIND_SUPPORT_DWARF_INDEX + #error "_LIBUNWIND_SUPPORT_DWARF_UNWIND requires _LIBUNWIND_SUPPORT_DWARF_INDEX on this platform." + #endif +size_t object_length; for (Elf_Half i = 0; i < pinfo->dlpi_phnum; i++) { const Elf_Phdr *phdr = &pinfo->dlpi_phdr[i]; if (phdr->p_type == PT_LOAD) { @@ -442,12 +426,27 @@ inline bool LocalAddressSpace::findUnwin } e
[PATCH] D30599: [ubsan] Extend the nonnull argument check to ObjC
This revision was automatically updated to reflect the committed changes. Closed by commit rL296996: [ubsan] Extend the nonnull arg check to ObjC (authored by vedantk). Changed prior to commit: https://reviews.llvm.org/D30599?vs=90564&id=90647#toc Repository: rL LLVM https://reviews.llvm.org/D30599 Files: cfe/trunk/lib/CodeGen/CGCall.cpp cfe/trunk/lib/CodeGen/CGExprCXX.cpp cfe/trunk/lib/CodeGen/CGObjC.cpp cfe/trunk/lib/CodeGen/CodeGenFunction.h cfe/trunk/test/CodeGenObjC/ubsan-nonnull.m Index: cfe/trunk/lib/CodeGen/CGCall.cpp === --- cfe/trunk/lib/CodeGen/CGCall.cpp +++ cfe/trunk/lib/CodeGen/CGCall.cpp @@ -3242,13 +3242,13 @@ void CodeGenFunction::EmitNonNullArgCheck(RValue RV, QualType ArgType, SourceLocation ArgLoc, - const FunctionDecl *FD, + AbstractCallee AC, unsigned ParmNum) { - if (!SanOpts.has(SanitizerKind::NonnullAttribute) || !FD) + if (!SanOpts.has(SanitizerKind::NonnullAttribute) || !AC.getDecl()) return; - auto PVD = ParmNum < FD->getNumParams() ? FD->getParamDecl(ParmNum) : nullptr; + auto PVD = ParmNum < AC.getNumParams() ? AC.getParamDecl(ParmNum) : nullptr; unsigned ArgNo = PVD ? PVD->getFunctionScopeIndex() : ParmNum; - auto NNAttr = getNonNullAttr(FD, PVD, ArgType, ArgNo); + auto NNAttr = getNonNullAttr(AC.getDecl(), PVD, ArgType, ArgNo); if (!NNAttr) return; SanitizerScope SanScope(this); @@ -3268,8 +3268,7 @@ void CodeGenFunction::EmitCallArgs( CallArgList &Args, ArrayRef ArgTypes, llvm::iterator_range ArgRange, -const FunctionDecl *CalleeDecl, unsigned ParamsToSkip, -EvaluationOrder Order) { +AbstractCallee AC, unsigned ParamsToSkip, EvaluationOrder Order) { assert((int)ArgTypes.size() == (ArgRange.end() - ArgRange.begin())); // We *have* to evaluate arguments from right to left in the MS C++ ABI, @@ -3284,9 +3283,9 @@ auto MaybeEmitImplicitObjectSize = [&](unsigned I, const Expr *Arg, RValue EmittedArg) { -if (CalleeDecl == nullptr || I >= CalleeDecl->getNumParams()) +if (!AC.hasFunctionDecl() || I >= AC.getNumParams()) return; -auto *PS = CalleeDecl->getParamDecl(I)->getAttr(); +auto *PS = AC.getParamDecl(I)->getAttr(); if (PS == nullptr) return; @@ -3328,7 +3327,7 @@ "The code below depends on only adding one arg per EmitCallArg"); (void)InitialArgSize; RValue RVArg = Args.back().RV; -EmitNonNullArgCheck(RVArg, ArgTypes[Idx], (*Arg)->getExprLoc(), CalleeDecl, +EmitNonNullArgCheck(RVArg, ArgTypes[Idx], (*Arg)->getExprLoc(), AC, ParamsToSkip + Idx); // @llvm.objectsize should never have side-effects and shouldn't need // destruction/cleanups, so we can safely "emit" it after its arg, Index: cfe/trunk/lib/CodeGen/CGObjC.cpp === --- cfe/trunk/lib/CodeGen/CGObjC.cpp +++ cfe/trunk/lib/CodeGen/CGObjC.cpp @@ -427,7 +427,7 @@ QualType ResultType = method ? method->getReturnType() : E->getType(); CallArgList Args; - EmitCallArgs(Args, method, E->arguments()); + EmitCallArgs(Args, method, E->arguments(), /*AC*/AbstractCallee(method)); // For delegate init calls in ARC, do an unsafe store of null into // self. This represents the call taking direct ownership of that Index: cfe/trunk/lib/CodeGen/CGExprCXX.cpp === --- cfe/trunk/lib/CodeGen/CGExprCXX.cpp +++ cfe/trunk/lib/CodeGen/CGExprCXX.cpp @@ -1579,7 +1579,7 @@ // FIXME: Why do we not pass a CalleeDecl here? EmitCallArgs(allocatorArgs, allocatorType, E->placement_arguments(), - /*CalleeDecl*/nullptr, /*ParamsToSkip*/ParamsToSkip); + /*AC*/AbstractCallee(), /*ParamsToSkip*/ParamsToSkip); RValue RV = EmitNewDeleteCall(*this, allocator, allocatorType, allocatorArgs); Index: cfe/trunk/lib/CodeGen/CodeGenFunction.h === --- cfe/trunk/lib/CodeGen/CodeGenFunction.h +++ cfe/trunk/lib/CodeGen/CodeGenFunction.h @@ -305,6 +305,31 @@ ~CGCapturedStmtRAII() { CGF.CapturedStmtInfo = PrevCapturedStmtInfo; } }; + /// An abstract representation of regular/ObjC call/message targets. + class AbstractCallee { +/// The function declaration of the callee. +const Decl *CalleeDecl; + + public: +AbstractCallee() : CalleeDecl(nullptr) {} +AbstractCallee(const FunctionDecl *FD) : CalleeDecl(FD) {} +AbstractCallee(const ObjCMethodDecl *OMD) : CalleeDecl(OMD) {} +bool hasFunctionDecl() const { + return dyn_cast_or_null(CalleeDecl); +} +const Decl *getDecl() const { return CalleeDecl; } +unsigned getNumP
[PATCH] D30599: [ubsan] Extend the nonnull argument check to ObjC
vsk marked an inline comment as done. vsk added a comment. Thanks for the reviews! Comment at: lib/CodeGen/CodeGenFunction.h:308 + /// \brief An abstract representation of regular/ObjC call/message targets. + class AbstractCallee { aprantl wrote: > The \brief is redundant (we use autobrief) and shouldn't be used any more. I will fix this before committing. Repository: rL LLVM https://reviews.llvm.org/D30599 ___ cfe-commits mailing list cfe-commits@lists.llvm.org http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
r296996 - [ubsan] Extend the nonnull arg check to ObjC
Author: vedantk Date: Sun Mar 5 23:28:22 2017 New Revision: 296996 URL: http://llvm.org/viewvc/llvm-project?rev=296996&view=rev Log: [ubsan] Extend the nonnull arg check to ObjC UBSan's nonnull argument check applies when a parameter has the "nonnull" attribute. The check currently works for FunctionDecls, but not for ObjCMethodDecls. This patch extends the check to work for ObjC. Differential Revision: https://reviews.llvm.org/D30599 Added: cfe/trunk/test/CodeGenObjC/ubsan-nonnull.m Modified: cfe/trunk/lib/CodeGen/CGCall.cpp cfe/trunk/lib/CodeGen/CGExprCXX.cpp cfe/trunk/lib/CodeGen/CGObjC.cpp cfe/trunk/lib/CodeGen/CodeGenFunction.h Modified: cfe/trunk/lib/CodeGen/CGCall.cpp URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CGCall.cpp?rev=296996&r1=296995&r2=296996&view=diff == --- cfe/trunk/lib/CodeGen/CGCall.cpp (original) +++ cfe/trunk/lib/CodeGen/CGCall.cpp Sun Mar 5 23:28:22 2017 @@ -3242,13 +3242,13 @@ void CallArgList::freeArgumentMemory(Cod void CodeGenFunction::EmitNonNullArgCheck(RValue RV, QualType ArgType, SourceLocation ArgLoc, - const FunctionDecl *FD, + AbstractCallee AC, unsigned ParmNum) { - if (!SanOpts.has(SanitizerKind::NonnullAttribute) || !FD) + if (!SanOpts.has(SanitizerKind::NonnullAttribute) || !AC.getDecl()) return; - auto PVD = ParmNum < FD->getNumParams() ? FD->getParamDecl(ParmNum) : nullptr; + auto PVD = ParmNum < AC.getNumParams() ? AC.getParamDecl(ParmNum) : nullptr; unsigned ArgNo = PVD ? PVD->getFunctionScopeIndex() : ParmNum; - auto NNAttr = getNonNullAttr(FD, PVD, ArgType, ArgNo); + auto NNAttr = getNonNullAttr(AC.getDecl(), PVD, ArgType, ArgNo); if (!NNAttr) return; SanitizerScope SanScope(this); @@ -3268,8 +3268,7 @@ void CodeGenFunction::EmitNonNullArgChec void CodeGenFunction::EmitCallArgs( CallArgList &Args, ArrayRef ArgTypes, llvm::iterator_range ArgRange, -const FunctionDecl *CalleeDecl, unsigned ParamsToSkip, -EvaluationOrder Order) { +AbstractCallee AC, unsigned ParamsToSkip, EvaluationOrder Order) { assert((int)ArgTypes.size() == (ArgRange.end() - ArgRange.begin())); // We *have* to evaluate arguments from right to left in the MS C++ ABI, @@ -3284,9 +3283,9 @@ void CodeGenFunction::EmitCallArgs( auto MaybeEmitImplicitObjectSize = [&](unsigned I, const Expr *Arg, RValue EmittedArg) { -if (CalleeDecl == nullptr || I >= CalleeDecl->getNumParams()) +if (!AC.hasFunctionDecl() || I >= AC.getNumParams()) return; -auto *PS = CalleeDecl->getParamDecl(I)->getAttr(); +auto *PS = AC.getParamDecl(I)->getAttr(); if (PS == nullptr) return; @@ -3328,7 +3327,7 @@ void CodeGenFunction::EmitCallArgs( "The code below depends on only adding one arg per EmitCallArg"); (void)InitialArgSize; RValue RVArg = Args.back().RV; -EmitNonNullArgCheck(RVArg, ArgTypes[Idx], (*Arg)->getExprLoc(), CalleeDecl, +EmitNonNullArgCheck(RVArg, ArgTypes[Idx], (*Arg)->getExprLoc(), AC, ParamsToSkip + Idx); // @llvm.objectsize should never have side-effects and shouldn't need // destruction/cleanups, so we can safely "emit" it after its arg, Modified: cfe/trunk/lib/CodeGen/CGExprCXX.cpp URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CGExprCXX.cpp?rev=296996&r1=296995&r2=296996&view=diff == --- cfe/trunk/lib/CodeGen/CGExprCXX.cpp (original) +++ cfe/trunk/lib/CodeGen/CGExprCXX.cpp Sun Mar 5 23:28:22 2017 @@ -1579,7 +1579,7 @@ llvm::Value *CodeGenFunction::EmitCXXNew // FIXME: Why do we not pass a CalleeDecl here? EmitCallArgs(allocatorArgs, allocatorType, E->placement_arguments(), - /*CalleeDecl*/nullptr, /*ParamsToSkip*/ParamsToSkip); + /*AC*/AbstractCallee(), /*ParamsToSkip*/ParamsToSkip); RValue RV = EmitNewDeleteCall(*this, allocator, allocatorType, allocatorArgs); Modified: cfe/trunk/lib/CodeGen/CGObjC.cpp URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CGObjC.cpp?rev=296996&r1=296995&r2=296996&view=diff == --- cfe/trunk/lib/CodeGen/CGObjC.cpp (original) +++ cfe/trunk/lib/CodeGen/CGObjC.cpp Sun Mar 5 23:28:22 2017 @@ -427,7 +427,7 @@ RValue CodeGenFunction::EmitObjCMessageE QualType ResultType = method ? method->getReturnType() : E->getType(); CallArgList Args; - EmitCallArgs(Args, method, E->arguments()); + EmitCallArgs(Args, method, E->arguments(), /*AC*/AbstractCallee(method)); // For delegate init calls in ARC, do an unsafe store of null into // self. Th
[PATCH] D30174: [Sema][ObjC] Warn about 'performSelector' calls with selectors that return record types
ahatanak accepted this revision. ahatanak added a comment. This revision is now accepted and ready to land. Looks good, thanks! Repository: rL LLVM https://reviews.llvm.org/D30174 ___ cfe-commits mailing list cfe-commits@lists.llvm.org http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
r296999 - [XRay] [clang] Allow logging the first argument of a function call.
Author: dberris Date: Mon Mar 6 01:08:21 2017 New Revision: 296999 URL: http://llvm.org/viewvc/llvm-project?rev=296999&view=rev Log: [XRay] [clang] Allow logging the first argument of a function call. Summary: Functions with the "xray_log_args" attribute will tell LLVM to emit a special XRay sled for compiler-rt to copy any call arguments to your logging handler. Reviewers: dberris Reviewed By: dberris Subscribers: cfe-commits Differential Revision: https://reviews.llvm.org/D29704 Added: cfe/trunk/test/CodeGen/xray-log-args.cpp cfe/trunk/test/Sema/xray-log-args-oob.c cfe/trunk/test/Sema/xray-log-args-oob.cpp Modified: cfe/trunk/include/clang/Basic/Attr.td cfe/trunk/include/clang/Basic/AttrDocs.td cfe/trunk/lib/CodeGen/CodeGenFunction.cpp cfe/trunk/lib/Sema/SemaDeclAttr.cpp Modified: cfe/trunk/include/clang/Basic/Attr.td URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Basic/Attr.td?rev=296999&r1=296998&r2=296999&view=diff == --- cfe/trunk/include/clang/Basic/Attr.td (original) +++ cfe/trunk/include/clang/Basic/Attr.td Mon Mar 6 01:08:21 2017 @@ -450,6 +450,15 @@ def XRayInstrument : InheritableAttr { let Documentation = [XRayDocs]; } +def XRayLogArgs : InheritableAttr { + let Spellings = [GNU<"xray_log_args">, CXX11<"clang", "xray_log_args">]; + let Subjects = SubjectList< + [CXXMethod, ObjCMethod, Function], WarnDiag, "ExpectedFunctionOrMethod" + >; + let Args = [UnsignedArgument<"ArgumentCount">]; + let Documentation = [XRayDocs]; +} + def TLSModel : InheritableAttr { let Spellings = [GCC<"tls_model">]; let Subjects = SubjectList<[TLSVar], ErrorDiag, "ExpectedTLSVar">; Modified: cfe/trunk/include/clang/Basic/AttrDocs.td URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Basic/AttrDocs.td?rev=296999&r1=296998&r2=296999&view=diff == --- cfe/trunk/include/clang/Basic/AttrDocs.td (original) +++ cfe/trunk/include/clang/Basic/AttrDocs.td Mon Mar 6 01:08:21 2017 @@ -2862,13 +2862,15 @@ See the RenderScript_ documentation for def XRayDocs : Documentation { let Category = DocCatFunction; - let Heading = "xray_always_instrument (clang::xray_always_instrument), xray_never_instrument (clang::xray_never_instrument)"; + let Heading = "xray_always_instrument (clang::xray_always_instrument), xray_never_instrument (clang::xray_never_instrument), xray_log_args (clang::xray_log_args)"; let Content = [{ ``__attribute__((xray_always_instrument))`` or ``[[clang::xray_always_instrument]]`` is used to mark member functions (in C++), methods (in Objective C), and free functions (in C, C++, and Objective C) to be instrumented with XRay. This will cause the function to always have space at the beginning and exit points to allow for runtime patching. Conversely, ``__attribute__((xray_never_instrument))`` or ``[[clang::xray_never_instrument]]`` will inhibit the insertion of these instrumentation points. If a function has neither of these attributes, they become subject to the XRay heuristics used to determine whether a function should be instrumented or otherwise. + +``__attribute__((xray_log_args(N)))`` or ``[[clang::xray_log_args(N)]]`` is used to preserve N function arguments for the logging function. Currently, only N==1 is supported. }]; } Modified: cfe/trunk/lib/CodeGen/CodeGenFunction.cpp URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CodeGenFunction.cpp?rev=296999&r1=296998&r2=296999&view=diff == --- cfe/trunk/lib/CodeGen/CodeGenFunction.cpp (original) +++ cfe/trunk/lib/CodeGen/CodeGenFunction.cpp Mon Mar 6 01:08:21 2017 @@ -779,6 +779,10 @@ void CodeGenFunction::StartFunction(Glob Fn->addFnAttr("function-instrument", "xray-always"); if (XRayAttr->neverXRayInstrument()) Fn->addFnAttr("function-instrument", "xray-never"); + if (const auto *LogArgs = D->getAttr()) { +Fn->addFnAttr("xray-log-args", + llvm::utostr(LogArgs->getArgumentCount())); + } } else { Fn->addFnAttr( "xray-instruction-threshold", Modified: cfe/trunk/lib/Sema/SemaDeclAttr.cpp URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaDeclAttr.cpp?rev=296999&r1=296998&r2=296999&view=diff == --- cfe/trunk/lib/Sema/SemaDeclAttr.cpp (original) +++ cfe/trunk/lib/Sema/SemaDeclAttr.cpp Mon Mar 6 01:08:21 2017 @@ -4424,6 +4424,19 @@ static void handleTypeTagForDatatypeAttr Attr.getAttributeSpellingListIndex())); } +static void handleXRayLogArgsAttr(Sema &S, Decl *D, + const AttributeList &Attr) { + uint64_t ArgCount; + if (!checkFunctionOrMethodParamet
[PATCH] D29704: [XRay] [clang] Allow logging the first argument of a function call.
This revision was automatically updated to reflect the committed changes. Closed by commit rL296999: [XRay] [clang] Allow logging the first argument of a function call. (authored by dberris). Changed prior to commit: https://reviews.llvm.org/D29704?vs=90431&id=90651#toc Repository: rL LLVM https://reviews.llvm.org/D29704 Files: cfe/trunk/include/clang/Basic/Attr.td cfe/trunk/include/clang/Basic/AttrDocs.td cfe/trunk/lib/CodeGen/CodeGenFunction.cpp cfe/trunk/lib/Sema/SemaDeclAttr.cpp cfe/trunk/test/CodeGen/xray-log-args.cpp cfe/trunk/test/Sema/xray-log-args-oob.c cfe/trunk/test/Sema/xray-log-args-oob.cpp Index: cfe/trunk/include/clang/Basic/Attr.td === --- cfe/trunk/include/clang/Basic/Attr.td +++ cfe/trunk/include/clang/Basic/Attr.td @@ -450,6 +450,15 @@ let Documentation = [XRayDocs]; } +def XRayLogArgs : InheritableAttr { + let Spellings = [GNU<"xray_log_args">, CXX11<"clang", "xray_log_args">]; + let Subjects = SubjectList< + [CXXMethod, ObjCMethod, Function], WarnDiag, "ExpectedFunctionOrMethod" + >; + let Args = [UnsignedArgument<"ArgumentCount">]; + let Documentation = [XRayDocs]; +} + def TLSModel : InheritableAttr { let Spellings = [GCC<"tls_model">]; let Subjects = SubjectList<[TLSVar], ErrorDiag, "ExpectedTLSVar">; Index: cfe/trunk/include/clang/Basic/AttrDocs.td === --- cfe/trunk/include/clang/Basic/AttrDocs.td +++ cfe/trunk/include/clang/Basic/AttrDocs.td @@ -2862,13 +2862,15 @@ def XRayDocs : Documentation { let Category = DocCatFunction; - let Heading = "xray_always_instrument (clang::xray_always_instrument), xray_never_instrument (clang::xray_never_instrument)"; + let Heading = "xray_always_instrument (clang::xray_always_instrument), xray_never_instrument (clang::xray_never_instrument), xray_log_args (clang::xray_log_args)"; let Content = [{ ``__attribute__((xray_always_instrument))`` or ``[[clang::xray_always_instrument]]`` is used to mark member functions (in C++), methods (in Objective C), and free functions (in C, C++, and Objective C) to be instrumented with XRay. This will cause the function to always have space at the beginning and exit points to allow for runtime patching. Conversely, ``__attribute__((xray_never_instrument))`` or ``[[clang::xray_never_instrument]]`` will inhibit the insertion of these instrumentation points. If a function has neither of these attributes, they become subject to the XRay heuristics used to determine whether a function should be instrumented or otherwise. + +``__attribute__((xray_log_args(N)))`` or ``[[clang::xray_log_args(N)]]`` is used to preserve N function arguments for the logging function. Currently, only N==1 is supported. }]; } Index: cfe/trunk/test/Sema/xray-log-args-oob.cpp === --- cfe/trunk/test/Sema/xray-log-args-oob.cpp +++ cfe/trunk/test/Sema/xray-log-args-oob.cpp @@ -0,0 +1,9 @@ +// RUN: %clang_cc1 %s -verify -fsyntax-only -std=c++11 -x c++ +void foo [[clang::xray_log_args(1)]] (int); +struct [[clang::xray_log_args(1)]] a { int x; }; // expected-warning {{'xray_log_args' attribute only applies to functions and methods}} + +void fop [[clang::xray_log_args(1)]] (); // expected-error {{'xray_log_args' attribute parameter 1 is out of bounds}} + +void foq [[clang::xray_log_args(-1)]] (); // expected-error {{'xray_log_args' attribute parameter 1 is out of bounds}} + +void fos [[clang::xray_log_args(0)]] (); // expected-error {{'xray_log_args' attribute parameter 1 is out of bounds}} Index: cfe/trunk/test/Sema/xray-log-args-oob.c === --- cfe/trunk/test/Sema/xray-log-args-oob.c +++ cfe/trunk/test/Sema/xray-log-args-oob.c @@ -0,0 +1,9 @@ +// RUN: %clang_cc1 %s -verify -fsyntax-only -std=c11 +void foo(int) __attribute__((xray_log_args(1))); +struct __attribute__((xray_log_args(1))) a { int x; }; // expected-warning {{'xray_log_args' attribute only applies to functions and methods}} + +void fop() __attribute__((xray_log_args(1))); // expected-error {{'xray_log_args' attribute parameter 1 is out of bounds}} + +void foq() __attribute__((xray_log_args(-1))); // expected-error {{'xray_log_args' attribute parameter 1 is out of bounds}} + +void fos() __attribute__((xray_log_args(0))); // expected-error {{'xray_log_args' attribute parameter 1 is out of bounds}} Index: cfe/trunk/test/CodeGen/xray-log-args.cpp === --- cfe/trunk/test/CodeGen/xray-log-args.cpp +++ cfe/trunk/test/CodeGen/xray-log-args.cpp @@ -0,0 +1,13 @@ +// RUN: %clang_cc1 %s -fxray-instrument -std=c++11 -x c++ -emit-llvm -o - -triple x86_64-unknown-linux-gnu | FileCheck %s + +// Make sure that the LLVM attribute for XRay-annotated functions do show up. +[[clang::xray_always_instrument,clang::xray_log_args(1