[clang] [clang] Fix a use-after-free in expression evaluation (PR #118480)

2025-04-24 Thread kadir çetinkaya via cfe-commits

https://github.com/kadircet updated 
https://github.com/llvm/llvm-project/pull/118480

From 9a3ddb6ca0805f238042f0b795de93066f386e08 Mon Sep 17 00:00:00 2001
From: Kadir Cetinkaya 
Date: Tue, 3 Dec 2024 11:21:44 +0100
Subject: [PATCH] [clang] Fix a use-after-free in expression evaluation

following ASAN failure is fixed with this patch.
We store cleanups in EvalInfo, which are usually run with certain
ScopeRAII objects.
We can have temporaries in the cleanup stack, backed by CallStackFrame.
If such temporaries aren't destroyed before the enclosing
CallStackFrame, we end up accessing the freed temporary to run the
cleanup.

```
=
==553356==ERROR: AddressSanitizer: heap-use-after-free on address 
0x7c63f05a65b0 at pc 0x561e4add6ae7 bp 0x7fff430f7770 sp 0x7fff430f7768
READ of size 4 at 0x7c63f05a65b0 thread T0
#0 0x561e4add6ae6 in clang::APValue::operator=(clang::APValue&&) 
third_party/llvm/llvm-project/clang/lib/AST/APValue.cpp:394:9
#1 0x561e4b41fd0b in (anonymous namespace)::Cleanup::endLifetime((anonymous 
namespace)::EvalInfo&, bool) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:749:27
#2 0x561e4b4d42a7 in (anonymous namespace)::ScopeRAII<((anonymous 
namespace)::ScopeKind)1>::cleanup((anonymous namespace)::EvalInfo&, bool, 
unsigned int) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:1449:41
#3 0x561e4b4246ec in destroy 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:1427:17
#4 0x561e4b4246ec in ~ScopeRAII 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:1433:9
#5 0x561e4b4246ec in EvaluateCond((anonymous namespace)::EvalInfo&, 
clang::VarDecl const*, clang::Expr const*, bool&) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:5185:1
#6 0x561e4b41ea8c in EvaluateStmt((anonymous namespace)::StmtResult&, 
(anonymous namespace)::EvalInfo&, clang::Stmt const*, clang::SwitchCase const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp::17
#7 0x561e4b423755 in EvaluateLoopBody((anonymous namespace)::StmtResult&, 
(anonymous namespace)::EvalInfo&, clang::Stmt const*, clang::SwitchCase const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:5221:24
#8 0x561e4b41d597 in EvaluateStmt((anonymous namespace)::StmtResult&, 
(anonymous namespace)::EvalInfo&, clang::Stmt const*, clang::SwitchCase const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:5635:28
#9 0x561e4b41d341 in EvaluateStmt((anonymous namespace)::StmtResult&, 
(anonymous namespace)::EvalInfo&, clang::Stmt const*, clang::SwitchCase const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:5521:28
#10 0x561e4b40113c in HandleFunctionCall(clang::SourceLocation, 
clang::FunctionDecl const*, (anonymous namespace)::LValue const*, clang::Expr 
const*, llvm::ArrayRef, (anonymous namespace)::CallRef, 
clang::Stmt const*, (anonymous namespace)::EvalInfo&, clang::APValue&, 
(anonymous namespace)::LValue const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:6520:24
#11 0x561e4b4c9652 in handleCallExpr 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:8332:10
#12 0x561e4b4c9652 in VisitCallExpr 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:8132:10
#13 0x561e4b4c9652 in visitNonBuiltinCallExpr 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:9749:28
#14 0x561e4b4c9652 in (anonymous 
namespace)::PointerExprEvaluator::VisitCallExpr(clang::CallExpr const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:9763:12
#15 0x561e4b4c3e5b in clang::StmtVisitorBase::Visit(clang::Stmt const*) 
blaze-out/k8-opt-asan/genfiles/third_party/llvm/llvm-project/clang/include/clang/AST/StmtNodes.inc
#16 0x561e4b3ff820 in EvaluatePointer 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:9458:60
#17 0x561e4b3ff820 in Evaluate(clang::APValue&, (anonymous 
namespace)::EvalInfo&, clang::Expr const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:16343:10
#18 0x561e4b41f204 in EvaluateStmt((anonymous namespace)::StmtResult&, 
(anonymous namespace)::EvalInfo&, clang::Stmt const*, clang::SwitchCase const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:5511:17
#19 0x561e4b41d341 in EvaluateStmt((anonymous namespace)::StmtResult&, 
(anonymous namespace)::EvalInfo&, clang::Stmt const*, clang::SwitchCase const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:5521:28
#20 0x561e4b40113c in HandleFunctionCall(clang::SourceLocation, 
clang::FunctionDecl const*, (anonymous namespace)::LValue const*, clang::Expr 
const*, llvm::ArrayRef, (anonymous namespace)::CallRef, 
clang::Stmt const*, (anonymous namespace)::EvalInfo&, clang::APValue&, 
(anonymous namespace)::LValue const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:6520:24
#21 0x561e4b4c9652 in handleCallExpr 
third_party/llvm/ll

[clang] [clang] Fix a use-after-free in expression evaluation (PR #118480)

2025-04-24 Thread kadir çetinkaya via cfe-commits

https://github.com/kadircet closed 
https://github.com/llvm/llvm-project/pull/118480
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] Fix a use-after-free in expression evaluation (PR #118480)

2025-04-24 Thread Aaron Ballman via cfe-commits

AaronBallman wrote:

Thanks! You're right, it may not address the issue we were seeing. Some of our 
were also ending up with:
```
==3187048==WARNING: MemorySanitizer: use-of-uninitialized-value
#0 0x1f73c115 in clang::APValue::operator=(clang::APValue&&) 
(/netbatch/donb2642835_00/runDir/dir/workspace/NIT/xmain/LX/xmainefi2linux_msan/ws/icsws/builds/xmainefi2linux_sprodusingprod/llvm/bin/clang-21+0x1f73c115)
```


https://github.com/llvm/llvm-project/pull/118480
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] Fix a use-after-free in expression evaluation (PR #118480)

2025-04-24 Thread kadir çetinkaya via cfe-commits

kadircet wrote:

Put together a new fix based on the discussions here in 
https://github.com/llvm/llvm-project/pull/137163, PTAL.

@AaronBallman I am afraid this might no longer fix the crashes you're seeing 
internally though, as the new fix is focused on handling of 
`CompoundLiteralExpr`s, whereas the failures you mentioned seem to involve 
different C++ constructs.

https://github.com/llvm/llvm-project/pull/118480
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] Fix a use-after-free in expression evaluation (PR #118480)

2025-04-23 Thread Ilya Biryukov via cfe-commits

ilya-biryukov wrote:

@kadircet and I have spent some time on this. 

The `LValueExprEvaluator` decides to "defer" the evaluation of compound 
literals to conversions, but does this in a way that assumes the evaluation 
happens inside the same expression.
https://github.com/llvm/llvm-project/blob/6c561604336497cbeebc90f9066a9f474458a38d/clang/lib/AST/ExprConstant.cpp#L9127

When we end up storing this resulting `LValue` anywhere (e.g. inside the value 
of a global `VarDecl`), we simply store a pointer to this expression inside the 
initializer.

Then the following code sees the expression in various random contexts it 
didn't belong to (e.g. when calling a constructor that happens to use the 
global variable)
https://github.com/llvm/llvm-project/blob/6c561604336497cbeebc90f9066a9f474458a38d/clang/lib/AST/ExprConstant.cpp#L4585

We feel that the right fix would be to instead create a proper l-value with the 
right lifetime (either static or block scope, depending the rules for the 
compound literals) and remove the "defering" logic altogether. @kadircet is 
preparing the fix.

This should be enough to fix the crash and properly evaluate the compound 
literals, but probably won't address the FIXMEs mentioned above.

@AaronBallman thanks for the pointers, they were really helpful to figure this 
out.

https://github.com/llvm/llvm-project/pull/118480
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] Fix a use-after-free in expression evaluation (PR #118480)

2025-04-22 Thread Aaron Ballman via cfe-commits

AaronBallman wrote:

> @kadircet let's team up tomorrow and poke at what's happening with the 
> smaller reproducer to figure out if this is the right fix?
> 
> @AaronBallman I was initially concerned that it would be incorrect to 
> consider the compound literal expression a full expression even if it fixes 
> the crash. After re-reading the code now, I'm not sure how to properly test 
> that as C++ does not have those (right?) and so I'd probably spend some time 
> poking at GCC and Clang's codegen to see if they exhibit the signs of full 
> expressions.
> 
> If you feel this fix is correct (or at least won't hurt too much), we can 
> definitely land this ASAP. Help with reviewing this or steering it in the 
> right direction is greatly appreciated.

In C:

> A full expression is an expression that is not part of another expression, 
> nor part of a declarator
or abstract declarator. There is also an implicit full expression in which the 
non-constant size
expressions for a variably modified type are evaluated; within that full 
expression, the evaluation of
different size expressions are unsequenced with respect to one another. There 
is a sequence point
between the evaluation of a full expression and the evaluation of the next full 
expression to be
evaluated.

So a compound literal is definitely not a full expression in C. C++'s rules are 
similar: https://eel.is/c++draft/intro.execution#5

What's more, in C, it produces an lvalue whose lifetime is that of the block 
which contains it whereas in C++ it creates a prvalue... most of the time. 
There are a pile of FIXMEs around here:
```
  // In C, compound literals are l-values for some reason.
  // For GCC compatibility, in C++, file-scope array compound literals with
  // constant initializers are also l-values, and compound literals are
  // otherwise prvalues.
  //
  // (GCC also treats C++ list-initialized file-scope array prvalues with
  // constant initializers as l-values, but that's non-conforming, so we don't
  // follow it there.)
  //
  // FIXME: It would be better to handle the lvalue cases as materializing and
  // lifetime-extending a temporary object, but our materialized temporaries
  // representation only supports lifetime extension from a variable, not "out
  // of thin air".
  // FIXME: For C++, we might want to instead lifetime-extend only if a pointer
  // is bound to the result of applying array-to-pointer decay to the compound
  // literal.
  // FIXME: GCC supports compound literals of reference type, which should
  // obviously have a value kind derived from the kind of reference involved.
```
so the correct fix may very well be elsewhere.

https://github.com/llvm/llvm-project/pull/118480
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] Fix a use-after-free in expression evaluation (PR #118480)

2025-04-22 Thread Ilya Biryukov via cfe-commits

ilya-biryukov wrote:

@kadircet let's team up tomorrow and poke at what's happening with the smaller 
reproducer to figure out if this is the right fix?

@AaronBallman I was initially concerned that it would be incorrect to consider 
the compound literal expression a full expression even if it fixes the crash. 
After re-reading the code now, I'm not sure how to properly test that as C++ 
does not have those (right?) and so I'd probably spend some time poking at GCC 
and Clang's codegen to see if they exhibit the signs of full expressions.

If you feel this fix is correct (or at least won't hurt too much), we can 
definitely land this ASAP. Help with reviewing this or steering it in the right 
direction is greatly appreciated.

https://github.com/llvm/llvm-project/pull/118480
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] Fix a use-after-free in expression evaluation (PR #118480)

2025-04-17 Thread Aaron Ballman via cfe-commits

AaronBallman wrote:

> hi @AaronBallman, no unfortunately we didn't make any progress here, and I 
> just verified that reproducer from [#118480 
> (comment)](https://github.com/llvm/llvm-project/pull/118480#issuecomment-2538988006)
>  is still triggering the issue (with -std=c++20).

Internal validation testing at Intel is hitting this same problem, so we can 
also reproduce the issue. Any chance we can get this PR across the finish line?

https://github.com/llvm/llvm-project/pull/118480
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] Fix a use-after-free in expression evaluation (PR #118480)

2025-04-17 Thread kadir çetinkaya via cfe-commits

kadircet wrote:

hi @AaronBallman, no unfortunately we didn't make any progress here, and I just 
verified that reproducer from  
https://github.com/llvm/llvm-project/pull/118480#issuecomment-2538988006 is 
still triggering the issue (with -std=c++20).

https://github.com/llvm/llvm-project/pull/118480
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] Fix a use-after-free in expression evaluation (PR #118480)

2025-04-17 Thread Aaron Ballman via cfe-commits

AaronBallman wrote:

> > > ping, is this still a problem?
> > 
> > 
> > yes, this is still happening. but I am currently lacking cycles to dig 
> > deeper into expression evaluation to see if this is the right fix given the 
> > reproducer. @VitaNuo was to take a look with some limited capacity, but I 
> > think she's also in a similar situation as me :D. If anyone wants to take 
> > over/help, feel free to do so. But I'll wait for an update from @VitaNuo, 
> > in case she already made progress here.
> 
> Has there been any chance to get back into this yet?

CC @kadircet @VitaNuo 

https://github.com/llvm/llvm-project/pull/118480
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] Fix a use-after-free in expression evaluation (PR #118480)

2025-04-15 Thread Aaron Ballman via cfe-commits

AaronBallman wrote:

> > ping, is this still a problem?
> 
> yes, this is still happening. but I am currently lacking cycles to dig deeper 
> into expression evaluation to see if this is the right fix given the 
> reproducer. @VitaNuo was to take a look with some limited capacity, but I 
> think she's also in a similar situation as me :D. If anyone wants to take 
> over/help, feel free to do so. But I'll wait for an update from @VitaNuo, in 
> case she already made progress here.

Has there been any chance to get back into this yet?

https://github.com/llvm/llvm-project/pull/118480
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] Fix a use-after-free in expression evaluation (PR #118480)

2025-01-27 Thread Viktoriia Bakalova via cfe-commits

VitaNuo wrote:

> If anyone wants to take over/help, feel free to do so.

SGTM. I could reproduce the issue, but then ran out of capacity. I'm not sure 
I'll be able to prioritize this soon vs. the module-related work.


https://github.com/llvm/llvm-project/pull/118480
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] Fix a use-after-free in expression evaluation (PR #118480)

2025-01-27 Thread kadir çetinkaya via cfe-commits

kadircet wrote:

> ping, is this still a problem?

yes, this is still happening. but I am currently lacking cycles to dig deeper 
into expression evaluation to see if this is the right fix given the 
reproducer. @VitaNuo was to take a look with some limited capacity, but I think 
she's also in a similar situation as me :D. If anyone wants to take over/help, 
feel free to do so. But I'll wait for an update from @VitaNuo, in case she 
already made progress here.

https://github.com/llvm/llvm-project/pull/118480
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] Fix a use-after-free in expression evaluation (PR #118480)

2025-01-24 Thread Shafik Yaghmour via cfe-commits

shafik wrote:

ping, is this still a problem?

https://github.com/llvm/llvm-project/pull/118480
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] Fix a use-after-free in expression evaluation (PR #118480)

2025-01-16 Thread Viktoriia Bakalova via cfe-commits

VitaNuo wrote:

> need to pass -std=c++20.
> passing -DLLVM_USE_SANITIZER=Address in your cmake configuration should be 
> enough for that.

Makes sense, I could reproduce the example.

https://github.com/llvm/llvm-project/pull/118480
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] Fix a use-after-free in expression evaluation (PR #118480)

2025-01-15 Thread kadir çetinkaya via cfe-commits

kadircet wrote:

sample in 
https://github.com/llvm/llvm-project/pull/118480#issuecomment-2538988006 still 
triggers the crash for me, need to pass `-std=c++20`.
but note that it isn't the sample that should be built with ASAN, it's the 
clang itself that needs to be built with ASAN. passing 
`-DLLVM_USE_SANITIZER=Address` in your cmake configuration should be enough for 
that.

https://github.com/llvm/llvm-project/pull/118480
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] Fix a use-after-free in expression evaluation (PR #118480)

2025-01-14 Thread Viktoriia Bakalova via cfe-commits

VitaNuo wrote:

> Here's a small reprocase (thanks to cvise for getting it)

The repro doesn't compile in this shape, I've changed it to

```
template 
constexpr InputIterator find_if(InputIterator first, Predicate pred) {
  if (pred(*first))
;
  return first;
}

template 
struct basic_string_view {
  char data;
};

template 
struct Span {
  T *begin;

  constexpr Span(T* begin): begin(begin) {}
};

constexpr Span> kNames((basic_string_view[]){});

int main() {
  return !find_if(kNames.begin, [](basic_string_view) { return true; });
}
```

This compiles but doesn't crash under ASAN (neither without ASAN). 
The commands:

```
// Compile
clang -O1 -g -fsanitize=address -fno-omit-frame-pointer -c file.cc
// Link
clang -g -fsanitize=address file.o
// Run
./a.out
```

@ilya-biryukov @kadircet Can you spot any changes in the reproducer that make 
it not crash anymore?

https://github.com/llvm/llvm-project/pull/118480
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] Fix a use-after-free in expression evaluation (PR #118480)

2024-12-12 Thread Ilya Biryukov via cfe-commits

ilya-biryukov wrote:

Here's a small reprocase (thanks for cvise for getting it):

```cpp
// Run under ASAN: clang -fsyntax-only 
template 
constexpr _InputIterator find_if(_InputIterator __first, _Predicate __pred) {
  if (__pred(*__first))
;
}

template 
struct basic_string_view {
  char __data_;
};

template 
struct Span {
  T *begin;
};

constexpr Span> kNames((basic_string_view[]){});

void StripConsentJoinIfNeeded() {
  !find_if(kNames.begin, [](basic_string_view) { return true; });
}
```

Somebody would need to dig a little deeper to understand what's causing the 
crash here, but it should be manageable with this size. (I'd look at it myself, 
but probably not until next week)

https://github.com/llvm/llvm-project/pull/118480
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] Fix a use-after-free in expression evaluation (PR #118480)

2024-12-03 Thread kadir çetinkaya via cfe-commits


@@ -4515,6 +4515,8 @@ handleLValueToRValueConversion(EvalInfo &Info, const Expr 
*Conv, QualType Type,
   }
 
   APValue Lit;
+  // Make sure we clean up the temporary created below.
+  FullExpressionRAII CleanupTemps(Info);

kadircet wrote:

> we could probably construct some examples that break after this change.

fair enough, i am not sure about the change either. wanted to throw it out to 
get some more thoughts from community.

> Could we get a reduced test case?

i hope so. i am still running a creduce, file is still too big though :(

https://github.com/llvm/llvm-project/pull/118480
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] Fix a use-after-free in expression evaluation (PR #118480)

2024-12-03 Thread Ilya Biryukov via cfe-commits


@@ -4515,6 +4515,8 @@ handleLValueToRValueConversion(EvalInfo &Info, const Expr 
*Conv, QualType Type,
   }
 
   APValue Lit;
+  // Make sure we clean up the temporary created below.
+  FullExpressionRAII CleanupTemps(Info);

ilya-biryukov wrote:

Could we get a reduced test case?

I don't think it's correct to do the cleanups here, we could probably construct 
some examples that break after this change.

There are `ExprWithCleanups` and various other mechanisms that ensure we do all 
the cleanups correctly. This delayed evaluation of compound literals might not 
play well with those cases today, but it's hard to know for sure without 
understanding the full picture. Having an example would help better understand 
if there's a fix needed in a different place.

https://github.com/llvm/llvm-project/pull/118480
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] Fix a use-after-free in expression evaluation (PR #118480)

2024-12-03 Thread kadir çetinkaya via cfe-commits

kadircet wrote:

still trying to come up with a reproducer.

i am also not sure if this is the best place to have the cleanup, but if i did 
that closer to 
[leaves](https://github.com/llvm/llvm-project/blob/main/clang/lib/AST/ExprConstant.cpp#L16376-L16385)
 tests start failing. so open for suggestions here :)

https://github.com/llvm/llvm-project/pull/118480
___
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] Fix a use-after-free in expression evaluation (PR #118480)

2024-12-03 Thread via cfe-commits

llvmbot wrote:




@llvm/pr-subscribers-clang

Author: kadir çetinkaya (kadircet)


Changes

following ASAN failure is fixed with this patch.
We store cleanups in EvalInfo, which are usually run with certain
ScopeRAII objects.
We can have temporaries in the cleanup stack, backed by CallStackFrame.
If such temporaries aren't destroyed before the enclosing
CallStackFrame, we end up accessing the freed temporary to run the
cleanup.

```
=
==553356==ERROR: AddressSanitizer: heap-use-after-free on address 
0x7c63f05a65b0 at pc 0x561e4add6ae7 bp 0x7fff430f7770 sp 0x7fff430f7768
READ of size 4 at 0x7c63f05a65b0 thread T0
#0 0x561e4add6ae6 in 
clang::APValue::operator=(clang::APValue&&) 
third_party/llvm/llvm-project/clang/lib/AST/APValue.cpp:394:9
#1 0x561e4b41fd0b in (anonymous 
namespace)::Cleanup::endLifetime((anonymous namespace)::EvalInfo&, bool) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:749:27
#2 0x561e4b4d42a7 in (anonymous 
namespace)::ScopeRAII<((anonymous 
namespace)::ScopeKind)1>::cleanup((anonymous namespace)::EvalInfo&, 
bool, unsigned int) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:1449:41
#3 0x561e4b4246ec in destroy 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:1427:17
#4 0x561e4b4246ec in ~ScopeRAII 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:1433:9
#5 0x561e4b4246ec in EvaluateCond((anonymous 
namespace)::EvalInfo&, clang::VarDecl const*, clang::Expr const*, 
bool&) third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:5185:1
#6 0x561e4b41ea8c in EvaluateStmt((anonymous 
namespace)::StmtResult&, (anonymous namespace)::EvalInfo&, clang::Stmt 
const*, clang::SwitchCase const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp::17
#7 0x561e4b423755 in EvaluateLoopBody((anonymous 
namespace)::StmtResult&, (anonymous namespace)::EvalInfo&, clang::Stmt 
const*, clang::SwitchCase const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:5221:24
#8 0x561e4b41d597 in EvaluateStmt((anonymous 
namespace)::StmtResult&, (anonymous namespace)::EvalInfo&, clang::Stmt 
const*, clang::SwitchCase const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:5635:28
#9 0x561e4b41d341 in EvaluateStmt((anonymous 
namespace)::StmtResult&, (anonymous namespace)::EvalInfo&, clang::Stmt 
const*, clang::SwitchCase const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:5521:28
#10 0x561e4b40113c in HandleFunctionCall(clang::SourceLocation, 
clang::FunctionDecl const*, (anonymous namespace)::LValue const*, clang::Expr 
const*, llvm::ArrayRef, (anonymous 
namespace)::CallRef, clang::Stmt const*, (anonymous namespace)::EvalInfo&, 
clang::APValue&, (anonymous namespace)::LValue const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:6520:24
#11 0x561e4b4c9652 in handleCallExpr 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:8332:10
#12 0x561e4b4c9652 in VisitCallExpr 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:8132:10
#13 0x561e4b4c9652 in visitNonBuiltinCallExpr 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:9749:28
#14 0x561e4b4c9652 in (anonymous 
namespace)::PointerExprEvaluator::VisitCallExpr(clang::CallExpr const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:9763:12
#15 0x561e4b4c3e5b in 
clang::StmtVisitorBase::Visit(clang::Stmt const*) 
blaze-out/k8-opt-asan/genfiles/third_party/llvm/llvm-project/clang/include/clang/AST/StmtNodes.inc
#16 0x561e4b3ff820 in EvaluatePointer 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:9458:60
#17 0x561e4b3ff820 in Evaluate(clang::APValue&, (anonymous 
namespace)::EvalInfo&, clang::Expr const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:16343:10
#18 0x561e4b41f204 in EvaluateStmt((anonymous 
namespace)::StmtResult&, (anonymous namespace)::EvalInfo&, clang::Stmt 
const*, clang::SwitchCase const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:5511:17
#19 0x561e4b41d341 in EvaluateStmt((anonymous 
namespace)::StmtResult&, (anonymous namespace)::EvalInfo&, clang::Stmt 
const*, clang::SwitchCase const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:5521:28
#20 0x561e4b40113c in HandleFunctionCall(clang::SourceLocation, 
clang::FunctionDecl const*, (anonymous namespace)::LValue const*, clang::Expr 
const*, llvm::ArrayRef, (anonymous 
namespace)::CallRef, clang::Stmt const*, (anonymous namespace)::EvalInfo&, 
clang::APValue&, (anonymous namespace)::LValue const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:6520:24
#21 0x561e4b4c9652 in handleCallExpr 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:8332:10
#22 0x561e4b4c9652 i

