@@ -334,6 +334,19 @@ class ItaniumCXXABI : public CodeGen::CGCXXABI {
334334 ArrayRef<llvm::Function *> CXXThreadLocalInits,
335335 ArrayRef<const VarDecl *> CXXThreadLocalInitVars) override ;
336336
337+ bool mayNeedDestruction (const VarDecl *VD) const {
338+ if (VD->needsDestruction (getContext ()))
339+ return true ;
340+
341+ // If the variable has an incomplete class type (or array thereof), it
342+ // might need destruction.
343+ const Type *T = VD->getType ()->getBaseElementTypeUnsafe ();
344+ if (T->getAs <RecordType>() && T->isIncompleteType ())
345+ return true ;
346+
347+ return false ;
348+ }
349+
337350 // / Determine whether we will definitely emit this variable with a constant
338351 // / initializer, either because the language semantics demand it or because
339352 // / we know that the initializer is a constant.
@@ -364,7 +377,7 @@ class ItaniumCXXABI : public CodeGen::CGCXXABI {
364377 // If we have the only definition, we don't need a thread wrapper if we
365378 // will emit the value as a constant.
366379 if (isUniqueGVALinkage (getContext ().GetGVALinkageForVariable (VD)))
367- return !VD-> needsDestruction ( getContext () ) && InitDecl->evaluateValue ();
380+ return !mayNeedDestruction (VD ) && InitDecl->evaluateValue ();
368381
369382 // Otherwise, we need a thread wrapper unless we know that every
370383 // translation unit will emit the value as a constant. We rely on the
@@ -376,7 +389,7 @@ class ItaniumCXXABI : public CodeGen::CGCXXABI {
376389
377390 bool usesThreadWrapperFunction (const VarDecl *VD) const override {
378391 return !isEmittedWithConstantInitializer (VD) ||
379- VD-> needsDestruction ( getContext () );
392+ mayNeedDestruction (VD );
380393 }
381394 LValue EmitThreadLocalVarDeclLValue (CodeGenFunction &CGF, const VarDecl *VD,
382395 QualType LValType) override ;
@@ -2963,7 +2976,7 @@ void ItaniumCXXABI::EmitThreadLocalInitFuncs(
29632976 // also when the symbol is weak.
29642977 if (CGM.getTriple ().isOSAIX () && VD->hasDefinition () &&
29652978 isEmittedWithConstantInitializer (VD, true ) &&
2966- !VD-> needsDestruction ( getContext () )) {
2979+ !mayNeedDestruction (VD )) {
29672980 // Init should be null. If it were non-null, then the logic above would
29682981 // either be defining the function to be an alias or declaring the
29692982 // function with the expectation that the definition of the variable
0 commit comments