@@ -1985,7 +1985,7 @@ llvm::Value *CodeGenFunction::EmitLoadOfScalar(Address Addr, bool Volatile,
19851985
19861986 if (const auto *ClangVecTy = Ty->getAs <VectorType>()) {
19871987 // Boolean vectors use `iN` as storage type.
1988- if (ClangVecTy->isExtVectorBoolType ( )) {
1988+ if (ClangVecTy->isPackedVectorBoolType ( getContext () )) {
19891989 llvm::Type *ValTy = ConvertType (Ty);
19901990 unsigned ValNumElems =
19911991 cast<llvm::FixedVectorType>(ValTy)->getNumElements ();
@@ -2064,6 +2064,10 @@ llvm::Value *CodeGenFunction::EmitToMemory(llvm::Value *Value, QualType Ty) {
20642064
20652065 if (Ty->isExtVectorBoolType ()) {
20662066 llvm::Type *StoreTy = convertTypeForLoadStore (Ty, Value->getType ());
2067+ if (StoreTy->isVectorTy () && StoreTy->getScalarSizeInBits () >
2068+ Value->getType ()->getScalarSizeInBits ())
2069+ return Builder.CreateZExt (Value, StoreTy);
2070+
20672071 // Expand to the memory bit width.
20682072 unsigned MemNumElems = StoreTy->getPrimitiveSizeInBits ();
20692073 // <N x i1> --> <P x i1>.
@@ -2079,8 +2083,9 @@ llvm::Value *CodeGenFunction::EmitToMemory(llvm::Value *Value, QualType Ty) {
20792083// / by convertTypeForLoadStore) to its primary IR type (as returned
20802084// / by ConvertType).
20812085llvm::Value *CodeGenFunction::EmitFromMemory (llvm::Value *Value, QualType Ty) {
2082- if (Ty->isExtVectorBoolType ( )) {
2086+ if (Ty->isPackedVectorBoolType ( getContext () )) {
20832087 const auto *RawIntTy = Value->getType ();
2088+
20842089 // Bitcast iP --> <P x i1>.
20852090 auto *PaddedVecTy = llvm::FixedVectorType::get (
20862091 Builder.getInt1Ty (), RawIntTy->getPrimitiveSizeInBits ());
@@ -2091,10 +2096,10 @@ llvm::Value *CodeGenFunction::EmitFromMemory(llvm::Value *Value, QualType Ty) {
20912096 return emitBoolVecConversion (V, ValNumElems, " extractvec" );
20922097 }
20932098
2094- if (hasBooleanRepresentation (Ty) || Ty->isBitIntType ()) {
2095- llvm::Type *ResTy = ConvertType (Ty);
2099+ llvm::Type *ResTy = ConvertType (Ty);
2100+ if (hasBooleanRepresentation (Ty) || Ty->isBitIntType () ||
2101+ Ty->isExtVectorBoolType ())
20962102 return Builder.CreateTrunc (Value, ResTy, " loadedv" );
2097- }
20982103
20992104 return Value;
21002105}
@@ -2152,7 +2157,8 @@ void CodeGenFunction::EmitStoreOfScalar(llvm::Value *Value, Address Addr,
21522157 if (auto *VecTy = dyn_cast<llvm::FixedVectorType>(SrcTy)) {
21532158 auto *NewVecTy =
21542159 CGM.getABIInfo ().getOptimalVectorMemoryType (VecTy, getLangOpts ());
2155- if (!ClangVecTy->isExtVectorBoolType () && VecTy != NewVecTy) {
2160+ if (!ClangVecTy->isPackedVectorBoolType (getContext ()) &&
2161+ VecTy != NewVecTy) {
21562162 SmallVector<int , 16 > Mask (NewVecTy->getNumElements (), -1 );
21572163 std::iota (Mask.begin (), Mask.begin () + VecTy->getNumElements (), 0 );
21582164 Value = Builder.CreateShuffleVector (Value, Mask, " extractVec" );
@@ -2343,7 +2349,15 @@ RValue CodeGenFunction::EmitLoadOfExtVectorElementLValue(LValue LV) {
23432349 if (!ExprVT) {
23442350 unsigned InIdx = getAccessedFieldNo (0 , Elts);
23452351 llvm::Value *Elt = llvm::ConstantInt::get (SizeTy, InIdx);
2346- return RValue::get (Builder.CreateExtractElement (Vec, Elt));
2352+
2353+ llvm::Value *Element = Builder.CreateExtractElement (Vec, Elt);
2354+
2355+ llvm::Type *LVTy = ConvertType (LV.getType ());
2356+ if (Element->getType ()->getPrimitiveSizeInBits () >
2357+ LVTy->getPrimitiveSizeInBits ())
2358+ Element = Builder.CreateTrunc (Element, LVTy);
2359+
2360+ return RValue::get (Element);
23472361 }
23482362
23492363 // Always use shuffle vector to try to retain the original program structure
@@ -2354,6 +2368,10 @@ RValue CodeGenFunction::EmitLoadOfExtVectorElementLValue(LValue LV) {
23542368 Mask.push_back (getAccessedFieldNo (i, Elts));
23552369
23562370 Vec = Builder.CreateShuffleVector (Vec, Mask);
2371+
2372+ if (LV.getType ()->isExtVectorBoolType ())
2373+ Vec = Builder.CreateTrunc (Vec, ConvertType (LV.getType ()), " truncv" );
2374+
23572375 return RValue::get (Vec);
23582376}
23592377
@@ -2407,26 +2425,35 @@ void CodeGenFunction::EmitStoreThroughLValue(RValue Src, LValue Dst,
24072425 // Read/modify/write the vector, inserting the new element.
24082426 llvm::Value *Vec = Builder.CreateLoad (Dst.getVectorAddress (),
24092427 Dst.isVolatileQualified ());
2428+ llvm::Type *VecTy = Vec->getType ();
2429+ llvm::Value *SrcVal = Src.getScalarVal ();
2430+
2431+ if (SrcVal->getType ()->getPrimitiveSizeInBits () <
2432+ VecTy->getScalarSizeInBits ())
2433+ SrcVal = Builder.CreateZExt (SrcVal, VecTy->getScalarType ());
2434+
24102435 auto *IRStoreTy = dyn_cast<llvm::IntegerType>(Vec->getType ());
24112436 if (IRStoreTy) {
24122437 auto *IRVecTy = llvm::FixedVectorType::get (
24132438 Builder.getInt1Ty (), IRStoreTy->getPrimitiveSizeInBits ());
24142439 Vec = Builder.CreateBitCast (Vec, IRVecTy);
24152440 // iN --> <N x i1>.
24162441 }
2417- llvm::Value *SrcVal = Src. getScalarVal ();
2442+
24182443 // Allow inserting `<1 x T>` into an `<N x T>`. It can happen with scalar
24192444 // types which are mapped to vector LLVM IR types (e.g. for implementing
24202445 // an ABI).
24212446 if (auto *EltTy = dyn_cast<llvm::FixedVectorType>(SrcVal->getType ());
24222447 EltTy && EltTy->getNumElements () == 1 )
24232448 SrcVal = Builder.CreateBitCast (SrcVal, EltTy->getElementType ());
2449+
24242450 Vec = Builder.CreateInsertElement (Vec, SrcVal, Dst.getVectorIdx (),
24252451 " vecins" );
24262452 if (IRStoreTy) {
24272453 // <N x i1> --> <iN>.
24282454 Vec = Builder.CreateBitCast (Vec, IRStoreTy);
24292455 }
2456+
24302457 Builder.CreateStore (Vec, Dst.getVectorAddress (),
24312458 Dst.isVolatileQualified ());
24322459 return ;
@@ -2623,14 +2650,12 @@ void CodeGenFunction::EmitStoreThroughExtVectorComponentLValue(RValue Src,
26232650 // This access turns into a read/modify/write of the vector. Load the input
26242651 // value now.
26252652 llvm::Value *Vec = Builder.CreateLoad (DstAddr, Dst.isVolatileQualified ());
2653+ llvm::Type *VecTy = Vec->getType ();
26262654 const llvm::Constant *Elts = Dst.getExtVectorElts ();
26272655
2628- llvm::Value *SrcVal = Src.getScalarVal ();
2629-
26302656 if (const VectorType *VTy = Dst.getType ()->getAs <VectorType>()) {
26312657 unsigned NumSrcElts = VTy->getNumElements ();
2632- unsigned NumDstElts =
2633- cast<llvm::FixedVectorType>(Vec->getType ())->getNumElements ();
2658+ unsigned NumDstElts = cast<llvm::FixedVectorType>(VecTy)->getNumElements ();
26342659 if (NumDstElts == NumSrcElts) {
26352660 // Use shuffle vector is the src and destination are the same number of
26362661 // elements and restore the vector mask since it is on the side it will be
@@ -2639,6 +2664,11 @@ void CodeGenFunction::EmitStoreThroughExtVectorComponentLValue(RValue Src,
26392664 for (unsigned i = 0 ; i != NumSrcElts; ++i)
26402665 Mask[getAccessedFieldNo (i, Elts)] = i;
26412666
2667+ llvm::Value *SrcVal = Src.getScalarVal ();
2668+ if (VecTy->getScalarSizeInBits () >
2669+ SrcVal->getType ()->getScalarSizeInBits ())
2670+ SrcVal = Builder.CreateZExt (SrcVal, VecTy);
2671+
26422672 Vec = Builder.CreateShuffleVector (SrcVal, Mask);
26432673 } else if (NumDstElts > NumSrcElts) {
26442674 // Extended the source vector to the same length and then shuffle it
@@ -2649,7 +2679,8 @@ void CodeGenFunction::EmitStoreThroughExtVectorComponentLValue(RValue Src,
26492679 for (unsigned i = 0 ; i != NumSrcElts; ++i)
26502680 ExtMask.push_back (i);
26512681 ExtMask.resize (NumDstElts, -1 );
2652- llvm::Value *ExtSrcVal = Builder.CreateShuffleVector (SrcVal, ExtMask);
2682+ llvm::Value *ExtSrcVal =
2683+ Builder.CreateShuffleVector (Src.getScalarVal (), ExtMask);
26532684 // build identity
26542685 SmallVector<int , 4 > Mask;
26552686 for (unsigned i = 0 ; i != NumDstElts; ++i)
@@ -2674,6 +2705,11 @@ void CodeGenFunction::EmitStoreThroughExtVectorComponentLValue(RValue Src,
26742705 // be updating one element.
26752706 unsigned InIdx = getAccessedFieldNo (0 , Elts);
26762707 llvm::Value *Elt = llvm::ConstantInt::get (SizeTy, InIdx);
2708+
2709+ llvm::Value *SrcVal = Src.getScalarVal ();
2710+ if (VecTy->getScalarSizeInBits () > SrcVal->getType ()->getScalarSizeInBits ())
2711+ SrcVal = Builder.CreateZExt (SrcVal, VecTy->getScalarType ());
2712+
26772713 Vec = Builder.CreateInsertElement (Vec, SrcVal, Elt);
26782714 }
26792715
@@ -4701,9 +4737,13 @@ EmitExtVectorElementExpr(const ExtVectorElementExpr *E) {
47014737
47024738 // Store the vector to memory (because LValue wants an address).
47034739 Address VecMem = CreateMemTemp (E->getBase ()->getType ());
4740+ // need to zero extend an hlsl boolean vector to store it back to memory
4741+ QualType Ty = E->getBase ()->getType ();
4742+ llvm::Type *LTy = convertTypeForLoadStore (Ty, Vec->getType ());
4743+ if (LTy->getScalarSizeInBits () > Vec->getType ()->getScalarSizeInBits ())
4744+ Vec = Builder.CreateZExt (Vec, LTy);
47044745 Builder.CreateStore (Vec, VecMem);
4705- Base = MakeAddrLValue (VecMem, E->getBase ()->getType (),
4706- AlignmentSource::Decl);
4746+ Base = MakeAddrLValue (VecMem, Ty, AlignmentSource::Decl);
47074747 }
47084748
47094749 QualType type =
0 commit comments