Skip to content

Commit 8267e8c

Browse files
committed
rebase
Created using spr 1.3.4
2 parents e5af6e0 + 4d59552 commit 8267e8c

File tree

160 files changed

+11147
-15202
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

160 files changed

+11147
-15202
lines changed

.github/workflows/libclang-python-tests.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,7 @@ jobs:
3030
strategy:
3131
fail-fast: false
3232
matrix:
33-
python-version: ["3.8", "3.11"]
33+
python-version: ["3.8", "3.13"]
3434
uses: ./.github/workflows/llvm-project-tests.yml
3535
with:
3636
build_target: check-clang-python

clang-tools-extra/clang-tidy/misc/UseInternalLinkageCheck.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -52,7 +52,7 @@ AST_MATCHER(FunctionDecl, hasBody) { return Node.hasBody(); }
5252
static bool isInMainFile(SourceLocation L, SourceManager &SM,
5353
const FileExtensionsSet &HeaderFileExtensions) {
5454
for (;;) {
55-
if (utils::isSpellingLocInHeaderFile(L, SM, HeaderFileExtensions))
55+
if (utils::isExpansionLocInHeaderFile(L, SM, HeaderFileExtensions))
5656
return false;
5757
if (SM.isInMainFile(L))
5858
return true;

clang-tools-extra/docs/ReleaseNotes.rst

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -129,6 +129,10 @@ Changes in existing checks
129129
<clang-tidy/checks/misc/redundant-expression>` check by providing additional
130130
examples and fixing some macro related false positives.
131131

132+
- Improved :doc:`misc-use-internal-linkage
133+
<clang-tidy/checks/misc/use-internal-linkage>` check by fix false positives
134+
for function or variable in header file which contains macro expansion.
135+
132136
- Improved :doc:`performance/unnecessary-value-param
133137
<clang-tidy/checks/performance/unnecessary-value-param>` check performance by
134138
tolerating fix-it breaking compilation when functions is used as pointers
Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
// RUN: %check_clang_tidy %s misc-use-internal-linkage %t -- -- -I%S/Inputs/use-internal-linkage
2+
3+
#define B A##C
4+
5+
inline void B() {}

clang/lib/AST/ByteCode/ByteCodeEmitter.cpp

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -367,6 +367,16 @@ bool ByteCodeEmitter::fallthrough(const LabelTy &Label) {
367367
return true;
368368
}
369369

370+
bool ByteCodeEmitter::speculate(const CallExpr *E, const LabelTy &EndLabel) {
371+
const Expr *Arg = E->getArg(0);
372+
PrimType T = Ctx.classify(Arg->getType()).value_or(PT_Ptr);
373+
if (!this->emitBCP(getOffset(EndLabel), T, E))
374+
return false;
375+
if (!this->visit(Arg))
376+
return false;
377+
return true;
378+
}
379+
370380
//===----------------------------------------------------------------------===//
371381
// Opcode emitters
372382
//===----------------------------------------------------------------------===//

clang/lib/AST/ByteCode/ByteCodeEmitter.h

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -48,12 +48,16 @@ class ByteCodeEmitter {
4848
virtual bool visitFunc(const FunctionDecl *E) = 0;
4949
virtual bool visitExpr(const Expr *E, bool DestroyToplevelScope) = 0;
5050
virtual bool visitDeclAndReturn(const VarDecl *E, bool ConstantContext) = 0;
51+
virtual bool visit(const Expr *E) = 0;
52+
virtual bool emitBool(bool V, const Expr *E) = 0;
5153

5254
/// Emits jumps.
5355
bool jumpTrue(const LabelTy &Label);
5456
bool jumpFalse(const LabelTy &Label);
5557
bool jump(const LabelTy &Label);
5658
bool fallthrough(const LabelTy &Label);
59+
/// Speculative execution.
60+
bool speculate(const CallExpr *E, const LabelTy &EndLabel);
5761

5862
/// We're always emitting bytecode.
5963
bool isActive() const { return true; }

clang/lib/AST/ByteCode/Compiler.cpp

Lines changed: 64 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,16 @@ using APSInt = llvm::APSInt;
2525
namespace clang {
2626
namespace interp {
2727

28+
static std::optional<bool> getBoolValue(const Expr *E) {
29+
if (const auto *CE = dyn_cast_if_present<ConstantExpr>(E);
30+
CE && CE->hasAPValueResult() &&
31+
CE->getResultAPValueKind() == APValue::ValueKind::Int) {
32+
return CE->getResultAsAPSInt().getBoolValue();
33+
}
34+
35+
return std::nullopt;
36+
}
37+
2838
/// Scope used to handle temporaries in toplevel variable declarations.
2939
template <class Emitter> class DeclScope final : public LocalScope<Emitter> {
3040
public:
@@ -2286,39 +2296,49 @@ bool Compiler<Emitter>::VisitAbstractConditionalOperator(
22862296
const Expr *TrueExpr = E->getTrueExpr();
22872297
const Expr *FalseExpr = E->getFalseExpr();
22882298

2299+
auto visitChildExpr = [&](const Expr *E) -> bool {
2300+
LocalScope<Emitter> S(this);
2301+
if (!this->delegate(E))
2302+
return false;
2303+
return S.destroyLocals();
2304+
};
2305+
2306+
if (std::optional<bool> BoolValue = getBoolValue(Condition)) {
2307+
if (BoolValue)
2308+
return visitChildExpr(TrueExpr);
2309+
return visitChildExpr(FalseExpr);
2310+
}
2311+
2312+
bool IsBcpCall = false;
2313+
if (const auto *CE = dyn_cast<CallExpr>(Condition->IgnoreParenCasts());
2314+
CE && CE->getBuiltinCallee() == Builtin::BI__builtin_constant_p) {
2315+
IsBcpCall = true;
2316+
}
2317+
22892318
LabelTy LabelEnd = this->getLabel(); // Label after the operator.
22902319
LabelTy LabelFalse = this->getLabel(); // Label for the false expr.
22912320

2321+
if (IsBcpCall) {
2322+
if (!this->emitStartSpeculation(E))
2323+
return false;
2324+
}
2325+
22922326
if (!this->visitBool(Condition))
22932327
return false;
2294-
22952328
if (!this->jumpFalse(LabelFalse))
22962329
return false;
2297-
2298-
{
2299-
LocalScope<Emitter> S(this);
2300-
if (!this->delegate(TrueExpr))
2301-
return false;
2302-
if (!S.destroyLocals())
2303-
return false;
2304-
}
2305-
2330+
if (!visitChildExpr(TrueExpr))
2331+
return false;
23062332
if (!this->jump(LabelEnd))
23072333
return false;
2308-
23092334
this->emitLabel(LabelFalse);
2310-
2311-
{
2312-
LocalScope<Emitter> S(this);
2313-
if (!this->delegate(FalseExpr))
2314-
return false;
2315-
if (!S.destroyLocals())
2316-
return false;
2317-
}
2318-
2335+
if (!visitChildExpr(FalseExpr))
2336+
return false;
23192337
this->fallthrough(LabelEnd);
23202338
this->emitLabel(LabelEnd);
23212339

2340+
if (IsBcpCall)
2341+
return this->emitEndSpeculation(E);
23222342
return true;
23232343
}
23242344

@@ -4681,6 +4701,28 @@ bool Compiler<Emitter>::visitAPValueInitializer(const APValue &Val,
46814701
template <class Emitter>
46824702
bool Compiler<Emitter>::VisitBuiltinCallExpr(const CallExpr *E,
46834703
unsigned BuiltinID) {
4704+
4705+
if (BuiltinID == Builtin::BI__builtin_constant_p) {
4706+
// Void argument is always invalid and harder to handle later.
4707+
if (E->getArg(0)->getType()->isVoidType()) {
4708+
if (DiscardResult)
4709+
return true;
4710+
return this->emitConst(0, E);
4711+
}
4712+
4713+
if (!this->emitStartSpeculation(E))
4714+
return false;
4715+
LabelTy EndLabel = this->getLabel();
4716+
if (!this->speculate(E, EndLabel))
4717+
return false;
4718+
this->fallthrough(EndLabel);
4719+
if (!this->emitEndSpeculation(E))
4720+
return false;
4721+
if (DiscardResult)
4722+
return this->emitPop(classifyPrim(E), E);
4723+
return true;
4724+
}
4725+
46844726
const Function *Func = getFunction(E->getDirectCallee());
46854727
if (!Func)
46864728
return false;
@@ -5185,11 +5227,8 @@ template <class Emitter> bool Compiler<Emitter>::visitIfStmt(const IfStmt *IS) {
51855227
// stataically known to be either true or false. We could look at more cases
51865228
// here, but I think all the ones that actually happen are using a
51875229
// ConstantExpr.
5188-
if (const auto *CE = dyn_cast_if_present<ConstantExpr>(IS->getCond());
5189-
CE && CE->hasAPValueResult() &&
5190-
CE->getResultAPValueKind() == APValue::ValueKind::Int) {
5191-
APSInt Value = CE->getResultAsAPSInt();
5192-
if (Value.getBoolValue())
5230+
if (std::optional<bool> BoolValue = getBoolValue(IS->getCond())) {
5231+
if (*BoolValue)
51935232
return visitChildStmt(IS->getThen());
51945233
else if (const Stmt *Else = IS->getElse())
51955234
return visitChildStmt(Else);

clang/lib/AST/ByteCode/Compiler.h

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -274,7 +274,7 @@ class Compiler : public ConstStmtVisitor<Compiler<Emitter>, bool>,
274274
/// Evaluates an expression and places the result on the stack. If the
275275
/// expression is of composite type, a local variable will be created
276276
/// and a pointer to said variable will be placed on the stack.
277-
bool visit(const Expr *E);
277+
bool visit(const Expr *E) override;
278278
/// Compiles an initializer. This is like visit() but it will never
279279
/// create a variable and instead rely on a variable already having
280280
/// been created. visitInitializer() then relies on a pointer to this
@@ -342,6 +342,9 @@ class Compiler : public ConstStmtVisitor<Compiler<Emitter>, bool>,
342342
/// Emits an integer constant.
343343
template <typename T> bool emitConst(T Value, PrimType Ty, const Expr *E);
344344
template <typename T> bool emitConst(T Value, const Expr *E);
345+
bool emitBool(bool V, const Expr *E) override {
346+
return this->emitConst(V, E);
347+
}
345348

346349
llvm::RoundingMode getRoundingMode(const Expr *E) const {
347350
FPOptions FPO = E->getFPFeaturesInEffect(Ctx.getLangOpts());

clang/lib/AST/ByteCode/EvalEmitter.cpp

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -127,6 +127,33 @@ bool EvalEmitter::fallthrough(const LabelTy &Label) {
127127
return true;
128128
}
129129

130+
bool EvalEmitter::speculate(const CallExpr *E, const LabelTy &EndLabel) {
131+
size_t StackSizeBefore = S.Stk.size();
132+
const Expr *Arg = E->getArg(0);
133+
if (!this->visit(Arg)) {
134+
S.Stk.clearTo(StackSizeBefore);
135+
136+
if (S.inConstantContext() || Arg->HasSideEffects(S.getASTContext()))
137+
return this->emitBool(false, E);
138+
return Invalid(S, OpPC);
139+
}
140+
141+
PrimType T = Ctx.classify(Arg->getType()).value_or(PT_Ptr);
142+
if (T == PT_Ptr) {
143+
const auto &Ptr = S.Stk.pop<Pointer>();
144+
return this->emitBool(CheckBCPResult(S, Ptr), E);
145+
} else if (T == PT_FnPtr) {
146+
S.Stk.discard<FunctionPointer>();
147+
// Never accepted
148+
return this->emitBool(false, E);
149+
}
150+
151+
// Otherwise, this is fine!
152+
if (!this->emitPop(T, E))
153+
return false;
154+
return this->emitBool(true, E);
155+
}
156+
130157
template <PrimType OpType> bool EvalEmitter::emitRet(const SourceInfo &Info) {
131158
if (!isActive())
132159
return true;

clang/lib/AST/ByteCode/EvalEmitter.h

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -55,12 +55,16 @@ class EvalEmitter : public SourceMapper {
5555
virtual bool visitExpr(const Expr *E, bool DestroyToplevelScope) = 0;
5656
virtual bool visitDeclAndReturn(const VarDecl *VD, bool ConstantContext) = 0;
5757
virtual bool visitFunc(const FunctionDecl *F) = 0;
58+
virtual bool visit(const Expr *E) = 0;
59+
virtual bool emitBool(bool V, const Expr *E) = 0;
5860

5961
/// Emits jumps.
6062
bool jumpTrue(const LabelTy &Label);
6163
bool jumpFalse(const LabelTy &Label);
6264
bool jump(const LabelTy &Label);
6365
bool fallthrough(const LabelTy &Label);
66+
/// Speculative execution.
67+
bool speculate(const CallExpr *E, const LabelTy &EndLabel);
6468

6569
/// Since expressions can only jump forward, predicated execution is
6670
/// used to deal with if-else statements.

0 commit comments

Comments
 (0)