1 //===--- ByteCodeExprGen.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 "ByteCodeExprGen.h"
10 #include "ByteCodeEmitter.h"
11 #include "ByteCodeGenError.h"
12 #include "ByteCodeStmtGen.h"
13 #include "Context.h"
14 #include "Floating.h"
15 #include "Function.h"
16 #include "PrimType.h"
17 #include "Program.h"
18
19 using namespace clang;
20 using namespace clang::interp;
21
22 using APSInt = llvm::APSInt;
23
24 namespace clang {
25 namespace interp {
26
27 /// Scope used to handle temporaries in toplevel variable declarations.
28 template <class Emitter> class DeclScope final : public VariableScope<Emitter> {
29 public:
DeclScope(ByteCodeExprGen<Emitter> * Ctx,const ValueDecl * VD)30 DeclScope(ByteCodeExprGen<Emitter> *Ctx, const ValueDecl *VD)
31 : VariableScope<Emitter>(Ctx), Scope(Ctx->P, VD),
32 OldGlobalDecl(Ctx->GlobalDecl) {
33 Ctx->GlobalDecl = Context::shouldBeGloballyIndexed(VD);
34 }
35
addExtended(const Scope::Local & Local)36 void addExtended(const Scope::Local &Local) override {
37 return this->addLocal(Local);
38 }
39
~DeclScope()40 ~DeclScope() { this->Ctx->GlobalDecl = OldGlobalDecl; }
41
42 private:
43 Program::DeclScope Scope;
44 bool OldGlobalDecl;
45 };
46
47 /// Scope used to handle initialization methods.
48 template <class Emitter> class OptionScope final {
49 public:
50 /// Root constructor, compiling or discarding primitives.
OptionScope(ByteCodeExprGen<Emitter> * Ctx,bool NewDiscardResult,bool NewInitializing)51 OptionScope(ByteCodeExprGen<Emitter> *Ctx, bool NewDiscardResult,
52 bool NewInitializing)
53 : Ctx(Ctx), OldDiscardResult(Ctx->DiscardResult),
54 OldInitializing(Ctx->Initializing) {
55 Ctx->DiscardResult = NewDiscardResult;
56 Ctx->Initializing = NewInitializing;
57 }
58
~OptionScope()59 ~OptionScope() {
60 Ctx->DiscardResult = OldDiscardResult;
61 Ctx->Initializing = OldInitializing;
62 }
63
64 private:
65 /// Parent context.
66 ByteCodeExprGen<Emitter> *Ctx;
67 /// Old discard flag to restore.
68 bool OldDiscardResult;
69 bool OldInitializing;
70 };
71
72 } // namespace interp
73 } // namespace clang
74
75 template <class Emitter>
VisitCastExpr(const CastExpr * CE)76 bool ByteCodeExprGen<Emitter>::VisitCastExpr(const CastExpr *CE) {
77 const Expr *SubExpr = CE->getSubExpr();
78 switch (CE->getCastKind()) {
79
80 case CK_LValueToRValue: {
81 return dereference(
82 SubExpr, DerefKind::Read,
83 [](PrimType) {
84 // Value loaded - nothing to do here.
85 return true;
86 },
87 [this, CE](PrimType T) {
88 // Pointer on stack - dereference it.
89 if (!this->emitLoadPop(T, CE))
90 return false;
91 return DiscardResult ? this->emitPop(T, CE) : true;
92 });
93 }
94
95 case CK_UncheckedDerivedToBase:
96 case CK_DerivedToBase: {
97 if (!this->visit(SubExpr))
98 return false;
99
100 unsigned DerivedOffset = collectBaseOffset(getRecordTy(CE->getType()),
101 getRecordTy(SubExpr->getType()));
102
103 return this->emitGetPtrBasePop(DerivedOffset, CE);
104 }
105
106 case CK_BaseToDerived: {
107 if (!this->visit(SubExpr))
108 return false;
109
110 unsigned DerivedOffset = collectBaseOffset(getRecordTy(SubExpr->getType()),
111 getRecordTy(CE->getType()));
112
113 return this->emitGetPtrDerivedPop(DerivedOffset, CE);
114 }
115
116 case CK_FloatingCast: {
117 if (DiscardResult)
118 return this->discard(SubExpr);
119 if (!this->visit(SubExpr))
120 return false;
121 const auto *TargetSemantics = &Ctx.getFloatSemantics(CE->getType());
122 return this->emitCastFP(TargetSemantics, getRoundingMode(CE), CE);
123 }
124
125 case CK_IntegralToFloating: {
126 if (DiscardResult)
127 return this->discard(SubExpr);
128 std::optional<PrimType> FromT = classify(SubExpr->getType());
129 if (!FromT)
130 return false;
131
132 if (!this->visit(SubExpr))
133 return false;
134
135 const auto *TargetSemantics = &Ctx.getFloatSemantics(CE->getType());
136 llvm::RoundingMode RM = getRoundingMode(CE);
137 return this->emitCastIntegralFloating(*FromT, TargetSemantics, RM, CE);
138 }
139
140 case CK_FloatingToBoolean:
141 case CK_FloatingToIntegral: {
142 if (DiscardResult)
143 return this->discard(SubExpr);
144
145 std::optional<PrimType> ToT = classify(CE->getType());
146
147 if (!ToT)
148 return false;
149
150 if (!this->visit(SubExpr))
151 return false;
152
153 if (ToT == PT_IntAP)
154 return this->emitCastFloatingIntegralAP(Ctx.getBitWidth(CE->getType()),
155 CE);
156 if (ToT == PT_IntAPS)
157 return this->emitCastFloatingIntegralAPS(Ctx.getBitWidth(CE->getType()),
158 CE);
159
160 return this->emitCastFloatingIntegral(*ToT, CE);
161 }
162
163 case CK_NullToPointer:
164 if (DiscardResult)
165 return true;
166 return this->emitNull(classifyPrim(CE->getType()), CE);
167
168 case CK_PointerToIntegral: {
169 // TODO: Discard handling.
170 if (!this->visit(SubExpr))
171 return false;
172
173 PrimType T = classifyPrim(CE->getType());
174 return this->emitCastPointerIntegral(T, CE);
175 }
176
177 case CK_ArrayToPointerDecay: {
178 if (!this->visit(SubExpr))
179 return false;
180 if (!this->emitArrayDecay(CE))
181 return false;
182 if (DiscardResult)
183 return this->emitPopPtr(CE);
184 return true;
185 }
186
187 case CK_AtomicToNonAtomic:
188 case CK_ConstructorConversion:
189 case CK_FunctionToPointerDecay:
190 case CK_NonAtomicToAtomic:
191 case CK_NoOp:
192 case CK_UserDefinedConversion:
193 case CK_BitCast:
194 return this->delegate(SubExpr);
195
196 case CK_IntegralToBoolean:
197 case CK_IntegralCast: {
198 if (DiscardResult)
199 return this->discard(SubExpr);
200 std::optional<PrimType> FromT = classify(SubExpr->getType());
201 std::optional<PrimType> ToT = classify(CE->getType());
202
203 if (!FromT || !ToT)
204 return false;
205
206 if (!this->visit(SubExpr))
207 return false;
208
209 if (ToT == PT_IntAP)
210 return this->emitCastAP(*FromT, Ctx.getBitWidth(CE->getType()), CE);
211 if (ToT == PT_IntAPS)
212 return this->emitCastAPS(*FromT, Ctx.getBitWidth(CE->getType()), CE);
213
214 if (FromT == ToT)
215 return true;
216 return this->emitCast(*FromT, *ToT, CE);
217 }
218
219 case CK_PointerToBoolean: {
220 PrimType PtrT = classifyPrim(SubExpr->getType());
221
222 // Just emit p != nullptr for this.
223 if (!this->visit(SubExpr))
224 return false;
225
226 if (!this->emitNull(PtrT, CE))
227 return false;
228
229 return this->emitNE(PtrT, CE);
230 }
231
232 case CK_IntegralComplexToBoolean:
233 case CK_FloatingComplexToBoolean: {
234 std::optional<PrimType> ElemT =
235 classifyComplexElementType(SubExpr->getType());
236 if (!ElemT)
237 return false;
238 // We emit the expression (__real(E) != 0 || __imag(E) != 0)
239 // for us, that means (bool)E[0] || (bool)E[1]
240 if (!this->visit(SubExpr))
241 return false;
242 if (!this->emitConstUint8(0, CE))
243 return false;
244 if (!this->emitArrayElemPtrUint8(CE))
245 return false;
246 if (!this->emitLoadPop(*ElemT, CE))
247 return false;
248 if (*ElemT == PT_Float) {
249 if (!this->emitCastFloatingIntegral(PT_Bool, CE))
250 return false;
251 } else {
252 if (!this->emitCast(*ElemT, PT_Bool, CE))
253 return false;
254 }
255
256 // We now have the bool value of E[0] on the stack.
257 LabelTy LabelTrue = this->getLabel();
258 if (!this->jumpTrue(LabelTrue))
259 return false;
260
261 if (!this->emitConstUint8(1, CE))
262 return false;
263 if (!this->emitArrayElemPtrPopUint8(CE))
264 return false;
265 if (!this->emitLoadPop(*ElemT, CE))
266 return false;
267 if (*ElemT == PT_Float) {
268 if (!this->emitCastFloatingIntegral(PT_Bool, CE))
269 return false;
270 } else {
271 if (!this->emitCast(*ElemT, PT_Bool, CE))
272 return false;
273 }
274 // Leave the boolean value of E[1] on the stack.
275 LabelTy EndLabel = this->getLabel();
276 this->jump(EndLabel);
277
278 this->emitLabel(LabelTrue);
279 if (!this->emitPopPtr(CE))
280 return false;
281 if (!this->emitConstBool(true, CE))
282 return false;
283
284 this->fallthrough(EndLabel);
285 this->emitLabel(EndLabel);
286
287 return true;
288 }
289
290 case CK_IntegralComplexToReal:
291 case CK_FloatingComplexToReal:
292 return this->emitComplexReal(SubExpr);
293
294 case CK_IntegralRealToComplex:
295 case CK_FloatingRealToComplex: {
296 // We're creating a complex value here, so we need to
297 // allocate storage for it.
298 if (!Initializing) {
299 std::optional<unsigned> LocalIndex =
300 allocateLocal(CE, /*IsExtended=*/true);
301 if (!LocalIndex)
302 return false;
303 if (!this->emitGetPtrLocal(*LocalIndex, CE))
304 return false;
305 }
306
307 // Init the complex value to {SubExpr, 0}.
308 if (!this->visitArrayElemInit(0, SubExpr))
309 return false;
310 // Zero-init the second element.
311 PrimType T = classifyPrim(SubExpr->getType());
312 if (!this->visitZeroInitializer(T, SubExpr->getType(), SubExpr))
313 return false;
314 return this->emitInitElem(T, 1, SubExpr);
315 }
316
317 case CK_ToVoid:
318 return discard(SubExpr);
319
320 default:
321 assert(false && "Cast not implemented");
322 }
323 llvm_unreachable("Unhandled clang::CastKind enum");
324 }
325
326 template <class Emitter>
VisitIntegerLiteral(const IntegerLiteral * LE)327 bool ByteCodeExprGen<Emitter>::VisitIntegerLiteral(const IntegerLiteral *LE) {
328 if (DiscardResult)
329 return true;
330
331 return this->emitConst(LE->getValue(), LE);
332 }
333
334 template <class Emitter>
VisitFloatingLiteral(const FloatingLiteral * E)335 bool ByteCodeExprGen<Emitter>::VisitFloatingLiteral(const FloatingLiteral *E) {
336 if (DiscardResult)
337 return true;
338
339 return this->emitConstFloat(E->getValue(), E);
340 }
341
342 template <class Emitter>
VisitParenExpr(const ParenExpr * E)343 bool ByteCodeExprGen<Emitter>::VisitParenExpr(const ParenExpr *E) {
344 return this->delegate(E->getSubExpr());
345 }
346
347 template <class Emitter>
VisitBinaryOperator(const BinaryOperator * BO)348 bool ByteCodeExprGen<Emitter>::VisitBinaryOperator(const BinaryOperator *BO) {
349 // Need short-circuiting for these.
350 if (BO->isLogicalOp())
351 return this->VisitLogicalBinOp(BO);
352
353 if (BO->getType()->isAnyComplexType())
354 return this->VisitComplexBinOp(BO);
355
356 const Expr *LHS = BO->getLHS();
357 const Expr *RHS = BO->getRHS();
358
359 if (BO->isPtrMemOp())
360 return this->visit(RHS);
361
362 // Typecheck the args.
363 std::optional<PrimType> LT = classify(LHS->getType());
364 std::optional<PrimType> RT = classify(RHS->getType());
365 std::optional<PrimType> T = classify(BO->getType());
366
367 // Deal with operations which have composite or void types.
368 if (BO->isCommaOp()) {
369 if (!this->discard(LHS))
370 return false;
371 if (RHS->getType()->isVoidType())
372 return this->discard(RHS);
373
374 return this->delegate(RHS);
375 }
376
377 // Special case for C++'s three-way/spaceship operator <=>, which
378 // returns a std::{strong,weak,partial}_ordering (which is a class, so doesn't
379 // have a PrimType).
380 if (!T) {
381 if (DiscardResult)
382 return true;
383 const ComparisonCategoryInfo *CmpInfo =
384 Ctx.getASTContext().CompCategories.lookupInfoForType(BO->getType());
385 assert(CmpInfo);
386
387 // We need a temporary variable holding our return value.
388 if (!Initializing) {
389 std::optional<unsigned> ResultIndex = this->allocateLocal(BO, false);
390 if (!this->emitGetPtrLocal(*ResultIndex, BO))
391 return false;
392 }
393
394 if (!visit(LHS) || !visit(RHS))
395 return false;
396
397 return this->emitCMP3(*LT, CmpInfo, BO);
398 }
399
400 if (!LT || !RT || !T)
401 return false;
402
403 // Pointer arithmetic special case.
404 if (BO->getOpcode() == BO_Add || BO->getOpcode() == BO_Sub) {
405 if (T == PT_Ptr || (LT == PT_Ptr && RT == PT_Ptr))
406 return this->VisitPointerArithBinOp(BO);
407 }
408
409 if (!visit(LHS) || !visit(RHS))
410 return false;
411
412 // For languages such as C, cast the result of one
413 // of our comparision opcodes to T (which is usually int).
414 auto MaybeCastToBool = [this, T, BO](bool Result) {
415 if (!Result)
416 return false;
417 if (DiscardResult)
418 return this->emitPop(*T, BO);
419 if (T != PT_Bool)
420 return this->emitCast(PT_Bool, *T, BO);
421 return true;
422 };
423
424 auto Discard = [this, T, BO](bool Result) {
425 if (!Result)
426 return false;
427 return DiscardResult ? this->emitPop(*T, BO) : true;
428 };
429
430 switch (BO->getOpcode()) {
431 case BO_EQ:
432 return MaybeCastToBool(this->emitEQ(*LT, BO));
433 case BO_NE:
434 return MaybeCastToBool(this->emitNE(*LT, BO));
435 case BO_LT:
436 return MaybeCastToBool(this->emitLT(*LT, BO));
437 case BO_LE:
438 return MaybeCastToBool(this->emitLE(*LT, BO));
439 case BO_GT:
440 return MaybeCastToBool(this->emitGT(*LT, BO));
441 case BO_GE:
442 return MaybeCastToBool(this->emitGE(*LT, BO));
443 case BO_Sub:
444 if (BO->getType()->isFloatingType())
445 return Discard(this->emitSubf(getRoundingMode(BO), BO));
446 return Discard(this->emitSub(*T, BO));
447 case BO_Add:
448 if (BO->getType()->isFloatingType())
449 return Discard(this->emitAddf(getRoundingMode(BO), BO));
450 return Discard(this->emitAdd(*T, BO));
451 case BO_Mul:
452 if (BO->getType()->isFloatingType())
453 return Discard(this->emitMulf(getRoundingMode(BO), BO));
454 return Discard(this->emitMul(*T, BO));
455 case BO_Rem:
456 return Discard(this->emitRem(*T, BO));
457 case BO_Div:
458 if (BO->getType()->isFloatingType())
459 return Discard(this->emitDivf(getRoundingMode(BO), BO));
460 return Discard(this->emitDiv(*T, BO));
461 case BO_Assign:
462 if (DiscardResult)
463 return LHS->refersToBitField() ? this->emitStoreBitFieldPop(*T, BO)
464 : this->emitStorePop(*T, BO);
465 return LHS->refersToBitField() ? this->emitStoreBitField(*T, BO)
466 : this->emitStore(*T, BO);
467 case BO_And:
468 return Discard(this->emitBitAnd(*T, BO));
469 case BO_Or:
470 return Discard(this->emitBitOr(*T, BO));
471 case BO_Shl:
472 return Discard(this->emitShl(*LT, *RT, BO));
473 case BO_Shr:
474 return Discard(this->emitShr(*LT, *RT, BO));
475 case BO_Xor:
476 return Discard(this->emitBitXor(*T, BO));
477 case BO_LOr:
478 case BO_LAnd:
479 llvm_unreachable("Already handled earlier");
480 default:
481 return false;
482 }
483
484 llvm_unreachable("Unhandled binary op");
485 }
486
487 /// Perform addition/subtraction of a pointer and an integer or
488 /// subtraction of two pointers.
489 template <class Emitter>
VisitPointerArithBinOp(const BinaryOperator * E)490 bool ByteCodeExprGen<Emitter>::VisitPointerArithBinOp(const BinaryOperator *E) {
491 BinaryOperatorKind Op = E->getOpcode();
492 const Expr *LHS = E->getLHS();
493 const Expr *RHS = E->getRHS();
494
495 if ((Op != BO_Add && Op != BO_Sub) ||
496 (!LHS->getType()->isPointerType() && !RHS->getType()->isPointerType()))
497 return false;
498
499 std::optional<PrimType> LT = classify(LHS);
500 std::optional<PrimType> RT = classify(RHS);
501
502 if (!LT || !RT)
503 return false;
504
505 if (LHS->getType()->isPointerType() && RHS->getType()->isPointerType()) {
506 if (Op != BO_Sub)
507 return false;
508
509 assert(E->getType()->isIntegerType());
510 if (!visit(RHS) || !visit(LHS))
511 return false;
512
513 return this->emitSubPtr(classifyPrim(E->getType()), E);
514 }
515
516 PrimType OffsetType;
517 if (LHS->getType()->isIntegerType()) {
518 if (!visit(RHS) || !visit(LHS))
519 return false;
520 OffsetType = *LT;
521 } else if (RHS->getType()->isIntegerType()) {
522 if (!visit(LHS) || !visit(RHS))
523 return false;
524 OffsetType = *RT;
525 } else {
526 return false;
527 }
528
529 if (Op == BO_Add)
530 return this->emitAddOffset(OffsetType, E);
531 else if (Op == BO_Sub)
532 return this->emitSubOffset(OffsetType, E);
533
534 return false;
535 }
536
537 template <class Emitter>
VisitLogicalBinOp(const BinaryOperator * E)538 bool ByteCodeExprGen<Emitter>::VisitLogicalBinOp(const BinaryOperator *E) {
539 assert(E->isLogicalOp());
540 BinaryOperatorKind Op = E->getOpcode();
541 const Expr *LHS = E->getLHS();
542 const Expr *RHS = E->getRHS();
543 std::optional<PrimType> T = classify(E->getType());
544
545 if (Op == BO_LOr) {
546 // Logical OR. Visit LHS and only evaluate RHS if LHS was FALSE.
547 LabelTy LabelTrue = this->getLabel();
548 LabelTy LabelEnd = this->getLabel();
549
550 if (!this->visitBool(LHS))
551 return false;
552 if (!this->jumpTrue(LabelTrue))
553 return false;
554
555 if (!this->visitBool(RHS))
556 return false;
557 if (!this->jump(LabelEnd))
558 return false;
559
560 this->emitLabel(LabelTrue);
561 this->emitConstBool(true, E);
562 this->fallthrough(LabelEnd);
563 this->emitLabel(LabelEnd);
564
565 } else {
566 assert(Op == BO_LAnd);
567 // Logical AND.
568 // Visit LHS. Only visit RHS if LHS was TRUE.
569 LabelTy LabelFalse = this->getLabel();
570 LabelTy LabelEnd = this->getLabel();
571
572 if (!this->visitBool(LHS))
573 return false;
574 if (!this->jumpFalse(LabelFalse))
575 return false;
576
577 if (!this->visitBool(RHS))
578 return false;
579 if (!this->jump(LabelEnd))
580 return false;
581
582 this->emitLabel(LabelFalse);
583 this->emitConstBool(false, E);
584 this->fallthrough(LabelEnd);
585 this->emitLabel(LabelEnd);
586 }
587
588 if (DiscardResult)
589 return this->emitPopBool(E);
590
591 // For C, cast back to integer type.
592 assert(T);
593 if (T != PT_Bool)
594 return this->emitCast(PT_Bool, *T, E);
595 return true;
596 }
597
598 template <class Emitter>
VisitComplexBinOp(const BinaryOperator * E)599 bool ByteCodeExprGen<Emitter>::VisitComplexBinOp(const BinaryOperator *E) {
600 assert(Initializing);
601
602 const Expr *LHS = E->getLHS();
603 const Expr *RHS = E->getRHS();
604 PrimType LHSElemT = *this->classifyComplexElementType(LHS->getType());
605 PrimType RHSElemT = *this->classifyComplexElementType(RHS->getType());
606
607 unsigned LHSOffset = this->allocateLocalPrimitive(LHS, PT_Ptr, true, false);
608 unsigned RHSOffset = this->allocateLocalPrimitive(RHS, PT_Ptr, true, false);
609 unsigned ResultOffset = ~0u;
610 if (!this->DiscardResult)
611 ResultOffset = this->allocateLocalPrimitive(E, PT_Ptr, true, false);
612
613 assert(LHSElemT == RHSElemT);
614
615 // Save result pointer in ResultOffset
616 if (!this->DiscardResult) {
617 if (!this->emitDupPtr(E))
618 return false;
619 if (!this->emitSetLocal(PT_Ptr, ResultOffset, E))
620 return false;
621 }
622
623 // Evaluate LHS and save value to LHSOffset.
624 if (!this->visit(LHS))
625 return false;
626 if (!this->emitSetLocal(PT_Ptr, LHSOffset, E))
627 return false;
628
629 // Same with RHS.
630 if (!this->visit(RHS))
631 return false;
632 if (!this->emitSetLocal(PT_Ptr, RHSOffset, E))
633 return false;
634
635 // Now we can get pointers to the LHS and RHS from the offsets above.
636 BinaryOperatorKind Op = E->getOpcode();
637 for (unsigned ElemIndex = 0; ElemIndex != 2; ++ElemIndex) {
638 // Result pointer for the store later.
639 if (!this->DiscardResult) {
640 if (!this->emitGetLocal(PT_Ptr, ResultOffset, E))
641 return false;
642 }
643
644 if (!this->emitGetLocal(PT_Ptr, LHSOffset, E))
645 return false;
646 if (!this->emitConstUint8(ElemIndex, E))
647 return false;
648 if (!this->emitArrayElemPtrPopUint8(E))
649 return false;
650 if (!this->emitLoadPop(LHSElemT, E))
651 return false;
652
653 if (!this->emitGetLocal(PT_Ptr, RHSOffset, E))
654 return false;
655 if (!this->emitConstUint8(ElemIndex, E))
656 return false;
657 if (!this->emitArrayElemPtrPopUint8(E))
658 return false;
659 if (!this->emitLoadPop(RHSElemT, E))
660 return false;
661
662 // The actual operation.
663 switch (Op) {
664 case BO_Add:
665 if (LHSElemT == PT_Float) {
666 if (!this->emitAddf(getRoundingMode(E), E))
667 return false;
668 } else {
669 if (!this->emitAdd(LHSElemT, E))
670 return false;
671 }
672 break;
673 case BO_Sub:
674 if (LHSElemT == PT_Float) {
675 if (!this->emitSubf(getRoundingMode(E), E))
676 return false;
677 } else {
678 if (!this->emitSub(LHSElemT, E))
679 return false;
680 }
681 break;
682
683 default:
684 return false;
685 }
686
687 if (!this->DiscardResult) {
688 // Initialize array element with the value we just computed.
689 if (!this->emitInitElemPop(LHSElemT, ElemIndex, E))
690 return false;
691 } else {
692 if (!this->emitPop(LHSElemT, E))
693 return false;
694 }
695 }
696 return true;
697 }
698
699 template <class Emitter>
VisitImplicitValueInitExpr(const ImplicitValueInitExpr * E)700 bool ByteCodeExprGen<Emitter>::VisitImplicitValueInitExpr(const ImplicitValueInitExpr *E) {
701 QualType QT = E->getType();
702
703 if (std::optional<PrimType> T = classify(QT))
704 return this->visitZeroInitializer(*T, QT, E);
705
706 if (QT->isRecordType())
707 return false;
708
709 if (QT->isIncompleteArrayType())
710 return true;
711
712 if (QT->isArrayType()) {
713 const ArrayType *AT = QT->getAsArrayTypeUnsafe();
714 assert(AT);
715 const auto *CAT = cast<ConstantArrayType>(AT);
716 size_t NumElems = CAT->getSize().getZExtValue();
717 PrimType ElemT = classifyPrim(CAT->getElementType());
718
719 for (size_t I = 0; I != NumElems; ++I) {
720 if (!this->visitZeroInitializer(ElemT, CAT->getElementType(), E))
721 return false;
722 if (!this->emitInitElem(ElemT, I, E))
723 return false;
724 }
725
726 return true;
727 }
728
729 return false;
730 }
731
732 template <class Emitter>
VisitArraySubscriptExpr(const ArraySubscriptExpr * E)733 bool ByteCodeExprGen<Emitter>::VisitArraySubscriptExpr(
734 const ArraySubscriptExpr *E) {
735 const Expr *Base = E->getBase();
736 const Expr *Index = E->getIdx();
737
738 if (DiscardResult)
739 return this->discard(Base) && this->discard(Index);
740
741 // Take pointer of LHS, add offset from RHS.
742 // What's left on the stack after this is a pointer.
743 if (!this->visit(Base))
744 return false;
745
746 if (!this->visit(Index))
747 return false;
748
749 PrimType IndexT = classifyPrim(Index->getType());
750 return this->emitArrayElemPtrPop(IndexT, E);
751 }
752
753 template <class Emitter>
visitInitList(ArrayRef<const Expr * > Inits,const Expr * E)754 bool ByteCodeExprGen<Emitter>::visitInitList(ArrayRef<const Expr *> Inits,
755 const Expr *E) {
756 assert(E->getType()->isRecordType());
757 const Record *R = getRecord(E->getType());
758
759 unsigned InitIndex = 0;
760 for (const Expr *Init : Inits) {
761 if (!this->emitDupPtr(E))
762 return false;
763
764 if (std::optional<PrimType> T = classify(Init)) {
765 const Record::Field *FieldToInit = R->getField(InitIndex);
766 if (!this->visit(Init))
767 return false;
768
769 if (FieldToInit->isBitField()) {
770 if (!this->emitInitBitField(*T, FieldToInit, E))
771 return false;
772 } else {
773 if (!this->emitInitField(*T, FieldToInit->Offset, E))
774 return false;
775 }
776
777 if (!this->emitPopPtr(E))
778 return false;
779 ++InitIndex;
780 } else {
781 // Initializer for a direct base class.
782 if (const Record::Base *B = R->getBase(Init->getType())) {
783 if (!this->emitGetPtrBasePop(B->Offset, Init))
784 return false;
785
786 if (!this->visitInitializer(Init))
787 return false;
788
789 if (!this->emitInitPtrPop(E))
790 return false;
791 // Base initializers don't increase InitIndex, since they don't count
792 // into the Record's fields.
793 } else {
794 const Record::Field *FieldToInit = R->getField(InitIndex);
795 // Non-primitive case. Get a pointer to the field-to-initialize
796 // on the stack and recurse into visitInitializer().
797 if (!this->emitGetPtrField(FieldToInit->Offset, Init))
798 return false;
799
800 if (!this->visitInitializer(Init))
801 return false;
802
803 if (!this->emitPopPtr(E))
804 return false;
805 ++InitIndex;
806 }
807 }
808 }
809 return true;
810 }
811
812 /// Pointer to the array(not the element!) must be on the stack when calling
813 /// this.
814 template <class Emitter>
visitArrayElemInit(unsigned ElemIndex,const Expr * Init)815 bool ByteCodeExprGen<Emitter>::visitArrayElemInit(unsigned ElemIndex,
816 const Expr *Init) {
817 if (std::optional<PrimType> T = classify(Init->getType())) {
818 // Visit the primitive element like normal.
819 if (!this->visit(Init))
820 return false;
821 return this->emitInitElem(*T, ElemIndex, Init);
822 }
823
824 // Advance the pointer currently on the stack to the given
825 // dimension.
826 if (!this->emitConstUint32(ElemIndex, Init))
827 return false;
828 if (!this->emitArrayElemPtrUint32(Init))
829 return false;
830 if (!this->visitInitializer(Init))
831 return false;
832 return this->emitPopPtr(Init);
833 }
834
835 template <class Emitter>
VisitInitListExpr(const InitListExpr * E)836 bool ByteCodeExprGen<Emitter>::VisitInitListExpr(const InitListExpr *E) {
837 // Handle discarding first.
838 if (DiscardResult) {
839 for (const Expr *Init : E->inits()) {
840 if (!this->discard(Init))
841 return false;
842 }
843 return true;
844 }
845
846 // Primitive values.
847 if (std::optional<PrimType> T = classify(E->getType())) {
848 assert(!DiscardResult);
849 if (E->getNumInits() == 0)
850 return this->visitZeroInitializer(*T, E->getType(), E);
851 assert(E->getNumInits() == 1);
852 return this->delegate(E->inits()[0]);
853 }
854
855 QualType T = E->getType();
856 if (T->isRecordType())
857 return this->visitInitList(E->inits(), E);
858
859 if (T->isArrayType()) {
860 // FIXME: Array fillers.
861 unsigned ElementIndex = 0;
862 for (const Expr *Init : E->inits()) {
863 if (!this->visitArrayElemInit(ElementIndex, Init))
864 return false;
865 ++ElementIndex;
866 }
867 return true;
868 }
869
870 if (T->isAnyComplexType()) {
871 unsigned NumInits = E->getNumInits();
872
873 if (NumInits == 1)
874 return this->delegate(E->inits()[0]);
875
876 QualType ElemQT = E->getType()->getAs<ComplexType>()->getElementType();
877 PrimType ElemT = classifyPrim(ElemQT);
878 if (NumInits == 0) {
879 // Zero-initialize both elements.
880 for (unsigned I = 0; I < 2; ++I) {
881 if (!this->visitZeroInitializer(ElemT, ElemQT, E))
882 return false;
883 if (!this->emitInitElem(ElemT, I, E))
884 return false;
885 }
886 } else if (NumInits == 2) {
887 unsigned InitIndex = 0;
888 for (const Expr *Init : E->inits()) {
889 if (!this->visit(Init))
890 return false;
891
892 if (!this->emitInitElem(ElemT, InitIndex, E))
893 return false;
894 ++InitIndex;
895 }
896 }
897 return true;
898 }
899
900 return false;
901 }
902
903 template <class Emitter>
VisitCXXParenListInitExpr(const CXXParenListInitExpr * E)904 bool ByteCodeExprGen<Emitter>::VisitCXXParenListInitExpr(
905 const CXXParenListInitExpr *E) {
906 if (DiscardResult) {
907 for (const Expr *Init : E->getInitExprs()) {
908 if (!this->discard(Init))
909 return false;
910 }
911 return true;
912 }
913
914 assert(E->getType()->isRecordType());
915 return this->visitInitList(E->getInitExprs(), E);
916 }
917
918 template <class Emitter>
VisitSubstNonTypeTemplateParmExpr(const SubstNonTypeTemplateParmExpr * E)919 bool ByteCodeExprGen<Emitter>::VisitSubstNonTypeTemplateParmExpr(
920 const SubstNonTypeTemplateParmExpr *E) {
921 return this->delegate(E->getReplacement());
922 }
923
924 template <class Emitter>
VisitConstantExpr(const ConstantExpr * E)925 bool ByteCodeExprGen<Emitter>::VisitConstantExpr(const ConstantExpr *E) {
926 // Try to emit the APValue directly, without visiting the subexpr.
927 // This will only fail if we can't emit the APValue, so won't emit any
928 // diagnostics or any double values.
929 std::optional<PrimType> T = classify(E->getType());
930 if (T && E->hasAPValueResult() &&
931 this->visitAPValue(E->getAPValueResult(), *T, E))
932 return true;
933
934 return this->delegate(E->getSubExpr());
935 }
936
AlignOfType(QualType T,const ASTContext & ASTCtx,UnaryExprOrTypeTrait Kind)937 static CharUnits AlignOfType(QualType T, const ASTContext &ASTCtx,
938 UnaryExprOrTypeTrait Kind) {
939 bool AlignOfReturnsPreferred =
940 ASTCtx.getLangOpts().getClangABICompat() <= LangOptions::ClangABI::Ver7;
941
942 // C++ [expr.alignof]p3:
943 // When alignof is applied to a reference type, the result is the
944 // alignment of the referenced type.
945 if (const auto *Ref = T->getAs<ReferenceType>())
946 T = Ref->getPointeeType();
947
948 // __alignof is defined to return the preferred alignment.
949 // Before 8, clang returned the preferred alignment for alignof and
950 // _Alignof as well.
951 if (Kind == UETT_PreferredAlignOf || AlignOfReturnsPreferred)
952 return ASTCtx.toCharUnitsFromBits(ASTCtx.getPreferredTypeAlign(T));
953
954 return ASTCtx.getTypeAlignInChars(T);
955 }
956
957 template <class Emitter>
VisitUnaryExprOrTypeTraitExpr(const UnaryExprOrTypeTraitExpr * E)958 bool ByteCodeExprGen<Emitter>::VisitUnaryExprOrTypeTraitExpr(
959 const UnaryExprOrTypeTraitExpr *E) {
960 UnaryExprOrTypeTrait Kind = E->getKind();
961 ASTContext &ASTCtx = Ctx.getASTContext();
962
963 if (Kind == UETT_SizeOf) {
964 QualType ArgType = E->getTypeOfArgument();
965 CharUnits Size;
966 if (ArgType->isVoidType() || ArgType->isFunctionType())
967 Size = CharUnits::One();
968 else {
969 if (ArgType->isDependentType() || !ArgType->isConstantSizeType())
970 return false;
971
972 Size = ASTCtx.getTypeSizeInChars(ArgType);
973 }
974
975 if (DiscardResult)
976 return true;
977
978 return this->emitConst(Size.getQuantity(), E);
979 }
980
981 if (Kind == UETT_AlignOf || Kind == UETT_PreferredAlignOf) {
982 CharUnits Size;
983
984 if (E->isArgumentType()) {
985 QualType ArgType = E->getTypeOfArgument();
986
987 Size = AlignOfType(ArgType, ASTCtx, Kind);
988 } else {
989 // Argument is an expression, not a type.
990 const Expr *Arg = E->getArgumentExpr()->IgnoreParens();
991
992 // The kinds of expressions that we have special-case logic here for
993 // should be kept up to date with the special checks for those
994 // expressions in Sema.
995
996 // alignof decl is always accepted, even if it doesn't make sense: we
997 // default to 1 in those cases.
998 if (const auto *DRE = dyn_cast<DeclRefExpr>(Arg))
999 Size = ASTCtx.getDeclAlign(DRE->getDecl(),
1000 /*RefAsPointee*/ true);
1001 else if (const auto *ME = dyn_cast<MemberExpr>(Arg))
1002 Size = ASTCtx.getDeclAlign(ME->getMemberDecl(),
1003 /*RefAsPointee*/ true);
1004 else
1005 Size = AlignOfType(Arg->getType(), ASTCtx, Kind);
1006 }
1007
1008 if (DiscardResult)
1009 return true;
1010
1011 return this->emitConst(Size.getQuantity(), E);
1012 }
1013
1014 return false;
1015 }
1016
1017 template <class Emitter>
VisitMemberExpr(const MemberExpr * E)1018 bool ByteCodeExprGen<Emitter>::VisitMemberExpr(const MemberExpr *E) {
1019 // 'Base.Member'
1020 const Expr *Base = E->getBase();
1021
1022 if (DiscardResult)
1023 return this->discard(Base);
1024
1025 if (!this->visit(Base))
1026 return false;
1027
1028 // Base above gives us a pointer on the stack.
1029 // TODO: Implement non-FieldDecl members.
1030 const ValueDecl *Member = E->getMemberDecl();
1031 if (const auto *FD = dyn_cast<FieldDecl>(Member)) {
1032 const RecordDecl *RD = FD->getParent();
1033 const Record *R = getRecord(RD);
1034 const Record::Field *F = R->getField(FD);
1035 // Leave a pointer to the field on the stack.
1036 if (F->Decl->getType()->isReferenceType())
1037 return this->emitGetFieldPop(PT_Ptr, F->Offset, E);
1038 return this->emitGetPtrField(F->Offset, E);
1039 }
1040
1041 return false;
1042 }
1043
1044 template <class Emitter>
VisitArrayInitIndexExpr(const ArrayInitIndexExpr * E)1045 bool ByteCodeExprGen<Emitter>::VisitArrayInitIndexExpr(
1046 const ArrayInitIndexExpr *E) {
1047 // ArrayIndex might not be set if a ArrayInitIndexExpr is being evaluated
1048 // stand-alone, e.g. via EvaluateAsInt().
1049 if (!ArrayIndex)
1050 return false;
1051 return this->emitConst(*ArrayIndex, E);
1052 }
1053
1054 template <class Emitter>
VisitArrayInitLoopExpr(const ArrayInitLoopExpr * E)1055 bool ByteCodeExprGen<Emitter>::VisitArrayInitLoopExpr(
1056 const ArrayInitLoopExpr *E) {
1057 assert(Initializing);
1058 assert(!DiscardResult);
1059 // TODO: This compiles to quite a lot of bytecode if the array is larger.
1060 // Investigate compiling this to a loop.
1061
1062 const Expr *SubExpr = E->getSubExpr();
1063 const Expr *CommonExpr = E->getCommonExpr();
1064 size_t Size = E->getArraySize().getZExtValue();
1065
1066 // If the common expression is an opaque expression, we visit it
1067 // here once so we have its value cached.
1068 // FIXME: This might be necessary (or useful) for all expressions.
1069 if (isa<OpaqueValueExpr>(CommonExpr)) {
1070 if (!this->discard(CommonExpr))
1071 return false;
1072 }
1073
1074 // So, every iteration, we execute an assignment here
1075 // where the LHS is on the stack (the target array)
1076 // and the RHS is our SubExpr.
1077 for (size_t I = 0; I != Size; ++I) {
1078 ArrayIndexScope<Emitter> IndexScope(this, I);
1079 BlockScope<Emitter> BS(this);
1080
1081 if (!this->visitArrayElemInit(I, SubExpr))
1082 return false;
1083 }
1084 return true;
1085 }
1086
1087 template <class Emitter>
VisitOpaqueValueExpr(const OpaqueValueExpr * E)1088 bool ByteCodeExprGen<Emitter>::VisitOpaqueValueExpr(const OpaqueValueExpr *E) {
1089 if (Initializing)
1090 return this->visitInitializer(E->getSourceExpr());
1091
1092 PrimType SubExprT = classify(E->getSourceExpr()).value_or(PT_Ptr);
1093 if (auto It = OpaqueExprs.find(E); It != OpaqueExprs.end())
1094 return this->emitGetLocal(SubExprT, It->second, E);
1095
1096 if (!this->visit(E->getSourceExpr()))
1097 return false;
1098
1099 // At this point we either have the evaluated source expression or a pointer
1100 // to an object on the stack. We want to create a local variable that stores
1101 // this value.
1102 std::optional<unsigned> LocalIndex =
1103 allocateLocalPrimitive(E, SubExprT, /*IsConst=*/true);
1104 if (!LocalIndex)
1105 return false;
1106 if (!this->emitSetLocal(SubExprT, *LocalIndex, E))
1107 return false;
1108
1109 // Here the local variable is created but the value is removed from the stack,
1110 // so we put it back, because the caller might need it.
1111 if (!DiscardResult) {
1112 if (!this->emitGetLocal(SubExprT, *LocalIndex, E))
1113 return false;
1114 }
1115
1116 // FIXME: Ideally the cached value should be cleaned up later.
1117 OpaqueExprs.insert({E, *LocalIndex});
1118
1119 return true;
1120 }
1121
1122 template <class Emitter>
VisitAbstractConditionalOperator(const AbstractConditionalOperator * E)1123 bool ByteCodeExprGen<Emitter>::VisitAbstractConditionalOperator(
1124 const AbstractConditionalOperator *E) {
1125 const Expr *Condition = E->getCond();
1126 const Expr *TrueExpr = E->getTrueExpr();
1127 const Expr *FalseExpr = E->getFalseExpr();
1128
1129 LabelTy LabelEnd = this->getLabel(); // Label after the operator.
1130 LabelTy LabelFalse = this->getLabel(); // Label for the false expr.
1131
1132 if (!this->visitBool(Condition))
1133 return false;
1134
1135 if (!this->jumpFalse(LabelFalse))
1136 return false;
1137
1138 if (!this->delegate(TrueExpr))
1139 return false;
1140 if (!this->jump(LabelEnd))
1141 return false;
1142
1143 this->emitLabel(LabelFalse);
1144
1145 if (!this->delegate(FalseExpr))
1146 return false;
1147
1148 this->fallthrough(LabelEnd);
1149 this->emitLabel(LabelEnd);
1150
1151 return true;
1152 }
1153
1154 template <class Emitter>
VisitStringLiteral(const StringLiteral * E)1155 bool ByteCodeExprGen<Emitter>::VisitStringLiteral(const StringLiteral *E) {
1156 if (DiscardResult)
1157 return true;
1158
1159 if (!Initializing) {
1160 unsigned StringIndex = P.createGlobalString(E);
1161 return this->emitGetPtrGlobal(StringIndex, E);
1162 }
1163
1164 // We are initializing an array on the stack.
1165 const ConstantArrayType *CAT =
1166 Ctx.getASTContext().getAsConstantArrayType(E->getType());
1167 assert(CAT && "a string literal that's not a constant array?");
1168
1169 // If the initializer string is too long, a diagnostic has already been
1170 // emitted. Read only the array length from the string literal.
1171 unsigned ArraySize = CAT->getSize().getZExtValue();
1172 unsigned N = std::min(ArraySize, E->getLength());
1173 size_t CharWidth = E->getCharByteWidth();
1174
1175 for (unsigned I = 0; I != N; ++I) {
1176 uint32_t CodeUnit = E->getCodeUnit(I);
1177
1178 if (CharWidth == 1) {
1179 this->emitConstSint8(CodeUnit, E);
1180 this->emitInitElemSint8(I, E);
1181 } else if (CharWidth == 2) {
1182 this->emitConstUint16(CodeUnit, E);
1183 this->emitInitElemUint16(I, E);
1184 } else if (CharWidth == 4) {
1185 this->emitConstUint32(CodeUnit, E);
1186 this->emitInitElemUint32(I, E);
1187 } else {
1188 llvm_unreachable("unsupported character width");
1189 }
1190 }
1191
1192 // Fill up the rest of the char array with NUL bytes.
1193 for (unsigned I = N; I != ArraySize; ++I) {
1194 if (CharWidth == 1) {
1195 this->emitConstSint8(0, E);
1196 this->emitInitElemSint8(I, E);
1197 } else if (CharWidth == 2) {
1198 this->emitConstUint16(0, E);
1199 this->emitInitElemUint16(I, E);
1200 } else if (CharWidth == 4) {
1201 this->emitConstUint32(0, E);
1202 this->emitInitElemUint32(I, E);
1203 } else {
1204 llvm_unreachable("unsupported character width");
1205 }
1206 }
1207
1208 return true;
1209 }
1210
1211 template <class Emitter>
VisitCharacterLiteral(const CharacterLiteral * E)1212 bool ByteCodeExprGen<Emitter>::VisitCharacterLiteral(
1213 const CharacterLiteral *E) {
1214 if (DiscardResult)
1215 return true;
1216 return this->emitConst(E->getValue(), E);
1217 }
1218
1219 template <class Emitter>
VisitFloatCompoundAssignOperator(const CompoundAssignOperator * E)1220 bool ByteCodeExprGen<Emitter>::VisitFloatCompoundAssignOperator(
1221 const CompoundAssignOperator *E) {
1222
1223 const Expr *LHS = E->getLHS();
1224 const Expr *RHS = E->getRHS();
1225 QualType LHSType = LHS->getType();
1226 QualType LHSComputationType = E->getComputationLHSType();
1227 QualType ResultType = E->getComputationResultType();
1228 std::optional<PrimType> LT = classify(LHSComputationType);
1229 std::optional<PrimType> RT = classify(ResultType);
1230
1231 assert(ResultType->isFloatingType());
1232
1233 if (!LT || !RT)
1234 return false;
1235
1236 PrimType LHST = classifyPrim(LHSType);
1237
1238 // C++17 onwards require that we evaluate the RHS first.
1239 // Compute RHS and save it in a temporary variable so we can
1240 // load it again later.
1241 if (!visit(RHS))
1242 return false;
1243
1244 unsigned TempOffset = this->allocateLocalPrimitive(E, *RT, /*IsConst=*/true);
1245 if (!this->emitSetLocal(*RT, TempOffset, E))
1246 return false;
1247
1248 // First, visit LHS.
1249 if (!visit(LHS))
1250 return false;
1251 if (!this->emitLoad(LHST, E))
1252 return false;
1253
1254 // If necessary, convert LHS to its computation type.
1255 if (!this->emitPrimCast(LHST, classifyPrim(LHSComputationType),
1256 LHSComputationType, E))
1257 return false;
1258
1259 // Now load RHS.
1260 if (!this->emitGetLocal(*RT, TempOffset, E))
1261 return false;
1262
1263 llvm::RoundingMode RM = getRoundingMode(E);
1264 switch (E->getOpcode()) {
1265 case BO_AddAssign:
1266 if (!this->emitAddf(RM, E))
1267 return false;
1268 break;
1269 case BO_SubAssign:
1270 if (!this->emitSubf(RM, E))
1271 return false;
1272 break;
1273 case BO_MulAssign:
1274 if (!this->emitMulf(RM, E))
1275 return false;
1276 break;
1277 case BO_DivAssign:
1278 if (!this->emitDivf(RM, E))
1279 return false;
1280 break;
1281 default:
1282 return false;
1283 }
1284
1285 if (!this->emitPrimCast(classifyPrim(ResultType), LHST, LHS->getType(), E))
1286 return false;
1287
1288 if (DiscardResult)
1289 return this->emitStorePop(LHST, E);
1290 return this->emitStore(LHST, E);
1291 }
1292
1293 template <class Emitter>
VisitPointerCompoundAssignOperator(const CompoundAssignOperator * E)1294 bool ByteCodeExprGen<Emitter>::VisitPointerCompoundAssignOperator(
1295 const CompoundAssignOperator *E) {
1296 BinaryOperatorKind Op = E->getOpcode();
1297 const Expr *LHS = E->getLHS();
1298 const Expr *RHS = E->getRHS();
1299 std::optional<PrimType> LT = classify(LHS->getType());
1300 std::optional<PrimType> RT = classify(RHS->getType());
1301
1302 if (Op != BO_AddAssign && Op != BO_SubAssign)
1303 return false;
1304
1305 if (!LT || !RT)
1306 return false;
1307 assert(*LT == PT_Ptr);
1308
1309 if (!visit(LHS))
1310 return false;
1311
1312 if (!this->emitLoadPtr(LHS))
1313 return false;
1314
1315 if (!visit(RHS))
1316 return false;
1317
1318 if (Op == BO_AddAssign)
1319 this->emitAddOffset(*RT, E);
1320 else
1321 this->emitSubOffset(*RT, E);
1322
1323 if (DiscardResult)
1324 return this->emitStorePopPtr(E);
1325 return this->emitStorePtr(E);
1326 }
1327
1328 template <class Emitter>
VisitCompoundAssignOperator(const CompoundAssignOperator * E)1329 bool ByteCodeExprGen<Emitter>::VisitCompoundAssignOperator(
1330 const CompoundAssignOperator *E) {
1331
1332 const Expr *LHS = E->getLHS();
1333 const Expr *RHS = E->getRHS();
1334 std::optional<PrimType> LHSComputationT =
1335 classify(E->getComputationLHSType());
1336 std::optional<PrimType> LT = classify(LHS->getType());
1337 std::optional<PrimType> RT = classify(E->getComputationResultType());
1338 std::optional<PrimType> ResultT = classify(E->getType());
1339
1340 if (!LT || !RT || !ResultT || !LHSComputationT)
1341 return false;
1342
1343 // Handle floating point operations separately here, since they
1344 // require special care.
1345
1346 if (ResultT == PT_Float || RT == PT_Float)
1347 return VisitFloatCompoundAssignOperator(E);
1348
1349 if (E->getType()->isPointerType())
1350 return VisitPointerCompoundAssignOperator(E);
1351
1352 assert(!E->getType()->isPointerType() && "Handled above");
1353 assert(!E->getType()->isFloatingType() && "Handled above");
1354
1355 // C++17 onwards require that we evaluate the RHS first.
1356 // Compute RHS and save it in a temporary variable so we can
1357 // load it again later.
1358 // FIXME: Compound assignments are unsequenced in C, so we might
1359 // have to figure out how to reject them.
1360 if (!visit(RHS))
1361 return false;
1362
1363 unsigned TempOffset = this->allocateLocalPrimitive(E, *RT, /*IsConst=*/true);
1364
1365 if (!this->emitSetLocal(*RT, TempOffset, E))
1366 return false;
1367
1368 // Get LHS pointer, load its value and cast it to the
1369 // computation type if necessary.
1370 if (!visit(LHS))
1371 return false;
1372 if (!this->emitLoad(*LT, E))
1373 return false;
1374 if (*LT != *LHSComputationT) {
1375 if (!this->emitCast(*LT, *LHSComputationT, E))
1376 return false;
1377 }
1378
1379 // Get the RHS value on the stack.
1380 if (!this->emitGetLocal(*RT, TempOffset, E))
1381 return false;
1382
1383 // Perform operation.
1384 switch (E->getOpcode()) {
1385 case BO_AddAssign:
1386 if (!this->emitAdd(*LHSComputationT, E))
1387 return false;
1388 break;
1389 case BO_SubAssign:
1390 if (!this->emitSub(*LHSComputationT, E))
1391 return false;
1392 break;
1393 case BO_MulAssign:
1394 if (!this->emitMul(*LHSComputationT, E))
1395 return false;
1396 break;
1397 case BO_DivAssign:
1398 if (!this->emitDiv(*LHSComputationT, E))
1399 return false;
1400 break;
1401 case BO_RemAssign:
1402 if (!this->emitRem(*LHSComputationT, E))
1403 return false;
1404 break;
1405 case BO_ShlAssign:
1406 if (!this->emitShl(*LHSComputationT, *RT, E))
1407 return false;
1408 break;
1409 case BO_ShrAssign:
1410 if (!this->emitShr(*LHSComputationT, *RT, E))
1411 return false;
1412 break;
1413 case BO_AndAssign:
1414 if (!this->emitBitAnd(*LHSComputationT, E))
1415 return false;
1416 break;
1417 case BO_XorAssign:
1418 if (!this->emitBitXor(*LHSComputationT, E))
1419 return false;
1420 break;
1421 case BO_OrAssign:
1422 if (!this->emitBitOr(*LHSComputationT, E))
1423 return false;
1424 break;
1425 default:
1426 llvm_unreachable("Unimplemented compound assign operator");
1427 }
1428
1429 // And now cast from LHSComputationT to ResultT.
1430 if (*ResultT != *LHSComputationT) {
1431 if (!this->emitCast(*LHSComputationT, *ResultT, E))
1432 return false;
1433 }
1434
1435 // And store the result in LHS.
1436 if (DiscardResult) {
1437 if (LHS->refersToBitField())
1438 return this->emitStoreBitFieldPop(*ResultT, E);
1439 return this->emitStorePop(*ResultT, E);
1440 }
1441 if (LHS->refersToBitField())
1442 return this->emitStoreBitField(*ResultT, E);
1443 return this->emitStore(*ResultT, E);
1444 }
1445
1446 template <class Emitter>
VisitExprWithCleanups(const ExprWithCleanups * E)1447 bool ByteCodeExprGen<Emitter>::VisitExprWithCleanups(
1448 const ExprWithCleanups *E) {
1449 const Expr *SubExpr = E->getSubExpr();
1450
1451 assert(E->getNumObjects() == 0 && "TODO: Implement cleanups");
1452
1453 return this->delegate(SubExpr);
1454 }
1455
1456 template <class Emitter>
VisitMaterializeTemporaryExpr(const MaterializeTemporaryExpr * E)1457 bool ByteCodeExprGen<Emitter>::VisitMaterializeTemporaryExpr(
1458 const MaterializeTemporaryExpr *E) {
1459 const Expr *SubExpr = E->getSubExpr();
1460
1461 if (Initializing) {
1462 // We already have a value, just initialize that.
1463 return this->visitInitializer(SubExpr);
1464 }
1465 // If we don't end up using the materialized temporary anyway, don't
1466 // bother creating it.
1467 if (DiscardResult)
1468 return this->discard(SubExpr);
1469
1470 // When we're initializing a global variable *or* the storage duration of
1471 // the temporary is explicitly static, create a global variable.
1472 std::optional<PrimType> SubExprT = classify(SubExpr);
1473 bool IsStatic = E->getStorageDuration() == SD_Static;
1474 if (GlobalDecl || IsStatic) {
1475 std::optional<unsigned> GlobalIndex = P.createGlobal(E);
1476 if (!GlobalIndex)
1477 return false;
1478
1479 const LifetimeExtendedTemporaryDecl *TempDecl =
1480 E->getLifetimeExtendedTemporaryDecl();
1481 if (IsStatic)
1482 assert(TempDecl);
1483
1484 if (SubExprT) {
1485 if (!this->visit(SubExpr))
1486 return false;
1487 if (IsStatic) {
1488 if (!this->emitInitGlobalTemp(*SubExprT, *GlobalIndex, TempDecl, E))
1489 return false;
1490 } else {
1491 if (!this->emitInitGlobal(*SubExprT, *GlobalIndex, E))
1492 return false;
1493 }
1494 return this->emitGetPtrGlobal(*GlobalIndex, E);
1495 }
1496
1497 // Non-primitive values.
1498 if (!this->emitGetPtrGlobal(*GlobalIndex, E))
1499 return false;
1500 if (!this->visitInitializer(SubExpr))
1501 return false;
1502 if (IsStatic)
1503 return this->emitInitGlobalTempComp(TempDecl, E);
1504 return true;
1505 }
1506
1507 // For everyhing else, use local variables.
1508 if (SubExprT) {
1509 if (std::optional<unsigned> LocalIndex = allocateLocalPrimitive(
1510 SubExpr, *SubExprT, /*IsConst=*/true, /*IsExtended=*/true)) {
1511 if (!this->visit(SubExpr))
1512 return false;
1513 this->emitSetLocal(*SubExprT, *LocalIndex, E);
1514 return this->emitGetPtrLocal(*LocalIndex, E);
1515 }
1516 } else {
1517 if (std::optional<unsigned> LocalIndex =
1518 allocateLocal(SubExpr, /*IsExtended=*/true)) {
1519 if (!this->emitGetPtrLocal(*LocalIndex, E))
1520 return false;
1521 return this->visitInitializer(SubExpr);
1522 }
1523 }
1524 return false;
1525 }
1526
1527 template <class Emitter>
VisitCXXBindTemporaryExpr(const CXXBindTemporaryExpr * E)1528 bool ByteCodeExprGen<Emitter>::VisitCXXBindTemporaryExpr(
1529 const CXXBindTemporaryExpr *E) {
1530 return this->delegate(E->getSubExpr());
1531 }
1532
1533 template <class Emitter>
VisitCompoundLiteralExpr(const CompoundLiteralExpr * E)1534 bool ByteCodeExprGen<Emitter>::VisitCompoundLiteralExpr(
1535 const CompoundLiteralExpr *E) {
1536 const Expr *Init = E->getInitializer();
1537 if (Initializing) {
1538 // We already have a value, just initialize that.
1539 return this->visitInitializer(Init);
1540 }
1541
1542 std::optional<PrimType> T = classify(E->getType());
1543 if (E->isFileScope()) {
1544 if (std::optional<unsigned> GlobalIndex = P.createGlobal(E)) {
1545 if (classify(E->getType()))
1546 return this->visit(Init);
1547 if (!this->emitGetPtrGlobal(*GlobalIndex, E))
1548 return false;
1549 return this->visitInitializer(Init);
1550 }
1551 }
1552
1553 // Otherwise, use a local variable.
1554 if (T) {
1555 // For primitive types, we just visit the initializer.
1556 return this->delegate(Init);
1557 } else {
1558 if (std::optional<unsigned> LocalIndex = allocateLocal(Init)) {
1559 if (!this->emitGetPtrLocal(*LocalIndex, E))
1560 return false;
1561 if (!this->visitInitializer(Init))
1562 return false;
1563 if (DiscardResult)
1564 return this->emitPopPtr(E);
1565 return true;
1566 }
1567 }
1568
1569 return false;
1570 }
1571
1572 template <class Emitter>
VisitTypeTraitExpr(const TypeTraitExpr * E)1573 bool ByteCodeExprGen<Emitter>::VisitTypeTraitExpr(const TypeTraitExpr *E) {
1574 if (DiscardResult)
1575 return true;
1576 return this->emitConstBool(E->getValue(), E);
1577 }
1578
1579 template <class Emitter>
VisitLambdaExpr(const LambdaExpr * E)1580 bool ByteCodeExprGen<Emitter>::VisitLambdaExpr(const LambdaExpr *E) {
1581 assert(Initializing);
1582 const Record *R = P.getOrCreateRecord(E->getLambdaClass());
1583
1584 auto *CaptureInitIt = E->capture_init_begin();
1585 // Initialize all fields (which represent lambda captures) of the
1586 // record with their initializers.
1587 for (const Record::Field &F : R->fields()) {
1588 const Expr *Init = *CaptureInitIt;
1589 ++CaptureInitIt;
1590
1591 if (std::optional<PrimType> T = classify(Init)) {
1592 if (!this->visit(Init))
1593 return false;
1594
1595 if (!this->emitSetField(*T, F.Offset, E))
1596 return false;
1597 } else {
1598 if (!this->emitDupPtr(E))
1599 return false;
1600
1601 if (!this->emitGetPtrField(F.Offset, E))
1602 return false;
1603
1604 if (!this->visitInitializer(Init))
1605 return false;
1606
1607 if (!this->emitPopPtr(E))
1608 return false;
1609 }
1610 }
1611
1612 return true;
1613 }
1614
1615 template <class Emitter>
VisitPredefinedExpr(const PredefinedExpr * E)1616 bool ByteCodeExprGen<Emitter>::VisitPredefinedExpr(const PredefinedExpr *E) {
1617 if (DiscardResult)
1618 return true;
1619
1620 assert(!Initializing);
1621 return this->visit(E->getFunctionName());
1622 }
1623
1624 template <class Emitter>
VisitCXXThrowExpr(const CXXThrowExpr * E)1625 bool ByteCodeExprGen<Emitter>::VisitCXXThrowExpr(const CXXThrowExpr *E) {
1626 if (E->getSubExpr() && !this->discard(E->getSubExpr()))
1627 return false;
1628
1629 return this->emitInvalid(E);
1630 }
1631
1632 template <class Emitter>
VisitCXXReinterpretCastExpr(const CXXReinterpretCastExpr * E)1633 bool ByteCodeExprGen<Emitter>::VisitCXXReinterpretCastExpr(
1634 const CXXReinterpretCastExpr *E) {
1635 if (!this->discard(E->getSubExpr()))
1636 return false;
1637
1638 return this->emitInvalidCast(CastKind::Reinterpret, E);
1639 }
1640
1641 template <class Emitter>
VisitCXXNoexceptExpr(const CXXNoexceptExpr * E)1642 bool ByteCodeExprGen<Emitter>::VisitCXXNoexceptExpr(const CXXNoexceptExpr *E) {
1643 assert(E->getType()->isBooleanType());
1644
1645 if (DiscardResult)
1646 return true;
1647 return this->emitConstBool(E->getValue(), E);
1648 }
1649
1650 template <class Emitter>
VisitCXXConstructExpr(const CXXConstructExpr * E)1651 bool ByteCodeExprGen<Emitter>::VisitCXXConstructExpr(
1652 const CXXConstructExpr *E) {
1653 QualType T = E->getType();
1654 assert(!classify(T));
1655
1656 if (T->isRecordType()) {
1657 const CXXConstructorDecl *Ctor = E->getConstructor();
1658
1659 // Trivial zero initialization.
1660 if (E->requiresZeroInitialization() && Ctor->isTrivial()) {
1661 const Record *R = getRecord(E->getType());
1662 return this->visitZeroRecordInitializer(R, E);
1663 }
1664
1665 const Function *Func = getFunction(Ctor);
1666
1667 if (!Func)
1668 return false;
1669
1670 assert(Func->hasThisPointer());
1671 assert(!Func->hasRVO());
1672
1673 // If we're discarding a construct expression, we still need
1674 // to allocate a variable and call the constructor and destructor.
1675 if (DiscardResult) {
1676 assert(!Initializing);
1677 std::optional<unsigned> LocalIndex =
1678 allocateLocal(E, /*IsExtended=*/true);
1679
1680 if (!LocalIndex)
1681 return false;
1682
1683 if (!this->emitGetPtrLocal(*LocalIndex, E))
1684 return false;
1685 }
1686
1687 // The This pointer is already on the stack because this is an initializer,
1688 // but we need to dup() so the call() below has its own copy.
1689 if (!this->emitDupPtr(E))
1690 return false;
1691
1692 // Constructor arguments.
1693 for (const auto *Arg : E->arguments()) {
1694 if (!this->visit(Arg))
1695 return false;
1696 }
1697
1698 if (!this->emitCall(Func, E))
1699 return false;
1700
1701 // Immediately call the destructor if we have to.
1702 if (DiscardResult) {
1703 if (!this->emitPopPtr(E))
1704 return false;
1705 }
1706 return true;
1707 }
1708
1709 if (T->isArrayType()) {
1710 const ConstantArrayType *CAT =
1711 Ctx.getASTContext().getAsConstantArrayType(E->getType());
1712 assert(CAT);
1713 size_t NumElems = CAT->getSize().getZExtValue();
1714 const Function *Func = getFunction(E->getConstructor());
1715 if (!Func || !Func->isConstexpr())
1716 return false;
1717
1718 // FIXME(perf): We're calling the constructor once per array element here,
1719 // in the old intepreter we had a special-case for trivial constructors.
1720 for (size_t I = 0; I != NumElems; ++I) {
1721 if (!this->emitConstUint64(I, E))
1722 return false;
1723 if (!this->emitArrayElemPtrUint64(E))
1724 return false;
1725
1726 // Constructor arguments.
1727 for (const auto *Arg : E->arguments()) {
1728 if (!this->visit(Arg))
1729 return false;
1730 }
1731
1732 if (!this->emitCall(Func, E))
1733 return false;
1734 }
1735 return true;
1736 }
1737
1738 return false;
1739 }
1740
1741 template <class Emitter>
VisitSourceLocExpr(const SourceLocExpr * E)1742 bool ByteCodeExprGen<Emitter>::VisitSourceLocExpr(const SourceLocExpr *E) {
1743 if (DiscardResult)
1744 return true;
1745
1746 const APValue Val =
1747 E->EvaluateInContext(Ctx.getASTContext(), SourceLocDefaultExpr);
1748
1749 // Things like __builtin_LINE().
1750 if (E->getType()->isIntegerType()) {
1751 assert(Val.isInt());
1752 const APSInt &I = Val.getInt();
1753 return this->emitConst(I, E);
1754 }
1755 // Otherwise, the APValue is an LValue, with only one element.
1756 // Theoretically, we don't need the APValue at all of course.
1757 assert(E->getType()->isPointerType());
1758 assert(Val.isLValue());
1759 const APValue::LValueBase &Base = Val.getLValueBase();
1760 if (const Expr *LValueExpr = Base.dyn_cast<const Expr *>())
1761 return this->visit(LValueExpr);
1762
1763 // Otherwise, we have a decl (which is the case for
1764 // __builtin_source_location).
1765 assert(Base.is<const ValueDecl *>());
1766 assert(Val.getLValuePath().size() == 0);
1767 const auto *BaseDecl = Base.dyn_cast<const ValueDecl *>();
1768 assert(BaseDecl);
1769
1770 auto *UGCD = cast<UnnamedGlobalConstantDecl>(BaseDecl);
1771
1772 std::optional<unsigned> GlobalIndex = P.getOrCreateGlobal(UGCD);
1773 if (!GlobalIndex)
1774 return false;
1775
1776 if (!this->emitGetPtrGlobal(*GlobalIndex, E))
1777 return false;
1778
1779 const Record *R = getRecord(E->getType());
1780 const APValue &V = UGCD->getValue();
1781 for (unsigned I = 0, N = R->getNumFields(); I != N; ++I) {
1782 const Record::Field *F = R->getField(I);
1783 const APValue &FieldValue = V.getStructField(I);
1784
1785 PrimType FieldT = classifyPrim(F->Decl->getType());
1786
1787 if (!this->visitAPValue(FieldValue, FieldT, E))
1788 return false;
1789 if (!this->emitInitField(FieldT, F->Offset, E))
1790 return false;
1791 }
1792
1793 // Leave the pointer to the global on the stack.
1794 return true;
1795 }
1796
1797 template <class Emitter>
VisitOffsetOfExpr(const OffsetOfExpr * E)1798 bool ByteCodeExprGen<Emitter>::VisitOffsetOfExpr(const OffsetOfExpr *E) {
1799 unsigned N = E->getNumComponents();
1800 if (N == 0)
1801 return false;
1802
1803 for (unsigned I = 0; I != N; ++I) {
1804 const OffsetOfNode &Node = E->getComponent(I);
1805 if (Node.getKind() == OffsetOfNode::Array) {
1806 const Expr *ArrayIndexExpr = E->getIndexExpr(Node.getArrayExprIndex());
1807 PrimType IndexT = classifyPrim(ArrayIndexExpr->getType());
1808
1809 if (DiscardResult) {
1810 if (!this->discard(ArrayIndexExpr))
1811 return false;
1812 continue;
1813 }
1814
1815 if (!this->visit(ArrayIndexExpr))
1816 return false;
1817 // Cast to Sint64.
1818 if (IndexT != PT_Sint64) {
1819 if (!this->emitCast(IndexT, PT_Sint64, E))
1820 return false;
1821 }
1822 }
1823 }
1824
1825 if (DiscardResult)
1826 return true;
1827
1828 PrimType T = classifyPrim(E->getType());
1829 return this->emitOffsetOf(T, E, E);
1830 }
1831
1832 template <class Emitter>
VisitCXXScalarValueInitExpr(const CXXScalarValueInitExpr * E)1833 bool ByteCodeExprGen<Emitter>::VisitCXXScalarValueInitExpr(
1834 const CXXScalarValueInitExpr *E) {
1835 QualType Ty = E->getType();
1836
1837 if (Ty->isVoidType())
1838 return true;
1839
1840 return this->visitZeroInitializer(classifyPrim(Ty), Ty, E);
1841 }
1842
1843 template <class Emitter>
VisitSizeOfPackExpr(const SizeOfPackExpr * E)1844 bool ByteCodeExprGen<Emitter>::VisitSizeOfPackExpr(const SizeOfPackExpr *E) {
1845 return this->emitConst(E->getPackLength(), E);
1846 }
1847
discard(const Expr * E)1848 template <class Emitter> bool ByteCodeExprGen<Emitter>::discard(const Expr *E) {
1849 if (E->containsErrors())
1850 return false;
1851
1852 OptionScope<Emitter> Scope(this, /*NewDiscardResult=*/true,
1853 /*NewInitializing=*/false);
1854 return this->Visit(E);
1855 }
1856
1857 template <class Emitter>
delegate(const Expr * E)1858 bool ByteCodeExprGen<Emitter>::delegate(const Expr *E) {
1859 if (E->containsErrors())
1860 return false;
1861
1862 // We're basically doing:
1863 // OptionScope<Emitter> Scope(this, DicardResult, Initializing);
1864 // but that's unnecessary of course.
1865 return this->Visit(E);
1866 }
1867
visit(const Expr * E)1868 template <class Emitter> bool ByteCodeExprGen<Emitter>::visit(const Expr *E) {
1869 if (E->containsErrors())
1870 return false;
1871
1872 if (E->getType()->isVoidType())
1873 return this->discard(E);
1874
1875 // Create local variable to hold the return value.
1876 if (!E->isGLValue() && !E->getType()->isAnyComplexType() &&
1877 !classify(E->getType())) {
1878 std::optional<unsigned> LocalIndex = allocateLocal(E, /*IsExtended=*/true);
1879 if (!LocalIndex)
1880 return false;
1881
1882 if (!this->emitGetPtrLocal(*LocalIndex, E))
1883 return false;
1884 return this->visitInitializer(E);
1885 }
1886
1887 // Otherwise,we have a primitive return value, produce the value directly
1888 // and push it on the stack.
1889 OptionScope<Emitter> Scope(this, /*NewDiscardResult=*/false,
1890 /*NewInitializing=*/false);
1891 return this->Visit(E);
1892 }
1893
1894 template <class Emitter>
visitInitializer(const Expr * E)1895 bool ByteCodeExprGen<Emitter>::visitInitializer(const Expr *E) {
1896 assert(!classify(E->getType()));
1897
1898 if (E->containsErrors())
1899 return false;
1900
1901 OptionScope<Emitter> Scope(this, /*NewDiscardResult=*/false,
1902 /*NewInitializing=*/true);
1903 return this->Visit(E);
1904 }
1905
1906 template <class Emitter>
visitBool(const Expr * E)1907 bool ByteCodeExprGen<Emitter>::visitBool(const Expr *E) {
1908 std::optional<PrimType> T = classify(E->getType());
1909 if (!T)
1910 return false;
1911
1912 if (!this->visit(E))
1913 return false;
1914
1915 if (T == PT_Bool)
1916 return true;
1917
1918 // Convert pointers to bool.
1919 if (T == PT_Ptr || T == PT_FnPtr) {
1920 if (!this->emitNull(*T, E))
1921 return false;
1922 return this->emitNE(*T, E);
1923 }
1924
1925 // Or Floats.
1926 if (T == PT_Float)
1927 return this->emitCastFloatingIntegralBool(E);
1928
1929 // Or anything else we can.
1930 return this->emitCast(*T, PT_Bool, E);
1931 }
1932
1933 template <class Emitter>
visitZeroInitializer(PrimType T,QualType QT,const Expr * E)1934 bool ByteCodeExprGen<Emitter>::visitZeroInitializer(PrimType T, QualType QT,
1935 const Expr *E) {
1936 switch (T) {
1937 case PT_Bool:
1938 return this->emitZeroBool(E);
1939 case PT_Sint8:
1940 return this->emitZeroSint8(E);
1941 case PT_Uint8:
1942 return this->emitZeroUint8(E);
1943 case PT_Sint16:
1944 return this->emitZeroSint16(E);
1945 case PT_Uint16:
1946 return this->emitZeroUint16(E);
1947 case PT_Sint32:
1948 return this->emitZeroSint32(E);
1949 case PT_Uint32:
1950 return this->emitZeroUint32(E);
1951 case PT_Sint64:
1952 return this->emitZeroSint64(E);
1953 case PT_Uint64:
1954 return this->emitZeroUint64(E);
1955 case PT_IntAP:
1956 return this->emitZeroIntAP(Ctx.getBitWidth(QT), E);
1957 case PT_IntAPS:
1958 return this->emitZeroIntAPS(Ctx.getBitWidth(QT), E);
1959 case PT_Ptr:
1960 return this->emitNullPtr(E);
1961 case PT_FnPtr:
1962 return this->emitNullFnPtr(E);
1963 case PT_Float: {
1964 return this->emitConstFloat(APFloat::getZero(Ctx.getFloatSemantics(QT)), E);
1965 }
1966 }
1967 llvm_unreachable("unknown primitive type");
1968 }
1969
1970 template <class Emitter>
visitZeroRecordInitializer(const Record * R,const Expr * E)1971 bool ByteCodeExprGen<Emitter>::visitZeroRecordInitializer(const Record *R,
1972 const Expr *E) {
1973 assert(E);
1974 assert(R);
1975 // Fields
1976 for (const Record::Field &Field : R->fields()) {
1977 const Descriptor *D = Field.Desc;
1978 if (D->isPrimitive()) {
1979 QualType QT = D->getType();
1980 PrimType T = classifyPrim(D->getType());
1981 if (!this->visitZeroInitializer(T, QT, E))
1982 return false;
1983 if (!this->emitInitField(T, Field.Offset, E))
1984 return false;
1985 continue;
1986 }
1987
1988 // TODO: Add GetPtrFieldPop and get rid of this dup.
1989 if (!this->emitDupPtr(E))
1990 return false;
1991 if (!this->emitGetPtrField(Field.Offset, E))
1992 return false;
1993
1994 if (D->isPrimitiveArray()) {
1995 QualType ET = D->getElemQualType();
1996 PrimType T = classifyPrim(ET);
1997 for (uint32_t I = 0, N = D->getNumElems(); I != N; ++I) {
1998 if (!this->visitZeroInitializer(T, ET, E))
1999 return false;
2000 if (!this->emitInitElem(T, I, E))
2001 return false;
2002 }
2003 } else if (D->isCompositeArray()) {
2004 const Record *ElemRecord = D->ElemDesc->ElemRecord;
2005 assert(D->ElemDesc->ElemRecord);
2006 for (uint32_t I = 0, N = D->getNumElems(); I != N; ++I) {
2007 if (!this->emitConstUint32(I, E))
2008 return false;
2009 if (!this->emitArrayElemPtr(PT_Uint32, E))
2010 return false;
2011 if (!this->visitZeroRecordInitializer(ElemRecord, E))
2012 return false;
2013 if (!this->emitPopPtr(E))
2014 return false;
2015 }
2016 } else if (D->isRecord()) {
2017 if (!this->visitZeroRecordInitializer(D->ElemRecord, E))
2018 return false;
2019 } else {
2020 assert(false);
2021 }
2022
2023 if (!this->emitPopPtr(E))
2024 return false;
2025 }
2026
2027 for (const Record::Base &B : R->bases()) {
2028 if (!this->emitGetPtrBase(B.Offset, E))
2029 return false;
2030 if (!this->visitZeroRecordInitializer(B.R, E))
2031 return false;
2032 if (!this->emitInitPtrPop(E))
2033 return false;
2034 }
2035
2036 // FIXME: Virtual bases.
2037
2038 return true;
2039 }
2040
2041 template <class Emitter>
dereference(const Expr * LV,DerefKind AK,llvm::function_ref<bool (PrimType)> Direct,llvm::function_ref<bool (PrimType)> Indirect)2042 bool ByteCodeExprGen<Emitter>::dereference(
2043 const Expr *LV, DerefKind AK, llvm::function_ref<bool(PrimType)> Direct,
2044 llvm::function_ref<bool(PrimType)> Indirect) {
2045 if (std::optional<PrimType> T = classify(LV->getType())) {
2046 if (!LV->refersToBitField()) {
2047 // Only primitive, non bit-field types can be dereferenced directly.
2048 if (const auto *DE = dyn_cast<DeclRefExpr>(LV)) {
2049 if (!DE->getDecl()->getType()->isReferenceType()) {
2050 if (const auto *PD = dyn_cast<ParmVarDecl>(DE->getDecl()))
2051 return dereferenceParam(LV, *T, PD, AK, Direct, Indirect);
2052 if (const auto *VD = dyn_cast<VarDecl>(DE->getDecl()))
2053 return dereferenceVar(LV, *T, VD, AK, Direct, Indirect);
2054 }
2055 }
2056 }
2057
2058 if (!visit(LV))
2059 return false;
2060 return Indirect(*T);
2061 }
2062
2063 if (LV->getType()->isAnyComplexType())
2064 return this->delegate(LV);
2065
2066 return false;
2067 }
2068
2069 template <class Emitter>
dereferenceParam(const Expr * LV,PrimType T,const ParmVarDecl * PD,DerefKind AK,llvm::function_ref<bool (PrimType)> Direct,llvm::function_ref<bool (PrimType)> Indirect)2070 bool ByteCodeExprGen<Emitter>::dereferenceParam(
2071 const Expr *LV, PrimType T, const ParmVarDecl *PD, DerefKind AK,
2072 llvm::function_ref<bool(PrimType)> Direct,
2073 llvm::function_ref<bool(PrimType)> Indirect) {
2074 auto It = this->Params.find(PD);
2075 if (It != this->Params.end()) {
2076 unsigned Idx = It->second.Offset;
2077 switch (AK) {
2078 case DerefKind::Read:
2079 return DiscardResult ? true : this->emitGetParam(T, Idx, LV);
2080
2081 case DerefKind::Write:
2082 if (!Direct(T))
2083 return false;
2084 if (!this->emitSetParam(T, Idx, LV))
2085 return false;
2086 return DiscardResult ? true : this->emitGetPtrParam(Idx, LV);
2087
2088 case DerefKind::ReadWrite:
2089 if (!this->emitGetParam(T, Idx, LV))
2090 return false;
2091 if (!Direct(T))
2092 return false;
2093 if (!this->emitSetParam(T, Idx, LV))
2094 return false;
2095 return DiscardResult ? true : this->emitGetPtrParam(Idx, LV);
2096 }
2097 return true;
2098 }
2099
2100 // If the param is a pointer, we can dereference a dummy value.
2101 if (!DiscardResult && T == PT_Ptr && AK == DerefKind::Read) {
2102 if (auto Idx = P.getOrCreateDummy(PD))
2103 return this->emitGetPtrGlobal(*Idx, PD);
2104 return false;
2105 }
2106
2107 // Value cannot be produced - try to emit pointer and do stuff with it.
2108 return visit(LV) && Indirect(T);
2109 }
2110
2111 template <class Emitter>
dereferenceVar(const Expr * LV,PrimType T,const VarDecl * VD,DerefKind AK,llvm::function_ref<bool (PrimType)> Direct,llvm::function_ref<bool (PrimType)> Indirect)2112 bool ByteCodeExprGen<Emitter>::dereferenceVar(
2113 const Expr *LV, PrimType T, const VarDecl *VD, DerefKind AK,
2114 llvm::function_ref<bool(PrimType)> Direct,
2115 llvm::function_ref<bool(PrimType)> Indirect) {
2116 auto It = Locals.find(VD);
2117 if (It != Locals.end()) {
2118 const auto &L = It->second;
2119 switch (AK) {
2120 case DerefKind::Read:
2121 if (!this->emitGetLocal(T, L.Offset, LV))
2122 return false;
2123 return DiscardResult ? this->emitPop(T, LV) : true;
2124
2125 case DerefKind::Write:
2126 if (!Direct(T))
2127 return false;
2128 if (!this->emitSetLocal(T, L.Offset, LV))
2129 return false;
2130 return DiscardResult ? true : this->emitGetPtrLocal(L.Offset, LV);
2131
2132 case DerefKind::ReadWrite:
2133 if (!this->emitGetLocal(T, L.Offset, LV))
2134 return false;
2135 if (!Direct(T))
2136 return false;
2137 if (!this->emitSetLocal(T, L.Offset, LV))
2138 return false;
2139 return DiscardResult ? true : this->emitGetPtrLocal(L.Offset, LV);
2140 }
2141 } else if (auto Idx = P.getGlobal(VD)) {
2142 switch (AK) {
2143 case DerefKind::Read:
2144 if (!this->emitGetGlobal(T, *Idx, LV))
2145 return false;
2146 return DiscardResult ? this->emitPop(T, LV) : true;
2147
2148 case DerefKind::Write:
2149 if (!Direct(T))
2150 return false;
2151 if (!this->emitSetGlobal(T, *Idx, LV))
2152 return false;
2153 return DiscardResult ? true : this->emitGetPtrGlobal(*Idx, LV);
2154
2155 case DerefKind::ReadWrite:
2156 if (!this->emitGetGlobal(T, *Idx, LV))
2157 return false;
2158 if (!Direct(T))
2159 return false;
2160 if (!this->emitSetGlobal(T, *Idx, LV))
2161 return false;
2162 return DiscardResult ? true : this->emitGetPtrGlobal(*Idx, LV);
2163 }
2164 }
2165
2166 // If the declaration is a constant value, emit it here even
2167 // though the declaration was not evaluated in the current scope.
2168 // The access mode can only be read in this case.
2169 if (!DiscardResult && AK == DerefKind::Read) {
2170 if (VD->hasLocalStorage() && VD->hasInit() && !VD->isConstexpr()) {
2171 QualType VT = VD->getType();
2172 if (VT.isConstQualified() && VT->isFundamentalType())
2173 return this->visit(VD->getInit());
2174 }
2175 }
2176
2177 // Value cannot be produced - try to emit pointer.
2178 return visit(LV) && Indirect(T);
2179 }
2180
2181 template <class Emitter>
2182 template <typename T>
emitConst(T Value,PrimType Ty,const Expr * E)2183 bool ByteCodeExprGen<Emitter>::emitConst(T Value, PrimType Ty, const Expr *E) {
2184 switch (Ty) {
2185 case PT_Sint8:
2186 return this->emitConstSint8(Value, E);
2187 case PT_Uint8:
2188 return this->emitConstUint8(Value, E);
2189 case PT_Sint16:
2190 return this->emitConstSint16(Value, E);
2191 case PT_Uint16:
2192 return this->emitConstUint16(Value, E);
2193 case PT_Sint32:
2194 return this->emitConstSint32(Value, E);
2195 case PT_Uint32:
2196 return this->emitConstUint32(Value, E);
2197 case PT_Sint64:
2198 return this->emitConstSint64(Value, E);
2199 case PT_Uint64:
2200 return this->emitConstUint64(Value, E);
2201 case PT_IntAP:
2202 case PT_IntAPS:
2203 assert(false);
2204 return false;
2205 case PT_Bool:
2206 return this->emitConstBool(Value, E);
2207 case PT_Ptr:
2208 case PT_FnPtr:
2209 case PT_Float:
2210 llvm_unreachable("Invalid integral type");
2211 break;
2212 }
2213 llvm_unreachable("unknown primitive type");
2214 }
2215
2216 template <class Emitter>
2217 template <typename T>
emitConst(T Value,const Expr * E)2218 bool ByteCodeExprGen<Emitter>::emitConst(T Value, const Expr *E) {
2219 return this->emitConst(Value, classifyPrim(E->getType()), E);
2220 }
2221
2222 template <class Emitter>
emitConst(const APSInt & Value,PrimType Ty,const Expr * E)2223 bool ByteCodeExprGen<Emitter>::emitConst(const APSInt &Value, PrimType Ty,
2224 const Expr *E) {
2225 if (Value.isSigned())
2226 return this->emitConst(Value.getSExtValue(), Ty, E);
2227 return this->emitConst(Value.getZExtValue(), Ty, E);
2228 }
2229
2230 template <class Emitter>
emitConst(const APSInt & Value,const Expr * E)2231 bool ByteCodeExprGen<Emitter>::emitConst(const APSInt &Value, const Expr *E) {
2232 return this->emitConst(Value, classifyPrim(E->getType()), E);
2233 }
2234
2235 template <class Emitter>
allocateLocalPrimitive(DeclTy && Src,PrimType Ty,bool IsConst,bool IsExtended)2236 unsigned ByteCodeExprGen<Emitter>::allocateLocalPrimitive(DeclTy &&Src,
2237 PrimType Ty,
2238 bool IsConst,
2239 bool IsExtended) {
2240 // Make sure we don't accidentally register the same decl twice.
2241 if (const auto *VD =
2242 dyn_cast_if_present<ValueDecl>(Src.dyn_cast<const Decl *>())) {
2243 assert(!P.getGlobal(VD));
2244 assert(!Locals.contains(VD));
2245 }
2246
2247 // FIXME: There are cases where Src.is<Expr*>() is wrong, e.g.
2248 // (int){12} in C. Consider using Expr::isTemporaryObject() instead
2249 // or isa<MaterializeTemporaryExpr>().
2250 Descriptor *D = P.createDescriptor(Src, Ty, Descriptor::InlineDescMD, IsConst,
2251 Src.is<const Expr *>());
2252 Scope::Local Local = this->createLocal(D);
2253 if (auto *VD = dyn_cast_if_present<ValueDecl>(Src.dyn_cast<const Decl *>()))
2254 Locals.insert({VD, Local});
2255 VarScope->add(Local, IsExtended);
2256 return Local.Offset;
2257 }
2258
2259 template <class Emitter>
2260 std::optional<unsigned>
allocateLocal(DeclTy && Src,bool IsExtended)2261 ByteCodeExprGen<Emitter>::allocateLocal(DeclTy &&Src, bool IsExtended) {
2262 // Make sure we don't accidentally register the same decl twice.
2263 if ([[maybe_unused]] const auto *VD =
2264 dyn_cast_if_present<ValueDecl>(Src.dyn_cast<const Decl *>())) {
2265 assert(!P.getGlobal(VD));
2266 assert(!Locals.contains(VD));
2267 }
2268
2269 QualType Ty;
2270 const ValueDecl *Key = nullptr;
2271 const Expr *Init = nullptr;
2272 bool IsTemporary = false;
2273 if (auto *VD = dyn_cast_if_present<ValueDecl>(Src.dyn_cast<const Decl *>())) {
2274 Key = VD;
2275 Ty = VD->getType();
2276
2277 if (const auto *VarD = dyn_cast<VarDecl>(VD))
2278 Init = VarD->getInit();
2279 }
2280 if (auto *E = Src.dyn_cast<const Expr *>()) {
2281 IsTemporary = true;
2282 Ty = E->getType();
2283 }
2284
2285 Descriptor *D = P.createDescriptor(
2286 Src, Ty.getTypePtr(), Descriptor::InlineDescMD, Ty.isConstQualified(),
2287 IsTemporary, /*IsMutable=*/false, Init);
2288 if (!D)
2289 return {};
2290
2291 Scope::Local Local = this->createLocal(D);
2292 if (Key)
2293 Locals.insert({Key, Local});
2294 VarScope->add(Local, IsExtended);
2295 return Local.Offset;
2296 }
2297
2298 template <class Emitter>
getRecordTy(QualType Ty)2299 const RecordType *ByteCodeExprGen<Emitter>::getRecordTy(QualType Ty) {
2300 if (const PointerType *PT = dyn_cast<PointerType>(Ty))
2301 return PT->getPointeeType()->getAs<RecordType>();
2302 return Ty->getAs<RecordType>();
2303 }
2304
2305 template <class Emitter>
getRecord(QualType Ty)2306 Record *ByteCodeExprGen<Emitter>::getRecord(QualType Ty) {
2307 if (const auto *RecordTy = getRecordTy(Ty))
2308 return getRecord(RecordTy->getDecl());
2309 return nullptr;
2310 }
2311
2312 template <class Emitter>
getRecord(const RecordDecl * RD)2313 Record *ByteCodeExprGen<Emitter>::getRecord(const RecordDecl *RD) {
2314 return P.getOrCreateRecord(RD);
2315 }
2316
2317 template <class Emitter>
getFunction(const FunctionDecl * FD)2318 const Function *ByteCodeExprGen<Emitter>::getFunction(const FunctionDecl *FD) {
2319 return Ctx.getOrCreateFunction(FD);
2320 }
2321
2322 template <class Emitter>
visitExpr(const Expr * E)2323 bool ByteCodeExprGen<Emitter>::visitExpr(const Expr *E) {
2324 ExprScope<Emitter> RootScope(this);
2325 // Void expressions.
2326 if (E->getType()->isVoidType()) {
2327 if (!visit(E))
2328 return false;
2329 return this->emitRetVoid(E);
2330 }
2331
2332 // Expressions with a primitive return type.
2333 if (std::optional<PrimType> T = classify(E)) {
2334 if (!visit(E))
2335 return false;
2336 return this->emitRet(*T, E);
2337 }
2338
2339 // Expressions with a composite return type.
2340 // For us, that means everything we don't
2341 // have a PrimType for.
2342 if (std::optional<unsigned> LocalOffset = this->allocateLocal(E)) {
2343 if (!this->visitLocalInitializer(E, *LocalOffset))
2344 return false;
2345
2346 if (!this->emitGetPtrLocal(*LocalOffset, E))
2347 return false;
2348 return this->emitRetValue(E);
2349 }
2350
2351 return false;
2352 }
2353
2354 /// Toplevel visitDecl().
2355 /// We get here from evaluateAsInitializer().
2356 /// We need to evaluate the initializer and return its value.
2357 template <class Emitter>
visitDecl(const VarDecl * VD)2358 bool ByteCodeExprGen<Emitter>::visitDecl(const VarDecl *VD) {
2359 assert(!VD->isInvalidDecl() && "Trying to constant evaluate an invalid decl");
2360
2361 // Create and initialize the variable.
2362 if (!this->visitVarDecl(VD))
2363 return false;
2364
2365 std::optional<PrimType> VarT = classify(VD->getType());
2366 // Get a pointer to the variable
2367 if (Context::shouldBeGloballyIndexed(VD)) {
2368 auto GlobalIndex = P.getGlobal(VD);
2369 assert(GlobalIndex); // visitVarDecl() didn't return false.
2370 if (VarT) {
2371 if (!this->emitGetGlobalUnchecked(*VarT, *GlobalIndex, VD))
2372 return false;
2373 } else {
2374 if (!this->emitGetPtrGlobal(*GlobalIndex, VD))
2375 return false;
2376 }
2377 } else {
2378 auto Local = Locals.find(VD);
2379 assert(Local != Locals.end()); // Same here.
2380 if (VarT) {
2381 if (!this->emitGetLocal(*VarT, Local->second.Offset, VD))
2382 return false;
2383 } else {
2384 if (!this->emitGetPtrLocal(Local->second.Offset, VD))
2385 return false;
2386 }
2387 }
2388
2389 // Return the value
2390 if (VarT)
2391 return this->emitRet(*VarT, VD);
2392
2393 // Return non-primitive values as pointers here.
2394 return this->emitRet(PT_Ptr, VD);
2395 }
2396
2397 template <class Emitter>
visitVarDecl(const VarDecl * VD)2398 bool ByteCodeExprGen<Emitter>::visitVarDecl(const VarDecl *VD) {
2399 // We don't know what to do with these, so just return false.
2400 if (VD->getType().isNull())
2401 return false;
2402
2403 const Expr *Init = VD->getInit();
2404 std::optional<PrimType> VarT = classify(VD->getType());
2405
2406 if (Context::shouldBeGloballyIndexed(VD)) {
2407 // We've already seen and initialized this global.
2408 if (P.getGlobal(VD))
2409 return true;
2410
2411 std::optional<unsigned> GlobalIndex = P.createGlobal(VD, Init);
2412
2413 if (!GlobalIndex)
2414 return false;
2415
2416 assert(Init);
2417 {
2418 DeclScope<Emitter> LocalScope(this, VD);
2419
2420 if (VarT) {
2421 if (!this->visit(Init))
2422 return false;
2423 return this->emitInitGlobal(*VarT, *GlobalIndex, VD);
2424 }
2425 return this->visitGlobalInitializer(Init, *GlobalIndex);
2426 }
2427 } else {
2428 VariableScope<Emitter> LocalScope(this);
2429 if (VarT) {
2430 unsigned Offset = this->allocateLocalPrimitive(
2431 VD, *VarT, VD->getType().isConstQualified());
2432 if (Init) {
2433 // Compile the initializer in its own scope.
2434 ExprScope<Emitter> Scope(this);
2435 if (!this->visit(Init))
2436 return false;
2437
2438 return this->emitSetLocal(*VarT, Offset, VD);
2439 }
2440 } else {
2441 if (std::optional<unsigned> Offset = this->allocateLocal(VD)) {
2442 if (Init)
2443 return this->visitLocalInitializer(Init, *Offset);
2444 }
2445 }
2446 return true;
2447 }
2448
2449 return false;
2450 }
2451
2452 template <class Emitter>
visitAPValue(const APValue & Val,PrimType ValType,const Expr * E)2453 bool ByteCodeExprGen<Emitter>::visitAPValue(const APValue &Val,
2454 PrimType ValType, const Expr *E) {
2455 assert(!DiscardResult);
2456 if (Val.isInt())
2457 return this->emitConst(Val.getInt(), ValType, E);
2458
2459 if (Val.isLValue()) {
2460 APValue::LValueBase Base = Val.getLValueBase();
2461 if (const Expr *BaseExpr = Base.dyn_cast<const Expr *>())
2462 return this->visit(BaseExpr);
2463 }
2464
2465 return false;
2466 }
2467
2468 template <class Emitter>
VisitBuiltinCallExpr(const CallExpr * E)2469 bool ByteCodeExprGen<Emitter>::VisitBuiltinCallExpr(const CallExpr *E) {
2470 const Function *Func = getFunction(E->getDirectCallee());
2471 if (!Func)
2472 return false;
2473
2474 if (!Func->isUnevaluatedBuiltin()) {
2475 // Put arguments on the stack.
2476 for (const auto *Arg : E->arguments()) {
2477 if (!this->visit(Arg))
2478 return false;
2479 }
2480 }
2481
2482 if (!this->emitCallBI(Func, E, E))
2483 return false;
2484
2485 QualType ReturnType = E->getCallReturnType(Ctx.getASTContext());
2486 if (DiscardResult && !ReturnType->isVoidType()) {
2487 PrimType T = classifyPrim(ReturnType);
2488 return this->emitPop(T, E);
2489 }
2490
2491 return true;
2492 }
2493
2494 template <class Emitter>
VisitCallExpr(const CallExpr * E)2495 bool ByteCodeExprGen<Emitter>::VisitCallExpr(const CallExpr *E) {
2496 if (E->getBuiltinCallee())
2497 return VisitBuiltinCallExpr(E);
2498
2499 QualType ReturnType = E->getCallReturnType(Ctx.getASTContext());
2500 std::optional<PrimType> T = classify(ReturnType);
2501 bool HasRVO = !ReturnType->isVoidType() && !T;
2502
2503 if (HasRVO) {
2504 if (DiscardResult) {
2505 // If we need to discard the return value but the function returns its
2506 // value via an RVO pointer, we need to create one such pointer just
2507 // for this call.
2508 if (std::optional<unsigned> LocalIndex = allocateLocal(E)) {
2509 if (!this->emitGetPtrLocal(*LocalIndex, E))
2510 return false;
2511 }
2512 } else {
2513 assert(Initializing);
2514 if (!this->emitDupPtr(E))
2515 return false;
2516 }
2517 }
2518
2519 // Add the (optional, implicit) This pointer.
2520 if (const auto *MC = dyn_cast<CXXMemberCallExpr>(E)) {
2521 if (!this->visit(MC->getImplicitObjectArgument()))
2522 return false;
2523 }
2524
2525 // Put arguments on the stack.
2526 for (const auto *Arg : E->arguments()) {
2527 if (!this->visit(Arg))
2528 return false;
2529 }
2530
2531 if (const FunctionDecl *FuncDecl = E->getDirectCallee()) {
2532 const Function *Func = getFunction(FuncDecl);
2533 if (!Func)
2534 return false;
2535 // If the function is being compiled right now, this is a recursive call.
2536 // In that case, the function can't be valid yet, even though it will be
2537 // later.
2538 // If the function is already fully compiled but not constexpr, it was
2539 // found to be faulty earlier on, so bail out.
2540 if (Func->isFullyCompiled() && !Func->isConstexpr())
2541 return false;
2542
2543 assert(HasRVO == Func->hasRVO());
2544
2545 bool HasQualifier = false;
2546 if (const auto *ME = dyn_cast<MemberExpr>(E->getCallee()))
2547 HasQualifier = ME->hasQualifier();
2548
2549 bool IsVirtual = false;
2550 if (const auto *MD = dyn_cast<CXXMethodDecl>(FuncDecl))
2551 IsVirtual = MD->isVirtual();
2552
2553 // In any case call the function. The return value will end up on the stack
2554 // and if the function has RVO, we already have the pointer on the stack to
2555 // write the result into.
2556 if (IsVirtual && !HasQualifier) {
2557 if (!this->emitCallVirt(Func, E))
2558 return false;
2559 } else {
2560 if (!this->emitCall(Func, E))
2561 return false;
2562 }
2563 } else {
2564 // Indirect call. Visit the callee, which will leave a FunctionPointer on
2565 // the stack. Cleanup of the returned value if necessary will be done after
2566 // the function call completed.
2567 if (!this->visit(E->getCallee()))
2568 return false;
2569
2570 if (!this->emitCallPtr(E))
2571 return false;
2572 }
2573
2574 // Cleanup for discarded return values.
2575 if (DiscardResult && !ReturnType->isVoidType() && T)
2576 return this->emitPop(*T, E);
2577
2578 return true;
2579 }
2580
2581 template <class Emitter>
VisitCXXDefaultInitExpr(const CXXDefaultInitExpr * E)2582 bool ByteCodeExprGen<Emitter>::VisitCXXDefaultInitExpr(
2583 const CXXDefaultInitExpr *E) {
2584 SourceLocScope<Emitter> SLS(this, E);
2585 if (Initializing)
2586 return this->visitInitializer(E->getExpr());
2587
2588 assert(classify(E->getType()));
2589 return this->visit(E->getExpr());
2590 }
2591
2592 template <class Emitter>
VisitCXXDefaultArgExpr(const CXXDefaultArgExpr * E)2593 bool ByteCodeExprGen<Emitter>::VisitCXXDefaultArgExpr(
2594 const CXXDefaultArgExpr *E) {
2595 SourceLocScope<Emitter> SLS(this, E);
2596
2597 const Expr *SubExpr = E->getExpr();
2598 if (std::optional<PrimType> T = classify(E->getExpr()))
2599 return this->visit(SubExpr);
2600
2601 assert(Initializing);
2602 return this->visitInitializer(SubExpr);
2603 }
2604
2605 template <class Emitter>
VisitCXXBoolLiteralExpr(const CXXBoolLiteralExpr * E)2606 bool ByteCodeExprGen<Emitter>::VisitCXXBoolLiteralExpr(
2607 const CXXBoolLiteralExpr *E) {
2608 if (DiscardResult)
2609 return true;
2610
2611 return this->emitConstBool(E->getValue(), E);
2612 }
2613
2614 template <class Emitter>
VisitCXXNullPtrLiteralExpr(const CXXNullPtrLiteralExpr * E)2615 bool ByteCodeExprGen<Emitter>::VisitCXXNullPtrLiteralExpr(
2616 const CXXNullPtrLiteralExpr *E) {
2617 if (DiscardResult)
2618 return true;
2619
2620 return this->emitNullPtr(E);
2621 }
2622
2623 template <class Emitter>
VisitGNUNullExpr(const GNUNullExpr * E)2624 bool ByteCodeExprGen<Emitter>::VisitGNUNullExpr(const GNUNullExpr *E) {
2625 if (DiscardResult)
2626 return true;
2627
2628 assert(E->getType()->isIntegerType());
2629
2630 PrimType T = classifyPrim(E->getType());
2631 return this->emitZero(T, E);
2632 }
2633
2634 template <class Emitter>
VisitCXXThisExpr(const CXXThisExpr * E)2635 bool ByteCodeExprGen<Emitter>::VisitCXXThisExpr(const CXXThisExpr *E) {
2636 if (DiscardResult)
2637 return true;
2638
2639 if (this->LambdaThisCapture > 0)
2640 return this->emitGetThisFieldPtr(this->LambdaThisCapture, E);
2641
2642 return this->emitThis(E);
2643 }
2644
2645 template <class Emitter>
VisitUnaryOperator(const UnaryOperator * E)2646 bool ByteCodeExprGen<Emitter>::VisitUnaryOperator(const UnaryOperator *E) {
2647 const Expr *SubExpr = E->getSubExpr();
2648 std::optional<PrimType> T = classify(SubExpr->getType());
2649
2650 switch (E->getOpcode()) {
2651 case UO_PostInc: { // x++
2652 if (!this->visit(SubExpr))
2653 return false;
2654
2655 if (T == PT_Ptr) {
2656 if (!this->emitIncPtr(E))
2657 return false;
2658
2659 return DiscardResult ? this->emitPopPtr(E) : true;
2660 }
2661
2662 if (T == PT_Float) {
2663 return DiscardResult ? this->emitIncfPop(getRoundingMode(E), E)
2664 : this->emitIncf(getRoundingMode(E), E);
2665 }
2666
2667 return DiscardResult ? this->emitIncPop(*T, E) : this->emitInc(*T, E);
2668 }
2669 case UO_PostDec: { // x--
2670 if (!this->visit(SubExpr))
2671 return false;
2672
2673 if (T == PT_Ptr) {
2674 if (!this->emitDecPtr(E))
2675 return false;
2676
2677 return DiscardResult ? this->emitPopPtr(E) : true;
2678 }
2679
2680 if (T == PT_Float) {
2681 return DiscardResult ? this->emitDecfPop(getRoundingMode(E), E)
2682 : this->emitDecf(getRoundingMode(E), E);
2683 }
2684
2685 return DiscardResult ? this->emitDecPop(*T, E) : this->emitDec(*T, E);
2686 }
2687 case UO_PreInc: { // ++x
2688 if (!this->visit(SubExpr))
2689 return false;
2690
2691 if (T == PT_Ptr) {
2692 if (!this->emitLoadPtr(E))
2693 return false;
2694 if (!this->emitConstUint8(1, E))
2695 return false;
2696 if (!this->emitAddOffsetUint8(E))
2697 return false;
2698 return DiscardResult ? this->emitStorePopPtr(E) : this->emitStorePtr(E);
2699 }
2700
2701 // Post-inc and pre-inc are the same if the value is to be discarded.
2702 if (DiscardResult) {
2703 if (T == PT_Float)
2704 return this->emitIncfPop(getRoundingMode(E), E);
2705 return this->emitIncPop(*T, E);
2706 }
2707
2708 if (T == PT_Float) {
2709 const auto &TargetSemantics = Ctx.getFloatSemantics(E->getType());
2710 if (!this->emitLoadFloat(E))
2711 return false;
2712 if (!this->emitConstFloat(llvm::APFloat(TargetSemantics, 1), E))
2713 return false;
2714 if (!this->emitAddf(getRoundingMode(E), E))
2715 return false;
2716 return this->emitStoreFloat(E);
2717 }
2718 if (!this->emitLoad(*T, E))
2719 return false;
2720 if (!this->emitConst(1, E))
2721 return false;
2722 if (!this->emitAdd(*T, E))
2723 return false;
2724 return this->emitStore(*T, E);
2725 }
2726 case UO_PreDec: { // --x
2727 if (!this->visit(SubExpr))
2728 return false;
2729
2730 if (T == PT_Ptr) {
2731 if (!this->emitLoadPtr(E))
2732 return false;
2733 if (!this->emitConstUint8(1, E))
2734 return false;
2735 if (!this->emitSubOffsetUint8(E))
2736 return false;
2737 return DiscardResult ? this->emitStorePopPtr(E) : this->emitStorePtr(E);
2738 }
2739
2740 // Post-dec and pre-dec are the same if the value is to be discarded.
2741 if (DiscardResult) {
2742 if (T == PT_Float)
2743 return this->emitDecfPop(getRoundingMode(E), E);
2744 return this->emitDecPop(*T, E);
2745 }
2746
2747 if (T == PT_Float) {
2748 const auto &TargetSemantics = Ctx.getFloatSemantics(E->getType());
2749 if (!this->emitLoadFloat(E))
2750 return false;
2751 if (!this->emitConstFloat(llvm::APFloat(TargetSemantics, 1), E))
2752 return false;
2753 if (!this->emitSubf(getRoundingMode(E), E))
2754 return false;
2755 return this->emitStoreFloat(E);
2756 }
2757 if (!this->emitLoad(*T, E))
2758 return false;
2759 if (!this->emitConst(1, E))
2760 return false;
2761 if (!this->emitSub(*T, E))
2762 return false;
2763 return this->emitStore(*T, E);
2764 }
2765 case UO_LNot: // !x
2766 if (DiscardResult)
2767 return this->discard(SubExpr);
2768
2769 if (!this->visitBool(SubExpr))
2770 return false;
2771
2772 if (!this->emitInvBool(E))
2773 return false;
2774
2775 if (PrimType ET = classifyPrim(E->getType()); ET != PT_Bool)
2776 return this->emitCast(PT_Bool, ET, E);
2777 return true;
2778 case UO_Minus: // -x
2779 if (!this->visit(SubExpr))
2780 return false;
2781 return DiscardResult ? this->emitPop(*T, E) : this->emitNeg(*T, E);
2782 case UO_Plus: // +x
2783 if (!this->visit(SubExpr)) // noop
2784 return false;
2785 return DiscardResult ? this->emitPop(*T, E) : true;
2786 case UO_AddrOf: // &x
2787 // We should already have a pointer when we get here.
2788 return this->delegate(SubExpr);
2789 case UO_Deref: // *x
2790 return dereference(
2791 SubExpr, DerefKind::Read,
2792 [](PrimType) {
2793 llvm_unreachable("Dereferencing requires a pointer");
2794 return false;
2795 },
2796 [this, E](PrimType T) {
2797 return DiscardResult ? this->emitPop(T, E) : true;
2798 });
2799 case UO_Not: // ~x
2800 if (!this->visit(SubExpr))
2801 return false;
2802 return DiscardResult ? this->emitPop(*T, E) : this->emitComp(*T, E);
2803 case UO_Real: // __real x
2804 if (T)
2805 return this->delegate(SubExpr);
2806 return this->emitComplexReal(SubExpr);
2807 case UO_Imag: { // __imag x
2808 if (T) {
2809 if (!this->discard(SubExpr))
2810 return false;
2811 return this->visitZeroInitializer(*T, SubExpr->getType(), SubExpr);
2812 }
2813 if (!this->visit(SubExpr))
2814 return false;
2815 if (!this->emitConstUint8(1, E))
2816 return false;
2817 if (!this->emitArrayElemPtrPopUint8(E))
2818 return false;
2819
2820 // Since our _Complex implementation does not map to a primitive type,
2821 // we sometimes have to do the lvalue-to-rvalue conversion here manually.
2822 if (!SubExpr->isLValue())
2823 return this->emitLoadPop(classifyPrim(E->getType()), E);
2824 return true;
2825 }
2826 case UO_Extension:
2827 return this->delegate(SubExpr);
2828 case UO_Coawait:
2829 assert(false && "Unhandled opcode");
2830 }
2831
2832 return false;
2833 }
2834
2835 template <class Emitter>
VisitDeclRefExpr(const DeclRefExpr * E)2836 bool ByteCodeExprGen<Emitter>::VisitDeclRefExpr(const DeclRefExpr *E) {
2837 if (DiscardResult)
2838 return true;
2839
2840 const auto *D = E->getDecl();
2841
2842 if (const auto *ECD = dyn_cast<EnumConstantDecl>(D)) {
2843 return this->emitConst(ECD->getInitVal(), E);
2844 } else if (const auto *BD = dyn_cast<BindingDecl>(D)) {
2845 return this->visit(BD->getBinding());
2846 } else if (const auto *FuncDecl = dyn_cast<FunctionDecl>(D)) {
2847 const Function *F = getFunction(FuncDecl);
2848 return F && this->emitGetFnPtr(F, E);
2849 }
2850
2851 // References are implemented via pointers, so when we see a DeclRefExpr
2852 // pointing to a reference, we need to get its value directly (i.e. the
2853 // pointer to the actual value) instead of a pointer to the pointer to the
2854 // value.
2855 bool IsReference = D->getType()->isReferenceType();
2856
2857 // Check for local/global variables and parameters.
2858 if (auto It = Locals.find(D); It != Locals.end()) {
2859 const unsigned Offset = It->second.Offset;
2860
2861 if (IsReference)
2862 return this->emitGetLocal(PT_Ptr, Offset, E);
2863 return this->emitGetPtrLocal(Offset, E);
2864 } else if (auto GlobalIndex = P.getGlobal(D)) {
2865 if (IsReference)
2866 return this->emitGetGlobalPtr(*GlobalIndex, E);
2867
2868 return this->emitGetPtrGlobal(*GlobalIndex, E);
2869 } else if (const auto *PVD = dyn_cast<ParmVarDecl>(D)) {
2870 if (auto It = this->Params.find(PVD); It != this->Params.end()) {
2871 if (IsReference || !It->second.IsPtr)
2872 return this->emitGetParamPtr(It->second.Offset, E);
2873
2874 return this->emitGetPtrParam(It->second.Offset, E);
2875 }
2876 }
2877
2878 // Handle lambda captures.
2879 if (auto It = this->LambdaCaptures.find(D);
2880 It != this->LambdaCaptures.end()) {
2881 auto [Offset, IsPtr] = It->second;
2882
2883 if (IsPtr)
2884 return this->emitGetThisFieldPtr(Offset, E);
2885 return this->emitGetPtrThisField(Offset, E);
2886 }
2887
2888 // Lazily visit global declarations we haven't seen yet.
2889 // This happens in C.
2890 if (!Ctx.getLangOpts().CPlusPlus) {
2891 if (const auto *VD = dyn_cast<VarDecl>(D);
2892 VD && VD->hasGlobalStorage() && VD->getAnyInitializer() &&
2893 VD->getType().isConstQualified()) {
2894 if (!this->visitVarDecl(VD))
2895 return false;
2896 // Retry.
2897 return this->VisitDeclRefExpr(E);
2898 }
2899
2900 if (std::optional<unsigned> I = P.getOrCreateDummy(D))
2901 return this->emitGetPtrGlobal(*I, E);
2902 }
2903
2904 return this->emitInvalidDeclRef(E, E);
2905 }
2906
2907 template <class Emitter>
emitCleanup()2908 void ByteCodeExprGen<Emitter>::emitCleanup() {
2909 for (VariableScope<Emitter> *C = VarScope; C; C = C->getParent())
2910 C->emitDestruction();
2911 }
2912
2913 template <class Emitter>
2914 unsigned
collectBaseOffset(const RecordType * BaseType,const RecordType * DerivedType)2915 ByteCodeExprGen<Emitter>::collectBaseOffset(const RecordType *BaseType,
2916 const RecordType *DerivedType) {
2917 const auto *FinalDecl = cast<CXXRecordDecl>(BaseType->getDecl());
2918 const RecordDecl *CurDecl = DerivedType->getDecl();
2919 const Record *CurRecord = getRecord(CurDecl);
2920 assert(CurDecl && FinalDecl);
2921
2922 unsigned OffsetSum = 0;
2923 for (;;) {
2924 assert(CurRecord->getNumBases() > 0);
2925 // One level up
2926 for (const Record::Base &B : CurRecord->bases()) {
2927 const auto *BaseDecl = cast<CXXRecordDecl>(B.Decl);
2928
2929 if (BaseDecl == FinalDecl || BaseDecl->isDerivedFrom(FinalDecl)) {
2930 OffsetSum += B.Offset;
2931 CurRecord = B.R;
2932 CurDecl = BaseDecl;
2933 break;
2934 }
2935 }
2936 if (CurDecl == FinalDecl)
2937 break;
2938 }
2939
2940 assert(OffsetSum > 0);
2941 return OffsetSum;
2942 }
2943
2944 /// Emit casts from a PrimType to another PrimType.
2945 template <class Emitter>
emitPrimCast(PrimType FromT,PrimType ToT,QualType ToQT,const Expr * E)2946 bool ByteCodeExprGen<Emitter>::emitPrimCast(PrimType FromT, PrimType ToT,
2947 QualType ToQT, const Expr *E) {
2948
2949 if (FromT == PT_Float) {
2950 // Floating to floating.
2951 if (ToT == PT_Float) {
2952 const llvm::fltSemantics *ToSem = &Ctx.getFloatSemantics(ToQT);
2953 return this->emitCastFP(ToSem, getRoundingMode(E), E);
2954 }
2955
2956 // Float to integral.
2957 if (isIntegralType(ToT) || ToT == PT_Bool)
2958 return this->emitCastFloatingIntegral(ToT, E);
2959 }
2960
2961 if (isIntegralType(FromT) || FromT == PT_Bool) {
2962 // Integral to integral.
2963 if (isIntegralType(ToT) || ToT == PT_Bool)
2964 return FromT != ToT ? this->emitCast(FromT, ToT, E) : true;
2965
2966 if (ToT == PT_Float) {
2967 // Integral to floating.
2968 const llvm::fltSemantics *ToSem = &Ctx.getFloatSemantics(ToQT);
2969 return this->emitCastIntegralFloating(FromT, ToSem, getRoundingMode(E),
2970 E);
2971 }
2972 }
2973
2974 return false;
2975 }
2976
2977 /// Emits __real(SubExpr)
2978 template <class Emitter>
emitComplexReal(const Expr * SubExpr)2979 bool ByteCodeExprGen<Emitter>::emitComplexReal(const Expr *SubExpr) {
2980 assert(SubExpr->getType()->isAnyComplexType());
2981
2982 if (DiscardResult)
2983 return this->discard(SubExpr);
2984
2985 if (!this->visit(SubExpr))
2986 return false;
2987 if (!this->emitConstUint8(0, SubExpr))
2988 return false;
2989 if (!this->emitArrayElemPtrPopUint8(SubExpr))
2990 return false;
2991
2992 // Since our _Complex implementation does not map to a primitive type,
2993 // we sometimes have to do the lvalue-to-rvalue conversion here manually.
2994 if (!SubExpr->isLValue())
2995 return this->emitLoadPop(*classifyComplexElementType(SubExpr->getType()),
2996 SubExpr);
2997 return true;
2998 }
2999
3000 /// When calling this, we have a pointer of the local-to-destroy
3001 /// on the stack.
3002 /// Emit destruction of record types (or arrays of record types).
3003 template <class Emitter>
emitRecordDestruction(const Descriptor * Desc)3004 bool ByteCodeExprGen<Emitter>::emitRecordDestruction(const Descriptor *Desc) {
3005 assert(Desc);
3006 assert(!Desc->isPrimitive());
3007 assert(!Desc->isPrimitiveArray());
3008
3009 // Arrays.
3010 if (Desc->isArray()) {
3011 const Descriptor *ElemDesc = Desc->ElemDesc;
3012 assert(ElemDesc);
3013
3014 // Don't need to do anything for these.
3015 if (ElemDesc->isPrimitiveArray())
3016 return this->emitPopPtr(SourceInfo{});
3017
3018 // If this is an array of record types, check if we need
3019 // to call the element destructors at all. If not, try
3020 // to save the work.
3021 if (const Record *ElemRecord = ElemDesc->ElemRecord) {
3022 if (const CXXDestructorDecl *Dtor = ElemRecord->getDestructor();
3023 !Dtor || Dtor->isTrivial())
3024 return this->emitPopPtr(SourceInfo{});
3025 }
3026
3027 for (ssize_t I = Desc->getNumElems() - 1; I >= 0; --I) {
3028 if (!this->emitConstUint64(I, SourceInfo{}))
3029 return false;
3030 if (!this->emitArrayElemPtrUint64(SourceInfo{}))
3031 return false;
3032 if (!this->emitRecordDestruction(ElemDesc))
3033 return false;
3034 }
3035 return this->emitPopPtr(SourceInfo{});
3036 }
3037
3038 const Record *R = Desc->ElemRecord;
3039 assert(R);
3040 // First, destroy all fields.
3041 for (const Record::Field &Field : llvm::reverse(R->fields())) {
3042 const Descriptor *D = Field.Desc;
3043 if (!D->isPrimitive() && !D->isPrimitiveArray()) {
3044 if (!this->emitDupPtr(SourceInfo{}))
3045 return false;
3046 if (!this->emitGetPtrField(Field.Offset, SourceInfo{}))
3047 return false;
3048 if (!this->emitRecordDestruction(D))
3049 return false;
3050 }
3051 }
3052
3053 // FIXME: Unions need to be handled differently here. We don't want to
3054 // call the destructor of its members.
3055
3056 // Now emit the destructor and recurse into base classes.
3057 if (const CXXDestructorDecl *Dtor = R->getDestructor();
3058 Dtor && !Dtor->isTrivial()) {
3059 if (const Function *DtorFunc = getFunction(Dtor)) {
3060 assert(DtorFunc->hasThisPointer());
3061 assert(DtorFunc->getNumParams() == 1);
3062 if (!this->emitDupPtr(SourceInfo{}))
3063 return false;
3064 if (!this->emitCall(DtorFunc, SourceInfo{}))
3065 return false;
3066 }
3067 }
3068
3069 for (const Record::Base &Base : llvm::reverse(R->bases())) {
3070 if (!this->emitGetPtrBase(Base.Offset, SourceInfo{}))
3071 return false;
3072 if (!this->emitRecordDestruction(Base.Desc))
3073 return false;
3074 }
3075 // FIXME: Virtual bases.
3076
3077 // Remove the instance pointer.
3078 return this->emitPopPtr(SourceInfo{});
3079 }
3080
3081 namespace clang {
3082 namespace interp {
3083
3084 template class ByteCodeExprGen<ByteCodeEmitter>;
3085 template class ByteCodeExprGen<EvalEmitter>;
3086
3087 } // namespace interp
3088 } // namespace clang
3089