[clang] [clang] Fix a use-after-free in expression evaluation (PR #118480)

2024-12-03 Thread kadir çetinkaya via cfe-commits

https://github.com/kadircet created 
https://github.com/llvm/llvm-project/pull/118480

following ASAN failure is fixed with this patch.
We store cleanups in EvalInfo, which are usually run with certain
ScopeRAII objects.
We can have temporaries in the cleanup stack, backed by CallStackFrame.
If such temporaries aren't destroyed before the enclosing
CallStackFrame, we end up accessing the freed temporary to run the
cleanup.

```
=
==553356==ERROR: AddressSanitizer: heap-use-after-free on address 
0x7c63f05a65b0 at pc 0x561e4add6ae7 bp 0x7fff430f7770 sp 0x7fff430f7768
READ of size 4 at 0x7c63f05a65b0 thread T0
#0 0x561e4add6ae6 in clang::APValue::operator=(clang::APValue&&) 
third_party/llvm/llvm-project/clang/lib/AST/APValue.cpp:394:9
#1 0x561e4b41fd0b in (anonymous namespace)::Cleanup::endLifetime((anonymous 
namespace)::EvalInfo&, bool) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:749:27
#2 0x561e4b4d42a7 in (anonymous namespace)::ScopeRAII<((anonymous 
namespace)::ScopeKind)1>::cleanup((anonymous namespace)::EvalInfo&, bool, 
unsigned int) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:1449:41
#3 0x561e4b4246ec in destroy 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:1427:17
#4 0x561e4b4246ec in ~ScopeRAII 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:1433:9
#5 0x561e4b4246ec in EvaluateCond((anonymous namespace)::EvalInfo&, 
clang::VarDecl const*, clang::Expr const*, bool&) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:5185:1
#6 0x561e4b41ea8c in EvaluateStmt((anonymous namespace)::StmtResult&, 
(anonymous namespace)::EvalInfo&, clang::Stmt const*, clang::SwitchCase const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp::17
#7 0x561e4b423755 in EvaluateLoopBody((anonymous namespace)::StmtResult&, 
(anonymous namespace)::EvalInfo&, clang::Stmt const*, clang::SwitchCase const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:5221:24
#8 0x561e4b41d597 in EvaluateStmt((anonymous namespace)::StmtResult&, 
(anonymous namespace)::EvalInfo&, clang::Stmt const*, clang::SwitchCase const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:5635:28
#9 0x561e4b41d341 in EvaluateStmt((anonymous namespace)::StmtResult&, 
(anonymous namespace)::EvalInfo&, clang::Stmt const*, clang::SwitchCase const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:5521:28
#10 0x561e4b40113c in HandleFunctionCall(clang::SourceLocation, 
clang::FunctionDecl const*, (anonymous namespace)::LValue const*, clang::Expr 
const*, llvm::ArrayRef, (anonymous namespace)::CallRef, 
clang::Stmt const*, (anonymous namespace)::EvalInfo&, clang::APValue&, 
(anonymous namespace)::LValue const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:6520:24
#11 0x561e4b4c9652 in handleCallExpr 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:8332:10
#12 0x561e4b4c9652 in VisitCallExpr 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:8132:10
#13 0x561e4b4c9652 in visitNonBuiltinCallExpr 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:9749:28
#14 0x561e4b4c9652 in (anonymous 
namespace)::PointerExprEvaluator::VisitCallExpr(clang::CallExpr const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:9763:12
#15 0x561e4b4c3e5b in clang::StmtVisitorBase::Visit(clang::Stmt const*) 
blaze-out/k8-opt-asan/genfiles/third_party/llvm/llvm-project/clang/include/clang/AST/StmtNodes.inc
#16 0x561e4b3ff820 in EvaluatePointer 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:9458:60
#17 0x561e4b3ff820 in Evaluate(clang::APValue&, (anonymous 
namespace)::EvalInfo&, clang::Expr const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:16343:10
#18 0x561e4b41f204 in EvaluateStmt((anonymous namespace)::StmtResult&, 
(anonymous namespace)::EvalInfo&, clang::Stmt const*, clang::SwitchCase const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:5511:17
#19 0x561e4b41d341 in EvaluateStmt((anonymous namespace)::StmtResult&, 
(anonymous namespace)::EvalInfo&, clang::Stmt const*, clang::SwitchCase const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:5521:28
#20 0x561e4b40113c in HandleFunctionCall(clang::SourceLocation, 
clang::FunctionDecl const*, (anonymous namespace)::LValue const*, clang::Expr 
const*, llvm::ArrayRef, (anonymous namespace)::CallRef, 
clang::Stmt const*, (anonymous namespace)::EvalInfo&, clang::APValue&, 
(anonymous namespace)::LValue const*) 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:6520:24
#21 0x561e4b4c9652 in handleCallExpr 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:8332:10
#22 0x561e4b4c9652 in VisitCallExpr 
third_party/llvm/llvm-project/clang/lib/AST/ExprConstant.cpp:8132:10
#23 0x561e4b4c9652 in visitNonBuiltinCa