@@ -25,34 +25,6 @@ using APSInt = llvm::APSInt;
2525namespace clang {
2626namespace interp {
2727
28- static bool refersToUnion (const Expr *E) {
29- for (;;) {
30- if (const auto *ME = dyn_cast<MemberExpr>(E)) {
31- if (const auto *FD = dyn_cast<FieldDecl>(ME->getMemberDecl ());
32- FD && FD->getParent ()->isUnion ())
33- return true ;
34- E = ME->getBase ();
35- continue ;
36- }
37-
38- if (const auto *ASE = dyn_cast<ArraySubscriptExpr>(E)) {
39- E = ASE->getBase ()->IgnoreImplicit ();
40- continue ;
41- }
42-
43- if (const auto *ICE = dyn_cast<ImplicitCastExpr>(E);
44- ICE && (ICE->getCastKind () == CK_NoOp ||
45- ICE->getCastKind () == CK_DerivedToBase ||
46- ICE->getCastKind () == CK_UncheckedDerivedToBase)) {
47- E = ICE->getSubExpr ();
48- continue ;
49- }
50-
51- break ;
52- }
53- return false ;
54- }
55-
5628static std::optional<bool > getBoolValue (const Expr *E) {
5729 if (const auto *CE = dyn_cast_if_present<ConstantExpr>(E);
5830 CE && CE->hasAPValueResult () &&
@@ -5401,6 +5373,53 @@ bool Compiler<Emitter>::maybeEmitDeferredVarInit(const VarDecl *VD) {
54015373 return true ;
54025374}
54035375
5376+ static bool hasTrivialDefaultCtorParent (const FieldDecl *FD) {
5377+ assert (FD);
5378+ assert (FD->getParent ()->isUnion ());
5379+ const auto *CXXRD = dyn_cast<CXXRecordDecl>(FD->getParent ());
5380+ return !CXXRD || CXXRD->hasTrivialDefaultConstructor ();
5381+ }
5382+
5383+ template <class Emitter > bool Compiler<Emitter>::refersToUnion(const Expr *E) {
5384+ for (;;) {
5385+ if (const auto *ME = dyn_cast<MemberExpr>(E)) {
5386+ if (const auto *FD = dyn_cast<FieldDecl>(ME->getMemberDecl ());
5387+ FD && FD->getParent ()->isUnion () && hasTrivialDefaultCtorParent (FD))
5388+ return true ;
5389+ E = ME->getBase ();
5390+ continue ;
5391+ }
5392+
5393+ if (const auto *ASE = dyn_cast<ArraySubscriptExpr>(E)) {
5394+ E = ASE->getBase ()->IgnoreImplicit ();
5395+ continue ;
5396+ }
5397+
5398+ if (const auto *ICE = dyn_cast<ImplicitCastExpr>(E);
5399+ ICE && (ICE->getCastKind () == CK_NoOp ||
5400+ ICE->getCastKind () == CK_DerivedToBase ||
5401+ ICE->getCastKind () == CK_UncheckedDerivedToBase)) {
5402+ E = ICE->getSubExpr ();
5403+ continue ;
5404+ }
5405+
5406+ if (const auto *This = dyn_cast<CXXThisExpr>(E)) {
5407+ const auto *ThisRecord =
5408+ This->getType ()->getPointeeType ()->getAsRecordDecl ();
5409+ if (!ThisRecord->isUnion ())
5410+ return false ;
5411+ // Otherwise, always activate if we're in the ctor.
5412+ if (const auto *Ctor =
5413+ dyn_cast_if_present<CXXConstructorDecl>(CompilingFunction))
5414+ return Ctor->getParent () == ThisRecord;
5415+ return false ;
5416+ }
5417+
5418+ break ;
5419+ }
5420+ return false ;
5421+ }
5422+
54045423template <class Emitter >
54055424bool Compiler<Emitter>::visitDeclStmt(const DeclStmt *DS,
54065425 bool EvaluateConditionDecl) {
@@ -5933,16 +5952,15 @@ bool Compiler<Emitter>::compileConstructor(const CXXConstructorDecl *Ctor) {
59335952 return false ;
59345953
59355954 if (OptPrimType T = this ->classify (InitExpr)) {
5955+ if (Activate && !this ->emitActivateThisField (FieldOffset, InitExpr))
5956+ return false ;
5957+
59365958 if (!this ->visit (InitExpr))
59375959 return false ;
59385960
59395961 bool BitField = F->isBitField ();
5940- if (BitField && Activate)
5941- return this ->emitInitThisBitFieldActivate (*T, F, FieldOffset, InitExpr);
59425962 if (BitField)
59435963 return this ->emitInitThisBitField (*T, F, FieldOffset, InitExpr);
5944- if (Activate)
5945- return this ->emitInitThisFieldActivate (*T, FieldOffset, InitExpr);
59465964 return this ->emitInitThisField (*T, FieldOffset, InitExpr);
59475965 }
59485966 // Non-primitive case. Get a pointer to the field-to-initialize
0 commit comments