[clang] 1fe993c - [clang][bytecode] Allocate operator new data as array (#146471)
via cfe-commits
cfe-commits at lists.llvm.org
Tue Jul 1 06:45:53 PDT 2025
Author: Timm Baeder
Date: 2025-07-01T15:45:50+02:00
New Revision: 1fe993c251966697d75123eb38fa710cdb346c8d
URL: https://github.com/llvm/llvm-project/commit/1fe993c251966697d75123eb38fa710cdb346c8d
DIFF: https://github.com/llvm/llvm-project/commit/1fe993c251966697d75123eb38fa710cdb346c8d.diff
LOG: [clang][bytecode] Allocate operator new data as array (#146471)
Even if we only allocate one element, we still need to allocate it as a
single-element array. This matches what the current interpreter does.
Added:
Modified:
clang/lib/AST/ByteCode/InterpBuiltin.cpp
clang/lib/AST/ByteCode/Pointer.cpp
Removed:
################################################################################
diff --git a/clang/lib/AST/ByteCode/InterpBuiltin.cpp b/clang/lib/AST/ByteCode/InterpBuiltin.cpp
index 5c49e13a581e2..a73fc6c7bf2b3 100644
--- a/clang/lib/AST/ByteCode/InterpBuiltin.cpp
+++ b/clang/lib/AST/ByteCode/InterpBuiltin.cpp
@@ -1531,34 +1531,21 @@ static bool interp__builtin_operator_new(InterpState &S, CodePtr OpPC,
std::optional<PrimType> ElemT = S.getContext().classify(ElemType);
DynamicAllocator &Allocator = S.getAllocator();
if (ElemT) {
- if (IsArray) {
- Block *B = Allocator.allocate(NewCall, *ElemT, NumElems.getZExtValue(),
- S.Ctx.getEvalID(),
- DynamicAllocator::Form::Operator);
- assert(B);
- S.Stk.push<Pointer>(Pointer(B).atIndex(0));
- return true;
- }
-
- const Descriptor *Desc = S.P.createDescriptor(
- NewCall, *ElemT, ElemType.getTypePtr(), Descriptor::InlineDescMD,
- /*IsConst=*/false, /*IsTemporary=*/false,
- /*IsMutable=*/false);
- Block *B = Allocator.allocate(Desc, S.getContext().getEvalID(),
- DynamicAllocator::Form::Operator);
+ Block *B =
+ Allocator.allocate(NewCall, *ElemT, NumElems.getZExtValue(),
+ S.Ctx.getEvalID(), DynamicAllocator::Form::Operator);
assert(B);
-
- S.Stk.push<Pointer>(B);
+ S.Stk.push<Pointer>(Pointer(B).atIndex(0));
return true;
}
assert(!ElemT);
- // Structs etc.
- const Descriptor *Desc =
- S.P.createDescriptor(NewCall, ElemType.getTypePtr(),
- IsArray ? std::nullopt : Descriptor::InlineDescMD);
+ // Composite arrays
if (IsArray) {
+ const Descriptor *Desc =
+ S.P.createDescriptor(NewCall, ElemType.getTypePtr(),
+ IsArray ? std::nullopt : Descriptor::InlineDescMD);
Block *B =
Allocator.allocate(Desc, NumElems.getZExtValue(), S.Ctx.getEvalID(),
DynamicAllocator::Form::Operator);
@@ -1567,10 +1554,17 @@ static bool interp__builtin_operator_new(InterpState &S, CodePtr OpPC,
return true;
}
+ // Records. Still allocate them as single-element arrays.
+ QualType AllocType = S.getASTContext().getConstantArrayType(
+ ElemType, NumElems, nullptr, ArraySizeModifier::Normal, 0);
+
+ const Descriptor *Desc =
+ S.P.createDescriptor(NewCall, AllocType.getTypePtr(),
+ IsArray ? std::nullopt : Descriptor::InlineDescMD);
Block *B = Allocator.allocate(Desc, S.getContext().getEvalID(),
DynamicAllocator::Form::Operator);
assert(B);
- S.Stk.push<Pointer>(B);
+ S.Stk.push<Pointer>(Pointer(B).atIndex(0));
return true;
}
diff --git a/clang/lib/AST/ByteCode/Pointer.cpp b/clang/lib/AST/ByteCode/Pointer.cpp
index f0b0384f32ac8..0ad47645d39cc 100644
--- a/clang/lib/AST/ByteCode/Pointer.cpp
+++ b/clang/lib/AST/ByteCode/Pointer.cpp
@@ -176,19 +176,8 @@ APValue Pointer::toAPValue(const ASTContext &ASTCtx) const {
if (const auto *VD = Desc->asValueDecl())
Base = VD;
else if (const auto *E = Desc->asExpr()) {
- // Create a DynamicAlloc base of the right type.
- if (const auto *NewExpr = dyn_cast<CXXNewExpr>(E)) {
- QualType AllocatedType;
- if (NewExpr->isArray()) {
- assert(Desc->isArray());
- APInt ArraySize(64, static_cast<uint64_t>(Desc->getNumElems()),
- /*IsSigned=*/false);
- AllocatedType =
- ASTCtx.getConstantArrayType(NewExpr->getAllocatedType(), ArraySize,
- nullptr, ArraySizeModifier::Normal, 0);
- } else {
- AllocatedType = NewExpr->getAllocatedType();
- }
+ if (block()->isDynamic()) {
+ QualType AllocatedType = getDeclPtr().getFieldDesc()->getDataType(ASTCtx);
// FIXME: Suboptimal counting of dynamic allocations. Move this to Context
// or InterpState?
static int ReportedDynamicAllocs = 0;
More information about the cfe-commits
mailing list