@@ -171,12 +171,6 @@ class MatchDescendantVisitor
171
171
return VisitorBase::TraverseCXXTypeidExpr (Node);
172
172
}
173
173
174
- bool TraverseCXXDefaultInitExpr (CXXDefaultInitExpr *Node) {
175
- if (!TraverseStmt (Node->getExpr ()))
176
- return false ;
177
- return VisitorBase::TraverseCXXDefaultInitExpr (Node);
178
- }
179
-
180
174
bool TraverseStmt (Stmt *Node, DataRecursionQueue *Queue = nullptr ) {
181
175
if (!Node)
182
176
return true ;
@@ -1998,18 +1992,14 @@ class DerefSimplePtrArithFixableGadget : public FixableGadget {
1998
1992
};
1999
1993
2000
1994
// / Scan the function and return a list of gadgets found with provided kits.
2001
- static void findGadgets (const Stmt *S, ASTContext &Ctx,
2002
- const UnsafeBufferUsageHandler &Handler,
2003
- bool EmitSuggestions, FixableGadgetList &FixableGadgets,
2004
- WarningGadgetList &WarningGadgets,
2005
- DeclUseTracker &Tracker) {
1995
+ static std::tuple<FixableGadgetList, WarningGadgetList, DeclUseTracker>
1996
+ findGadgets (const Decl *D, const UnsafeBufferUsageHandler &Handler,
1997
+ bool EmitSuggestions) {
2006
1998
2007
1999
struct GadgetFinderCallback : MatchFinder::MatchCallback {
2008
- GadgetFinderCallback (FixableGadgetList &FixableGadgets,
2009
- WarningGadgetList &WarningGadgets,
2010
- DeclUseTracker &Tracker)
2011
- : FixableGadgets(FixableGadgets), WarningGadgets(WarningGadgets),
2012
- Tracker (Tracker) {}
2000
+ FixableGadgetList FixableGadgets;
2001
+ WarningGadgetList WarningGadgets;
2002
+ DeclUseTracker Tracker;
2013
2003
2014
2004
void run (const MatchFinder::MatchResult &Result) override {
2015
2005
// In debug mode, assert that we've found exactly one gadget.
@@ -2050,14 +2040,10 @@ static void findGadgets(const Stmt *S, ASTContext &Ctx,
2050
2040
assert (numFound >= 1 && " Gadgets not found in match result!" );
2051
2041
assert (numFound <= 1 && " Conflicting bind tags in gadgets!" );
2052
2042
}
2053
-
2054
- FixableGadgetList &FixableGadgets;
2055
- WarningGadgetList &WarningGadgets;
2056
- DeclUseTracker &Tracker;
2057
2043
};
2058
2044
2059
2045
MatchFinder M;
2060
- GadgetFinderCallback CB{FixableGadgets, WarningGadgets, Tracker} ;
2046
+ GadgetFinderCallback CB;
2061
2047
2062
2048
// clang-format off
2063
2049
M.addMatcher (
@@ -2102,7 +2088,9 @@ static void findGadgets(const Stmt *S, ASTContext &Ctx,
2102
2088
// clang-format on
2103
2089
}
2104
2090
2105
- M.match(*S, Ctx);
2091
+ M.match (*D->getBody (), D->getASTContext ());
2092
+ return {std::move (CB.FixableGadgets ), std::move (CB.WarningGadgets ),
2093
+ std::move (CB.Tracker )};
2106
2094
}
2107
2095
2108
2096
// Compares AST nodes by source locations.
@@ -3646,9 +3634,39 @@ class VariableGroupsManagerImpl : public VariableGroupsManager {
3646
3634
}
3647
3635
};
3648
3636
3649
- void applyGadgets (const Decl *D, FixableGadgetList FixableGadgets,
3650
- WarningGadgetList WarningGadgets, DeclUseTracker Tracker,
3651
- UnsafeBufferUsageHandler &Handler, bool EmitSuggestions) {
3637
+ void clang::checkUnsafeBufferUsage (const Decl *D,
3638
+ UnsafeBufferUsageHandler &Handler,
3639
+ bool EmitSuggestions) {
3640
+ #ifndef NDEBUG
3641
+ Handler.clearDebugNotes ();
3642
+ #endif
3643
+
3644
+ assert (D && D->getBody ());
3645
+ // We do not want to visit a Lambda expression defined inside a method
3646
+ // independently. Instead, it should be visited along with the outer method.
3647
+ // FIXME: do we want to do the same thing for `BlockDecl`s?
3648
+ if (const auto *fd = dyn_cast<CXXMethodDecl>(D)) {
3649
+ if (fd->getParent ()->isLambda () && fd->getParent ()->isLocalClass ())
3650
+ return ;
3651
+ }
3652
+
3653
+ // Do not emit fixit suggestions for functions declared in an
3654
+ // extern "C" block.
3655
+ if (const auto *FD = dyn_cast<FunctionDecl>(D)) {
3656
+ for (FunctionDecl *FReDecl : FD->redecls ()) {
3657
+ if (FReDecl->isExternC ()) {
3658
+ EmitSuggestions = false ;
3659
+ break ;
3660
+ }
3661
+ }
3662
+ }
3663
+
3664
+ WarningGadgetSets UnsafeOps;
3665
+ FixableGadgetSets FixablesForAllVars;
3666
+
3667
+ auto [FixableGadgets, WarningGadgets, Tracker] =
3668
+ findGadgets (D, Handler, EmitSuggestions);
3669
+
3652
3670
if (!EmitSuggestions) {
3653
3671
// Our job is very easy without suggestions. Just warn about
3654
3672
// every problematic operation and consider it done. No need to deal
@@ -3692,10 +3710,8 @@ void applyGadgets(const Decl *D, FixableGadgetList FixableGadgets,
3692
3710
if (WarningGadgets.empty ())
3693
3711
return ;
3694
3712
3695
- WarningGadgetSets UnsafeOps =
3696
- groupWarningGadgetsByVar (std::move (WarningGadgets));
3697
- FixableGadgetSets FixablesForAllVars =
3698
- groupFixablesByVar (std::move (FixableGadgets));
3713
+ UnsafeOps = groupWarningGadgetsByVar (std::move (WarningGadgets));
3714
+ FixablesForAllVars = groupFixablesByVar (std::move (FixableGadgets));
3699
3715
3700
3716
std::map<const VarDecl *, FixItList> FixItsForVariableGroup;
3701
3717
@@ -3916,56 +3932,3 @@ void applyGadgets(const Decl *D, FixableGadgetList FixableGadgets,
3916
3932
}
3917
3933
}
3918
3934
}
3919
-
3920
- void clang::checkUnsafeBufferUsage (const Decl *D,
3921
- UnsafeBufferUsageHandler &Handler,
3922
- bool EmitSuggestions) {
3923
- #ifndef NDEBUG
3924
- Handler.clearDebugNotes ();
3925
- #endif
3926
-
3927
- assert (D);
3928
-
3929
- SmallVector<Stmt *> Stmts;
3930
-
3931
- if (const auto *FD = dyn_cast<FunctionDecl>(D)) {
3932
- // We do not want to visit a Lambda expression defined inside a method
3933
- // independently. Instead, it should be visited along with the outer method.
3934
- // FIXME: do we want to do the same thing for `BlockDecl`s?
3935
- if (const auto *MD = dyn_cast<CXXMethodDecl>(D)) {
3936
- if (MD->getParent ()->isLambda () && MD->getParent ()->isLocalClass ())
3937
- return ;
3938
- }
3939
-
3940
- for (FunctionDecl *FReDecl : FD->redecls ()) {
3941
- if (FReDecl->isExternC ()) {
3942
- // Do not emit fixit suggestions for functions declared in an
3943
- // extern "C" block.
3944
- EmitSuggestions = false ;
3945
- break ;
3946
- }
3947
- }
3948
-
3949
- Stmts.push_back (FD->getBody ());
3950
-
3951
- if (const auto *ID = dyn_cast<CXXConstructorDecl>(D)) {
3952
- for (const CXXCtorInitializer *CI : ID->inits ()) {
3953
- Stmts.push_back (CI->getInit ());
3954
- }
3955
- }
3956
- } else if (isa<BlockDecl>(D) || isa<ObjCMethodDecl>(D)) {
3957
- Stmts.push_back (D->getBody ());
3958
- }
3959
-
3960
- assert (!Stmts.empty ());
3961
-
3962
- FixableGadgetList FixableGadgets;
3963
- WarningGadgetList WarningGadgets;
3964
- DeclUseTracker Tracker;
3965
- for (Stmt *S : Stmts) {
3966
- findGadgets (S, D->getASTContext (), Handler, EmitSuggestions, FixableGadgets,
3967
- WarningGadgets, Tracker);
3968
- }
3969
- applyGadgets (D, std::move (FixableGadgets), std::move (WarningGadgets),
3970
- std::move (Tracker), Handler, EmitSuggestions);
3971
- }
0 commit comments