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; _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits