clang 20.0.0git
Compiler.cpp
Go to the documentation of this file.
1//===--- Compiler.cpp - Code generator for expressions ---*- C++ -*-===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8
9#include "Compiler.h"
10#include "ByteCodeEmitter.h"
11#include "Context.h"
12#include "Floating.h"
13#include "Function.h"
14#include "InterpShared.h"
15#include "PrimType.h"
16#include "Program.h"
17#include "clang/AST/Attr.h"
18
19using namespace clang;
20using namespace clang::interp;
21
22using APSInt = llvm::APSInt;
23
24namespace clang {
25namespace interp {
26
27/// Scope used to handle temporaries in toplevel variable declarations.
28template <class Emitter> class DeclScope final : public LocalScope<Emitter> {
29public:
31 : LocalScope<Emitter>(Ctx, VD), Scope(Ctx->P, VD),
32 OldInitializingDecl(Ctx->InitializingDecl) {
33 Ctx->InitializingDecl = VD;
34 Ctx->InitStack.push_back(InitLink::Decl(VD));
35 }
36
37 void addExtended(const Scope::Local &Local) override {
38 return this->addLocal(Local);
39 }
40
42 this->Ctx->InitializingDecl = OldInitializingDecl;
43 this->Ctx->InitStack.pop_back();
44 }
45
46private:
48 const ValueDecl *OldInitializingDecl;
49};
50
51/// Scope used to handle initialization methods.
52template <class Emitter> class OptionScope final {
53public:
54 /// Root constructor, compiling or discarding primitives.
55 OptionScope(Compiler<Emitter> *Ctx, bool NewDiscardResult,
56 bool NewInitializing)
57 : Ctx(Ctx), OldDiscardResult(Ctx->DiscardResult),
58 OldInitializing(Ctx->Initializing) {
59 Ctx->DiscardResult = NewDiscardResult;
60 Ctx->Initializing = NewInitializing;
61 }
62
64 Ctx->DiscardResult = OldDiscardResult;
65 Ctx->Initializing = OldInitializing;
66 }
67
68private:
69 /// Parent context.
71 /// Old discard flag to restore.
72 bool OldDiscardResult;
73 bool OldInitializing;
74};
75
76template <class Emitter>
77bool InitLink::emit(Compiler<Emitter> *Ctx, const Expr *E) const {
78 switch (Kind) {
79 case K_This:
80 return Ctx->emitThis(E);
81 case K_Field:
82 // We're assuming there's a base pointer on the stack already.
83 return Ctx->emitGetPtrFieldPop(Offset, E);
84 case K_Temp:
85 return Ctx->emitGetPtrLocal(Offset, E);
86 case K_Decl:
87 return Ctx->visitDeclRef(D, E);
88 case K_Elem:
89 if (!Ctx->emitConstUint32(Offset, E))
90 return false;
91 return Ctx->emitArrayElemPtrPopUint32(E);
92 default:
93 llvm_unreachable("Unhandled InitLink kind");
94 }
95 return true;
96}
97
98/// Scope managing label targets.
99template <class Emitter> class LabelScope {
100public:
101 virtual ~LabelScope() {}
102
103protected:
105 /// Compiler instance.
107};
108
109/// Sets the context for break/continue statements.
110template <class Emitter> class LoopScope final : public LabelScope<Emitter> {
111public:
114
115 LoopScope(Compiler<Emitter> *Ctx, LabelTy BreakLabel, LabelTy ContinueLabel)
116 : LabelScope<Emitter>(Ctx), OldBreakLabel(Ctx->BreakLabel),
117 OldContinueLabel(Ctx->ContinueLabel) {
118 this->Ctx->BreakLabel = BreakLabel;
119 this->Ctx->ContinueLabel = ContinueLabel;
120 }
121
123 this->Ctx->BreakLabel = OldBreakLabel;
124 this->Ctx->ContinueLabel = OldContinueLabel;
125 }
126
127private:
128 OptLabelTy OldBreakLabel;
129 OptLabelTy OldContinueLabel;
130};
131
132// Sets the context for a switch scope, mapping labels.
133template <class Emitter> class SwitchScope final : public LabelScope<Emitter> {
134public:
138
139 SwitchScope(Compiler<Emitter> *Ctx, CaseMap &&CaseLabels, LabelTy BreakLabel,
140 OptLabelTy DefaultLabel)
141 : LabelScope<Emitter>(Ctx), OldBreakLabel(Ctx->BreakLabel),
142 OldDefaultLabel(this->Ctx->DefaultLabel),
143 OldCaseLabels(std::move(this->Ctx->CaseLabels)) {
144 this->Ctx->BreakLabel = BreakLabel;
145 this->Ctx->DefaultLabel = DefaultLabel;
146 this->Ctx->CaseLabels = std::move(CaseLabels);
147 }
148
150 this->Ctx->BreakLabel = OldBreakLabel;
151 this->Ctx->DefaultLabel = OldDefaultLabel;
152 this->Ctx->CaseLabels = std::move(OldCaseLabels);
153 }
154
155private:
156 OptLabelTy OldBreakLabel;
157 OptLabelTy OldDefaultLabel;
158 CaseMap OldCaseLabels;
159};
160
161template <class Emitter> class StmtExprScope final {
162public:
163 StmtExprScope(Compiler<Emitter> *Ctx) : Ctx(Ctx), OldFlag(Ctx->InStmtExpr) {
164 Ctx->InStmtExpr = true;
165 }
166
167 ~StmtExprScope() { Ctx->InStmtExpr = OldFlag; }
168
169private:
171 bool OldFlag;
172};
173
174} // namespace interp
175} // namespace clang
176
177template <class Emitter>
179 const Expr *SubExpr = CE->getSubExpr();
180 switch (CE->getCastKind()) {
181
182 case CK_LValueToRValue: {
183 if (DiscardResult)
184 return this->discard(SubExpr);
185
186 std::optional<PrimType> SubExprT = classify(SubExpr->getType());
187 // Prepare storage for the result.
188 if (!Initializing && !SubExprT) {
189 std::optional<unsigned> LocalIndex = allocateLocal(SubExpr);
190 if (!LocalIndex)
191 return false;
192 if (!this->emitGetPtrLocal(*LocalIndex, CE))
193 return false;
194 }
195
196 if (!this->visit(SubExpr))
197 return false;
198
199 if (SubExprT)
200 return this->emitLoadPop(*SubExprT, CE);
201
202 // If the subexpr type is not primitive, we need to perform a copy here.
203 // This happens for example in C when dereferencing a pointer of struct
204 // type.
205 return this->emitMemcpy(CE);
206 }
207
208 case CK_DerivedToBaseMemberPointer: {
209 assert(classifyPrim(CE->getType()) == PT_MemberPtr);
210 assert(classifyPrim(SubExpr->getType()) == PT_MemberPtr);
211 const auto *FromMP = SubExpr->getType()->getAs<MemberPointerType>();
212 const auto *ToMP = CE->getType()->getAs<MemberPointerType>();
213
214 unsigned DerivedOffset = collectBaseOffset(QualType(ToMP->getClass(), 0),
215 QualType(FromMP->getClass(), 0));
216
217 if (!this->delegate(SubExpr))
218 return false;
219
220 return this->emitGetMemberPtrBasePop(DerivedOffset, CE);
221 }
222
223 case CK_BaseToDerivedMemberPointer: {
224 assert(classifyPrim(CE) == PT_MemberPtr);
225 assert(classifyPrim(SubExpr) == PT_MemberPtr);
226 const auto *FromMP = SubExpr->getType()->getAs<MemberPointerType>();
227 const auto *ToMP = CE->getType()->getAs<MemberPointerType>();
228
229 unsigned DerivedOffset = collectBaseOffset(QualType(FromMP->getClass(), 0),
230 QualType(ToMP->getClass(), 0));
231
232 if (!this->delegate(SubExpr))
233 return false;
234 return this->emitGetMemberPtrBasePop(-DerivedOffset, CE);
235 }
236
237 case CK_UncheckedDerivedToBase:
238 case CK_DerivedToBase: {
239 if (!this->delegate(SubExpr))
240 return false;
241
242 const auto extractRecordDecl = [](QualType Ty) -> const CXXRecordDecl * {
243 if (const auto *PT = dyn_cast<PointerType>(Ty))
244 return PT->getPointeeType()->getAsCXXRecordDecl();
245 return Ty->getAsCXXRecordDecl();
246 };
247
248 // FIXME: We can express a series of non-virtual casts as a single
249 // GetPtrBasePop op.
250 QualType CurType = SubExpr->getType();
251 for (const CXXBaseSpecifier *B : CE->path()) {
252 if (B->isVirtual()) {
253 if (!this->emitGetPtrVirtBasePop(extractRecordDecl(B->getType()), CE))
254 return false;
255 CurType = B->getType();
256 } else {
257 unsigned DerivedOffset = collectBaseOffset(B->getType(), CurType);
258 if (!this->emitGetPtrBasePop(DerivedOffset, CE))
259 return false;
260 CurType = B->getType();
261 }
262 }
263
264 return true;
265 }
266
267 case CK_BaseToDerived: {
268 if (!this->delegate(SubExpr))
269 return false;
270
271 unsigned DerivedOffset =
272 collectBaseOffset(SubExpr->getType(), CE->getType());
273
274 return this->emitGetPtrDerivedPop(DerivedOffset, CE);
275 }
276
277 case CK_FloatingCast: {
278 // HLSL uses CK_FloatingCast to cast between vectors.
279 if (!SubExpr->getType()->isFloatingType() ||
280 !CE->getType()->isFloatingType())
281 return false;
282 if (DiscardResult)
283 return this->discard(SubExpr);
284 if (!this->visit(SubExpr))
285 return false;
286 const auto *TargetSemantics = &Ctx.getFloatSemantics(CE->getType());
287 return this->emitCastFP(TargetSemantics, getRoundingMode(CE), CE);
288 }
289
290 case CK_IntegralToFloating: {
291 if (DiscardResult)
292 return this->discard(SubExpr);
293 std::optional<PrimType> FromT = classify(SubExpr->getType());
294 if (!FromT)
295 return false;
296
297 if (!this->visit(SubExpr))
298 return false;
299
300 const auto *TargetSemantics = &Ctx.getFloatSemantics(CE->getType());
301 llvm::RoundingMode RM = getRoundingMode(CE);
302 return this->emitCastIntegralFloating(*FromT, TargetSemantics, RM, CE);
303 }
304
305 case CK_FloatingToBoolean:
306 case CK_FloatingToIntegral: {
307 if (DiscardResult)
308 return this->discard(SubExpr);
309
310 std::optional<PrimType> ToT = classify(CE->getType());
311
312 if (!ToT)
313 return false;
314
315 if (!this->visit(SubExpr))
316 return false;
317
318 if (ToT == PT_IntAP)
319 return this->emitCastFloatingIntegralAP(Ctx.getBitWidth(CE->getType()),
320 CE);
321 if (ToT == PT_IntAPS)
322 return this->emitCastFloatingIntegralAPS(Ctx.getBitWidth(CE->getType()),
323 CE);
324
325 return this->emitCastFloatingIntegral(*ToT, CE);
326 }
327
328 case CK_NullToPointer:
329 case CK_NullToMemberPointer: {
330 if (!this->discard(SubExpr))
331 return false;
332 if (DiscardResult)
333 return true;
334
335 const Descriptor *Desc = nullptr;
336 const QualType PointeeType = CE->getType()->getPointeeType();
337 if (!PointeeType.isNull()) {
338 if (std::optional<PrimType> T = classify(PointeeType))
339 Desc = P.createDescriptor(SubExpr, *T);
340 else
341 Desc = P.createDescriptor(SubExpr, PointeeType.getTypePtr(),
342 std::nullopt, true, false,
343 /*IsMutable=*/false, nullptr);
344 }
345 return this->emitNull(classifyPrim(CE->getType()), Desc, CE);
346 }
347
348 case CK_PointerToIntegral: {
349 if (DiscardResult)
350 return this->discard(SubExpr);
351
352 if (!this->visit(SubExpr))
353 return false;
354
355 // If SubExpr doesn't result in a pointer, make it one.
356 if (PrimType FromT = classifyPrim(SubExpr->getType()); FromT != PT_Ptr) {
357 assert(isPtrType(FromT));
358 if (!this->emitDecayPtr(FromT, PT_Ptr, CE))
359 return false;
360 }
361
362 PrimType T = classifyPrim(CE->getType());
363 if (T == PT_IntAP)
364 return this->emitCastPointerIntegralAP(Ctx.getBitWidth(CE->getType()),
365 CE);
366 if (T == PT_IntAPS)
367 return this->emitCastPointerIntegralAPS(Ctx.getBitWidth(CE->getType()),
368 CE);
369 return this->emitCastPointerIntegral(T, CE);
370 }
371
372 case CK_ArrayToPointerDecay: {
373 if (!this->visit(SubExpr))
374 return false;
375 if (!this->emitArrayDecay(CE))
376 return false;
377 if (DiscardResult)
378 return this->emitPopPtr(CE);
379 return true;
380 }
381
382 case CK_IntegralToPointer: {
383 QualType IntType = SubExpr->getType();
384 assert(IntType->isIntegralOrEnumerationType());
385 if (!this->visit(SubExpr))
386 return false;
387 // FIXME: I think the discard is wrong since the int->ptr cast might cause a
388 // diagnostic.
389 PrimType T = classifyPrim(IntType);
390 if (DiscardResult)
391 return this->emitPop(T, CE);
392
393 QualType PtrType = CE->getType();
394 const Descriptor *Desc;
395 if (std::optional<PrimType> T = classify(PtrType->getPointeeType()))
396 Desc = P.createDescriptor(SubExpr, *T);
397 else if (PtrType->getPointeeType()->isVoidType())
398 Desc = nullptr;
399 else
400 Desc = P.createDescriptor(CE, PtrType->getPointeeType().getTypePtr(),
401 Descriptor::InlineDescMD, true, false,
402 /*IsMutable=*/false, nullptr);
403
404 if (!this->emitGetIntPtr(T, Desc, CE))
405 return false;
406
407 PrimType DestPtrT = classifyPrim(PtrType);
408 if (DestPtrT == PT_Ptr)
409 return true;
410
411 // In case we're converting the integer to a non-Pointer.
412 return this->emitDecayPtr(PT_Ptr, DestPtrT, CE);
413 }
414
415 case CK_AtomicToNonAtomic:
416 case CK_ConstructorConversion:
417 case CK_FunctionToPointerDecay:
418 case CK_NonAtomicToAtomic:
419 case CK_NoOp:
420 case CK_UserDefinedConversion:
421 case CK_AddressSpaceConversion:
422 return this->delegate(SubExpr);
423
424 case CK_BitCast: {
425 // Reject bitcasts to atomic types.
426 if (CE->getType()->isAtomicType()) {
427 if (!this->discard(SubExpr))
428 return false;
429 return this->emitInvalidCast(CastKind::Reinterpret, /*Fatal=*/true, CE);
430 }
431
432 if (DiscardResult)
433 return this->discard(SubExpr);
434
435 QualType SubExprTy = SubExpr->getType();
436 std::optional<PrimType> FromT = classify(SubExprTy);
437 std::optional<PrimType> ToT = classify(CE->getType());
438 if (!FromT || !ToT)
439 return false;
440
441 assert(isPtrType(*FromT));
442 assert(isPtrType(*ToT));
443 if (FromT == ToT) {
444 if (CE->getType()->isVoidPointerType())
445 return this->delegate(SubExpr);
446
447 if (!this->visit(SubExpr))
448 return false;
449 if (FromT == PT_Ptr)
450 return this->emitPtrPtrCast(SubExprTy->isVoidPointerType(), CE);
451 return true;
452 }
453
454 if (!this->visit(SubExpr))
455 return false;
456 return this->emitDecayPtr(*FromT, *ToT, CE);
457 }
458
459 case CK_IntegralToBoolean:
460 case CK_BooleanToSignedIntegral:
461 case CK_IntegralCast: {
462 if (DiscardResult)
463 return this->discard(SubExpr);
464 std::optional<PrimType> FromT = classify(SubExpr->getType());
465 std::optional<PrimType> ToT = classify(CE->getType());
466
467 if (!FromT || !ToT)
468 return false;
469
470 if (!this->visit(SubExpr))
471 return false;
472
473 // Possibly diagnose casts to enum types if the target type does not
474 // have a fixed size.
475 if (Ctx.getLangOpts().CPlusPlus && CE->getType()->isEnumeralType()) {
476 if (const auto *ET = CE->getType().getCanonicalType()->getAs<EnumType>();
477 ET && !ET->getDecl()->isFixed()) {
478 if (!this->emitCheckEnumValue(*FromT, ET->getDecl(), CE))
479 return false;
480 }
481 }
482
483 auto maybeNegate = [&]() -> bool {
484 if (CE->getCastKind() == CK_BooleanToSignedIntegral)
485 return this->emitNeg(*ToT, CE);
486 return true;
487 };
488
489 if (ToT == PT_IntAP)
490 return this->emitCastAP(*FromT, Ctx.getBitWidth(CE->getType()), CE) &&
491 maybeNegate();
492 if (ToT == PT_IntAPS)
493 return this->emitCastAPS(*FromT, Ctx.getBitWidth(CE->getType()), CE) &&
494 maybeNegate();
495
496 if (FromT == ToT)
497 return true;
498 if (!this->emitCast(*FromT, *ToT, CE))
499 return false;
500
501 return maybeNegate();
502 }
503
504 case CK_PointerToBoolean:
505 case CK_MemberPointerToBoolean: {
506 PrimType PtrT = classifyPrim(SubExpr->getType());
507
508 // Just emit p != nullptr for this.
509 if (!this->visit(SubExpr))
510 return false;
511
512 if (!this->emitNull(PtrT, nullptr, CE))
513 return false;
514
515 return this->emitNE(PtrT, CE);
516 }
517
518 case CK_IntegralComplexToBoolean:
519 case CK_FloatingComplexToBoolean: {
520 if (DiscardResult)
521 return this->discard(SubExpr);
522 if (!this->visit(SubExpr))
523 return false;
524 return this->emitComplexBoolCast(SubExpr);
525 }
526
527 case CK_IntegralComplexToReal:
528 case CK_FloatingComplexToReal:
529 return this->emitComplexReal(SubExpr);
530
531 case CK_IntegralRealToComplex:
532 case CK_FloatingRealToComplex: {
533 // We're creating a complex value here, so we need to
534 // allocate storage for it.
535 if (!Initializing) {
536 unsigned LocalIndex = allocateTemporary(CE);
537 if (!this->emitGetPtrLocal(LocalIndex, CE))
538 return false;
539 }
540
541 // Init the complex value to {SubExpr, 0}.
542 if (!this->visitArrayElemInit(0, SubExpr))
543 return false;
544 // Zero-init the second element.
545 PrimType T = classifyPrim(SubExpr->getType());
546 if (!this->visitZeroInitializer(T, SubExpr->getType(), SubExpr))
547 return false;
548 return this->emitInitElem(T, 1, SubExpr);
549 }
550
551 case CK_IntegralComplexCast:
552 case CK_FloatingComplexCast:
553 case CK_IntegralComplexToFloatingComplex:
554 case CK_FloatingComplexToIntegralComplex: {
555 assert(CE->getType()->isAnyComplexType());
556 assert(SubExpr->getType()->isAnyComplexType());
557 if (DiscardResult)
558 return this->discard(SubExpr);
559
560 if (!Initializing) {
561 std::optional<unsigned> LocalIndex = allocateLocal(CE);
562 if (!LocalIndex)
563 return false;
564 if (!this->emitGetPtrLocal(*LocalIndex, CE))
565 return false;
566 }
567
568 // Location for the SubExpr.
569 // Since SubExpr is of complex type, visiting it results in a pointer
570 // anyway, so we just create a temporary pointer variable.
571 unsigned SubExprOffset = allocateLocalPrimitive(
572 SubExpr, PT_Ptr, /*IsConst=*/true, /*IsExtended=*/false);
573 if (!this->visit(SubExpr))
574 return false;
575 if (!this->emitSetLocal(PT_Ptr, SubExprOffset, CE))
576 return false;
577
578 PrimType SourceElemT = classifyComplexElementType(SubExpr->getType());
579 QualType DestElemType =
580 CE->getType()->getAs<ComplexType>()->getElementType();
581 PrimType DestElemT = classifyPrim(DestElemType);
582 // Cast both elements individually.
583 for (unsigned I = 0; I != 2; ++I) {
584 if (!this->emitGetLocal(PT_Ptr, SubExprOffset, CE))
585 return false;
586 if (!this->emitArrayElemPop(SourceElemT, I, CE))
587 return false;
588
589 // Do the cast.
590 if (!this->emitPrimCast(SourceElemT, DestElemT, DestElemType, CE))
591 return false;
592
593 // Save the value.
594 if (!this->emitInitElem(DestElemT, I, CE))
595 return false;
596 }
597 return true;
598 }
599
600 case CK_VectorSplat: {
601 assert(!classify(CE->getType()));
602 assert(classify(SubExpr->getType()));
603 assert(CE->getType()->isVectorType());
604
605 if (DiscardResult)
606 return this->discard(SubExpr);
607
608 if (!Initializing) {
609 std::optional<unsigned> LocalIndex = allocateLocal(CE);
610 if (!LocalIndex)
611 return false;
612 if (!this->emitGetPtrLocal(*LocalIndex, CE))
613 return false;
614 }
615
616 const auto *VT = CE->getType()->getAs<VectorType>();
617 PrimType ElemT = classifyPrim(SubExpr->getType());
618 unsigned ElemOffset = allocateLocalPrimitive(
619 SubExpr, ElemT, /*IsConst=*/true, /*IsExtended=*/false);
620
621 // Prepare a local variable for the scalar value.
622 if (!this->visit(SubExpr))
623 return false;
624 if (classifyPrim(SubExpr) == PT_Ptr && !this->emitLoadPop(ElemT, CE))
625 return false;
626
627 if (!this->emitSetLocal(ElemT, ElemOffset, CE))
628 return false;
629
630 for (unsigned I = 0; I != VT->getNumElements(); ++I) {
631 if (!this->emitGetLocal(ElemT, ElemOffset, CE))
632 return false;
633 if (!this->emitInitElem(ElemT, I, CE))
634 return false;
635 }
636
637 return true;
638 }
639
640 case CK_ToVoid:
641 return discard(SubExpr);
642
643 default:
644 return this->emitInvalid(CE);
645 }
646 llvm_unreachable("Unhandled clang::CastKind enum");
647}
648
649template <class Emitter>
651 if (DiscardResult)
652 return true;
653
654 return this->emitConst(LE->getValue(), LE);
655}
656
657template <class Emitter>
659 if (DiscardResult)
660 return true;
661
662 return this->emitConstFloat(E->getValue(), E);
663}
664
665template <class Emitter>
667 assert(E->getType()->isAnyComplexType());
668 if (DiscardResult)
669 return true;
670
671 if (!Initializing) {
672 unsigned LocalIndex = allocateTemporary(E);
673 if (!this->emitGetPtrLocal(LocalIndex, E))
674 return false;
675 }
676
677 const Expr *SubExpr = E->getSubExpr();
678 PrimType SubExprT = classifyPrim(SubExpr->getType());
679
680 if (!this->visitZeroInitializer(SubExprT, SubExpr->getType(), SubExpr))
681 return false;
682 if (!this->emitInitElem(SubExprT, 0, SubExpr))
683 return false;
684 return this->visitArrayElemInit(1, SubExpr);
685}
686
687template <class Emitter>
689 return this->delegate(E->getSubExpr());
690}
691
692template <class Emitter>
694 // Need short-circuiting for these.
695 if (BO->isLogicalOp())
696 return this->VisitLogicalBinOp(BO);
697
698 const Expr *LHS = BO->getLHS();
699 const Expr *RHS = BO->getRHS();
700
701 // Handle comma operators. Just discard the LHS
702 // and delegate to RHS.
703 if (BO->isCommaOp()) {
704 if (!this->discard(LHS))
705 return false;
706 if (RHS->getType()->isVoidType())
707 return this->discard(RHS);
708
709 return this->delegate(RHS);
710 }
711
712 if (BO->getType()->isAnyComplexType())
713 return this->VisitComplexBinOp(BO);
714 if ((LHS->getType()->isAnyComplexType() ||
715 RHS->getType()->isAnyComplexType()) &&
716 BO->isComparisonOp())
717 return this->emitComplexComparison(LHS, RHS, BO);
718
719 if (BO->isPtrMemOp()) {
720 if (!this->visit(LHS))
721 return false;
722
723 if (!this->visit(RHS))
724 return false;
725
726 if (!this->emitToMemberPtr(BO))
727 return false;
728
729 if (classifyPrim(BO) == PT_MemberPtr)
730 return true;
731
732 if (!this->emitCastMemberPtrPtr(BO))
733 return false;
734 return DiscardResult ? this->emitPopPtr(BO) : true;
735 }
736
737 // Typecheck the args.
738 std::optional<PrimType> LT = classify(LHS);
739 std::optional<PrimType> RT = classify(RHS);
740 std::optional<PrimType> T = classify(BO->getType());
741
742 // Special case for C++'s three-way/spaceship operator <=>, which
743 // returns a std::{strong,weak,partial}_ordering (which is a class, so doesn't
744 // have a PrimType).
745 if (!T && BO->getOpcode() == BO_Cmp) {
746 if (DiscardResult)
747 return true;
748 const ComparisonCategoryInfo *CmpInfo =
749 Ctx.getASTContext().CompCategories.lookupInfoForType(BO->getType());
750 assert(CmpInfo);
751
752 // We need a temporary variable holding our return value.
753 if (!Initializing) {
754 std::optional<unsigned> ResultIndex = this->allocateLocal(BO);
755 if (!this->emitGetPtrLocal(*ResultIndex, BO))
756 return false;
757 }
758
759 if (!visit(LHS) || !visit(RHS))
760 return false;
761
762 return this->emitCMP3(*LT, CmpInfo, BO);
763 }
764
765 if (!LT || !RT || !T)
766 return false;
767
768 // Pointer arithmetic special case.
769 if (BO->getOpcode() == BO_Add || BO->getOpcode() == BO_Sub) {
770 if (isPtrType(*T) || (isPtrType(*LT) && isPtrType(*RT)))
771 return this->VisitPointerArithBinOp(BO);
772 }
773
774 // Assignmentes require us to evalute the RHS first.
775 if (BO->getOpcode() == BO_Assign) {
776 if (!visit(RHS) || !visit(LHS))
777 return false;
778 if (!this->emitFlip(*LT, *RT, BO))
779 return false;
780 } else {
781 if (!visit(LHS) || !visit(RHS))
782 return false;
783 }
784
785 // For languages such as C, cast the result of one
786 // of our comparision opcodes to T (which is usually int).
787 auto MaybeCastToBool = [this, T, BO](bool Result) {
788 if (!Result)
789 return false;
790 if (DiscardResult)
791 return this->emitPop(*T, BO);
792 if (T != PT_Bool)
793 return this->emitCast(PT_Bool, *T, BO);
794 return true;
795 };
796
797 auto Discard = [this, T, BO](bool Result) {
798 if (!Result)
799 return false;
800 return DiscardResult ? this->emitPop(*T, BO) : true;
801 };
802
803 switch (BO->getOpcode()) {
804 case BO_EQ:
805 return MaybeCastToBool(this->emitEQ(*LT, BO));
806 case BO_NE:
807 return MaybeCastToBool(this->emitNE(*LT, BO));
808 case BO_LT:
809 return MaybeCastToBool(this->emitLT(*LT, BO));
810 case BO_LE:
811 return MaybeCastToBool(this->emitLE(*LT, BO));
812 case BO_GT:
813 return MaybeCastToBool(this->emitGT(*LT, BO));
814 case BO_GE:
815 return MaybeCastToBool(this->emitGE(*LT, BO));
816 case BO_Sub:
817 if (BO->getType()->isFloatingType())
818 return Discard(this->emitSubf(getRoundingMode(BO), BO));
819 return Discard(this->emitSub(*T, BO));
820 case BO_Add:
821 if (BO->getType()->isFloatingType())
822 return Discard(this->emitAddf(getRoundingMode(BO), BO));
823 return Discard(this->emitAdd(*T, BO));
824 case BO_Mul:
825 if (BO->getType()->isFloatingType())
826 return Discard(this->emitMulf(getRoundingMode(BO), BO));
827 return Discard(this->emitMul(*T, BO));
828 case BO_Rem:
829 return Discard(this->emitRem(*T, BO));
830 case BO_Div:
831 if (BO->getType()->isFloatingType())
832 return Discard(this->emitDivf(getRoundingMode(BO), BO));
833 return Discard(this->emitDiv(*T, BO));
834 case BO_Assign:
835 if (DiscardResult)
836 return LHS->refersToBitField() ? this->emitStoreBitFieldPop(*T, BO)
837 : this->emitStorePop(*T, BO);
838 if (LHS->refersToBitField()) {
839 if (!this->emitStoreBitField(*T, BO))
840 return false;
841 } else {
842 if (!this->emitStore(*T, BO))
843 return false;
844 }
845 // Assignments aren't necessarily lvalues in C.
846 // Load from them in that case.
847 if (!BO->isLValue())
848 return this->emitLoadPop(*T, BO);
849 return true;
850 case BO_And:
851 return Discard(this->emitBitAnd(*T, BO));
852 case BO_Or:
853 return Discard(this->emitBitOr(*T, BO));
854 case BO_Shl:
855 return Discard(this->emitShl(*LT, *RT, BO));
856 case BO_Shr:
857 return Discard(this->emitShr(*LT, *RT, BO));
858 case BO_Xor:
859 return Discard(this->emitBitXor(*T, BO));
860 case BO_LOr:
861 case BO_LAnd:
862 llvm_unreachable("Already handled earlier");
863 default:
864 return false;
865 }
866
867 llvm_unreachable("Unhandled binary op");
868}
869
870/// Perform addition/subtraction of a pointer and an integer or
871/// subtraction of two pointers.
872template <class Emitter>
874 BinaryOperatorKind Op = E->getOpcode();
875 const Expr *LHS = E->getLHS();
876 const Expr *RHS = E->getRHS();
877
878 if ((Op != BO_Add && Op != BO_Sub) ||
879 (!LHS->getType()->isPointerType() && !RHS->getType()->isPointerType()))
880 return false;
881
882 std::optional<PrimType> LT = classify(LHS);
883 std::optional<PrimType> RT = classify(RHS);
884
885 if (!LT || !RT)
886 return false;
887
888 // Visit the given pointer expression and optionally convert to a PT_Ptr.
889 auto visitAsPointer = [&](const Expr *E, PrimType T) -> bool {
890 if (!this->visit(E))
891 return false;
892 if (T != PT_Ptr)
893 return this->emitDecayPtr(T, PT_Ptr, E);
894 return true;
895 };
896
897 if (LHS->getType()->isPointerType() && RHS->getType()->isPointerType()) {
898 if (Op != BO_Sub)
899 return false;
900
901 assert(E->getType()->isIntegerType());
902 if (!visitAsPointer(RHS, *RT) || !visitAsPointer(LHS, *LT))
903 return false;
904
905 return this->emitSubPtr(classifyPrim(E->getType()), E);
906 }
907
908 PrimType OffsetType;
909 if (LHS->getType()->isIntegerType()) {
910 if (!visitAsPointer(RHS, *RT))
911 return false;
912 if (!this->visit(LHS))
913 return false;
914 OffsetType = *LT;
915 } else if (RHS->getType()->isIntegerType()) {
916 if (!visitAsPointer(LHS, *LT))
917 return false;
918 if (!this->visit(RHS))
919 return false;
920 OffsetType = *RT;
921 } else {
922 return false;
923 }
924
925 // Do the operation and optionally transform to
926 // result pointer type.
927 if (Op == BO_Add) {
928 if (!this->emitAddOffset(OffsetType, E))
929 return false;
930
931 if (classifyPrim(E) != PT_Ptr)
932 return this->emitDecayPtr(PT_Ptr, classifyPrim(E), E);
933 return true;
934 } else if (Op == BO_Sub) {
935 if (!this->emitSubOffset(OffsetType, E))
936 return false;
937
938 if (classifyPrim(E) != PT_Ptr)
939 return this->emitDecayPtr(PT_Ptr, classifyPrim(E), E);
940 return true;
941 }
942
943 return false;
944}
945
946template <class Emitter>
948 assert(E->isLogicalOp());
949 BinaryOperatorKind Op = E->getOpcode();
950 const Expr *LHS = E->getLHS();
951 const Expr *RHS = E->getRHS();
952 std::optional<PrimType> T = classify(E->getType());
953
954 if (Op == BO_LOr) {
955 // Logical OR. Visit LHS and only evaluate RHS if LHS was FALSE.
956 LabelTy LabelTrue = this->getLabel();
957 LabelTy LabelEnd = this->getLabel();
958
959 if (!this->visitBool(LHS))
960 return false;
961 if (!this->jumpTrue(LabelTrue))
962 return false;
963
964 if (!this->visitBool(RHS))
965 return false;
966 if (!this->jump(LabelEnd))
967 return false;
968
969 this->emitLabel(LabelTrue);
970 this->emitConstBool(true, E);
971 this->fallthrough(LabelEnd);
972 this->emitLabel(LabelEnd);
973
974 } else {
975 assert(Op == BO_LAnd);
976 // Logical AND.
977 // Visit LHS. Only visit RHS if LHS was TRUE.
978 LabelTy LabelFalse = this->getLabel();
979 LabelTy LabelEnd = this->getLabel();
980
981 if (!this->visitBool(LHS))
982 return false;
983 if (!this->jumpFalse(LabelFalse))
984 return false;
985
986 if (!this->visitBool(RHS))
987 return false;
988 if (!this->jump(LabelEnd))
989 return false;
990
991 this->emitLabel(LabelFalse);
992 this->emitConstBool(false, E);
993 this->fallthrough(LabelEnd);
994 this->emitLabel(LabelEnd);
995 }
996
997 if (DiscardResult)
998 return this->emitPopBool(E);
999
1000 // For C, cast back to integer type.
1001 assert(T);
1002 if (T != PT_Bool)
1003 return this->emitCast(PT_Bool, *T, E);
1004 return true;
1005}
1006
1007template <class Emitter>
1009 // Prepare storage for result.
1010 if (!Initializing) {
1011 unsigned LocalIndex = allocateTemporary(E);
1012 if (!this->emitGetPtrLocal(LocalIndex, E))
1013 return false;
1014 }
1015
1016 // Both LHS and RHS might _not_ be of complex type, but one of them
1017 // needs to be.
1018 const Expr *LHS = E->getLHS();
1019 const Expr *RHS = E->getRHS();
1020
1021 PrimType ResultElemT = this->classifyComplexElementType(E->getType());
1022 unsigned ResultOffset = ~0u;
1023 if (!DiscardResult)
1024 ResultOffset = this->allocateLocalPrimitive(E, PT_Ptr, true, false);
1025
1026 // Save result pointer in ResultOffset
1027 if (!this->DiscardResult) {
1028 if (!this->emitDupPtr(E))
1029 return false;
1030 if (!this->emitSetLocal(PT_Ptr, ResultOffset, E))
1031 return false;
1032 }
1033 QualType LHSType = LHS->getType();
1034 if (const auto *AT = LHSType->getAs<AtomicType>())
1035 LHSType = AT->getValueType();
1036 QualType RHSType = RHS->getType();
1037 if (const auto *AT = RHSType->getAs<AtomicType>())
1038 RHSType = AT->getValueType();
1039
1040 bool LHSIsComplex = LHSType->isAnyComplexType();
1041 unsigned LHSOffset;
1042 bool RHSIsComplex = RHSType->isAnyComplexType();
1043
1044 // For ComplexComplex Mul, we have special ops to make their implementation
1045 // easier.
1046 BinaryOperatorKind Op = E->getOpcode();
1047 if (Op == BO_Mul && LHSIsComplex && RHSIsComplex) {
1048 assert(classifyPrim(LHSType->getAs<ComplexType>()->getElementType()) ==
1049 classifyPrim(RHSType->getAs<ComplexType>()->getElementType()));
1050 PrimType ElemT =
1051 classifyPrim(LHSType->getAs<ComplexType>()->getElementType());
1052 if (!this->visit(LHS))
1053 return false;
1054 if (!this->visit(RHS))
1055 return false;
1056 return this->emitMulc(ElemT, E);
1057 }
1058
1059 if (Op == BO_Div && RHSIsComplex) {
1060 QualType ElemQT = RHSType->getAs<ComplexType>()->getElementType();
1061 PrimType ElemT = classifyPrim(ElemQT);
1062 // If the LHS is not complex, we still need to do the full complex
1063 // division, so just stub create a complex value and stub it out with
1064 // the LHS and a zero.
1065
1066 if (!LHSIsComplex) {
1067 // This is using the RHS type for the fake-complex LHS.
1068 LHSOffset = allocateTemporary(RHS);
1069
1070 if (!this->emitGetPtrLocal(LHSOffset, E))
1071 return false;
1072
1073 if (!this->visit(LHS))
1074 return false;
1075 // real is LHS
1076 if (!this->emitInitElem(ElemT, 0, E))
1077 return false;
1078 // imag is zero
1079 if (!this->visitZeroInitializer(ElemT, ElemQT, E))
1080 return false;
1081 if (!this->emitInitElem(ElemT, 1, E))
1082 return false;
1083 } else {
1084 if (!this->visit(LHS))
1085 return false;
1086 }
1087
1088 if (!this->visit(RHS))
1089 return false;
1090 return this->emitDivc(ElemT, E);
1091 }
1092
1093 // Evaluate LHS and save value to LHSOffset.
1094 if (LHSType->isAnyComplexType()) {
1095 LHSOffset = this->allocateLocalPrimitive(LHS, PT_Ptr, true, false);
1096 if (!this->visit(LHS))
1097 return false;
1098 if (!this->emitSetLocal(PT_Ptr, LHSOffset, E))
1099 return false;
1100 } else {
1101 PrimType LHST = classifyPrim(LHSType);
1102 LHSOffset = this->allocateLocalPrimitive(LHS, LHST, true, false);
1103 if (!this->visit(LHS))
1104 return false;
1105 if (!this->emitSetLocal(LHST, LHSOffset, E))
1106 return false;
1107 }
1108
1109 // Same with RHS.
1110 unsigned RHSOffset;
1111 if (RHSType->isAnyComplexType()) {
1112 RHSOffset = this->allocateLocalPrimitive(RHS, PT_Ptr, true, false);
1113 if (!this->visit(RHS))
1114 return false;
1115 if (!this->emitSetLocal(PT_Ptr, RHSOffset, E))
1116 return false;
1117 } else {
1118 PrimType RHST = classifyPrim(RHSType);
1119 RHSOffset = this->allocateLocalPrimitive(RHS, RHST, true, false);
1120 if (!this->visit(RHS))
1121 return false;
1122 if (!this->emitSetLocal(RHST, RHSOffset, E))
1123 return false;
1124 }
1125
1126 // For both LHS and RHS, either load the value from the complex pointer, or
1127 // directly from the local variable. For index 1 (i.e. the imaginary part),
1128 // just load 0 and do the operation anyway.
1129 auto loadComplexValue = [this](bool IsComplex, bool LoadZero,
1130 unsigned ElemIndex, unsigned Offset,
1131 const Expr *E) -> bool {
1132 if (IsComplex) {
1133 if (!this->emitGetLocal(PT_Ptr, Offset, E))
1134 return false;
1135 return this->emitArrayElemPop(classifyComplexElementType(E->getType()),
1136 ElemIndex, E);
1137 }
1138 if (ElemIndex == 0 || !LoadZero)
1139 return this->emitGetLocal(classifyPrim(E->getType()), Offset, E);
1140 return this->visitZeroInitializer(classifyPrim(E->getType()), E->getType(),
1141 E);
1142 };
1143
1144 // Now we can get pointers to the LHS and RHS from the offsets above.
1145 for (unsigned ElemIndex = 0; ElemIndex != 2; ++ElemIndex) {
1146 // Result pointer for the store later.
1147 if (!this->DiscardResult) {
1148 if (!this->emitGetLocal(PT_Ptr, ResultOffset, E))
1149 return false;
1150 }
1151
1152 // The actual operation.
1153 switch (Op) {
1154 case BO_Add:
1155 if (!loadComplexValue(LHSIsComplex, true, ElemIndex, LHSOffset, LHS))
1156 return false;
1157
1158 if (!loadComplexValue(RHSIsComplex, true, ElemIndex, RHSOffset, RHS))
1159 return false;
1160 if (ResultElemT == PT_Float) {
1161 if (!this->emitAddf(getRoundingMode(E), E))
1162 return false;
1163 } else {
1164 if (!this->emitAdd(ResultElemT, E))
1165 return false;
1166 }
1167 break;
1168 case BO_Sub:
1169 if (!loadComplexValue(LHSIsComplex, true, ElemIndex, LHSOffset, LHS))
1170 return false;
1171
1172 if (!loadComplexValue(RHSIsComplex, true, ElemIndex, RHSOffset, RHS))
1173 return false;
1174 if (ResultElemT == PT_Float) {
1175 if (!this->emitSubf(getRoundingMode(E), E))
1176 return false;
1177 } else {
1178 if (!this->emitSub(ResultElemT, E))
1179 return false;
1180 }
1181 break;
1182 case BO_Mul:
1183 if (!loadComplexValue(LHSIsComplex, false, ElemIndex, LHSOffset, LHS))
1184 return false;
1185
1186 if (!loadComplexValue(RHSIsComplex, false, ElemIndex, RHSOffset, RHS))
1187 return false;
1188
1189 if (ResultElemT == PT_Float) {
1190 if (!this->emitMulf(getRoundingMode(E), E))
1191 return false;
1192 } else {
1193 if (!this->emitMul(ResultElemT, E))
1194 return false;
1195 }
1196 break;
1197 case BO_Div:
1198 assert(!RHSIsComplex);
1199 if (!loadComplexValue(LHSIsComplex, false, ElemIndex, LHSOffset, LHS))
1200 return false;
1201
1202 if (!loadComplexValue(RHSIsComplex, false, ElemIndex, RHSOffset, RHS))
1203 return false;
1204
1205 if (ResultElemT == PT_Float) {
1206 if (!this->emitDivf(getRoundingMode(E), E))
1207 return false;
1208 } else {
1209 if (!this->emitDiv(ResultElemT, E))
1210 return false;
1211 }
1212 break;
1213
1214 default:
1215 return false;
1216 }
1217
1218 if (!this->DiscardResult) {
1219 // Initialize array element with the value we just computed.
1220 if (!this->emitInitElemPop(ResultElemT, ElemIndex, E))
1221 return false;
1222 } else {
1223 if (!this->emitPop(ResultElemT, E))
1224 return false;
1225 }
1226 }
1227 return true;
1228}
1229
1230template <class Emitter>
1232 const ImplicitValueInitExpr *E) {
1233 QualType QT = E->getType();
1234
1235 if (std::optional<PrimType> T = classify(QT))
1236 return this->visitZeroInitializer(*T, QT, E);
1237
1238 if (QT->isRecordType()) {
1239 const RecordDecl *RD = QT->getAsRecordDecl();
1240 assert(RD);
1241 if (RD->isInvalidDecl())
1242 return false;
1243 if (RD->isUnion()) {
1244 // C++11 [dcl.init]p5: If T is a (possibly cv-qualified) union type, the
1245 // object's first non-static named data member is zero-initialized
1246 // FIXME
1247 return false;
1248 }
1249
1250 if (const auto *CXXRD = dyn_cast<CXXRecordDecl>(RD);
1251 CXXRD && CXXRD->getNumVBases() > 0) {
1252 // TODO: Diagnose.
1253 return false;
1254 }
1255
1256 const Record *R = getRecord(QT);
1257 if (!R)
1258 return false;
1259
1260 assert(Initializing);
1261 return this->visitZeroRecordInitializer(R, E);
1262 }
1263
1264 if (QT->isIncompleteArrayType())
1265 return true;
1266
1267 if (QT->isArrayType()) {
1268 const ArrayType *AT = QT->getAsArrayTypeUnsafe();
1269 assert(AT);
1270 const auto *CAT = cast<ConstantArrayType>(AT);
1271 size_t NumElems = CAT->getZExtSize();
1272 PrimType ElemT = classifyPrim(CAT->getElementType());
1273
1274 for (size_t I = 0; I != NumElems; ++I) {
1275 if (!this->visitZeroInitializer(ElemT, CAT->getElementType(), E))
1276 return false;
1277 if (!this->emitInitElem(ElemT, I, E))
1278 return false;
1279 }
1280
1281 return true;
1282 }
1283
1284 if (const auto *ComplexTy = E->getType()->getAs<ComplexType>()) {
1285 assert(Initializing);
1286 QualType ElemQT = ComplexTy->getElementType();
1287 PrimType ElemT = classifyPrim(ElemQT);
1288 for (unsigned I = 0; I < 2; ++I) {
1289 if (!this->visitZeroInitializer(ElemT, ElemQT, E))
1290 return false;
1291 if (!this->emitInitElem(ElemT, I, E))
1292 return false;
1293 }
1294 return true;
1295 }
1296
1297 if (const auto *VecT = E->getType()->getAs<VectorType>()) {
1298 unsigned NumVecElements = VecT->getNumElements();
1299 QualType ElemQT = VecT->getElementType();
1300 PrimType ElemT = classifyPrim(ElemQT);
1301
1302 for (unsigned I = 0; I < NumVecElements; ++I) {
1303 if (!this->visitZeroInitializer(ElemT, ElemQT, E))
1304 return false;
1305 if (!this->emitInitElem(ElemT, I, E))
1306 return false;
1307 }
1308 return true;
1309 }
1310
1311 return false;
1312}
1313
1314template <class Emitter>
1316 const Expr *LHS = E->getLHS();
1317 const Expr *RHS = E->getRHS();
1318 const Expr *Index = E->getIdx();
1319
1320 if (DiscardResult)
1321 return this->discard(LHS) && this->discard(RHS);
1322
1323 // C++17's rules require us to evaluate the LHS first, regardless of which
1324 // side is the base.
1325 bool Success = true;
1326 for (const Expr *SubExpr : {LHS, RHS}) {
1327 if (!this->visit(SubExpr))
1328 Success = false;
1329 }
1330
1331 if (!Success)
1332 return false;
1333
1334 PrimType IndexT = classifyPrim(Index->getType());
1335 // If the index is first, we need to change that.
1336 if (LHS == Index) {
1337 if (!this->emitFlip(PT_Ptr, IndexT, E))
1338 return false;
1339 }
1340
1341 return this->emitArrayElemPtrPop(IndexT, E);
1342}
1343
1344template <class Emitter>
1346 const Expr *ArrayFiller, const Expr *E) {
1347 QualType QT = E->getType();
1348 if (const auto *AT = QT->getAs<AtomicType>())
1349 QT = AT->getValueType();
1350
1351 if (QT->isVoidType()) {
1352 if (Inits.size() == 0)
1353 return true;
1354 return this->emitInvalid(E);
1355 }
1356
1357 // Handle discarding first.
1358 if (DiscardResult) {
1359 for (const Expr *Init : Inits) {
1360 if (!this->discard(Init))
1361 return false;
1362 }
1363 return true;
1364 }
1365
1366 // Primitive values.
1367 if (std::optional<PrimType> T = classify(QT)) {
1368 assert(!DiscardResult);
1369 if (Inits.size() == 0)
1370 return this->visitZeroInitializer(*T, QT, E);
1371 assert(Inits.size() == 1);
1372 return this->delegate(Inits[0]);
1373 }
1374
1375 if (QT->isRecordType()) {
1376 const Record *R = getRecord(QT);
1377
1378 if (Inits.size() == 1 && E->getType() == Inits[0]->getType())
1379 return this->delegate(Inits[0]);
1380
1381 auto initPrimitiveField = [=](const Record::Field *FieldToInit,
1382 const Expr *Init, PrimType T) -> bool {
1383 InitStackScope<Emitter> ISS(this, isa<CXXDefaultInitExpr>(Init));
1384 if (!this->visit(Init))
1385 return false;
1386
1387 if (FieldToInit->isBitField())
1388 return this->emitInitBitField(T, FieldToInit, E);
1389 return this->emitInitField(T, FieldToInit->Offset, E);
1390 };
1391
1392 auto initCompositeField = [=](const Record::Field *FieldToInit,
1393 const Expr *Init) -> bool {
1394 InitStackScope<Emitter> ISS(this, isa<CXXDefaultInitExpr>(Init));
1395 InitLinkScope<Emitter> ILS(this, InitLink::Field(FieldToInit->Offset));
1396 // Non-primitive case. Get a pointer to the field-to-initialize
1397 // on the stack and recurse into visitInitializer().
1398 if (!this->emitGetPtrField(FieldToInit->Offset, Init))
1399 return false;
1400 if (!this->visitInitializer(Init))
1401 return false;
1402 return this->emitPopPtr(E);
1403 };
1404
1405 if (R->isUnion()) {
1406 if (Inits.size() == 0) {
1407 if (!this->visitZeroRecordInitializer(R, E))
1408 return false;
1409 } else {
1410 const Expr *Init = Inits[0];
1411 const FieldDecl *FToInit = nullptr;
1412 if (const auto *ILE = dyn_cast<InitListExpr>(E))
1413 FToInit = ILE->getInitializedFieldInUnion();
1414 else
1415 FToInit = cast<CXXParenListInitExpr>(E)->getInitializedFieldInUnion();
1416
1417 const Record::Field *FieldToInit = R->getField(FToInit);
1418 if (std::optional<PrimType> T = classify(Init)) {
1419 if (!initPrimitiveField(FieldToInit, Init, *T))
1420 return false;
1421 } else {
1422 if (!initCompositeField(FieldToInit, Init))
1423 return false;
1424 }
1425 }
1426 return this->emitFinishInit(E);
1427 }
1428
1429 assert(!R->isUnion());
1430 unsigned InitIndex = 0;
1431 for (const Expr *Init : Inits) {
1432 // Skip unnamed bitfields.
1433 while (InitIndex < R->getNumFields() &&
1434 R->getField(InitIndex)->Decl->isUnnamedBitField())
1435 ++InitIndex;
1436
1437 if (std::optional<PrimType> T = classify(Init)) {
1438 const Record::Field *FieldToInit = R->getField(InitIndex);
1439 if (!initPrimitiveField(FieldToInit, Init, *T))
1440 return false;
1441 ++InitIndex;
1442 } else {
1443 // Initializer for a direct base class.
1444 if (const Record::Base *B = R->getBase(Init->getType())) {
1445 if (!this->emitGetPtrBase(B->Offset, Init))
1446 return false;
1447
1448 if (!this->visitInitializer(Init))
1449 return false;
1450
1451 if (!this->emitFinishInitPop(E))
1452 return false;
1453 // Base initializers don't increase InitIndex, since they don't count
1454 // into the Record's fields.
1455 } else {
1456 const Record::Field *FieldToInit = R->getField(InitIndex);
1457 if (!initCompositeField(FieldToInit, Init))
1458 return false;
1459 ++InitIndex;
1460 }
1461 }
1462 }
1463 return this->emitFinishInit(E);
1464 }
1465
1466 if (QT->isArrayType()) {
1467 if (Inits.size() == 1 && QT == Inits[0]->getType())
1468 return this->delegate(Inits[0]);
1469
1470 unsigned ElementIndex = 0;
1471 for (const Expr *Init : Inits) {
1472 if (const auto *EmbedS =
1473 dyn_cast<EmbedExpr>(Init->IgnoreParenImpCasts())) {
1474 PrimType TargetT = classifyPrim(Init->getType());
1475
1476 auto Eval = [&](const Expr *Init, unsigned ElemIndex) {
1477 PrimType InitT = classifyPrim(Init->getType());
1478 if (!this->visit(Init))
1479 return false;
1480 if (InitT != TargetT) {
1481 if (!this->emitCast(InitT, TargetT, E))
1482 return false;
1483 }
1484 return this->emitInitElem(TargetT, ElemIndex, Init);
1485 };
1486 if (!EmbedS->doForEachDataElement(Eval, ElementIndex))
1487 return false;
1488 } else {
1489 if (!this->visitArrayElemInit(ElementIndex, Init))
1490 return false;
1491 ++ElementIndex;
1492 }
1493 }
1494
1495 // Expand the filler expression.
1496 // FIXME: This should go away.
1497 if (ArrayFiller) {
1498 const ConstantArrayType *CAT =
1499 Ctx.getASTContext().getAsConstantArrayType(QT);
1500 uint64_t NumElems = CAT->getZExtSize();
1501
1502 for (; ElementIndex != NumElems; ++ElementIndex) {
1503 if (!this->visitArrayElemInit(ElementIndex, ArrayFiller))
1504 return false;
1505 }
1506 }
1507
1508 return this->emitFinishInit(E);
1509 }
1510
1511 if (const auto *ComplexTy = QT->getAs<ComplexType>()) {
1512 unsigned NumInits = Inits.size();
1513
1514 if (NumInits == 1)
1515 return this->delegate(Inits[0]);
1516
1517 QualType ElemQT = ComplexTy->getElementType();
1518 PrimType ElemT = classifyPrim(ElemQT);
1519 if (NumInits == 0) {
1520 // Zero-initialize both elements.
1521 for (unsigned I = 0; I < 2; ++I) {
1522 if (!this->visitZeroInitializer(ElemT, ElemQT, E))
1523 return false;
1524 if (!this->emitInitElem(ElemT, I, E))
1525 return false;
1526 }
1527 } else if (NumInits == 2) {
1528 unsigned InitIndex = 0;
1529 for (const Expr *Init : Inits) {
1530 if (!this->visit(Init))
1531 return false;
1532
1533 if (!this->emitInitElem(ElemT, InitIndex, E))
1534 return false;
1535 ++InitIndex;
1536 }
1537 }
1538 return true;
1539 }
1540
1541 if (const auto *VecT = QT->getAs<VectorType>()) {
1542 unsigned NumVecElements = VecT->getNumElements();
1543 assert(NumVecElements >= Inits.size());
1544
1545 QualType ElemQT = VecT->getElementType();
1546 PrimType ElemT = classifyPrim(ElemQT);
1547
1548 // All initializer elements.
1549 unsigned InitIndex = 0;
1550 for (const Expr *Init : Inits) {
1551 if (!this->visit(Init))
1552 return false;
1553
1554 // If the initializer is of vector type itself, we have to deconstruct
1555 // that and initialize all the target fields from the initializer fields.
1556 if (const auto *InitVecT = Init->getType()->getAs<VectorType>()) {
1557 if (!this->emitCopyArray(ElemT, 0, InitIndex,
1558 InitVecT->getNumElements(), E))
1559 return false;
1560 InitIndex += InitVecT->getNumElements();
1561 } else {
1562 if (!this->emitInitElem(ElemT, InitIndex, E))
1563 return false;
1564 ++InitIndex;
1565 }
1566 }
1567
1568 assert(InitIndex <= NumVecElements);
1569
1570 // Fill the rest with zeroes.
1571 for (; InitIndex != NumVecElements; ++InitIndex) {
1572 if (!this->visitZeroInitializer(ElemT, ElemQT, E))
1573 return false;
1574 if (!this->emitInitElem(ElemT, InitIndex, E))
1575 return false;
1576 }
1577 return true;
1578 }
1579
1580 return false;
1581}
1582
1583/// Pointer to the array(not the element!) must be on the stack when calling
1584/// this.
1585template <class Emitter>
1587 const Expr *Init) {
1588 if (std::optional<PrimType> T = classify(Init->getType())) {
1589 // Visit the primitive element like normal.
1590 if (!this->visit(Init))
1591 return false;
1592 return this->emitInitElem(*T, ElemIndex, Init);
1593 }
1594
1595 InitLinkScope<Emitter> ILS(this, InitLink::Elem(ElemIndex));
1596 // Advance the pointer currently on the stack to the given
1597 // dimension.
1598 if (!this->emitConstUint32(ElemIndex, Init))
1599 return false;
1600 if (!this->emitArrayElemPtrUint32(Init))
1601 return false;
1602 if (!this->visitInitializer(Init))
1603 return false;
1604 return this->emitFinishInitPop(Init);
1605}
1606
1607template <class Emitter>
1609 return this->visitInitList(E->inits(), E->getArrayFiller(), E);
1610}
1611
1612template <class Emitter>
1614 const CXXParenListInitExpr *E) {
1615 return this->visitInitList(E->getInitExprs(), E->getArrayFiller(), E);
1616}
1617
1618template <class Emitter>
1621 return this->delegate(E->getReplacement());
1622}
1623
1624template <class Emitter>
1626 std::optional<PrimType> T = classify(E->getType());
1627 if (T && E->hasAPValueResult()) {
1628 // Try to emit the APValue directly, without visiting the subexpr.
1629 // This will only fail if we can't emit the APValue, so won't emit any
1630 // diagnostics or any double values.
1631 if (DiscardResult)
1632 return true;
1633
1634 if (this->visitAPValue(E->getAPValueResult(), *T, E))
1635 return true;
1636 }
1637 return this->delegate(E->getSubExpr());
1638}
1639
1640template <class Emitter>
1642 auto It = E->begin();
1643 return this->visit(*It);
1644}
1645
1647 UnaryExprOrTypeTrait Kind) {
1648 bool AlignOfReturnsPreferred =
1649 ASTCtx.getLangOpts().getClangABICompat() <= LangOptions::ClangABI::Ver7;
1650
1651 // C++ [expr.alignof]p3:
1652 // When alignof is applied to a reference type, the result is the
1653 // alignment of the referenced type.
1654 if (const auto *Ref = T->getAs<ReferenceType>())
1655 T = Ref->getPointeeType();
1656
1657 if (T.getQualifiers().hasUnaligned())
1658 return CharUnits::One();
1659
1660 // __alignof is defined to return the preferred alignment.
1661 // Before 8, clang returned the preferred alignment for alignof and
1662 // _Alignof as well.
1663 if (Kind == UETT_PreferredAlignOf || AlignOfReturnsPreferred)
1664 return ASTCtx.toCharUnitsFromBits(ASTCtx.getPreferredTypeAlign(T));
1665
1666 return ASTCtx.getTypeAlignInChars(T);
1667}
1668
1669template <class Emitter>
1671 const UnaryExprOrTypeTraitExpr *E) {
1672 UnaryExprOrTypeTrait Kind = E->getKind();
1673 const ASTContext &ASTCtx = Ctx.getASTContext();
1674
1675 if (Kind == UETT_SizeOf || Kind == UETT_DataSizeOf) {
1676 QualType ArgType = E->getTypeOfArgument();
1677
1678 // C++ [expr.sizeof]p2: "When applied to a reference or a reference type,
1679 // the result is the size of the referenced type."
1680 if (const auto *Ref = ArgType->getAs<ReferenceType>())
1681 ArgType = Ref->getPointeeType();
1682
1683 CharUnits Size;
1684 if (ArgType->isVoidType() || ArgType->isFunctionType())
1685 Size = CharUnits::One();
1686 else {
1687 if (ArgType->isDependentType() || !ArgType->isConstantSizeType())
1688 return false;
1689
1690 if (Kind == UETT_SizeOf)
1691 Size = ASTCtx.getTypeSizeInChars(ArgType);
1692 else
1693 Size = ASTCtx.getTypeInfoDataSizeInChars(ArgType).Width;
1694 }
1695
1696 if (DiscardResult)
1697 return true;
1698
1699 return this->emitConst(Size.getQuantity(), E);
1700 }
1701
1702 if (Kind == UETT_AlignOf || Kind == UETT_PreferredAlignOf) {
1703 CharUnits Size;
1704
1705 if (E->isArgumentType()) {
1706 QualType ArgType = E->getTypeOfArgument();
1707
1708 Size = AlignOfType(ArgType, ASTCtx, Kind);
1709 } else {
1710 // Argument is an expression, not a type.
1711 const Expr *Arg = E->getArgumentExpr()->IgnoreParens();
1712
1713 // The kinds of expressions that we have special-case logic here for
1714 // should be kept up to date with the special checks for those
1715 // expressions in Sema.
1716
1717 // alignof decl is always accepted, even if it doesn't make sense: we
1718 // default to 1 in those cases.
1719 if (const auto *DRE = dyn_cast<DeclRefExpr>(Arg))
1720 Size = ASTCtx.getDeclAlign(DRE->getDecl(),
1721 /*RefAsPointee*/ true);
1722 else if (const auto *ME = dyn_cast<MemberExpr>(Arg))
1723 Size = ASTCtx.getDeclAlign(ME->getMemberDecl(),
1724 /*RefAsPointee*/ true);
1725 else
1726 Size = AlignOfType(Arg->getType(), ASTCtx, Kind);
1727 }
1728
1729 if (DiscardResult)
1730 return true;
1731
1732 return this->emitConst(Size.getQuantity(), E);
1733 }
1734
1735 if (Kind == UETT_VectorElements) {
1736 if (const auto *VT = E->getTypeOfArgument()->getAs<VectorType>())
1737 return this->emitConst(VT->getNumElements(), E);
1738 assert(E->getTypeOfArgument()->isSizelessVectorType());
1739 return this->emitSizelessVectorElementSize(E);
1740 }
1741
1742 if (Kind == UETT_VecStep) {
1743 if (const auto *VT = E->getTypeOfArgument()->getAs<VectorType>()) {
1744 unsigned N = VT->getNumElements();
1745
1746 // The vec_step built-in functions that take a 3-component
1747 // vector return 4. (OpenCL 1.1 spec 6.11.12)
1748 if (N == 3)
1749 N = 4;
1750
1751 return this->emitConst(N, E);
1752 }
1753 return this->emitConst(1, E);
1754 }
1755
1756 return false;
1757}
1758
1759template <class Emitter>
1761 // 'Base.Member'
1762 const Expr *Base = E->getBase();
1763 const ValueDecl *Member = E->getMemberDecl();
1764
1765 if (DiscardResult)
1766 return this->discard(Base);
1767
1768 // MemberExprs are almost always lvalues, in which case we don't need to
1769 // do the load. But sometimes they aren't.
1770 const auto maybeLoadValue = [&]() -> bool {
1771 if (E->isGLValue())
1772 return true;
1773 if (std::optional<PrimType> T = classify(E))
1774 return this->emitLoadPop(*T, E);
1775 return false;
1776 };
1777
1778 if (const auto *VD = dyn_cast<VarDecl>(Member)) {
1779 // I am almost confident in saying that a var decl must be static
1780 // and therefore registered as a global variable. But this will probably
1781 // turn out to be wrong some time in the future, as always.
1782 if (auto GlobalIndex = P.getGlobal(VD))
1783 return this->emitGetPtrGlobal(*GlobalIndex, E) && maybeLoadValue();
1784 return false;
1785 }
1786
1787 if (!isa<FieldDecl>(Member))
1788 return this->discard(Base) && this->visitDeclRef(Member, E);
1789
1790 if (Initializing) {
1791 if (!this->delegate(Base))
1792 return false;
1793 } else {
1794 if (!this->visit(Base))
1795 return false;
1796 }
1797
1798 // Base above gives us a pointer on the stack.
1799 const auto *FD = cast<FieldDecl>(Member);
1800 const RecordDecl *RD = FD->getParent();
1801 const Record *R = getRecord(RD);
1802 if (!R)
1803 return false;
1804 const Record::Field *F = R->getField(FD);
1805 // Leave a pointer to the field on the stack.
1806 if (F->Decl->getType()->isReferenceType())
1807 return this->emitGetFieldPop(PT_Ptr, F->Offset, E) && maybeLoadValue();
1808 return this->emitGetPtrFieldPop(F->Offset, E) && maybeLoadValue();
1809}
1810
1811template <class Emitter>
1813 // ArrayIndex might not be set if a ArrayInitIndexExpr is being evaluated
1814 // stand-alone, e.g. via EvaluateAsInt().
1815 if (!ArrayIndex)
1816 return false;
1817 return this->emitConst(*ArrayIndex, E);
1818}
1819
1820template <class Emitter>
1822 assert(Initializing);
1823 assert(!DiscardResult);
1824
1825 // We visit the common opaque expression here once so we have its value
1826 // cached.
1827 if (!this->discard(E->getCommonExpr()))
1828 return false;
1829
1830 // TODO: This compiles to quite a lot of bytecode if the array is larger.
1831 // Investigate compiling this to a loop.
1832 const Expr *SubExpr = E->getSubExpr();
1833 size_t Size = E->getArraySize().getZExtValue();
1834
1835 // So, every iteration, we execute an assignment here
1836 // where the LHS is on the stack (the target array)
1837 // and the RHS is our SubExpr.
1838 for (size_t I = 0; I != Size; ++I) {
1839 ArrayIndexScope<Emitter> IndexScope(this, I);
1840 BlockScope<Emitter> BS(this);
1841
1842 if (!this->visitArrayElemInit(I, SubExpr))
1843 return false;
1844 if (!BS.destroyLocals())
1845 return false;
1846 }
1847 return true;
1848}
1849
1850template <class Emitter>
1852 const Expr *SourceExpr = E->getSourceExpr();
1853 if (!SourceExpr)
1854 return false;
1855
1856 if (Initializing)
1857 return this->visitInitializer(SourceExpr);
1858
1859 PrimType SubExprT = classify(SourceExpr).value_or(PT_Ptr);
1860 if (auto It = OpaqueExprs.find(E); It != OpaqueExprs.end())
1861 return this->emitGetLocal(SubExprT, It->second, E);
1862
1863 if (!this->visit(SourceExpr))
1864 return false;
1865
1866 // At this point we either have the evaluated source expression or a pointer
1867 // to an object on the stack. We want to create a local variable that stores
1868 // this value.
1869 unsigned LocalIndex = allocateLocalPrimitive(E, SubExprT, /*IsConst=*/true);
1870 if (!this->emitSetLocal(SubExprT, LocalIndex, E))
1871 return false;
1872
1873 // Here the local variable is created but the value is removed from the stack,
1874 // so we put it back if the caller needs it.
1875 if (!DiscardResult) {
1876 if (!this->emitGetLocal(SubExprT, LocalIndex, E))
1877 return false;
1878 }
1879
1880 // This is cleaned up when the local variable is destroyed.
1881 OpaqueExprs.insert({E, LocalIndex});
1882
1883 return true;
1884}
1885
1886template <class Emitter>
1889 const Expr *Condition = E->getCond();
1890 const Expr *TrueExpr = E->getTrueExpr();
1891 const Expr *FalseExpr = E->getFalseExpr();
1892
1893 LabelTy LabelEnd = this->getLabel(); // Label after the operator.
1894 LabelTy LabelFalse = this->getLabel(); // Label for the false expr.
1895
1896 if (!this->visitBool(Condition))
1897 return false;
1898
1899 if (!this->jumpFalse(LabelFalse))
1900 return false;
1901
1902 {
1903 LocalScope<Emitter> S(this);
1904 if (!this->delegate(TrueExpr))
1905 return false;
1906 if (!S.destroyLocals())
1907 return false;
1908 }
1909
1910 if (!this->jump(LabelEnd))
1911 return false;
1912
1913 this->emitLabel(LabelFalse);
1914
1915 {
1916 LocalScope<Emitter> S(this);
1917 if (!this->delegate(FalseExpr))
1918 return false;
1919 if (!S.destroyLocals())
1920 return false;
1921 }
1922
1923 this->fallthrough(LabelEnd);
1924 this->emitLabel(LabelEnd);
1925
1926 return true;
1927}
1928
1929template <class Emitter>
1931 if (DiscardResult)
1932 return true;
1933
1934 if (!Initializing) {
1935 unsigned StringIndex = P.createGlobalString(E);
1936 return this->emitGetPtrGlobal(StringIndex, E);
1937 }
1938
1939 // We are initializing an array on the stack.
1940 const ConstantArrayType *CAT =
1941 Ctx.getASTContext().getAsConstantArrayType(E->getType());
1942 assert(CAT && "a string literal that's not a constant array?");
1943
1944 // If the initializer string is too long, a diagnostic has already been
1945 // emitted. Read only the array length from the string literal.
1946 unsigned ArraySize = CAT->getZExtSize();
1947 unsigned N = std::min(ArraySize, E->getLength());
1948 size_t CharWidth = E->getCharByteWidth();
1949
1950 for (unsigned I = 0; I != N; ++I) {
1951 uint32_t CodeUnit = E->getCodeUnit(I);
1952
1953 if (CharWidth == 1) {
1954 this->emitConstSint8(CodeUnit, E);
1955 this->emitInitElemSint8(I, E);
1956 } else if (CharWidth == 2) {
1957 this->emitConstUint16(CodeUnit, E);
1958 this->emitInitElemUint16(I, E);
1959 } else if (CharWidth == 4) {
1960 this->emitConstUint32(CodeUnit, E);
1961 this->emitInitElemUint32(I, E);
1962 } else {
1963 llvm_unreachable("unsupported character width");
1964 }
1965 }
1966
1967 // Fill up the rest of the char array with NUL bytes.
1968 for (unsigned I = N; I != ArraySize; ++I) {
1969 if (CharWidth == 1) {
1970 this->emitConstSint8(0, E);
1971 this->emitInitElemSint8(I, E);
1972 } else if (CharWidth == 2) {
1973 this->emitConstUint16(0, E);
1974 this->emitInitElemUint16(I, E);
1975 } else if (CharWidth == 4) {
1976 this->emitConstUint32(0, E);
1977 this->emitInitElemUint32(I, E);
1978 } else {
1979 llvm_unreachable("unsupported character width");
1980 }
1981 }
1982
1983 return true;
1984}
1985
1986template <class Emitter>
1988 return this->delegate(E->getString());
1989}
1990
1991template <class Emitter>
1993 auto &A = Ctx.getASTContext();
1994 std::string Str;
1995 A.getObjCEncodingForType(E->getEncodedType(), Str);
1996 StringLiteral *SL =
1997 StringLiteral::Create(A, Str, StringLiteralKind::Ordinary,
1998 /*Pascal=*/false, E->getType(), E->getAtLoc());
1999 return this->delegate(SL);
2000}
2001
2002template <class Emitter>
2004 const SYCLUniqueStableNameExpr *E) {
2005 if (DiscardResult)
2006 return true;
2007
2008 assert(!Initializing);
2009
2010 auto &A = Ctx.getASTContext();
2011 std::string ResultStr = E->ComputeName(A);
2012
2013 QualType CharTy = A.CharTy.withConst();
2014 APInt Size(A.getTypeSize(A.getSizeType()), ResultStr.size() + 1);
2015 QualType ArrayTy = A.getConstantArrayType(CharTy, Size, nullptr,
2016 ArraySizeModifier::Normal, 0);
2017
2018 StringLiteral *SL =
2019 StringLiteral::Create(A, ResultStr, StringLiteralKind::Ordinary,
2020 /*Pascal=*/false, ArrayTy, E->getLocation());
2021
2022 unsigned StringIndex = P.createGlobalString(SL);
2023 return this->emitGetPtrGlobal(StringIndex, E);
2024}
2025
2026template <class Emitter>
2028 if (DiscardResult)
2029 return true;
2030 return this->emitConst(E->getValue(), E);
2031}
2032
2033template <class Emitter>
2035 const CompoundAssignOperator *E) {
2036
2037 const Expr *LHS = E->getLHS();
2038 const Expr *RHS = E->getRHS();
2039 QualType LHSType = LHS->getType();
2040 QualType LHSComputationType = E->getComputationLHSType();
2041 QualType ResultType = E->getComputationResultType();
2042 std::optional<PrimType> LT = classify(LHSComputationType);
2043 std::optional<PrimType> RT = classify(ResultType);
2044
2045 assert(ResultType->isFloatingType());
2046
2047 if (!LT || !RT)
2048 return false;
2049
2050 PrimType LHST = classifyPrim(LHSType);
2051
2052 // C++17 onwards require that we evaluate the RHS first.
2053 // Compute RHS and save it in a temporary variable so we can
2054 // load it again later.
2055 if (!visit(RHS))
2056 return false;
2057
2058 unsigned TempOffset = this->allocateLocalPrimitive(E, *RT, /*IsConst=*/true);
2059 if (!this->emitSetLocal(*RT, TempOffset, E))
2060 return false;
2061
2062 // First, visit LHS.
2063 if (!visit(LHS))
2064 return false;
2065 if (!this->emitLoad(LHST, E))
2066 return false;
2067
2068 // If necessary, convert LHS to its computation type.
2069 if (!this->emitPrimCast(LHST, classifyPrim(LHSComputationType),
2070 LHSComputationType, E))
2071 return false;
2072
2073 // Now load RHS.
2074 if (!this->emitGetLocal(*RT, TempOffset, E))
2075 return false;
2076
2077 llvm::RoundingMode RM = getRoundingMode(E);
2078 switch (E->getOpcode()) {
2079 case BO_AddAssign:
2080 if (!this->emitAddf(RM, E))
2081 return false;
2082 break;
2083 case BO_SubAssign:
2084 if (!this->emitSubf(RM, E))
2085 return false;
2086 break;
2087 case BO_MulAssign:
2088 if (!this->emitMulf(RM, E))
2089 return false;
2090 break;
2091 case BO_DivAssign:
2092 if (!this->emitDivf(RM, E))
2093 return false;
2094 break;
2095 default:
2096 return false;
2097 }
2098
2099 if (!this->emitPrimCast(classifyPrim(ResultType), LHST, LHS->getType(), E))
2100 return false;
2101
2102 if (DiscardResult)
2103 return this->emitStorePop(LHST, E);
2104 return this->emitStore(LHST, E);
2105}
2106
2107template <class Emitter>
2109 const CompoundAssignOperator *E) {
2110 BinaryOperatorKind Op = E->getOpcode();
2111 const Expr *LHS = E->getLHS();
2112 const Expr *RHS = E->getRHS();
2113 std::optional<PrimType> LT = classify(LHS->getType());
2114 std::optional<PrimType> RT = classify(RHS->getType());
2115
2116 if (Op != BO_AddAssign && Op != BO_SubAssign)
2117 return false;
2118
2119 if (!LT || !RT)
2120 return false;
2121
2122 if (!visit(LHS))
2123 return false;
2124
2125 if (!this->emitLoad(*LT, LHS))
2126 return false;
2127
2128 if (!visit(RHS))
2129 return false;
2130
2131 if (Op == BO_AddAssign) {
2132 if (!this->emitAddOffset(*RT, E))
2133 return false;
2134 } else {
2135 if (!this->emitSubOffset(*RT, E))
2136 return false;
2137 }
2138
2139 if (DiscardResult)
2140 return this->emitStorePopPtr(E);
2141 return this->emitStorePtr(E);
2142}
2143
2144template <class Emitter>
2146 const CompoundAssignOperator *E) {
2147
2148 const Expr *LHS = E->getLHS();
2149 const Expr *RHS = E->getRHS();
2150 std::optional<PrimType> LHSComputationT =
2151 classify(E->getComputationLHSType());
2152 std::optional<PrimType> LT = classify(LHS->getType());
2153 std::optional<PrimType> RT = classify(RHS->getType());
2154 std::optional<PrimType> ResultT = classify(E->getType());
2155
2156 if (!Ctx.getLangOpts().CPlusPlus14)
2157 return this->visit(RHS) && this->visit(LHS) && this->emitError(E);
2158
2159 if (!LT || !RT || !ResultT || !LHSComputationT)
2160 return false;
2161
2162 // Handle floating point operations separately here, since they
2163 // require special care.
2164
2165 if (ResultT == PT_Float || RT == PT_Float)
2166 return VisitFloatCompoundAssignOperator(E);
2167
2168 if (E->getType()->isPointerType())
2169 return VisitPointerCompoundAssignOperator(E);
2170
2171 assert(!E->getType()->isPointerType() && "Handled above");
2172 assert(!E->getType()->isFloatingType() && "Handled above");
2173
2174 // C++17 onwards require that we evaluate the RHS first.
2175 // Compute RHS and save it in a temporary variable so we can
2176 // load it again later.
2177 // FIXME: Compound assignments are unsequenced in C, so we might
2178 // have to figure out how to reject them.
2179 if (!visit(RHS))
2180 return false;
2181
2182 unsigned TempOffset = this->allocateLocalPrimitive(E, *RT, /*IsConst=*/true);
2183
2184 if (!this->emitSetLocal(*RT, TempOffset, E))
2185 return false;
2186
2187 // Get LHS pointer, load its value and cast it to the
2188 // computation type if necessary.
2189 if (!visit(LHS))
2190 return false;
2191 if (!this->emitLoad(*LT, E))
2192 return false;
2193 if (LT != LHSComputationT) {
2194 if (!this->emitCast(*LT, *LHSComputationT, E))
2195 return false;
2196 }
2197
2198 // Get the RHS value on the stack.
2199 if (!this->emitGetLocal(*RT, TempOffset, E))
2200 return false;
2201
2202 // Perform operation.
2203 switch (E->getOpcode()) {
2204 case BO_AddAssign:
2205 if (!this->emitAdd(*LHSComputationT, E))
2206 return false;
2207 break;
2208 case BO_SubAssign:
2209 if (!this->emitSub(*LHSComputationT, E))
2210 return false;
2211 break;
2212 case BO_MulAssign:
2213 if (!this->emitMul(*LHSComputationT, E))
2214 return false;
2215 break;
2216 case BO_DivAssign:
2217 if (!this->emitDiv(*LHSComputationT, E))
2218 return false;
2219 break;
2220 case BO_RemAssign:
2221 if (!this->emitRem(*LHSComputationT, E))
2222 return false;
2223 break;
2224 case BO_ShlAssign:
2225 if (!this->emitShl(*LHSComputationT, *RT, E))
2226 return false;
2227 break;
2228 case BO_ShrAssign:
2229 if (!this->emitShr(*LHSComputationT, *RT, E))
2230 return false;
2231 break;
2232 case BO_AndAssign:
2233 if (!this->emitBitAnd(*LHSComputationT, E))
2234 return false;
2235 break;
2236 case BO_XorAssign:
2237 if (!this->emitBitXor(*LHSComputationT, E))
2238 return false;
2239 break;
2240 case BO_OrAssign:
2241 if (!this->emitBitOr(*LHSComputationT, E))
2242 return false;
2243 break;
2244 default:
2245 llvm_unreachable("Unimplemented compound assign operator");
2246 }
2247
2248 // And now cast from LHSComputationT to ResultT.
2249 if (ResultT != LHSComputationT) {
2250 if (!this->emitCast(*LHSComputationT, *ResultT, E))
2251 return false;
2252 }
2253
2254 // And store the result in LHS.
2255 if (DiscardResult) {
2256 if (LHS->refersToBitField())
2257 return this->emitStoreBitFieldPop(*ResultT, E);
2258 return this->emitStorePop(*ResultT, E);
2259 }
2260 if (LHS->refersToBitField())
2261 return this->emitStoreBitField(*ResultT, E);
2262 return this->emitStore(*ResultT, E);
2263}
2264
2265template <class Emitter>
2267 LocalScope<Emitter> ES(this);
2268 const Expr *SubExpr = E->getSubExpr();
2269
2270 return this->delegate(SubExpr) && ES.destroyLocals(E);
2271}
2272
2273template <class Emitter>
2275 const MaterializeTemporaryExpr *E) {
2276 const Expr *SubExpr = E->getSubExpr();
2277
2278 if (Initializing) {
2279 // We already have a value, just initialize that.
2280 return this->delegate(SubExpr);
2281 }
2282 // If we don't end up using the materialized temporary anyway, don't
2283 // bother creating it.
2284 if (DiscardResult)
2285 return this->discard(SubExpr);
2286
2287 // When we're initializing a global variable *or* the storage duration of
2288 // the temporary is explicitly static, create a global variable.
2289 std::optional<PrimType> SubExprT = classify(SubExpr);
2290 bool IsStatic = E->getStorageDuration() == SD_Static;
2291 if (IsStatic) {
2292 std::optional<unsigned> GlobalIndex = P.createGlobal(E);
2293 if (!GlobalIndex)
2294 return false;
2295
2296 const LifetimeExtendedTemporaryDecl *TempDecl =
2297 E->getLifetimeExtendedTemporaryDecl();
2298 if (IsStatic)
2299 assert(TempDecl);
2300
2301 if (SubExprT) {
2302 if (!this->visit(SubExpr))
2303 return false;
2304 if (IsStatic) {
2305 if (!this->emitInitGlobalTemp(*SubExprT, *GlobalIndex, TempDecl, E))
2306 return false;
2307 } else {
2308 if (!this->emitInitGlobal(*SubExprT, *GlobalIndex, E))
2309 return false;
2310 }
2311 return this->emitGetPtrGlobal(*GlobalIndex, E);
2312 }
2313
2314 // Non-primitive values.
2315 if (!this->emitGetPtrGlobal(*GlobalIndex, E))
2316 return false;
2317 if (!this->visitInitializer(SubExpr))
2318 return false;
2319 if (IsStatic)
2320 return this->emitInitGlobalTempComp(TempDecl, E);
2321 return true;
2322 }
2323
2324 // For everyhing else, use local variables.
2325 if (SubExprT) {
2326 unsigned LocalIndex = allocateLocalPrimitive(
2327 SubExpr, *SubExprT, /*IsConst=*/true, /*IsExtended=*/true);
2328 if (!this->visit(SubExpr))
2329 return false;
2330 if (!this->emitSetLocal(*SubExprT, LocalIndex, E))
2331 return false;
2332 return this->emitGetPtrLocal(LocalIndex, E);
2333 } else {
2334 const Expr *Inner = E->getSubExpr()->skipRValueSubobjectAdjustments();
2335 if (std::optional<unsigned> LocalIndex =
2336 allocateLocal(Inner, E->getExtendingDecl())) {
2337 InitLinkScope<Emitter> ILS(this, InitLink::Temp(*LocalIndex));
2338 if (!this->emitGetPtrLocal(*LocalIndex, E))
2339 return false;
2340 return this->visitInitializer(SubExpr);
2341 }
2342 }
2343 return false;
2344}
2345
2346template <class Emitter>
2348 const CXXBindTemporaryExpr *E) {
2349 return this->delegate(E->getSubExpr());
2350}
2351
2352template <class Emitter>
2354 const Expr *Init = E->getInitializer();
2355 if (DiscardResult)
2356 return this->discard(Init);
2357
2358 if (Initializing) {
2359 // We already have a value, just initialize that.
2360 return this->visitInitializer(Init) && this->emitFinishInit(E);
2361 }
2362
2363 std::optional<PrimType> T = classify(E->getType());
2364 if (E->isFileScope()) {
2365 // Avoid creating a variable if this is a primitive RValue anyway.
2366 if (T && !E->isLValue())
2367 return this->delegate(Init);
2368
2369 if (std::optional<unsigned> GlobalIndex = P.createGlobal(E)) {
2370 if (!this->emitGetPtrGlobal(*GlobalIndex, E))
2371 return false;
2372
2373 if (T) {
2374 if (!this->visit(Init))
2375 return false;
2376 return this->emitInitGlobal(*T, *GlobalIndex, E);
2377 }
2378
2379 return this->visitInitializer(Init) && this->emitFinishInit(E);
2380 }
2381
2382 return false;
2383 }
2384
2385 // Otherwise, use a local variable.
2386 if (T && !E->isLValue()) {
2387 // For primitive types, we just visit the initializer.
2388 return this->delegate(Init);
2389 } else {
2390 unsigned LocalIndex;
2391
2392 if (T)
2393 LocalIndex = this->allocateLocalPrimitive(Init, *T, false, false);
2394 else if (std::optional<unsigned> MaybeIndex = this->allocateLocal(Init))
2395 LocalIndex = *MaybeIndex;
2396 else
2397 return false;
2398
2399 if (!this->emitGetPtrLocal(LocalIndex, E))
2400 return false;
2401
2402 if (T) {
2403 if (!this->visit(Init)) {
2404 return false;
2405 }
2406 return this->emitInit(*T, E);
2407 } else {
2408 if (!this->visitInitializer(Init) || !this->emitFinishInit(E))
2409 return false;
2410 }
2411 return true;
2412 }
2413
2414 return false;
2415}
2416
2417template <class Emitter>
2419 if (DiscardResult)
2420 return true;
2421 if (E->getType()->isBooleanType())
2422 return this->emitConstBool(E->getValue(), E);
2423 return this->emitConst(E->getValue(), E);
2424}
2425
2426template <class Emitter>
2428 if (DiscardResult)
2429 return true;
2430 return this->emitConst(E->getValue(), E);
2431}
2432
2433template <class Emitter>
2435 if (DiscardResult)
2436 return true;
2437
2438 assert(Initializing);
2439 const Record *R = P.getOrCreateRecord(E->getLambdaClass());
2440
2441 auto *CaptureInitIt = E->capture_init_begin();
2442 // Initialize all fields (which represent lambda captures) of the
2443 // record with their initializers.
2444 for (const Record::Field &F : R->fields()) {
2445 const Expr *Init = *CaptureInitIt;
2446 ++CaptureInitIt;
2447
2448 if (!Init)
2449 continue;
2450
2451 if (std::optional<PrimType> T = classify(Init)) {
2452 if (!this->visit(Init))
2453 return false;
2454
2455 if (!this->emitInitField(*T, F.Offset, E))
2456 return false;
2457 } else {
2458 if (!this->emitGetPtrField(F.Offset, E))
2459 return false;
2460
2461 if (!this->visitInitializer(Init))
2462 return false;
2463
2464 if (!this->emitPopPtr(E))
2465 return false;
2466 }
2467 }
2468
2469 return true;
2470}
2471
2472template <class Emitter>
2474 if (DiscardResult)
2475 return true;
2476
2477 return this->delegate(E->getFunctionName());
2478}
2479
2480template <class Emitter>
2482 if (E->getSubExpr() && !this->discard(E->getSubExpr()))
2483 return false;
2484
2485 return this->emitInvalid(E);
2486}
2487
2488template <class Emitter>
2490 const CXXReinterpretCastExpr *E) {
2491 const Expr *SubExpr = E->getSubExpr();
2492
2493 bool TypesMatch = classify(E) == classify(SubExpr);
2494 if (!this->emitInvalidCast(CastKind::Reinterpret, /*Fatal=*/!TypesMatch, E))
2495 return false;
2496
2497 return this->delegate(SubExpr);
2498}
2499
2500template <class Emitter>
2502 assert(E->getType()->isBooleanType());
2503
2504 if (DiscardResult)
2505 return true;
2506 return this->emitConstBool(E->getValue(), E);
2507}
2508
2509template <class Emitter>
2511 QualType T = E->getType();
2512 assert(!classify(T));
2513
2514 if (T->isRecordType()) {
2515 const CXXConstructorDecl *Ctor = E->getConstructor();
2516
2517 // Trivial copy/move constructor. Avoid copy.
2518 if (Ctor->isDefaulted() && Ctor->isCopyOrMoveConstructor() &&
2519 Ctor->isTrivial() &&
2520 E->getArg(0)->isTemporaryObject(Ctx.getASTContext(),
2522 return this->visitInitializer(E->getArg(0));
2523
2524 // If we're discarding a construct expression, we still need
2525 // to allocate a variable and call the constructor and destructor.
2526 if (DiscardResult) {
2527 if (Ctor->isTrivial())
2528 return true;
2529 assert(!Initializing);
2530 std::optional<unsigned> LocalIndex = allocateLocal(E);
2531
2532 if (!LocalIndex)
2533 return false;
2534
2535 if (!this->emitGetPtrLocal(*LocalIndex, E))
2536 return false;
2537 }
2538
2539 // Zero initialization.
2540 if (E->requiresZeroInitialization()) {
2541 const Record *R = getRecord(E->getType());
2542
2543 if (!this->visitZeroRecordInitializer(R, E))
2544 return false;
2545
2546 // If the constructor is trivial anyway, we're done.
2547 if (Ctor->isTrivial())
2548 return true;
2549 }
2550
2551 const Function *Func = getFunction(Ctor);
2552
2553 if (!Func)
2554 return false;
2555
2556 assert(Func->hasThisPointer());
2557 assert(!Func->hasRVO());
2558
2559 // The This pointer is already on the stack because this is an initializer,
2560 // but we need to dup() so the call() below has its own copy.
2561 if (!this->emitDupPtr(E))
2562 return false;
2563
2564 // Constructor arguments.
2565 for (const auto *Arg : E->arguments()) {
2566 if (!this->visit(Arg))
2567 return false;
2568 }
2569
2570 if (Func->isVariadic()) {
2571 uint32_t VarArgSize = 0;
2572 unsigned NumParams = Func->getNumWrittenParams();
2573 for (unsigned I = NumParams, N = E->getNumArgs(); I != N; ++I) {
2574 VarArgSize +=
2575 align(primSize(classify(E->getArg(I)->getType()).value_or(PT_Ptr)));
2576 }
2577 if (!this->emitCallVar(Func, VarArgSize, E))
2578 return false;
2579 } else {
2580 if (!this->emitCall(Func, 0, E))
2581 return false;
2582 }
2583
2584 if (DiscardResult)
2585 return this->emitPopPtr(E);
2586 return this->emitFinishInit(E);
2587 }
2588
2589 if (T->isArrayType()) {
2590 const ConstantArrayType *CAT =
2591 Ctx.getASTContext().getAsConstantArrayType(E->getType());
2592 if (!CAT)
2593 return false;
2594
2595 size_t NumElems = CAT->getZExtSize();
2596 const Function *Func = getFunction(E->getConstructor());
2597 if (!Func || !Func->isConstexpr())
2598 return false;
2599
2600 // FIXME(perf): We're calling the constructor once per array element here,
2601 // in the old intepreter we had a special-case for trivial constructors.
2602 for (size_t I = 0; I != NumElems; ++I) {
2603 if (!this->emitConstUint64(I, E))
2604 return false;
2605 if (!this->emitArrayElemPtrUint64(E))
2606 return false;
2607
2608 // Constructor arguments.
2609 for (const auto *Arg : E->arguments()) {
2610 if (!this->visit(Arg))
2611 return false;
2612 }
2613
2614 if (!this->emitCall(Func, 0, E))
2615 return false;
2616 }
2617 return true;
2618 }
2619
2620 return false;
2621}
2622
2623template <class Emitter>
2625 if (DiscardResult)
2626 return true;
2627
2628 const APValue Val =
2629 E->EvaluateInContext(Ctx.getASTContext(), SourceLocDefaultExpr);
2630
2631 // Things like __builtin_LINE().
2632 if (E->getType()->isIntegerType()) {
2633 assert(Val.isInt());
2634 const APSInt &I = Val.getInt();
2635 return this->emitConst(I, E);
2636 }
2637 // Otherwise, the APValue is an LValue, with only one element.
2638 // Theoretically, we don't need the APValue at all of course.
2639 assert(E->getType()->isPointerType());
2640 assert(Val.isLValue());
2641 const APValue::LValueBase &Base = Val.getLValueBase();
2642 if (const Expr *LValueExpr = Base.dyn_cast<const Expr *>())
2643 return this->visit(LValueExpr);
2644
2645 // Otherwise, we have a decl (which is the case for
2646 // __builtin_source_location).
2647 assert(Base.is<const ValueDecl *>());
2648 assert(Val.getLValuePath().size() == 0);
2649 const auto *BaseDecl = Base.dyn_cast<const ValueDecl *>();
2650 assert(BaseDecl);
2651
2652 auto *UGCD = cast<UnnamedGlobalConstantDecl>(BaseDecl);
2653
2654 std::optional<unsigned> GlobalIndex = P.getOrCreateGlobal(UGCD);
2655 if (!GlobalIndex)
2656 return false;
2657
2658 if (!this->emitGetPtrGlobal(*GlobalIndex, E))
2659 return false;
2660
2661 const Record *R = getRecord(E->getType());
2662 const APValue &V = UGCD->getValue();
2663 for (unsigned I = 0, N = R->getNumFields(); I != N; ++I) {
2664 const Record::Field *F = R->getField(I);
2665 const APValue &FieldValue = V.getStructField(I);
2666
2667 PrimType FieldT = classifyPrim(F->Decl->getType());
2668
2669 if (!this->visitAPValue(FieldValue, FieldT, E))
2670 return false;
2671 if (!this->emitInitField(FieldT, F->Offset, E))
2672 return false;
2673 }
2674
2675 // Leave the pointer to the global on the stack.
2676 return true;
2677}
2678
2679template <class Emitter>
2681 unsigned N = E->getNumComponents();
2682 if (N == 0)
2683 return false;
2684
2685 for (unsigned I = 0; I != N; ++I) {
2686 const OffsetOfNode &Node = E->getComponent(I);
2687 if (Node.getKind() == OffsetOfNode::Array) {
2688 const Expr *ArrayIndexExpr = E->getIndexExpr(Node.getArrayExprIndex());
2689 PrimType IndexT = classifyPrim(ArrayIndexExpr->getType());
2690
2691 if (DiscardResult) {
2692 if (!this->discard(ArrayIndexExpr))
2693 return false;
2694 continue;
2695 }
2696
2697 if (!this->visit(ArrayIndexExpr))
2698 return false;
2699 // Cast to Sint64.
2700 if (IndexT != PT_Sint64) {
2701 if (!this->emitCast(IndexT, PT_Sint64, E))
2702 return false;
2703 }
2704 }
2705 }
2706
2707 if (DiscardResult)
2708 return true;
2709
2710 PrimType T = classifyPrim(E->getType());
2711 return this->emitOffsetOf(T, E, E);
2712}
2713
2714template <class Emitter>
2716 const CXXScalarValueInitExpr *E) {
2717 QualType Ty = E->getType();
2718
2719 if (DiscardResult || Ty->isVoidType())
2720 return true;
2721
2722 if (std::optional<PrimType> T = classify(Ty))
2723 return this->visitZeroInitializer(*T, Ty, E);
2724
2725 if (const auto *CT = Ty->getAs<ComplexType>()) {
2726 if (!Initializing) {
2727 std::optional<unsigned> LocalIndex = allocateLocal(E);
2728 if (!LocalIndex)
2729 return false;
2730 if (!this->emitGetPtrLocal(*LocalIndex, E))
2731 return false;
2732 }
2733
2734 // Initialize both fields to 0.
2735 QualType ElemQT = CT->getElementType();
2736 PrimType ElemT = classifyPrim(ElemQT);
2737
2738 for (unsigned I = 0; I != 2; ++I) {
2739 if (!this->visitZeroInitializer(ElemT, ElemQT, E))
2740 return false;
2741 if (!this->emitInitElem(ElemT, I, E))
2742 return false;
2743 }
2744 return true;
2745 }
2746
2747 if (const auto *VT = Ty->getAs<VectorType>()) {
2748 // FIXME: Code duplication with the _Complex case above.
2749 if (!Initializing) {
2750 std::optional<unsigned> LocalIndex = allocateLocal(E);
2751 if (!LocalIndex)
2752 return false;
2753 if (!this->emitGetPtrLocal(*LocalIndex, E))
2754 return false;
2755 }
2756
2757 // Initialize all fields to 0.
2758 QualType ElemQT = VT->getElementType();
2759 PrimType ElemT = classifyPrim(ElemQT);
2760
2761 for (unsigned I = 0, N = VT->getNumElements(); I != N; ++I) {
2762 if (!this->visitZeroInitializer(ElemT, ElemQT, E))
2763 return false;
2764 if (!this->emitInitElem(ElemT, I, E))
2765 return false;
2766 }
2767 return true;
2768 }
2769
2770 return false;
2771}
2772
2773template <class Emitter>
2775 return this->emitConst(E->getPackLength(), E);
2776}
2777
2778template <class Emitter>
2780 const GenericSelectionExpr *E) {
2781 return this->delegate(E->getResultExpr());
2782}
2783
2784template <class Emitter>
2786 return this->delegate(E->getChosenSubExpr());
2787}
2788
2789template <class Emitter>
2791 if (DiscardResult)
2792 return true;
2793
2794 return this->emitConst(E->getValue(), E);
2795}
2796
2797template <class Emitter>
2799 const CXXInheritedCtorInitExpr *E) {
2800 const CXXConstructorDecl *Ctor = E->getConstructor();
2801 assert(!Ctor->isTrivial() &&
2802 "Trivial CXXInheritedCtorInitExpr, implement. (possible?)");
2803 const Function *F = this->getFunction(Ctor);
2804 assert(F);
2805 assert(!F->hasRVO());
2806 assert(F->hasThisPointer());
2807
2808 if (!this->emitDupPtr(SourceInfo{}))
2809 return false;
2810
2811 // Forward all arguments of the current function (which should be a
2812 // constructor itself) to the inherited ctor.
2813 // This is necessary because the calling code has pushed the pointer
2814 // of the correct base for us already, but the arguments need
2815 // to come after.
2816 unsigned Offset = align(primSize(PT_Ptr)); // instance pointer.
2817 for (const ParmVarDecl *PD : Ctor->parameters()) {
2818 PrimType PT = this->classify(PD->getType()).value_or(PT_Ptr);
2819
2820 if (!this->emitGetParam(PT, Offset, E))
2821 return false;
2822 Offset += align(primSize(PT));
2823 }
2824
2825 return this->emitCall(F, 0, E);
2826}
2827
2828template <class Emitter>
2830 assert(classifyPrim(E->getType()) == PT_Ptr);
2831 const Expr *Init = E->getInitializer();
2832 QualType ElementType = E->getAllocatedType();
2833 std::optional<PrimType> ElemT = classify(ElementType);
2834 unsigned PlacementArgs = E->getNumPlacementArgs();
2835 bool IsNoThrow = false;
2836
2837 // FIXME: Better diagnostic. diag::note_constexpr_new_placement
2838 if (PlacementArgs != 0) {
2839 // The only new-placement list we support is of the form (std::nothrow).
2840 //
2841 // FIXME: There is no restriction on this, but it's not clear that any
2842 // other form makes any sense. We get here for cases such as:
2843 //
2844 // new (std::align_val_t{N}) X(int)
2845 //
2846 // (which should presumably be valid only if N is a multiple of
2847 // alignof(int), and in any case can't be deallocated unless N is
2848 // alignof(X) and X has new-extended alignment).
2849 if (PlacementArgs != 1 || !E->getPlacementArg(0)->getType()->isNothrowT())
2850 return this->emitInvalid(E);
2851
2852 if (!this->discard(E->getPlacementArg(0)))
2853 return false;
2854 IsNoThrow = true;
2855 }
2856
2857 const Descriptor *Desc;
2858 if (ElemT) {
2859 if (E->isArray())
2860 Desc = nullptr; // We're not going to use it in this case.
2861 else
2862 Desc = P.createDescriptor(E, *ElemT, Descriptor::InlineDescMD,
2863 /*IsConst=*/false, /*IsTemporary=*/false,
2864 /*IsMutable=*/false);
2865 } else {
2866 Desc = P.createDescriptor(
2867 E, ElementType.getTypePtr(),
2868 E->isArray() ? std::nullopt : Descriptor::InlineDescMD,
2869 /*IsConst=*/false, /*IsTemporary=*/false, /*IsMutable=*/false, Init);
2870 }
2871
2872 if (E->isArray()) {
2873 std::optional<const Expr *> ArraySizeExpr = E->getArraySize();
2874 if (!ArraySizeExpr)
2875 return false;
2876
2877 const Expr *Stripped = *ArraySizeExpr;
2878 for (; auto *ICE = dyn_cast<ImplicitCastExpr>(Stripped);
2879 Stripped = ICE->getSubExpr())
2880 if (ICE->getCastKind() != CK_NoOp &&
2881 ICE->getCastKind() != CK_IntegralCast)
2882 break;
2883
2884 PrimType SizeT = classifyPrim(Stripped->getType());
2885
2886 if (!this->visit(Stripped))
2887 return false;
2888
2889 if (ElemT) {
2890 // N primitive elements.
2891 if (!this->emitAllocN(SizeT, *ElemT, E, IsNoThrow, E))
2892 return false;
2893 } else {
2894 // N Composite elements.
2895 if (!this->emitAllocCN(SizeT, Desc, IsNoThrow, E))
2896 return false;
2897 }
2898
2899 if (Init && !this->visitInitializer(Init))
2900 return false;
2901
2902 } else {
2903 // Allocate just one element.
2904 if (!this->emitAlloc(Desc, E))
2905 return false;
2906
2907 if (Init) {
2908 if (ElemT) {
2909 if (!this->visit(Init))
2910 return false;
2911
2912 if (!this->emitInit(*ElemT, E))
2913 return false;
2914 } else {
2915 // Composite.
2916 if (!this->visitInitializer(Init))
2917 return false;
2918 }
2919 }
2920 }
2921
2922 if (DiscardResult)
2923 return this->emitPopPtr(E);
2924
2925 return true;
2926}
2927
2928template <class Emitter>
2930 const Expr *Arg = E->getArgument();
2931
2932 // Arg must be an lvalue.
2933 if (!this->visit(Arg))
2934 return false;
2935
2936 return this->emitFree(E->isArrayForm(), E);
2937}
2938
2939template <class Emitter>
2941 const Function *Func = nullptr;
2942 if (auto F = Compiler<ByteCodeEmitter>(Ctx, P).compileObjCBlock(E))
2943 Func = F;
2944
2945 if (!Func)
2946 return false;
2947 return this->emitGetFnPtr(Func, E);
2948}
2949
2950template <class Emitter>
2952 assert(Ctx.getLangOpts().CPlusPlus);
2953 return this->emitConstBool(E->getValue(), E);
2954}
2955
2956template <class Emitter>
2958 if (DiscardResult)
2959 return true;
2960 assert(!Initializing);
2961
2962 const MSGuidDecl *GuidDecl = E->getGuidDecl();
2963 const RecordDecl *RD = GuidDecl->getType()->getAsRecordDecl();
2964 assert(RD);
2965 // If the definiton of the result type is incomplete, just return a dummy.
2966 // If (and when) that is read from, we will fail, but not now.
2967 if (!RD->isCompleteDefinition()) {
2968 if (std::optional<unsigned> I = P.getOrCreateDummy(GuidDecl))
2969 return this->emitGetPtrGlobal(*I, E);
2970 return false;
2971 }
2972
2973 std::optional<unsigned> GlobalIndex = P.getOrCreateGlobal(GuidDecl);
2974 if (!GlobalIndex)
2975 return false;
2976 if (!this->emitGetPtrGlobal(*GlobalIndex, E))
2977 return false;
2978
2979 assert(this->getRecord(E->getType()));
2980
2981 const APValue &V = GuidDecl->getAsAPValue();
2982 if (V.getKind() == APValue::None)
2983 return true;
2984
2985 assert(V.isStruct());
2986 assert(V.getStructNumBases() == 0);
2987 if (!this->visitAPValueInitializer(V, E))
2988 return false;
2989
2990 return this->emitFinishInit(E);
2991}
2992
2993template <class Emitter>
2995 assert(classifyPrim(E->getType()) == PT_Bool);
2996 if (DiscardResult)
2997 return true;
2998 return this->emitConstBool(E->isSatisfied(), E);
2999}
3000
3001template <class Emitter>
3004 assert(classifyPrim(E->getType()) == PT_Bool);
3005 if (DiscardResult)
3006 return true;
3007 return this->emitConstBool(E->isSatisfied(), E);
3008}
3009
3010template <class Emitter>
3013 return this->delegate(E->getSemanticForm());
3014}
3015
3016template <class Emitter>
3018
3019 for (const Expr *SemE : E->semantics()) {
3020 if (auto *OVE = dyn_cast<OpaqueValueExpr>(SemE)) {
3021 if (SemE == E->getResultExpr())
3022 return false;
3023
3024 if (OVE->isUnique())
3025 continue;
3026
3027 if (!this->discard(OVE))
3028 return false;
3029 } else if (SemE == E->getResultExpr()) {
3030 if (!this->delegate(SemE))
3031 return false;
3032 } else {
3033 if (!this->discard(SemE))
3034 return false;
3035 }
3036 }
3037 return true;
3038}
3039
3040template <class Emitter>
3042 return this->delegate(E->getSelectedExpr());
3043}
3044
3045template <class Emitter>
3047 return this->emitError(E);
3048}
3049
3050template <class Emitter>
3052 assert(E->getType()->isVoidPointerType());
3053
3054 unsigned Offset = allocateLocalPrimitive(
3055 E->getLabel(), PT_Ptr, /*IsConst=*/true, /*IsExtended=*/false);
3056
3057 return this->emitGetLocal(PT_Ptr, Offset, E);
3058}
3059
3060template <class Emitter>
3062 assert(Initializing);
3063 const auto *VT = E->getType()->castAs<VectorType>();
3064 QualType ElemType = VT->getElementType();
3065 PrimType ElemT = classifyPrim(ElemType);
3066 const Expr *Src = E->getSrcExpr();
3067 PrimType SrcElemT =
3068 classifyPrim(Src->getType()->castAs<VectorType>()->getElementType());
3069
3070 unsigned SrcOffset = this->allocateLocalPrimitive(Src, PT_Ptr, true, false);
3071 if (!this->visit(Src))
3072 return false;
3073 if (!this->emitSetLocal(PT_Ptr, SrcOffset, E))
3074 return false;
3075
3076 for (unsigned I = 0; I != VT->getNumElements(); ++I) {
3077 if (!this->emitGetLocal(PT_Ptr, SrcOffset, E))
3078 return false;
3079 if (!this->emitArrayElemPop(SrcElemT, I, E))
3080 return false;
3081 if (SrcElemT != ElemT) {
3082 if (!this->emitPrimCast(SrcElemT, ElemT, ElemType, E))
3083 return false;
3084 }
3085 if (!this->emitInitElem(ElemT, I, E))
3086 return false;
3087 }
3088
3089 return true;
3090}
3091
3092template <class Emitter>
3094 assert(Initializing);
3095 assert(E->getNumSubExprs() > 2);
3096
3097 const Expr *Vecs[] = {E->getExpr(0), E->getExpr(1)};
3098 const VectorType *VT = Vecs[0]->getType()->castAs<VectorType>();
3099 PrimType ElemT = classifyPrim(VT->getElementType());
3100 unsigned NumInputElems = VT->getNumElements();
3101 unsigned NumOutputElems = E->getNumSubExprs() - 2;
3102 assert(NumOutputElems > 0);
3103
3104 // Save both input vectors to a local variable.
3105 unsigned VectorOffsets[2];
3106 for (unsigned I = 0; I != 2; ++I) {
3107 VectorOffsets[I] = this->allocateLocalPrimitive(
3108 Vecs[I], PT_Ptr, /*IsConst=*/true, /*IsExtended=*/false);
3109 if (!this->visit(Vecs[I]))
3110 return false;
3111 if (!this->emitSetLocal(PT_Ptr, VectorOffsets[I], E))
3112 return false;
3113 }
3114 for (unsigned I = 0; I != NumOutputElems; ++I) {
3115 APSInt ShuffleIndex = E->getShuffleMaskIdx(Ctx.getASTContext(), I);
3116 if (ShuffleIndex == -1)
3117 return this->emitInvalid(E); // FIXME: Better diagnostic.
3118
3119 assert(ShuffleIndex < (NumInputElems * 2));
3120 if (!this->emitGetLocal(PT_Ptr,
3121 VectorOffsets[ShuffleIndex >= NumInputElems], E))
3122 return false;
3123 unsigned InputVectorIndex = ShuffleIndex.getZExtValue() % NumInputElems;
3124 if (!this->emitArrayElemPop(ElemT, InputVectorIndex, E))
3125 return false;
3126
3127 if (!this->emitInitElem(ElemT, I, E))
3128 return false;
3129 }
3130
3131 return true;
3132}
3133
3134template <class Emitter>
3136 const ExtVectorElementExpr *E) {
3137 const Expr *Base = E->getBase();
3138 assert(
3139 Base->getType()->isVectorType() ||
3140 Base->getType()->getAs<PointerType>()->getPointeeType()->isVectorType());
3141
3143 E->getEncodedElementAccess(Indices);
3144
3145 if (Indices.size() == 1) {
3146 if (!this->visit(Base))
3147 return false;
3148
3149 if (E->isGLValue()) {
3150 if (!this->emitConstUint32(Indices[0], E))
3151 return false;
3152 return this->emitArrayElemPtrPop(PT_Uint32, E);
3153 }
3154 // Else, also load the value.
3155 return this->emitArrayElemPop(classifyPrim(E->getType()), Indices[0], E);
3156 }
3157
3158 // Create a local variable for the base.
3159 unsigned BaseOffset = allocateLocalPrimitive(Base, PT_Ptr, /*IsConst=*/true,
3160 /*IsExtended=*/false);
3161 if (!this->visit(Base))
3162 return false;
3163 if (!this->emitSetLocal(PT_Ptr, BaseOffset, E))
3164 return false;
3165
3166 // Now the vector variable for the return value.
3167 if (!Initializing) {
3168 std::optional<unsigned> ResultIndex;
3169 ResultIndex = allocateLocal(E);
3170 if (!ResultIndex)
3171 return false;
3172 if (!this->emitGetPtrLocal(*ResultIndex, E))
3173 return false;
3174 }
3175
3176 assert(Indices.size() == E->getType()->getAs<VectorType>()->getNumElements());
3177
3178 PrimType ElemT =
3179 classifyPrim(E->getType()->getAs<VectorType>()->getElementType());
3180 uint32_t DstIndex = 0;
3181 for (uint32_t I : Indices) {
3182 if (!this->emitGetLocal(PT_Ptr, BaseOffset, E))
3183 return false;
3184 if (!this->emitArrayElemPop(ElemT, I, E))
3185 return false;
3186 if (!this->emitInitElem(ElemT, DstIndex, E))
3187 return false;
3188 ++DstIndex;
3189 }
3190
3191 // Leave the result pointer on the stack.
3192 assert(!DiscardResult);
3193 return true;
3194}
3195
3196template <class Emitter>
3198 const Expr *SubExpr = E->getSubExpr();
3199 if (!E->isExpressibleAsConstantInitializer())
3200 return this->discard(SubExpr) && this->emitInvalid(E);
3201
3202 return this->delegate(SubExpr);
3203}
3204
3205template <class Emitter>
3208 const Expr *SubExpr = E->getSubExpr();
3210 Ctx.getASTContext().getAsConstantArrayType(SubExpr->getType());
3211 const Record *R = getRecord(E->getType());
3212 assert(Initializing);
3213 assert(SubExpr->isGLValue());
3214
3215 if (!this->visit(SubExpr))
3216 return false;
3217 if (!this->emitInitFieldPtr(R->getField(0u)->Offset, E))
3218 return false;
3219
3220 PrimType SecondFieldT = classifyPrim(R->getField(1u)->Decl->getType());
3221 if (isIntegralType(SecondFieldT)) {
3222 if (!this->emitConst(static_cast<APSInt>(ArrayType->getSize()),
3223 SecondFieldT, E))
3224 return false;
3225 return this->emitInitField(SecondFieldT, R->getField(1u)->Offset, E);
3226 }
3227 assert(SecondFieldT == PT_Ptr);
3228
3229 if (!this->emitGetFieldPtr(R->getField(0u)->Offset, E))
3230 return false;
3231 if (!this->emitConst(static_cast<APSInt>(ArrayType->getSize()), PT_Uint64, E))
3232 return false;
3233 if (!this->emitArrayElemPtrPop(PT_Uint64, E))
3234 return false;
3235 return this->emitInitFieldPtr(R->getField(1u)->Offset, E);
3236}
3237
3238template <class Emitter>
3240 BlockScope<Emitter> BS(this);
3241 StmtExprScope<Emitter> SS(this);
3242
3243 const CompoundStmt *CS = E->getSubStmt();
3244 const Stmt *Result = CS->getStmtExprResult();
3245 for (const Stmt *S : CS->body()) {
3246 if (S != Result) {
3247 if (!this->visitStmt(S))
3248 return false;
3249 continue;
3250 }
3251
3252 assert(S == Result);
3253 if (const Expr *ResultExpr = dyn_cast<Expr>(S))
3254 return this->delegate(ResultExpr);
3255 return this->emitUnsupported(E);
3256 }
3257
3258 return BS.destroyLocals();
3259}
3260
3261template <class Emitter> bool Compiler<Emitter>::discard(const Expr *E) {
3262 OptionScope<Emitter> Scope(this, /*NewDiscardResult=*/true,
3263 /*NewInitializing=*/false);
3264 return this->Visit(E);
3265}
3266
3267template <class Emitter> bool Compiler<Emitter>::delegate(const Expr *E) {
3268 // We're basically doing:
3269 // OptionScope<Emitter> Scope(this, DicardResult, Initializing);
3270 // but that's unnecessary of course.
3271 return this->Visit(E);
3272}
3273
3274template <class Emitter> bool Compiler<Emitter>::visit(const Expr *E) {
3275 if (E->getType().isNull())
3276 return false;
3277
3278 if (E->getType()->isVoidType())
3279 return this->discard(E);
3280
3281 // Create local variable to hold the return value.
3282 if (!E->isGLValue() && !E->getType()->isAnyComplexType() &&
3283 !classify(E->getType())) {
3284 std::optional<unsigned> LocalIndex = allocateLocal(E);
3285 if (!LocalIndex)
3286 return false;
3287
3288 if (!this->emitGetPtrLocal(*LocalIndex, E))
3289 return false;
3290 return this->visitInitializer(E);
3291 }
3292
3293 // Otherwise,we have a primitive return value, produce the value directly
3294 // and push it on the stack.
3295 OptionScope<Emitter> Scope(this, /*NewDiscardResult=*/false,
3296 /*NewInitializing=*/false);
3297 return this->Visit(E);
3298}
3299
3300template <class Emitter>
3302 assert(!classify(E->getType()));
3303
3304 if (E->containsErrors())
3305 return this->emitError(E);
3306
3307 if (!this->checkLiteralType(E))
3308 return false;
3309
3310 OptionScope<Emitter> Scope(this, /*NewDiscardResult=*/false,
3311 /*NewInitializing=*/true);
3312 return this->Visit(E);
3313}
3314
3315template <class Emitter> bool Compiler<Emitter>::visitBool(const Expr *E) {
3316 std::optional<PrimType> T = classify(E->getType());
3317 if (!T) {
3318 // Convert complex values to bool.
3319 if (E->getType()->isAnyComplexType()) {
3320 if (!this->visit(E))
3321 return false;
3322 return this->emitComplexBoolCast(E);
3323 }
3324 return false;
3325 }
3326
3327 if (!this->visit(E))
3328 return false;
3329
3330 if (T == PT_Bool)
3331 return true;
3332
3333 // Convert pointers to bool.
3334 if (T == PT_Ptr || T == PT_FnPtr) {
3335 if (!this->emitNull(*T, nullptr, E))
3336 return false;
3337 return this->emitNE(*T, E);
3338 }
3339
3340 // Or Floats.
3341 if (T == PT_Float)
3342 return this->emitCastFloatingIntegralBool(E);
3343
3344 // Or anything else we can.
3345 return this->emitCast(*T, PT_Bool, E);
3346}
3347
3348template <class Emitter>
3350 const Expr *E) {
3351 switch (T) {
3352 case PT_Bool:
3353 return this->emitZeroBool(E);
3354 case PT_Sint8:
3355 return this->emitZeroSint8(E);
3356 case PT_Uint8:
3357 return this->emitZeroUint8(E);
3358 case PT_Sint16:
3359 return this->emitZeroSint16(E);
3360 case PT_Uint16:
3361 return this->emitZeroUint16(E);
3362 case PT_Sint32:
3363 return this->emitZeroSint32(E);
3364 case PT_Uint32:
3365 return this->emitZeroUint32(E);
3366 case PT_Sint64:
3367 return this->emitZeroSint64(E);
3368 case PT_Uint64:
3369 return this->emitZeroUint64(E);
3370 case PT_IntAP:
3371 return this->emitZeroIntAP(Ctx.getBitWidth(QT), E);
3372 case PT_IntAPS:
3373 return this->emitZeroIntAPS(Ctx.getBitWidth(QT), E);
3374 case PT_Ptr:
3375 return this->emitNullPtr(nullptr, E);
3376 case PT_FnPtr:
3377 return this->emitNullFnPtr(nullptr, E);
3378 case PT_MemberPtr:
3379 return this->emitNullMemberPtr(nullptr, E);
3380 case PT_Float: {
3381 return this->emitConstFloat(APFloat::getZero(Ctx.getFloatSemantics(QT)), E);
3382 }
3383 }
3384 llvm_unreachable("unknown primitive type");
3385}
3386
3387template <class Emitter>
3389 const Expr *E) {
3390 assert(E);
3391 assert(R);
3392 // Fields
3393 for (const Record::Field &Field : R->fields()) {
3394 if (Field.Decl->isUnnamedBitField())
3395 continue;
3396
3397 const Descriptor *D = Field.Desc;
3398 if (D->isPrimitive()) {
3399 QualType QT = D->getType();
3400 PrimType T = classifyPrim(D->getType());
3401 if (!this->visitZeroInitializer(T, QT, E))
3402 return false;
3403 if (!this->emitInitField(T, Field.Offset, E))
3404 return false;
3405 if (R->isUnion())
3406 break;
3407 continue;
3408 }
3409
3410 if (!this->emitGetPtrField(Field.Offset, E))
3411 return false;
3412
3413 if (D->isPrimitiveArray()) {
3414 QualType ET = D->getElemQualType();
3415 PrimType T = classifyPrim(ET);
3416 for (uint32_t I = 0, N = D->getNumElems(); I != N; ++I) {
3417 if (!this->visitZeroInitializer(T, ET, E))
3418 return false;
3419 if (!this->emitInitElem(T, I, E))
3420 return false;
3421 }
3422 } else if (D->isCompositeArray()) {
3423 const Record *ElemRecord = D->ElemDesc->ElemRecord;
3424 assert(D->ElemDesc->ElemRecord);
3425 for (uint32_t I = 0, N = D->getNumElems(); I != N; ++I) {
3426 if (!this->emitConstUint32(I, E))
3427 return false;
3428 if (!this->emitArrayElemPtr(PT_Uint32, E))
3429 return false;
3430 if (!this->visitZeroRecordInitializer(ElemRecord, E))
3431 return false;
3432 if (!this->emitPopPtr(E))
3433 return false;
3434 }
3435 } else if (D->isRecord()) {
3436 if (!this->visitZeroRecordInitializer(D->ElemRecord, E))
3437 return false;
3438 } else {
3439 assert(false);
3440 }
3441
3442 if (!this->emitFinishInitPop(E))
3443 return false;
3444
3445 if (R->isUnion())
3446 break;
3447 }
3448
3449 for (const Record::Base &B : R->bases()) {
3450 if (!this->emitGetPtrBase(B.Offset, E))
3451 return false;
3452 if (!this->visitZeroRecordInitializer(B.R, E))
3453 return false;
3454 if (!this->emitFinishInitPop(E))
3455 return false;
3456 }
3457
3458 // FIXME: Virtual bases.
3459
3460 return true;
3461}
3462
3463template <class Emitter>
3464template <typename T>
3466 switch (Ty) {
3467 case PT_Sint8:
3468 return this->emitConstSint8(Value, E);
3469 case PT_Uint8:
3470 return this->emitConstUint8(Value, E);
3471 case PT_Sint16:
3472 return this->emitConstSint16(Value, E);
3473 case PT_Uint16:
3474 return this->emitConstUint16(Value, E);
3475 case PT_Sint32:
3476 return this->emitConstSint32(Value, E);
3477 case PT_Uint32:
3478 return this->emitConstUint32(Value, E);
3479 case PT_Sint64:
3480 return this->emitConstSint64(Value, E);
3481 case PT_Uint64:
3482 return this->emitConstUint64(Value, E);
3483 case PT_Bool:
3484 return this->emitConstBool(Value, E);
3485 case PT_Ptr:
3486 case PT_FnPtr:
3487 case PT_MemberPtr:
3488 case PT_Float:
3489 case PT_IntAP:
3490 case PT_IntAPS:
3491 llvm_unreachable("Invalid integral type");
3492 break;
3493 }
3494 llvm_unreachable("unknown primitive type");
3495}
3496
3497template <class Emitter>
3498template <typename T>
3500 return this->emitConst(Value, classifyPrim(E->getType()), E);
3501}
3502
3503template <class Emitter>
3505 const Expr *E) {
3506 if (Ty == PT_IntAPS)
3507 return this->emitConstIntAPS(Value, E);
3508 if (Ty == PT_IntAP)
3509 return this->emitConstIntAP(Value, E);
3510
3511 if (Value.isSigned())
3512 return this->emitConst(Value.getSExtValue(), Ty, E);
3513 return this->emitConst(Value.getZExtValue(), Ty, E);
3514}
3515
3516template <class Emitter>
3517bool Compiler<Emitter>::emitConst(const APSInt &Value, const Expr *E) {
3518 return this->emitConst(Value, classifyPrim(E->getType()), E);
3519}
3520
3521template <class Emitter>
3523 bool IsConst,
3524 bool IsExtended) {
3525 // Make sure we don't accidentally register the same decl twice.
3526 if (const auto *VD =
3527 dyn_cast_if_present<ValueDecl>(Src.dyn_cast<const Decl *>())) {
3528 assert(!P.getGlobal(VD));
3529 assert(!Locals.contains(VD));
3530 (void)VD;
3531 }
3532
3533 // FIXME: There are cases where Src.is<Expr*>() is wrong, e.g.
3534 // (int){12} in C. Consider using Expr::isTemporaryObject() instead
3535 // or isa<MaterializeTemporaryExpr>().
3536 Descriptor *D = P.createDescriptor(Src, Ty, Descriptor::InlineDescMD, IsConst,
3537 Src.is<const Expr *>());
3538 Scope::Local Local = this->createLocal(D);
3539 if (auto *VD = dyn_cast_if_present<ValueDecl>(Src.dyn_cast<const Decl *>()))
3540 Locals.insert({VD, Local});
3541 VarScope->add(Local, IsExtended);
3542 return Local.Offset;
3543}
3544
3545template <class Emitter>
3546std::optional<unsigned>
3548 // Make sure we don't accidentally register the same decl twice.
3549 if ([[maybe_unused]] const auto *VD =
3550 dyn_cast_if_present<ValueDecl>(Src.dyn_cast<const Decl *>())) {
3551 assert(!P.getGlobal(VD));
3552 assert(!Locals.contains(VD));
3553 }
3554
3555 QualType Ty;
3556 const ValueDecl *Key = nullptr;
3557 const Expr *Init = nullptr;
3558 bool IsTemporary = false;
3559 if (auto *VD = dyn_cast_if_present<ValueDecl>(Src.dyn_cast<const Decl *>())) {
3560 Key = VD;
3561 Ty = VD->getType();
3562
3563 if (const auto *VarD = dyn_cast<VarDecl>(VD))
3564 Init = VarD->getInit();
3565 }
3566 if (auto *E = Src.dyn_cast<const Expr *>()) {
3567 IsTemporary = true;
3568 Ty = E->getType();
3569 }
3570
3571 Descriptor *D = P.createDescriptor(
3573 IsTemporary, /*IsMutable=*/false, Init);
3574 if (!D)
3575 return std::nullopt;
3576
3577 Scope::Local Local = this->createLocal(D);
3578 if (Key)
3579 Locals.insert({Key, Local});
3580 if (ExtendingDecl)
3581 VarScope->addExtended(Local, ExtendingDecl);
3582 else
3583 VarScope->add(Local, false);
3584 return Local.Offset;
3585}
3586
3587template <class Emitter>
3589 QualType Ty = E->getType();
3590 assert(!Ty->isRecordType());
3591
3592 Descriptor *D = P.createDescriptor(
3594 /*IsTemporary=*/true, /*IsMutable=*/false, /*Init=*/nullptr);
3595 assert(D);
3596
3597 Scope::Local Local = this->createLocal(D);
3598 VariableScope<Emitter> *S = VarScope;
3599 assert(S);
3600 // Attach to topmost scope.
3601 while (S->getParent())
3602 S = S->getParent();
3603 assert(S && !S->getParent());
3604 S->addLocal(Local);
3605 return Local.Offset;
3606}
3607
3608template <class Emitter>
3610 if (const PointerType *PT = dyn_cast<PointerType>(Ty))
3611 return PT->getPointeeType()->getAs<RecordType>();
3612 return Ty->getAs<RecordType>();
3613}
3614
3615template <class Emitter> Record *Compiler<Emitter>::getRecord(QualType Ty) {
3616 if (const auto *RecordTy = getRecordTy(Ty))
3617 return getRecord(RecordTy->getDecl());
3618 return nullptr;
3619}
3620
3621template <class Emitter>
3623 return P.getOrCreateRecord(RD);
3624}
3625
3626template <class Emitter>
3628 return Ctx.getOrCreateFunction(FD);
3629}
3630
3631template <class Emitter> bool Compiler<Emitter>::visitExpr(const Expr *E) {
3632 LocalScope<Emitter> RootScope(this);
3633 // Void expressions.
3634 if (E->getType()->isVoidType()) {
3635 if (!visit(E))
3636 return false;
3637 return this->emitRetVoid(E) && RootScope.destroyLocals();
3638 }
3639
3640 // Expressions with a primitive return type.
3641 if (std::optional<PrimType> T = classify(E)) {
3642 if (!visit(E))
3643 return false;
3644 return this->emitRet(*T, E) && RootScope.destroyLocals();
3645 }
3646
3647 // Expressions with a composite return type.
3648 // For us, that means everything we don't
3649 // have a PrimType for.
3650 if (std::optional<unsigned> LocalOffset = this->allocateLocal(E)) {
3651 if (!this->emitGetPtrLocal(*LocalOffset, E))
3652 return false;
3653
3654 if (!visitInitializer(E))
3655 return false;
3656
3657 if (!this->emitFinishInit(E))
3658 return false;
3659 // We are destroying the locals AFTER the Ret op.
3660 // The Ret op needs to copy the (alive) values, but the
3661 // destructors may still turn the entire expression invalid.
3662 return this->emitRetValue(E) && RootScope.destroyLocals();
3663 }
3664
3665 RootScope.destroyLocals();
3666 return false;
3667}
3668
3669template <class Emitter>
3671
3672 auto R = this->visitVarDecl(VD, /*Toplevel=*/true);
3673
3674 if (R.notCreated())
3675 return R;
3676
3677 if (R)
3678 return true;
3679
3680 if (!R && Context::shouldBeGloballyIndexed(VD)) {
3681 if (auto GlobalIndex = P.getGlobal(VD)) {
3682 Block *GlobalBlock = P.getGlobal(*GlobalIndex);
3684 *reinterpret_cast<GlobalInlineDescriptor *>(GlobalBlock->rawData());
3685
3686 GD.InitState = GlobalInitState::InitializerFailed;
3687 GlobalBlock->invokeDtor();
3688 }
3689 }
3690
3691 return R;
3692}
3693
3694/// Toplevel visitDeclAndReturn().
3695/// We get here from evaluateAsInitializer().
3696/// We need to evaluate the initializer and return its value.
3697template <class Emitter>
3699 bool ConstantContext) {
3700 std::optional<PrimType> VarT = classify(VD->getType());
3701
3702 // We only create variables if we're evaluating in a constant context.
3703 // Otherwise, just evaluate the initializer and return it.
3704 if (!ConstantContext) {
3705 DeclScope<Emitter> LS(this, VD);
3706 if (!this->visit(VD->getAnyInitializer()))
3707 return false;
3708 return this->emitRet(VarT.value_or(PT_Ptr), VD) && LS.destroyLocals();
3709 }
3710
3711 LocalScope<Emitter> VDScope(this, VD);
3712 if (!this->visitVarDecl(VD, /*Toplevel=*/true))
3713 return false;
3714
3716 auto GlobalIndex = P.getGlobal(VD);
3717 assert(GlobalIndex); // visitVarDecl() didn't return false.
3718 if (VarT) {
3719 if (!this->emitGetGlobalUnchecked(*VarT, *GlobalIndex, VD))
3720 return false;
3721 } else {
3722 if (!this->emitGetPtrGlobal(*GlobalIndex, VD))
3723 return false;
3724 }
3725 } else {
3726 auto Local = Locals.find(VD);
3727 assert(Local != Locals.end()); // Same here.
3728 if (VarT) {
3729 if (!this->emitGetLocal(*VarT, Local->second.Offset, VD))
3730 return false;
3731 } else {
3732 if (!this->emitGetPtrLocal(Local->second.Offset, VD))
3733 return false;
3734 }
3735 }
3736
3737 // Return the value.
3738 if (!this->emitRet(VarT.value_or(PT_Ptr), VD)) {
3739 // If the Ret above failed and this is a global variable, mark it as
3740 // uninitialized, even everything else succeeded.
3742 auto GlobalIndex = P.getGlobal(VD);
3743 assert(GlobalIndex);
3744 Block *GlobalBlock = P.getGlobal(*GlobalIndex);
3746 *reinterpret_cast<GlobalInlineDescriptor *>(GlobalBlock->rawData());
3747
3748 GD.InitState = GlobalInitState::InitializerFailed;
3749 GlobalBlock->invokeDtor();
3750 }
3751 return false;
3752 }
3753
3754 return VDScope.destroyLocals();
3755}
3756
3757template <class Emitter>
3759 bool Toplevel) {
3760 // We don't know what to do with these, so just return false.
3761 if (VD->getType().isNull())
3762 return false;
3763
3764 // This case is EvalEmitter-only. If we won't create any instructions for the
3765 // initializer anyway, don't bother creating the variable in the first place.
3766 if (!this->isActive())
3768
3769 const Expr *Init = VD->getInit();
3770 std::optional<PrimType> VarT = classify(VD->getType());
3771
3772 if (Init && Init->isValueDependent())
3773 return false;
3774
3776 auto checkDecl = [&]() -> bool {
3777 bool NeedsOp = !Toplevel && VD->isLocalVarDecl() && VD->isStaticLocal();
3778 return !NeedsOp || this->emitCheckDecl(VD, VD);
3779 };
3780
3781 auto initGlobal = [&](unsigned GlobalIndex) -> bool {
3782 assert(Init);
3784
3785 if (VarT) {
3786 if (!this->visit(Init))
3787 return checkDecl() && false;
3788
3789 return checkDecl() && this->emitInitGlobal(*VarT, GlobalIndex, VD);
3790 }
3791
3792 if (!checkDecl())
3793 return false;
3794
3795 if (!this->emitGetPtrGlobal(GlobalIndex, Init))
3796 return false;
3797
3798 if (!visitInitializer(Init))
3799 return false;
3800
3801 if (!this->emitFinishInit(Init))
3802 return false;
3803
3804 return this->emitPopPtr(Init);
3805 };
3806
3807 // We've already seen and initialized this global.
3808 if (std::optional<unsigned> GlobalIndex = P.getGlobal(VD)) {
3809 if (P.getPtrGlobal(*GlobalIndex).isInitialized())
3810 return checkDecl();
3811
3812 // The previous attempt at initialization might've been unsuccessful,
3813 // so let's try this one.
3814 return Init && checkDecl() && initGlobal(*GlobalIndex);
3815 }
3816
3817 std::optional<unsigned> GlobalIndex = P.createGlobal(VD, Init);
3818
3819 if (!GlobalIndex)
3820 return false;
3821
3822 return !Init || (checkDecl() && initGlobal(*GlobalIndex));
3823 } else {
3825
3826 if (VarT) {
3827 unsigned Offset = this->allocateLocalPrimitive(
3828 VD, *VarT, VD->getType().isConstQualified());
3829 if (Init) {
3830 // If this is a toplevel declaration, create a scope for the
3831 // initializer.
3832 if (Toplevel) {
3834 if (!this->visit(Init))
3835 return false;
3836 return this->emitSetLocal(*VarT, Offset, VD) && Scope.destroyLocals();
3837 } else {
3838 if (!this->visit(Init))
3839 return false;
3840 return this->emitSetLocal(*VarT, Offset, VD);
3841 }
3842 }
3843 } else {
3844 if (std::optional<unsigned> Offset = this->allocateLocal(VD)) {
3845 if (!Init)
3846 return true;
3847
3848 if (!this->emitGetPtrLocal(*Offset, Init))
3849 return false;
3850
3851 if (!visitInitializer(Init))
3852 return false;
3853
3854 if (!this->emitFinishInit(Init))
3855 return false;
3856
3857 return this->emitPopPtr(Init);
3858 }
3859 return false;
3860 }
3861 return true;
3862 }
3863
3864 return false;
3865}
3866
3867template <class Emitter>
3869 const Expr *E) {
3870 assert(!DiscardResult);
3871 if (Val.isInt())
3872 return this->emitConst(Val.getInt(), ValType, E);
3873 else if (Val.isFloat())
3874 return this->emitConstFloat(Val.getFloat(), E);
3875
3876 if (Val.isLValue()) {
3877 if (Val.isNullPointer())
3878 return this->emitNull(ValType, nullptr, E);
3880 if (const Expr *BaseExpr = Base.dyn_cast<const Expr *>())
3881 return this->visit(BaseExpr);
3882 else if (const auto *VD = Base.dyn_cast<const ValueDecl *>()) {
3883 return this->visitDeclRef(VD, E);
3884 }
3885 } else if (Val.isMemberPointer()) {
3886 if (const ValueDecl *MemberDecl = Val.getMemberPointerDecl())
3887 return this->emitGetMemberPtr(MemberDecl, E);
3888 return this->emitNullMemberPtr(nullptr, E);
3889 }
3890
3891 return false;
3892}
3893
3894template <class Emitter>
3896 const Expr *E) {
3897
3898 if (Val.isStruct()) {
3899 const Record *R = this->getRecord(E->getType());
3900 assert(R);
3901 for (unsigned I = 0, N = Val.getStructNumFields(); I != N; ++I) {
3902 const APValue &F = Val.getStructField(I);
3903 const Record::Field *RF = R->getField(I);
3904
3905 if (F.isInt() || F.isFloat() || F.isLValue() || F.isMemberPointer()) {
3906 PrimType T = classifyPrim(RF->Decl->getType());
3907 if (!this->visitAPValue(F, T, E))
3908 return false;
3909 if (!this->emitInitField(T, RF->Offset, E))
3910 return false;
3911 } else if (F.isArray()) {
3912 assert(RF->Desc->isPrimitiveArray());
3913 const auto *ArrType = RF->Decl->getType()->getAsArrayTypeUnsafe();
3914 PrimType ElemT = classifyPrim(ArrType->getElementType());
3915 assert(ArrType);
3916
3917 if (!this->emitGetPtrField(RF->Offset, E))
3918 return false;
3919
3920 for (unsigned A = 0, AN = F.getArraySize(); A != AN; ++A) {
3921 if (!this->visitAPValue(F.getArrayInitializedElt(A), ElemT, E))
3922 return false;
3923 if (!this->emitInitElem(ElemT, A, E))
3924 return false;
3925 }
3926
3927 if (!this->emitPopPtr(E))
3928 return false;
3929 } else if (F.isStruct() || F.isUnion()) {
3930 if (!this->emitGetPtrField(RF->Offset, E))
3931 return false;
3932 if (!this->visitAPValueInitializer(F, E))
3933 return false;
3934 if (!this->emitPopPtr(E))
3935 return false;
3936 } else {
3937 assert(false && "I don't think this should be possible");
3938 }
3939 }
3940 return true;
3941 } else if (Val.isUnion()) {
3942 const FieldDecl *UnionField = Val.getUnionField();
3943 const Record *R = this->getRecord(UnionField->getParent());
3944 assert(R);
3945 const APValue &F = Val.getUnionValue();
3946 const Record::Field *RF = R->getField(UnionField);
3947 PrimType T = classifyPrim(RF->Decl->getType());
3948 if (!this->visitAPValue(F, T, E))
3949 return false;
3950 return this->emitInitField(T, RF->Offset, E);
3951 }
3952 // TODO: Other types.
3953
3954 return false;
3955}
3956
3957template <class Emitter>
3959 const Function *Func = getFunction(E->getDirectCallee());
3960 if (!Func)
3961 return false;
3962
3963 // For these, we're expected to ultimately return an APValue pointing
3964 // to the CallExpr. This is needed to get the correct codegen.
3965 unsigned Builtin = E->getBuiltinCallee();
3966 if (Builtin == Builtin::BI__builtin___CFStringMakeConstantString ||
3967 Builtin == Builtin::BI__builtin___NSStringMakeConstantString ||
3968 Builtin == Builtin::BI__builtin_ptrauth_sign_constant ||
3969 Builtin == Builtin::BI__builtin_function_start) {
3970 if (std::optional<unsigned> GlobalOffset = P.createGlobal(E)) {
3971 if (!this->emitGetPtrGlobal(*GlobalOffset, E))
3972 return false;
3973
3974 if (PrimType PT = classifyPrim(E); PT != PT_Ptr && isPtrType(PT))
3975 return this->emitDecayPtr(PT_Ptr, PT, E);
3976 return true;
3977 }
3978 return false;
3979 }
3980
3981 QualType ReturnType = E->getType();
3982 std::optional<PrimType> ReturnT = classify(E);
3983
3984 // Non-primitive return type. Prepare storage.
3985 if (!Initializing && !ReturnT && !ReturnType->isVoidType()) {
3986 std::optional<unsigned> LocalIndex = allocateLocal(E);
3987 if (!LocalIndex)
3988 return false;
3989 if (!this->emitGetPtrLocal(*LocalIndex, E))
3990 return false;
3991 }
3992
3993 if (!Func->isUnevaluatedBuiltin()) {
3994 // Put arguments on the stack.
3995 for (const auto *Arg : E->arguments()) {
3996 if (!this->visit(Arg))
3997 return false;
3998 }
3999 }
4000
4001 if (!this->emitCallBI(Func, E, E))
4002 return false;
4003
4004 if (DiscardResult && !ReturnType->isVoidType()) {
4005 assert(ReturnT);
4006 return this->emitPop(*ReturnT, E);
4007 }
4008
4009 return true;
4010}
4011
4012template <class Emitter>
4014 if (E->getBuiltinCallee())
4015 return VisitBuiltinCallExpr(E);
4016
4017 QualType ReturnType = E->getCallReturnType(Ctx.getASTContext());
4018 std::optional<PrimType> T = classify(ReturnType);
4019 bool HasRVO = !ReturnType->isVoidType() && !T;
4020 const FunctionDecl *FuncDecl = E->getDirectCallee();
4021
4022 if (HasRVO) {
4023 if (DiscardResult) {
4024 // If we need to discard the return value but the function returns its
4025 // value via an RVO pointer, we need to create one such pointer just
4026 // for this call.
4027 if (std::optional<unsigned> LocalIndex = allocateLocal(E)) {
4028 if (!this->emitGetPtrLocal(*LocalIndex, E))
4029 return false;
4030 }
4031 } else {
4032 // We need the result. Prepare a pointer to return or
4033 // dup the current one.
4034 if (!Initializing) {
4035 if (std::optional<unsigned> LocalIndex = allocateLocal(E)) {
4036 if (!this->emitGetPtrLocal(*LocalIndex, E))
4037 return false;
4038 }
4039 }
4040 if (!this->emitDupPtr(E))
4041 return false;
4042 }
4043 }
4044
4046 llvm::ArrayRef(E->getArgs(), E->getNumArgs()));
4047
4048 bool IsAssignmentOperatorCall = false;
4049 if (const auto *OCE = dyn_cast<CXXOperatorCallExpr>(E);
4050 OCE && OCE->isAssignmentOp()) {
4051 // Just like with regular assignments, we need to special-case assignment
4052 // operators here and evaluate the RHS (the second arg) before the LHS (the
4053 // first arg. We fix this by using a Flip op later.
4054 assert(Args.size() == 2);
4055 IsAssignmentOperatorCall = true;
4056 std::reverse(Args.begin(), Args.end());
4057 }
4058 // Calling a static operator will still
4059 // pass the instance, but we don't need it.
4060 // Discard it here.
4061 if (isa<CXXOperatorCallExpr>(E)) {
4062 if (const auto *MD = dyn_cast_if_present<CXXMethodDecl>(FuncDecl);
4063 MD && MD->isStatic()) {
4064 if (!this->discard(E->getArg(0)))
4065 return false;
4066 // Drop first arg.
4067 Args.erase(Args.begin());
4068 }
4069 }
4070
4071 std::optional<unsigned> CalleeOffset;
4072 // Add the (optional, implicit) This pointer.
4073 if (const auto *MC = dyn_cast<CXXMemberCallExpr>(E)) {
4074 if (!FuncDecl && classifyPrim(E->getCallee()) == PT_MemberPtr) {
4075 // If we end up creating a CallPtr op for this, we need the base of the
4076 // member pointer as the instance pointer, and later extract the function
4077 // decl as the function pointer.
4078 const Expr *Callee = E->getCallee();
4079 CalleeOffset =
4080 this->allocateLocalPrimitive(Callee, PT_MemberPtr, true, false);
4081 if (!this->visit(Callee))
4082 return false;
4083 if (!this->emitSetLocal(PT_MemberPtr, *CalleeOffset, E))
4084 return false;
4085 if (!this->emitGetLocal(PT_MemberPtr, *CalleeOffset, E))
4086 return false;
4087 if (!this->emitGetMemberPtrBase(E))
4088 return false;
4089 } else if (!this->visit(MC->getImplicitObjectArgument())) {
4090 return false;
4091 }
4092 } else if (!FuncDecl) {
4093 const Expr *Callee = E->getCallee();
4094 CalleeOffset = this->allocateLocalPrimitive(Callee, PT_FnPtr, true, false);
4095 if (!this->visit(Callee))
4096 return false;
4097 if (!this->emitSetLocal(PT_FnPtr, *CalleeOffset, E))
4098 return false;
4099 }
4100
4101 llvm::BitVector NonNullArgs = collectNonNullArgs(FuncDecl, Args);
4102 // Put arguments on the stack.
4103 unsigned ArgIndex = 0;
4104 for (const auto *Arg : Args) {
4105 if (!this->visit(Arg))
4106 return false;
4107
4108 // If we know the callee already, check the known parametrs for nullability.
4109 if (FuncDecl && NonNullArgs[ArgIndex]) {
4110 PrimType ArgT = classify(Arg).value_or(PT_Ptr);
4111 if (ArgT == PT_Ptr || ArgT == PT_FnPtr) {
4112 if (!this->emitCheckNonNullArg(ArgT, Arg))
4113 return false;
4114 }
4115 }
4116 ++ArgIndex;
4117 }
4118
4119 // Undo the argument reversal we did earlier.
4120 if (IsAssignmentOperatorCall) {
4121 assert(Args.size() == 2);
4122 PrimType Arg1T = classify(Args[0]).value_or(PT_Ptr);
4123 PrimType Arg2T = classify(Args[1]).value_or(PT_Ptr);
4124 if (!this->emitFlip(Arg2T, Arg1T, E))
4125 return false;
4126 }
4127
4128 if (FuncDecl) {
4129 const Function *Func = getFunction(FuncDecl);
4130 if (!Func)
4131 return false;
4132 assert(HasRVO == Func->hasRVO());
4133
4134 bool HasQualifier = false;
4135 if (const auto *ME = dyn_cast<MemberExpr>(E->getCallee()))
4136 HasQualifier = ME->hasQualifier();
4137
4138 bool IsVirtual = false;
4139 if (const auto *MD = dyn_cast<CXXMethodDecl>(FuncDecl))
4140 IsVirtual = MD->isVirtual();
4141
4142 // In any case call the function. The return value will end up on the stack
4143 // and if the function has RVO, we already have the pointer on the stack to
4144 // write the result into.
4145 if (IsVirtual && !HasQualifier) {
4146 uint32_t VarArgSize = 0;
4147 unsigned NumParams =
4148 Func->getNumWrittenParams() + isa<CXXOperatorCallExpr>(E);
4149 for (unsigned I = NumParams, N = E->getNumArgs(); I != N; ++I)
4150 VarArgSize += align(primSize(classify(E->getArg(I)).value_or(PT_Ptr)));
4151
4152 if (!this->emitCallVirt(Func, VarArgSize, E))
4153 return false;
4154 } else if (Func->isVariadic()) {
4155 uint32_t VarArgSize = 0;
4156 unsigned NumParams =
4157 Func->getNumWrittenParams() + isa<CXXOperatorCallExpr>(E);
4158 for (unsigned I = NumParams, N = E->getNumArgs(); I != N; ++I)
4159 VarArgSize += align(primSize(classify(E->getArg(I)).value_or(PT_Ptr)));
4160 if (!this->emitCallVar(Func, VarArgSize, E))
4161 return false;
4162 } else {
4163 if (!this->emitCall(Func, 0, E))
4164 return false;
4165 }
4166 } else {
4167 // Indirect call. Visit the callee, which will leave a FunctionPointer on
4168 // the stack. Cleanup of the returned value if necessary will be done after
4169 // the function call completed.
4170
4171 // Sum the size of all args from the call expr.
4172 uint32_t ArgSize = 0;
4173 for (unsigned I = 0, N = E->getNumArgs(); I != N; ++I)
4174 ArgSize += align(primSize(classify(E->getArg(I)).value_or(PT_Ptr)));
4175
4176 // Get the callee, either from a member pointer or function pointer saved in
4177 // CalleeOffset.
4178 if (isa<CXXMemberCallExpr>(E) && CalleeOffset) {
4179 if (!this->emitGetLocal(PT_MemberPtr, *CalleeOffset, E))
4180 return false;
4181 if (!this->emitGetMemberPtrDecl(E))
4182 return false;
4183 } else {
4184 if (!this->emitGetLocal(PT_FnPtr, *CalleeOffset, E))
4185 return false;
4186 }
4187 if (!this->emitCallPtr(ArgSize, E, E))
4188 return false;
4189 }
4190
4191 // Cleanup for discarded return values.
4192 if (DiscardResult && !ReturnType->isVoidType() && T)
4193 return this->emitPop(*T, E);
4194
4195 return true;
4196}
4197
4198template <class Emitter>
4200 SourceLocScope<Emitter> SLS(this, E);
4201
4202 return this->delegate(E->getExpr());
4203}
4204
4205template <class Emitter>
4207 SourceLocScope<Emitter> SLS(this, E);
4208
4209 const Expr *SubExpr = E->getExpr();
4210 if (std::optional<PrimType> T = classify(E->getExpr()))
4211 return this->visit(SubExpr);
4212
4213 assert(Initializing);
4214 return this->visitInitializer(SubExpr);
4215}
4216
4217template <class Emitter>
4219 if (DiscardResult)
4220 return true;
4221
4222 return this->emitConstBool(E->getValue(), E);
4223}
4224
4225template <class Emitter>
4227 const CXXNullPtrLiteralExpr *E) {
4228 if (DiscardResult)
4229 return true;
4230
4231 return this->emitNullPtr(nullptr, E);
4232}
4233
4234template <class Emitter>
4236 if (DiscardResult)
4237 return true;
4238
4239 assert(E->getType()->isIntegerType());
4240
4241 PrimType T = classifyPrim(E->getType());
4242 return this->emitZero(T, E);
4243}
4244
4245template <class Emitter>
4247 if (DiscardResult)
4248 return true;
4249
4250 if (this->LambdaThisCapture.Offset > 0) {
4251 if (this->LambdaThisCapture.IsPtr)
4252 return this->emitGetThisFieldPtr(this->LambdaThisCapture.Offset, E);
4253 return this->emitGetPtrThisField(this->LambdaThisCapture.Offset, E);
4254 }
4255
4256 // In some circumstances, the 'this' pointer does not actually refer to the
4257 // instance pointer of the current function frame, but e.g. to the declaration
4258 // currently being initialized. Here we emit the necessary instruction(s) for
4259 // this scenario.
4260 if (!InitStackActive || !E->isImplicit())
4261 return this->emitThis(E);
4262
4263 if (InitStackActive && !InitStack.empty()) {
4264 unsigned StartIndex = 0;
4265 for (StartIndex = InitStack.size() - 1; StartIndex > 0; --StartIndex) {
4266 if (InitStack[StartIndex].Kind != InitLink::K_Field &&
4267 InitStack[StartIndex].Kind != InitLink::K_Elem)
4268 break;
4269 }
4270
4271 for (unsigned I = StartIndex, N = InitStack.size(); I != N; ++I) {
4272 if (!InitStack[I].template emit<Emitter>(this, E))
4273 return false;
4274 }
4275 return true;
4276 }
4277 return this->emitThis(E);
4278}
4279
4280template <class Emitter> bool Compiler<Emitter>::visitStmt(const Stmt *S) {
4281 switch (S->getStmtClass()) {
4282 case Stmt::CompoundStmtClass:
4283 return visitCompoundStmt(cast<CompoundStmt>(S));
4284 case Stmt::DeclStmtClass:
4285 return visitDeclStmt(cast<DeclStmt>(S));
4286 case Stmt::ReturnStmtClass:
4287 return visitReturnStmt(cast<ReturnStmt>(S));
4288 case Stmt::IfStmtClass:
4289 return visitIfStmt(cast<IfStmt>(S));
4290 case Stmt::WhileStmtClass:
4291 return visitWhileStmt(cast<WhileStmt>(S));
4292 case Stmt::DoStmtClass:
4293 return visitDoStmt(cast<DoStmt>(S));
4294 case Stmt::ForStmtClass:
4295 return visitForStmt(cast<ForStmt>(S));
4296 case Stmt::CXXForRangeStmtClass:
4297 return visitCXXForRangeStmt(cast<CXXForRangeStmt>(S));
4298 case Stmt::BreakStmtClass:
4299 return visitBreakStmt(cast<BreakStmt>(S));
4300 case Stmt::ContinueStmtClass:
4301 return visitContinueStmt(cast<ContinueStmt>(S));
4302 case Stmt::SwitchStmtClass:
4303 return visitSwitchStmt(cast<SwitchStmt>(S));
4304 case Stmt::CaseStmtClass:
4305 return visitCaseStmt(cast<CaseStmt>(S));
4306 case Stmt::DefaultStmtClass:
4307 return visitDefaultStmt(cast<DefaultStmt>(S));
4308 case Stmt::AttributedStmtClass:
4309 return visitAttributedStmt(cast<AttributedStmt>(S));
4310 case Stmt::CXXTryStmtClass:
4311 return visitCXXTryStmt(cast<CXXTryStmt>(S));
4312 case Stmt::NullStmtClass:
4313 return true;
4314 // Always invalid statements.
4315 case Stmt::GCCAsmStmtClass:
4316 case Stmt::MSAsmStmtClass:
4317 case Stmt::GotoStmtClass:
4318 return this->emitInvalid(S);
4319 case Stmt::LabelStmtClass:
4320 return this->visitStmt(cast<LabelStmt>(S)->getSubStmt());
4321 default: {
4322 if (const auto *E = dyn_cast<Expr>(S))
4323 return this->discard(E);
4324 return false;
4325 }
4326 }
4327}
4328
4329template <class Emitter>
4332 for (const auto *InnerStmt : S->body())
4333 if (!visitStmt(InnerStmt))
4334 return false;
4335 return Scope.destroyLocals();
4336}
4337
4338template <class Emitter>
4340 for (const auto *D : DS->decls()) {
4342 FunctionDecl>(D))
4343 continue;
4344
4345 const auto *VD = dyn_cast<VarDecl>(D);
4346 if (!VD)
4347 return false;
4348 if (!this->visitVarDecl(VD))
4349 return false;
4350 }
4351
4352 return true;
4353}
4354
4355template <class Emitter>
4357 if (this->InStmtExpr)
4358 return this->emitUnsupported(RS);
4359
4360 if (const Expr *RE = RS->getRetValue()) {
4361 LocalScope<Emitter> RetScope(this);
4362 if (ReturnType) {
4363 // Primitive types are simply returned.
4364 if (!this->visit(RE))
4365 return false;
4366 this->emitCleanup();
4367 return this->emitRet(*ReturnType, RS);
4368 } else if (RE->getType()->isVoidType()) {
4369 if (!this->visit(RE))
4370 return false;
4371 } else {
4372 // RVO - construct the value in the return location.
4373 if (!this->emitRVOPtr(RE))
4374 return false;
4375 if (!this->visitInitializer(RE))
4376 return false;
4377 if (!this->emitPopPtr(RE))
4378 return false;
4379
4380 this->emitCleanup();
4381 return this->emitRetVoid(RS);
4382 }
4383 }
4384
4385 // Void return.
4386 this->emitCleanup();
4387 return this->emitRetVoid(RS);
4388}
4389
4390template <class Emitter> bool Compiler<Emitter>::visitIfStmt(const IfStmt *IS) {
4391 if (auto *CondInit = IS->getInit())
4392 if (!visitStmt(CondInit))
4393 return false;
4394
4395 if (const DeclStmt *CondDecl = IS->getConditionVariableDeclStmt())
4396 if (!visitDeclStmt(CondDecl))
4397 return false;
4398
4399 // Compile condition.
4400 if (IS->isNonNegatedConsteval()) {
4401 if (!this->emitIsConstantContext(IS))
4402 return false;
4403 } else if (IS->isNegatedConsteval()) {
4404 if (!this->emitIsConstantContext(IS))
4405 return false;
4406 if (!this->emitInv(IS))
4407 return false;
4408 } else {
4409 if (!this->visitBool(IS->getCond()))
4410 return false;
4411 }
4412
4413 if (const Stmt *Else = IS->getElse()) {
4414 LabelTy LabelElse = this->getLabel();
4415 LabelTy LabelEnd = this->getLabel();
4416 if (!this->jumpFalse(LabelElse))
4417 return false;
4418 if (!visitStmt(IS->getThen()))
4419 return false;
4420 if (!this->jump(LabelEnd))
4421 return false;
4422 this->emitLabel(LabelElse);
4423 if (!visitStmt(Else))
4424 return false;
4425 this->emitLabel(LabelEnd);
4426 } else {
4427 LabelTy LabelEnd = this->getLabel();
4428 if (!this->jumpFalse(LabelEnd))
4429 return false;
4430 if (!visitStmt(IS->getThen()))
4431 return false;
4432 this->emitLabel(LabelEnd);
4433 }
4434
4435 return true;
4436}
4437
4438template <class Emitter>
4440 const Expr *Cond = S->getCond();
4441 const Stmt *Body = S->getBody();
4442
4443 LabelTy CondLabel = this->getLabel(); // Label before the condition.
4444 LabelTy EndLabel = this->getLabel(); // Label after the loop.
4445 LoopScope<Emitter> LS(this, EndLabel, CondLabel);
4446
4447 this->fallthrough(CondLabel);
4448 this->emitLabel(CondLabel);
4449
4450 if (const DeclStmt *CondDecl = S->getConditionVariableDeclStmt())
4451 if (!visitDeclStmt(CondDecl))
4452 return false;
4453
4454 if (!this->visitBool(Cond))
4455 return false;
4456 if (!this->jumpFalse(EndLabel))
4457 return false;
4458
4459 if (!this->visitStmt(Body))
4460 return false;
4461
4462 if (!this->jump(CondLabel))
4463 return false;
4464 this->fallthrough(EndLabel);
4465 this->emitLabel(EndLabel);
4466
4467 return true;
4468}
4469
4470template <class Emitter> bool Compiler<Emitter>::visitDoStmt(const DoStmt *S) {
4471 const Expr *Cond = S->getCond();
4472 const Stmt *Body = S->getBody();
4473
4474 LabelTy StartLabel = this->getLabel();
4475 LabelTy EndLabel = this->getLabel();
4476 LabelTy CondLabel = this->getLabel();
4477 LoopScope<Emitter> LS(this, EndLabel, CondLabel);
4478
4479 this->fallthrough(StartLabel);
4480 this->emitLabel(StartLabel);
4481 {
4482 if (!this->visitStmt(Body))
4483 return false;
4484 this->fallthrough(CondLabel);
4485 this->emitLabel(CondLabel);
4486 if (!this->visitBool(Cond))
4487 return false;
4488 }
4489 if (!this->jumpTrue(StartLabel))
4490 return false;
4491
4492 this->fallthrough(EndLabel);
4493 this->emitLabel(EndLabel);
4494 return true;
4495}
4496
4497template <class Emitter>
4499 // for (Init; Cond; Inc) { Body }
4500 const Stmt *Init = S->getInit();
4501 const Expr *Cond = S->getCond();
4502 const Expr *Inc = S->getInc();
4503 const Stmt *Body = S->getBody();
4504
4505 LabelTy EndLabel = this->getLabel();
4506 LabelTy CondLabel = this->getLabel();
4507 LabelTy IncLabel = this->getLabel();
4508 LoopScope<Emitter> LS(this, EndLabel, IncLabel);
4509
4510 if (Init && !this->visitStmt(Init))
4511 return false;
4512
4513 this->fallthrough(CondLabel);
4514 this->emitLabel(CondLabel);
4515
4516 if (const DeclStmt *CondDecl = S->getConditionVariableDeclStmt())
4517 if (!visitDeclStmt(CondDecl))
4518 return false;
4519
4520 if (Cond) {
4521 if (!this->visitBool(Cond))
4522 return false;
4523 if (!this->jumpFalse(EndLabel))
4524 return false;
4525 }
4526
4527 {
4528 if (Body && !this->visitStmt(Body))
4529 return false;
4530
4531 this->fallthrough(IncLabel);
4532 this->emitLabel(IncLabel);
4533 if (Inc && !this->discard(Inc))
4534 return false;
4535 }
4536
4537 if (!this->jump(CondLabel))
4538 return false;
4539 this->fallthrough(EndLabel);
4540 this->emitLabel(EndLabel);
4541 return true;
4542}
4543
4544template <class Emitter>
4546 const Stmt *Init = S->getInit();
4547 const Expr *Cond = S->getCond();
4548 const Expr *Inc = S->getInc();
4549 const Stmt *Body = S->getBody();
4550 const Stmt *BeginStmt = S->getBeginStmt();
4551 const Stmt *RangeStmt = S->getRangeStmt();
4552 const Stmt *EndStmt = S->getEndStmt();
4553 const VarDecl *LoopVar = S->getLoopVariable();
4554
4555 LabelTy EndLabel = this->getLabel();
4556 LabelTy CondLabel = this->getLabel();
4557 LabelTy IncLabel = this->getLabel();
4558 LoopScope<Emitter> LS(this, EndLabel, IncLabel);
4559
4560 // Emit declarations needed in the loop.
4561 if (Init && !this->visitStmt(Init))
4562 return false;
4563 if (!this->visitStmt(RangeStmt))
4564 return false;
4565 if (!this->visitStmt(BeginStmt))
4566 return false;
4567 if (!this->visitStmt(EndStmt))
4568 return false;
4569
4570 // Now the condition as well as the loop variable assignment.
4571 this->fallthrough(CondLabel);
4572 this->emitLabel(CondLabel);
4573 if (!this->visitBool(Cond))
4574 return false;
4575 if (!this->jumpFalse(EndLabel))
4576 return false;
4577
4578 if (!this->visitVarDecl(LoopVar))
4579 return false;
4580
4581 // Body.
4582 {
4583 if (!this->visitStmt(Body))
4584 return false;
4585
4586 this->fallthrough(IncLabel);
4587 this->emitLabel(IncLabel);
4588 if (!this->discard(Inc))
4589 return false;
4590 }
4591
4592 if (!this->jump(CondLabel))
4593 return false;
4594
4595 this->fallthrough(EndLabel);
4596 this->emitLabel(EndLabel);
4597 return true;
4598}
4599
4600template <class Emitter>
4602 if (!BreakLabel)
4603 return false;
4604
4605 this->emitCleanup();
4606 return this->jump(*BreakLabel);
4607}
4608
4609template <class Emitter>
4611 if (!ContinueLabel)
4612 return false;
4613
4614 this->emitCleanup();
4615 return this->jump(*ContinueLabel);
4616}
4617
4618template <class Emitter>
4620 const Expr *Cond = S->getCond();
4621 PrimType CondT = this->classifyPrim(Cond->getType());
4622
4623 LabelTy EndLabel = this->getLabel();
4624 OptLabelTy DefaultLabel = std::nullopt;
4625 unsigned CondVar = this->allocateLocalPrimitive(Cond, CondT, true, false);
4626
4627 if (const auto *CondInit = S->getInit())
4628 if (!visitStmt(CondInit))
4629 return false;
4630
4631 if (const DeclStmt *CondDecl = S->getConditionVariableDeclStmt())
4632 if (!visitDeclStmt(CondDecl))
4633 return false;
4634
4635 // Initialize condition variable.
4636 if (!this->visit(Cond))
4637 return false;
4638 if (!this->emitSetLocal(CondT, CondVar, S))
4639 return false;
4640
4641 CaseMap CaseLabels;
4642 // Create labels and comparison ops for all case statements.
4643 for (const SwitchCase *SC = S->getSwitchCaseList(); SC;
4644 SC = SC->getNextSwitchCase()) {
4645 if (const auto *CS = dyn_cast<CaseStmt>(SC)) {
4646 // FIXME: Implement ranges.
4647 if (CS->caseStmtIsGNURange())
4648 return false;
4649 CaseLabels[SC] = this->getLabel();
4650
4651 const Expr *Value = CS->getLHS();
4652 PrimType ValueT = this->classifyPrim(Value->getType());
4653
4654 // Compare the case statement's value to the switch condition.
4655 if (!this->emitGetLocal(CondT, CondVar, CS))
4656 return false;
4657 if (!this->visit(Value))
4658 return false;
4659
4660 // Compare and jump to the case label.
4661 if (!this->emitEQ(ValueT, S))
4662 return false;
4663 if (!this->jumpTrue(CaseLabels[CS]))
4664 return false;
4665 } else {
4666 assert(!DefaultLabel);
4667 DefaultLabel = this->getLabel();
4668 }
4669 }
4670
4671 // If none of the conditions above were true, fall through to the default
4672 // statement or jump after the switch statement.
4673 if (DefaultLabel) {
4674 if (!this->jump(*DefaultLabel))
4675 return false;
4676 } else {
4677 if (!this->jump(EndLabel))
4678 return false;
4679 }
4680
4681 SwitchScope<Emitter> SS(this, std::move(CaseLabels), EndLabel, DefaultLabel);
4682 if (!this->visitStmt(S->getBody()))
4683 return false;
4684 this->emitLabel(EndLabel);
4685 return true;
4686}
4687
4688template <class Emitter>
4690 this->emitLabel(CaseLabels[S]);
4691 return this->visitStmt(S->getSubStmt());
4692}
4693
4694template <class Emitter>
4696 this->emitLabel(*DefaultLabel);
4697 return this->visitStmt(S->getSubStmt());
4698}
4699
4700template <class Emitter>
4702 if (this->Ctx.getLangOpts().CXXAssumptions &&
4703 !this->Ctx.getLangOpts().MSVCCompat) {
4704 for (const Attr *A : S->getAttrs()) {
4705 auto *AA = dyn_cast<CXXAssumeAttr>(A);
4706 if (!AA)
4707 continue;
4708
4709 assert(isa<NullStmt>(S->getSubStmt()));
4710
4711 const Expr *Assumption = AA->getAssumption();
4712 if (Assumption->isValueDependent())
4713 return false;
4714
4715 if (Assumption->HasSideEffects(this->Ctx.getASTContext()))
4716 continue;
4717
4718 // Evaluate assumption.
4719 if (!this->visitBool(Assumption))
4720 return false;
4721
4722 if (!this->emitAssume(Assumption))
4723 return false;
4724 }
4725 }
4726
4727 // Ignore other attributes.
4728 return this->visitStmt(S->getSubStmt());
4729}
4730
4731template <class Emitter>
4733 // Ignore all handlers.
4734 return this->visitStmt(S->getTryBlock());
4735}
4736
4737template <class Emitter>
4739 assert(MD->isLambdaStaticInvoker());
4740 assert(MD->hasBody());
4741 assert(cast<CompoundStmt>(MD->getBody())->body_empty());
4742
4743 const CXXRecordDecl *ClosureClass = MD->getParent();
4744 const CXXMethodDecl *LambdaCallOp = ClosureClass->getLambdaCallOperator();
4745 assert(ClosureClass->captures_begin() == ClosureClass->captures_end());
4746 const Function *Func = this->getFunction(LambdaCallOp);
4747 if (!Func)
4748 return false;
4749 assert(Func->hasThisPointer());
4750 assert(Func->getNumParams() == (MD->getNumParams() + 1 + Func->hasRVO()));
4751
4752 if (Func->hasRVO()) {
4753 if (!this->emitRVOPtr(MD))
4754 return false;
4755 }
4756
4757 // The lambda call operator needs an instance pointer, but we don't have
4758 // one here, and we don't need one either because the lambda cannot have
4759 // any captures, as verified above. Emit a null pointer. This is then
4760 // special-cased when interpreting to not emit any misleading diagnostics.
4761 if (!this->emitNullPtr(nullptr, MD))
4762 return false;
4763
4764 // Forward all arguments from the static invoker to the lambda call operator.
4765 for (const ParmVarDecl *PVD : MD->parameters()) {
4766 auto It = this->Params.find(PVD);
4767 assert(It != this->Params.end());
4768
4769 // We do the lvalue-to-rvalue conversion manually here, so no need
4770 // to care about references.
4771 PrimType ParamType = this->classify(PVD->getType()).value_or(PT_Ptr);
4772 if (!this->emitGetParam(ParamType, It->second.Offset, MD))
4773 return false;
4774 }
4775
4776 if (!this->emitCall(Func, 0, LambdaCallOp))
4777 return false;
4778
4779 this->emitCleanup();
4780 if (ReturnType)
4781 return this->emitRet(*ReturnType, MD);
4782
4783 // Nothing to do, since we emitted the RVO pointer above.
4784 return this->emitRetVoid(MD);
4785}
4786
4787template <class Emitter>
4789 if (Ctx.getLangOpts().CPlusPlus23)
4790 return true;
4791
4792 if (!E->isPRValue() || E->getType()->isLiteralType(Ctx.getASTContext()))
4793 return true;
4794
4795 return this->emitCheckLiteralType(E->getType().getTypePtr(), E);
4796}
4797
4798template <class Emitter>
4800 assert(!ReturnType);
4801
4802 auto emitFieldInitializer = [&](const Record::Field *F, unsigned FieldOffset,
4803 const Expr *InitExpr) -> bool {
4804 // We don't know what to do with these, so just return false.
4805 if (InitExpr->getType().isNull())
4806 return false;
4807
4808 if (std::optional<PrimType> T = this->classify(InitExpr)) {
4809 if (!this->visit(InitExpr))
4810 return false;
4811
4812 if (F->isBitField())
4813 return this->emitInitThisBitField(*T, F, FieldOffset, InitExpr);
4814 return this->emitInitThisField(*T, FieldOffset, InitExpr);
4815 }
4816 // Non-primitive case. Get a pointer to the field-to-initialize
4817 // on the stack and call visitInitialzer() for it.
4818 InitLinkScope<Emitter> FieldScope(this, InitLink::Field(F->Offset));
4819 if (!this->emitGetPtrThisField(FieldOffset, InitExpr))
4820 return false;
4821
4822 if (!this->visitInitializer(InitExpr))
4823 return false;
4824
4825 return this->emitFinishInitPop(InitExpr);
4826 };
4827
4828 const RecordDecl *RD = Ctor->getParent();
4829 const Record *R = this->getRecord(RD);
4830 if (!R)
4831 return false;
4832
4833 if (R->isUnion() && Ctor->isCopyOrMoveConstructor()) {
4834 // union copy and move ctors are special.
4835 assert(cast<CompoundStmt>(Ctor->getBody())->body_empty());
4836 if (!this->emitThis(Ctor))
4837 return false;
4838
4839 auto PVD = Ctor->getParamDecl(0);
4840 ParamOffset PO = this->Params[PVD]; // Must exist.
4841
4842 if (!this->emitGetParam(PT_Ptr, PO.Offset, Ctor))
4843 return false;
4844
4845 return this->emitMemcpy(Ctor) && this->emitPopPtr(Ctor) &&
4846 this->emitRetVoid(Ctor);
4847 }
4848
4850 for (const auto *Init : Ctor->inits()) {
4851 // Scope needed for the initializers.
4853
4854 const Expr *InitExpr = Init->getInit();
4855 if (const FieldDecl *Member = Init->getMember()) {
4856 const Record::Field *F = R->getField(Member);
4857
4858 if (!emitFieldInitializer(F, F->Offset, InitExpr))
4859 return false;
4860 } else if (const Type *Base = Init->getBaseClass()) {
4861 const auto *BaseDecl = Base->getAsCXXRecordDecl();
4862 assert(BaseDecl);
4863
4864 if (Init->isBaseVirtual()) {
4865 assert(R->getVirtualBase(BaseDecl));
4866 if (!this->emitGetPtrThisVirtBase(BaseDecl, InitExpr))
4867 return false;
4868
4869 } else {
4870 // Base class initializer.
4871 // Get This Base and call initializer on it.
4872 const Record::Base *B = R->getBase(BaseDecl);
4873 assert(B);
4874 if (!this->emitGetPtrThisBase(B->Offset, InitExpr))
4875 return false;
4876 }
4877
4878 if (!this->visitInitializer(InitExpr))
4879 return false;
4880 if (!this->emitFinishInitPop(InitExpr))
4881 return false;
4882 } else if (const IndirectFieldDecl *IFD = Init->getIndirectMember()) {
4883 assert(IFD->getChainingSize() >= 2);
4884
4885 unsigned NestedFieldOffset = 0;
4886 const Record::Field *NestedField = nullptr;
4887 for (const NamedDecl *ND : IFD->chain()) {
4888 const auto *FD = cast<FieldDecl>(ND);
4889 const Record *FieldRecord = this->P.getOrCreateRecord(FD->getParent());
4890 assert(FieldRecord);
4891
4892 NestedField = FieldRecord->getField(FD);
4893 assert(NestedField);
4894
4895 NestedFieldOffset += NestedField->Offset;
4896 }
4897 assert(NestedField);
4898
4899 if (!emitFieldInitializer(NestedField, NestedFieldOffset, InitExpr))
4900 return false;
4901 } else {
4902 assert(Init->isDelegatingInitializer());
4903 if (!this->emitThis(InitExpr))
4904 return false;
4905 if (!this->visitInitializer(Init->getInit()))
4906 return false;
4907 if (!this->emitPopPtr(InitExpr))
4908 return false;
4909 }
4910
4911 if (!Scope.destroyLocals())
4912 return false;
4913 }
4914
4915 if (const auto *Body = Ctor->getBody())
4916 if (!visitStmt(Body))
4917 return false;
4918
4919 return this->emitRetVoid(SourceInfo{});
4920}
4921
4922template <class Emitter>
4924 const RecordDecl *RD = Dtor->getParent();
4925 const Record *R = this->getRecord(RD);
4926 if (!R)
4927 return false;
4928
4929 if (!Dtor->isTrivial() && Dtor->getBody()) {
4930 if (!this->visitStmt(Dtor->getBody()))
4931 return false;
4932 }
4933
4934 if (!this->emitThis(Dtor))
4935 return false;
4936
4937 assert(R);
4938 if (!R->isUnion()) {
4939 // First, destroy all fields.
4940 for (const Record::Field &Field : llvm::reverse(R->fields())) {
4941 const Descriptor *D = Field.Desc;
4942 if (!D->isPrimitive() && !D->isPrimitiveArray()) {
4943 if (!this->emitGetPtrField(Field.Offset, SourceInfo{}))
4944 return false;
4945 if (!this->emitDestruction(D))
4946 return false;
4947 if (!this->emitPopPtr(SourceInfo{}))
4948 return false;
4949 }
4950 }
4951 }
4952
4953 for (const Record::Base &Base : llvm::reverse(R->bases())) {
4954 if (!this->emitGetPtrBase(Base.Offset, SourceInfo{}))
4955 return false;
4956 if (!this->emitRecordDestruction(Base.R))
4957 return false;
4958 if (!this->emitPopPtr(SourceInfo{}))
4959 return false;
4960 }
4961
4962 // FIXME: Virtual bases.
4963 return this->emitPopPtr(Dtor) && this->emitRetVoid(Dtor);
4964}
4965
4966template <class Emitter>
4968 // Classify the return type.
4969 ReturnType = this->classify(F->getReturnType());
4970
4971 if (const auto *Ctor = dyn_cast<CXXConstructorDecl>(F))
4972 return this->compileConstructor(Ctor);
4973 if (const auto *Dtor = dyn_cast<CXXDestructorDecl>(F))
4974 return this->compileDestructor(Dtor);
4975
4976 // Emit custom code if this is a lambda static invoker.
4977 if (const auto *MD = dyn_cast<CXXMethodDecl>(F);
4978 MD && MD->isLambdaStaticInvoker())
4979 return this->emitLambdaStaticInvokerBody(MD);
4980
4981 // Regular functions.
4982 if (const auto *Body = F->getBody())
4983 if (!visitStmt(Body))
4984 return false;
4985
4986 // Emit a guard return to protect against a code path missing one.
4987 if (F->getReturnType()->isVoidType())
4988 return this->emitRetVoid(SourceInfo{});
4989 return this->emitNoRet(SourceInfo{});
4990}
4991
4992template <class Emitter>
4994 const Expr *SubExpr = E->getSubExpr();
4995 if (SubExpr->getType()->isAnyComplexType())
4996 return this->VisitComplexUnaryOperator(E);
4997 std::optional<PrimType> T = classify(SubExpr->getType());
4998
4999 switch (E->getOpcode()) {
5000 case UO_PostInc: { // x++
5001 if (!Ctx.getLangOpts().CPlusPlus14)
5002 return this->emitInvalid(E);
5003 if (!T)
5004 return this->emitError(E);
5005
5006 if (!this->visit(SubExpr))
5007 return false;
5008
5009 if (T == PT_Ptr || T == PT_FnPtr) {
5010 if (!this->emitIncPtr(E))
5011 return false;
5012
5013 return DiscardResult ? this->emitPopPtr(E) : true;
5014 }
5015
5016 if (T == PT_Float) {
5017 return DiscardResult ? this->emitIncfPop(getRoundingMode(E), E)
5018 : this->emitIncf(getRoundingMode(E), E);
5019 }
5020
5021 return DiscardResult ? this->emitIncPop(*T, E) : this->emitInc(*T, E);
5022 }
5023 case UO_PostDec: { // x--
5024 if (!Ctx.getLangOpts().CPlusPlus14)
5025 return this->emitInvalid(E);
5026 if (!T)
5027 return this->emitError(E);
5028
5029 if (!this->visit(SubExpr))
5030 return false;
5031
5032 if (T == PT_Ptr || T == PT_FnPtr) {
5033 if (!this->emitDecPtr(E))
5034 return false;
5035
5036 return DiscardResult ? this->emitPopPtr(E) : true;
5037 }
5038
5039 if (T == PT_Float) {
5040 return DiscardResult ? this->emitDecfPop(getRoundingMode(E), E)
5041 : this->emitDecf(getRoundingMode(E), E);
5042 }
5043
5044 return DiscardResult ? this->emitDecPop(*T, E) : this->emitDec(*T, E);
5045 }
5046 case UO_PreInc: { // ++x
5047 if (!Ctx.getLangOpts().CPlusPlus14)
5048 return this->emitInvalid(E);
5049 if (!T)
5050 return this->emitError(E);
5051
5052 if (!this->visit(SubExpr))
5053 return false;
5054
5055 if (T == PT_Ptr || T == PT_FnPtr) {
5056 if (!this->emitLoadPtr(E))
5057 return false;
5058 if (!this->emitConstUint8(1, E))
5059 return false;
5060 if (!this->emitAddOffsetUint8(E))
5061 return false;
5062 return DiscardResult ? this->emitStorePopPtr(E) : this->emitStorePtr(E);
5063 }
5064
5065 // Post-inc and pre-inc are the same if the value is to be discarded.
5066 if (DiscardResult) {
5067 if (T == PT_Float)
5068 return this->emitIncfPop(getRoundingMode(E), E);
5069 return this->emitIncPop(*T, E);
5070 }
5071
5072 if (T == PT_Float) {
5073 const auto &TargetSemantics = Ctx.getFloatSemantics(E->getType());
5074 if (!this->emitLoadFloat(E))
5075 return false;
5076 if (!this->emitConstFloat(llvm::APFloat(TargetSemantics, 1), E))
5077 return false;
5078 if (!this->emitAddf(getRoundingMode(E), E))
5079 return false;
5080 if (!this->emitStoreFloat(E))
5081 return false;
5082 } else {
5083 assert(isIntegralType(*T));
5084 if (!this->emitLoad(*T, E))
5085 return false;
5086 if (!this->emitConst(1, E))
5087 return false;
5088 if (!this->emitAdd(*T, E))
5089 return false;
5090 if (!this->emitStore(*T, E))
5091 return false;
5092 }
5093 return E->isGLValue() || this->emitLoadPop(*T, E);
5094 }
5095 case UO_PreDec: { // --x
5096 if (!Ctx.getLangOpts().CPlusPlus14)
5097 return this->emitInvalid(E);
5098 if (!T)
5099 return this->emitError(E);
5100
5101 if (!this->visit(SubExpr))
5102 return false;
5103
5104 if (T == PT_Ptr || T == PT_FnPtr) {
5105 if (!this->emitLoadPtr(E))
5106 return false;
5107 if (!this->emitConstUint8(1, E))
5108 return false;
5109 if (!this->emitSubOffsetUint8(E))
5110 return false;
5111 return DiscardResult ? this->emitStorePopPtr(E) : this->emitStorePtr(E);
5112 }
5113
5114 // Post-dec and pre-dec are the same if the value is to be discarded.
5115 if (DiscardResult) {
5116 if (T == PT_Float)
5117 return this->emitDecfPop(getRoundingMode(E), E);
5118 return this->emitDecPop(*T, E);
5119 }
5120
5121 if (T == PT_Float) {
5122 const auto &TargetSemantics = Ctx.getFloatSemantics(E->getType());
5123 if (!this->emitLoadFloat(E))
5124 return false;
5125 if (!this->emitConstFloat(llvm::APFloat(TargetSemantics, 1), E))
5126 return false;
5127 if (!this->emitSubf(getRoundingMode(E), E))
5128 return false;
5129 if (!this->emitStoreFloat(E))
5130 return false;
5131 } else {
5132 assert(isIntegralType(*T));
5133 if (!this->emitLoad(*T, E))
5134 return false;
5135 if (!this->emitConst(1, E))
5136 return false;
5137 if (!this->emitSub(*T, E))
5138 return false;
5139 if (!this->emitStore(*T, E))
5140 return false;
5141 }
5142 return E->isGLValue() || this->emitLoadPop(*T, E);
5143 }
5144 case UO_LNot: // !x
5145 if (!T)
5146 return this->emitError(E);
5147
5148 if (DiscardResult)
5149 return this->discard(SubExpr);
5150
5151 if (!this->visitBool(SubExpr))
5152 return false;
5153
5154 if (!this->emitInv(E))
5155 return false;
5156
5157 if (PrimType ET = classifyPrim(E->getType()); ET != PT_Bool)
5158 return this->emitCast(PT_Bool, ET, E);
5159 return true;
5160 case UO_Minus: // -x
5161 if (!T)
5162 return this->emitError(E);
5163
5164 if (!this->visit(SubExpr))
5165 return false;
5166 return DiscardResult ? this->emitPop(*T, E) : this->emitNeg(*T, E);
5167 case UO_Plus: // +x
5168 if (!T)
5169 return this->emitError(E);
5170
5171 if (!this->visit(SubExpr)) // noop
5172 return false;
5173 return DiscardResult ? this->emitPop(*T, E) : true;
5174 case UO_AddrOf: // &x
5175 if (E->getType()->isMemberPointerType()) {
5176 // C++11 [expr.unary.op]p3 has very strict rules on how the address of a
5177 // member can be formed.
5178 return this->emitGetMemberPtr(cast<DeclRefExpr>(SubExpr)->getDecl(), E);
5179 }
5180 // We should already have a pointer when we get here.
5181 return this->delegate(SubExpr);
5182 case UO_Deref: // *x
5183 if (DiscardResult)
5184 return this->discard(SubExpr);
5185 return this->visit(SubExpr);
5186 case UO_Not: // ~x
5187 if (!T)
5188 return this->emitError(E);
5189
5190 if (!this->visit(SubExpr))
5191 return false;
5192 return DiscardResult ? this->emitPop(*T, E) : this->emitComp(*T, E);
5193 case UO_Real: // __real x
5194 assert(T);
5195 return this->delegate(SubExpr);
5196 case UO_Imag: { // __imag x
5197 assert(T);
5198 if (!this->discard(SubExpr))
5199 return false;
5200 return this->visitZeroInitializer(*T, SubExpr->getType(), SubExpr);
5201 }
5202 case UO_Extension:
5203 return this->delegate(SubExpr);
5204 case UO_Coawait:
5205 assert(false && "Unhandled opcode");
5206 }
5207
5208 return false;
5209}
5210
5211template <class Emitter>
5213 const Expr *SubExpr = E->getSubExpr();
5214 assert(SubExpr->getType()->isAnyComplexType());
5215
5216 if (DiscardResult)
5217 return this->discard(SubExpr);
5218
5219 std::optional<PrimType> ResT = classify(E);
5220 auto prepareResult = [=]() -> bool {
5221 if (!ResT && !Initializing) {
5222 std::optional<unsigned> LocalIndex = allocateLocal(SubExpr);
5223 if (!LocalIndex)
5224 return false;
5225 return this->emitGetPtrLocal(*LocalIndex, E);
5226 }
5227
5228 return true;
5229 };
5230
5231 // The offset of the temporary, if we created one.
5232 unsigned SubExprOffset = ~0u;
5233 auto createTemp = [=, &SubExprOffset]() -> bool {
5234 SubExprOffset = this->allocateLocalPrimitive(SubExpr, PT_Ptr, true, false);
5235 if (!this->visit(SubExpr))
5236 return false;
5237 return this->emitSetLocal(PT_Ptr, SubExprOffset, E);
5238 };
5239
5240 PrimType ElemT = classifyComplexElementType(SubExpr->getType());
5241 auto getElem = [=](unsigned Offset, unsigned Index) -> bool {
5242 if (!this->emitGetLocal(PT_Ptr, Offset, E))
5243 return false;
5244 return this->emitArrayElemPop(ElemT, Index, E);
5245 };
5246
5247 switch (E->getOpcode()) {
5248 case UO_Minus:
5249 if (!prepareResult())
5250 return false;
5251 if (!createTemp())
5252 return false;
5253 for (unsigned I = 0; I != 2; ++I) {
5254 if (!getElem(SubExprOffset, I))
5255 return false;
5256 if (!this->emitNeg(ElemT, E))
5257 return false;
5258 if (!this->emitInitElem(ElemT, I, E))
5259 return false;
5260 }
5261 break;
5262
5263 case UO_Plus: // +x
5264 case UO_AddrOf: // &x
5265 case UO_Deref: // *x
5266 return this->delegate(SubExpr);
5267
5268 case UO_LNot:
5269 if (!this->visit(SubExpr))
5270 return false;
5271 if (!this->emitComplexBoolCast(SubExpr))
5272 return false;
5273 if (!this->emitInv(E))
5274 return false;
5275 if (PrimType ET = classifyPrim(E->getType()); ET != PT_Bool)
5276 return this->emitCast(PT_Bool, ET, E);
5277 return true;
5278
5279 case UO_Real:
5280 return this->emitComplexReal(SubExpr);
5281
5282 case UO_Imag:
5283 if (!this->visit(SubExpr))
5284 return false;
5285
5286 if (SubExpr->isLValue()) {
5287 if (!this->emitConstUint8(1, E))
5288 return false;
5289 return this->emitArrayElemPtrPopUint8(E);
5290 }
5291
5292 // Since our _Complex implementation does not map to a primitive type,
5293 // we sometimes have to do the lvalue-to-rvalue conversion here manually.
5294 return this->emitArrayElemPop(classifyPrim(E->getType()), 1, E);
5295
5296 case UO_Not: // ~x
5297 if (!this->visit(SubExpr))
5298 return false;
5299 // Negate the imaginary component.
5300 if (!this->emitArrayElem(ElemT, 1, E))
5301 return false;
5302 if (!this->emitNeg(ElemT, E))
5303 return false;
5304 if (!this->emitInitElem(ElemT, 1, E))
5305 return false;
5306 return DiscardResult ? this->emitPopPtr(E) : true;
5307
5308 case UO_Extension:
5309 return this->delegate(SubExpr);
5310
5311 default:
5312 return this->emitInvalid(E);
5313 }
5314
5315 return true;
5316}
5317
5318template <class Emitter>
5320 if (DiscardResult)
5321 return true;
5322
5323 if (const auto *ECD = dyn_cast<EnumConstantDecl>(D)) {
5324 return this->emitConst(ECD->getInitVal(), E);
5325 } else if (const auto *BD = dyn_cast<BindingDecl>(D)) {
5326 return this->visit(BD->getBinding());
5327 } else if (const auto *FuncDecl = dyn_cast<FunctionDecl>(D)) {
5328 const Function *F = getFunction(FuncDecl);
5329 return F && this->emitGetFnPtr(F, E);
5330 } else if (const auto *TPOD = dyn_cast<TemplateParamObjectDecl>(D)) {
5331 if (std::optional<unsigned> Index = P.getOrCreateGlobal(D)) {
5332 if (!this->emitGetPtrGlobal(*Index, E))
5333 return false;
5334 if (std::optional<PrimType> T = classify(E->getType())) {
5335 if (!this->visitAPValue(TPOD->getValue(), *T, E))
5336 return false;
5337 return this->emitInitGlobal(*T, *Index, E);
5338 }
5339 return this->visitAPValueInitializer(TPOD->getValue(), E);
5340 }
5341 return false;
5342 }
5343
5344 // References are implemented via pointers, so when we see a DeclRefExpr
5345 // pointing to a reference, we need to get its value directly (i.e. the
5346 // pointer to the actual value) instead of a pointer to the pointer to the
5347 // value.
5348 bool IsReference = D->getType()->isReferenceType();
5349
5350 // Check for local/global variables and parameters.
5351 if (auto It = Locals.find(D); It != Locals.end()) {
5352 const unsigned Offset = It->second.Offset;
5353 if (IsReference)
5354 return this->emitGetLocal(PT_Ptr, Offset, E);
5355 return this->emitGetPtrLocal(Offset, E);
5356 } else if (auto GlobalIndex = P.getGlobal(D)) {
5357 if (IsReference) {
5358 if (!Ctx.getLangOpts().CPlusPlus11)
5359 return this->emitGetGlobal(classifyPrim(E), *GlobalIndex, E);
5360 return this->emitGetGlobalUnchecked(classifyPrim(E), *GlobalIndex, E);
5361 }
5362
5363 return this->emitGetPtrGlobal(*GlobalIndex, E);
5364 } else if (const auto *PVD = dyn_cast<ParmVarDecl>(D)) {
5365 if (auto It = this->Params.find(PVD); It != this->Params.end()) {
5366 if (IsReference || !It->second.IsPtr)
5367 return this->emitGetParam(classifyPrim(E), It->second.Offset, E);
5368
5369 return this->emitGetPtrParam(It->second.Offset, E);
5370 }
5371 }
5372
5373 // In case we need to re-visit a declaration.
5374 auto revisit = [&](const VarDecl *VD) -> bool {
5375 auto VarState = this->visitDecl(VD);
5376
5377 if (VarState.notCreated())
5378 return true;
5379 if (!VarState)
5380 return false;
5381 // Retry.
5382 return this->visitDeclRef(D, E);
5383 };
5384
5385 // Handle lambda captures.
5386 if (auto It = this->LambdaCaptures.find(D);
5387 It != this->LambdaCaptures.end()) {
5388 auto [Offset, IsPtr] = It->second;
5389
5390 if (IsPtr)
5391 return this->emitGetThisFieldPtr(Offset, E);
5392 return this->emitGetPtrThisField(Offset, E);
5393 } else if (const auto *DRE = dyn_cast<DeclRefExpr>(E);
5394 DRE && DRE->refersToEnclosingVariableOrCapture()) {
5395 if (const auto *VD = dyn_cast<VarDecl>(D); VD && VD->isInitCapture())
5396 return revisit(VD);
5397 }
5398
5399 if (D != InitializingDecl) {
5400 // Try to lazily visit (or emit dummy pointers for) declarations
5401 // we haven't seen yet.
5402 if (Ctx.getLangOpts().CPlusPlus) {
5403 if (const auto *VD = dyn_cast<VarDecl>(D)) {
5404 const auto typeShouldBeVisited = [&](QualType T) -> bool {
5405 if (T.isConstant(Ctx.getASTContext()))
5406 return true;
5407 if (const auto *RT = T->getAs<ReferenceType>())
5408 return RT->getPointeeType().isConstQualified();
5409 return false;
5410 };
5411
5412 // DecompositionDecls are just proxies for us.
5413 if (isa<DecompositionDecl>(VD))
5414 return revisit(VD);
5415
5416 // Visit local const variables like normal.
5417 if ((VD->hasGlobalStorage() || VD->isLocalVarDecl() ||
5418 VD->isStaticDataMember()) &&
5419 typeShouldBeVisited(VD->getType()))
5420 return revisit(VD);
5421 }
5422 } else {
5423 if (const auto *VD = dyn_cast<VarDecl>(D);
5424 VD && VD->getAnyInitializer() &&
5425 VD->getType().isConstant(Ctx.getASTContext()) && !VD->isWeak())
5426 return revisit(VD);
5427 }
5428 }
5429
5430 if (std::optional<unsigned> I = P.getOrCreateDummy(D)) {
5431 if (!this->emitGetPtrGlobal(*I, E))
5432 return false;
5433 if (E->getType()->isVoidType())
5434 return true;
5435 // Convert the dummy pointer to another pointer type if we have to.
5436 if (PrimType PT = classifyPrim(E); PT != PT_Ptr) {
5437 if (isPtrType(PT))
5438 return this->emitDecayPtr(PT_Ptr, PT, E);
5439 return false;
5440 }
5441 return true;
5442 }
5443
5444 if (const auto *DRE = dyn_cast<DeclRefExpr>(E))
5445 return this->emitInvalidDeclRef(DRE, E);
5446 return false;
5447}
5448
5449template <class Emitter>
5451 const auto *D = E->getDecl();
5452 return this->visitDeclRef(D, E);
5453}
5454
5455template <class Emitter> void Compiler<Emitter>::emitCleanup() {
5456 for (VariableScope<Emitter> *C = VarScope; C; C = C->getParent())
5457 C->emitDestruction();
5458}
5459
5460template <class Emitter>
5461unsigned Compiler<Emitter>::collectBaseOffset(const QualType BaseType,
5462 const QualType DerivedType) {
5463 const auto extractRecordDecl = [](QualType Ty) -> const CXXRecordDecl * {
5464 if (const auto *R = Ty->getPointeeCXXRecordDecl())
5465 return R;
5466 return Ty->getAsCXXRecordDecl();
5467 };
5468 const CXXRecordDecl *BaseDecl = extractRecordDecl(BaseType);
5469 const CXXRecordDecl *DerivedDecl = extractRecordDecl(DerivedType);
5470
5471 return Ctx.collectBaseOffset(BaseDecl, DerivedDecl);
5472}
5473
5474/// Emit casts from a PrimType to another PrimType.
5475template <class Emitter>
5477 QualType ToQT, const Expr *E) {
5478
5479 if (FromT == PT_Float) {
5480 // Floating to floating.
5481 if (ToT == PT_Float) {
5482 const llvm::fltSemantics *ToSem = &Ctx.getFloatSemantics(ToQT);
5483 return this->emitCastFP(ToSem, getRoundingMode(E), E);
5484 }
5485
5486 if (ToT == PT_IntAP)
5487 return this->emitCastFloatingIntegralAP(Ctx.getBitWidth(ToQT), E);
5488 if (ToT == PT_IntAPS)
5489 return this->emitCastFloatingIntegralAPS(Ctx.getBitWidth(ToQT), E);
5490
5491 // Float to integral.
5492 if (isIntegralType(ToT) || ToT == PT_Bool)
5493 return this->emitCastFloatingIntegral(ToT, E);
5494 }
5495
5496 if (isIntegralType(FromT) || FromT == PT_Bool) {
5497 if (ToT == PT_IntAP)
5498 return this->emitCastAP(FromT, Ctx.getBitWidth(ToQT), E);
5499 if (ToT == PT_IntAPS)
5500 return this->emitCastAPS(FromT, Ctx.getBitWidth(ToQT), E);
5501
5502 // Integral to integral.
5503 if (isIntegralType(ToT) || ToT == PT_Bool)
5504 return FromT != ToT ? this->emitCast(FromT, ToT, E) : true;
5505
5506 if (ToT == PT_Float) {
5507 // Integral to floating.
5508 const llvm::fltSemantics *ToSem = &Ctx.getFloatSemantics(ToQT);
5509 return this->emitCastIntegralFloating(FromT, ToSem, getRoundingMode(E),
5510 E);
5511 }
5512 }
5513
5514 return false;
5515}
5516
5517/// Emits __real(SubExpr)
5518template <class Emitter>
5519bool Compiler<Emitter>::emitComplexReal(const Expr *SubExpr) {
5520 assert(SubExpr->getType()->isAnyComplexType());
5521
5522 if (DiscardResult)
5523 return this->discard(SubExpr);
5524
5525 if (!this->visit(SubExpr))
5526 return false;
5527 if (SubExpr->isLValue()) {
5528 if (!this->emitConstUint8(0, SubExpr))
5529 return false;
5530 return this->emitArrayElemPtrPopUint8(SubExpr);
5531 }
5532
5533 // Rvalue, load the actual element.
5534 return this->emitArrayElemPop(classifyComplexElementType(SubExpr->getType()),
5535 0, SubExpr);
5536}
5537
5538template <class Emitter>
5540 assert(!DiscardResult);
5541 PrimType ElemT = classifyComplexElementType(E->getType());
5542 // We emit the expression (__real(E) != 0 || __imag(E) != 0)
5543 // for us, that means (bool)E[0] || (bool)E[1]
5544 if (!this->emitArrayElem(ElemT, 0, E))
5545 return false;
5546 if (ElemT == PT_Float) {
5547 if (!this->emitCastFloatingIntegral(PT_Bool, E))
5548 return false;
5549 } else {
5550 if (!this->emitCast(ElemT, PT_Bool, E))
5551 return false;
5552 }
5553
5554 // We now have the bool value of E[0] on the stack.
5555 LabelTy LabelTrue = this->getLabel();
5556 if (!this->jumpTrue(LabelTrue))
5557 return false;
5558
5559 if (!this->emitArrayElemPop(ElemT, 1, E))
5560 return false;
5561 if (ElemT == PT_Float) {
5562 if (!this->emitCastFloatingIntegral(PT_Bool, E))
5563 return false;
5564 } else {
5565 if (!this->emitCast(ElemT, PT_Bool, E))
5566 return false;
5567 }
5568 // Leave the boolean value of E[1] on the stack.
5569 LabelTy EndLabel = this->getLabel();
5570 this->jump(EndLabel);
5571
5572 this->emitLabel(LabelTrue);
5573 if (!this->emitPopPtr(E))
5574 return false;
5575 if (!this->emitConstBool(true, E))
5576 return false;
5577
5578 this->fallthrough(EndLabel);
5579 this->emitLabel(EndLabel);
5580
5581 return true;
5582}
5583
5584template <class Emitter>
5585bool Compiler<Emitter>::emitComplexComparison(const Expr *LHS, const Expr *RHS,
5586 const BinaryOperator *E) {
5587 assert(E->isComparisonOp());
5588 assert(!Initializing);
5589 assert(!DiscardResult);
5590
5591 PrimType ElemT;
5592 bool LHSIsComplex;
5593 unsigned LHSOffset;
5594 if (LHS->getType()->isAnyComplexType()) {
5595 LHSIsComplex = true;
5596 ElemT = classifyComplexElementType(LHS->getType());
5597 LHSOffset = allocateLocalPrimitive(LHS, PT_Ptr, /*IsConst=*/true,
5598 /*IsExtended=*/false);
5599 if (!this->visit(LHS))
5600 return false;
5601 if (!this->emitSetLocal(PT_Ptr, LHSOffset, E))
5602 return false;
5603 } else {
5604 LHSIsComplex = false;
5605 PrimType LHST = classifyPrim(LHS->getType());
5606 LHSOffset = this->allocateLocalPrimitive(LHS, LHST, true, false);
5607 if (!this->visit(LHS))
5608 return false;
5609 if (!this->emitSetLocal(LHST, LHSOffset, E))
5610 return false;
5611 }
5612
5613 bool RHSIsComplex;
5614 unsigned RHSOffset;
5615 if (RHS->getType()->isAnyComplexType()) {
5616 RHSIsComplex = true;
5617 ElemT = classifyComplexElementType(RHS->getType());
5618 RHSOffset = allocateLocalPrimitive(RHS, PT_Ptr, /*IsConst=*/true,
5619 /*IsExtended=*/false);
5620 if (!this->visit(RHS))
5621 return false;
5622 if (!this->emitSetLocal(PT_Ptr, RHSOffset, E))
5623 return false;
5624 } else {
5625 RHSIsComplex = false;
5626 PrimType RHST = classifyPrim(RHS->getType());
5627 RHSOffset = this->allocateLocalPrimitive(RHS, RHST, true, false);
5628 if (!this->visit(RHS))
5629 return false;
5630 if (!this->emitSetLocal(RHST, RHSOffset, E))
5631 return false;
5632 }
5633
5634 auto getElem = [&](unsigned LocalOffset, unsigned Index,
5635 bool IsComplex) -> bool {
5636 if (IsComplex) {
5637 if (!this->emitGetLocal(PT_Ptr, LocalOffset, E))
5638 return false;
5639 return this->emitArrayElemPop(ElemT, Index, E);
5640 }
5641 return this->emitGetLocal(ElemT, LocalOffset, E);
5642 };
5643
5644 for (unsigned I = 0; I != 2; ++I) {
5645 // Get both values.
5646 if (!getElem(LHSOffset, I, LHSIsComplex))
5647 return false;
5648 if (!getElem(RHSOffset, I, RHSIsComplex))
5649 return false;
5650 // And compare them.
5651 if (!this->emitEQ(ElemT, E))
5652 return false;
5653
5654 if (!this->emitCastBoolUint8(E))
5655 return false;
5656 }
5657
5658 // We now have two bool values on the stack. Compare those.
5659 if (!this->emitAddUint8(E))
5660 return false;
5661 if (!this->emitConstUint8(2, E))
5662 return false;
5663
5664 if (E->getOpcode() == BO_EQ) {
5665 if (!this->emitEQUint8(E))
5666 return false;
5667 } else if (E->getOpcode() == BO_NE) {
5668 if (!this->emitNEUint8(E))
5669 return false;
5670 } else
5671 return false;
5672
5673 // In C, this returns an int.
5674 if (PrimType ResT = classifyPrim(E->getType()); ResT != PT_Bool)
5675 return this->emitCast(PT_Bool, ResT, E);
5676 return true;
5677}
5678
5679/// When calling this, we have a pointer of the local-to-destroy
5680/// on the stack.
5681/// Emit destruction of record types (or arrays of record types).
5682template <class Emitter>
5684 assert(R);
5685 const CXXDestructorDecl *Dtor = R->getDestructor();
5686 if (!Dtor || Dtor->isTrivial())
5687 return true;
5688
5689 assert(Dtor);
5690 const Function *DtorFunc = getFunction(Dtor);
5691 if (!DtorFunc)
5692 return false;
5693 assert(DtorFunc->hasThisPointer());
5694 assert(DtorFunc->getNumParams() == 1);
5695 if (!this->emitDupPtr(SourceInfo{}))
5696 return false;
5697 return this->emitCall(DtorFunc, 0, SourceInfo{});
5698}
5699/// When calling this, we have a pointer of the local-to-destroy
5700/// on the stack.
5701/// Emit destruction of record types (or arrays of record types).
5702template <class Emitter>
5704 assert(Desc);
5705 assert(!Desc->isPrimitive());
5706 assert(!Desc->isPrimitiveArray());
5707
5708 // Arrays.
5709 if (Desc->isArray()) {
5710 const Descriptor *ElemDesc = Desc->ElemDesc;
5711 assert(ElemDesc);
5712
5713 // Don't need to do anything for these.
5714 if (ElemDesc->isPrimitiveArray())
5715 return true;
5716
5717 // If this is an array of record types, check if we need
5718 // to call the element destructors at all. If not, try
5719 // to save the work.
5720 if (const Record *ElemRecord = ElemDesc->ElemRecord) {
5721 if (const CXXDestructorDecl *Dtor = ElemRecord->getDestructor();
5722 !Dtor || Dtor->isTrivial())
5723 return true;
5724 }
5725
5726 for (ssize_t I = Desc->getNumElems() - 1; I >= 0; --I) {
5727 if (!this->emitConstUint64(I, SourceInfo{}))
5728 return false;
5729 if (!this->emitArrayElemPtrUint64(SourceInfo{}))
5730 return false;
5731 if (!this->emitDestruction(ElemDesc))
5732 return false;
5733 if (!this->emitPopPtr(SourceInfo{}))
5734 return false;
5735 }
5736 return true;
5737 }
5738
5739 assert(Desc->ElemRecord);
5740 return this->emitRecordDestruction(Desc->ElemRecord);
5741}
5742
5743namespace clang {
5744namespace interp {
5745
5746template class Compiler<ByteCodeEmitter>;
5747template class Compiler<EvalEmitter>;
5748
5749} // namespace interp
5750} // namespace clang
#define V(N, I)
Definition: ASTContext.h:3341
ASTImporterLookupTable & LT
DynTypedNode Node
StringRef P
const Decl * D
Expr * E
static CharUnits AlignOfType(QualType T, const ASTContext &ASTCtx, UnaryExprOrTypeTrait Kind)
Definition: Compiler.cpp:1646
llvm::APSInt APSInt
Definition: Compiler.cpp:22
bool IsStatic
Definition: Format.cpp:3026
APValue - This class implements a discriminated union of [uninitialized] [APSInt] [APFloat],...
Definition: APValue.h:122
const LValueBase getLValueBase() const
Definition: APValue.cpp:974
APValue & getArrayInitializedElt(unsigned I)
Definition: APValue.h:510
ArrayRef< LValuePathEntry > getLValuePath() const
Definition: APValue.cpp:994
APSInt & getInt()
Definition: APValue.h:423
APValue & getStructField(unsigned i)
Definition: APValue.h:551
const FieldDecl * getUnionField() const
Definition: APValue.h:563
unsigned getStructNumFields() const
Definition: APValue.h:542
bool isArray() const
Definition: APValue.h:408
bool isFloat() const
Definition: APValue.h:402
const ValueDecl * getMemberPointerDecl() const
Definition: APValue.cpp:1057
APValue & getUnionValue()
Definition: APValue.h:567
bool isLValue() const
Definition: APValue.h:406
bool isMemberPointer() const
Definition: APValue.h:411
bool isInt() const
Definition: APValue.h:401
unsigned getArraySize() const
Definition: APValue.h:533
bool isUnion() const
Definition: APValue.h:410
@ None
There is no such object (it's outside its lifetime).
Definition: APValue.h:129
bool isStruct() const
Definition: APValue.h:409
bool isNullPointer() const
Definition: APValue.cpp:1010
APFloat & getFloat()
Definition: APValue.h:437
Holds long-lived AST nodes (such as types and decls) that can be referred to throughout the semantic ...
Definition: ASTContext.h:187
CharUnits getTypeAlignInChars(QualType T) const
Return the ABI-specified alignment of a (complete) type T, in characters.
unsigned getPreferredTypeAlign(QualType T) const
Return the "preferred" alignment of the specified type T for the current target, in bits.
Definition: ASTContext.h:2485
const LangOptions & getLangOpts() const
Definition: ASTContext.h:797
TypeInfoChars getTypeInfoDataSizeInChars(QualType T) const
CharUnits getDeclAlign(const Decl *D, bool ForAlignof=false) const
Return a conservative estimate of the alignment of the specified decl D.
CharUnits getTypeSizeInChars(QualType T) const
Return the size of the specified (complete) type T, in characters.
CharUnits toCharUnitsFromBits(int64_t BitSize) const
Convert a size in bits to a size in characters.
AbstractConditionalOperator - An abstract base class for ConditionalOperator and BinaryConditionalOpe...
Definition: Expr.h:4175
AddrLabelExpr - The GNU address of label extension, representing &&label.
Definition: Expr.h:4372
Represents the index of the current element of an array being initialized by an ArrayInitLoopExpr.
Definition: Expr.h:5756
Represents a loop initializing the elements of an array.
Definition: Expr.h:5703
ArraySubscriptExpr - [C99 6.5.2.1] Array Subscripting.
Definition: Expr.h:2674
An Embarcadero array type trait, as used in the implementation of __array_rank and __array_extent.
Definition: ExprCXX.h:2853
Represents an array type, per C99 6.7.5.2 - Array Declarators.
Definition: Type.h:3571
Attr - This represents one attribute.
Definition: Attr.h:42
Represents an attribute applied to a statement.
Definition: Stmt.h:2090
A builtin binary operation expression such as "x + y" or "x <= y".
Definition: Expr.h:3860
static bool isLogicalOp(Opcode Opc)
Definition: Expr.h:3993
Expr * getLHS() const
Definition: Expr.h:3910
static bool isComparisonOp(Opcode Opc)
Definition: Expr.h:3960
static bool isCommaOp(Opcode Opc)
Definition: Expr.h:3963
Expr * getRHS() const
Definition: Expr.h:3912
static bool isPtrMemOp(Opcode Opc)
predicates to categorize the respective opcodes.
Definition: Expr.h:3937
Opcode getOpcode() const
Definition: Expr.h:3905
BlockExpr - Adaptor class for mixing a BlockDecl with expressions.
Definition: Expr.h:6365
BreakStmt - This represents a break.
Definition: Stmt.h:2990
Represents a base class of a C++ class.
Definition: DeclCXX.h:146
Represents binding an expression to a temporary.
Definition: ExprCXX.h:1491
A boolean literal, per ([C++ lex.bool] Boolean literals).
Definition: ExprCXX.h:720
Represents a call to a C++ constructor.
Definition: ExprCXX.h:1546
Represents a C++ constructor within a class.
Definition: DeclCXX.h:2539
bool isCopyOrMoveConstructor(unsigned &TypeQuals) const
Determine whether this is a copy or move constructor.
Definition: DeclCXX.cpp:2811
A default argument (C++ [dcl.fct.default]).
Definition: ExprCXX.h:1268
A use of a default initializer in a constructor or in aggregate initialization.
Definition: ExprCXX.h:1375
Represents a delete expression for memory deallocation and destructor calls, e.g.
Definition: ExprCXX.h:2498
Represents a C++ destructor within a class.
Definition: DeclCXX.h:2803
CXXForRangeStmt - This represents C++0x [stmt.ranged]'s ranged for statement, represented as 'for (ra...
Definition: StmtCXX.h:135
Represents a call to an inherited base class constructor from an inheriting constructor.
Definition: ExprCXX.h:1737
Represents a static or instance method of a struct/union/class.
Definition: DeclCXX.h:2064
const CXXRecordDecl * getParent() const
Return the parent of this method declaration, which is the class in which this method is defined.
Definition: DeclCXX.h:2190
bool isLambdaStaticInvoker() const
Determine whether this is a lambda closure type's static member function that is used for the result ...
Definition: DeclCXX.cpp:2639
Represents a new-expression for memory allocation and constructor calls, e.g: "new CXXNewExpr(foo)".
Definition: ExprCXX.h:2241
Represents a C++11 noexcept expression (C++ [expr.unary.noexcept]).
Definition: ExprCXX.h:4126
The null pointer literal (C++11 [lex.nullptr])
Definition: ExprCXX.h:765
Represents a list-initialization with parenthesis.
Definition: ExprCXX.h:4954
Represents a C++ struct/union/class.
Definition: DeclCXX.h:258
capture_const_iterator captures_end() const
Definition: DeclCXX.h:1112
capture_const_iterator captures_begin() const
Definition: DeclCXX.h:1106
CXXMethodDecl * getLambdaCallOperator() const
Retrieve the lambda call operator of the closure type if this is a closure type.
Definition: DeclCXX.cpp:1633
A C++ reinterpret_cast expression (C++ [expr.reinterpret.cast]).
Definition: ExprCXX.h:523
A rewritten comparison expression that was originally written using operator syntax.
Definition: ExprCXX.h:283
An expression "T()" which creates an rvalue of a non-class type T.
Definition: ExprCXX.h:2182
Implicit construction of a std::initializer_list<T> object from an array temporary within list-initia...
Definition: ExprCXX.h:797
Represents the this expression in C++.
Definition: ExprCXX.h:1152
A C++ throw-expression (C++ [except.throw]).
Definition: ExprCXX.h:1206
CXXTryStmt - A C++ try block, including all handlers.
Definition: StmtCXX.h:69
A Microsoft C++ __uuidof expression, which gets the _GUID that corresponds to the supplied type or ex...
Definition: ExprCXX.h:1066
CallExpr - Represents a function call (C99 6.5.2.2, C++ [expr.call]).
Definition: Expr.h:2830
CaseStmt - Represent a case statement.
Definition: Stmt.h:1811
CastExpr - Base class for type casts, including both implicit casts (ImplicitCastExpr) and explicit c...
Definition: Expr.h:3498
CastKind getCastKind() const
Definition: Expr.h:3542
llvm::iterator_range< path_iterator > path()
Path through the class hierarchy taken by casts between base and derived classes (see implementation ...
Definition: Expr.h:3585
Expr * getSubExpr()
Definition: Expr.h:3548
CharUnits - This is an opaque type for sizes expressed in character units.
Definition: CharUnits.h:38
static CharUnits One()
One - Construct a CharUnits quantity of one.
Definition: CharUnits.h:58
ChooseExpr - GNU builtin-in function __builtin_choose_expr.
Definition: Expr.h:4592
Complex values, per C99 6.2.5p11.
Definition: Type.h:3139
QualType getElementType() const
Definition: Type.h:3149
CompoundAssignOperator - For compound assignments (e.g.
Definition: Expr.h:4122
CompoundLiteralExpr - [C99 6.5.2.5].
Definition: Expr.h:3428
CompoundStmt - This represents a group of statements like { stmt stmt }.
Definition: Stmt.h:1611
body_range body()
Definition: Stmt.h:1674
Stmt * getStmtExprResult()
Definition: Stmt.h:1733
Represents the specialization of a concept - evaluates to a prvalue of type bool.
Definition: ExprConcepts.h:42
Represents the canonical version of C arrays with a specified constant size.
Definition: Type.h:3609
uint64_t getZExtSize() const
Return the size zero-extended as a uint64_t.
Definition: Type.h:3685
ConstantExpr - An expression that occurs in a constant context and optionally the result of evaluatin...
Definition: Expr.h:1077
ContinueStmt - This represents a continue.
Definition: Stmt.h:2960
ConvertVectorExpr - Clang builtin function __builtin_convertvector This AST node provides support for...
Definition: Expr.h:4533
DeclContext * getParent()
getParent - Returns the containing DeclContext.
Definition: DeclBase.h:2090
A reference to a declared variable, function, enum, etc.
Definition: Expr.h:1265
DeclStmt - Adaptor class for mixing declarations with statements and expressions.
Definition: Stmt.h:1502
decl_range decls()
Definition: Stmt.h:1550
Decl - This represents one declaration (or definition), e.g.
Definition: DeclBase.h:86
bool isInvalidDecl() const
Definition: DeclBase.h:595
DoStmt - This represents a 'do/while' stmt.
Definition: Stmt.h:2735
Represents a reference to #emded data.
Definition: Expr.h:4867
bool isFixed() const
Returns true if this is an Objective-C, C++11, or Microsoft-style enumeration with a fixed underlying...
Definition: Decl.h:4058
A helper class that allows the use of isa/cast/dyncast to detect TagType objects of enums.
Definition: Type.h:5996
EnumDecl * getDecl() const
Definition: Type.h:6003
Represents an expression – generally a full-expression – that introduces cleanups to be run at the en...
Definition: ExprCXX.h:3474
This represents one expression.
Definition: Expr.h:110
const Expr * skipRValueSubobjectAdjustments(SmallVectorImpl< const Expr * > &CommaLHS, SmallVectorImpl< SubobjectAdjustment > &Adjustments) const
Walk outwards from an expression we want to bind a reference to and find the expression whose lifetim...
Definition: Expr.cpp:82
bool isGLValue() const
Definition: Expr.h:280
bool isValueDependent() const
Determines whether the value of this expression depends on.
Definition: Expr.h:175
bool containsErrors() const
Whether this expression contains subexpressions which had errors, e.g.
Definition: Expr.h:245
Expr * IgnoreParens() LLVM_READONLY
Skip past any parentheses which might surround this expression until reaching a fixed point.
Definition: Expr.cpp:3066
bool isPRValue() const
Definition: Expr.h:278
bool isLValue() const
isLValue - True if this expression is an "l-value" according to the rules of the current language.
Definition: Expr.h:277
bool HasSideEffects(const ASTContext &Ctx, bool IncludePossibleEffects=true) const
HasSideEffects - This routine returns true for all those expressions which have any effect other than...
Definition: Expr.cpp:3567
bool isTemporaryObject(ASTContext &Ctx, const CXXRecordDecl *TempTy) const
Determine whether the result of this expression is a temporary object of the given class type.
Definition: Expr.cpp:3204
bool refersToBitField() const
Returns true if this expression is a gl-value that potentially refers to a bit-field.
Definition: Expr.h:469
QualType getType() const
Definition: Expr.h:142
An expression trait intrinsic.
Definition: ExprCXX.h:2924
ExtVectorElementExpr - This represents access to specific elements of a vector, and may occur on the ...
Definition: Expr.h:6305
Represents a member of a struct/union/class.
Definition: Decl.h:3030
const RecordDecl * getParent() const
Returns the parent of this field declaration, which is the struct in which this field is defined.
Definition: Decl.h:3247
bool isUnnamedBitField() const
Determines whether this is an unnamed bitfield.
Definition: Decl.h:3124
ForStmt - This represents a 'for (init;cond;inc)' stmt.
Definition: Stmt.h:2791
Represents a function declaration or definition.
Definition: Decl.h:1932
const ParmVarDecl * getParamDecl(unsigned i) const
Definition: Decl.h:2669
Stmt * getBody(const FunctionDecl *&Definition) const
Retrieve the body (definition) of the function.
Definition: Decl.cpp:3224
QualType getReturnType() const
Definition: Decl.h:2717
ArrayRef< ParmVarDecl * > parameters() const
Definition: Decl.h:2646
bool isTrivial() const
Whether this function is "trivial" in some specialized C++ senses.
Definition: Decl.h:2302
bool isDefaulted() const
Whether this function is defaulted.
Definition: Decl.h:2310
unsigned getNumParams() const
Return the number of parameters this function must have based on its FunctionType.
Definition: Decl.cpp:3678
bool hasBody(const FunctionDecl *&Definition) const
Returns true if the function has a body.
Definition: Decl.cpp:3144
GNUNullExpr - Implements the GNU __null extension, which is a name for a null pointer constant that h...
Definition: Expr.h:4667
Represents a C11 generic selection.
Definition: Expr.h:5917
IfStmt - This represents an if/then/else.
Definition: Stmt.h:2148
Stmt * getThen()
Definition: Stmt.h:2237
Stmt * getInit()
Definition: Stmt.h:2298
bool isNonNegatedConsteval() const
Definition: Stmt.h:2333
Expr * getCond()
Definition: Stmt.h:2225
bool isNegatedConsteval() const
Definition: Stmt.h:2337
Stmt * getElse()
Definition: Stmt.h:2246
DeclStmt * getConditionVariableDeclStmt()
If this IfStmt has a condition variable, return the faux DeclStmt associated with the creation of tha...
Definition: Stmt.h:2281
ImaginaryLiteral - We support imaginary integer and floating point literals, like "1....
Definition: Expr.h:1717
Represents an implicitly-generated value initialization of an object of a given type.
Definition: Expr.h:5792
Represents a field injected from an anonymous union/struct into the parent scope.
Definition: Decl.h:3318
Describes an C or C++ initializer list.
Definition: Expr.h:5039
A C++ lambda expression, which produces a function object (of unspecified type) that can be invoked l...
Definition: ExprCXX.h:1954
Implicit declaration of a temporary that was materialized by a MaterializeTemporaryExpr and lifetime-...
Definition: DeclCXX.h:3233
A global _GUID constant.
Definition: DeclCXX.h:4293
APValue & getAsAPValue() const
Get the value of this MSGuidDecl as an APValue.
Definition: DeclCXX.cpp:3508
Represents a prvalue temporary that is written into memory so that a reference can bind to it.
Definition: ExprCXX.h:4728
MemberExpr - [C99 6.5.2.3] Structure and Union Members.
Definition: Expr.h:3187
A pointer to member type per C++ 8.3.3 - Pointers to members.
Definition: Type.h:3513
const Type * getClass() const
Definition: Type.h:3543
This represents a decl that may have a name.
Definition: Decl.h:249
ObjCBoolLiteralExpr - Objective-C Boolean Literal.
Definition: ExprObjC.h:87
ObjCBoxedExpr - used for generalized expression boxing.
Definition: ExprObjC.h:127
ObjCEncodeExpr, used for @encode in Objective-C.
Definition: ExprObjC.h:410
ObjCStringLiteral, used for Objective-C string literals i.e.
Definition: ExprObjC.h:51
OffsetOfExpr - [C99 7.17] - This represents an expression of the form offsetof(record-type,...
Definition: Expr.h:2475
Helper class for OffsetOfExpr.
Definition: Expr.h:2369
@ Array
An index into an array.
Definition: Expr.h:2374
OpaqueValueExpr - An expression referring to an opaque object of a fixed type and value class.
Definition: Expr.h:1173
ParenExpr - This represents a parenthesized expression, e.g.
Definition: Expr.h:2135
Represents a parameter to a function.
Definition: Decl.h:1722
PointerType - C99 6.7.5.1 - Pointer Declarators.
Definition: Type.h:3192
QualType getPointeeType() const
Definition: Type.h:3202
[C99 6.4.2.2] - A predefined identifier such as func.
Definition: Expr.h:1991
PseudoObjectExpr - An expression which accesses a pseudo-object l-value.
Definition: Expr.h:6497
A (possibly-)qualified type.
Definition: Type.h:941
QualType withConst() const
Definition: Type.h:1166
bool isNull() const
Return true if this QualType doesn't point to a type yet.
Definition: Type.h:1008
const Type * getTypePtr() const
Retrieves a pointer to the underlying (unqualified) type.
Definition: Type.h:7755
QualType getCanonicalType() const
Definition: Type.h:7807
bool isConstQualified() const
Determine whether this type is const-qualified.
Definition: Type.h:7828
Represents a struct/union/class.
Definition: Decl.h:4145
A helper class that allows the use of isa/cast/dyncast to detect TagType objects of structs/unions/cl...
Definition: Type.h:5970
Frontend produces RecoveryExprs on semantic errors that prevent creating other well-formed expression...
Definition: Expr.h:7101
Base for LValueReferenceType and RValueReferenceType.
Definition: Type.h:3433
C++2a [expr.prim.req]: A requires-expression provides a concise way to express requirements on templa...
Definition: ExprConcepts.h:510
ReturnStmt - This represents a return, optionally of an expression: return; return 4;.
Definition: Stmt.h:3029
Expr * getRetValue()
Definition: Stmt.h:3060
Scope - A scope is a transient data structure that is used while parsing the program.
Definition: Scope.h:41
ShuffleVectorExpr - clang-specific builtin-in function __builtin_shufflevector.
Definition: Expr.h:4465
Represents an expression that computes the length of a parameter pack.
Definition: ExprCXX.h:4258
Represents a function call to one of __builtin_LINE(), __builtin_COLUMN(), __builtin_FUNCTION(),...
Definition: Expr.h:4761
Represents a C++11 static_assert declaration.
Definition: DeclCXX.h:4062
StmtExpr - This is the GNU Statement Expression extension: ({int X=4; X;}).
Definition: Expr.h:4417
Stmt - This represents one statement.
Definition: Stmt.h:84
StringLiteral - This represents a string literal expression, e.g.
Definition: Expr.h:1778
static StringLiteral * Create(const ASTContext &Ctx, StringRef Str, StringLiteralKind Kind, bool Pascal, QualType Ty, const SourceLocation *Loc, unsigned NumConcatenated)
This is the "fully general" constructor that allows representation of strings formed from multiple co...
Definition: Expr.cpp:1191
Represents a reference to a non-type template parameter that has been substituted with a template arg...
Definition: ExprCXX.h:4484
SwitchStmt - This represents a 'switch' stmt.
Definition: Stmt.h:2398
Represents the declaration of a struct/union/class/enum.
Definition: Decl.h:3561
bool isCompleteDefinition() const
Return true if this decl has its body fully specified.
Definition: Decl.h:3664
bool isUnion() const
Definition: Decl.h:3767
A type trait used in the implementation of various C++11 and Library TR1 trait templates.
Definition: ExprCXX.h:2768
The base class of the type hierarchy.
Definition: Type.h:1829
CXXRecordDecl * getAsCXXRecordDecl() const
Retrieves the CXXRecordDecl that this type refers to, either because the type is a RecordType or beca...
Definition: Type.cpp:1882
bool isVoidType() const
Definition: Type.h:8324
bool isBooleanType() const
Definition: Type.h:8452
bool isLiteralType(const ASTContext &Ctx) const
Return true if this is a literal type (C++11 [basic.types]p10)
Definition: Type.cpp:2892
bool isIncompleteArrayType() const
Definition: Type.h:8088
bool isNothrowT() const
Definition: Type.cpp:3061
bool isVoidPointerType() const
Definition: Type.cpp:665
bool isConstantSizeType() const
Return true if this is not a variable sized type, according to the rules of C99 6....
Definition: Type.cpp:2352
bool isArrayType() const
Definition: Type.h:8080
bool isPointerType() const
Definition: Type.h:8008
bool isIntegerType() const
isIntegerType() does not include complex integers (a GCC extension).
Definition: Type.h:8364
const T * castAs() const
Member-template castAs<specific type>.
Definition: Type.h:8612
bool isEnumeralType() const
Definition: Type.h:8112
QualType getPointeeType() const
If this is a pointer, ObjC object pointer, or block pointer, this returns the respective pointee.
Definition: Type.cpp:705
bool isIntegralOrEnumerationType() const
Determine whether this type is an integral or enumeration type.
Definition: Type.h:8439
bool isDependentType() const
Whether this type is a dependent type, meaning that its definition somehow depends on a template para...
Definition: Type.h:2700
bool isAnyComplexType() const
Definition: Type.h:8116
bool isMemberPointerType() const
Definition: Type.h:8062
bool isAtomicType() const
Definition: Type.h:8163
const ArrayType * getAsArrayTypeUnsafe() const
A variant of getAs<> for array types which silently discards qualifiers from the outermost type.
Definition: Type.h:8598
bool isFunctionType() const
Definition: Type.h:8004
bool isVectorType() const
Definition: Type.h:8120
bool isFloatingType() const
Definition: Type.cpp:2249
const T * getAs() const
Member-template getAs<specific type>'.
Definition: Type.h:8545
bool isRecordType() const
Definition: Type.h:8108
RecordDecl * getAsRecordDecl() const
Retrieves the RecordDecl this type refers to.
Definition: Type.cpp:1886
Base class for declarations which introduce a typedef-name.
Definition: Decl.h:3409
UnaryExprOrTypeTraitExpr - expression with either a type or (unevaluated) expression operand.
Definition: Expr.h:2578
UnaryOperator - This represents the unary-expression's (except sizeof and alignof),...
Definition: Expr.h:2188
Represents a C++ using-enum-declaration.
Definition: DeclCXX.h:3717
Represent the declaration of a variable (in which case it is an lvalue) a function (in which case it ...
Definition: Decl.h:667
QualType getType() const
Definition: Decl.h:678
QualType getType() const
Definition: Value.cpp:234
Represents a variable declaration or definition.
Definition: Decl.h:879
bool isStaticLocal() const
Returns true if a variable with function scope is a static local variable.
Definition: Decl.h:1156
const Expr * getInit() const
Definition: Decl.h:1316
bool isLocalVarDecl() const
Returns true for local variable declarations other than parameters.
Definition: Decl.h:1201
const Expr * getAnyInitializer() const
Get the initializer for this variable, no matter which declaration it is attached to.
Definition: Decl.h:1306
Represents a GCC generic vector type.
Definition: Type.h:4026
unsigned getNumElements() const
Definition: Type.h:4041
QualType getElementType() const
Definition: Type.h:4040
WhileStmt - This represents a 'while' stmt.
Definition: Stmt.h:2594
Scope for storage declared in a compound statement.
Definition: Compiler.h:563
A memory block, either on the stack or in the heap.
Definition: InterpBlock.h:49
void invokeDtor()
Invokes the Destructor.
Definition: InterpBlock.h:121
std::byte * rawData()
Returns a pointer to the raw data, including metadata.
Definition: InterpBlock.h:102
Compilation context for expressions.
Definition: Compiler.h:104
OptLabelTy BreakLabel
Point to break to.
Definition: Compiler.h:403
bool VisitArrayInitIndexExpr(const ArrayInitIndexExpr *E)
Definition: Compiler.cpp:1812
bool VisitCXXDeleteExpr(const CXXDeleteExpr *E)
Definition: Compiler.cpp:2929
bool VisitOffsetOfExpr(const OffsetOfExpr *E)
Definition: Compiler.cpp:2680
bool visitContinueStmt(const ContinueStmt *S)
Definition: Compiler.cpp:4610
bool VisitCharacterLiteral(const CharacterLiteral *E)
Definition: Compiler.cpp:2027
bool VisitCXXParenListInitExpr(const CXXParenListInitExpr *E)
Definition: Compiler.cpp:1613
bool VisitConceptSpecializationExpr(const ConceptSpecializationExpr *E)
Definition: Compiler.cpp:3002
bool VisitCompoundLiteralExpr(const CompoundLiteralExpr *E)
Definition: Compiler.cpp:2353
bool visitBool(const Expr *E)
Visits an expression and converts it to a boolean.
Definition: Compiler.cpp:3315
bool VisitCXXDefaultInitExpr(const CXXDefaultInitExpr *E)
Definition: Compiler.cpp:4199
bool visitDeclAndReturn(const VarDecl *VD, bool ConstantContext) override
Toplevel visitDeclAndReturn().
Definition: Compiler.cpp:3698
bool visitExpr(const Expr *E) override
Definition: Compiler.cpp:3631
bool VisitTypeTraitExpr(const TypeTraitExpr *E)
Definition: Compiler.cpp:2418
bool VisitLambdaExpr(const LambdaExpr *E)
Definition: Compiler.cpp:2434
bool VisitMemberExpr(const MemberExpr *E)
Definition: Compiler.cpp:1760
bool VisitBinaryOperator(const BinaryOperator *E)
Definition: Compiler.cpp:693
bool visitAttributedStmt(const AttributedStmt *S)
Definition: Compiler.cpp:4701
bool VisitPackIndexingExpr(const PackIndexingExpr *E)
Definition: Compiler.cpp:3041
bool VisitArraySubscriptExpr(const ArraySubscriptExpr *E)
Definition: Compiler.cpp:1315
bool VisitCallExpr(const CallExpr *E)
Definition: Compiler.cpp:4013
bool VisitPseudoObjectExpr(const PseudoObjectExpr *E)
Definition: Compiler.cpp:3017
bool VisitCXXReinterpretCastExpr(const CXXReinterpretCastExpr *E)
Definition: Compiler.cpp:2489
const Function * getFunction(const FunctionDecl *FD)
Returns a function for the given FunctionDecl.
Definition: Compiler.cpp:3627
void emitCleanup()
Emits scope cleanup instructions.
Definition: Compiler.cpp:5455
bool VisitCastExpr(const CastExpr *E)
Definition: Compiler.cpp:178
bool VisitObjCEncodeExpr(const ObjCEncodeExpr *E)
Definition: Compiler.cpp:1992
bool VisitComplexUnaryOperator(const UnaryOperator *E)
Definition: Compiler.cpp:5212
llvm::DenseMap< const SwitchCase *, LabelTy > CaseMap
Definition: Compiler.h:110
bool visitDeclStmt(const DeclStmt *DS)
Definition: Compiler.cpp:4339
bool VisitBlockExpr(const BlockExpr *E)
Definition: Compiler.cpp:2940
bool visitAPValue(const APValue &Val, PrimType ValType, const Expr *E)
Visit an APValue.
Definition: Compiler.cpp:3868
bool VisitCXXScalarValueInitExpr(const CXXScalarValueInitExpr *E)
Definition: Compiler.cpp:2715
bool VisitLogicalBinOp(const BinaryOperator *E)
Definition: Compiler.cpp:947
bool visitCompoundStmt(const CompoundStmt *S)
Definition: Compiler.cpp:4330
bool visitDeclRef(const ValueDecl *D, const Expr *E)
Visit the given decl as if we have a reference to it.
Definition: Compiler.cpp:5319
bool visitBreakStmt(const BreakStmt *S)
Definition: Compiler.cpp:4601
bool visitForStmt(const ForStmt *S)
Definition: Compiler.cpp:4498
bool VisitDeclRefExpr(const DeclRefExpr *E)
Definition: Compiler.cpp:5450
bool VisitOpaqueValueExpr(const OpaqueValueExpr *E)
Definition: Compiler.cpp:1851
bool VisitArrayInitLoopExpr(const ArrayInitLoopExpr *E)
Definition: Compiler.cpp:1821
OptLabelTy DefaultLabel
Default case label.
Definition: Compiler.h:407
bool VisitStmtExpr(const StmtExpr *E)
Definition: Compiler.cpp:3239
bool VisitCXXBoolLiteralExpr(const CXXBoolLiteralExpr *E)
Definition: Compiler.cpp:4218
bool VisitCXXNewExpr(const CXXNewExpr *E)
Definition: Compiler.cpp:2829
bool VisitCompoundAssignOperator(const CompoundAssignOperator *E)
Definition: Compiler.cpp:2145
bool visitArrayElemInit(unsigned ElemIndex, const Expr *Init)
Pointer to the array(not the element!) must be on the stack when calling this.
Definition: Compiler.cpp:1586
bool delegate(const Expr *E)
Just pass evaluation on to E.
Definition: Compiler.cpp:3267
bool discard(const Expr *E)
Evaluates an expression for side effects and discards the result.
Definition: Compiler.cpp:3261
bool VisitCXXDefaultArgExpr(const CXXDefaultArgExpr *E)
Definition: Compiler.cpp:4206
CaseMap CaseLabels
Switch case mapping.
Definition: Compiler.h:400
Record * getRecord(QualType Ty)
Returns a record from a record or pointer type.
Definition: Compiler.cpp:3615
bool visit(const Expr *E)
Evaluates an expression and places the result on the stack.
Definition: Compiler.cpp:3274
const RecordType * getRecordTy(QualType Ty)
Returns a record type from a record or pointer type.
Definition: Compiler.cpp:3609
bool VisitCXXStdInitializerListExpr(const CXXStdInitializerListExpr *E)
Definition: Compiler.cpp:3206
std::optional< unsigned > allocateLocal(DeclTy &&Decl, const ValueDecl *ExtendingDecl=nullptr)
Allocates a space storing a local given its type.
Definition: Compiler.cpp:3547
bool visitInitList(ArrayRef< const Expr * > Inits, const Expr *ArrayFiller, const Expr *E)
Definition: Compiler.cpp:1345
bool VisitSizeOfPackExpr(const SizeOfPackExpr *E)
Definition: Compiler.cpp:2774
bool VisitPredefinedExpr(const PredefinedExpr *E)
Definition: Compiler.cpp:2473
bool VisitSourceLocExpr(const SourceLocExpr *E)
Definition: Compiler.cpp:2624
bool VisitExtVectorElementExpr(const ExtVectorElementExpr *E)
Definition: Compiler.cpp:3135
bool VisitObjCStringLiteral(const ObjCStringLiteral *E)
Definition: Compiler.cpp:1987
bool VisitArrayTypeTraitExpr(const ArrayTypeTraitExpr *E)
Definition: Compiler.cpp:2427
bool visitInitializer(const Expr *E)
Compiles an initializer.
Definition: Compiler.cpp:3301
bool VisitCXXBindTemporaryExpr(const CXXBindTemporaryExpr *E)
Definition: Compiler.cpp:2347
bool VisitPointerArithBinOp(const BinaryOperator *E)
Perform addition/subtraction of a pointer and an integer or subtraction of two pointers.
Definition: Compiler.cpp:873
bool VisitObjCBoolLiteralExpr(const ObjCBoolLiteralExpr *E)
Definition: Compiler.cpp:2790
bool visitDefaultStmt(const DefaultStmt *S)
Definition: Compiler.cpp:4695
typename Emitter::LabelTy LabelTy
Definition: Compiler.h:107
VarCreationState visitDecl(const VarDecl *VD)
Definition: Compiler.cpp:3670
bool visitStmt(const Stmt *S)
Definition: Compiler.cpp:4280
bool VisitExpressionTraitExpr(const ExpressionTraitExpr *E)
Definition: Compiler.cpp:2951
bool visitAPValueInitializer(const APValue &Val, const Expr *E)
Definition: Compiler.cpp:3895
bool VisitCXXConstructExpr(const CXXConstructExpr *E)
Definition: Compiler.cpp:2510
bool VisitCXXNullPtrLiteralExpr(const CXXNullPtrLiteralExpr *E)
Definition: Compiler.cpp:4226
bool VisitObjCBoxedExpr(const ObjCBoxedExpr *E)
Definition: Compiler.cpp:3197
bool VisitCXXInheritedCtorInitExpr(const CXXInheritedCtorInitExpr *E)
Definition: Compiler.cpp:2798
bool VisitRecoveryExpr(const RecoveryExpr *E)
Definition: Compiler.cpp:3046
bool VisitRequiresExpr(const RequiresExpr *E)
Definition: Compiler.cpp:2994
bool Initializing
Flag inidicating if we're initializing an already created variable.
Definition: Compiler.h:390
bool visitReturnStmt(const ReturnStmt *RS)
Definition: Compiler.cpp:4356
bool VisitCXXThrowExpr(const CXXThrowExpr *E)
Definition: Compiler.cpp:2481
bool VisitSubstNonTypeTemplateParmExpr(const SubstNonTypeTemplateParmExpr *E)
Definition: Compiler.cpp:1619
bool VisitChooseExpr(const ChooseExpr *E)
Definition: Compiler.cpp:2785
bool visitFunc(const FunctionDecl *F) override
Definition: Compiler.cpp:4967
bool visitCXXForRangeStmt(const CXXForRangeStmt *S)
Definition: Compiler.cpp:4545
bool visitCaseStmt(const CaseStmt *S)
Definition: Compiler.cpp:4689
bool VisitComplexBinOp(const BinaryOperator *E)
Definition: Compiler.cpp:1008
bool VisitAbstractConditionalOperator(const AbstractConditionalOperator *E)
Definition: Compiler.cpp:1887
OptLabelTy ContinueLabel
Point to continue to.
Definition: Compiler.h:405
bool VisitImplicitValueInitExpr(const ImplicitValueInitExpr *E)
Definition: Compiler.cpp:1231
bool VisitCXXRewrittenBinaryOperator(const CXXRewrittenBinaryOperator *E)
Definition: Compiler.cpp:3011
bool VisitUnaryOperator(const UnaryOperator *E)
Definition: Compiler.cpp:4993
bool VisitFloatCompoundAssignOperator(const CompoundAssignOperator *E)
Definition: Compiler.cpp:2034
bool VisitGenericSelectionExpr(const GenericSelectionExpr *E)
Definition: Compiler.cpp:2779
bool visitDoStmt(const DoStmt *S)
Definition: Compiler.cpp:4470
bool VisitIntegerLiteral(const IntegerLiteral *E)
Definition: Compiler.cpp:650
bool VisitInitListExpr(const InitListExpr *E)
Definition: Compiler.cpp:1608
bool VisitStringLiteral(const StringLiteral *E)
Definition: Compiler.cpp:1930
bool VisitParenExpr(const ParenExpr *E)
Definition: Compiler.cpp:688
bool VisitCXXNoexceptExpr(const CXXNoexceptExpr *E)
Definition: Compiler.cpp:2501
bool VisitShuffleVectorExpr(const ShuffleVectorExpr *E)
Definition: Compiler.cpp:3093
bool VisitPointerCompoundAssignOperator(const CompoundAssignOperator *E)
Definition: Compiler.cpp:2108
std::optional< LabelTy > OptLabelTy
Definition: Compiler.h:109
bool DiscardResult
Flag indicating if return value is to be discarded.
Definition: Compiler.h:384
bool VisitEmbedExpr(const EmbedExpr *E)
Definition: Compiler.cpp:1641
bool VisitConvertVectorExpr(const ConvertVectorExpr *E)
Definition: Compiler.cpp:3061
bool VisitCXXThisExpr(const CXXThisExpr *E)
Definition: Compiler.cpp:4246
bool VisitConstantExpr(const ConstantExpr *E)
Definition: Compiler.cpp:1625
unsigned allocateTemporary(const Expr *E)
Definition: Compiler.cpp:3588
bool VisitUnaryExprOrTypeTraitExpr(const UnaryExprOrTypeTraitExpr *E)
Definition: Compiler.cpp:1670
bool visitSwitchStmt(const SwitchStmt *S)
Definition: Compiler.cpp:4619
bool VisitCXXUuidofExpr(const CXXUuidofExpr *E)
Definition: Compiler.cpp:2957
unsigned allocateLocalPrimitive(DeclTy &&Decl, PrimType Ty, bool IsConst, bool IsExtended=false)
Creates a local primitive value.
Definition: Compiler.cpp:3522
bool VisitExprWithCleanups(const ExprWithCleanups *E)
Definition: Compiler.cpp:2266
bool visitWhileStmt(const WhileStmt *S)
Definition: Compiler.cpp:4439
bool visitIfStmt(const IfStmt *IS)
Definition: Compiler.cpp:4390
bool VisitAddrLabelExpr(const AddrLabelExpr *E)
Definition: Compiler.cpp:3051
bool VisitFloatingLiteral(const FloatingLiteral *E)
Definition: Compiler.cpp:658
bool VisitBuiltinCallExpr(const CallExpr *E)
Definition: Compiler.cpp:3958
bool VisitMaterializeTemporaryExpr(const MaterializeTemporaryExpr *E)
Definition: Compiler.cpp:2274
bool VisitGNUNullExpr(const GNUNullExpr *E)
Definition: Compiler.cpp:4235
bool VisitImaginaryLiteral(const ImaginaryLiteral *E)
Definition: Compiler.cpp:666
bool VisitSYCLUniqueStableNameExpr(const SYCLUniqueStableNameExpr *E)
Definition: Compiler.cpp:2003
VarCreationState visitVarDecl(const VarDecl *VD, bool Toplevel=false)
Creates and initializes a variable from the given decl.
Definition: Compiler.cpp:3758
bool visitCXXTryStmt(const CXXTryStmt *S)
Definition: Compiler.cpp:4732
static bool shouldBeGloballyIndexed(const ValueDecl *VD)
Returns whether we should create a global variable for the given ValueDecl.
Definition: Context.h:97
Scope used to handle temporaries in toplevel variable declarations.
Definition: Compiler.cpp:28
void addExtended(const Scope::Local &Local) override
Definition: Compiler.cpp:37
DeclScope(Compiler< Emitter > *Ctx, const ValueDecl *VD)
Definition: Compiler.cpp:30
Bytecode function.
Definition: Function.h:81
unsigned getNumParams() const
Definition: Function.h:206
bool hasThisPointer() const
Definition: Function.h:186
bool hasRVO() const
Checks if the first argument is a RVO pointer.
Definition: Function.h:116
Scope managing label targets.
Definition: Compiler.cpp:99
LabelScope(Compiler< Emitter > *Ctx)
Definition: Compiler.cpp:104
Compiler< Emitter > * Ctx
Compiler instance.
Definition: Compiler.cpp:106
Generic scope for local variables.
Definition: Compiler.h:475
bool destroyLocals(const Expr *E=nullptr) override
Explicit destruction of local variables.
Definition: Compiler.h:499
void addLocal(const Scope::Local &Local) override
Definition: Compiler.h:509
Sets the context for break/continue statements.
Definition: Compiler.cpp:110
typename Compiler< Emitter >::LabelTy LabelTy
Definition: Compiler.cpp:112
LoopScope(Compiler< Emitter > *Ctx, LabelTy BreakLabel, LabelTy ContinueLabel)
Definition: Compiler.cpp:115
typename Compiler< Emitter >::OptLabelTy OptLabelTy
Definition: Compiler.cpp:113
Scope used to handle initialization methods.
Definition: Compiler.cpp:52
OptionScope(Compiler< Emitter > *Ctx, bool NewDiscardResult, bool NewInitializing)
Root constructor, compiling or discarding primitives.
Definition: Compiler.cpp:55
Context to manage declaration lifetimes.
Definition: Program.h:132
Structure/Class descriptor.
Definition: Record.h:25
bool isUnion() const
Checks if the record is a union.
Definition: Record.h:56
const CXXDestructorDecl * getDestructor() const
Returns the destructor of the record, if any.
Definition: Record.h:70
const Field * getField(const FieldDecl *FD) const
Returns a field.
Definition: Record.cpp:39
llvm::iterator_range< const_base_iter > bases() const
Definition: Record.h:85
const Base * getVirtualBase(const RecordDecl *RD) const
Returns a virtual base descriptor.
Definition: Record.cpp:59
unsigned getNumFields() const
Definition: Record.h:81
llvm::iterator_range< const_field_iter > fields() const
Definition: Record.h:77
const Base * getBase(const RecordDecl *FD) const
Returns a base descriptor.
Definition: Record.cpp:45
Describes a scope block.
Definition: Function.h:36
Describes the statement/declaration an opcode was generated from.
Definition: Source.h:77
StmtExprScope(Compiler< Emitter > *Ctx)
Definition: Compiler.cpp:163
typename Compiler< Emitter >::LabelTy LabelTy
Definition: Compiler.cpp:135
typename Compiler< Emitter >::OptLabelTy OptLabelTy
Definition: Compiler.cpp:136
SwitchScope(Compiler< Emitter > *Ctx, CaseMap &&CaseLabels, LabelTy BreakLabel, OptLabelTy DefaultLabel)
Definition: Compiler.cpp:139
typename Compiler< Emitter >::CaseMap CaseMap
Definition: Compiler.cpp:137
Scope chain managing the variable lifetimes.
Definition: Compiler.h:414
Compiler< Emitter > * Ctx
Compiler instance.
Definition: Compiler.h:468
llvm::APInt APInt
Definition: Integral.h:29
constexpr bool isPtrType(PrimType T)
Definition: PrimType.h:51
constexpr size_t align(size_t Size)
Aligns a size to the pointer alignment.
Definition: PrimType.h:126
bool InitScope(InterpState &S, CodePtr OpPC, uint32_t I)
Definition: Interp.h:2063
bool LE(InterpState &S, CodePtr OpPC)
Definition: Interp.h:1104
PrimType
Enumeration of the primitive types of the VM.
Definition: PrimType.h:33
llvm::BitVector collectNonNullArgs(const FunctionDecl *F, const llvm::ArrayRef< const Expr * > &Args)
size_t primSize(PrimType Type)
Returns the size of a primitive type in bytes.
Definition: PrimType.cpp:23
llvm::APSInt APSInt
Definition: Floating.h:24
llvm::PointerUnion< const Decl *, const Expr * > DeclTy
Definition: Descriptor.h:28
constexpr bool isIntegralType(PrimType T)
Definition: PrimType.h:72
The JSON file list parser is used to communicate input to InstallAPI.
bool isa(CodeGen::Address addr)
Definition: Address.h:328
BinaryOperatorKind
UnaryExprOrTypeTrait
Names for the "expression or type" traits.
Definition: TypeTraits.h:51
@ SD_Static
Static storage duration.
Definition: Specifiers.h:331
const FunctionProtoType * T
@ Success
Template argument deduction was successful.
#define true
Definition: stdbool.h:25
Describes a memory block created by an allocation site.
Definition: Descriptor.h:111
unsigned getNumElems() const
Returns the number of elements stored in the block.
Definition: Descriptor.h:237
bool isPrimitive() const
Checks if the descriptor is of a primitive.
Definition: Descriptor.h:251
const Descriptor *const ElemDesc
Descriptor of the array element.
Definition: Descriptor.h:143
static constexpr MetadataSize InlineDescMD
Definition: Descriptor.h:132
bool isPrimitiveArray() const
Checks if the descriptor is of an array of primitives.
Definition: Descriptor.h:242
const Record *const ElemRecord
Pointer to the record, if block contains records.
Definition: Descriptor.h:141
bool isArray() const
Checks if the descriptor is of an array.
Definition: Descriptor.h:254
Descriptor used for global variables.
Definition: Descriptor.h:58
const FieldDecl * Decl
Definition: Record.h:29
Information about a local's storage.
Definition: Function.h:39
State encapsulating if a the variable creation has been successful, unsuccessful, or no variable has ...
Definition: Compiler.h:91
static VarCreationState NotCreated()
Definition: Compiler.h:95