diff --git a/clang/include/clang/Basic/OpenMPKinds.h b/clang/include/clang/Basic/OpenMPKinds.h index f40db4c13c55a..e37887e8b86ba 100644 --- a/clang/include/clang/Basic/OpenMPKinds.h +++ b/clang/include/clang/Basic/OpenMPKinds.h @@ -301,6 +301,14 @@ bool isOpenMPTargetExecutionDirective(OpenMPDirectiveKind DKind); /// otherwise - false. bool isOpenMPTargetDataManagementDirective(OpenMPDirectiveKind DKind); +/// Checks if the specified directive is a map-entering target directive. +/// \param DKind Specified directive. +/// \return true - the directive is a map-entering target directive like +/// 'omp target', 'omp target data', 'omp target enter data', +/// 'omp target parallel', etc. (excludes 'omp target exit data', 'omp target +/// update') otherwise - false. +bool isOpenMPTargetMapEnteringDirective(OpenMPDirectiveKind DKind); + /// Checks if the specified composite/combined directive constitutes a teams /// directive in the outermost nest. For example /// 'omp teams distribute' or 'omp teams distribute parallel for'. diff --git a/clang/lib/Basic/OpenMPKinds.cpp b/clang/lib/Basic/OpenMPKinds.cpp index d3d393bd09396..8a8ede203361b 100644 --- a/clang/lib/Basic/OpenMPKinds.cpp +++ b/clang/lib/Basic/OpenMPKinds.cpp @@ -650,6 +650,11 @@ bool clang::isOpenMPTargetDataManagementDirective(OpenMPDirectiveKind DKind) { DKind == OMPD_target_exit_data || DKind == OMPD_target_update; } +bool clang::isOpenMPTargetMapEnteringDirective(OpenMPDirectiveKind DKind) { + return DKind == OMPD_target_data || DKind == OMPD_target_enter_data || + isOpenMPTargetExecutionDirective(DKind); +} + bool clang::isOpenMPNestingTeamsDirective(OpenMPDirectiveKind DKind) { if (DKind == OMPD_teams) return true; diff --git a/clang/lib/CodeGen/CGOpenMPRuntime.cpp b/clang/lib/CodeGen/CGOpenMPRuntime.cpp index 28818d5ac0568..245a48d1ec6c0 100644 --- a/clang/lib/CodeGen/CGOpenMPRuntime.cpp +++ b/clang/lib/CodeGen/CGOpenMPRuntime.cpp @@ -6839,6 +6839,11 @@ class MappableExprsHandler { Address LB = Address::invalid(); bool IsArraySection = false; bool HasCompleteRecord = false; + // ATTACH information for delayed processing + Address AttachPtrAddr = Address::invalid(); + Address AttachPteeAddr = Address::invalid(); + const ValueDecl *AttachPtrDecl = nullptr; + const Expr *AttachMapExpr = nullptr; }; private: @@ -7080,6 +7085,34 @@ class MappableExprsHandler { return ConstLength.getSExtValue() != 1; } + /// Utility function to add an ATTACH entry to the CombinedInfo structure. + /// Generates an ATTACH entry: &pointer, &pointer[idx], sizeof(pointer), + /// ATTACH + void addAttachEntry(CodeGenFunction &CGF, MapCombinedInfoTy &CombinedInfo, + Address AttachBaseAddr, Address AttachFirstElemAddr, + const ValueDecl *BaseDecl, const Expr *MapExpr) const { + + // Size is the size of the pointer itself - use pointer size, not BaseDecl + // size + llvm::Value *PointerSize = CGF.Builder.CreateIntCast( + llvm::ConstantInt::get( + CGF.CGM.SizeTy, + CGF.getContext().getTypeSize( + CGF.getContext().getPointerType(CGF.getContext().VoidTy)) / + 8), + CGF.Int64Ty, /*isSigned=*/true); + + CombinedInfo.Exprs.emplace_back(BaseDecl, MapExpr); + CombinedInfo.BasePointers.push_back(AttachBaseAddr.emitRawPointer(CGF)); + CombinedInfo.DevicePtrDecls.push_back(nullptr); + CombinedInfo.DevicePointers.push_back(DeviceInfoTy::None); + CombinedInfo.Pointers.push_back(AttachFirstElemAddr.emitRawPointer(CGF)); + CombinedInfo.Sizes.push_back(PointerSize); + CombinedInfo.Types.push_back(OpenMPOffloadMappingFlags::OMP_MAP_ATTACH); + CombinedInfo.Mappers.push_back(nullptr); + CombinedInfo.NonContigInfo.Dims.push_back(1); + } + /// Generate the base pointers, section pointers, sizes, map type bits, and /// user-defined mappers (all included in \a CombinedInfo) for the provided /// map type, map or motion modifiers, and expression components. @@ -7096,8 +7129,8 @@ class MappableExprsHandler { const ValueDecl *Mapper = nullptr, bool ForDeviceAddr = false, const ValueDecl *BaseDecl = nullptr, const Expr *MapExpr = nullptr, ArrayRef - OverlappedElements = {}, - bool AreBothBasePtrAndPteeMapped = false) const { + OverlappedElements = {}) const { + // The following summarizes what has to be generated for each map and the // types below. The generated information is expressed in this order: // base pointer, section pointer, size, flags @@ -7136,9 +7169,12 @@ class MappableExprsHandler { // &p, &p, sizeof(float*), TARGET_PARAM | TO | FROM // // map(p[1:24]) - // &p, &p[1], 24*sizeof(float), TARGET_PARAM | TO | FROM | PTR_AND_OBJ - // in unified shared memory mode or for local pointers // p, &p[1], 24*sizeof(float), TARGET_PARAM | TO | FROM + // &p, &p[1], sizeof(p), ATTACH + // + // map((22])p) + // p, p, 22*sizeof(float), TARGET_PARAM | TO | FROM + // &p, p, sizeof(float*), ATTACH // // map((*a)[0:3]) // &(*a), &(*a), sizeof(pointer), TARGET_PARAM | TO | FROM @@ -7208,12 +7244,15 @@ class MappableExprsHandler { // // map(ps->i) // ps, &(ps->i), sizeof(int), TARGET_PARAM | TO | FROM + // &ps, &(ps->i), sizeof(ps), ATTACH // // map(ps->s.f) // ps, &(ps->s.f[0]), 50*sizeof(float), TARGET_PARAM | TO | FROM + // &ps, &(ps->s.f[0]), sizeof(ps), ATTACH // // map(from: ps->p) // ps, &(ps->p), sizeof(double*), TARGET_PARAM | FROM + // &ps, &(ps->p), sizeof(ps), ATTACH // // map(to: ps->p[:22]) // ps, &(ps->p), sizeof(double*), TARGET_PARAM @@ -7222,6 +7261,7 @@ class MappableExprsHandler { // // map(ps->ps) // ps, &(ps->ps), sizeof(S2*), TARGET_PARAM | TO | FROM + // &ps, &(ps->ps), sizeof(ps), ATTACH // // map(from: ps->ps->s.i) // ps, &(ps->ps), sizeof(S2*), TARGET_PARAM @@ -7275,14 +7315,9 @@ class MappableExprsHandler { // of arguments, hence MEMBER_OF(4) // // map(p, p[:100]) - // For "pragma omp target": - // &p, &p, sizeof(p), TARGET_PARAM | TO | FROM - // &p, &p[0], 100*sizeof(float), PTR_AND_OBJ | TO | FROM (*) - // Otherwise: - // ===> map(p[:100]) - // &p, &p[0], 100*sizeof(float), TARGET_PARAM | PTR_AND_OBJ | TO | FROM - // (*) We need to use PTR_AND_OBJ here to ensure that the mapped copies of - // p and p[0] get attached. + // &p, &p, sizeof(float*), TARGET_PARAM | TO | FROM + // &p[0], &p[0], 100*sizeof(float), TO | FROM + // &p, &p[0], sizeof(float*), ATTACH // Track if the map information being generated is the first for a capture. bool IsCaptureFirstInfo = IsFirstComponentList; @@ -7300,25 +7335,15 @@ class MappableExprsHandler { // components. bool IsExpressionFirstInfo = true; bool FirstPointerInComplexData = false; - bool SkipStandalonePtrMapping = false; Address BP = Address::invalid(); + Address FinalLowestElem = Address::invalid(); const Expr *AssocExpr = I->getAssociatedExpression(); const auto *AE = dyn_cast(AssocExpr); const auto *OASE = dyn_cast(AssocExpr); const auto *OAShE = dyn_cast(AssocExpr); - // For map(p, p[0]) on a "target" construct, we need to map "p" by itself - // as it has to be passed by-reference as the kernel argument. - // For other constructs, we can skip mapping "p" because the PTR_AND_OBJ - // mapping for map(p[0]) will take care of mapping p as well. - SkipStandalonePtrMapping = - AreBothBasePtrAndPteeMapped && - (!isa(CurDir) || - !isOpenMPTargetExecutionDirective( - cast(CurDir)->getDirectiveKind())); - - if (SkipStandalonePtrMapping && std::next(I) == CE) - return; + // Find the pointer-attachment base-pointer for the given list, if any. + const Expr *AttachPtrExpr = findAttachPtrExpr(Components); if (isa(AssocExpr)) { // The base is the 'this' pointer. The content of the pointer is going @@ -7362,9 +7387,10 @@ class MappableExprsHandler { // can be associated with the combined storage if shared memory mode is // active or the base declaration is not global variable. const auto *VD = dyn_cast(I->getAssociatedDeclaration()); - if (!AreBothBasePtrAndPteeMapped && - (CGF.CGM.getOpenMPRuntime().hasRequiresUnifiedSharedMemory() || - !VD || VD->hasLocalStorage())) + if (CGF.CGM.getOpenMPRuntime().hasRequiresUnifiedSharedMemory() || + !VD || VD->hasLocalStorage() || + (isa_and_nonnull(AttachPtrExpr) && + VD == cast(AttachPtrExpr)->getDecl())) BP = CGF.EmitLoadOfPointer(BP, Ty->castAs()); else FirstPointerInComplexData = true; @@ -7548,6 +7574,11 @@ class MappableExprsHandler { .getAddress(); } + // Save the final LowestElem, to use it as the pointee in attach maps, + // if emitted. + if (Next == CE) + FinalLowestElem = LowestElem; + // If this component is a pointer inside the base struct then we don't // need to create any entry for it - it will be combined with the object // it is pointing to into a single PTR_AND_OBJ entry. @@ -7691,13 +7722,11 @@ class MappableExprsHandler { // same expression except for the first one. We also need to signal // this map is the first one that relates with the current capture // (there is a set of entries for each capture). - OpenMPOffloadMappingFlags Flags = - getMapTypeBits(MapType, MapModifiers, MotionModifiers, IsImplicit, - !IsExpressionFirstInfo || RequiresReference || - FirstPointerInComplexData || IsMemberReference, - SkipStandalonePtrMapping || - (IsCaptureFirstInfo && !RequiresReference), - IsNonContiguous); + OpenMPOffloadMappingFlags Flags = getMapTypeBits( + MapType, MapModifiers, MotionModifiers, IsImplicit, + !IsExpressionFirstInfo || RequiresReference || + FirstPointerInComplexData || IsMemberReference, + IsCaptureFirstInfo && !RequiresReference, IsNonContiguous); if (!IsExpressionFirstInfo || IsMemberReference) { // If we have a PTR_AND_OBJ pair where the OBJ is a pointer as well, @@ -7789,6 +7818,31 @@ class MappableExprsHandler { if (!EncounteredME) PartialStruct.HasCompleteRecord = true; + // Add ATTACH entries for pointer-attachment: delay if PartialStruct is + // being populated, otherwise add immediately. + if (shouldEmitAttachEntry(AttachPtrExpr, BaseDecl, CGF, CurDir)) { + Address AttachPtrAddr = CGF.EmitLValue(AttachPtrExpr).getAddress(); + Address AttachPteeAddr = FinalLowestElem; + + assert(AttachPtrAddr.isValid() && "Attach ptr address is not valid."); + assert(AttachPteeAddr.isValid() && "Attach ptee address is not valid."); + + if (PartialStruct.Base.isValid()) { + // We're populating PartialStruct, delay ATTACH entry addition until + // after emitCombinedEntry. + PartialStruct.AttachPtrAddr = AttachPtrAddr; + PartialStruct.AttachPteeAddr = AttachPteeAddr; + PartialStruct.AttachPtrDecl = BaseDecl; + PartialStruct.AttachMapExpr = MapExpr; + } else if (IsMappingWholeStruct) { + addAttachEntry(CGF, StructBaseCombinedInfo, AttachPtrAddr, + AttachPteeAddr, BaseDecl, MapExpr); + } else { + addAttachEntry(CGF, CombinedInfo, AttachPtrAddr, AttachPteeAddr, + BaseDecl, MapExpr); + } + } + if (!IsNonContiguous) return; @@ -8062,6 +8116,98 @@ class MappableExprsHandler { } } + /// Returns whether an attach entry should be emitted for a map on + /// \p MapBaseDecl on the directive \p CurDir. + static bool + shouldEmitAttachEntry(const Expr *PointerExpr, const ValueDecl *MapBaseDecl, + CodeGenFunction &CGF, + llvm::PointerUnion + CurDir) { + if (!PointerExpr) + return false; + + // Pointer attachment is needed at map-entering time or for declare + // mappers. + if (!isa(CurDir) && + !isOpenMPTargetMapEnteringDirective( + cast(CurDir)->getDirectiveKind())) + return false; + + const auto *DRE = dyn_cast(PointerExpr); + const VarDecl *PointerDecl = + !DRE ? nullptr : dyn_cast_if_present(DRE->getDecl()); + + // For now, we are emitting ATTACH entries only when the + // "attach-base-pointer" is a vardecl that matches the base var of the map. + if (!PointerDecl || PointerDecl != MapBaseDecl) + return false; + + return true; + } + + // Traverse the list of Components to find the first pointer expression, which + // should be the attachable-base-pointer for the current component-list. + // For example, for: + // `map(pp->p->s.a[0])`, the base-pointer is `pp->p`, while the pointee is + // `pp->p->s.a[0]`. + static const Expr *findAttachPtrExpr( + OMPClauseMappableExprCommon::MappableExprComponentListRef Components) { + + const auto *Begin = Components.begin(); + const auto *End = Components.end(); + + // Keep stripping away one component at a time, until we reach a pointer. + // The first pointer we encounter should be the base-pointer for + // pointer-attachment. + for (const auto *I = Begin; I != End; ++I) { + const Expr *CurrentExpr = I->getAssociatedExpression(); + if (!CurrentExpr) + break; + + const auto *NextI = std::next(I); + if (NextI == End) + break; + + QualType NextType; + if (const auto *NextDecl = NextI->getAssociatedDeclaration()) { + NextType = NextDecl->getType().getNonReferenceType().getCanonicalType(); + } else if (const auto *NextExpr = NextI->getAssociatedExpression()) { + // If NextExpr is an array-section, compute the result type using + // getBaseOriginalType + if (const auto *OASE = dyn_cast(NextExpr)) { + // Get the original base type, handling chains of array sections + // properly + QualType BaseType = + ArraySectionExpr::getBaseOriginalType(OASE->getBase()); + if (const auto *ATy = BaseType->getAsArrayTypeUnsafe()) + NextType = ATy->getElementType(); + else + NextType = BaseType->getPointeeType(); + + NextType = NextType.getNonReferenceType().getCanonicalType(); + } else { + NextType = + NextExpr->getType().getNonReferenceType().getCanonicalType(); + } + } else { + break; + } + + // Stop if the next component is a pointer type - this means we found + // the base-pointer + if (!NextType->isPointerType()) + continue; + + // The Next component is the first pointer expression encountered, so + // that is the attachable-base-pointer for the current component-list. + const Expr *BasePtrExpr = NextI->getAssociatedExpression(); + return BasePtrExpr; + } + + return nullptr; + } + /// Generate all the base pointers, section pointers, sizes, map types, and /// mappers for the extracted mappable expressions (all included in \a /// CombinedInfo). Also, for each item that relates with a device pointer, a @@ -8235,8 +8381,9 @@ class MappableExprsHandler { // returned and move on to the next declaration. Exclude cases where // the base pointer is mapped as array subscript, array section or // array shaping. The base address is passed as a pointer to base in - // this case and cannot be used as a base for use_device_ptr list - // item. + // this case (i.e. as a PTR_AND_OBJ) and cannot be used as a base + // for use_device_ptr list item. However, we don't use PTR_AND_OBJ + // mapping for any pointers when using ATTACH-style mapping. if (CI != Data.end()) { if (IsDevAddr) { CI->ForDeviceAddr = IsDevAddr; @@ -8246,12 +8393,15 @@ class MappableExprsHandler { } else { auto PrevCI = std::next(CI->Components.rbegin()); const auto *VarD = dyn_cast(VD); + const Expr *AttachPtrExpr = findAttachPtrExpr(CI->Components); if (CGF.CGM.getOpenMPRuntime().hasRequiresUnifiedSharedMemory() || isa(IE) || !VD->getType().getNonReferenceType()->isPointerType() || PrevCI == CI->Components.rend() || isa(PrevCI->getAssociatedExpression()) || !VarD || - VarD->hasLocalStorage()) { + VarD->hasLocalStorage() || + (isa_and_nonnull(AttachPtrExpr) && + VD == cast(AttachPtrExpr)->getDecl())) { CI->ForDeviceAddr = IsDevAddr; CI->ReturnDevicePointer = true; Found = true; @@ -8320,21 +8470,6 @@ class MappableExprsHandler { MapCombinedInfoTy StructBaseCurInfo; const Decl *D = Data.first; const ValueDecl *VD = cast_or_null(D); - bool HasMapBasePtr = false; - bool HasMapArraySec = false; - if (VD && VD->getType()->isAnyPointerType()) { - for (const auto &M : Data.second) { - HasMapBasePtr = any_of(M, [](const MapInfo &L) { - return isa_and_present(L.VarRef); - }); - HasMapArraySec = any_of(M, [](const MapInfo &L) { - return isa_and_present( - L.VarRef); - }); - if (HasMapBasePtr && HasMapArraySec) - break; - } - } for (const auto &M : Data.second) { for (const MapInfo &L : M) { assert(!L.Components.empty() && @@ -8351,8 +8486,7 @@ class MappableExprsHandler { CurInfo, StructBaseCurInfo, PartialStruct, /*IsFirstComponentList=*/false, L.IsImplicit, /*GenerateAllInfoForClauses*/ true, L.Mapper, L.ForDeviceAddr, VD, - L.VarRef, /*OverlappedElements*/ {}, - HasMapBasePtr && HasMapArraySec); + L.VarRef, /*OverlappedElements*/ {}); // If this entry relates to a device pointer, set the relevant // declaration and add the 'return pointer' flag. @@ -8447,15 +8581,20 @@ class MappableExprsHandler { // If there is an entry in PartialStruct it means we have a struct with // individual members mapped. Emit an extra combined entry. + MapCombinedInfoTy AttachCombinedInfo; if (PartialStruct.Base.isValid()) { UnionCurInfo.NonContigInfo.Dims.push_back(0); // Emit a combined entry: - emitCombinedEntry(CombinedInfo, UnionCurInfo.Types, PartialStruct, - /*IsMapThis*/ !VD, OMPBuilder, VD); + emitCombinedEntry(CombinedInfo, AttachCombinedInfo, UnionCurInfo.Types, + PartialStruct, + /*IsMapThis*/ !VD, OMPBuilder, VD, + /*OffsetForMemberOfFlag=*/0, /*NotTargetParam=*/true); } // We need to append the results of this capture to what we already have. CombinedInfo.append(UnionCurInfo); + // Append AttachCombinedInfo after UnionCurInfo + CombinedInfo.append(AttachCombinedInfo); } // Append data for use_device_ptr clauses. CombinedInfo.append(UseDeviceDataCombinedInfo); @@ -8514,18 +8653,29 @@ class MappableExprsHandler { /// Generate code for the combined entry if we have a partially mapped struct /// and take care of the mapping flags of the arguments corresponding to /// individual struct members. + /// AttachCombinedInfo will be populated with ATTACH entries if + /// \p PartialStruct contains attach base-pointer information. void emitCombinedEntry(MapCombinedInfoTy &CombinedInfo, + MapCombinedInfoTy &AttachCombinedInfo, MapFlagsArrayTy &CurTypes, const StructRangeInfoTy &PartialStruct, bool IsMapThis, - llvm::OpenMPIRBuilder &OMPBuilder, - const ValueDecl *VD = nullptr, - unsigned OffsetForMemberOfFlag = 0, - bool NotTargetParams = true) const { + llvm::OpenMPIRBuilder &OMPBuilder, const ValueDecl *VD, + unsigned OffsetForMemberOfFlag, + bool NotTargetParams) const { if (CurTypes.size() == 1 && ((CurTypes.back() & OpenMPOffloadMappingFlags::OMP_MAP_MEMBER_OF) != OpenMPOffloadMappingFlags::OMP_MAP_MEMBER_OF) && - !PartialStruct.IsArraySection) + !PartialStruct.IsArraySection) { + // Even if we are not creating a combined-entry, we need to process any + // previously delayed ATTACH entries. + if (PartialStruct.AttachPtrAddr.isValid() && + PartialStruct.AttachPteeAddr.isValid()) + addAttachEntry(CGF, AttachCombinedInfo, PartialStruct.AttachPtrAddr, + PartialStruct.AttachPteeAddr, + PartialStruct.AttachPtrDecl, + PartialStruct.AttachMapExpr); return; + } Address LBAddr = PartialStruct.LowestElem.second; Address HBAddr = PartialStruct.HighestElem.second; if (PartialStruct.HasCompleteRecord) { @@ -8606,11 +8756,25 @@ class MappableExprsHandler { // All other current entries will be MEMBER_OF the combined entry // (except for PTR_AND_OBJ entries which do not have a placeholder value - // 0xFFFF in the MEMBER_OF field). + // 0xFFFF in the MEMBER_OF field, or ATTACH entries since they are expected + // to be handled by themselves, after all other maps). OpenMPOffloadMappingFlags MemberOfFlag = OMPBuilder.getMemberOfFlag( OffsetForMemberOfFlag + CombinedInfo.BasePointers.size() - 1); for (auto &M : CurTypes) OMPBuilder.setCorrectMemberOfFlag(M, MemberOfFlag); + + // When we are emitting a combined entry. If there were any pending + // attachments to be done, we do them to the begin address of the combined + // entry. Note that this means only one attachment per combined-entry will + // be done. So, for instance, if we have: + // S *ps; + // ... map(ps->a, ps->b) + // We won't emit separate ATTACH entries for the two list items, just one. + if (PartialStruct.AttachPtrAddr.isValid() && + PartialStruct.AttachPteeAddr.isValid()) + addAttachEntry(CGF, AttachCombinedInfo, PartialStruct.AttachPtrAddr, + LBAddr, PartialStruct.AttachPtrDecl, + PartialStruct.AttachMapExpr); } /// Generate all the base pointers, section pointers, sizes, map types, and @@ -8809,8 +8973,6 @@ class MappableExprsHandler { assert(isa(CurDir) && "Expect a executable directive"); const auto *CurExecDir = cast(CurDir); - bool HasMapBasePtr = false; - bool HasMapArraySec = false; for (const auto *C : CurExecDir->getClausesOfKind()) { const auto *EI = C->getVarRefs().begin(); for (const auto L : C->decl_component_lists(VD)) { @@ -8822,11 +8984,6 @@ class MappableExprsHandler { assert(VDecl == VD && "We got information for the wrong declaration??"); assert(!Components.empty() && "Not expecting declaration with no component lists."); - if (VD && E && VD->getType()->isAnyPointerType() && isa(E)) - HasMapBasePtr = true; - if (VD && E && VD->getType()->isAnyPointerType() && - (isa(E) || isa(E))) - HasMapArraySec = true; DeclComponentLists.emplace_back(Components, C->getMapType(), C->getMapTypeModifiers(), C->isImplicit(), Mapper, E); @@ -8859,26 +9016,25 @@ class MappableExprsHandler { generateInfoForCaptureFromComponentLists( VD, DeclComponentLists, CurInfoForComponentLists, PartialStruct, - IsEligibleForTargetParamFlag, - /*AreBothBasePtrAndPteeMapped=*/HasMapBasePtr && HasMapArraySec); + IsEligibleForTargetParamFlag); // If there is an entry in PartialStruct it means we have a // struct with individual members mapped. Emit an extra combined // entry. + MapCombinedInfoTy AttachCombinedInfo; if (PartialStruct.Base.isValid()) { CurCaptureVarInfo.append(PartialStruct.PreliminaryMapData); emitCombinedEntry( - CurCaptureVarInfo, CurInfoForComponentLists.Types, - PartialStruct, Cap->capturesThis(), OMPBuilder, nullptr, - OffsetForMemberOfFlag, + CurCaptureVarInfo, AttachCombinedInfo, + CurInfoForComponentLists.Types, PartialStruct, + Cap->capturesThis(), OMPBuilder, nullptr, OffsetForMemberOfFlag, /*NotTargetParams*/ !IsEligibleForTargetParamFlag); } - // Return if we didn't add any entries. - if (CurInfoForComponentLists.BasePointers.empty()) - return; - + // We do the appends to get the entries in the following order: + // combined-entry -> individual-field-entries -> attach-entry CurCaptureVarInfo.append(CurInfoForComponentLists); + CurCaptureVarInfo.append(AttachCombinedInfo); }; // Next, we break-down the lists of components into lists that should be @@ -8939,8 +9095,7 @@ class MappableExprsHandler { void generateInfoForCaptureFromComponentLists( const ValueDecl *VD, ArrayRef DeclComponentLists, MapCombinedInfoTy &CurComponentListInfo, StructRangeInfoTy &PartialStruct, - bool IsListEligibleForTargetParamFlag, - bool AreBothBasePtrAndPteeMapped = false) const { + bool IsListEligibleForTargetParamFlag) const { // Find overlapping elements (including the offset from the base element). llvm::SmallDenseMap< const MapData *, @@ -9102,7 +9257,7 @@ class MappableExprsHandler { StructBaseCombinedInfo, PartialStruct, AddTargetParamFlag, IsImplicit, /*GenerateAllInfoForClauses*/ false, Mapper, /*ForDeviceAddr=*/false, VD, VarRef, - /*OverlappedElements*/ {}, AreBothBasePtrAndPteeMapped); + /*OverlappedElements*/ {}); AddTargetParamFlag = false; } } diff --git a/clang/test/OpenMP/bug60602.cpp b/clang/test/OpenMP/bug60602.cpp index 0789ef958e523..9b2dff791cccd 100644 --- a/clang/test/OpenMP/bug60602.cpp +++ b/clang/test/OpenMP/bug60602.cpp @@ -1,4 +1,4 @@ -// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --include-generated-funcs --replace-value-regex "__omp_offloading_[0-9a-z]+_[0-9a-z]+" "reduction_size[.].+[.]" "pl_cond[.].+[.|,]" --prefix-filecheck-ir-name _ --version 2 +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --check-globals --include-generated-funcs --replace-value-regex "__omp_offloading_[0-9a-z]+_[0-9a-z]+" "reduction_size[.].+[.]" "pl_cond[.].+[.|,]" --prefix-filecheck-ir-name _ --global-value-regex "\.offload_.*" --version 2 // Test host codegen. // RUN: %clang_cc1 -verify -fopenmp -x c++ -triple powerpc64le-unknown-unknown -fopenmp-targets=powerpc64le-ibm-linux-gnu -emit-llvm %s -o - | FileCheck %s // expected-no-diagnostics @@ -16,6 +16,12 @@ int kernel_within_loop(int *a, int *b, int N, int num_iters) { } return a[N-1]; } +//. +// CHECK: @.offload_sizes = private unnamed_addr constant [5 x i64] [i64 4, i64 0, i64 8, i64 0, i64 8] +// CHECK: @.offload_maptypes = private unnamed_addr constant [5 x i64] [i64 800, i64 35, i64 16384, i64 35, i64 16384] +// CHECK: @.offload_sizes.1 = private unnamed_addr constant [5 x i64] [i64 4, i64 0, i64 8, i64 0, i64 8] +// CHECK: @.offload_maptypes.2 = private unnamed_addr constant [5 x i64] [i64 800, i64 35, i64 16384, i64 35, i64 16384] +//. // CHECK-LABEL: define dso_local noundef signext i32 @_Z18kernel_within_loopPiS_ii // CHECK-SAME: (ptr noundef [[A:%.*]], ptr noundef [[B:%.*]], i32 noundef signext [[N:%.*]], i32 noundef signext [[NUM_ITERS:%.*]]) #[[ATTR0:[0-9]+]] { // CHECK-NEXT: entry: @@ -25,16 +31,16 @@ int kernel_within_loop(int *a, int *b, int N, int num_iters) { // CHECK-NEXT: [[NUM_ITERS_ADDR:%.*]] = alloca i32, align 4 // CHECK-NEXT: [[I:%.*]] = alloca i32, align 4 // CHECK-NEXT: [[N_CASTED:%.*]] = alloca i64, align 8 -// CHECK-NEXT: [[DOTOFFLOAD_BASEPTRS:%.*]] = alloca [3 x ptr], align 8 -// CHECK-NEXT: [[DOTOFFLOAD_PTRS:%.*]] = alloca [3 x ptr], align 8 -// CHECK-NEXT: [[DOTOFFLOAD_MAPPERS:%.*]] = alloca [3 x ptr], align 8 -// CHECK-NEXT: [[DOTOFFLOAD_SIZES:%.*]] = alloca [3 x i64], align 8 +// CHECK-NEXT: [[DOTOFFLOAD_BASEPTRS:%.*]] = alloca [5 x ptr], align 8 +// CHECK-NEXT: [[DOTOFFLOAD_PTRS:%.*]] = alloca [5 x ptr], align 8 +// CHECK-NEXT: [[DOTOFFLOAD_MAPPERS:%.*]] = alloca [5 x ptr], align 8 +// CHECK-NEXT: [[DOTOFFLOAD_SIZES:%.*]] = alloca [5 x i64], align 8 // CHECK-NEXT: [[KERNEL_ARGS:%.*]] = alloca [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], align 8 // CHECK-NEXT: [[N_CASTED3:%.*]] = alloca i64, align 8 -// CHECK-NEXT: [[DOTOFFLOAD_BASEPTRS8:%.*]] = alloca [3 x ptr], align 8 -// CHECK-NEXT: [[DOTOFFLOAD_PTRS9:%.*]] = alloca [3 x ptr], align 8 -// CHECK-NEXT: [[DOTOFFLOAD_MAPPERS10:%.*]] = alloca [3 x ptr], align 8 -// CHECK-NEXT: [[DOTOFFLOAD_SIZES11:%.*]] = alloca [3 x i64], align 8 +// CHECK-NEXT: [[DOTOFFLOAD_BASEPTRS8:%.*]] = alloca [5 x ptr], align 8 +// CHECK-NEXT: [[DOTOFFLOAD_PTRS9:%.*]] = alloca [5 x ptr], align 8 +// CHECK-NEXT: [[DOTOFFLOAD_MAPPERS10:%.*]] = alloca [5 x ptr], align 8 +// CHECK-NEXT: [[DOTOFFLOAD_SIZES11:%.*]] = alloca [5 x i64], align 8 // CHECK-NEXT: [[TMP:%.*]] = alloca i32, align 4 // CHECK-NEXT: [[DOTCAPTURE_EXPR_:%.*]] = alloca i32, align 4 // CHECK-NEXT: [[DOTCAPTURE_EXPR_12:%.*]] = alloca i32, align 4 @@ -68,165 +74,189 @@ int kernel_within_loop(int *a, int *b, int N, int num_iters) { // CHECK-NEXT: [[TMP12:%.*]] = load i32, ptr [[N_ADDR]], align 4 // CHECK-NEXT: [[CONV2:%.*]] = sext i32 [[TMP12]] to i64 // CHECK-NEXT: [[TMP13:%.*]] = mul nuw i64 [[CONV2]], 4 -// CHECK-NEXT: call void @llvm.memcpy.p0.p0.i64(ptr align 8 [[DOTOFFLOAD_SIZES]], ptr align 8 @.offload_sizes, i64 24, i1 false) -// CHECK-NEXT: [[TMP14:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK-NEXT: call void @llvm.memcpy.p0.p0.i64(ptr align 8 [[DOTOFFLOAD_SIZES]], ptr align 8 @.offload_sizes, i64 40, i1 false) +// CHECK-NEXT: [[TMP14:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 // CHECK-NEXT: store i64 [[TMP3]], ptr [[TMP14]], align 8 -// CHECK-NEXT: [[TMP15:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK-NEXT: [[TMP15:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 // CHECK-NEXT: store i64 [[TMP3]], ptr [[TMP15]], align 8 -// CHECK-NEXT: [[TMP16:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 0 +// CHECK-NEXT: [[TMP16:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 0 // CHECK-NEXT: store ptr null, ptr [[TMP16]], align 8 -// CHECK-NEXT: [[TMP17:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK-NEXT: [[TMP17:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 // CHECK-NEXT: store ptr [[TMP6]], ptr [[TMP17]], align 8 -// CHECK-NEXT: [[TMP18:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK-NEXT: [[TMP18:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 // CHECK-NEXT: store ptr [[ARRAYIDX]], ptr [[TMP18]], align 8 -// CHECK-NEXT: [[TMP19:%.*]] = getelementptr inbounds [3 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 1 +// CHECK-NEXT: [[TMP19:%.*]] = getelementptr inbounds [5 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 1 // CHECK-NEXT: store i64 [[TMP9]], ptr [[TMP19]], align 8 -// CHECK-NEXT: [[TMP20:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK-NEXT: [[TMP20:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 // CHECK-NEXT: store ptr null, ptr [[TMP20]], align 8 -// CHECK-NEXT: [[TMP21:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 2 -// CHECK-NEXT: store ptr [[TMP10]], ptr [[TMP21]], align 8 -// CHECK-NEXT: [[TMP22:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 2 -// CHECK-NEXT: store ptr [[ARRAYIDX1]], ptr [[TMP22]], align 8 -// CHECK-NEXT: [[TMP23:%.*]] = getelementptr inbounds [3 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 2 -// CHECK-NEXT: store i64 [[TMP13]], ptr [[TMP23]], align 8 -// CHECK-NEXT: [[TMP24:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 2 -// CHECK-NEXT: store ptr null, ptr [[TMP24]], align 8 -// CHECK-NEXT: [[TMP25:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK-NEXT: [[TMP26:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK-NEXT: [[TMP27:%.*]] = getelementptr inbounds [3 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 0 -// CHECK-NEXT: [[TMP28:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 0 -// CHECK-NEXT: store i32 3, ptr [[TMP28]], align 4 -// CHECK-NEXT: [[TMP29:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 1 -// CHECK-NEXT: store i32 3, ptr [[TMP29]], align 4 -// CHECK-NEXT: [[TMP30:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 2 -// CHECK-NEXT: store ptr [[TMP25]], ptr [[TMP30]], align 8 -// CHECK-NEXT: [[TMP31:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 3 -// CHECK-NEXT: store ptr [[TMP26]], ptr [[TMP31]], align 8 -// CHECK-NEXT: [[TMP32:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 4 -// CHECK-NEXT: store ptr [[TMP27]], ptr [[TMP32]], align 8 -// CHECK-NEXT: [[TMP33:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 5 -// CHECK-NEXT: store ptr @.offload_maptypes, ptr [[TMP33]], align 8 -// CHECK-NEXT: [[TMP34:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 6 -// CHECK-NEXT: store ptr null, ptr [[TMP34]], align 8 -// CHECK-NEXT: [[TMP35:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 7 -// CHECK-NEXT: store ptr null, ptr [[TMP35]], align 8 -// CHECK-NEXT: [[TMP36:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 8 -// CHECK-NEXT: store i64 0, ptr [[TMP36]], align 8 -// CHECK-NEXT: [[TMP37:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 9 -// CHECK-NEXT: store i64 0, ptr [[TMP37]], align 8 -// CHECK-NEXT: [[TMP38:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 10 -// CHECK-NEXT: store [3 x i32] [i32 1, i32 0, i32 0], ptr [[TMP38]], align 4 -// CHECK-NEXT: [[TMP39:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 11 -// CHECK-NEXT: store [3 x i32] zeroinitializer, ptr [[TMP39]], align 4 -// CHECK-NEXT: [[TMP40:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 12 -// CHECK-NEXT: store i32 0, ptr [[TMP40]], align 4 -// CHECK-NEXT: [[TMP41:%.*]] = call i32 @__tgt_target_kernel(ptr @[[GLOB2:[0-9]+]], i64 -1, i32 1, i32 0, ptr @.{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z18kernel_within_loopPiS_ii_l9.region_id, ptr [[KERNEL_ARGS]]) -// CHECK-NEXT: [[TMP42:%.*]] = icmp ne i32 [[TMP41]], 0 -// CHECK-NEXT: br i1 [[TMP42]], label [[OMP_OFFLOAD_FAILED:%.*]], label [[OMP_OFFLOAD_CONT:%.*]] +// CHECK-NEXT: [[TMP21:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 2 +// CHECK-NEXT: store ptr [[A_ADDR]], ptr [[TMP21]], align 8 +// CHECK-NEXT: [[TMP22:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 2 +// CHECK-NEXT: store ptr [[ARRAYIDX]], ptr [[TMP22]], align 8 +// CHECK-NEXT: [[TMP23:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 2 +// CHECK-NEXT: store ptr null, ptr [[TMP23]], align 8 +// CHECK-NEXT: [[TMP24:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 3 +// CHECK-NEXT: store ptr [[TMP10]], ptr [[TMP24]], align 8 +// CHECK-NEXT: [[TMP25:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 3 +// CHECK-NEXT: store ptr [[ARRAYIDX1]], ptr [[TMP25]], align 8 +// CHECK-NEXT: [[TMP26:%.*]] = getelementptr inbounds [5 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 3 +// CHECK-NEXT: store i64 [[TMP13]], ptr [[TMP26]], align 8 +// CHECK-NEXT: [[TMP27:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 3 +// CHECK-NEXT: store ptr null, ptr [[TMP27]], align 8 +// CHECK-NEXT: [[TMP28:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 4 +// CHECK-NEXT: store ptr [[B_ADDR]], ptr [[TMP28]], align 8 +// CHECK-NEXT: [[TMP29:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 4 +// CHECK-NEXT: store ptr [[ARRAYIDX1]], ptr [[TMP29]], align 8 +// CHECK-NEXT: [[TMP30:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 4 +// CHECK-NEXT: store ptr null, ptr [[TMP30]], align 8 +// CHECK-NEXT: [[TMP31:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK-NEXT: [[TMP32:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK-NEXT: [[TMP33:%.*]] = getelementptr inbounds [5 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 0 +// CHECK-NEXT: [[TMP34:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 0 +// CHECK-NEXT: store i32 3, ptr [[TMP34]], align 4 +// CHECK-NEXT: [[TMP35:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 1 +// CHECK-NEXT: store i32 5, ptr [[TMP35]], align 4 +// CHECK-NEXT: [[TMP36:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 2 +// CHECK-NEXT: store ptr [[TMP31]], ptr [[TMP36]], align 8 +// CHECK-NEXT: [[TMP37:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 3 +// CHECK-NEXT: store ptr [[TMP32]], ptr [[TMP37]], align 8 +// CHECK-NEXT: [[TMP38:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 4 +// CHECK-NEXT: store ptr [[TMP33]], ptr [[TMP38]], align 8 +// CHECK-NEXT: [[TMP39:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 5 +// CHECK-NEXT: store ptr @.offload_maptypes, ptr [[TMP39]], align 8 +// CHECK-NEXT: [[TMP40:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 6 +// CHECK-NEXT: store ptr null, ptr [[TMP40]], align 8 +// CHECK-NEXT: [[TMP41:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 7 +// CHECK-NEXT: store ptr null, ptr [[TMP41]], align 8 +// CHECK-NEXT: [[TMP42:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 8 +// CHECK-NEXT: store i64 0, ptr [[TMP42]], align 8 +// CHECK-NEXT: [[TMP43:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 9 +// CHECK-NEXT: store i64 0, ptr [[TMP43]], align 8 +// CHECK-NEXT: [[TMP44:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 10 +// CHECK-NEXT: store [3 x i32] [i32 1, i32 0, i32 0], ptr [[TMP44]], align 4 +// CHECK-NEXT: [[TMP45:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 11 +// CHECK-NEXT: store [3 x i32] zeroinitializer, ptr [[TMP45]], align 4 +// CHECK-NEXT: [[TMP46:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 12 +// CHECK-NEXT: store i32 0, ptr [[TMP46]], align 4 +// CHECK-NEXT: [[TMP47:%.*]] = call i32 @__tgt_target_kernel(ptr @[[GLOB2:[0-9]+]], i64 -1, i32 1, i32 0, ptr @.{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z18kernel_within_loopPiS_ii_l9.region_id, ptr [[KERNEL_ARGS]]) +// CHECK-NEXT: [[TMP48:%.*]] = icmp ne i32 [[TMP47]], 0 +// CHECK-NEXT: br i1 [[TMP48]], label [[OMP_OFFLOAD_FAILED:%.*]], label [[OMP_OFFLOAD_CONT:%.*]] // CHECK: omp_offload.failed: // CHECK-NEXT: call void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z18kernel_within_loopPiS_ii_l9(i64 [[TMP3]], ptr [[TMP4]], ptr [[TMP5]]) #[[ATTR2:[0-9]+]] // CHECK-NEXT: br label [[OMP_OFFLOAD_CONT]] // CHECK: omp_offload.cont: -// CHECK-NEXT: [[TMP43:%.*]] = load i32, ptr [[N_ADDR]], align 4 -// CHECK-NEXT: store i32 [[TMP43]], ptr [[N_CASTED3]], align 4 -// CHECK-NEXT: [[TMP44:%.*]] = load i64, ptr [[N_CASTED3]], align 8 -// CHECK-NEXT: [[TMP45:%.*]] = load ptr, ptr [[A_ADDR]], align 8 -// CHECK-NEXT: [[TMP46:%.*]] = load ptr, ptr [[B_ADDR]], align 8 -// CHECK-NEXT: [[TMP47:%.*]] = load ptr, ptr [[A_ADDR]], align 8 -// CHECK-NEXT: [[TMP48:%.*]] = load ptr, ptr [[A_ADDR]], align 8 -// CHECK-NEXT: [[ARRAYIDX4:%.*]] = getelementptr inbounds nuw i32, ptr [[TMP48]], i64 0 // CHECK-NEXT: [[TMP49:%.*]] = load i32, ptr [[N_ADDR]], align 4 -// CHECK-NEXT: [[CONV5:%.*]] = sext i32 [[TMP49]] to i64 -// CHECK-NEXT: [[TMP50:%.*]] = mul nuw i64 [[CONV5]], 4 -// CHECK-NEXT: [[TMP51:%.*]] = load ptr, ptr [[B_ADDR]], align 8 +// CHECK-NEXT: store i32 [[TMP49]], ptr [[N_CASTED3]], align 4 +// CHECK-NEXT: [[TMP50:%.*]] = load i64, ptr [[N_CASTED3]], align 8 +// CHECK-NEXT: [[TMP51:%.*]] = load ptr, ptr [[A_ADDR]], align 8 // CHECK-NEXT: [[TMP52:%.*]] = load ptr, ptr [[B_ADDR]], align 8 -// CHECK-NEXT: [[ARRAYIDX6:%.*]] = getelementptr inbounds nuw i32, ptr [[TMP52]], i64 0 -// CHECK-NEXT: [[TMP53:%.*]] = load i32, ptr [[N_ADDR]], align 4 -// CHECK-NEXT: [[CONV7:%.*]] = sext i32 [[TMP53]] to i64 -// CHECK-NEXT: [[TMP54:%.*]] = mul nuw i64 [[CONV7]], 4 -// CHECK-NEXT: call void @llvm.memcpy.p0.p0.i64(ptr align 8 [[DOTOFFLOAD_SIZES11]], ptr align 8 @.offload_sizes.1, i64 24, i1 false) -// CHECK-NEXT: [[TMP55:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS8]], i32 0, i32 0 -// CHECK-NEXT: store i64 [[TMP44]], ptr [[TMP55]], align 8 -// CHECK-NEXT: [[TMP56:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS9]], i32 0, i32 0 -// CHECK-NEXT: store i64 [[TMP44]], ptr [[TMP56]], align 8 -// CHECK-NEXT: [[TMP57:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS10]], i64 0, i64 0 -// CHECK-NEXT: store ptr null, ptr [[TMP57]], align 8 -// CHECK-NEXT: [[TMP58:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS8]], i32 0, i32 1 -// CHECK-NEXT: store ptr [[TMP47]], ptr [[TMP58]], align 8 -// CHECK-NEXT: [[TMP59:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS9]], i32 0, i32 1 -// CHECK-NEXT: store ptr [[ARRAYIDX4]], ptr [[TMP59]], align 8 -// CHECK-NEXT: [[TMP60:%.*]] = getelementptr inbounds [3 x i64], ptr [[DOTOFFLOAD_SIZES11]], i32 0, i32 1 -// CHECK-NEXT: store i64 [[TMP50]], ptr [[TMP60]], align 8 -// CHECK-NEXT: [[TMP61:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS10]], i64 0, i64 1 -// CHECK-NEXT: store ptr null, ptr [[TMP61]], align 8 -// CHECK-NEXT: [[TMP62:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS8]], i32 0, i32 2 -// CHECK-NEXT: store ptr [[TMP51]], ptr [[TMP62]], align 8 -// CHECK-NEXT: [[TMP63:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS9]], i32 0, i32 2 -// CHECK-NEXT: store ptr [[ARRAYIDX6]], ptr [[TMP63]], align 8 -// CHECK-NEXT: [[TMP64:%.*]] = getelementptr inbounds [3 x i64], ptr [[DOTOFFLOAD_SIZES11]], i32 0, i32 2 -// CHECK-NEXT: store i64 [[TMP54]], ptr [[TMP64]], align 8 -// CHECK-NEXT: [[TMP65:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS10]], i64 0, i64 2 -// CHECK-NEXT: store ptr null, ptr [[TMP65]], align 8 -// CHECK-NEXT: [[TMP66:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS8]], i32 0, i32 0 -// CHECK-NEXT: [[TMP67:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS9]], i32 0, i32 0 -// CHECK-NEXT: [[TMP68:%.*]] = getelementptr inbounds [3 x i64], ptr [[DOTOFFLOAD_SIZES11]], i32 0, i32 0 -// CHECK-NEXT: [[TMP69:%.*]] = load i32, ptr [[N_ADDR]], align 4 -// CHECK-NEXT: store i32 [[TMP69]], ptr [[DOTCAPTURE_EXPR_]], align 4 -// CHECK-NEXT: [[TMP70:%.*]] = load i32, ptr [[DOTCAPTURE_EXPR_]], align 4 -// CHECK-NEXT: [[SUB:%.*]] = sub i32 [[TMP70]], -2 +// CHECK-NEXT: [[TMP53:%.*]] = load ptr, ptr [[A_ADDR]], align 8 +// CHECK-NEXT: [[TMP54:%.*]] = load ptr, ptr [[A_ADDR]], align 8 +// CHECK-NEXT: [[ARRAYIDX4:%.*]] = getelementptr inbounds nuw i32, ptr [[TMP54]], i64 0 +// CHECK-NEXT: [[TMP55:%.*]] = load i32, ptr [[N_ADDR]], align 4 +// CHECK-NEXT: [[CONV5:%.*]] = sext i32 [[TMP55]] to i64 +// CHECK-NEXT: [[TMP56:%.*]] = mul nuw i64 [[CONV5]], 4 +// CHECK-NEXT: [[TMP57:%.*]] = load ptr, ptr [[B_ADDR]], align 8 +// CHECK-NEXT: [[TMP58:%.*]] = load ptr, ptr [[B_ADDR]], align 8 +// CHECK-NEXT: [[ARRAYIDX6:%.*]] = getelementptr inbounds nuw i32, ptr [[TMP58]], i64 0 +// CHECK-NEXT: [[TMP59:%.*]] = load i32, ptr [[N_ADDR]], align 4 +// CHECK-NEXT: [[CONV7:%.*]] = sext i32 [[TMP59]] to i64 +// CHECK-NEXT: [[TMP60:%.*]] = mul nuw i64 [[CONV7]], 4 +// CHECK-NEXT: call void @llvm.memcpy.p0.p0.i64(ptr align 8 [[DOTOFFLOAD_SIZES11]], ptr align 8 @.offload_sizes.1, i64 40, i1 false) +// CHECK-NEXT: [[TMP61:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS8]], i32 0, i32 0 +// CHECK-NEXT: store i64 [[TMP50]], ptr [[TMP61]], align 8 +// CHECK-NEXT: [[TMP62:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS9]], i32 0, i32 0 +// CHECK-NEXT: store i64 [[TMP50]], ptr [[TMP62]], align 8 +// CHECK-NEXT: [[TMP63:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS10]], i64 0, i64 0 +// CHECK-NEXT: store ptr null, ptr [[TMP63]], align 8 +// CHECK-NEXT: [[TMP64:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS8]], i32 0, i32 1 +// CHECK-NEXT: store ptr [[TMP53]], ptr [[TMP64]], align 8 +// CHECK-NEXT: [[TMP65:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS9]], i32 0, i32 1 +// CHECK-NEXT: store ptr [[ARRAYIDX4]], ptr [[TMP65]], align 8 +// CHECK-NEXT: [[TMP66:%.*]] = getelementptr inbounds [5 x i64], ptr [[DOTOFFLOAD_SIZES11]], i32 0, i32 1 +// CHECK-NEXT: store i64 [[TMP56]], ptr [[TMP66]], align 8 +// CHECK-NEXT: [[TMP67:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS10]], i64 0, i64 1 +// CHECK-NEXT: store ptr null, ptr [[TMP67]], align 8 +// CHECK-NEXT: [[TMP68:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS8]], i32 0, i32 2 +// CHECK-NEXT: store ptr [[A_ADDR]], ptr [[TMP68]], align 8 +// CHECK-NEXT: [[TMP69:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS9]], i32 0, i32 2 +// CHECK-NEXT: store ptr [[ARRAYIDX4]], ptr [[TMP69]], align 8 +// CHECK-NEXT: [[TMP70:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS10]], i64 0, i64 2 +// CHECK-NEXT: store ptr null, ptr [[TMP70]], align 8 +// CHECK-NEXT: [[TMP71:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS8]], i32 0, i32 3 +// CHECK-NEXT: store ptr [[TMP57]], ptr [[TMP71]], align 8 +// CHECK-NEXT: [[TMP72:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS9]], i32 0, i32 3 +// CHECK-NEXT: store ptr [[ARRAYIDX6]], ptr [[TMP72]], align 8 +// CHECK-NEXT: [[TMP73:%.*]] = getelementptr inbounds [5 x i64], ptr [[DOTOFFLOAD_SIZES11]], i32 0, i32 3 +// CHECK-NEXT: store i64 [[TMP60]], ptr [[TMP73]], align 8 +// CHECK-NEXT: [[TMP74:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS10]], i64 0, i64 3 +// CHECK-NEXT: store ptr null, ptr [[TMP74]], align 8 +// CHECK-NEXT: [[TMP75:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS8]], i32 0, i32 4 +// CHECK-NEXT: store ptr [[B_ADDR]], ptr [[TMP75]], align 8 +// CHECK-NEXT: [[TMP76:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS9]], i32 0, i32 4 +// CHECK-NEXT: store ptr [[ARRAYIDX6]], ptr [[TMP76]], align 8 +// CHECK-NEXT: [[TMP77:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS10]], i64 0, i64 4 +// CHECK-NEXT: store ptr null, ptr [[TMP77]], align 8 +// CHECK-NEXT: [[TMP78:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS8]], i32 0, i32 0 +// CHECK-NEXT: [[TMP79:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS9]], i32 0, i32 0 +// CHECK-NEXT: [[TMP80:%.*]] = getelementptr inbounds [5 x i64], ptr [[DOTOFFLOAD_SIZES11]], i32 0, i32 0 +// CHECK-NEXT: [[TMP81:%.*]] = load i32, ptr [[N_ADDR]], align 4 +// CHECK-NEXT: store i32 [[TMP81]], ptr [[DOTCAPTURE_EXPR_]], align 4 +// CHECK-NEXT: [[TMP82:%.*]] = load i32, ptr [[DOTCAPTURE_EXPR_]], align 4 +// CHECK-NEXT: [[SUB:%.*]] = sub i32 [[TMP82]], -2 // CHECK-NEXT: [[DIV:%.*]] = udiv i32 [[SUB]], 3 // CHECK-NEXT: [[SUB13:%.*]] = sub i32 [[DIV]], 1 // CHECK-NEXT: store i32 [[SUB13]], ptr [[DOTCAPTURE_EXPR_12]], align 4 -// CHECK-NEXT: [[TMP71:%.*]] = load i32, ptr [[DOTCAPTURE_EXPR_12]], align 4 -// CHECK-NEXT: [[ADD:%.*]] = add i32 [[TMP71]], 1 -// CHECK-NEXT: [[TMP72:%.*]] = zext i32 [[ADD]] to i64 -// CHECK-NEXT: [[TMP73:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS14]], i32 0, i32 0 -// CHECK-NEXT: store i32 3, ptr [[TMP73]], align 4 -// CHECK-NEXT: [[TMP74:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS14]], i32 0, i32 1 -// CHECK-NEXT: store i32 3, ptr [[TMP74]], align 4 -// CHECK-NEXT: [[TMP75:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS14]], i32 0, i32 2 -// CHECK-NEXT: store ptr [[TMP66]], ptr [[TMP75]], align 8 -// CHECK-NEXT: [[TMP76:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS14]], i32 0, i32 3 -// CHECK-NEXT: store ptr [[TMP67]], ptr [[TMP76]], align 8 -// CHECK-NEXT: [[TMP77:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS14]], i32 0, i32 4 -// CHECK-NEXT: store ptr [[TMP68]], ptr [[TMP77]], align 8 -// CHECK-NEXT: [[TMP78:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS14]], i32 0, i32 5 -// CHECK-NEXT: store ptr @.offload_maptypes.2, ptr [[TMP78]], align 8 -// CHECK-NEXT: [[TMP79:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS14]], i32 0, i32 6 -// CHECK-NEXT: store ptr null, ptr [[TMP79]], align 8 -// CHECK-NEXT: [[TMP80:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS14]], i32 0, i32 7 -// CHECK-NEXT: store ptr null, ptr [[TMP80]], align 8 -// CHECK-NEXT: [[TMP81:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS14]], i32 0, i32 8 -// CHECK-NEXT: store i64 [[TMP72]], ptr [[TMP81]], align 8 -// CHECK-NEXT: [[TMP82:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS14]], i32 0, i32 9 -// CHECK-NEXT: store i64 0, ptr [[TMP82]], align 8 -// CHECK-NEXT: [[TMP83:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS14]], i32 0, i32 10 -// CHECK-NEXT: store [3 x i32] zeroinitializer, ptr [[TMP83]], align 4 -// CHECK-NEXT: [[TMP84:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS14]], i32 0, i32 11 -// CHECK-NEXT: store [3 x i32] zeroinitializer, ptr [[TMP84]], align 4 -// CHECK-NEXT: [[TMP85:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS14]], i32 0, i32 12 -// CHECK-NEXT: store i32 0, ptr [[TMP85]], align 4 -// CHECK-NEXT: [[TMP86:%.*]] = call i32 @__tgt_target_kernel(ptr @[[GLOB2]], i64 -1, i32 0, i32 0, ptr @.{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z18kernel_within_loopPiS_ii_l13.region_id, ptr [[KERNEL_ARGS14]]) -// CHECK-NEXT: [[TMP87:%.*]] = icmp ne i32 [[TMP86]], 0 -// CHECK-NEXT: br i1 [[TMP87]], label [[OMP_OFFLOAD_FAILED15:%.*]], label [[OMP_OFFLOAD_CONT16:%.*]] +// CHECK-NEXT: [[TMP83:%.*]] = load i32, ptr [[DOTCAPTURE_EXPR_12]], align 4 +// CHECK-NEXT: [[ADD:%.*]] = add i32 [[TMP83]], 1 +// CHECK-NEXT: [[TMP84:%.*]] = zext i32 [[ADD]] to i64 +// CHECK-NEXT: [[TMP85:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS14]], i32 0, i32 0 +// CHECK-NEXT: store i32 3, ptr [[TMP85]], align 4 +// CHECK-NEXT: [[TMP86:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS14]], i32 0, i32 1 +// CHECK-NEXT: store i32 5, ptr [[TMP86]], align 4 +// CHECK-NEXT: [[TMP87:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS14]], i32 0, i32 2 +// CHECK-NEXT: store ptr [[TMP78]], ptr [[TMP87]], align 8 +// CHECK-NEXT: [[TMP88:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS14]], i32 0, i32 3 +// CHECK-NEXT: store ptr [[TMP79]], ptr [[TMP88]], align 8 +// CHECK-NEXT: [[TMP89:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS14]], i32 0, i32 4 +// CHECK-NEXT: store ptr [[TMP80]], ptr [[TMP89]], align 8 +// CHECK-NEXT: [[TMP90:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS14]], i32 0, i32 5 +// CHECK-NEXT: store ptr @.offload_maptypes.2, ptr [[TMP90]], align 8 +// CHECK-NEXT: [[TMP91:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS14]], i32 0, i32 6 +// CHECK-NEXT: store ptr null, ptr [[TMP91]], align 8 +// CHECK-NEXT: [[TMP92:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS14]], i32 0, i32 7 +// CHECK-NEXT: store ptr null, ptr [[TMP92]], align 8 +// CHECK-NEXT: [[TMP93:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS14]], i32 0, i32 8 +// CHECK-NEXT: store i64 [[TMP84]], ptr [[TMP93]], align 8 +// CHECK-NEXT: [[TMP94:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS14]], i32 0, i32 9 +// CHECK-NEXT: store i64 0, ptr [[TMP94]], align 8 +// CHECK-NEXT: [[TMP95:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS14]], i32 0, i32 10 +// CHECK-NEXT: store [3 x i32] zeroinitializer, ptr [[TMP95]], align 4 +// CHECK-NEXT: [[TMP96:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS14]], i32 0, i32 11 +// CHECK-NEXT: store [3 x i32] zeroinitializer, ptr [[TMP96]], align 4 +// CHECK-NEXT: [[TMP97:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS14]], i32 0, i32 12 +// CHECK-NEXT: store i32 0, ptr [[TMP97]], align 4 +// CHECK-NEXT: [[TMP98:%.*]] = call i32 @__tgt_target_kernel(ptr @[[GLOB2]], i64 -1, i32 0, i32 0, ptr @.{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z18kernel_within_loopPiS_ii_l13.region_id, ptr [[KERNEL_ARGS14]]) +// CHECK-NEXT: [[TMP99:%.*]] = icmp ne i32 [[TMP98]], 0 +// CHECK-NEXT: br i1 [[TMP99]], label [[OMP_OFFLOAD_FAILED15:%.*]], label [[OMP_OFFLOAD_CONT16:%.*]] // CHECK: omp_offload.failed15: -// CHECK-NEXT: call void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z18kernel_within_loopPiS_ii_l13(i64 [[TMP44]], ptr [[TMP45]], ptr [[TMP46]]) #[[ATTR2]] +// CHECK-NEXT: call void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z18kernel_within_loopPiS_ii_l13(i64 [[TMP50]], ptr [[TMP51]], ptr [[TMP52]]) #[[ATTR2]] // CHECK-NEXT: br label [[OMP_OFFLOAD_CONT16]] // CHECK: omp_offload.cont16: // CHECK-NEXT: br label [[FOR_INC:%.*]] // CHECK: for.inc: -// CHECK-NEXT: [[TMP88:%.*]] = load i32, ptr [[I]], align 4 -// CHECK-NEXT: [[INC:%.*]] = add nsw i32 [[TMP88]], 1 +// CHECK-NEXT: [[TMP100:%.*]] = load i32, ptr [[I]], align 4 +// CHECK-NEXT: [[INC:%.*]] = add nsw i32 [[TMP100]], 1 // CHECK-NEXT: store i32 [[INC]], ptr [[I]], align 4 -// CHECK-NEXT: br label [[FOR_COND]], !llvm.loop [[LOOP5:![0-9]+]] +// CHECK-NEXT: br label [[FOR_COND]], !llvm.loop [[LOOP7:![0-9]+]] // CHECK: for.end: -// CHECK-NEXT: [[TMP89:%.*]] = load ptr, ptr [[A_ADDR]], align 8 -// CHECK-NEXT: [[TMP90:%.*]] = load i32, ptr [[N_ADDR]], align 4 -// CHECK-NEXT: [[SUB17:%.*]] = sub nsw i32 [[TMP90]], 1 +// CHECK-NEXT: [[TMP101:%.*]] = load ptr, ptr [[A_ADDR]], align 8 +// CHECK-NEXT: [[TMP102:%.*]] = load i32, ptr [[N_ADDR]], align 4 +// CHECK-NEXT: [[SUB17:%.*]] = sub nsw i32 [[TMP102]], 1 // CHECK-NEXT: [[IDXPROM:%.*]] = sext i32 [[SUB17]] to i64 -// CHECK-NEXT: [[ARRAYIDX18:%.*]] = getelementptr inbounds i32, ptr [[TMP89]], i64 [[IDXPROM]] -// CHECK-NEXT: [[TMP91:%.*]] = load i32, ptr [[ARRAYIDX18]], align 4 -// CHECK-NEXT: ret i32 [[TMP91]] +// CHECK-NEXT: [[ARRAYIDX18:%.*]] = getelementptr inbounds i32, ptr [[TMP101]], i64 [[IDXPROM]] +// CHECK-NEXT: [[TMP103:%.*]] = load i32, ptr [[ARRAYIDX18]], align 4 +// CHECK-NEXT: ret i32 [[TMP103]] // // // CHECK-LABEL: define internal void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z18kernel_within_loopPiS_ii_l9 diff --git a/clang/test/OpenMP/reduction_implicit_map.cpp b/clang/test/OpenMP/reduction_implicit_map.cpp index a7db3da7d1f86..79c85447d7422 100644 --- a/clang/test/OpenMP/reduction_implicit_map.cpp +++ b/clang/test/OpenMP/reduction_implicit_map.cpp @@ -1,4 +1,4 @@ -// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --function-signature --include-generated-funcs --replace-value-regex "__omp_offloading_[0-9a-z]+_[0-9a-z]+" "reduction_size[.].+[.]" "pl_cond[.].+[.|,]" --prefix-filecheck-ir-name _ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --function-signature --check-globals --include-generated-funcs --replace-value-regex "__omp_offloading_[0-9a-z]+_[0-9a-z]+" "reduction_size[.].+[.]" "pl_cond[.].+[.|,]" --prefix-filecheck-ir-name _ --global-value-regex "\.offload_.*" // RUN: %clang_cc1 -verify -fopenmp -fopenmp-cuda-mode -x c++ \ // RUN: -triple powerpc64le-unknown-unknown -DCUDA \ // RUN: -fopenmp-targets=nvptx64-nvidia-cuda -emit-llvm-bc %s -o \ @@ -97,6 +97,21 @@ int main() #endif return 0; } +//. +// CHECK1: @.offload_sizes = private unnamed_addr constant [1 x i64] [i64 4] +// CHECK1: @.offload_maptypes = private unnamed_addr constant [1 x i64] [i64 547] +// CHECK1: @.offload_sizes.1 = private unnamed_addr constant [1 x i64] [i64 8000] +// CHECK1: @.offload_maptypes.2 = private unnamed_addr constant [1 x i64] [i64 547] +//. +// CHECK2: @.offload_sizes = private unnamed_addr constant [5 x i64] [i64 4, i64 4, i64 4, i64 0, i64 4] +// CHECK2: @.offload_maptypes = private unnamed_addr constant [5 x i64] [i64 800, i64 547, i64 16384, i64 33, i64 16384] +// CHECK2: @.offload_sizes.1 = private unnamed_addr constant [5 x i64] [i64 4, i64 12, i64 4, i64 0, i64 4] +// CHECK2: @.offload_maptypes.2 = private unnamed_addr constant [5 x i64] [i64 800, i64 547, i64 16384, i64 33, i64 16384] +// CHECK2: @.offload_sizes.3 = private unnamed_addr constant [2 x i64] [i64 4, i64 8] +// CHECK2: @.offload_maptypes.4 = private unnamed_addr constant [2 x i64] [i64 800, i64 547] +// CHECK2: @.offload_sizes.5 = private unnamed_addr constant [2 x i64] [i64 4, i64 4] +// CHECK2: @.offload_maptypes.6 = private unnamed_addr constant [2 x i64] [i64 800, i64 547] +//. // CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z3fooi_l32 // CHECK-SAME: (ptr noalias noundef [[DYN_PTR:%.*]], ptr noundef [[E:%.*]]) #[[ATTR0:[0-9]+]] { // CHECK-NEXT: entry: @@ -410,7 +425,7 @@ int main() // CHECK1-NEXT: entry: // CHECK1-NEXT: [[O_ADDR:%.*]] = alloca ptr, align 8 // CHECK1-NEXT: store ptr [[O]], ptr [[O_ADDR]], align 8 -// CHECK1-NEXT: [[TMP0:%.*]] = load ptr, ptr [[O_ADDR]], align 8 +// CHECK1-NEXT: [[TMP0:%.*]] = load ptr, ptr [[O_ADDR]], align 8, !nonnull [[META7:![0-9]+]], !align [[META8:![0-9]+]] // CHECK1-NEXT: call void (ptr, i32, ptr, ...) @__kmpc_fork_call(ptr @[[GLOB2]], i32 1, ptr @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z3barv_l50.omp_outlined, ptr [[TMP0]]) // CHECK1-NEXT: ret void // @@ -427,7 +442,7 @@ int main() // CHECK1-NEXT: store ptr [[DOTGLOBAL_TID_]], ptr [[DOTGLOBAL_TID__ADDR]], align 8 // CHECK1-NEXT: store ptr [[DOTBOUND_TID_]], ptr [[DOTBOUND_TID__ADDR]], align 8 // CHECK1-NEXT: store ptr [[O]], ptr [[O_ADDR]], align 8 -// CHECK1-NEXT: [[TMP0:%.*]] = load ptr, ptr [[O_ADDR]], align 8 +// CHECK1-NEXT: [[TMP0:%.*]] = load ptr, ptr [[O_ADDR]], align 8, !nonnull [[META7]], !align [[META8]] // CHECK1-NEXT: [[ARRAYIDX:%.*]] = getelementptr inbounds [5 x %class.S2], ptr [[TMP0]], i64 0, i64 0 // CHECK1-NEXT: call void @_ZN2S2C1Ev(ptr noundef nonnull align 4 dereferenceable(4) [[O1]]) // CHECK1-NEXT: [[TMP1:%.*]] = ptrtoint ptr [[TMP0]] to i64 @@ -447,7 +462,7 @@ int main() // CHECK1-NEXT: [[TMP7:%.*]] = load i32, ptr [[I]], align 4 // CHECK1-NEXT: [[INC:%.*]] = add nsw i32 [[TMP7]], 1 // CHECK1-NEXT: store i32 [[INC]], ptr [[I]], align 4 -// CHECK1-NEXT: br label [[FOR_COND]], !llvm.loop [[LOOP5:![0-9]+]] +// CHECK1-NEXT: br label [[FOR_COND]], !llvm.loop [[LOOP9:![0-9]+]] // CHECK1: for.end: // CHECK1-NEXT: [[TMP8:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOMP_REDUCTION_RED_LIST]], i64 0, i64 0 // CHECK1-NEXT: store ptr [[O1]], ptr [[TMP8]], align 8 @@ -498,7 +513,7 @@ int main() // CHECK1-NEXT: entry: // CHECK1-NEXT: [[B_ADDR:%.*]] = alloca ptr, align 8 // CHECK1-NEXT: store ptr [[B]], ptr [[B_ADDR]], align 8 -// CHECK1-NEXT: [[TMP0:%.*]] = load ptr, ptr [[B_ADDR]], align 8 +// CHECK1-NEXT: [[TMP0:%.*]] = load ptr, ptr [[B_ADDR]], align 8, !nonnull [[META7]], !align [[META13:![0-9]+]] // CHECK1-NEXT: call void (ptr, i32, ptr, ...) @__kmpc_fork_call(ptr @[[GLOB2]], i32 1, ptr @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z3barv_l55.omp_outlined, ptr [[TMP0]]) // CHECK1-NEXT: ret void // @@ -524,7 +539,7 @@ int main() // CHECK1-NEXT: store ptr [[DOTGLOBAL_TID_]], ptr [[DOTGLOBAL_TID__ADDR]], align 8 // CHECK1-NEXT: store ptr [[DOTBOUND_TID_]], ptr [[DOTBOUND_TID__ADDR]], align 8 // CHECK1-NEXT: store ptr [[B]], ptr [[B_ADDR]], align 8 -// CHECK1-NEXT: [[TMP0:%.*]] = load ptr, ptr [[B_ADDR]], align 8 +// CHECK1-NEXT: [[TMP0:%.*]] = load ptr, ptr [[B_ADDR]], align 8, !nonnull [[META7]], !align [[META13]] // CHECK1-NEXT: store i64 0, ptr [[DOTOMP_LB]], align 8 // CHECK1-NEXT: store i64 9, ptr [[DOTOMP_UB]], align 8 // CHECK1-NEXT: store i64 1, ptr [[DOTOMP_STRIDE]], align 8 @@ -811,19 +826,19 @@ int main() // CHECK2-NEXT: [[SIZE_ADDR:%.*]] = alloca i32, align 4 // CHECK2-NEXT: [[OUTPUT_ADDR:%.*]] = alloca ptr, align 4 // CHECK2-NEXT: [[SIZE_CASTED:%.*]] = alloca i32, align 4 -// CHECK2-NEXT: [[DOTOFFLOAD_BASEPTRS:%.*]] = alloca [3 x ptr], align 4 -// CHECK2-NEXT: [[DOTOFFLOAD_PTRS:%.*]] = alloca [3 x ptr], align 4 -// CHECK2-NEXT: [[DOTOFFLOAD_MAPPERS:%.*]] = alloca [3 x ptr], align 4 -// CHECK2-NEXT: [[DOTOFFLOAD_SIZES:%.*]] = alloca [3 x i64], align 4 +// CHECK2-NEXT: [[DOTOFFLOAD_BASEPTRS:%.*]] = alloca [5 x ptr], align 4 +// CHECK2-NEXT: [[DOTOFFLOAD_PTRS:%.*]] = alloca [5 x ptr], align 4 +// CHECK2-NEXT: [[DOTOFFLOAD_MAPPERS:%.*]] = alloca [5 x ptr], align 4 +// CHECK2-NEXT: [[DOTOFFLOAD_SIZES:%.*]] = alloca [5 x i64], align 4 // CHECK2-NEXT: [[TMP:%.*]] = alloca i32, align 4 // CHECK2-NEXT: [[DOTCAPTURE_EXPR_:%.*]] = alloca i32, align 4 // CHECK2-NEXT: [[DOTCAPTURE_EXPR_2:%.*]] = alloca i32, align 4 // CHECK2-NEXT: [[KERNEL_ARGS:%.*]] = alloca [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], align 8 // CHECK2-NEXT: [[SIZE_CASTED4:%.*]] = alloca i32, align 4 -// CHECK2-NEXT: [[DOTOFFLOAD_BASEPTRS7:%.*]] = alloca [3 x ptr], align 4 -// CHECK2-NEXT: [[DOTOFFLOAD_PTRS8:%.*]] = alloca [3 x ptr], align 4 -// CHECK2-NEXT: [[DOTOFFLOAD_MAPPERS9:%.*]] = alloca [3 x ptr], align 4 -// CHECK2-NEXT: [[DOTOFFLOAD_SIZES10:%.*]] = alloca [3 x i64], align 4 +// CHECK2-NEXT: [[DOTOFFLOAD_BASEPTRS7:%.*]] = alloca [5 x ptr], align 4 +// CHECK2-NEXT: [[DOTOFFLOAD_PTRS8:%.*]] = alloca [5 x ptr], align 4 +// CHECK2-NEXT: [[DOTOFFLOAD_MAPPERS9:%.*]] = alloca [5 x ptr], align 4 +// CHECK2-NEXT: [[DOTOFFLOAD_SIZES10:%.*]] = alloca [5 x i64], align 4 // CHECK2-NEXT: [[_TMP11:%.*]] = alloca i32, align 4 // CHECK2-NEXT: [[DOTCAPTURE_EXPR_12:%.*]] = alloca i32, align 4 // CHECK2-NEXT: [[DOTCAPTURE_EXPR_13:%.*]] = alloca i32, align 4 @@ -856,254 +871,278 @@ int main() // CHECK2-NEXT: [[TMP8:%.*]] = load i32, ptr [[SIZE_ADDR]], align 4 // CHECK2-NEXT: [[TMP9:%.*]] = mul nuw i32 [[TMP8]], 4 // CHECK2-NEXT: [[TMP10:%.*]] = sext i32 [[TMP9]] to i64 -// CHECK2-NEXT: call void @llvm.memcpy.p0.p0.i32(ptr align 4 [[DOTOFFLOAD_SIZES]], ptr align 4 @.offload_sizes, i32 24, i1 false) -// CHECK2-NEXT: [[TMP11:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK2-NEXT: call void @llvm.memcpy.p0.p0.i32(ptr align 4 [[DOTOFFLOAD_SIZES]], ptr align 4 @.offload_sizes, i32 40, i1 false) +// CHECK2-NEXT: [[TMP11:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 // CHECK2-NEXT: store i32 [[TMP1]], ptr [[TMP11]], align 4 -// CHECK2-NEXT: [[TMP12:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK2-NEXT: [[TMP12:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 // CHECK2-NEXT: store i32 [[TMP1]], ptr [[TMP12]], align 4 -// CHECK2-NEXT: [[TMP13:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i32 0, i32 0 +// CHECK2-NEXT: [[TMP13:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i32 0, i32 0 // CHECK2-NEXT: store ptr null, ptr [[TMP13]], align 4 -// CHECK2-NEXT: [[TMP14:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK2-NEXT: [[TMP14:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 // CHECK2-NEXT: store ptr [[TMP4]], ptr [[TMP14]], align 4 -// CHECK2-NEXT: [[TMP15:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK2-NEXT: [[TMP15:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 // CHECK2-NEXT: store ptr [[ARRAYIDX]], ptr [[TMP15]], align 4 -// CHECK2-NEXT: [[TMP16:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i32 0, i32 1 +// CHECK2-NEXT: [[TMP16:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i32 0, i32 1 // CHECK2-NEXT: store ptr null, ptr [[TMP16]], align 4 -// CHECK2-NEXT: [[TMP17:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 2 -// CHECK2-NEXT: store ptr [[TMP6]], ptr [[TMP17]], align 4 -// CHECK2-NEXT: [[TMP18:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 2 -// CHECK2-NEXT: store ptr [[ARRAYIDX1]], ptr [[TMP18]], align 4 -// CHECK2-NEXT: [[TMP19:%.*]] = getelementptr inbounds [3 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 2 -// CHECK2-NEXT: store i64 [[TMP10]], ptr [[TMP19]], align 4 -// CHECK2-NEXT: [[TMP20:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i32 0, i32 2 -// CHECK2-NEXT: store ptr null, ptr [[TMP20]], align 4 -// CHECK2-NEXT: [[TMP21:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK2-NEXT: [[TMP22:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK2-NEXT: [[TMP23:%.*]] = getelementptr inbounds [3 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 0 -// CHECK2-NEXT: [[TMP24:%.*]] = load i32, ptr [[SIZE_ADDR]], align 4 -// CHECK2-NEXT: store i32 [[TMP24]], ptr [[DOTCAPTURE_EXPR_]], align 4 -// CHECK2-NEXT: [[TMP25:%.*]] = load i32, ptr [[DOTCAPTURE_EXPR_]], align 4 -// CHECK2-NEXT: [[SUB:%.*]] = sub nsw i32 [[TMP25]], 0 +// CHECK2-NEXT: [[TMP17:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 2 +// CHECK2-NEXT: store ptr [[OUTPUT_ADDR]], ptr [[TMP17]], align 4 +// CHECK2-NEXT: [[TMP18:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 2 +// CHECK2-NEXT: store ptr [[ARRAYIDX]], ptr [[TMP18]], align 4 +// CHECK2-NEXT: [[TMP19:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i32 0, i32 2 +// CHECK2-NEXT: store ptr null, ptr [[TMP19]], align 4 +// CHECK2-NEXT: [[TMP20:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 3 +// CHECK2-NEXT: store ptr [[TMP6]], ptr [[TMP20]], align 4 +// CHECK2-NEXT: [[TMP21:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 3 +// CHECK2-NEXT: store ptr [[ARRAYIDX1]], ptr [[TMP21]], align 4 +// CHECK2-NEXT: [[TMP22:%.*]] = getelementptr inbounds [5 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 3 +// CHECK2-NEXT: store i64 [[TMP10]], ptr [[TMP22]], align 4 +// CHECK2-NEXT: [[TMP23:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i32 0, i32 3 +// CHECK2-NEXT: store ptr null, ptr [[TMP23]], align 4 +// CHECK2-NEXT: [[TMP24:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 4 +// CHECK2-NEXT: store ptr [[INPUT_ADDR]], ptr [[TMP24]], align 4 +// CHECK2-NEXT: [[TMP25:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 4 +// CHECK2-NEXT: store ptr [[ARRAYIDX1]], ptr [[TMP25]], align 4 +// CHECK2-NEXT: [[TMP26:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i32 0, i32 4 +// CHECK2-NEXT: store ptr null, ptr [[TMP26]], align 4 +// CHECK2-NEXT: [[TMP27:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK2-NEXT: [[TMP28:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK2-NEXT: [[TMP29:%.*]] = getelementptr inbounds [5 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 0 +// CHECK2-NEXT: [[TMP30:%.*]] = load i32, ptr [[SIZE_ADDR]], align 4 +// CHECK2-NEXT: store i32 [[TMP30]], ptr [[DOTCAPTURE_EXPR_]], align 4 +// CHECK2-NEXT: [[TMP31:%.*]] = load i32, ptr [[DOTCAPTURE_EXPR_]], align 4 +// CHECK2-NEXT: [[SUB:%.*]] = sub nsw i32 [[TMP31]], 0 // CHECK2-NEXT: [[DIV:%.*]] = sdiv i32 [[SUB]], 1 // CHECK2-NEXT: [[SUB3:%.*]] = sub nsw i32 [[DIV]], 1 // CHECK2-NEXT: store i32 [[SUB3]], ptr [[DOTCAPTURE_EXPR_2]], align 4 -// CHECK2-NEXT: [[TMP26:%.*]] = load i32, ptr [[DOTCAPTURE_EXPR_2]], align 4 -// CHECK2-NEXT: [[ADD:%.*]] = add nsw i32 [[TMP26]], 1 -// CHECK2-NEXT: [[TMP27:%.*]] = zext i32 [[ADD]] to i64 -// CHECK2-NEXT: [[TMP28:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 0 -// CHECK2-NEXT: store i32 3, ptr [[TMP28]], align 4 -// CHECK2-NEXT: [[TMP29:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 1 -// CHECK2-NEXT: store i32 3, ptr [[TMP29]], align 4 -// CHECK2-NEXT: [[TMP30:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 2 -// CHECK2-NEXT: store ptr [[TMP21]], ptr [[TMP30]], align 4 -// CHECK2-NEXT: [[TMP31:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 3 -// CHECK2-NEXT: store ptr [[TMP22]], ptr [[TMP31]], align 4 -// CHECK2-NEXT: [[TMP32:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 4 -// CHECK2-NEXT: store ptr [[TMP23]], ptr [[TMP32]], align 4 -// CHECK2-NEXT: [[TMP33:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 5 -// CHECK2-NEXT: store ptr @.offload_maptypes, ptr [[TMP33]], align 4 -// CHECK2-NEXT: [[TMP34:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 6 -// CHECK2-NEXT: store ptr null, ptr [[TMP34]], align 4 -// CHECK2-NEXT: [[TMP35:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 7 -// CHECK2-NEXT: store ptr null, ptr [[TMP35]], align 4 -// CHECK2-NEXT: [[TMP36:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 8 -// CHECK2-NEXT: store i64 [[TMP27]], ptr [[TMP36]], align 8 -// CHECK2-NEXT: [[TMP37:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 9 -// CHECK2-NEXT: store i64 0, ptr [[TMP37]], align 8 -// CHECK2-NEXT: [[TMP38:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 10 -// CHECK2-NEXT: store [3 x i32] zeroinitializer, ptr [[TMP38]], align 4 -// CHECK2-NEXT: [[TMP39:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 11 -// CHECK2-NEXT: store [3 x i32] zeroinitializer, ptr [[TMP39]], align 4 -// CHECK2-NEXT: [[TMP40:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 12 -// CHECK2-NEXT: store i32 0, ptr [[TMP40]], align 4 -// CHECK2-NEXT: [[TMP41:%.*]] = call i32 @__tgt_target_kernel(ptr @[[GLOB4:[0-9]+]], i64 -1, i32 0, i32 0, ptr @.{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z3sumPiiS__l69.region_id, ptr [[KERNEL_ARGS]]) -// CHECK2-NEXT: [[TMP42:%.*]] = icmp ne i32 [[TMP41]], 0 -// CHECK2-NEXT: br i1 [[TMP42]], label [[OMP_OFFLOAD_FAILED:%.*]], label [[OMP_OFFLOAD_CONT:%.*]] +// CHECK2-NEXT: [[TMP32:%.*]] = load i32, ptr [[DOTCAPTURE_EXPR_2]], align 4 +// CHECK2-NEXT: [[ADD:%.*]] = add nsw i32 [[TMP32]], 1 +// CHECK2-NEXT: [[TMP33:%.*]] = zext i32 [[ADD]] to i64 +// CHECK2-NEXT: [[TMP34:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 0 +// CHECK2-NEXT: store i32 3, ptr [[TMP34]], align 4 +// CHECK2-NEXT: [[TMP35:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 1 +// CHECK2-NEXT: store i32 5, ptr [[TMP35]], align 4 +// CHECK2-NEXT: [[TMP36:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 2 +// CHECK2-NEXT: store ptr [[TMP27]], ptr [[TMP36]], align 4 +// CHECK2-NEXT: [[TMP37:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 3 +// CHECK2-NEXT: store ptr [[TMP28]], ptr [[TMP37]], align 4 +// CHECK2-NEXT: [[TMP38:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 4 +// CHECK2-NEXT: store ptr [[TMP29]], ptr [[TMP38]], align 4 +// CHECK2-NEXT: [[TMP39:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 5 +// CHECK2-NEXT: store ptr @.offload_maptypes, ptr [[TMP39]], align 4 +// CHECK2-NEXT: [[TMP40:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 6 +// CHECK2-NEXT: store ptr null, ptr [[TMP40]], align 4 +// CHECK2-NEXT: [[TMP41:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 7 +// CHECK2-NEXT: store ptr null, ptr [[TMP41]], align 4 +// CHECK2-NEXT: [[TMP42:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 8 +// CHECK2-NEXT: store i64 [[TMP33]], ptr [[TMP42]], align 8 +// CHECK2-NEXT: [[TMP43:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 9 +// CHECK2-NEXT: store i64 0, ptr [[TMP43]], align 8 +// CHECK2-NEXT: [[TMP44:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 10 +// CHECK2-NEXT: store [3 x i32] zeroinitializer, ptr [[TMP44]], align 4 +// CHECK2-NEXT: [[TMP45:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 11 +// CHECK2-NEXT: store [3 x i32] zeroinitializer, ptr [[TMP45]], align 4 +// CHECK2-NEXT: [[TMP46:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 12 +// CHECK2-NEXT: store i32 0, ptr [[TMP46]], align 4 +// CHECK2-NEXT: [[TMP47:%.*]] = call i32 @__tgt_target_kernel(ptr @[[GLOB4:[0-9]+]], i64 -1, i32 0, i32 0, ptr @.{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z3sumPiiS__l69.region_id, ptr [[KERNEL_ARGS]]) +// CHECK2-NEXT: [[TMP48:%.*]] = icmp ne i32 [[TMP47]], 0 +// CHECK2-NEXT: br i1 [[TMP48]], label [[OMP_OFFLOAD_FAILED:%.*]], label [[OMP_OFFLOAD_CONT:%.*]] // CHECK2: omp_offload.failed: // CHECK2-NEXT: call void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z3sumPiiS__l69(i32 [[TMP1]], ptr [[TMP2]], ptr [[TMP3]]) #[[ATTR2:[0-9]+]] // CHECK2-NEXT: br label [[OMP_OFFLOAD_CONT]] // CHECK2: omp_offload.cont: -// CHECK2-NEXT: [[TMP43:%.*]] = load i32, ptr [[SIZE_ADDR]], align 4 -// CHECK2-NEXT: store i32 [[TMP43]], ptr [[SIZE_CASTED4]], align 4 -// CHECK2-NEXT: [[TMP44:%.*]] = load i32, ptr [[SIZE_CASTED4]], align 4 -// CHECK2-NEXT: [[TMP45:%.*]] = load ptr, ptr [[OUTPUT_ADDR]], align 4 -// CHECK2-NEXT: [[TMP46:%.*]] = load ptr, ptr [[INPUT_ADDR]], align 4 -// CHECK2-NEXT: [[TMP47:%.*]] = load ptr, ptr [[OUTPUT_ADDR]], align 4 -// CHECK2-NEXT: [[TMP48:%.*]] = load ptr, ptr [[OUTPUT_ADDR]], align 4 -// CHECK2-NEXT: [[ARRAYIDX5:%.*]] = getelementptr inbounds nuw i32, ptr [[TMP48]], i32 0 -// CHECK2-NEXT: [[TMP49:%.*]] = load ptr, ptr [[INPUT_ADDR]], align 4 -// CHECK2-NEXT: [[TMP50:%.*]] = load ptr, ptr [[INPUT_ADDR]], align 4 -// CHECK2-NEXT: [[ARRAYIDX6:%.*]] = getelementptr inbounds nuw i32, ptr [[TMP50]], i32 0 -// CHECK2-NEXT: [[TMP51:%.*]] = load i32, ptr [[SIZE_ADDR]], align 4 -// CHECK2-NEXT: [[TMP52:%.*]] = mul nuw i32 [[TMP51]], 4 -// CHECK2-NEXT: [[TMP53:%.*]] = sext i32 [[TMP52]] to i64 -// CHECK2-NEXT: call void @llvm.memcpy.p0.p0.i32(ptr align 4 [[DOTOFFLOAD_SIZES10]], ptr align 4 @.offload_sizes.1, i32 24, i1 false) -// CHECK2-NEXT: [[TMP54:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS7]], i32 0, i32 0 -// CHECK2-NEXT: store i32 [[TMP44]], ptr [[TMP54]], align 4 -// CHECK2-NEXT: [[TMP55:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS8]], i32 0, i32 0 -// CHECK2-NEXT: store i32 [[TMP44]], ptr [[TMP55]], align 4 -// CHECK2-NEXT: [[TMP56:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS9]], i32 0, i32 0 -// CHECK2-NEXT: store ptr null, ptr [[TMP56]], align 4 -// CHECK2-NEXT: [[TMP57:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS7]], i32 0, i32 1 -// CHECK2-NEXT: store ptr [[TMP47]], ptr [[TMP57]], align 4 -// CHECK2-NEXT: [[TMP58:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS8]], i32 0, i32 1 -// CHECK2-NEXT: store ptr [[ARRAYIDX5]], ptr [[TMP58]], align 4 -// CHECK2-NEXT: [[TMP59:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS9]], i32 0, i32 1 -// CHECK2-NEXT: store ptr null, ptr [[TMP59]], align 4 -// CHECK2-NEXT: [[TMP60:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS7]], i32 0, i32 2 -// CHECK2-NEXT: store ptr [[TMP49]], ptr [[TMP60]], align 4 -// CHECK2-NEXT: [[TMP61:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS8]], i32 0, i32 2 -// CHECK2-NEXT: store ptr [[ARRAYIDX6]], ptr [[TMP61]], align 4 -// CHECK2-NEXT: [[TMP62:%.*]] = getelementptr inbounds [3 x i64], ptr [[DOTOFFLOAD_SIZES10]], i32 0, i32 2 -// CHECK2-NEXT: store i64 [[TMP53]], ptr [[TMP62]], align 4 -// CHECK2-NEXT: [[TMP63:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS9]], i32 0, i32 2 -// CHECK2-NEXT: store ptr null, ptr [[TMP63]], align 4 -// CHECK2-NEXT: [[TMP64:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS7]], i32 0, i32 0 -// CHECK2-NEXT: [[TMP65:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS8]], i32 0, i32 0 -// CHECK2-NEXT: [[TMP66:%.*]] = getelementptr inbounds [3 x i64], ptr [[DOTOFFLOAD_SIZES10]], i32 0, i32 0 -// CHECK2-NEXT: [[TMP67:%.*]] = load i32, ptr [[SIZE_ADDR]], align 4 -// CHECK2-NEXT: store i32 [[TMP67]], ptr [[DOTCAPTURE_EXPR_12]], align 4 -// CHECK2-NEXT: [[TMP68:%.*]] = load i32, ptr [[DOTCAPTURE_EXPR_12]], align 4 -// CHECK2-NEXT: [[SUB14:%.*]] = sub nsw i32 [[TMP68]], 0 +// CHECK2-NEXT: [[TMP49:%.*]] = load i32, ptr [[SIZE_ADDR]], align 4 +// CHECK2-NEXT: store i32 [[TMP49]], ptr [[SIZE_CASTED4]], align 4 +// CHECK2-NEXT: [[TMP50:%.*]] = load i32, ptr [[SIZE_CASTED4]], align 4 +// CHECK2-NEXT: [[TMP51:%.*]] = load ptr, ptr [[OUTPUT_ADDR]], align 4 +// CHECK2-NEXT: [[TMP52:%.*]] = load ptr, ptr [[INPUT_ADDR]], align 4 +// CHECK2-NEXT: [[TMP53:%.*]] = load ptr, ptr [[OUTPUT_ADDR]], align 4 +// CHECK2-NEXT: [[TMP54:%.*]] = load ptr, ptr [[OUTPUT_ADDR]], align 4 +// CHECK2-NEXT: [[ARRAYIDX5:%.*]] = getelementptr inbounds nuw i32, ptr [[TMP54]], i32 0 +// CHECK2-NEXT: [[TMP55:%.*]] = load ptr, ptr [[INPUT_ADDR]], align 4 +// CHECK2-NEXT: [[TMP56:%.*]] = load ptr, ptr [[INPUT_ADDR]], align 4 +// CHECK2-NEXT: [[ARRAYIDX6:%.*]] = getelementptr inbounds nuw i32, ptr [[TMP56]], i32 0 +// CHECK2-NEXT: [[TMP57:%.*]] = load i32, ptr [[SIZE_ADDR]], align 4 +// CHECK2-NEXT: [[TMP58:%.*]] = mul nuw i32 [[TMP57]], 4 +// CHECK2-NEXT: [[TMP59:%.*]] = sext i32 [[TMP58]] to i64 +// CHECK2-NEXT: call void @llvm.memcpy.p0.p0.i32(ptr align 4 [[DOTOFFLOAD_SIZES10]], ptr align 4 @.offload_sizes.1, i32 40, i1 false) +// CHECK2-NEXT: [[TMP60:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS7]], i32 0, i32 0 +// CHECK2-NEXT: store i32 [[TMP50]], ptr [[TMP60]], align 4 +// CHECK2-NEXT: [[TMP61:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS8]], i32 0, i32 0 +// CHECK2-NEXT: store i32 [[TMP50]], ptr [[TMP61]], align 4 +// CHECK2-NEXT: [[TMP62:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS9]], i32 0, i32 0 +// CHECK2-NEXT: store ptr null, ptr [[TMP62]], align 4 +// CHECK2-NEXT: [[TMP63:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS7]], i32 0, i32 1 +// CHECK2-NEXT: store ptr [[TMP53]], ptr [[TMP63]], align 4 +// CHECK2-NEXT: [[TMP64:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS8]], i32 0, i32 1 +// CHECK2-NEXT: store ptr [[ARRAYIDX5]], ptr [[TMP64]], align 4 +// CHECK2-NEXT: [[TMP65:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS9]], i32 0, i32 1 +// CHECK2-NEXT: store ptr null, ptr [[TMP65]], align 4 +// CHECK2-NEXT: [[TMP66:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS7]], i32 0, i32 2 +// CHECK2-NEXT: store ptr [[OUTPUT_ADDR]], ptr [[TMP66]], align 4 +// CHECK2-NEXT: [[TMP67:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS8]], i32 0, i32 2 +// CHECK2-NEXT: store ptr [[ARRAYIDX5]], ptr [[TMP67]], align 4 +// CHECK2-NEXT: [[TMP68:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS9]], i32 0, i32 2 +// CHECK2-NEXT: store ptr null, ptr [[TMP68]], align 4 +// CHECK2-NEXT: [[TMP69:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS7]], i32 0, i32 3 +// CHECK2-NEXT: store ptr [[TMP55]], ptr [[TMP69]], align 4 +// CHECK2-NEXT: [[TMP70:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS8]], i32 0, i32 3 +// CHECK2-NEXT: store ptr [[ARRAYIDX6]], ptr [[TMP70]], align 4 +// CHECK2-NEXT: [[TMP71:%.*]] = getelementptr inbounds [5 x i64], ptr [[DOTOFFLOAD_SIZES10]], i32 0, i32 3 +// CHECK2-NEXT: store i64 [[TMP59]], ptr [[TMP71]], align 4 +// CHECK2-NEXT: [[TMP72:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS9]], i32 0, i32 3 +// CHECK2-NEXT: store ptr null, ptr [[TMP72]], align 4 +// CHECK2-NEXT: [[TMP73:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS7]], i32 0, i32 4 +// CHECK2-NEXT: store ptr [[INPUT_ADDR]], ptr [[TMP73]], align 4 +// CHECK2-NEXT: [[TMP74:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS8]], i32 0, i32 4 +// CHECK2-NEXT: store ptr [[ARRAYIDX6]], ptr [[TMP74]], align 4 +// CHECK2-NEXT: [[TMP75:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS9]], i32 0, i32 4 +// CHECK2-NEXT: store ptr null, ptr [[TMP75]], align 4 +// CHECK2-NEXT: [[TMP76:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS7]], i32 0, i32 0 +// CHECK2-NEXT: [[TMP77:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS8]], i32 0, i32 0 +// CHECK2-NEXT: [[TMP78:%.*]] = getelementptr inbounds [5 x i64], ptr [[DOTOFFLOAD_SIZES10]], i32 0, i32 0 +// CHECK2-NEXT: [[TMP79:%.*]] = load i32, ptr [[SIZE_ADDR]], align 4 +// CHECK2-NEXT: store i32 [[TMP79]], ptr [[DOTCAPTURE_EXPR_12]], align 4 +// CHECK2-NEXT: [[TMP80:%.*]] = load i32, ptr [[DOTCAPTURE_EXPR_12]], align 4 +// CHECK2-NEXT: [[SUB14:%.*]] = sub nsw i32 [[TMP80]], 0 // CHECK2-NEXT: [[DIV15:%.*]] = sdiv i32 [[SUB14]], 1 // CHECK2-NEXT: [[SUB16:%.*]] = sub nsw i32 [[DIV15]], 1 // CHECK2-NEXT: store i32 [[SUB16]], ptr [[DOTCAPTURE_EXPR_13]], align 4 -// CHECK2-NEXT: [[TMP69:%.*]] = load i32, ptr [[DOTCAPTURE_EXPR_13]], align 4 -// CHECK2-NEXT: [[ADD17:%.*]] = add nsw i32 [[TMP69]], 1 -// CHECK2-NEXT: [[TMP70:%.*]] = zext i32 [[ADD17]] to i64 -// CHECK2-NEXT: [[TMP71:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS18]], i32 0, i32 0 -// CHECK2-NEXT: store i32 3, ptr [[TMP71]], align 4 -// CHECK2-NEXT: [[TMP72:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS18]], i32 0, i32 1 -// CHECK2-NEXT: store i32 3, ptr [[TMP72]], align 4 -// CHECK2-NEXT: [[TMP73:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS18]], i32 0, i32 2 -// CHECK2-NEXT: store ptr [[TMP64]], ptr [[TMP73]], align 4 -// CHECK2-NEXT: [[TMP74:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS18]], i32 0, i32 3 -// CHECK2-NEXT: store ptr [[TMP65]], ptr [[TMP74]], align 4 -// CHECK2-NEXT: [[TMP75:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS18]], i32 0, i32 4 -// CHECK2-NEXT: store ptr [[TMP66]], ptr [[TMP75]], align 4 -// CHECK2-NEXT: [[TMP76:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS18]], i32 0, i32 5 -// CHECK2-NEXT: store ptr @.offload_maptypes.2, ptr [[TMP76]], align 4 -// CHECK2-NEXT: [[TMP77:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS18]], i32 0, i32 6 -// CHECK2-NEXT: store ptr null, ptr [[TMP77]], align 4 -// CHECK2-NEXT: [[TMP78:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS18]], i32 0, i32 7 -// CHECK2-NEXT: store ptr null, ptr [[TMP78]], align 4 -// CHECK2-NEXT: [[TMP79:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS18]], i32 0, i32 8 -// CHECK2-NEXT: store i64 [[TMP70]], ptr [[TMP79]], align 8 -// CHECK2-NEXT: [[TMP80:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS18]], i32 0, i32 9 -// CHECK2-NEXT: store i64 0, ptr [[TMP80]], align 8 -// CHECK2-NEXT: [[TMP81:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS18]], i32 0, i32 10 -// CHECK2-NEXT: store [3 x i32] zeroinitializer, ptr [[TMP81]], align 4 -// CHECK2-NEXT: [[TMP82:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS18]], i32 0, i32 11 -// CHECK2-NEXT: store [3 x i32] zeroinitializer, ptr [[TMP82]], align 4 -// CHECK2-NEXT: [[TMP83:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS18]], i32 0, i32 12 -// CHECK2-NEXT: store i32 0, ptr [[TMP83]], align 4 -// CHECK2-NEXT: [[TMP84:%.*]] = call i32 @__tgt_target_kernel(ptr @[[GLOB4]], i64 -1, i32 0, i32 0, ptr @.{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z3sumPiiS__l73.region_id, ptr [[KERNEL_ARGS18]]) -// CHECK2-NEXT: [[TMP85:%.*]] = icmp ne i32 [[TMP84]], 0 -// CHECK2-NEXT: br i1 [[TMP85]], label [[OMP_OFFLOAD_FAILED19:%.*]], label [[OMP_OFFLOAD_CONT20:%.*]] +// CHECK2-NEXT: [[TMP81:%.*]] = load i32, ptr [[DOTCAPTURE_EXPR_13]], align 4 +// CHECK2-NEXT: [[ADD17:%.*]] = add nsw i32 [[TMP81]], 1 +// CHECK2-NEXT: [[TMP82:%.*]] = zext i32 [[ADD17]] to i64 +// CHECK2-NEXT: [[TMP83:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS18]], i32 0, i32 0 +// CHECK2-NEXT: store i32 3, ptr [[TMP83]], align 4 +// CHECK2-NEXT: [[TMP84:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS18]], i32 0, i32 1 +// CHECK2-NEXT: store i32 5, ptr [[TMP84]], align 4 +// CHECK2-NEXT: [[TMP85:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS18]], i32 0, i32 2 +// CHECK2-NEXT: store ptr [[TMP76]], ptr [[TMP85]], align 4 +// CHECK2-NEXT: [[TMP86:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS18]], i32 0, i32 3 +// CHECK2-NEXT: store ptr [[TMP77]], ptr [[TMP86]], align 4 +// CHECK2-NEXT: [[TMP87:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS18]], i32 0, i32 4 +// CHECK2-NEXT: store ptr [[TMP78]], ptr [[TMP87]], align 4 +// CHECK2-NEXT: [[TMP88:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS18]], i32 0, i32 5 +// CHECK2-NEXT: store ptr @.offload_maptypes.2, ptr [[TMP88]], align 4 +// CHECK2-NEXT: [[TMP89:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS18]], i32 0, i32 6 +// CHECK2-NEXT: store ptr null, ptr [[TMP89]], align 4 +// CHECK2-NEXT: [[TMP90:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS18]], i32 0, i32 7 +// CHECK2-NEXT: store ptr null, ptr [[TMP90]], align 4 +// CHECK2-NEXT: [[TMP91:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS18]], i32 0, i32 8 +// CHECK2-NEXT: store i64 [[TMP82]], ptr [[TMP91]], align 8 +// CHECK2-NEXT: [[TMP92:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS18]], i32 0, i32 9 +// CHECK2-NEXT: store i64 0, ptr [[TMP92]], align 8 +// CHECK2-NEXT: [[TMP93:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS18]], i32 0, i32 10 +// CHECK2-NEXT: store [3 x i32] zeroinitializer, ptr [[TMP93]], align 4 +// CHECK2-NEXT: [[TMP94:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS18]], i32 0, i32 11 +// CHECK2-NEXT: store [3 x i32] zeroinitializer, ptr [[TMP94]], align 4 +// CHECK2-NEXT: [[TMP95:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS18]], i32 0, i32 12 +// CHECK2-NEXT: store i32 0, ptr [[TMP95]], align 4 +// CHECK2-NEXT: [[TMP96:%.*]] = call i32 @__tgt_target_kernel(ptr @[[GLOB4]], i64 -1, i32 0, i32 0, ptr @.{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z3sumPiiS__l73.region_id, ptr [[KERNEL_ARGS18]]) +// CHECK2-NEXT: [[TMP97:%.*]] = icmp ne i32 [[TMP96]], 0 +// CHECK2-NEXT: br i1 [[TMP97]], label [[OMP_OFFLOAD_FAILED19:%.*]], label [[OMP_OFFLOAD_CONT20:%.*]] // CHECK2: omp_offload.failed19: -// CHECK2-NEXT: call void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z3sumPiiS__l73(i32 [[TMP44]], ptr [[TMP45]], ptr [[TMP46]]) #[[ATTR2]] +// CHECK2-NEXT: call void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z3sumPiiS__l73(i32 [[TMP50]], ptr [[TMP51]], ptr [[TMP52]]) #[[ATTR2]] // CHECK2-NEXT: br label [[OMP_OFFLOAD_CONT20]] // CHECK2: omp_offload.cont20: -// CHECK2-NEXT: [[TMP86:%.*]] = load i32, ptr [[SIZE_ADDR]], align 4 -// CHECK2-NEXT: store i32 [[TMP86]], ptr [[SIZE_CASTED21]], align 4 -// CHECK2-NEXT: [[TMP87:%.*]] = load i32, ptr [[SIZE_CASTED21]], align 4 +// CHECK2-NEXT: [[TMP98:%.*]] = load i32, ptr [[SIZE_ADDR]], align 4 +// CHECK2-NEXT: store i32 [[TMP98]], ptr [[SIZE_CASTED21]], align 4 +// CHECK2-NEXT: [[TMP99:%.*]] = load i32, ptr [[SIZE_CASTED21]], align 4 // CHECK2-NEXT: [[ARRAYIDX22:%.*]] = getelementptr inbounds nuw [10 x i32], ptr [[A]], i32 0, i32 0 -// CHECK2-NEXT: [[TMP88:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS23]], i32 0, i32 0 -// CHECK2-NEXT: store i32 [[TMP87]], ptr [[TMP88]], align 4 -// CHECK2-NEXT: [[TMP89:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS24]], i32 0, i32 0 -// CHECK2-NEXT: store i32 [[TMP87]], ptr [[TMP89]], align 4 -// CHECK2-NEXT: [[TMP90:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS25]], i32 0, i32 0 -// CHECK2-NEXT: store ptr null, ptr [[TMP90]], align 4 -// CHECK2-NEXT: [[TMP91:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS23]], i32 0, i32 1 -// CHECK2-NEXT: store ptr [[A]], ptr [[TMP91]], align 4 -// CHECK2-NEXT: [[TMP92:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS24]], i32 0, i32 1 -// CHECK2-NEXT: store ptr [[ARRAYIDX22]], ptr [[TMP92]], align 4 -// CHECK2-NEXT: [[TMP93:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS25]], i32 0, i32 1 -// CHECK2-NEXT: store ptr null, ptr [[TMP93]], align 4 -// CHECK2-NEXT: [[TMP94:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS23]], i32 0, i32 0 -// CHECK2-NEXT: [[TMP95:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS24]], i32 0, i32 0 -// CHECK2-NEXT: [[TMP96:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS26]], i32 0, i32 0 -// CHECK2-NEXT: store i32 3, ptr [[TMP96]], align 4 -// CHECK2-NEXT: [[TMP97:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS26]], i32 0, i32 1 -// CHECK2-NEXT: store i32 2, ptr [[TMP97]], align 4 -// CHECK2-NEXT: [[TMP98:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS26]], i32 0, i32 2 -// CHECK2-NEXT: store ptr [[TMP94]], ptr [[TMP98]], align 4 -// CHECK2-NEXT: [[TMP99:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS26]], i32 0, i32 3 -// CHECK2-NEXT: store ptr [[TMP95]], ptr [[TMP99]], align 4 -// CHECK2-NEXT: [[TMP100:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS26]], i32 0, i32 4 -// CHECK2-NEXT: store ptr @.offload_sizes.3, ptr [[TMP100]], align 4 -// CHECK2-NEXT: [[TMP101:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS26]], i32 0, i32 5 -// CHECK2-NEXT: store ptr @.offload_maptypes.4, ptr [[TMP101]], align 4 -// CHECK2-NEXT: [[TMP102:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS26]], i32 0, i32 6 +// CHECK2-NEXT: [[TMP100:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS23]], i32 0, i32 0 +// CHECK2-NEXT: store i32 [[TMP99]], ptr [[TMP100]], align 4 +// CHECK2-NEXT: [[TMP101:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS24]], i32 0, i32 0 +// CHECK2-NEXT: store i32 [[TMP99]], ptr [[TMP101]], align 4 +// CHECK2-NEXT: [[TMP102:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS25]], i32 0, i32 0 // CHECK2-NEXT: store ptr null, ptr [[TMP102]], align 4 -// CHECK2-NEXT: [[TMP103:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS26]], i32 0, i32 7 -// CHECK2-NEXT: store ptr null, ptr [[TMP103]], align 4 -// CHECK2-NEXT: [[TMP104:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS26]], i32 0, i32 8 -// CHECK2-NEXT: store i64 0, ptr [[TMP104]], align 8 -// CHECK2-NEXT: [[TMP105:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS26]], i32 0, i32 9 -// CHECK2-NEXT: store i64 0, ptr [[TMP105]], align 8 -// CHECK2-NEXT: [[TMP106:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS26]], i32 0, i32 10 -// CHECK2-NEXT: store [3 x i32] [i32 1, i32 0, i32 0], ptr [[TMP106]], align 4 -// CHECK2-NEXT: [[TMP107:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS26]], i32 0, i32 11 -// CHECK2-NEXT: store [3 x i32] zeroinitializer, ptr [[TMP107]], align 4 -// CHECK2-NEXT: [[TMP108:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS26]], i32 0, i32 12 -// CHECK2-NEXT: store i32 0, ptr [[TMP108]], align 4 -// CHECK2-NEXT: [[TMP109:%.*]] = call i32 @__tgt_target_kernel(ptr @[[GLOB4]], i64 -1, i32 1, i32 0, ptr @.{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z3sumPiiS__l78.region_id, ptr [[KERNEL_ARGS26]]) -// CHECK2-NEXT: [[TMP110:%.*]] = icmp ne i32 [[TMP109]], 0 -// CHECK2-NEXT: br i1 [[TMP110]], label [[OMP_OFFLOAD_FAILED27:%.*]], label [[OMP_OFFLOAD_CONT28:%.*]] +// CHECK2-NEXT: [[TMP103:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS23]], i32 0, i32 1 +// CHECK2-NEXT: store ptr [[A]], ptr [[TMP103]], align 4 +// CHECK2-NEXT: [[TMP104:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS24]], i32 0, i32 1 +// CHECK2-NEXT: store ptr [[ARRAYIDX22]], ptr [[TMP104]], align 4 +// CHECK2-NEXT: [[TMP105:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS25]], i32 0, i32 1 +// CHECK2-NEXT: store ptr null, ptr [[TMP105]], align 4 +// CHECK2-NEXT: [[TMP106:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS23]], i32 0, i32 0 +// CHECK2-NEXT: [[TMP107:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS24]], i32 0, i32 0 +// CHECK2-NEXT: [[TMP108:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS26]], i32 0, i32 0 +// CHECK2-NEXT: store i32 3, ptr [[TMP108]], align 4 +// CHECK2-NEXT: [[TMP109:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS26]], i32 0, i32 1 +// CHECK2-NEXT: store i32 2, ptr [[TMP109]], align 4 +// CHECK2-NEXT: [[TMP110:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS26]], i32 0, i32 2 +// CHECK2-NEXT: store ptr [[TMP106]], ptr [[TMP110]], align 4 +// CHECK2-NEXT: [[TMP111:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS26]], i32 0, i32 3 +// CHECK2-NEXT: store ptr [[TMP107]], ptr [[TMP111]], align 4 +// CHECK2-NEXT: [[TMP112:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS26]], i32 0, i32 4 +// CHECK2-NEXT: store ptr @.offload_sizes.3, ptr [[TMP112]], align 4 +// CHECK2-NEXT: [[TMP113:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS26]], i32 0, i32 5 +// CHECK2-NEXT: store ptr @.offload_maptypes.4, ptr [[TMP113]], align 4 +// CHECK2-NEXT: [[TMP114:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS26]], i32 0, i32 6 +// CHECK2-NEXT: store ptr null, ptr [[TMP114]], align 4 +// CHECK2-NEXT: [[TMP115:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS26]], i32 0, i32 7 +// CHECK2-NEXT: store ptr null, ptr [[TMP115]], align 4 +// CHECK2-NEXT: [[TMP116:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS26]], i32 0, i32 8 +// CHECK2-NEXT: store i64 0, ptr [[TMP116]], align 8 +// CHECK2-NEXT: [[TMP117:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS26]], i32 0, i32 9 +// CHECK2-NEXT: store i64 0, ptr [[TMP117]], align 8 +// CHECK2-NEXT: [[TMP118:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS26]], i32 0, i32 10 +// CHECK2-NEXT: store [3 x i32] [i32 1, i32 0, i32 0], ptr [[TMP118]], align 4 +// CHECK2-NEXT: [[TMP119:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS26]], i32 0, i32 11 +// CHECK2-NEXT: store [3 x i32] zeroinitializer, ptr [[TMP119]], align 4 +// CHECK2-NEXT: [[TMP120:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS26]], i32 0, i32 12 +// CHECK2-NEXT: store i32 0, ptr [[TMP120]], align 4 +// CHECK2-NEXT: [[TMP121:%.*]] = call i32 @__tgt_target_kernel(ptr @[[GLOB4]], i64 -1, i32 1, i32 0, ptr @.{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z3sumPiiS__l78.region_id, ptr [[KERNEL_ARGS26]]) +// CHECK2-NEXT: [[TMP122:%.*]] = icmp ne i32 [[TMP121]], 0 +// CHECK2-NEXT: br i1 [[TMP122]], label [[OMP_OFFLOAD_FAILED27:%.*]], label [[OMP_OFFLOAD_CONT28:%.*]] // CHECK2: omp_offload.failed27: -// CHECK2-NEXT: call void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z3sumPiiS__l78(i32 [[TMP87]], ptr [[A]]) #[[ATTR2]] +// CHECK2-NEXT: call void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z3sumPiiS__l78(i32 [[TMP99]], ptr [[A]]) #[[ATTR2]] // CHECK2-NEXT: br label [[OMP_OFFLOAD_CONT28]] // CHECK2: omp_offload.cont28: -// CHECK2-NEXT: [[TMP111:%.*]] = load i32, ptr [[SIZE_ADDR]], align 4 -// CHECK2-NEXT: store i32 [[TMP111]], ptr [[SIZE_CASTED29]], align 4 -// CHECK2-NEXT: [[TMP112:%.*]] = load i32, ptr [[SIZE_CASTED29]], align 4 +// CHECK2-NEXT: [[TMP123:%.*]] = load i32, ptr [[SIZE_ADDR]], align 4 +// CHECK2-NEXT: store i32 [[TMP123]], ptr [[SIZE_CASTED29]], align 4 +// CHECK2-NEXT: [[TMP124:%.*]] = load i32, ptr [[SIZE_CASTED29]], align 4 // CHECK2-NEXT: [[ARRAYIDX30:%.*]] = getelementptr inbounds [10 x i32], ptr [[A]], i32 0, i32 3 -// CHECK2-NEXT: [[TMP113:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS31]], i32 0, i32 0 -// CHECK2-NEXT: store i32 [[TMP112]], ptr [[TMP113]], align 4 -// CHECK2-NEXT: [[TMP114:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS32]], i32 0, i32 0 -// CHECK2-NEXT: store i32 [[TMP112]], ptr [[TMP114]], align 4 -// CHECK2-NEXT: [[TMP115:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS33]], i32 0, i32 0 -// CHECK2-NEXT: store ptr null, ptr [[TMP115]], align 4 -// CHECK2-NEXT: [[TMP116:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS31]], i32 0, i32 1 -// CHECK2-NEXT: store ptr [[A]], ptr [[TMP116]], align 4 -// CHECK2-NEXT: [[TMP117:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS32]], i32 0, i32 1 -// CHECK2-NEXT: store ptr [[ARRAYIDX30]], ptr [[TMP117]], align 4 -// CHECK2-NEXT: [[TMP118:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS33]], i32 0, i32 1 -// CHECK2-NEXT: store ptr null, ptr [[TMP118]], align 4 -// CHECK2-NEXT: [[TMP119:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS31]], i32 0, i32 0 -// CHECK2-NEXT: [[TMP120:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS32]], i32 0, i32 0 -// CHECK2-NEXT: [[TMP121:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS34]], i32 0, i32 0 -// CHECK2-NEXT: store i32 3, ptr [[TMP121]], align 4 -// CHECK2-NEXT: [[TMP122:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS34]], i32 0, i32 1 -// CHECK2-NEXT: store i32 2, ptr [[TMP122]], align 4 -// CHECK2-NEXT: [[TMP123:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS34]], i32 0, i32 2 -// CHECK2-NEXT: store ptr [[TMP119]], ptr [[TMP123]], align 4 -// CHECK2-NEXT: [[TMP124:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS34]], i32 0, i32 3 -// CHECK2-NEXT: store ptr [[TMP120]], ptr [[TMP124]], align 4 -// CHECK2-NEXT: [[TMP125:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS34]], i32 0, i32 4 -// CHECK2-NEXT: store ptr @.offload_sizes.5, ptr [[TMP125]], align 4 -// CHECK2-NEXT: [[TMP126:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS34]], i32 0, i32 5 -// CHECK2-NEXT: store ptr @.offload_maptypes.6, ptr [[TMP126]], align 4 -// CHECK2-NEXT: [[TMP127:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS34]], i32 0, i32 6 +// CHECK2-NEXT: [[TMP125:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS31]], i32 0, i32 0 +// CHECK2-NEXT: store i32 [[TMP124]], ptr [[TMP125]], align 4 +// CHECK2-NEXT: [[TMP126:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS32]], i32 0, i32 0 +// CHECK2-NEXT: store i32 [[TMP124]], ptr [[TMP126]], align 4 +// CHECK2-NEXT: [[TMP127:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS33]], i32 0, i32 0 // CHECK2-NEXT: store ptr null, ptr [[TMP127]], align 4 -// CHECK2-NEXT: [[TMP128:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS34]], i32 0, i32 7 -// CHECK2-NEXT: store ptr null, ptr [[TMP128]], align 4 -// CHECK2-NEXT: [[TMP129:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS34]], i32 0, i32 8 -// CHECK2-NEXT: store i64 0, ptr [[TMP129]], align 8 -// CHECK2-NEXT: [[TMP130:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS34]], i32 0, i32 9 -// CHECK2-NEXT: store i64 0, ptr [[TMP130]], align 8 -// CHECK2-NEXT: [[TMP131:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS34]], i32 0, i32 10 -// CHECK2-NEXT: store [3 x i32] [i32 1, i32 0, i32 0], ptr [[TMP131]], align 4 -// CHECK2-NEXT: [[TMP132:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS34]], i32 0, i32 11 -// CHECK2-NEXT: store [3 x i32] zeroinitializer, ptr [[TMP132]], align 4 -// CHECK2-NEXT: [[TMP133:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS34]], i32 0, i32 12 -// CHECK2-NEXT: store i32 0, ptr [[TMP133]], align 4 -// CHECK2-NEXT: [[TMP134:%.*]] = call i32 @__tgt_target_kernel(ptr @[[GLOB4]], i64 -1, i32 1, i32 0, ptr @.{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z3sumPiiS__l81.region_id, ptr [[KERNEL_ARGS34]]) -// CHECK2-NEXT: [[TMP135:%.*]] = icmp ne i32 [[TMP134]], 0 -// CHECK2-NEXT: br i1 [[TMP135]], label [[OMP_OFFLOAD_FAILED35:%.*]], label [[OMP_OFFLOAD_CONT36:%.*]] +// CHECK2-NEXT: [[TMP128:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS31]], i32 0, i32 1 +// CHECK2-NEXT: store ptr [[A]], ptr [[TMP128]], align 4 +// CHECK2-NEXT: [[TMP129:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS32]], i32 0, i32 1 +// CHECK2-NEXT: store ptr [[ARRAYIDX30]], ptr [[TMP129]], align 4 +// CHECK2-NEXT: [[TMP130:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS33]], i32 0, i32 1 +// CHECK2-NEXT: store ptr null, ptr [[TMP130]], align 4 +// CHECK2-NEXT: [[TMP131:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS31]], i32 0, i32 0 +// CHECK2-NEXT: [[TMP132:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS32]], i32 0, i32 0 +// CHECK2-NEXT: [[TMP133:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS34]], i32 0, i32 0 +// CHECK2-NEXT: store i32 3, ptr [[TMP133]], align 4 +// CHECK2-NEXT: [[TMP134:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS34]], i32 0, i32 1 +// CHECK2-NEXT: store i32 2, ptr [[TMP134]], align 4 +// CHECK2-NEXT: [[TMP135:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS34]], i32 0, i32 2 +// CHECK2-NEXT: store ptr [[TMP131]], ptr [[TMP135]], align 4 +// CHECK2-NEXT: [[TMP136:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS34]], i32 0, i32 3 +// CHECK2-NEXT: store ptr [[TMP132]], ptr [[TMP136]], align 4 +// CHECK2-NEXT: [[TMP137:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS34]], i32 0, i32 4 +// CHECK2-NEXT: store ptr @.offload_sizes.5, ptr [[TMP137]], align 4 +// CHECK2-NEXT: [[TMP138:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS34]], i32 0, i32 5 +// CHECK2-NEXT: store ptr @.offload_maptypes.6, ptr [[TMP138]], align 4 +// CHECK2-NEXT: [[TMP139:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS34]], i32 0, i32 6 +// CHECK2-NEXT: store ptr null, ptr [[TMP139]], align 4 +// CHECK2-NEXT: [[TMP140:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS34]], i32 0, i32 7 +// CHECK2-NEXT: store ptr null, ptr [[TMP140]], align 4 +// CHECK2-NEXT: [[TMP141:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS34]], i32 0, i32 8 +// CHECK2-NEXT: store i64 0, ptr [[TMP141]], align 8 +// CHECK2-NEXT: [[TMP142:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS34]], i32 0, i32 9 +// CHECK2-NEXT: store i64 0, ptr [[TMP142]], align 8 +// CHECK2-NEXT: [[TMP143:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS34]], i32 0, i32 10 +// CHECK2-NEXT: store [3 x i32] [i32 1, i32 0, i32 0], ptr [[TMP143]], align 4 +// CHECK2-NEXT: [[TMP144:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS34]], i32 0, i32 11 +// CHECK2-NEXT: store [3 x i32] zeroinitializer, ptr [[TMP144]], align 4 +// CHECK2-NEXT: [[TMP145:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS34]], i32 0, i32 12 +// CHECK2-NEXT: store i32 0, ptr [[TMP145]], align 4 +// CHECK2-NEXT: [[TMP146:%.*]] = call i32 @__tgt_target_kernel(ptr @[[GLOB4]], i64 -1, i32 1, i32 0, ptr @.{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z3sumPiiS__l81.region_id, ptr [[KERNEL_ARGS34]]) +// CHECK2-NEXT: [[TMP147:%.*]] = icmp ne i32 [[TMP146]], 0 +// CHECK2-NEXT: br i1 [[TMP147]], label [[OMP_OFFLOAD_FAILED35:%.*]], label [[OMP_OFFLOAD_CONT36:%.*]] // CHECK2: omp_offload.failed35: -// CHECK2-NEXT: call void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z3sumPiiS__l81(i32 [[TMP112]], ptr [[A]]) #[[ATTR2]] +// CHECK2-NEXT: call void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z3sumPiiS__l81(i32 [[TMP124]], ptr [[A]]) #[[ATTR2]] // CHECK2-NEXT: br label [[OMP_OFFLOAD_CONT36]] // CHECK2: omp_offload.cont36: // CHECK2-NEXT: ret void @@ -1855,7 +1894,7 @@ int main() // CHECK2-NEXT: [[SIZE_CASTED:%.*]] = alloca i32, align 4 // CHECK2-NEXT: store i32 [[SIZE]], ptr [[SIZE_ADDR]], align 4 // CHECK2-NEXT: store ptr [[A]], ptr [[A_ADDR]], align 4 -// CHECK2-NEXT: [[TMP0:%.*]] = load ptr, ptr [[A_ADDR]], align 4 +// CHECK2-NEXT: [[TMP0:%.*]] = load ptr, ptr [[A_ADDR]], align 4, !nonnull [[META14:![0-9]+]], !align [[META15:![0-9]+]] // CHECK2-NEXT: [[TMP1:%.*]] = load i32, ptr [[SIZE_ADDR]], align 4 // CHECK2-NEXT: store i32 [[TMP1]], ptr [[SIZE_CASTED]], align 4 // CHECK2-NEXT: [[TMP2:%.*]] = load i32, ptr [[SIZE_CASTED]], align 4 @@ -1877,7 +1916,7 @@ int main() // CHECK2-NEXT: store ptr [[DOTBOUND_TID_]], ptr [[DOTBOUND_TID__ADDR]], align 4 // CHECK2-NEXT: store i32 [[SIZE]], ptr [[SIZE_ADDR]], align 4 // CHECK2-NEXT: store ptr [[A]], ptr [[A_ADDR]], align 4 -// CHECK2-NEXT: [[TMP0:%.*]] = load ptr, ptr [[A_ADDR]], align 4 +// CHECK2-NEXT: [[TMP0:%.*]] = load ptr, ptr [[A_ADDR]], align 4, !nonnull [[META14]], !align [[META15]] // CHECK2-NEXT: [[ARRAYIDX:%.*]] = getelementptr inbounds nuw [10 x i32], ptr [[TMP0]], i32 0, i32 0 // CHECK2-NEXT: [[ARRAYIDX1:%.*]] = getelementptr inbounds nuw [10 x i32], ptr [[TMP0]], i32 0, i32 1 // CHECK2-NEXT: [[ARRAY_BEGIN:%.*]] = getelementptr inbounds [2 x i32], ptr [[A2]], i32 0, i32 0 @@ -1909,7 +1948,7 @@ int main() // CHECK2-NEXT: [[TMP9:%.*]] = load i32, ptr [[I]], align 4 // CHECK2-NEXT: [[INC:%.*]] = add nsw i32 [[TMP9]], 1 // CHECK2-NEXT: store i32 [[INC]], ptr [[I]], align 4 -// CHECK2-NEXT: br label [[FOR_COND]], !llvm.loop [[LOOP10:![0-9]+]] +// CHECK2-NEXT: br label [[FOR_COND]], !llvm.loop [[LOOP16:![0-9]+]] // CHECK2: for.end: // CHECK2-NEXT: [[TMP10:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOMP_REDUCTION_RED_LIST]], i32 0, i32 0 // CHECK2-NEXT: store ptr [[A2]], ptr [[TMP10]], align 4 @@ -1996,7 +2035,7 @@ int main() // CHECK2-NEXT: [[SIZE_CASTED:%.*]] = alloca i32, align 4 // CHECK2-NEXT: store i32 [[SIZE]], ptr [[SIZE_ADDR]], align 4 // CHECK2-NEXT: store ptr [[A]], ptr [[A_ADDR]], align 4 -// CHECK2-NEXT: [[TMP0:%.*]] = load ptr, ptr [[A_ADDR]], align 4 +// CHECK2-NEXT: [[TMP0:%.*]] = load ptr, ptr [[A_ADDR]], align 4, !nonnull [[META14]], !align [[META15]] // CHECK2-NEXT: [[TMP1:%.*]] = load i32, ptr [[SIZE_ADDR]], align 4 // CHECK2-NEXT: store i32 [[TMP1]], ptr [[SIZE_CASTED]], align 4 // CHECK2-NEXT: [[TMP2:%.*]] = load i32, ptr [[SIZE_CASTED]], align 4 @@ -2018,7 +2057,7 @@ int main() // CHECK2-NEXT: store ptr [[DOTBOUND_TID_]], ptr [[DOTBOUND_TID__ADDR]], align 4 // CHECK2-NEXT: store i32 [[SIZE]], ptr [[SIZE_ADDR]], align 4 // CHECK2-NEXT: store ptr [[A]], ptr [[A_ADDR]], align 4 -// CHECK2-NEXT: [[TMP0:%.*]] = load ptr, ptr [[A_ADDR]], align 4 +// CHECK2-NEXT: [[TMP0:%.*]] = load ptr, ptr [[A_ADDR]], align 4, !nonnull [[META14]], !align [[META15]] // CHECK2-NEXT: [[ARRAYIDX:%.*]] = getelementptr inbounds [10 x i32], ptr [[TMP0]], i32 0, i32 3 // CHECK2-NEXT: store i32 0, ptr [[A1]], align 4 // CHECK2-NEXT: [[TMP1:%.*]] = ptrtoint ptr [[TMP0]] to i64 @@ -2039,7 +2078,7 @@ int main() // CHECK2-NEXT: [[TMP8:%.*]] = load i32, ptr [[I]], align 4 // CHECK2-NEXT: [[INC:%.*]] = add nsw i32 [[TMP8]], 1 // CHECK2-NEXT: store i32 [[INC]], ptr [[I]], align 4 -// CHECK2-NEXT: br label [[FOR_COND]], !llvm.loop [[LOOP12:![0-9]+]] +// CHECK2-NEXT: br label [[FOR_COND]], !llvm.loop [[LOOP18:![0-9]+]] // CHECK2: for.end: // CHECK2-NEXT: [[TMP9:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOMP_REDUCTION_RED_LIST]], i32 0, i32 0 // CHECK2-NEXT: store ptr [[A1]], ptr [[TMP9]], align 4 diff --git a/clang/test/OpenMP/target_data_codegen.cpp b/clang/test/OpenMP/target_data_codegen.cpp index 926aa593f2ba1..b1da245110fb1 100644 --- a/clang/test/OpenMP/target_data_codegen.cpp +++ b/clang/test/OpenMP/target_data_codegen.cpp @@ -625,8 +625,8 @@ void test_present_modifier(int arg) { // Make sure the struct picks up present even if another element of the struct // doesn't have present. - // CK8: private unnamed_addr constant [11 x i64] [i64 0, i64 {{4|8}}, i64 {{4|8}}, i64 4, i64 4, i64 4, i64 0, i64 4, i64 {{4|8}}, i64 {{4|8}}, i64 4] - // CK8: private unnamed_addr constant [11 x i64] + // CK8: private unnamed_addr constant [13 x i64] [i64 0, i64 {{4|8}}, i64 {{4|8}}, i64 4, i64 4, i64 {{4|8}}, i64 4, i64 0, i64 4, i64 {{4|8}}, i64 {{4|8}}, i64 4, i64 {{8|4}}] + // CK8: private unnamed_addr constant [13 x i64] // ps1 // @@ -635,9 +635,11 @@ void test_present_modifier(int arg) { // PRESENT=0x1000 | PTR_AND_OBJ=0x10 = 0x1010 // PRESENT=0x1000 | PTR_AND_OBJ=0x10 | FROM=0x2 | TO=0x1 = 0x1013 // MEMBER_OF_1=0x1000000000000 | FROM=0x2 | TO=0x1 = 0x1000000000003 +// ATTACH=0x4000 // // CK8-SAME: {{^}} [i64 [[#0x1000]], i64 [[#0x1000000001010]], // CK8-SAME: {{^}} i64 [[#0x1010]], i64 [[#0x1013]], i64 [[#0x1000000000003]], +// CK8-SAME: {{^}} i64 [[#0x4000]], // arg // @@ -648,13 +650,15 @@ void test_present_modifier(int arg) { // ps2 // // PRESENT=0x1000 = 0x1000 -// MEMBER_OF_7=0x7000000000000 | PRESENT=0x1000 | FROM=0x2 | TO=0x1 = 0x7000000001003 -// MEMBER_OF_7=0x7000000000000 | PTR_AND_OBJ=0x10 = 0x7000000000010 +// MEMBER_OF_8=0x8000000000000 | PRESENT=0x1000 | FROM=0x2 | TO=0x1 = 0x8000000001003 +// MEMBER_OF_8=0x8000000000000 | PTR_AND_OBJ=0x10 = 0x8000000000010 // PTR_AND_OBJ=0x10 = 0x10 // PTR_AND_OBJ=0x10 | FROM=0x2 | TO=0x1 = 0x13 +// ATTACH=0x4000 // -// CK8-SAME: {{^}} i64 [[#0x1000]], i64 [[#0x7000000001003]], -// CK8-SAME: {{^}} i64 [[#0x7000000000010]], i64 [[#0x10]], i64 [[#0x13]]] +// CK8-SAME: {{^}} i64 [[#0x1000]], i64 [[#0x8000000001003]], +// CK8-SAME: {{^}} i64 [[#0x8000000000010]], i64 [[#0x10]], i64 [[#0x13]], +// CK8-SAME: {{^}} i64 [[#0x4000]]] #pragma omp target data map(tofrom \ : ps1->s) \ map(present, tofrom \ diff --git a/clang/test/OpenMP/target_data_map_codegen_hold.cpp b/clang/test/OpenMP/target_data_map_codegen_hold.cpp index 3b115acaa2afb..4b8b2f0a059e6 100644 --- a/clang/test/OpenMP/target_data_map_codegen_hold.cpp +++ b/clang/test/OpenMP/target_data_map_codegen_hold.cpp @@ -49,8 +49,9 @@ struct S2 { // PTR_AND_OBJ = 0x10 // CLOSE = 0x400 // OMPX_HOLD = 0x2000 +// ATTACH = 0x4000 // MEMBER_OF_1 = 0x1000000000000 -// MEMBER_OF_7 = 0x7000000000000 +// MEMBER_OF_8 = 0x8000000000000 //. // CHECK-PPC64LE: @.offload_sizes = private unnamed_addr constant [1 x i64] [i64 20] @@ -59,8 +60,8 @@ struct S2 { // CHECK-PPC64LE: @.offload_maptypes.2 = private unnamed_addr constant [1 x i64] [i64 [[#0x2405]]] // CHECK-PPC64LE: @.offload_sizes.3 = private unnamed_addr constant [1 x i64] [i64 4] // CHECK-PPC64LE: @.offload_maptypes.4 = private unnamed_addr constant [1 x i64] [i64 [[#0x2003]]] -// CHECK-PPC64LE: @.offload_sizes.5 = private unnamed_addr constant [11 x i64] [i64 0, i64 4, i64 8, i64 8, i64 4, i64 4, i64 0, i64 4, i64 8, i64 8, i64 4] -// CHECK-PPC64LE: @.offload_maptypes.6 = private unnamed_addr constant [11 x i64] [i64 [[#0x2000]], i64 [[#0x1000000002003]], i64 [[#0x1000000002010]], i64 [[#0x2010]], i64 [[#0x2013]], i64 [[#0x3]], i64 [[#0x2000]], i64 [[#0x7000000002003]], i64 [[#0x7000000002010]], i64 [[#0x2010]], i64 [[#0x2013]]] +// CHECK-PPC64LE: @.offload_sizes.5 = private unnamed_addr constant [13 x i64] [i64 0, i64 4, i64 8, i64 8, i64 4, i64 8, i64 4, i64 0, i64 4, i64 8, i64 8, i64 4, i64 8] +// CHECK-PPC64LE: @.offload_maptypes.6 = private unnamed_addr constant [13 x i64] [i64 [[#0x2000]], i64 [[#0x1000000002003]], i64 [[#0x1000000002010]], i64 [[#0x2010]], i64 [[#0x2013]], i64 [[#0x4000]], i64 [[#0x3]], i64 [[#0x2000]], i64 [[#0x8000000002003]], i64 [[#0x8000000002010]], i64 [[#0x2010]], i64 [[#0x2013]], i64 [[#0x4000]]] //. // CHECK-I386: @.offload_sizes = private unnamed_addr constant [1 x i64] [i64 20] // CHECK-I386: @.offload_maptypes = private unnamed_addr constant [1 x i64] [i64 [[#0x2001]]] @@ -68,8 +69,8 @@ struct S2 { // CHECK-I386: @.offload_maptypes.2 = private unnamed_addr constant [1 x i64] [i64 [[#0x2405]]] // CHECK-I386: @.offload_sizes.3 = private unnamed_addr constant [1 x i64] [i64 4] // CHECK-I386: @.offload_maptypes.4 = private unnamed_addr constant [1 x i64] [i64 [[#0x2003]]] -// CHECK-I386: @.offload_sizes.5 = private unnamed_addr constant [11 x i64] [i64 0, i64 4, i64 4, i64 4, i64 4, i64 4, i64 0, i64 4, i64 4, i64 4, i64 4] -// CHECK-I386: @.offload_maptypes.6 = private unnamed_addr constant [11 x i64] [i64 [[#0x2000]], i64 [[#0x1000000002003]], i64 [[#0x1000000002010]], i64 [[#0x2010]], i64 [[#0x2013]], i64 [[#0x3]], i64 [[#0x2000]], i64 [[#0x7000000002003]], i64 [[#0x7000000002010]], i64 [[#0x2010]], i64 [[#0x2013]]] +// CHECK-I386: @.offload_sizes.5 = private unnamed_addr constant [13 x i64] [i64 0, i64 4, i64 4, i64 4, i64 4, i64 4, i64 4, i64 0, i64 4, i64 4, i64 4, i64 4, i64 4] +// CHECK-I386: @.offload_maptypes.6 = private unnamed_addr constant [13 x i64] [i64 [[#0x2000]], i64 [[#0x1000000002003]], i64 [[#0x1000000002010]], i64 [[#0x2010]], i64 [[#0x2013]], i64 [[#0x4000]], i64 [[#0x3]], i64 [[#0x2000]], i64 [[#0x8000000002003]], i64 [[#0x8000000002010]], i64 [[#0x2010]], i64 [[#0x2013]], i64 [[#0x4000]]] //. // CHECK-PPC64LE-LABEL: @_Z3fooi( // CHECK-PPC64LE-NEXT: entry: @@ -86,10 +87,10 @@ struct S2 { // CHECK-PPC64LE-NEXT: [[DOTOFFLOAD_BASEPTRS5:%.*]] = alloca [1 x ptr], align 8 // CHECK-PPC64LE-NEXT: [[DOTOFFLOAD_PTRS6:%.*]] = alloca [1 x ptr], align 8 // CHECK-PPC64LE-NEXT: [[DOTOFFLOAD_MAPPERS7:%.*]] = alloca [1 x ptr], align 8 -// CHECK-PPC64LE-NEXT: [[DOTOFFLOAD_BASEPTRS29:%.*]] = alloca [11 x ptr], align 8 -// CHECK-PPC64LE-NEXT: [[DOTOFFLOAD_PTRS30:%.*]] = alloca [11 x ptr], align 8 -// CHECK-PPC64LE-NEXT: [[DOTOFFLOAD_MAPPERS31:%.*]] = alloca [11 x ptr], align 8 -// CHECK-PPC64LE-NEXT: [[DOTOFFLOAD_SIZES:%.*]] = alloca [11 x i64], align 8 +// CHECK-PPC64LE-NEXT: [[DOTOFFLOAD_BASEPTRS29:%.*]] = alloca [13 x ptr], align 8 +// CHECK-PPC64LE-NEXT: [[DOTOFFLOAD_PTRS30:%.*]] = alloca [13 x ptr], align 8 +// CHECK-PPC64LE-NEXT: [[DOTOFFLOAD_MAPPERS31:%.*]] = alloca [13 x ptr], align 8 +// CHECK-PPC64LE-NEXT: [[DOTOFFLOAD_SIZES:%.*]] = alloca [13 x i64], align 8 // CHECK-PPC64LE-NEXT: store i32 [[ARG:%.*]], ptr [[ARG_ADDR]], align 4 // CHECK-PPC64LE-NEXT: [[TMP0:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 // CHECK-PPC64LE-NEXT: store ptr [[LB]], ptr [[TMP0]], align 8 @@ -194,88 +195,100 @@ struct S2 { // CHECK-PPC64LE-NEXT: [[TMP57:%.*]] = ptrtoint ptr [[S18]] to i64 // CHECK-PPC64LE-NEXT: [[TMP58:%.*]] = sub i64 [[TMP56]], [[TMP57]] // CHECK-PPC64LE-NEXT: [[TMP59:%.*]] = sdiv exact i64 [[TMP58]], ptrtoint (ptr getelementptr (i8, ptr null, i32 1) to i64) -// CHECK-PPC64LE-NEXT: call void @llvm.memcpy.p0.p0.i64(ptr align 8 [[DOTOFFLOAD_SIZES]], ptr align 8 @.offload_sizes.5, i64 88, i1 false) -// CHECK-PPC64LE-NEXT: [[TMP60:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 0 +// CHECK-PPC64LE-NEXT: call void @llvm.memcpy.p0.p0.i64(ptr align 8 [[DOTOFFLOAD_SIZES]], ptr align 8 @.offload_sizes.5, i64 104, i1 false) +// CHECK-PPC64LE-NEXT: [[TMP60:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 0 // CHECK-PPC64LE-NEXT: store ptr [[TMP24]], ptr [[TMP60]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP61:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 0 +// CHECK-PPC64LE-NEXT: [[TMP61:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 0 // CHECK-PPC64LE-NEXT: store ptr [[S]], ptr [[TMP61]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP62:%.*]] = getelementptr inbounds [11 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 0 +// CHECK-PPC64LE-NEXT: [[TMP62:%.*]] = getelementptr inbounds [13 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 0 // CHECK-PPC64LE-NEXT: store i64 [[TMP41]], ptr [[TMP62]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP63:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i64 0, i64 0 +// CHECK-PPC64LE-NEXT: [[TMP63:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i64 0, i64 0 // CHECK-PPC64LE-NEXT: store ptr null, ptr [[TMP63]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP64:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 1 +// CHECK-PPC64LE-NEXT: [[TMP64:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 1 // CHECK-PPC64LE-NEXT: store ptr [[TMP24]], ptr [[TMP64]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP65:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 1 +// CHECK-PPC64LE-NEXT: [[TMP65:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 1 // CHECK-PPC64LE-NEXT: store ptr [[S]], ptr [[TMP65]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP66:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i64 0, i64 1 +// CHECK-PPC64LE-NEXT: [[TMP66:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i64 0, i64 1 // CHECK-PPC64LE-NEXT: store ptr null, ptr [[TMP66]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP67:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 2 +// CHECK-PPC64LE-NEXT: [[TMP67:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 2 // CHECK-PPC64LE-NEXT: store ptr [[PS]], ptr [[TMP67]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP68:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 2 +// CHECK-PPC64LE-NEXT: [[TMP68:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 2 // CHECK-PPC64LE-NEXT: store ptr [[PS10]], ptr [[TMP68]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP69:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i64 0, i64 2 +// CHECK-PPC64LE-NEXT: [[TMP69:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i64 0, i64 2 // CHECK-PPC64LE-NEXT: store ptr null, ptr [[TMP69]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP70:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 3 +// CHECK-PPC64LE-NEXT: [[TMP70:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 3 // CHECK-PPC64LE-NEXT: store ptr [[PS10]], ptr [[TMP70]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP71:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 3 +// CHECK-PPC64LE-NEXT: [[TMP71:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 3 // CHECK-PPC64LE-NEXT: store ptr [[PS13]], ptr [[TMP71]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP72:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i64 0, i64 3 +// CHECK-PPC64LE-NEXT: [[TMP72:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i64 0, i64 3 // CHECK-PPC64LE-NEXT: store ptr null, ptr [[TMP72]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP73:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 4 +// CHECK-PPC64LE-NEXT: [[TMP73:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 4 // CHECK-PPC64LE-NEXT: store ptr [[PS13]], ptr [[TMP73]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP74:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 4 +// CHECK-PPC64LE-NEXT: [[TMP74:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 4 // CHECK-PPC64LE-NEXT: store ptr [[S17]], ptr [[TMP74]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP75:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i64 0, i64 4 +// CHECK-PPC64LE-NEXT: [[TMP75:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i64 0, i64 4 // CHECK-PPC64LE-NEXT: store ptr null, ptr [[TMP75]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP76:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 5 -// CHECK-PPC64LE-NEXT: store ptr [[ARG_ADDR]], ptr [[TMP76]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP77:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 5 -// CHECK-PPC64LE-NEXT: store ptr [[ARG_ADDR]], ptr [[TMP77]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP78:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i64 0, i64 5 +// CHECK-PPC64LE-NEXT: [[TMP76:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 5 +// CHECK-PPC64LE-NEXT: store ptr [[PS1]], ptr [[TMP76]], align 8 +// CHECK-PPC64LE-NEXT: [[TMP77:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 5 +// CHECK-PPC64LE-NEXT: store ptr [[S]], ptr [[TMP77]], align 8 +// CHECK-PPC64LE-NEXT: [[TMP78:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i64 0, i64 5 // CHECK-PPC64LE-NEXT: store ptr null, ptr [[TMP78]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP79:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 6 -// CHECK-PPC64LE-NEXT: store ptr [[TMP42]], ptr [[TMP79]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP80:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 6 -// CHECK-PPC64LE-NEXT: store ptr [[S18]], ptr [[TMP80]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP81:%.*]] = getelementptr inbounds [11 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 6 -// CHECK-PPC64LE-NEXT: store i64 [[TMP59]], ptr [[TMP81]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP82:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i64 0, i64 6 -// CHECK-PPC64LE-NEXT: store ptr null, ptr [[TMP82]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP83:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 7 -// CHECK-PPC64LE-NEXT: store ptr [[TMP42]], ptr [[TMP83]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP84:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 7 -// CHECK-PPC64LE-NEXT: store ptr [[S18]], ptr [[TMP84]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP85:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i64 0, i64 7 +// CHECK-PPC64LE-NEXT: [[TMP79:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 6 +// CHECK-PPC64LE-NEXT: store ptr [[ARG_ADDR]], ptr [[TMP79]], align 8 +// CHECK-PPC64LE-NEXT: [[TMP80:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 6 +// CHECK-PPC64LE-NEXT: store ptr [[ARG_ADDR]], ptr [[TMP80]], align 8 +// CHECK-PPC64LE-NEXT: [[TMP81:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i64 0, i64 6 +// CHECK-PPC64LE-NEXT: store ptr null, ptr [[TMP81]], align 8 +// CHECK-PPC64LE-NEXT: [[TMP82:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 7 +// CHECK-PPC64LE-NEXT: store ptr [[TMP42]], ptr [[TMP82]], align 8 +// CHECK-PPC64LE-NEXT: [[TMP83:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 7 +// CHECK-PPC64LE-NEXT: store ptr [[S18]], ptr [[TMP83]], align 8 +// CHECK-PPC64LE-NEXT: [[TMP84:%.*]] = getelementptr inbounds [13 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 7 +// CHECK-PPC64LE-NEXT: store i64 [[TMP59]], ptr [[TMP84]], align 8 +// CHECK-PPC64LE-NEXT: [[TMP85:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i64 0, i64 7 // CHECK-PPC64LE-NEXT: store ptr null, ptr [[TMP85]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP86:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 8 -// CHECK-PPC64LE-NEXT: store ptr [[PS19]], ptr [[TMP86]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP87:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 8 -// CHECK-PPC64LE-NEXT: store ptr [[PS21]], ptr [[TMP87]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP88:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i64 0, i64 8 +// CHECK-PPC64LE-NEXT: [[TMP86:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 8 +// CHECK-PPC64LE-NEXT: store ptr [[TMP42]], ptr [[TMP86]], align 8 +// CHECK-PPC64LE-NEXT: [[TMP87:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 8 +// CHECK-PPC64LE-NEXT: store ptr [[S18]], ptr [[TMP87]], align 8 +// CHECK-PPC64LE-NEXT: [[TMP88:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i64 0, i64 8 // CHECK-PPC64LE-NEXT: store ptr null, ptr [[TMP88]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP89:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 9 -// CHECK-PPC64LE-NEXT: store ptr [[PS21]], ptr [[TMP89]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP90:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 9 -// CHECK-PPC64LE-NEXT: store ptr [[PS24]], ptr [[TMP90]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP91:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i64 0, i64 9 +// CHECK-PPC64LE-NEXT: [[TMP89:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 9 +// CHECK-PPC64LE-NEXT: store ptr [[PS19]], ptr [[TMP89]], align 8 +// CHECK-PPC64LE-NEXT: [[TMP90:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 9 +// CHECK-PPC64LE-NEXT: store ptr [[PS21]], ptr [[TMP90]], align 8 +// CHECK-PPC64LE-NEXT: [[TMP91:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i64 0, i64 9 // CHECK-PPC64LE-NEXT: store ptr null, ptr [[TMP91]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP92:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 10 -// CHECK-PPC64LE-NEXT: store ptr [[PS24]], ptr [[TMP92]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP93:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 10 -// CHECK-PPC64LE-NEXT: store ptr [[S28]], ptr [[TMP93]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP94:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i64 0, i64 10 +// CHECK-PPC64LE-NEXT: [[TMP92:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 10 +// CHECK-PPC64LE-NEXT: store ptr [[PS21]], ptr [[TMP92]], align 8 +// CHECK-PPC64LE-NEXT: [[TMP93:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 10 +// CHECK-PPC64LE-NEXT: store ptr [[PS24]], ptr [[TMP93]], align 8 +// CHECK-PPC64LE-NEXT: [[TMP94:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i64 0, i64 10 // CHECK-PPC64LE-NEXT: store ptr null, ptr [[TMP94]], align 8 -// CHECK-PPC64LE-NEXT: [[TMP95:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 0 -// CHECK-PPC64LE-NEXT: [[TMP96:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 0 -// CHECK-PPC64LE-NEXT: [[TMP97:%.*]] = getelementptr inbounds [11 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 0 -// CHECK-PPC64LE-NEXT: call void @__tgt_target_data_begin_mapper(ptr @[[GLOB1]], i64 -1, i32 11, ptr [[TMP95]], ptr [[TMP96]], ptr [[TMP97]], ptr @.offload_maptypes.6, ptr null, ptr null) -// CHECK-PPC64LE-NEXT: [[TMP98:%.*]] = load i32, ptr [[ARG_ADDR]], align 4 -// CHECK-PPC64LE-NEXT: [[INC32:%.*]] = add nsw i32 [[TMP98]], 1 +// CHECK-PPC64LE-NEXT: [[TMP95:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 11 +// CHECK-PPC64LE-NEXT: store ptr [[PS24]], ptr [[TMP95]], align 8 +// CHECK-PPC64LE-NEXT: [[TMP96:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 11 +// CHECK-PPC64LE-NEXT: store ptr [[S28]], ptr [[TMP96]], align 8 +// CHECK-PPC64LE-NEXT: [[TMP97:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i64 0, i64 11 +// CHECK-PPC64LE-NEXT: store ptr null, ptr [[TMP97]], align 8 +// CHECK-PPC64LE-NEXT: [[TMP98:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 12 +// CHECK-PPC64LE-NEXT: store ptr [[PS2]], ptr [[TMP98]], align 8 +// CHECK-PPC64LE-NEXT: [[TMP99:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 12 +// CHECK-PPC64LE-NEXT: store ptr [[S18]], ptr [[TMP99]], align 8 +// CHECK-PPC64LE-NEXT: [[TMP100:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i64 0, i64 12 +// CHECK-PPC64LE-NEXT: store ptr null, ptr [[TMP100]], align 8 +// CHECK-PPC64LE-NEXT: [[TMP101:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 0 +// CHECK-PPC64LE-NEXT: [[TMP102:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 0 +// CHECK-PPC64LE-NEXT: [[TMP103:%.*]] = getelementptr inbounds [13 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 0 +// CHECK-PPC64LE-NEXT: call void @__tgt_target_data_begin_mapper(ptr @[[GLOB1]], i64 -1, i32 13, ptr [[TMP101]], ptr [[TMP102]], ptr [[TMP103]], ptr @.offload_maptypes.6, ptr null, ptr null) +// CHECK-PPC64LE-NEXT: [[TMP104:%.*]] = load i32, ptr [[ARG_ADDR]], align 4 +// CHECK-PPC64LE-NEXT: [[INC32:%.*]] = add nsw i32 [[TMP104]], 1 // CHECK-PPC64LE-NEXT: store i32 [[INC32]], ptr [[ARG_ADDR]], align 4 -// CHECK-PPC64LE-NEXT: [[TMP99:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 0 -// CHECK-PPC64LE-NEXT: [[TMP100:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 0 -// CHECK-PPC64LE-NEXT: [[TMP101:%.*]] = getelementptr inbounds [11 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 0 -// CHECK-PPC64LE-NEXT: call void @__tgt_target_data_end_mapper(ptr @[[GLOB1]], i64 -1, i32 11, ptr [[TMP99]], ptr [[TMP100]], ptr [[TMP101]], ptr @.offload_maptypes.6, ptr null, ptr null) +// CHECK-PPC64LE-NEXT: [[TMP105:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 0 +// CHECK-PPC64LE-NEXT: [[TMP106:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 0 +// CHECK-PPC64LE-NEXT: [[TMP107:%.*]] = getelementptr inbounds [13 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 0 +// CHECK-PPC64LE-NEXT: call void @__tgt_target_data_end_mapper(ptr @[[GLOB1]], i64 -1, i32 13, ptr [[TMP105]], ptr [[TMP106]], ptr [[TMP107]], ptr @.offload_maptypes.6, ptr null, ptr null) // CHECK-PPC64LE-NEXT: ret void // // CHECK-I386-LABEL: @_Z3fooi( @@ -293,10 +306,10 @@ struct S2 { // CHECK-I386-NEXT: [[DOTOFFLOAD_BASEPTRS5:%.*]] = alloca [1 x ptr], align 4 // CHECK-I386-NEXT: [[DOTOFFLOAD_PTRS6:%.*]] = alloca [1 x ptr], align 4 // CHECK-I386-NEXT: [[DOTOFFLOAD_MAPPERS7:%.*]] = alloca [1 x ptr], align 4 -// CHECK-I386-NEXT: [[DOTOFFLOAD_BASEPTRS29:%.*]] = alloca [11 x ptr], align 4 -// CHECK-I386-NEXT: [[DOTOFFLOAD_PTRS30:%.*]] = alloca [11 x ptr], align 4 -// CHECK-I386-NEXT: [[DOTOFFLOAD_MAPPERS31:%.*]] = alloca [11 x ptr], align 4 -// CHECK-I386-NEXT: [[DOTOFFLOAD_SIZES:%.*]] = alloca [11 x i64], align 4 +// CHECK-I386-NEXT: [[DOTOFFLOAD_BASEPTRS29:%.*]] = alloca [13 x ptr], align 4 +// CHECK-I386-NEXT: [[DOTOFFLOAD_PTRS30:%.*]] = alloca [13 x ptr], align 4 +// CHECK-I386-NEXT: [[DOTOFFLOAD_MAPPERS31:%.*]] = alloca [13 x ptr], align 4 +// CHECK-I386-NEXT: [[DOTOFFLOAD_SIZES:%.*]] = alloca [13 x i64], align 4 // CHECK-I386-NEXT: store i32 [[ARG:%.*]], ptr [[ARG_ADDR]], align 4 // CHECK-I386-NEXT: [[TMP0:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 // CHECK-I386-NEXT: store ptr [[LB]], ptr [[TMP0]], align 4 @@ -401,88 +414,100 @@ struct S2 { // CHECK-I386-NEXT: [[TMP57:%.*]] = ptrtoint ptr [[S18]] to i64 // CHECK-I386-NEXT: [[TMP58:%.*]] = sub i64 [[TMP56]], [[TMP57]] // CHECK-I386-NEXT: [[TMP59:%.*]] = sdiv exact i64 [[TMP58]], ptrtoint (ptr getelementptr (i8, ptr null, i32 1) to i64) -// CHECK-I386-NEXT: call void @llvm.memcpy.p0.p0.i32(ptr align 4 [[DOTOFFLOAD_SIZES]], ptr align 4 @.offload_sizes.5, i32 88, i1 false) -// CHECK-I386-NEXT: [[TMP60:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 0 +// CHECK-I386-NEXT: call void @llvm.memcpy.p0.p0.i32(ptr align 4 [[DOTOFFLOAD_SIZES]], ptr align 4 @.offload_sizes.5, i32 104, i1 false) +// CHECK-I386-NEXT: [[TMP60:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 0 // CHECK-I386-NEXT: store ptr [[TMP24]], ptr [[TMP60]], align 4 -// CHECK-I386-NEXT: [[TMP61:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 0 +// CHECK-I386-NEXT: [[TMP61:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 0 // CHECK-I386-NEXT: store ptr [[S]], ptr [[TMP61]], align 4 -// CHECK-I386-NEXT: [[TMP62:%.*]] = getelementptr inbounds [11 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 0 +// CHECK-I386-NEXT: [[TMP62:%.*]] = getelementptr inbounds [13 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 0 // CHECK-I386-NEXT: store i64 [[TMP41]], ptr [[TMP62]], align 4 -// CHECK-I386-NEXT: [[TMP63:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i32 0, i32 0 +// CHECK-I386-NEXT: [[TMP63:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i32 0, i32 0 // CHECK-I386-NEXT: store ptr null, ptr [[TMP63]], align 4 -// CHECK-I386-NEXT: [[TMP64:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 1 +// CHECK-I386-NEXT: [[TMP64:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 1 // CHECK-I386-NEXT: store ptr [[TMP24]], ptr [[TMP64]], align 4 -// CHECK-I386-NEXT: [[TMP65:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 1 +// CHECK-I386-NEXT: [[TMP65:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 1 // CHECK-I386-NEXT: store ptr [[S]], ptr [[TMP65]], align 4 -// CHECK-I386-NEXT: [[TMP66:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i32 0, i32 1 +// CHECK-I386-NEXT: [[TMP66:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i32 0, i32 1 // CHECK-I386-NEXT: store ptr null, ptr [[TMP66]], align 4 -// CHECK-I386-NEXT: [[TMP67:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 2 +// CHECK-I386-NEXT: [[TMP67:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 2 // CHECK-I386-NEXT: store ptr [[PS]], ptr [[TMP67]], align 4 -// CHECK-I386-NEXT: [[TMP68:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 2 +// CHECK-I386-NEXT: [[TMP68:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 2 // CHECK-I386-NEXT: store ptr [[PS10]], ptr [[TMP68]], align 4 -// CHECK-I386-NEXT: [[TMP69:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i32 0, i32 2 +// CHECK-I386-NEXT: [[TMP69:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i32 0, i32 2 // CHECK-I386-NEXT: store ptr null, ptr [[TMP69]], align 4 -// CHECK-I386-NEXT: [[TMP70:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 3 +// CHECK-I386-NEXT: [[TMP70:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 3 // CHECK-I386-NEXT: store ptr [[PS10]], ptr [[TMP70]], align 4 -// CHECK-I386-NEXT: [[TMP71:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 3 +// CHECK-I386-NEXT: [[TMP71:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 3 // CHECK-I386-NEXT: store ptr [[PS13]], ptr [[TMP71]], align 4 -// CHECK-I386-NEXT: [[TMP72:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i32 0, i32 3 +// CHECK-I386-NEXT: [[TMP72:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i32 0, i32 3 // CHECK-I386-NEXT: store ptr null, ptr [[TMP72]], align 4 -// CHECK-I386-NEXT: [[TMP73:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 4 +// CHECK-I386-NEXT: [[TMP73:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 4 // CHECK-I386-NEXT: store ptr [[PS13]], ptr [[TMP73]], align 4 -// CHECK-I386-NEXT: [[TMP74:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 4 +// CHECK-I386-NEXT: [[TMP74:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 4 // CHECK-I386-NEXT: store ptr [[S17]], ptr [[TMP74]], align 4 -// CHECK-I386-NEXT: [[TMP75:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i32 0, i32 4 +// CHECK-I386-NEXT: [[TMP75:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i32 0, i32 4 // CHECK-I386-NEXT: store ptr null, ptr [[TMP75]], align 4 -// CHECK-I386-NEXT: [[TMP76:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 5 -// CHECK-I386-NEXT: store ptr [[ARG_ADDR]], ptr [[TMP76]], align 4 -// CHECK-I386-NEXT: [[TMP77:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 5 -// CHECK-I386-NEXT: store ptr [[ARG_ADDR]], ptr [[TMP77]], align 4 -// CHECK-I386-NEXT: [[TMP78:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i32 0, i32 5 +// CHECK-I386-NEXT: [[TMP76:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 5 +// CHECK-I386-NEXT: store ptr [[PS1]], ptr [[TMP76]], align 4 +// CHECK-I386-NEXT: [[TMP77:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 5 +// CHECK-I386-NEXT: store ptr [[S]], ptr [[TMP77]], align 4 +// CHECK-I386-NEXT: [[TMP78:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i32 0, i32 5 // CHECK-I386-NEXT: store ptr null, ptr [[TMP78]], align 4 -// CHECK-I386-NEXT: [[TMP79:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 6 -// CHECK-I386-NEXT: store ptr [[TMP42]], ptr [[TMP79]], align 4 -// CHECK-I386-NEXT: [[TMP80:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 6 -// CHECK-I386-NEXT: store ptr [[S18]], ptr [[TMP80]], align 4 -// CHECK-I386-NEXT: [[TMP81:%.*]] = getelementptr inbounds [11 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 6 -// CHECK-I386-NEXT: store i64 [[TMP59]], ptr [[TMP81]], align 4 -// CHECK-I386-NEXT: [[TMP82:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i32 0, i32 6 -// CHECK-I386-NEXT: store ptr null, ptr [[TMP82]], align 4 -// CHECK-I386-NEXT: [[TMP83:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 7 -// CHECK-I386-NEXT: store ptr [[TMP42]], ptr [[TMP83]], align 4 -// CHECK-I386-NEXT: [[TMP84:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 7 -// CHECK-I386-NEXT: store ptr [[S18]], ptr [[TMP84]], align 4 -// CHECK-I386-NEXT: [[TMP85:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i32 0, i32 7 +// CHECK-I386-NEXT: [[TMP79:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 6 +// CHECK-I386-NEXT: store ptr [[ARG_ADDR]], ptr [[TMP79]], align 4 +// CHECK-I386-NEXT: [[TMP80:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 6 +// CHECK-I386-NEXT: store ptr [[ARG_ADDR]], ptr [[TMP80]], align 4 +// CHECK-I386-NEXT: [[TMP81:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i32 0, i32 6 +// CHECK-I386-NEXT: store ptr null, ptr [[TMP81]], align 4 +// CHECK-I386-NEXT: [[TMP82:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 7 +// CHECK-I386-NEXT: store ptr [[TMP42]], ptr [[TMP82]], align 4 +// CHECK-I386-NEXT: [[TMP83:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 7 +// CHECK-I386-NEXT: store ptr [[S18]], ptr [[TMP83]], align 4 +// CHECK-I386-NEXT: [[TMP84:%.*]] = getelementptr inbounds [13 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 7 +// CHECK-I386-NEXT: store i64 [[TMP59]], ptr [[TMP84]], align 4 +// CHECK-I386-NEXT: [[TMP85:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i32 0, i32 7 // CHECK-I386-NEXT: store ptr null, ptr [[TMP85]], align 4 -// CHECK-I386-NEXT: [[TMP86:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 8 -// CHECK-I386-NEXT: store ptr [[PS19]], ptr [[TMP86]], align 4 -// CHECK-I386-NEXT: [[TMP87:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 8 -// CHECK-I386-NEXT: store ptr [[PS21]], ptr [[TMP87]], align 4 -// CHECK-I386-NEXT: [[TMP88:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i32 0, i32 8 +// CHECK-I386-NEXT: [[TMP86:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 8 +// CHECK-I386-NEXT: store ptr [[TMP42]], ptr [[TMP86]], align 4 +// CHECK-I386-NEXT: [[TMP87:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 8 +// CHECK-I386-NEXT: store ptr [[S18]], ptr [[TMP87]], align 4 +// CHECK-I386-NEXT: [[TMP88:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i32 0, i32 8 // CHECK-I386-NEXT: store ptr null, ptr [[TMP88]], align 4 -// CHECK-I386-NEXT: [[TMP89:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 9 -// CHECK-I386-NEXT: store ptr [[PS21]], ptr [[TMP89]], align 4 -// CHECK-I386-NEXT: [[TMP90:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 9 -// CHECK-I386-NEXT: store ptr [[PS24]], ptr [[TMP90]], align 4 -// CHECK-I386-NEXT: [[TMP91:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i32 0, i32 9 +// CHECK-I386-NEXT: [[TMP89:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 9 +// CHECK-I386-NEXT: store ptr [[PS19]], ptr [[TMP89]], align 4 +// CHECK-I386-NEXT: [[TMP90:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 9 +// CHECK-I386-NEXT: store ptr [[PS21]], ptr [[TMP90]], align 4 +// CHECK-I386-NEXT: [[TMP91:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i32 0, i32 9 // CHECK-I386-NEXT: store ptr null, ptr [[TMP91]], align 4 -// CHECK-I386-NEXT: [[TMP92:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 10 -// CHECK-I386-NEXT: store ptr [[PS24]], ptr [[TMP92]], align 4 -// CHECK-I386-NEXT: [[TMP93:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 10 -// CHECK-I386-NEXT: store ptr [[S28]], ptr [[TMP93]], align 4 -// CHECK-I386-NEXT: [[TMP94:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i32 0, i32 10 +// CHECK-I386-NEXT: [[TMP92:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 10 +// CHECK-I386-NEXT: store ptr [[PS21]], ptr [[TMP92]], align 4 +// CHECK-I386-NEXT: [[TMP93:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 10 +// CHECK-I386-NEXT: store ptr [[PS24]], ptr [[TMP93]], align 4 +// CHECK-I386-NEXT: [[TMP94:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i32 0, i32 10 // CHECK-I386-NEXT: store ptr null, ptr [[TMP94]], align 4 -// CHECK-I386-NEXT: [[TMP95:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 0 -// CHECK-I386-NEXT: [[TMP96:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 0 -// CHECK-I386-NEXT: [[TMP97:%.*]] = getelementptr inbounds [11 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 0 -// CHECK-I386-NEXT: call void @__tgt_target_data_begin_mapper(ptr @[[GLOB1]], i64 -1, i32 11, ptr [[TMP95]], ptr [[TMP96]], ptr [[TMP97]], ptr @.offload_maptypes.6, ptr null, ptr null) -// CHECK-I386-NEXT: [[TMP98:%.*]] = load i32, ptr [[ARG_ADDR]], align 4 -// CHECK-I386-NEXT: [[INC32:%.*]] = add nsw i32 [[TMP98]], 1 +// CHECK-I386-NEXT: [[TMP95:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 11 +// CHECK-I386-NEXT: store ptr [[PS24]], ptr [[TMP95]], align 4 +// CHECK-I386-NEXT: [[TMP96:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 11 +// CHECK-I386-NEXT: store ptr [[S28]], ptr [[TMP96]], align 4 +// CHECK-I386-NEXT: [[TMP97:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i32 0, i32 11 +// CHECK-I386-NEXT: store ptr null, ptr [[TMP97]], align 4 +// CHECK-I386-NEXT: [[TMP98:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 12 +// CHECK-I386-NEXT: store ptr [[PS2]], ptr [[TMP98]], align 4 +// CHECK-I386-NEXT: [[TMP99:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 12 +// CHECK-I386-NEXT: store ptr [[S18]], ptr [[TMP99]], align 4 +// CHECK-I386-NEXT: [[TMP100:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_MAPPERS31]], i32 0, i32 12 +// CHECK-I386-NEXT: store ptr null, ptr [[TMP100]], align 4 +// CHECK-I386-NEXT: [[TMP101:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 0 +// CHECK-I386-NEXT: [[TMP102:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 0 +// CHECK-I386-NEXT: [[TMP103:%.*]] = getelementptr inbounds [13 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 0 +// CHECK-I386-NEXT: call void @__tgt_target_data_begin_mapper(ptr @[[GLOB1]], i64 -1, i32 13, ptr [[TMP101]], ptr [[TMP102]], ptr [[TMP103]], ptr @.offload_maptypes.6, ptr null, ptr null) +// CHECK-I386-NEXT: [[TMP104:%.*]] = load i32, ptr [[ARG_ADDR]], align 4 +// CHECK-I386-NEXT: [[INC32:%.*]] = add nsw i32 [[TMP104]], 1 // CHECK-I386-NEXT: store i32 [[INC32]], ptr [[ARG_ADDR]], align 4 -// CHECK-I386-NEXT: [[TMP99:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 0 -// CHECK-I386-NEXT: [[TMP100:%.*]] = getelementptr inbounds [11 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 0 -// CHECK-I386-NEXT: [[TMP101:%.*]] = getelementptr inbounds [11 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 0 -// CHECK-I386-NEXT: call void @__tgt_target_data_end_mapper(ptr @[[GLOB1]], i64 -1, i32 11, ptr [[TMP99]], ptr [[TMP100]], ptr [[TMP101]], ptr @.offload_maptypes.6, ptr null, ptr null) +// CHECK-I386-NEXT: [[TMP105:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_BASEPTRS29]], i32 0, i32 0 +// CHECK-I386-NEXT: [[TMP106:%.*]] = getelementptr inbounds [13 x ptr], ptr [[DOTOFFLOAD_PTRS30]], i32 0, i32 0 +// CHECK-I386-NEXT: [[TMP107:%.*]] = getelementptr inbounds [13 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 0 +// CHECK-I386-NEXT: call void @__tgt_target_data_end_mapper(ptr @[[GLOB1]], i64 -1, i32 13, ptr [[TMP105]], ptr [[TMP106]], ptr [[TMP107]], ptr @.offload_maptypes.6, ptr null, ptr null) // CHECK-I386-NEXT: ret void // void foo(int arg) { diff --git a/clang/test/OpenMP/target_data_map_pointer_array_subscript_codegen.cpp b/clang/test/OpenMP/target_data_map_pointer_array_subscript_codegen.cpp index eed1889f3c5cb..60b65ba9a49da 100644 --- a/clang/test/OpenMP/target_data_map_pointer_array_subscript_codegen.cpp +++ b/clang/test/OpenMP/target_data_map_pointer_array_subscript_codegen.cpp @@ -33,15 +33,33 @@ typedef struct { MyObject *objects; #pragma omp end declare target -// CHECK-DAG: [[SIZES0:@.+]] = private unnamed_addr constant [1 x i64] [i64 {{8|4}}] -// CHECK-DAG: [[MAPS0:@.+]] = private unnamed_addr constant [1 x i64] [i64 17] +// CHECK-DAG: [[SIZES0:@.+]] = private unnamed_addr constant [2 x i64] [i64 {{8|4}}, i64 {{8|4}}] +// CHECK-DAG: [[MAPS0:@.+]] = private unnamed_addr constant [2 x i64] [i64 1, i64 16384] // CHECK-DAG: [[SIZES1:@.+]] = private unnamed_addr constant [2 x i64] [i64 0, i64 4] // CHECK-DAG: [[MAPS1:@.+]] = private unnamed_addr constant [2 x i64] [i64 0, i64 281474976710673] // CHECK: @main int main(void) { -// CHECK: [[BPTR0:%.+]] = getelementptr inbounds [1 x ptr], ptr %{{.+}}, i32 0, i32 0 -// CHECK: store ptr @objects, ptr [[BPTR0]], -// CHECK: call void @__tgt_target_data_begin_mapper(ptr @{{.+}}, i64 -1, i32 1, ptr %{{.+}}, ptr %{{.+}}, ptr [[SIZES0]], ptr [[MAPS0]], ptr null, ptr null) + +// &objects[0], &objects[1], 1 * sizeof(objects[0]), TO +// &objects, &objects[1], sizeof(objects), ATTACH + +// CHECK-DAG: call void @__tgt_target_data_begin_mapper(ptr @{{.+}}, i64 -1, i32 2, ptr [[BPGEP:%.+]], ptr [[PGEP:%.+]], ptr [[SIZES0]], ptr [[MAPS0]], ptr null, ptr null) +// CHECK-DAG: [[BPGEP]] = getelementptr inbounds {{.+}}[[BP:%[^,]+]] +// CHECK-DAG: [[PGEP]] = getelementptr inbounds {{.+}}[[P:%[^,]+]] + +// CHECK-DAG: [[BP0:%.+]] = getelementptr inbounds {{.*}}ptr [[BP]], i32 0, i32 0 +// CHECK-DAG: [[P0:%.+]] = getelementptr inbounds {{.*}}ptr [[P]], i32 0, i32 0 +// CHECK-DAG: store ptr [[RVAR0:%.+]], ptr [[BP0]] +// CHECK-DAG: store ptr [[SEC0:%.+]], ptr [[P0]] +// CHECK-DAG: [[RVAR0]] = load ptr, ptr @objects +// CHECK-DAG: [[SEC0]] = getelementptr {{.*}}ptr [[RVAR00:%.+]], i{{.+}} 1 +// CHECK-DAG: [[RVAR00]] = load ptr, ptr @objects + +// CHECK-DAG: [[BP1:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 1 +// CHECK-DAG: [[P1:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 1 +// CHECK-DAG: store ptr @objects, ptr [[BP1]] +// CHECK-DAG: store ptr [[SEC0]], ptr [[P1]] + #pragma omp target enter data map(to : objects [1:1]) // CHECK: [[OBJ:%.+]] = load ptr, ptr @objects, // CHECK: [[BPTR0:%.+]] = getelementptr inbounds [2 x ptr], ptr %{{.+}}, i32 0, i32 0 diff --git a/clang/test/OpenMP/target_data_use_device_addr_codegen.cpp b/clang/test/OpenMP/target_data_use_device_addr_codegen.cpp index 19a523ee165c8..40f3e3b4bc9f7 100644 --- a/clang/test/OpenMP/target_data_use_device_addr_codegen.cpp +++ b/clang/test/OpenMP/target_data_use_device_addr_codegen.cpp @@ -11,9 +11,9 @@ #ifndef HEADER #define HEADER -// CHECK-DAG: [[SIZES1:@.+]] = private unnamed_addr constant [6 x i64] [i64 4, i64 16, i64 4, i64 4, i64 0, i64 4] +// CHECK-DAG: [[SIZES1:@.+]] = private unnamed_addr constant [8 x i64] [i64 4, i64 16, i64 8, i64 4, i64 8, i64 4, i64 0, i64 4] // 64 = 0x40 = OMP_MAP_RETURN_PARAM -// CHECK-DAG: [[MAPTYPES1:@.+]] = private unnamed_addr constant [6 x i64] [i64 67, i64 115, i64 51, i64 67, i64 67, i64 67] +// CHECK-DAG: [[MAPTYPES1:@.+]] = private unnamed_addr constant [8 x i64] [i64 67, i64 67, i64 16384, i64 3, i64 16384, i64 67, i64 67, i64 67] // CHECK-DAG: [[SIZES2:@.+]] = private unnamed_addr constant [6 x i64] [i64 0, i64 4, i64 16, i64 4, i64 4, i64 0] // 0 = OMP_MAP_NONE // 281474976710720 = 0x1000000000040 = OMP_MAP_MEMBER_OF | OMP_MAP_RETURN_PARAM @@ -44,63 +44,82 @@ int main() { } // CHECK-LABEL: @main() +// +// &a, &a, TO | FROM | RETURN_PARAM +// &ptr[0], &ptr[3], TO | FROM | RETURN_PARAM +// &ptr, &ptr[3], ATTACH +// &ptr[0], &ptr[0], TO | FROM | RETURN_PARAM +// &ptr, &ptr[0], ATTACH +// &ref_ptee(ref), &ref_ptee(ref), TO | FROM | RETURN_PARAM +// &arr, &arr[0], TO | FROM | RETURN_PARAM +// // CHECK: [[A_ADDR:%.+]] = alloca float, // CHECK: [[PTR_ADDR:%.+]] = alloca ptr, // CHECK: [[REF_ADDR:%.+]] = alloca ptr, // CHECK: [[ARR_ADDR:%.+]] = alloca [4 x float], -// CHECK: [[BPTRS:%.+]] = alloca [6 x ptr], -// CHECK: [[PTRS:%.+]] = alloca [6 x ptr], -// CHECK: [[MAP_PTRS:%.+]] = alloca [6 x ptr], -// CHECK: [[SIZES:%.+]] = alloca [6 x i64], +// CHECK: [[BPTRS:%.+]] = alloca [8 x ptr], +// CHECK: [[PTRS:%.+]] = alloca [8 x ptr], +// CHECK: [[MAP_PTRS:%.+]] = alloca [8 x ptr], +// CHECK: [[SIZES:%.+]] = alloca [8 x i64], // CHECK: [[VLA_ADDR:%.+]] = alloca float, i64 %{{.+}}, -// CHECK: [[PTR:%.+]] = load ptr, ptr [[PTR_ADDR]], -// CHECK-NEXT: [[ARR_IDX:%.+]] = getelementptr inbounds nuw float, ptr [[PTR]], i64 3 -// CHECK: [[P5:%.+]] = load ptr, ptr [[PTR_ADDR]], align 8 +// CHECK: [[P0:%.+]] = load ptr, ptr [[PTR_ADDR]], +// CHECK: [[P1:%.+]] = load ptr, ptr [[PTR_ADDR]], +// CHECK-NEXT: [[ARR_IDX:%.+]] = getelementptr inbounds nuw float, ptr [[P1]], i64 3 +// CHECK: [[P2:%.+]] = load ptr, ptr [[PTR_ADDR]], +// CHECK: [[P5:%.+]] = load ptr, ptr [[PTR_ADDR]], // CHECK-NEXT: [[ARR_IDX1:%.+]] = getelementptr inbounds float, ptr [[P5]], i64 0 // CHECK: [[P7:%.+]] = load ptr, ptr [[REF_ADDR]], // CHECK-NEXT: [[REF:%.+]] = load ptr, ptr [[REF_ADDR]], // CHECK-NEXT: [[ARR_IDX2:%.+]] = getelementptr inbounds nuw [4 x float], ptr [[ARR_ADDR]], i64 0, i64 0 // CHECK: [[P10:%.+]] = mul nuw i64 {{.+}}, 4 // CHECK-NEXT: [[ARR_IDX5:%.+]] = getelementptr inbounds float, ptr [[VLA_ADDR]], i64 0 -// CHECK-NEXT: call void @llvm.memcpy.p0.p0.i64(ptr align 8 [[SIZES]], ptr align 8 [[SIZES1]], i64 48, i1 false) -// CHECK: [[BPTR0:%.+]] = getelementptr inbounds [6 x ptr], ptr [[BPTRS]], i32 0, i32 0 +// CHECK-NEXT: call void @llvm.memcpy.p0.p0.i64(ptr align 8 [[SIZES]], ptr align 8 [[SIZES1]], i64 64, i1 false) +// CHECK: [[BPTR0:%.+]] = getelementptr inbounds [8 x ptr], ptr [[BPTRS]], i32 0, i32 0 // CHECK: store ptr [[A_ADDR]], ptr [[BPTR0]], -// CHECK: [[PTR0:%.+]] = getelementptr inbounds [6 x ptr], ptr [[PTRS]], i32 0, i32 0 +// CHECK: [[PTR0:%.+]] = getelementptr inbounds [8 x ptr], ptr [[PTRS]], i32 0, i32 0 // CHECK: store ptr [[A_ADDR]], ptr [[PTR0]], -// CHECK: [[BPTR1:%.+]] = getelementptr inbounds [6 x ptr], ptr [[BPTRS]], i32 0, i32 1 -// CHECK: store ptr [[PTR_ADDR]], ptr [[BPTR1]], -// CHECK: [[PTR1:%.+]] = getelementptr inbounds [6 x ptr], ptr [[PTRS]], i32 0, i32 1 +// CHECK: [[BPTR1:%.+]] = getelementptr inbounds [8 x ptr], ptr [[BPTRS]], i32 0, i32 1 +// CHECK: store ptr [[P0]], ptr [[BPTR1]], +// CHECK: [[PTR1:%.+]] = getelementptr inbounds [8 x ptr], ptr [[PTRS]], i32 0, i32 1 // CHECK: store ptr [[ARR_IDX]], ptr [[PTR1]], -// CHECK: [[BPTR2:%.+]] = getelementptr inbounds [6 x ptr], ptr [[BPTRS]], i32 0, i32 2 +// CHECK: [[BPTR2:%.+]] = getelementptr inbounds [8 x ptr], ptr [[BPTRS]], i32 0, i32 2 // CHECK: store ptr [[PTR_ADDR]], ptr [[BPTR2]], -// CHECK: [[PTR2:%.+]] = getelementptr inbounds [6 x ptr], ptr [[PTRS]], i32 0, i32 2 -// CHECK: store ptr [[ARR_IDX1]], ptr [[PTR2]], -// CHECK: [[BPTR3:%.+]] = getelementptr inbounds [6 x ptr], ptr [[BPTRS]], i32 0, i32 3 -// CHECK: store ptr [[P7]], ptr [[BPTR3]], -// CHECK: [[PTR3:%.+]] = getelementptr inbounds [6 x ptr], ptr [[PTRS]], i32 0, i32 3 -// CHECK: store ptr [[REF]], ptr [[PTR3]], -// CHECK: [[BPTR4:%.+]] = getelementptr inbounds [6 x ptr], ptr [[BPTRS]], i32 0, i32 4 -// CHECK: store ptr [[ARR_ADDR]], ptr [[BPTR4]], align -// CHECK: [[PTR4:%.+]] = getelementptr inbounds [6 x ptr], ptr [[PTRS]], i32 0, i32 4 -// CHECK: store ptr [[ARR_IDX2]], ptr [[PTR4]], align 8 -// CHECK: [[SIZE_PTR:%.+]] = getelementptr inbounds [6 x i64], ptr [[SIZES]], i32 0, i32 4 +// CHECK: [[PTR2:%.+]] = getelementptr inbounds [8 x ptr], ptr [[PTRS]], i32 0, i32 2 +// CHECK: store ptr [[ARR_IDX]], ptr [[PTR2]], +// CHECK: [[BPTR3:%.+]] = getelementptr inbounds [8 x ptr], ptr [[BPTRS]], i32 0, i32 3 +// CHECK: store ptr [[P2]], ptr [[BPTR3]], +// CHECK: [[PTR3:%.+]] = getelementptr inbounds [8 x ptr], ptr [[PTRS]], i32 0, i32 3 +// CHECK: store ptr [[ARR_IDX1]], ptr [[PTR3]], +// CHECK: [[BPTR4:%.+]] = getelementptr inbounds [8 x ptr], ptr [[BPTRS]], i32 0, i32 4 +// CHECK: store ptr [[PTR_ADDR]], ptr [[BPTR4]], align +// CHECK: [[PTR4:%.+]] = getelementptr inbounds [8 x ptr], ptr [[PTRS]], i32 0, i32 4 +// CHECK: store ptr [[ARR_IDX1]], ptr [[PTR4]], align 8 +// CHECK: [[BPTR5:%.+]] = getelementptr inbounds [8 x ptr], ptr [[BPTRS]], i32 0, i32 5 +// CHECK: store ptr [[P7]], ptr [[BPTR5]], align +// CHECK: [[PTR5:%.+]] = getelementptr inbounds [8 x ptr], ptr [[PTRS]], i32 0, i32 5 +// CHECK: store ptr [[REF]], ptr [[PTR5]], align 8 +// CHECK: [[BPTR6:%.+]] = getelementptr inbounds [8 x ptr], ptr [[BPTRS]], i32 0, i32 6 +// CHECK: store ptr [[ARR_ADDR]], ptr [[BPTR6]], +// CHECK: [[PTR6:%.+]] = getelementptr inbounds [8 x ptr], ptr [[PTRS]], i32 0, i32 6 +// CHECK: store ptr [[ARR_IDX2]], ptr [[PTR6]], +// CHECK: [[SIZE_PTR:%.+]] = getelementptr inbounds [8 x i64], ptr [[SIZES]], i32 0, i32 6 // CHECK: store i64 [[P10:%.+]], ptr [[SIZE_PTR]], align 8 -// CHECK: [[MAP_PTR:%.+]] = getelementptr inbounds [6 x ptr], ptr [[MAP_PTRS]], i64 0, i64 4 +// CHECK: [[MAP_PTR:%.+]] = getelementptr inbounds [8 x ptr], ptr [[MAP_PTRS]], i64 0, i64 6 // CHECK: store ptr null, ptr [[MAP_PTR]], align 8 -// CHECK: [[BPTR5:%.+]] = getelementptr inbounds [6 x ptr], ptr [[BPTRS]], i32 0, i32 5 -// CHECK: store ptr [[VLA_ADDR]], ptr [[BPTR5]], -// CHECK: [[PTR5:%.+]] = getelementptr inbounds [6 x ptr], ptr [[PTRS]], i32 0, i32 5 -// CHECK: store ptr [[ARR_IDX5]], ptr [[PTR5]], +// CHECK: [[BPTR7:%.+]] = getelementptr inbounds [8 x ptr], ptr [[BPTRS]], i32 0, i32 7 +// CHECK: store ptr [[VLA_ADDR]], ptr [[BPTR7]], +// CHECK: [[PTR7:%.+]] = getelementptr inbounds [8 x ptr], ptr [[PTRS]], i32 0, i32 7 +// CHECK: store ptr [[ARR_IDX5]], ptr [[PTR7]], -// CHECK: [[BPTR:%.+]] = getelementptr inbounds [6 x ptr], ptr [[BPTRS]], i32 0, i32 0 -// CHECK: [[PTR:%.+]] = getelementptr inbounds [6 x ptr], ptr [[PTRS]], i32 0, i32 0 -// CHECK: [[SIZE:%.+]] = getelementptr inbounds [6 x i64], ptr [[SIZES]], i32 0, i32 0 -// CHECK: call void @__tgt_target_data_begin_mapper(ptr @{{.+}}, i64 -1, i32 6, ptr [[BPTR]], ptr [[PTR]], ptr [[SIZE]], ptr [[MAPTYPES1]], ptr null, ptr null) +// CHECK: [[BPTR:%.+]] = getelementptr inbounds [8 x ptr], ptr [[BPTRS]], i32 0, i32 0 +// CHECK: [[PTR:%.+]] = getelementptr inbounds [8 x ptr], ptr [[PTRS]], i32 0, i32 0 +// CHECK: [[SIZE:%.+]] = getelementptr inbounds [8 x i64], ptr [[SIZES]], i32 0, i32 0 +// CHECK: call void @__tgt_target_data_begin_mapper(ptr @{{.+}}, i64 -1, i32 8, ptr [[BPTR]], ptr [[PTR]], ptr [[SIZE]], ptr [[MAPTYPES1]], ptr null, ptr null) // CHECK: [[A_REF:%.+]] = load ptr, ptr [[BPTR0]], -// CHECK: [[REF_REF:%.+]] = load ptr, ptr [[BPTR3]], +// CHECK: [[REF_REF:%.+]] = load ptr, ptr [[BPTR5]], // CHECK: store ptr [[REF_REF]], ptr [[TMP_REF_ADDR:%.+]], -// CHECK: [[ARR_REF:%.+]] = load ptr, ptr [[BPTR4]], -// CHECK: [[VLA_REF:%.+]] = load ptr, ptr [[BPTR5]], +// CHECK: [[ARR_REF:%.+]] = load ptr, ptr [[BPTR6]], +// CHECK: [[VLA_REF:%.+]] = load ptr, ptr [[BPTR7]], // CHECK: [[A:%.+]] = load float, ptr [[A_REF]], // CHECK: [[INC:%.+]] = fadd float [[A]], 1.000000e+00 // CHECK: store float [[INC]], ptr [[A_REF]], @@ -120,12 +139,20 @@ int main() { // CHECK: [[VLA0:%.+]] = load float, ptr [[VLA0_ADDR]], // CHECK: [[INC:%.+]] = fadd float [[VLA0]], 1.000000e+00 // CHECK: store float [[INC]], ptr [[VLA0_ADDR]], -// CHECK: [[BPTR:%.+]] = getelementptr inbounds [6 x ptr], ptr [[BPTRS]], i32 0, i32 0 -// CHECK: [[PTR:%.+]] = getelementptr inbounds [6 x ptr], ptr [[PTRS]], i32 0, i32 0 -// CHECK: [[SIZE:%.+]] = getelementptr inbounds [6 x i64], ptr [[SIZES]], i32 0, i32 0 -// CHECK: call void @__tgt_target_data_end_mapper(ptr @{{.+}}, i64 -1, i32 6, ptr [[BPTR]], ptr [[PTR]], ptr [[SIZE]], ptr [[MAPTYPES1]], ptr null, ptr null) +// CHECK: [[BPTR:%.+]] = getelementptr inbounds [8 x ptr], ptr [[BPTRS]], i32 0, i32 0 +// CHECK: [[PTR:%.+]] = getelementptr inbounds [8 x ptr], ptr [[PTRS]], i32 0, i32 0 +// CHECK: [[SIZE:%.+]] = getelementptr inbounds [8 x i64], ptr [[SIZES]], i32 0, i32 0 +// CHECK: call void @__tgt_target_data_end_mapper(ptr @{{.+}}, i64 -1, i32 8, ptr [[BPTR]], ptr [[PTR]], ptr [[SIZE]], ptr [[MAPTYPES1]], ptr null, ptr null) // CHECK: foo +// +// &this[0], &this->a, sizeof(this[0].(a-to-arr[a]) | ALLOC +// &this[0], &this->a, sizeof(a), TO | FROM | RETURN_PARAM | MEMBER_OF(1) +// &this->ptr, &this->ptr[3], 4 * sizeof(ptr[0], TO | FROM | PTR_AND_OBJ | RETURN_PARAM | MEMBER_OF(1) +// &this[0], &ref_ptee(this->ref), sizeof(this->ref[0]), TO | FROM | PTR_AND_OBJ | RETURN_PARAM | MEMBER_OF(1) +// &this->ptr, &this->ptr[0], sizeof(ptr[0], TO | FROM | PTR_AND_OBJ | MEMBER_OF(1) +// &this, &this->arr[0], 4 * sizeof(arr[0]), TO | FROM | RETURN_PARAM | MEMBER_OF(1) +// // CHECK: [[BPTRS:%.+]] = alloca [6 x ptr], // CHECK: [[PTRS:%.+]] = alloca [6 x ptr], // CHECK: [[MAP_PTRS:%.+]] = alloca [6 x ptr], diff --git a/clang/test/OpenMP/target_data_use_device_ptr_codegen.cpp b/clang/test/OpenMP/target_data_use_device_ptr_codegen.cpp index 6d1c0213d648c..91bf97a6a5163 100644 --- a/clang/test/OpenMP/target_data_use_device_ptr_codegen.cpp +++ b/clang/test/OpenMP/target_data_use_device_ptr_codegen.cpp @@ -22,18 +22,18 @@ double *g; // CK1: @g ={{.*}} global ptr -// CK1: [[MTYPE00:@.+]] = {{.*}}constant [2 x i64] [i64 19, i64 64] -// CK1: [[MTYPE01:@.+]] = {{.*}}constant [1 x i64] [i64 67] -// CK1: [[MTYPE03:@.+]] = {{.*}}constant [1 x i64] [i64 67] -// CK1: [[MTYPE04:@.+]] = {{.*}}constant [1 x i64] [i64 67] -// CK1: [[MTYPE05:@.+]] = {{.*}}constant [1 x i64] [i64 67] -// CK1: [[MTYPE06:@.+]] = {{.*}}constant [1 x i64] [i64 67] -// CK1: [[MTYPE07:@.+]] = {{.*}}constant [1 x i64] [i64 67] -// CK1: [[MTYPE08:@.+]] = {{.*}}constant [2 x i64] [i64 67, i64 3] -// CK1: [[MTYPE09:@.+]] = {{.*}}constant [2 x i64] [i64 67, i64 67] -// CK1: [[MTYPE10:@.+]] = {{.*}}constant [2 x i64] [i64 67, i64 67] -// CK1: [[MTYPE11:@.+]] = {{.*}}constant [2 x i64] [i64 3, i64 64] -// CK1: [[MTYPE12:@.+]] = {{.*}}constant [2 x i64] [i64 3, i64 64] +// CK1: [[MTYPE00:@.+]] = {{.*}}constant [2 x i64] [i64 67, i64 16384] +// CK1: [[MTYPE01:@.+]] = {{.*}}constant [2 x i64] [i64 67, i64 16384] +// CK1: [[MTYPE03:@.+]] = {{.*}}constant [2 x i64] [i64 67, i64 16384] +// CK1: [[MTYPE04:@.+]] = {{.*}}constant [2 x i64] [i64 67, i64 16384] +// CK1: [[MTYPE05:@.+]] = {{.*}}constant [2 x i64] [i64 67, i64 16384] +// CK1: [[MTYPE06:@.+]] = {{.*}}constant [2 x i64] [i64 67, i64 16384] +// CK1: [[MTYPE07:@.+]] = {{.*}}constant [2 x i64] [i64 67, i64 16384] +// CK1: [[MTYPE08:@.+]] = {{.*}}constant [4 x i64] [i64 67, i64 16384, i64 3, i64 16384] +// CK1: [[MTYPE09:@.+]] = {{.*}}constant [4 x i64] [i64 67, i64 16384, i64 67, i64 16384] +// CK1: [[MTYPE10:@.+]] = {{.*}}constant [4 x i64] [i64 67, i64 16384, i64 67, i64 16384] +// CK1: [[MTYPE11:@.+]] = {{.*}}constant [3 x i64] [i64 3, i64 16384, i64 64] +// CK1: [[MTYPE12:@.+]] = {{.*}}constant [3 x i64] [i64 3, i64 16384, i64 64] // CK1-LABEL: @_Z3foo template @@ -41,8 +41,11 @@ void foo(float *&lr, T *&tr) { float *l; T *t; + // &g[0], &g[/*lb=*/0], 10 * sizeof(g[0]), TO | FROM | RETURN_PARAM + // &g, &g[/*lb=*/0], sizeof(g), ATTACH + // // CK1: [[T:%.+]] = load ptr, ptr [[DECL:@g]], - // CK1: [[BP:%.+]] = getelementptr inbounds [2 x ptr], ptr %{{.+}}, i32 0, i32 1 + // CK1: [[BP:%.+]] = getelementptr inbounds [2 x ptr], ptr %{{.+}}, i32 0, i32 0 // CK1: store ptr [[T]], ptr [[BP]], // CK1: call void @__tgt_target_data_begin{{.+}}[[MTYPE00]] // CK1: [[VAL:%.+]] = load ptr, ptr [[BP]], @@ -50,7 +53,7 @@ void foo(float *&lr, T *&tr) { // CK1: store ptr [[VAL]], ptr [[PVT:%.+]], // CK1: [[TT:%.+]] = load ptr, ptr [[PVT]], // CK1: getelementptr inbounds nuw double, ptr [[TT]], i32 1 - #pragma omp target data map(g[:10]) use_device_ptr(g) + #pragma omp target data map(g[0:10]) use_device_ptr(g) { ++g; } @@ -59,8 +62,11 @@ void foo(float *&lr, T *&tr) { // CK1: getelementptr inbounds nuw double, ptr [[TTT]], i32 1 ++g; + // &l[0], &l[/*lb=*/0], 10 * sizeof(l[0]), TO | FROM | RETURN_PARAM + // &l, &l[/*lb=*/0], sizeof(l), ATTACH + // // CK1: [[T1:%.+]] = load ptr, ptr [[DECL:%.+]], - // CK1: [[BP:%.+]] = getelementptr inbounds [1 x ptr], ptr %{{.+}}, i32 0, i32 0 + // CK1: [[BP:%.+]] = getelementptr inbounds [2 x ptr], ptr %{{.+}}, i32 0, i32 0 // CK1: store ptr [[T1]], ptr [[BP]], // CK1: call void @__tgt_target_data_begin{{.+}}[[MTYPE01]] // CK1: [[VAL:%.+]] = load ptr, ptr [[BP]], @@ -68,7 +74,7 @@ void foo(float *&lr, T *&tr) { // CK1: store ptr [[VAL]], ptr [[PVT:%.+]], // CK1: [[TT1:%.+]] = load ptr, ptr [[PVT]], // CK1: getelementptr inbounds nuw float, ptr [[TT1]], i32 1 - #pragma omp target data map(l[:10]) use_device_ptr(l) + #pragma omp target data map(l[0:10]) use_device_ptr(l) { ++l; } @@ -90,7 +96,7 @@ void foo(float *&lr, T *&tr) { ++l; // CK1: [[T1:%.+]] = load ptr, ptr [[DECL:%.+]], - // CK1: [[BP:%.+]] = getelementptr inbounds [1 x ptr], ptr %{{.+}}, i32 0, i32 0 + // CK1: [[BP:%.+]] = getelementptr inbounds [2 x ptr], ptr %{{.+}}, i32 0, i32 0 // CK1: store ptr [[T1]], ptr [[BP]], // CK1: call void @__tgt_target_data_begin{{.+}}[[MTYPE03]] // CK1: [[VAL:%.+]] = load ptr, ptr [[BP]], @@ -112,7 +118,7 @@ void foo(float *&lr, T *&tr) { // CK1: [[BTHEN]]: // CK1: [[T1:%.+]] = load ptr, ptr [[DECL:%.+]], - // CK1: [[BP:%.+]] = getelementptr inbounds [1 x ptr], ptr %{{.+}}, i32 0, i32 0 + // CK1: [[BP:%.+]] = getelementptr inbounds [2 x ptr], ptr %{{.+}}, i32 0, i32 0 // CK1: store ptr [[T1]], ptr [[BP]], // CK1: call void @__tgt_target_data_begin{{.+}}[[MTYPE04]] // CK1: [[VAL:%.+]] = load ptr, ptr [[BP]], @@ -145,9 +151,12 @@ void foo(float *&lr, T *&tr) { // CK1: getelementptr inbounds nuw float, ptr [[TTT]], i32 1 ++l; + // &(ref_ptee(lr)[0]), &(ref_ptee(lr)[/*lb=*/0]), 10 * sizeof(lr[0]), TO | FROM | RETURN_PARAM + // &(ref_ptee(lr)), &(ref_ptee(lr)[/*lb=*/0]), sizeof(ref_ptee(lr)), ATTACH + // // CK1: [[T2:%.+]] = load ptr, ptr [[DECL:%.+]], // CK1: [[T1:%.+]] = load ptr, ptr [[T2]], - // CK1: [[BP:%.+]] = getelementptr inbounds [1 x ptr], ptr %{{.+}}, i32 0, i32 0 + // CK1: [[BP:%.+]] = getelementptr inbounds [2 x ptr], ptr %{{.+}}, i32 0, i32 0 // CK1: store ptr [[T1]], ptr [[BP]], // CK1: call void @__tgt_target_data_begin{{.+}}[[MTYPE05]] // CK1: [[VAL:%.+]] = load ptr, ptr [[BP]], @@ -167,8 +176,11 @@ void foo(float *&lr, T *&tr) { // CK1: getelementptr inbounds nuw float, ptr [[TTTT]], i32 1 ++lr; + // &t[0], &t[/*lb=*/0], 10 * sizeof(t[0]), TO | FROM | RETURN_PARAM + // &t, &t[/*lb=*/0], sizeof(t), ATTACH + // // CK1: [[T1:%.+]] = load ptr, ptr [[DECL:%.+]], - // CK1: [[BP:%.+]] = getelementptr inbounds [1 x ptr], ptr %{{.+}}, i32 0, i32 0 + // CK1: [[BP:%.+]] = getelementptr inbounds [2 x ptr], ptr %{{.+}}, i32 0, i32 0 // CK1: store ptr [[T1]], ptr [[BP]], // CK1: call void @__tgt_target_data_begin{{.+}}[[MTYPE06]] // CK1: [[VAL:%.+]] = load ptr, ptr [[BP]], @@ -185,9 +197,12 @@ void foo(float *&lr, T *&tr) { // CK1: getelementptr inbounds nuw i32, ptr [[TTT]], i32 1 ++t; + // &(ref_ptee(tr)[0]), &(ref_ptee(tr)[/*lb=*/0]), 10 * sizeof(tr[0]), TO | FROM | RETURN_PARAM + // &(ref_ptee(tr)), &(ref_ptee(tr)[/*lb=*/0]), sizeof(ref_ptee(tr)), ATTACH + // // CK1: [[T2:%.+]] = load ptr, ptr [[DECL:%.+]], // CK1: [[T1:%.+]] = load ptr, ptr [[T2]], - // CK1: [[BP:%.+]] = getelementptr inbounds [1 x ptr], ptr %{{.+}}, i32 0, i32 0 + // CK1: [[BP:%.+]] = getelementptr inbounds [2 x ptr], ptr %{{.+}}, i32 0, i32 0 // CK1: store ptr [[T1]], ptr [[BP]], // CK1: call void @__tgt_target_data_begin{{.+}}[[MTYPE07]] // CK1: [[VAL:%.+]] = load ptr, ptr [[BP]], @@ -207,8 +222,13 @@ void foo(float *&lr, T *&tr) { // CK1: getelementptr inbounds nuw i32, ptr [[TTTT]], i32 1 ++tr; + // &l[0], &l[/*lb=*/0], 10 * sizeof(l[0]), TO | FROM [| RETURN_PARAM] + // &l, &l[/*lb=*/0], sizeof(l), ATTACH + // &t[0], &t[/*lb=*/0], 10 * sizeof(t[0]), TO | FROM [| RETURN_PARAM] + // &t, &t[/*lb=*/0], sizeof(t), ATTACH + // CK1: [[T1:%.+]] = load ptr, ptr [[DECL:%.+]], - // CK1: [[BP:%.+]] = getelementptr inbounds [2 x ptr], ptr %{{.+}}, i32 0, i32 0 + // CK1: [[BP:%.+]] = getelementptr inbounds [4 x ptr], ptr %{{.+}}, i32 0, i32 0 // CK1: store ptr [[T1]], ptr [[BP]], // CK1: call void @__tgt_target_data_begin{{.+}}[[MTYPE08]] // CK1: [[VAL:%.+]] = load ptr, ptr [[BP]], @@ -266,8 +286,11 @@ void foo(float *&lr, T *&tr) { // CK1: getelementptr inbounds nuw i32, ptr [[TTT]], i32 1 ++l; ++t; + // &l[0], &l[/*lb=*/0], 10 * sizeof(l[0]), TO | FROM [| RETURN_PARAM] + // &l, &l[/*lb=*/0], sizeof(l), ATTACH + // &t[0], &t[/*lb=*/0], 0, RETURN_PARAM // CK1: [[T1:%.+]] = load ptr, ptr [[DECL:%.+]], - // CK1: [[BP:%.+]] = getelementptr inbounds [2 x ptr], ptr %{{.+}}, i32 0, i32 1 + // CK1: [[BP:%.+]] = getelementptr inbounds [3 x ptr], ptr %{{.+}}, i32 0, i32 2 // CK1: store ptr [[T1]], ptr [[BP]], // CK1: call void @__tgt_target_data_begin{{.+}}[[MTYPE11]] // CK1: [[VAL:%.+]] = load ptr, ptr [[BP]], @@ -286,7 +309,7 @@ void foo(float *&lr, T *&tr) { // CK1: [[T2:%.+]] = load ptr, ptr [[DECL:%.+]], // CK1: [[T1:%.+]] = load ptr, ptr [[T2]], - // CK1: [[BP:%.+]] = getelementptr inbounds [2 x ptr], ptr %{{.+}}, i32 0, i32 1 + // CK1: [[BP:%.+]] = getelementptr inbounds [3 x ptr], ptr %{{.+}}, i32 0, i32 2 // CK1: store ptr [[T1]], ptr [[BP]], // CK1: call void @__tgt_target_data_begin{{.+}}[[MTYPE12]] // CK1: [[VAL:%.+]] = load ptr, ptr [[BP]], @@ -333,7 +356,7 @@ void bar(float *&a, int *&b) { // CK2: [[ST:%.+]] = type { ptr, ptr } // CK2: [[MTYPE00:@.+]] = {{.*}}constant [2 x i64] [i64 0, i64 281474976710739] // CK2: [[MTYPE01:@.+]] = {{.*}}constant [2 x i64] [i64 0, i64 281474976710739] -// CK2: [[MTYPE02:@.+]] = {{.*}}constant [3 x i64] [i64 3, i64 0, i64 562949953421392] +// CK2: [[MTYPE02:@.+]] = {{.*}}constant [4 x i64] [i64 3, i64 16384, i64 0, i64 844424930132048] // CK2: [[MTYPE03:@.+]] = {{.*}}constant [3 x i64] [i64 0, i64 281474976710739, i64 281474976710736] template @@ -385,7 +408,7 @@ struct ST { // CK2: getelementptr inbounds nuw double, ptr [[TTTT]], i32 1 b++; - // CK2: [[BP:%.+]] = getelementptr inbounds [3 x ptr], ptr %{{.+}}, i32 0, i32 2 + // CK2: [[BP:%.+]] = getelementptr inbounds [4 x ptr], ptr %{{.+}}, i32 0, i32 3 // CK2: store ptr [[RVAL:%.+]], ptr [[BP]], // CK2: call void @__tgt_target_data_begin{{.+}}[[MTYPE02]] // CK2: [[VAL:%.+]] = load ptr, ptr [[BP]], diff --git a/clang/test/OpenMP/target_data_use_device_ptr_if_codegen.cpp b/clang/test/OpenMP/target_data_use_device_ptr_if_codegen.cpp index 5da5806752cee..fd0e3ee032c6f 100644 --- a/clang/test/OpenMP/target_data_use_device_ptr_if_codegen.cpp +++ b/clang/test/OpenMP/target_data_use_device_ptr_if_codegen.cpp @@ -18,22 +18,39 @@ // SIMD-ONLY1-NOT: {{__kmpc|__tgt}} #ifdef CK1 -// CK1: [[MTYPE00:@.+]] = {{.*}}constant [1 x i64] [i64 67] +// CK1: [[MYSIZE00:@.+]] = {{.*}}constant [2 x i64] [i64 4, i64 {{8|4}}] +// CK1: [[MTYPE00:@.+]] = {{.*}}constant [2 x i64] [i64 67, i64 16384] // CK1: [[MTYPE01:@.+]] = {{.*}}constant [1 x i64] [i64 288] // CK1: [[MTYPE02:@.+]] = {{.*}}constant [1 x i64] [i64 288] void add_one(float *b, int dm) { - // CK1: [[BP:%.+]] = getelementptr inbounds [1 x ptr], ptr %{{.+}}, i32 0, i32 0 - // CK1: store ptr [[B_ADDR:%.+]], ptr [[BP]] - // CK1: call void @__tgt_target_data_begin{{.+}}[[MTYPE00]] - // CK1: [[VAL:%.+]] = load ptr, ptr [[BP]], + // &B[0], &B[0], 1 * sizeof(B[0]), PARAM | TO | FROM + // &B, &B[0], sizeof(B), ATTACH + + // CK1: [[RB_1:%.*]] = load ptr, ptr [[B:%b.addr]] + // CK1: [[RB_2:%.*]] = load ptr, ptr [[B]] + // CK1: [[RB0_1:%.*]] = getelementptr inbounds nuw float, ptr [[RB_2]], i{{.*}} 0 + + // CK1: [[BP0:%.+]] = getelementptr inbounds [2 x ptr], ptr [[BP:%.offload_baseptrs.*]], i32 0, i32 0 + // CK1: store ptr [[RB_1]], ptr [[BP0]] + // CK1: [[P0:%.+]] = getelementptr inbounds [2 x ptr], ptr [[P:%.offload_ptrs.*]], i32 0, i32 0 + // CK1: store ptr [[RB0_1]], ptr [[P0]] + + // CK1: [[BP1:%.+]] = getelementptr inbounds [2 x ptr], ptr [[BP]], i32 0, i32 1 + // CK1: store ptr [[B]], ptr [[BP1]] + // CK1: [[P1:%.+]] = getelementptr inbounds [2 x ptr], ptr [[P]], i32 0, i32 1 + // CK1: store ptr [[RB0_1]], ptr [[P1]] + + // CK1: call void @__tgt_target_data_begin{{.+}}ptr [[MYSIZE00]], ptr [[MTYPE00]] + + // CK1: [[VAL:%.+]] = load ptr, ptr [[BP0]], // CK1-NOT: store ptr [[VAL]], ptr {{%.+}}, // CK1: store ptr [[VAL]], ptr [[PVT:%.+]], // CK1: [[TT:%.+]] = load ptr, ptr [[PVT]], // CK1: call i32 @__tgt_target{{.+}} // CK1: call i32 @__tgt_target{{.+}} - // CK1: call void @__tgt_target_data_end{{.+}}[[MTYPE00]] + // CK1: call void @__tgt_target_data_end{{.+}}ptr [[MYSIZE00]], ptr [[MTYPE00]] #pragma omp target data map(tofrom:b[:1]) use_device_ptr(b) if(dm == 0) { #pragma omp target is_device_ptr(b) diff --git a/clang/test/OpenMP/target_map_both_pointer_pointee_codegen.cpp b/clang/test/OpenMP/target_map_both_pointer_pointee_codegen.cpp index 8a167a19ddbc9..737c855adc05b 100644 --- a/clang/test/OpenMP/target_map_both_pointer_pointee_codegen.cpp +++ b/clang/test/OpenMP/target_map_both_pointer_pointee_codegen.cpp @@ -17,6 +17,7 @@ void f1() { void f2() { int *ptr; // &ptr[0], &ptr[2], sizeof(ptr[2]), TO | FROM | PARAM + // &ptr, &ptr[2], sizeof(ptr), ATTACH #pragma omp target map(ptr[2]) ptr[1] = 6; } @@ -24,7 +25,8 @@ void f2() { void f3() { int *ptr; // &ptr, &ptr, sizeof(ptr), TO | FROM | PARAM - // &ptr, &ptr[0], 2 * sizeof(ptr[0]), TO | FROM | PTR_AND_OBJ + // &ptr[0], &ptr[0], 2 * sizeof(ptr[0]), TO | FROM + // &ptr, &ptr[0], sizeof(ptr), ATTACH #pragma omp target map(ptr, ptr[0:2]) ptr[1] = 7; } @@ -32,7 +34,8 @@ void f3() { void f4() { int *ptr; // &ptr, &ptr, sizeof(ptr), TO | FROM | PARAM - // &ptr, &ptr[2], sizeof(ptr[2]), TO | FROM | PTR_AND_OBJ + // &ptr[0], &ptr[2], sizeof(ptr[2]), TO | FROM + // &ptr, &ptr[2], sizeof(ptr), ATTACH #pragma omp target map(ptr, ptr[2]) ptr[2] = 8; } @@ -40,23 +43,26 @@ void f4() { void f5() { int *ptr; // &ptr, &ptr, sizeof(ptr), TO | FROM | PARAM - // &ptr, &ptr[2], sizeof(ptr[2]), TO | FROM | PTR_AND_OBJ + // &ptr[0], &ptr[2], sizeof(ptr[2]), TO | FROM + // &ptr, &ptr[2], sizeof(ptr), ATTACH #pragma omp target map(ptr[2], ptr) ptr[2] = 9; } void f6() { int *ptr; - // &ptr, &ptr[2], sizeof(ptr[2]), TO | FROM | PARAM | PTR_AND_OBJ - // TODO: PARAM should not be needed here. + // &ptr, &ptr, sizeof(ptr), TO | FROM | PARAM + // &ptr[0], &ptr[2], sizeof(ptr[2]), TO | FROM + // &ptr, &ptr[2], sizeof(ptr), ATTACH #pragma omp target data map(ptr, ptr[2]) ptr[2] = 10; } void f7() { int *ptr; - // &ptr, &ptr[2], sizeof(ptr[2]), TO | FROM | PARAM | PTR_AND_OBJ - // TODO: PARAM should not be needed here. + // &ptr[0], &ptr[2], sizeof(ptr[2]), TO | FROM + // &ptr, &ptr[2], sizeof(ptr), ATTACH + // &ptr, &ptr, sizeof(ptr), TO | FROM | PARAM #pragma omp target data map(ptr[2], ptr) ptr[2] = 11; } @@ -64,18 +70,18 @@ void f7() { //. // CHECK: @.offload_sizes = private unnamed_addr constant [1 x i64] [i64 8] // CHECK: @.offload_maptypes = private unnamed_addr constant [1 x i64] [i64 [[#0x23]]] -// CHECK: @.offload_sizes.1 = private unnamed_addr constant [1 x i64] [i64 4] -// CHECK: @.offload_maptypes.2 = private unnamed_addr constant [1 x i64] [i64 [[#0x23]]] -// CHECK: @.offload_sizes.3 = private unnamed_addr constant [2 x i64] [i64 8, i64 8] -// CHECK: @.offload_maptypes.4 = private unnamed_addr constant [2 x i64] [i64 [[#0x23]], i64 [[#0x13]]] -// CHECK: @.offload_sizes.5 = private unnamed_addr constant [2 x i64] [i64 8, i64 4] -// CHECK: @.offload_maptypes.6 = private unnamed_addr constant [2 x i64] [i64 [[#0x23]], i64 [[#0x13]]] -// CHECK: @.offload_sizes.7 = private unnamed_addr constant [2 x i64] [i64 8, i64 4] -// CHECK: @.offload_maptypes.8 = private unnamed_addr constant [2 x i64] [i64 [[#0x23]], i64 [[#0x13]]] -// CHECK: @.offload_sizes.9 = private unnamed_addr constant [1 x i64] [i64 4] -// CHECK: @.offload_maptypes.10 = private unnamed_addr constant [1 x i64] [i64 [[#0x33]]] -// CHECK: @.offload_sizes.11 = private unnamed_addr constant [1 x i64] [i64 4] -// CHECK: @.offload_maptypes.12 = private unnamed_addr constant [1 x i64] [i64 [[#0x33]]] +// CHECK: @.offload_sizes.1 = private unnamed_addr constant [2 x i64] [i64 4, i64 8] +// CHECK: @.offload_maptypes.2 = private unnamed_addr constant [2 x i64] [i64 [[#0x23]], i64 [[#0x4000]]] +// CHECK: @.offload_sizes.3 = private unnamed_addr constant [3 x i64] [i64 8, i64 8, i64 8] +// CHECK: @.offload_maptypes.4 = private unnamed_addr constant [3 x i64] [i64 [[#0x23]], i64 [[#0x3]], i64 [[#0x4000]]] +// CHECK: @.offload_sizes.5 = private unnamed_addr constant [3 x i64] [i64 8, i64 4, i64 8] +// CHECK: @.offload_maptypes.6 = private unnamed_addr constant [3 x i64] [i64 [[#0x23]], i64 [[#0x3]], i64 [[#0x4000]]] +// CHECK: @.offload_sizes.7 = private unnamed_addr constant [3 x i64] [i64 8, i64 4, i64 8] +// CHECK: @.offload_maptypes.8 = private unnamed_addr constant [3 x i64] [i64 [[#0x23]], i64 [[#0x3]], i64 [[#0x4000]]] +// CHECK: @.offload_sizes.9 = private unnamed_addr constant [3 x i64] [i64 8, i64 4, i64 8] +// CHECK: @.offload_maptypes.10 = private unnamed_addr constant [3 x i64] [i64 [[#0x3]], i64 [[#0x3]], i64 [[#0x4000]]] +// CHECK: @.offload_sizes.11 = private unnamed_addr constant [3 x i64] [i64 4, i64 8, i64 8] +// CHECK: @.offload_maptypes.12 = private unnamed_addr constant [3 x i64] [i64 [[#0x3]], i64 [[#0x4000]], i64 [[#0x3]]] //. // CHECK-LABEL: define {{[^@]+}}@_Z2f1v // CHECK-SAME: () #[[ATTR0:[0-9]+]] { @@ -109,18 +115,24 @@ void f7() { // CHECK: [[TMP1:%.*]] = load ptr, ptr [[PTR]], align 8 // CHECK: [[TMP2:%.*]] = load ptr, ptr [[PTR]], align 8 // CHECK: [[ARRAYIDX:%.*]] = getelementptr inbounds i32, ptr [[TMP2]], i64 2 -// CHECK: [[TMP3:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP3:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 // CHECK: store ptr [[TMP1]], ptr [[TMP3]], align 8 -// CHECK: [[TMP4:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP4:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 // CHECK: store ptr [[ARRAYIDX]], ptr [[TMP4]], align 8 -// CHECK: [[TMP5:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 +// CHECK: [[TMP5:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 // CHECK: store ptr null, ptr [[TMP5]], align 8 -// CHECK: [[TMP6:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP7:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: [[TMP8:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 +// CHECK: [[TMP6:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK: store ptr [[PTR]], ptr [[TMP6]], align 8 +// CHECK: [[TMP7:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP7]], align 8 +// CHECK: [[TMP8:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK: store ptr null, ptr [[TMP8]], align 8 +// CHECK: [[TMP9:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP10:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: [[TMP11:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 // // -// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f2v_l20 +// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f2v_l21 // CHECK-SAME: (ptr noundef [[PTR:%.*]]) #[[ATTR1]] { // CHECK: entry: // CHECK: store ptr [[PTR]], ptr [[PTR_ADDR:%.*]], align 8 @@ -134,25 +146,32 @@ void f7() { // CHECK-SAME: () #[[ATTR0]] { // CHECK: entry: // CHECK: [[TMP0:%.*]] = load ptr, ptr [[PTR:%.*]], align 8 -// CHECK: [[ARRAYIDX:%.*]] = getelementptr inbounds nuw i32, ptr [[TMP0]], i64 0 -// CHECK: [[TMP1:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 -// CHECK: store ptr [[PTR]], ptr [[TMP1]], align 8 -// CHECK: [[TMP2:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP1:%.*]] = load ptr, ptr [[PTR]], align 8 +// CHECK: [[ARRAYIDX:%.*]] = getelementptr inbounds nuw i32, ptr [[TMP1]], i64 0 +// CHECK: [[TMP2:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 // CHECK: store ptr [[PTR]], ptr [[TMP2]], align 8 -// CHECK: [[TMP3:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 -// CHECK: store ptr null, ptr [[TMP3]], align 8 -// CHECK: [[TMP4:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 -// CHECK: store ptr [[PTR]], ptr [[TMP4]], align 8 -// CHECK: [[TMP5:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 -// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP5]], align 8 -// CHECK: [[TMP6:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 -// CHECK: store ptr null, ptr [[TMP6]], align 8 -// CHECK: [[TMP7:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP8:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: [[TMP9:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 +// CHECK: [[TMP3:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: store ptr [[PTR]], ptr [[TMP3]], align 8 +// CHECK: [[TMP4:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 +// CHECK: store ptr null, ptr [[TMP4]], align 8 +// CHECK: [[TMP5:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK: store ptr [[TMP0]], ptr [[TMP5]], align 8 +// CHECK: [[TMP6:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP6]], align 8 +// CHECK: [[TMP7:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK: store ptr null, ptr [[TMP7]], align 8 +// CHECK: [[TMP8:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 2 +// CHECK: store ptr [[PTR]], ptr [[TMP8]], align 8 +// CHECK: [[TMP9:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 2 +// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP9]], align 8 +// CHECK: [[TMP10:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 2 +// CHECK: store ptr null, ptr [[TMP10]], align 8 +// CHECK: [[TMP11:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP12:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: [[TMP13:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 // // -// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f3v_l28 +// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f3v_l30 // CHECK-SAME: (ptr noundef nonnull align 8 dereferenceable(8) [[PTR:%.*]]) #[[ATTR1]] { // CHECK: entry: // CHECK: store ptr [[PTR]], ptr [[PTR_ADDR:%.*]], align 8 @@ -167,25 +186,32 @@ void f7() { // CHECK-SAME: () #[[ATTR0]] { // CHECK: entry: // CHECK: [[TMP0:%.*]] = load ptr, ptr [[PTR:%.*]], align 8 -// CHECK: [[ARRAYIDX:%.*]] = getelementptr inbounds i32, ptr [[TMP0]], i64 2 -// CHECK: [[TMP1:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 -// CHECK: store ptr [[PTR]], ptr [[TMP1]], align 8 -// CHECK: [[TMP2:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP1:%.*]] = load ptr, ptr [[PTR]], align 8 +// CHECK: [[ARRAYIDX:%.*]] = getelementptr inbounds i32, ptr [[TMP1]], i64 2 +// CHECK: [[TMP2:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 // CHECK: store ptr [[PTR]], ptr [[TMP2]], align 8 -// CHECK: [[TMP3:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 -// CHECK: store ptr null, ptr [[TMP3]], align 8 -// CHECK: [[TMP4:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 -// CHECK: store ptr [[PTR]], ptr [[TMP4]], align 8 -// CHECK: [[TMP5:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 -// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP5]], align 8 -// CHECK: [[TMP6:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 -// CHECK: store ptr null, ptr [[TMP6]], align 8 -// CHECK: [[TMP7:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP8:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: [[TMP9:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 +// CHECK: [[TMP3:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: store ptr [[PTR]], ptr [[TMP3]], align 8 +// CHECK: [[TMP4:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 +// CHECK: store ptr null, ptr [[TMP4]], align 8 +// CHECK: [[TMP5:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK: store ptr [[TMP0]], ptr [[TMP5]], align 8 +// CHECK: [[TMP6:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP6]], align 8 +// CHECK: [[TMP7:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK: store ptr null, ptr [[TMP7]], align 8 +// CHECK: [[TMP8:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 2 +// CHECK: store ptr [[PTR]], ptr [[TMP8]], align 8 +// CHECK: [[TMP9:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 2 +// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP9]], align 8 +// CHECK: [[TMP10:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 2 +// CHECK: store ptr null, ptr [[TMP10]], align 8 +// CHECK: [[TMP11:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP12:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: [[TMP13:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 // // -// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f4v_l36 +// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f4v_l39 // CHECK-SAME: (ptr noundef nonnull align 8 dereferenceable(8) [[PTR:%.*]]) #[[ATTR1]] { // CHECK: entry: // CHECK: store ptr [[PTR]], ptr [[PTR_ADDR:%.*]], align 8 @@ -200,25 +226,32 @@ void f7() { // CHECK-SAME: () #[[ATTR0]] { // CHECK: entry: // CHECK: [[TMP0:%.*]] = load ptr, ptr [[PTR:%.*]], align 8 -// CHECK: [[ARRAYIDX:%.*]] = getelementptr inbounds i32, ptr [[TMP0]], i64 2 -// CHECK: [[TMP1:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 -// CHECK: store ptr [[PTR]], ptr [[TMP1]], align 8 -// CHECK: [[TMP2:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP1:%.*]] = load ptr, ptr [[PTR]], align 8 +// CHECK: [[ARRAYIDX:%.*]] = getelementptr inbounds i32, ptr [[TMP1]], i64 2 +// CHECK: [[TMP2:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 // CHECK: store ptr [[PTR]], ptr [[TMP2]], align 8 -// CHECK: [[TMP3:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 -// CHECK: store ptr null, ptr [[TMP3]], align 8 -// CHECK: [[TMP4:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 -// CHECK: store ptr [[PTR]], ptr [[TMP4]], align 8 -// CHECK: [[TMP5:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 -// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP5]], align 8 -// CHECK: [[TMP6:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 -// CHECK: store ptr null, ptr [[TMP6]], align 8 -// CHECK: [[TMP7:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP8:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: [[TMP9:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 +// CHECK: [[TMP3:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: store ptr [[PTR]], ptr [[TMP3]], align 8 +// CHECK: [[TMP4:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 +// CHECK: store ptr null, ptr [[TMP4]], align 8 +// CHECK: [[TMP5:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK: store ptr [[TMP0]], ptr [[TMP5]], align 8 +// CHECK: [[TMP6:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP6]], align 8 +// CHECK: [[TMP7:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK: store ptr null, ptr [[TMP7]], align 8 +// CHECK: [[TMP8:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 2 +// CHECK: store ptr [[PTR]], ptr [[TMP8]], align 8 +// CHECK: [[TMP9:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 2 +// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP9]], align 8 +// CHECK: [[TMP10:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 2 +// CHECK: store ptr null, ptr [[TMP10]], align 8 +// CHECK: [[TMP11:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP12:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: [[TMP13:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 // // -// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f5v_l44 +// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f5v_l48 // CHECK-SAME: (ptr noundef nonnull align 8 dereferenceable(8) [[PTR:%.*]]) #[[ATTR1]] { // CHECK: entry: // CHECK: store ptr [[PTR]], ptr [[PTR_ADDR:%.*]], align 8 @@ -233,22 +266,35 @@ void f7() { // CHECK-SAME: () #[[ATTR0]] { // CHECK: entry: // CHECK: [[TMP0:%.*]] = load ptr, ptr [[PTR:%.*]], align 8 -// CHECK: [[ARRAYIDX:%.*]] = getelementptr inbounds i32, ptr [[TMP0]], i64 2 -// CHECK: [[TMP1:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 -// CHECK: store ptr [[PTR]], ptr [[TMP1]], align 8 -// CHECK: [[TMP2:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 -// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP2]], align 8 -// CHECK: [[TMP3:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 -// CHECK: store ptr null, ptr [[TMP3]], align 8 -// CHECK: [[TMP4:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP5:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: call void @__tgt_target_data_begin_mapper(ptr @[[GLOB1:[0-9]+]], i64 -1, i32 1, ptr [[TMP4]], ptr [[TMP5]], ptr @.offload_sizes.9, ptr @.offload_maptypes.10, ptr null, ptr null) -// CHECK: [[TMP6:%.*]] = load ptr, ptr [[PTR]], align 8 -// CHECK: [[ARRAYIDX1:%.*]] = getelementptr inbounds i32, ptr [[TMP6]], i64 2 +// CHECK: [[TMP1:%.*]] = load ptr, ptr [[PTR]], align 8 +// CHECK: [[ARRAYIDX:%.*]] = getelementptr inbounds i32, ptr [[TMP1]], i64 2 +// CHECK: [[TMP2:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 +// CHECK: store ptr [[PTR]], ptr [[TMP2]], align 8 +// CHECK: [[TMP3:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: store ptr [[PTR]], ptr [[TMP3]], align 8 +// CHECK: [[TMP4:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 +// CHECK: store ptr null, ptr [[TMP4]], align 8 +// CHECK: [[TMP5:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK: store ptr [[TMP0]], ptr [[TMP5]], align 8 +// CHECK: [[TMP6:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP6]], align 8 +// CHECK: [[TMP7:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK: store ptr null, ptr [[TMP7]], align 8 +// CHECK: [[TMP8:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 2 +// CHECK: store ptr [[PTR]], ptr [[TMP8]], align 8 +// CHECK: [[TMP9:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 2 +// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP9]], align 8 +// CHECK: [[TMP10:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 2 +// CHECK: store ptr null, ptr [[TMP10]], align 8 +// CHECK: [[TMP11:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP12:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: call void @__tgt_target_data_begin_mapper(ptr @[[GLOB1:[0-9]+]], i64 -1, i32 3, ptr [[TMP11]], ptr [[TMP12]], ptr @.offload_sizes.9, ptr @.offload_maptypes.10, ptr null, ptr null) +// CHECK: [[TMP13:%.*]] = load ptr, ptr [[PTR]], align 8 +// CHECK: [[ARRAYIDX1:%.*]] = getelementptr inbounds i32, ptr [[TMP13]], i64 2 // CHECK: store i32 10, ptr [[ARRAYIDX1]], align 4 -// CHECK: [[TMP7:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP8:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: call void @__tgt_target_data_end_mapper(ptr @[[GLOB1]], i64 -1, i32 1, ptr [[TMP7]], ptr [[TMP8]], ptr @.offload_sizes.9, ptr @.offload_maptypes.10, ptr null, ptr null) +// CHECK: [[TMP14:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP15:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: call void @__tgt_target_data_end_mapper(ptr @[[GLOB1]], i64 -1, i32 3, ptr [[TMP14]], ptr [[TMP15]], ptr @.offload_sizes.9, ptr @.offload_maptypes.10, ptr null, ptr null) // CHECK: ret void // // @@ -256,21 +302,34 @@ void f7() { // CHECK-SAME: () #[[ATTR0]] { // CHECK: entry: // CHECK: [[TMP0:%.*]] = load ptr, ptr [[PTR:%.*]], align 8 -// CHECK: [[ARRAYIDX:%.*]] = getelementptr inbounds i32, ptr [[TMP0]], i64 2 -// CHECK: [[TMP1:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 -// CHECK: store ptr [[PTR]], ptr [[TMP1]], align 8 -// CHECK: [[TMP2:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 -// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP2]], align 8 -// CHECK: [[TMP3:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 -// CHECK: store ptr null, ptr [[TMP3]], align 8 -// CHECK: [[TMP4:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP5:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: call void @__tgt_target_data_begin_mapper(ptr @[[GLOB1]], i64 -1, i32 1, ptr [[TMP4]], ptr [[TMP5]], ptr @.offload_sizes.11, ptr @.offload_maptypes.12, ptr null, ptr null) -// CHECK: [[TMP6:%.*]] = load ptr, ptr [[PTR]], align 8 -// CHECK: [[ARRAYIDX1:%.*]] = getelementptr inbounds i32, ptr [[TMP6]], i64 2 +// CHECK: [[TMP1:%.*]] = load ptr, ptr [[PTR]], align 8 +// CHECK: [[ARRAYIDX:%.*]] = getelementptr inbounds i32, ptr [[TMP1]], i64 2 +// CHECK: [[TMP2:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 +// CHECK: store ptr [[TMP0]], ptr [[TMP2]], align 8 +// CHECK: [[TMP3:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP3]], align 8 +// CHECK: [[TMP4:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 +// CHECK: store ptr null, ptr [[TMP4]], align 8 +// CHECK: [[TMP5:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK: store ptr [[PTR]], ptr [[TMP5]], align 8 +// CHECK: [[TMP6:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP6]], align 8 +// CHECK: [[TMP7:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK: store ptr null, ptr [[TMP7]], align 8 +// CHECK: [[TMP8:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 2 +// CHECK: store ptr [[PTR]], ptr [[TMP8]], align 8 +// CHECK: [[TMP9:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 2 +// CHECK: store ptr [[PTR]], ptr [[TMP9]], align 8 +// CHECK: [[TMP10:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 2 +// CHECK: store ptr null, ptr [[TMP10]], align 8 +// CHECK: [[TMP11:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP12:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: call void @__tgt_target_data_begin_mapper(ptr @[[GLOB1]], i64 -1, i32 3, ptr [[TMP11]], ptr [[TMP12]], ptr @.offload_sizes.11, ptr @.offload_maptypes.12, ptr null, ptr null) +// CHECK: [[TMP13:%.*]] = load ptr, ptr [[PTR]], align 8 +// CHECK: [[ARRAYIDX1:%.*]] = getelementptr inbounds i32, ptr [[TMP13]], i64 2 // CHECK: store i32 11, ptr [[ARRAYIDX1]], align 4 -// CHECK: [[TMP7:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP8:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: call void @__tgt_target_data_end_mapper(ptr @[[GLOB1]], i64 -1, i32 1, ptr [[TMP7]], ptr [[TMP8]], ptr @.offload_sizes.11, ptr @.offload_maptypes.12, ptr null, ptr null) +// CHECK: [[TMP14:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP15:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: call void @__tgt_target_data_end_mapper(ptr @[[GLOB1]], i64 -1, i32 3, ptr [[TMP14]], ptr [[TMP15]], ptr @.offload_sizes.11, ptr @.offload_maptypes.12, ptr null, ptr null) // CHECK: ret void // diff --git a/clang/test/OpenMP/target_map_both_pointer_pointee_codegen_global.cpp b/clang/test/OpenMP/target_map_both_pointer_pointee_codegen_global.cpp index e39d602dca316..701d09a4889fa 100644 --- a/clang/test/OpenMP/target_map_both_pointer_pointee_codegen_global.cpp +++ b/clang/test/OpenMP/target_map_both_pointer_pointee_codegen_global.cpp @@ -16,42 +16,48 @@ void f1() { } void f2() { - // &ptr, &ptr[2], sizeof(ptr[2]), TO | FROM | PARAM | PTR_AND_OBJ + // &ptr[0], &ptr[2], sizeof(ptr[2]), TO | FROM | PARAM + // &ptr, &ptr[2], sizeof(ptr), ATTACH #pragma omp target map(ptr[2]) ptr[1] = 6; } void f3() { // &ptr, &ptr, sizeof(ptr), TO | FROM | PARAM - // &ptr, &ptr[0], 2 * sizeof(ptr[0]), TO | FROM | PTR_AND_OBJ + // &ptr[0], &ptr[0], 2 * sizeof(ptr[0]), TO | FROM + // &ptr, &ptr[0], sizeof(ptr), ATTACH #pragma omp target map(ptr, ptr[0:2]) ptr[1] = 7; } void f4() { // &ptr, &ptr, sizeof(ptr), TO | FROM | PARAM - // &ptr, &ptr[2], sizeof(ptr[2]), TO | FROM | PTR_AND_OBJ + // &ptr[0], &ptr[2], sizeof(ptr[2]), TO | FROM + // &ptr, &ptr[2], sizeof(ptr), ATTACH #pragma omp target map(ptr, ptr[2]) ptr[2] = 8; } void f5() { // &ptr, &ptr, sizeof(ptr), TO | FROM | PARAM - // &ptr, &ptr[2], sizeof(ptr[2]), TO | FROM | PTR_AND_OBJ + // &ptr[0], &ptr[2], sizeof(ptr[2]), TO | FROM + // &ptr, &ptr[2], sizeof(ptr), ATTACH #pragma omp target map(ptr[2], ptr) ptr[2] = 9; } void f6() { - // &ptr, &ptr[2], sizeof(ptr[2]), TO | FROM | PARAM | PTR_AND_OBJ - // TODO: PARAM should not be needed here. + // &ptr, &ptr, sizeof(ptr), TO | FROM | PARAM + // &ptr[0], &ptr[2], sizeof(ptr[2]), TO | FROM + // &ptr, &ptr[2], sizeof(ptr), ATTACH #pragma omp target data map(ptr, ptr[2]) ptr[2] = 10; } void f7() { - // &ptr, &ptr[2], sizeof(ptr[2]), TO | FROM | PARAM | PTR_AND_OBJ - // TODO: PARAM should not be needed here. + // &ptr[0], &ptr[2], sizeof(ptr[2]), TO | FROM + // &ptr, &ptr[2], sizeof(ptr), ATTACH + // &ptr, &ptr, sizeof(ptr), TO | FROM | PARAM #pragma omp target data map(ptr[2], ptr) ptr[2] = 11; } @@ -59,18 +65,18 @@ void f7() { //. // CHECK: @.offload_sizes = private unnamed_addr constant [1 x i64] [i64 8] // CHECK: @.offload_maptypes = private unnamed_addr constant [1 x i64] [i64 [[#0x23]]] -// CHECK: @.offload_sizes.1 = private unnamed_addr constant [1 x i64] [i64 4] -// CHECK: @.offload_maptypes.2 = private unnamed_addr constant [1 x i64] [i64 [[#0x33]]] -// CHECK: @.offload_sizes.3 = private unnamed_addr constant [2 x i64] [i64 8, i64 8] -// CHECK: @.offload_maptypes.4 = private unnamed_addr constant [2 x i64] [i64 [[#0x23]], i64 [[#0x13]]] -// CHECK: @.offload_sizes.5 = private unnamed_addr constant [2 x i64] [i64 8, i64 4] -// CHECK: @.offload_maptypes.6 = private unnamed_addr constant [2 x i64] [i64 [[#0x23]], i64 [[#0x13]]] -// CHECK: @.offload_sizes.7 = private unnamed_addr constant [2 x i64] [i64 8, i64 4] -// CHECK: @.offload_maptypes.8 = private unnamed_addr constant [2 x i64] [i64 [[#0x23]], i64 [[#0x13]]] -// CHECK: @.offload_sizes.9 = private unnamed_addr constant [1 x i64] [i64 4] -// CHECK: @.offload_maptypes.10 = private unnamed_addr constant [1 x i64] [i64 [[#0x33]]] -// CHECK: @.offload_sizes.11 = private unnamed_addr constant [1 x i64] [i64 4] -// CHECK: @.offload_maptypes.12 = private unnamed_addr constant [1 x i64] [i64 [[#0x33]]] +// CHECK: @.offload_sizes.1 = private unnamed_addr constant [2 x i64] [i64 4, i64 8] +// CHECK: @.offload_maptypes.2 = private unnamed_addr constant [2 x i64] [i64 [[#0x23]], i64 [[#0x4000]]] +// CHECK: @.offload_sizes.3 = private unnamed_addr constant [3 x i64] [i64 8, i64 8, i64 8] +// CHECK: @.offload_maptypes.4 = private unnamed_addr constant [3 x i64] [i64 [[#0x23]], i64 [[#0x3]], i64 [[#0x4000]]] +// CHECK: @.offload_sizes.5 = private unnamed_addr constant [3 x i64] [i64 8, i64 4, i64 8] +// CHECK: @.offload_maptypes.6 = private unnamed_addr constant [3 x i64] [i64 [[#0x23]], i64 [[#0x3]], i64 [[#0x4000]]] +// CHECK: @.offload_sizes.7 = private unnamed_addr constant [3 x i64] [i64 8, i64 4, i64 8] +// CHECK: @.offload_maptypes.8 = private unnamed_addr constant [3 x i64] [i64 [[#0x23]], i64 [[#0x3]], i64 [[#0x4000]]] +// CHECK: @.offload_sizes.9 = private unnamed_addr constant [3 x i64] [i64 8, i64 4, i64 8] +// CHECK: @.offload_maptypes.10 = private unnamed_addr constant [3 x i64] [i64 [[#0x3]], i64 [[#0x3]], i64 [[#0x4000]]] +// CHECK: @.offload_sizes.11 = private unnamed_addr constant [3 x i64] [i64 4, i64 8, i64 8] +// CHECK: @.offload_maptypes.12 = private unnamed_addr constant [3 x i64] [i64 [[#0x3]], i64 [[#0x4000]], i64 [[#0x3]]] //. // CHECK-LABEL: define {{[^@]+}}@_Z2f1v // CHECK-SAME: () #[[ATTR0:[0-9]+]] { @@ -102,19 +108,26 @@ void f7() { // CHECK: entry: // CHECK: [[TMP0:%.*]] = load ptr, ptr @ptr, align 8 // CHECK: [[TMP1:%.*]] = load ptr, ptr @ptr, align 8 -// CHECK: [[ARRAYIDX:%.*]] = getelementptr inbounds i32, ptr [[TMP1]], i64 2 -// CHECK: [[TMP2:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 -// CHECK: store ptr @ptr, ptr [[TMP2]], align 8 -// CHECK: [[TMP3:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 -// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP3]], align 8 -// CHECK: [[TMP4:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 -// CHECK: store ptr null, ptr [[TMP4]], align 8 -// CHECK: [[TMP5:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP6:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: [[TMP7:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 +// CHECK: [[TMP2:%.*]] = load ptr, ptr @ptr, align 8 +// CHECK: [[ARRAYIDX:%.*]] = getelementptr inbounds i32, ptr [[TMP2]], i64 2 +// CHECK: [[TMP3:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 +// CHECK: store ptr [[TMP1]], ptr [[TMP3]], align 8 +// CHECK: [[TMP4:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP4]], align 8 +// CHECK: [[TMP5:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 +// CHECK: store ptr null, ptr [[TMP5]], align 8 +// CHECK: [[TMP6:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK: store ptr @ptr, ptr [[TMP6]], align 8 +// CHECK: [[TMP7:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP7]], align 8 +// CHECK: [[TMP8:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK: store ptr null, ptr [[TMP8]], align 8 +// CHECK: [[TMP9:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP10:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: [[TMP11:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 // // -// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f2v_l20 +// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f2v_l21 // CHECK-SAME: (ptr noundef [[PTR:%.*]]) #[[ATTR1]] { // CHECK: entry: // CHECK: store ptr [[PTR]], ptr [[PTR_ADDR:%.*]], align 8 @@ -128,25 +141,32 @@ void f7() { // CHECK-SAME: () #[[ATTR0]] { // CHECK: entry: // CHECK: [[TMP0:%.*]] = load ptr, ptr @ptr, align 8 -// CHECK: [[ARRAYIDX:%.*]] = getelementptr inbounds nuw i32, ptr [[TMP0]], i64 0 -// CHECK: [[TMP1:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 -// CHECK: store ptr @ptr, ptr [[TMP1]], align 8 -// CHECK: [[TMP2:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP1:%.*]] = load ptr, ptr @ptr, align 8 +// CHECK: [[ARRAYIDX:%.*]] = getelementptr inbounds nuw i32, ptr [[TMP1]], i64 0 +// CHECK: [[TMP2:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 // CHECK: store ptr @ptr, ptr [[TMP2]], align 8 -// CHECK: [[TMP3:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 -// CHECK: store ptr null, ptr [[TMP3]], align 8 -// CHECK: [[TMP4:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 -// CHECK: store ptr @ptr, ptr [[TMP4]], align 8 -// CHECK: [[TMP5:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 -// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP5]], align 8 -// CHECK: [[TMP6:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 -// CHECK: store ptr null, ptr [[TMP6]], align 8 -// CHECK: [[TMP7:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP8:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: [[TMP9:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 +// CHECK: [[TMP3:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: store ptr @ptr, ptr [[TMP3]], align 8 +// CHECK: [[TMP4:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 +// CHECK: store ptr null, ptr [[TMP4]], align 8 +// CHECK: [[TMP5:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK: store ptr [[TMP0]], ptr [[TMP5]], align 8 +// CHECK: [[TMP6:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP6]], align 8 +// CHECK: [[TMP7:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK: store ptr null, ptr [[TMP7]], align 8 +// CHECK: [[TMP8:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 2 +// CHECK: store ptr @ptr, ptr [[TMP8]], align 8 +// CHECK: [[TMP9:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 2 +// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP9]], align 8 +// CHECK: [[TMP10:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 2 +// CHECK: store ptr null, ptr [[TMP10]], align 8 +// CHECK: [[TMP11:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP12:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: [[TMP13:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 // // -// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f3v_l27 +// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f3v_l29 // CHECK-SAME: (ptr noundef nonnull align 8 dereferenceable(8) [[PTR:%.*]]) #[[ATTR1]] { // CHECK: entry: // CHECK: store ptr [[PTR]], ptr [[PTR_ADDR:%.*]], align 8 @@ -161,25 +181,32 @@ void f7() { // CHECK-SAME: () #[[ATTR0]] { // CHECK: entry: // CHECK: [[TMP0:%.*]] = load ptr, ptr @ptr, align 8 -// CHECK: [[ARRAYIDX:%.*]] = getelementptr inbounds i32, ptr [[TMP0]], i64 2 -// CHECK: [[TMP1:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 -// CHECK: store ptr @ptr, ptr [[TMP1]], align 8 -// CHECK: [[TMP2:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP1:%.*]] = load ptr, ptr @ptr, align 8 +// CHECK: [[ARRAYIDX:%.*]] = getelementptr inbounds i32, ptr [[TMP1]], i64 2 +// CHECK: [[TMP2:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 // CHECK: store ptr @ptr, ptr [[TMP2]], align 8 -// CHECK: [[TMP3:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 -// CHECK: store ptr null, ptr [[TMP3]], align 8 -// CHECK: [[TMP4:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 -// CHECK: store ptr @ptr, ptr [[TMP4]], align 8 -// CHECK: [[TMP5:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 -// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP5]], align 8 -// CHECK: [[TMP6:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 -// CHECK: store ptr null, ptr [[TMP6]], align 8 -// CHECK: [[TMP7:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP8:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: [[TMP9:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 +// CHECK: [[TMP3:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: store ptr @ptr, ptr [[TMP3]], align 8 +// CHECK: [[TMP4:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 +// CHECK: store ptr null, ptr [[TMP4]], align 8 +// CHECK: [[TMP5:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK: store ptr [[TMP0]], ptr [[TMP5]], align 8 +// CHECK: [[TMP6:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP6]], align 8 +// CHECK: [[TMP7:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK: store ptr null, ptr [[TMP7]], align 8 +// CHECK: [[TMP8:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 2 +// CHECK: store ptr @ptr, ptr [[TMP8]], align 8 +// CHECK: [[TMP9:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 2 +// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP9]], align 8 +// CHECK: [[TMP10:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 2 +// CHECK: store ptr null, ptr [[TMP10]], align 8 +// CHECK: [[TMP11:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP12:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: [[TMP13:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 // // -// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f4v_l34 +// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f4v_l37 // CHECK-SAME: (ptr noundef nonnull align 8 dereferenceable(8) [[PTR:%.*]]) #[[ATTR1]] { // CHECK: entry: // CHECK: store ptr [[PTR]], ptr [[PTR_ADDR:%.*]], align 8 @@ -194,25 +221,32 @@ void f7() { // CHECK-SAME: () #[[ATTR0]] { // CHECK: entry: // CHECK: [[TMP0:%.*]] = load ptr, ptr @ptr, align 8 -// CHECK: [[ARRAYIDX:%.*]] = getelementptr inbounds i32, ptr [[TMP0]], i64 2 -// CHECK: [[TMP1:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 -// CHECK: store ptr @ptr, ptr [[TMP1]], align 8 -// CHECK: [[TMP2:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP1:%.*]] = load ptr, ptr @ptr, align 8 +// CHECK: [[ARRAYIDX:%.*]] = getelementptr inbounds i32, ptr [[TMP1]], i64 2 +// CHECK: [[TMP2:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 // CHECK: store ptr @ptr, ptr [[TMP2]], align 8 -// CHECK: [[TMP3:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 -// CHECK: store ptr null, ptr [[TMP3]], align 8 -// CHECK: [[TMP4:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 -// CHECK: store ptr @ptr, ptr [[TMP4]], align 8 -// CHECK: [[TMP5:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 -// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP5]], align 8 -// CHECK: [[TMP6:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 -// CHECK: store ptr null, ptr [[TMP6]], align 8 -// CHECK: [[TMP7:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP8:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: [[TMP9:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 +// CHECK: [[TMP3:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: store ptr @ptr, ptr [[TMP3]], align 8 +// CHECK: [[TMP4:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 +// CHECK: store ptr null, ptr [[TMP4]], align 8 +// CHECK: [[TMP5:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK: store ptr [[TMP0]], ptr [[TMP5]], align 8 +// CHECK: [[TMP6:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP6]], align 8 +// CHECK: [[TMP7:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK: store ptr null, ptr [[TMP7]], align 8 +// CHECK: [[TMP8:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 2 +// CHECK: store ptr @ptr, ptr [[TMP8]], align 8 +// CHECK: [[TMP9:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 2 +// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP9]], align 8 +// CHECK: [[TMP10:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 2 +// CHECK: store ptr null, ptr [[TMP10]], align 8 +// CHECK: [[TMP11:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP12:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: [[TMP13:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 // // -// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f5v_l41 +// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f5v_l45 // CHECK-SAME: (ptr noundef nonnull align 8 dereferenceable(8) [[PTR:%.*]]) #[[ATTR1]] { // CHECK: entry: // CHECK: store ptr [[PTR]], ptr [[PTR_ADDR:%.*]], align 8 @@ -227,22 +261,35 @@ void f7() { // CHECK-SAME: () #[[ATTR0]] { // CHECK: entry: // CHECK: [[TMP0:%.*]] = load ptr, ptr @ptr, align 8 -// CHECK: [[ARRAYIDX:%.*]] = getelementptr inbounds i32, ptr [[TMP0]], i64 2 -// CHECK: [[TMP1:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 -// CHECK: store ptr @ptr, ptr [[TMP1]], align 8 -// CHECK: [[TMP2:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 -// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP2]], align 8 -// CHECK: [[TMP3:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 -// CHECK: store ptr null, ptr [[TMP3]], align 8 -// CHECK: [[TMP4:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP5:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: call void @__tgt_target_data_begin_mapper(ptr @[[GLOB1:[0-9]+]], i64 -1, i32 1, ptr [[TMP4]], ptr [[TMP5]], ptr @.offload_sizes.9, ptr @.offload_maptypes.10, ptr null, ptr null) -// CHECK: [[TMP6:%.*]] = load ptr, ptr @ptr, align 8 -// CHECK: [[ARRAYIDX1:%.*]] = getelementptr inbounds i32, ptr [[TMP6]], i64 2 +// CHECK: [[TMP1:%.*]] = load ptr, ptr @ptr, align 8 +// CHECK: [[ARRAYIDX:%.*]] = getelementptr inbounds i32, ptr [[TMP1]], i64 2 +// CHECK: [[TMP2:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 +// CHECK: store ptr @ptr, ptr [[TMP2]], align 8 +// CHECK: [[TMP3:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: store ptr @ptr, ptr [[TMP3]], align 8 +// CHECK: [[TMP4:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 +// CHECK: store ptr null, ptr [[TMP4]], align 8 +// CHECK: [[TMP5:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK: store ptr [[TMP0]], ptr [[TMP5]], align 8 +// CHECK: [[TMP6:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP6]], align 8 +// CHECK: [[TMP7:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK: store ptr null, ptr [[TMP7]], align 8 +// CHECK: [[TMP8:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 2 +// CHECK: store ptr @ptr, ptr [[TMP8]], align 8 +// CHECK: [[TMP9:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 2 +// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP9]], align 8 +// CHECK: [[TMP10:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 2 +// CHECK: store ptr null, ptr [[TMP10]], align 8 +// CHECK: [[TMP11:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP12:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: call void @__tgt_target_data_begin_mapper(ptr @[[GLOB1:[0-9]+]], i64 -1, i32 3, ptr [[TMP11]], ptr [[TMP12]], ptr @.offload_sizes.9, ptr @.offload_maptypes.10, ptr null, ptr null) +// CHECK: [[TMP13:%.*]] = load ptr, ptr @ptr, align 8 +// CHECK: [[ARRAYIDX1:%.*]] = getelementptr inbounds i32, ptr [[TMP13]], i64 2 // CHECK: store i32 10, ptr [[ARRAYIDX1]], align 4 -// CHECK: [[TMP7:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP8:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: call void @__tgt_target_data_end_mapper(ptr @[[GLOB1]], i64 -1, i32 1, ptr [[TMP7]], ptr [[TMP8]], ptr @.offload_sizes.9, ptr @.offload_maptypes.10, ptr null, ptr null) +// CHECK: [[TMP14:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP15:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: call void @__tgt_target_data_end_mapper(ptr @[[GLOB1]], i64 -1, i32 3, ptr [[TMP14]], ptr [[TMP15]], ptr @.offload_sizes.9, ptr @.offload_maptypes.10, ptr null, ptr null) // CHECK: ret void // // @@ -250,21 +297,34 @@ void f7() { // CHECK-SAME: () #[[ATTR0]] { // CHECK: entry: // CHECK: [[TMP0:%.*]] = load ptr, ptr @ptr, align 8 -// CHECK: [[ARRAYIDX:%.*]] = getelementptr inbounds i32, ptr [[TMP0]], i64 2 -// CHECK: [[TMP1:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 -// CHECK: store ptr @ptr, ptr [[TMP1]], align 8 -// CHECK: [[TMP2:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 -// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP2]], align 8 -// CHECK: [[TMP3:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 -// CHECK: store ptr null, ptr [[TMP3]], align 8 -// CHECK: [[TMP4:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP5:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: call void @__tgt_target_data_begin_mapper(ptr @[[GLOB1]], i64 -1, i32 1, ptr [[TMP4]], ptr [[TMP5]], ptr @.offload_sizes.11, ptr @.offload_maptypes.12, ptr null, ptr null) -// CHECK: [[TMP6:%.*]] = load ptr, ptr @ptr, align 8 -// CHECK: [[ARRAYIDX1:%.*]] = getelementptr inbounds i32, ptr [[TMP6]], i64 2 +// CHECK: [[TMP1:%.*]] = load ptr, ptr @ptr, align 8 +// CHECK: [[ARRAYIDX:%.*]] = getelementptr inbounds i32, ptr [[TMP1]], i64 2 +// CHECK: [[TMP2:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 +// CHECK: store ptr [[TMP0]], ptr [[TMP2]], align 8 +// CHECK: [[TMP3:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP3]], align 8 +// CHECK: [[TMP4:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 +// CHECK: store ptr null, ptr [[TMP4]], align 8 +// CHECK: [[TMP5:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK: store ptr @ptr, ptr [[TMP5]], align 8 +// CHECK: [[TMP6:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: store ptr [[ARRAYIDX]], ptr [[TMP6]], align 8 +// CHECK: [[TMP7:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK: store ptr null, ptr [[TMP7]], align 8 +// CHECK: [[TMP8:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 2 +// CHECK: store ptr @ptr, ptr [[TMP8]], align 8 +// CHECK: [[TMP9:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 2 +// CHECK: store ptr @ptr, ptr [[TMP9]], align 8 +// CHECK: [[TMP10:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 2 +// CHECK: store ptr null, ptr [[TMP10]], align 8 +// CHECK: [[TMP11:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP12:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: call void @__tgt_target_data_begin_mapper(ptr @[[GLOB1]], i64 -1, i32 3, ptr [[TMP11]], ptr [[TMP12]], ptr @.offload_sizes.11, ptr @.offload_maptypes.12, ptr null, ptr null) +// CHECK: [[TMP13:%.*]] = load ptr, ptr @ptr, align 8 +// CHECK: [[ARRAYIDX1:%.*]] = getelementptr inbounds i32, ptr [[TMP13]], i64 2 // CHECK: store i32 11, ptr [[ARRAYIDX1]], align 4 -// CHECK: [[TMP7:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP8:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: call void @__tgt_target_data_end_mapper(ptr @[[GLOB1]], i64 -1, i32 1, ptr [[TMP7]], ptr [[TMP8]], ptr @.offload_sizes.11, ptr @.offload_maptypes.12, ptr null, ptr null) +// CHECK: [[TMP14:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP15:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: call void @__tgt_target_data_end_mapper(ptr @[[GLOB1]], i64 -1, i32 3, ptr [[TMP14]], ptr [[TMP15]], ptr @.offload_sizes.11, ptr @.offload_maptypes.12, ptr null, ptr null) // CHECK: ret void // diff --git a/clang/test/OpenMP/target_map_codegen_18.inc b/clang/test/OpenMP/target_map_codegen_18.inc index 2930521975da8..a3a716b8fc8a1 100644 --- a/clang/test/OpenMP/target_map_codegen_18.inc +++ b/clang/test/OpenMP/target_map_codegen_18.inc @@ -63,32 +63,34 @@ // CK19-NOUSE: [[MTYPE09:@.+]] = private {{.*}}constant [1 x i64] [i64 2] // CK19-LABEL: @.__omp_offloading_{{.*}}explicit_maps_single{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 -// CK19: [[SIZE10:@.+]] = private {{.*}}constant [1 x i64] [i64 240] -// CK19-USE: [[MTYPE10:@.+]] = private {{.*}}constant [1 x i64] [i64 35] -// CK19-NOUSE: [[MTYPE10:@.+]] = private {{.*}}constant [1 x i64] [i64 3] +// CK19: [[SIZE10:@.+]] = private {{.*}}constant [2 x i64] [i64 240, i64 {{4|8}}] +// CK19-USE: [[MTYPE10:@.+]] = private {{.*}}constant [2 x i64] [i64 35, i64 16384] +// CK19-NOUSE: [[MTYPE10:@.+]] = private {{.*}}constant [2 x i64] [i64 3, i64 16384] // CK19-LABEL: @.__omp_offloading_{{.*}}explicit_maps_single{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 -// CK19: [[SIZE11:@.+]] = private {{.*}}constant [1 x i64] [i64 240] -// CK19-USE: [[MTYPE11:@.+]] = private {{.*}}constant [1 x i64] [i64 32] -// CK19-NOUSE: [[MTYPE11:@.+]] = private {{.*}}constant [1 x i64] zeroinitializer +// CK19: [[SIZE11:@.+]] = private {{.*}}constant [2 x i64] [i64 240, i64 {{4|8}}] +// CK19-USE: [[MTYPE11:@.+]] = private {{.*}}constant [2 x i64] [i64 32, i64 16384] +// CK19-NOUSE: [[MTYPE11:@.+]] = private {{.*}}constant [2 x i64] [i64 0, i64 16384] // CK19-LABEL: @.__omp_offloading_{{.*}}explicit_maps_single{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 -// CK19: [[SIZE12:@.+]] = private {{.*}}constant [1 x i64] [i64 4] -// CK19-USE: [[MTYPE12:@.+]] = private {{.*}}constant [1 x i64] [i64 33] -// CK19-NOUSE: [[MTYPE12:@.+]] = private {{.*}}constant [1 x i64] [i64 1] +// CK19: [[SIZE12:@.+]] = private {{.*}}constant [2 x i64] [i64 4, i64 {{4|8}}] +// CK19-USE: [[MTYPE12:@.+]] = private {{.*}}constant [2 x i64] [i64 33, i64 16384] +// CK19-NOUSE: [[MTYPE12:@.+]] = private {{.*}}constant [2 x i64] [i64 1, i64 16384] // CK19-LABEL: @.__omp_offloading_{{.*}}explicit_maps_single{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 -// CK19-USE: [[MTYPE13:@.+]] = private {{.*}}constant [1 x i64] [i64 32] -// CK19-NOUSE: [[MTYPE13:@.+]] = private {{.*}}constant [1 x i64] zeroinitializer +// CK19: [[SIZE13:@.+]] = private {{.*}}constant [2 x i64] [i64 0, i64 {{4|8}}] +// CK19-USE: [[MTYPE13:@.+]] = private {{.*}}constant [2 x i64] [i64 32, i64 16384] +// CK19-NOUSE: [[MTYPE13:@.+]] = private {{.*}}constant [2 x i64] [i64 0, i64 16384] // CK19-LABEL: @.__omp_offloading_{{.*}}explicit_maps_single{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 -// CK19-USE: [[MTYPE14:@.+]] = private {{.*}}constant [1 x i64] [i64 33] -// CK19-NOUSE: [[MTYPE14:@.+]] = private {{.*}}constant [1 x i64] [i64 1] +// CK19: [[SIZE14:@.+]] = private {{.*}}constant [2 x i64] [i64 0, i64 {{4|8}}] +// CK19-USE: [[MTYPE14:@.+]] = private {{.*}}constant [2 x i64] [i64 33, i64 16384] +// CK19-NOUSE: [[MTYPE14:@.+]] = private {{.*}}constant [2 x i64] [i64 1, i64 16384] // CK19-LABEL: @.__omp_offloading_{{.*}}explicit_maps_single{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 -// CK19: [[SIZE15:@.+]] = private {{.*}}constant [1 x i64] [i64 4] -// CK19-USE: [[MTYPE15:@.+]] = private {{.*}}constant [1 x i64] [i64 34] -// CK19-NOUSE: [[MTYPE15:@.+]] = private {{.*}}constant [1 x i64] [i64 2] +// CK19: [[SIZE15:@.+]] = private {{.*}}constant [2 x i64] [i64 4, i64 {{4|8}}] +// CK19-USE: [[MTYPE15:@.+]] = private {{.*}}constant [2 x i64] [i64 34, i64 16384] +// CK19-NOUSE: [[MTYPE15:@.+]] = private {{.*}}constant [2 x i64] [i64 2, i64 16384] // CK19-LABEL: @.__omp_offloading_{{.*}}explicit_maps_single{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 // CK19-USE: [[SIZE16:@.+]] = private {{.*}}constant [2 x i64] [i64 {{8|4}}, i64 0] @@ -527,6 +529,10 @@ void explicit_maps_single (int ii){ } // Region 10 + + // &pa[0], &pa[20], 60 * sizeof(pa[0]), TO | FROM [| PARAM] + // &pa, &pa[20], sizeof(pa), ATTACH + // CK19-DAG: call i32 @__tgt_target_kernel(ptr @{{.+}}, i64 [[DEVICE:.+]], i32 -1, i32 0, ptr @.{{.+}}.region_id, ptr [[ARGS:%.+]]) // CK19-DAG: [[BPARG:%.+]] = getelementptr inbounds {{.+}}[[ARGS]], i32 0, i32 2 // CK19-DAG: store ptr [[BPGEP:%.+]], ptr [[BPARG]] @@ -543,6 +549,14 @@ void explicit_maps_single (int ii){ // CK19-DAG: [[SEC0]] = getelementptr {{.*}}ptr [[RVAR00:%.+]], i{{.+}} 20 // CK19-DAG: [[RVAR00]] = load ptr, ptr [[VAR0]] + // CK19-DAG: [[BP1:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 1 + // CK19-DAG: [[P1:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 1 + // CK19-DAG: store ptr [[VAR0]], ptr [[BP1]] + // CK19-DAG: store ptr [[SEC1:%.+]], ptr [[P1]] + // CK19-DAG: [[RVAR0]] = load ptr, ptr [[VAR0:%[^,]+]] + // CK19-DAG: [[SEC1]] = getelementptr {{.*}}ptr [[RVAR1:%.+]], i{{.+}} 20 + // CK19-DAG: [[RVAR1]] = load ptr, ptr [[VAR0]] + // CK19-USE: call void [[CALL10:@.+]](ptr {{[^,]+}}) // CK19-NOUSE: call void [[CALL10:@.+]]() #pragma omp target map(tofrom:pa[20:60]) @@ -553,6 +567,10 @@ void explicit_maps_single (int ii){ } // Region 11 + + // &pa[0], &pa[/*lb=*/0], 60 * sizeof(pa[0]), ALLOC [| PARAM] + // &pa, &pa[/*lb=*/0], sizeof(pa), ATTACH + // CK19-DAG: call i32 @__tgt_target_kernel(ptr @{{.+}}, i64 [[DEVICE:.+]], i32 -1, i32 0, ptr @.{{.+}}.region_id, ptr [[ARGS:%.+]]) // CK19-DAG: [[BPARG:%.+]] = getelementptr inbounds {{.+}}[[ARGS]], i32 0, i32 2 // CK19-DAG: store ptr [[BPGEP:%.+]], ptr [[BPARG]] @@ -569,6 +587,14 @@ void explicit_maps_single (int ii){ // CK19-DAG: [[SEC0]] = getelementptr {{.*}}ptr [[RVAR00:%.+]], i{{.+}} 0 // CK19-DAG: [[RVAR00]] = load ptr, ptr [[VAR0]] + // CK19-DAG: [[BP1:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 1 + // CK19-DAG: [[P1:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 1 + // CK19-DAG: store ptr [[VAR0]], ptr [[BP1]] + // CK19-DAG: store ptr [[SEC1:%.+]], ptr [[P1]] + // CK19-DAG: [[RVAR0]] = load ptr, ptr [[VAR0:%[^,]+]] + // CK19-DAG: [[SEC1]] = getelementptr {{.*}}ptr [[RVAR1:%.+]], i{{.+}} 0 + // CK19-DAG: [[RVAR1]] = load ptr, ptr [[VAR0]] + // CK19-USE: call void [[CALL11:@.+]](ptr {{[^,]+}}) // CK19-NOUSE: call void [[CALL11:@.+]]() #pragma omp target map(alloc:pa[:60]) @@ -579,6 +605,10 @@ void explicit_maps_single (int ii){ } // Region 12 + + // &pa[0], &pa[15], 1 * sizeof(pa[0]), TO [| PARAM] + // &pa, &pa[15], sizeof(pa), ATTACH + // CK19-DAG: call i32 @__tgt_target_kernel(ptr @{{.+}}, i64 [[DEVICE:.+]], i32 -1, i32 0, ptr @.{{.+}}.region_id, ptr [[ARGS:%.+]]) // CK19-DAG: [[BPARG:%.+]] = getelementptr inbounds {{.+}}[[ARGS]], i32 0, i32 2 // CK19-DAG: store ptr [[BPGEP:%.+]], ptr [[BPARG]] @@ -595,6 +625,14 @@ void explicit_maps_single (int ii){ // CK19-DAG: [[SEC0]] = getelementptr {{.*}}ptr [[RVAR00:%.+]], i{{.+}} 15 // CK19-DAG: [[RVAR00]] = load ptr, ptr [[VAR0]] + // CK19-DAG: [[BP1:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 1 + // CK19-DAG: [[P1:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 1 + // CK19-DAG: store ptr [[VAR0]], ptr [[BP1]] + // CK19-DAG: store ptr [[SEC1:%.+]], ptr [[P1]] + // CK19-DAG: [[RVAR0]] = load ptr, ptr [[VAR0:%[^,]+]] + // CK19-DAG: [[SEC1]] = getelementptr {{.*}}ptr [[RVAR1:%.+]], i{{.+}} 15 + // CK19-DAG: [[RVAR1]] = load ptr, ptr [[VAR0]] + // CK19-USE: call void [[CALL12:@.+]](ptr {{[^,]+}}) // CK19-NOUSE: call void [[CALL12:@.+]]() #pragma omp target map(to:pa[15]) @@ -605,6 +643,10 @@ void explicit_maps_single (int ii){ } // Region 13 + + // &pa[0], &pa[ii-23], ii * sizeof(pa[0]), ALLOC [| PARAM] + // &pa, &pa[ii-23], sizeof(pa), ATTACH + // CK19-DAG: call i32 @__tgt_target_kernel(ptr @{{.+}}, i64 [[DEVICE:.+]], i32 -1, i32 0, ptr @.{{.+}}.region_id, ptr [[ARGS:%.+]]) // CK19-DAG: [[BPARG:%.+]] = getelementptr inbounds {{.+}}[[ARGS]], i32 0, i32 2 // CK19-DAG: store ptr [[BPGEP:%.+]], ptr [[BPARG]] @@ -627,6 +669,14 @@ void explicit_maps_single (int ii){ // CK19-DAG: [[SEC0]] = getelementptr {{.*}}ptr [[RVAR00:%.+]], i{{.+}} %{{.*}} // CK19-DAG: [[RVAR00]] = load ptr, ptr [[VAR0]] + // CK19-DAG: [[BP1:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 1 + // CK19-DAG: [[P1:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 1 + // CK19-DAG: store ptr [[VAR0]], ptr [[BP1]] + // CK19-DAG: store ptr [[SEC1:%.+]], ptr [[P1]] + // CK19-DAG: [[RVAR0]] = load ptr, ptr [[VAR0:%[^,]+]] + // CK19-DAG: [[SEC1]] = getelementptr {{.*}}ptr [[RVAR1:%.+]], i{{.+}} %{{.*}} + // CK19-DAG: [[RVAR1]] = load ptr, ptr [[VAR0]] + // CK19-USE: call void [[CALL13:@.+]](ptr {{[^,]+}}) // CK19-NOUSE: call void [[CALL13:@.+]]() #pragma omp target map(alloc:pa[ii-23:ii]) @@ -637,6 +687,10 @@ void explicit_maps_single (int ii){ } // Region 14 + + // &pa[0], &pa[/*lb=*/0], ii * sizeof(pa[0]), ALLOC [| PARAM] + // &pa, &pa[/*lb=*/0], sizeof(pa), ATTACH + // CK19-DAG: call i32 @__tgt_target_kernel(ptr @{{.+}}, i64 [[DEVICE:.+]], i32 -1, i32 0, ptr @.{{.+}}.region_id, ptr [[ARGS:%.+]]) // CK19-DAG: [[BPARG:%.+]] = getelementptr inbounds {{.+}}[[ARGS]], i32 0, i32 2 // CK19-DAG: store ptr [[BPGEP:%.+]], ptr [[BPARG]] @@ -659,6 +713,14 @@ void explicit_maps_single (int ii){ // CK19-DAG: [[SEC0]] = getelementptr {{.*}}ptr [[RVAR00:%.+]], i{{.+}} 0 // CK19-DAG: [[RVAR00]] = load ptr, ptr [[VAR0]] + // CK19-DAG: [[BP1:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 1 + // CK19-DAG: [[P1:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 1 + // CK19-DAG: store ptr [[VAR0]], ptr [[BP1]] + // CK19-DAG: store ptr [[SEC1:%.+]], ptr [[P1]] + // CK19-DAG: [[RVAR0]] = load ptr, ptr [[VAR0:%[^,]+]] + // CK19-DAG: [[SEC1]] = getelementptr {{.*}}ptr [[RVAR1:%.+]], i{{.+}} 0 + // CK19-DAG: [[RVAR1]] = load ptr, ptr [[VAR0]] + // CK19-USE: call void [[CALL14:@.+]](ptr {{[^,]+}}) // CK19-NOUSE: call void [[CALL14:@.+]]() #pragma omp target map(to:pa[:ii]) @@ -669,6 +731,10 @@ void explicit_maps_single (int ii){ } // Region 15 + + // &pa[0], &pa[ii + 12], 1 * sizeof(pa[0]), TO [| PARAM] + // &pa, &pa[ii + 12], sizeof(pa), ATTACH + // CK19-DAG: call i32 @__tgt_target_kernel(ptr @{{.+}}, i64 [[DEVICE:.+]], i32 -1, i32 0, ptr @.{{.+}}.region_id, ptr [[ARGS:%.+]]) // CK19-DAG: [[BPARG:%.+]] = getelementptr inbounds {{.+}}[[ARGS]], i32 0, i32 2 // CK19-DAG: store ptr [[BPGEP:%.+]], ptr [[BPARG]] @@ -685,6 +751,14 @@ void explicit_maps_single (int ii){ // CK19-DAG: [[SEC0]] = getelementptr {{.*}}ptr [[RVAR00:%.+]], i{{.+}} %{{.*}} // CK19-DAG: [[RVAR00]] = load ptr, ptr [[VAR0]] + // CK19-DAG: [[BP1:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 1 + // CK19-DAG: [[P1:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 1 + // CK19-DAG: store ptr [[VAR0]], ptr [[BP1]] + // CK19-DAG: store ptr [[SEC1:%.+]], ptr [[P1]] + // CK19-DAG: [[RVAR0]] = load ptr, ptr [[VAR0:%[^,]+]] + // CK19-DAG: [[SEC1]] = getelementptr {{.*}}ptr [[RVAR1:%.+]], i{{.+}} %{{.*}} + // CK19-DAG: [[RVAR1]] = load ptr, ptr [[VAR0]] + // CK19-USE: call void [[CALL15:@.+]](ptr {{[^,]+}}) // CK19-NOUSE: call void [[CALL15:@.+]]() #pragma omp target map(from:pa[ii+12]) diff --git a/clang/test/OpenMP/target_map_codegen_19.cpp b/clang/test/OpenMP/target_map_codegen_19.cpp index 1d6c781a09905..1c4d47da93785 100644 --- a/clang/test/OpenMP/target_map_codegen_19.cpp +++ b/clang/test/OpenMP/target_map_codegen_19.cpp @@ -46,8 +46,8 @@ // CK20: [[MTYPE02:@.+]] = private {{.*}}constant [1 x i64] [i64 34] // CK20-LABEL: @.__omp_offloading_{{.*}}explicit_maps_references_and_function_args{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 -// CK20: [[SIZE03:@.+]] = private {{.*}}constant [1 x i64] [i64 12] -// CK20: [[MTYPE03:@.+]] = private {{.*}}constant [1 x i64] [i64 34] +// CK20: [[SIZE03:@.+]] = private {{.*}}constant [2 x i64] [i64 12, i64 {{4|8}}] +// CK20: [[MTYPE03:@.+]] = private {{.*}}constant [2 x i64] [i64 34, i64 16384] // CK20-LABEL: explicit_maps_references_and_function_args{{.*}}( void explicit_maps_references_and_function_args (int a, float b, int (&c)[10], float *d){ @@ -126,6 +126,10 @@ void explicit_maps_references_and_function_args (int a, float b, int (&c)[10], f } // Region 03 + +// &d[0], &d[2], 3 * sizeof(d[0]), FROM | PARAM +// &d, &d[2], sizeof(d), ATTACH + // CK20-DAG: call i32 @__tgt_target_kernel(ptr @{{.+}}, i64 -1, i32 -1, i32 0, ptr @.{{.+}}.region_id, ptr [[ARGS:%.+]]) // CK20-DAG: [[BPARG:%.+]] = getelementptr inbounds {{.+}}[[ARGS]], i32 0, i32 2 // CK20-DAG: store ptr [[BPGEP:%.+]], ptr [[BPARG]] @@ -142,6 +146,13 @@ void explicit_maps_references_and_function_args (int a, float b, int (&c)[10], f // CK20-DAG: [[SEC0]] = getelementptr {{.*}}ptr [[RVAR00:%.+]], i{{.+}} 2 // CK20-DAG: [[RVAR00]] = load ptr, ptr [[VAR0]] +// CK20-DAG: [[BP1:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 1 +// CK20-DAG: [[P1:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 1 +// CK20-DAG: store ptr [[VAR0]], ptr [[BP1]] +// CK20-DAG: store ptr [[SEC1:%.+]], ptr [[P1]] +// CK20-DAG: [[SEC1]] = getelementptr {{.*}}ptr [[RVAR1:%.+]], i{{.+}} 2 +// CK20-DAG: [[RVAR1]] = load ptr, ptr [[VAR0]] + // CK20: call void [[CALL03:@.+]](ptr {{[^,]+}}) #pragma omp target map(from \ : d [2:3]) diff --git a/clang/test/OpenMP/target_map_codegen_20.cpp b/clang/test/OpenMP/target_map_codegen_20.cpp index 7ad2019b56ba4..afaa35b79b889 100644 --- a/clang/test/OpenMP/target_map_codegen_20.cpp +++ b/clang/test/OpenMP/target_map_codegen_20.cpp @@ -69,9 +69,9 @@ // CK21-NOUSE: [[MTYPE00:@.+]] = private {{.*}}constant [1 x i64] [i64 3] // CK21-LABEL: @.__omp_offloading_{{.*}}foo{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 -// CK21: [[SIZE01:@.+]] = private {{.*}}constant [1 x i64] [i64 492] -// CK21-USE: [[MTYPE01:@.+]] = private {{.*}}constant [1 x i64] [i64 35] -// CK21-NOUSE: [[MTYPE01:@.+]] = private {{.*}}constant [1 x i64] [i64 3] +// CK21: [[SIZE01:@.+]] = private {{.*}}constant [2 x i64] [i64 492, i64 {{4|8}}] +// CK21-USE: [[MTYPE01:@.+]] = private {{.*}}constant [2 x i64] [i64 35, i64 16384] +// CK21-NOUSE: [[MTYPE01:@.+]] = private {{.*}}constant [2 x i64] [i64 3, i64 16384] // CK21-LABEL: @.__omp_offloading_{{.*}}foo{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 // CK21: [[SIZE02:@.+]] = private {{.*}}constant [2 x i64] [i64 0, i64 500] @@ -130,6 +130,10 @@ struct CC { } // Region 01 + +// &lb[0], &lb[/*lower_bound=*/0], X * sizeof(T), (TO | FROM) / (TO | FROM | PARAM) +// &lb, &lb[/*lower_bound=*/0], sizeof(T*), ATTACH + // CK21-DAG: call i32 @__tgt_target_kernel(ptr @{{.+}}, i64 -1, i32 -1, i32 0, ptr @.{{.+}}.region_id, ptr [[ARGS:%.+]]) // CK21-DAG: [[BPARG:%.+]] = getelementptr inbounds {{.+}}[[ARGS]], i32 0, i32 2 // CK21-DAG: store ptr [[BPGEP:%.+]], ptr [[BPARG]] @@ -140,11 +144,18 @@ struct CC { // CK21-DAG: [[BP0:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 0 // CK21-DAG: [[P0:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 0 -// CK21-DAG: store ptr [[RVAR0:%.+]], ptr [[BP0]] -// CK21-DAG: store ptr [[SEC0:%.+]], ptr [[P0]] -// CK21-DAG: [[RVAR0]] = load ptr, ptr [[VAR0:%[^,]+]] -// CK21-DAG: [[SEC0]] = getelementptr {{.*}}ptr [[RVAR00:%.+]], i{{.+}} 0 -// CK21-DAG: [[RVAR00]] = load ptr, ptr [[VAR0]] +// CK21-DAG: store ptr [[RLB:%.+]], ptr [[BP0]] +// CK21-DAG: store ptr [[RLB0:%.+]], ptr [[P0]] +// CK21-DAG: [[RLB]] = load ptr, ptr %lb +// CK21-DAG: [[RLB0]] = getelementptr {{.*}}ptr [[RLB_1:%.+]], i{{.+}} 0 +// CK21-DAG: [[RLB_1]] = load ptr, ptr %lb + +// CK21-DAG: [[BP1:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 1 +// CK21-DAG: [[P1:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 1 +// CK21-DAG: store ptr %lb, ptr [[BP1]] +// CK21-DAG: store ptr [[RLB0_1:%.+]], ptr [[P1]] +// CK21-DAG: [[RLB0_1]] = getelementptr {{.*}}ptr [[RLB_2:%.+]], i{{.+}} 0 +// CK21-DAG: [[RLB_2]] = load ptr, ptr %lb // CK21-USE: call void [[CALL01:@.+]](ptr {{[^,]+}}) // CK21-NOUSE: call void [[CALL01:@.+]]() diff --git a/clang/test/OpenMP/target_map_codegen_21.cpp b/clang/test/OpenMP/target_map_codegen_21.cpp index f5c517692d8c8..1307da56874b7 100644 --- a/clang/test/OpenMP/target_map_codegen_21.cpp +++ b/clang/test/OpenMP/target_map_codegen_21.cpp @@ -53,8 +53,8 @@ // CK22: [[MTYPE03:@.+]] = private {{.*}}constant [1 x i64] [i64 35] // CK22-LABEL: @.__omp_offloading_{{.*}}explicit_maps_globals{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 -// CK22: [[SIZE04:@.+]] = private {{.*}}constant [1 x i64] [i64 20] -// CK22: [[MTYPE04:@.+]] = private {{.*}}constant [1 x i64] [i64 51] +// CK22: [[SIZE04:@.+]] = private {{.*}}constant [2 x i64] [i64 20, i64 {{4|8}}] +// CK22: [[MTYPE04:@.+]] = private {{.*}}constant [2 x i64] [i64 35, i64 16384] // CK22-LABEL: @.__omp_offloading_{{.*}}explicit_maps_globals{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 // CK22: [[SIZE05:@.+]] = private {{.*}}constant [1 x i64] [i64 4] @@ -73,8 +73,8 @@ // CK22: [[MTYPE08:@.+]] = private {{.*}}constant [1 x i64] [i64 35] // CK22-LABEL: @.__omp_offloading_{{.*}}explicit_maps_globals{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 -// CK22: [[SIZE09:@.+]] = private {{.*}}constant [1 x i64] [i64 20] -// CK22: [[MTYPE09:@.+]] = private {{.*}}constant [1 x i64] [i64 51] +// CK22: [[SIZE09:@.+]] = private {{.*}}constant [2 x i64] [i64 20, i64 {{4|8}}] +// CK22: [[MTYPE09:@.+]] = private {{.*}}constant [2 x i64] [i64 35, i64 16384] // CK22-LABEL: @.__omp_offloading_{{.*}}explicit_maps_globals{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 // CK22: [[SIZE10:@.+]] = private {{.*}}constant [1 x i64] [i64 4] @@ -93,8 +93,8 @@ // CK22: [[MTYPE13:@.+]] = private {{.*}}constant [1 x i64] [i64 35] // CK22-LABEL: @.__omp_offloading_{{.*}}explicit_maps_globals{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 -// CK22: [[SIZE14:@.+]] = private {{.*}}constant [1 x i64] [i64 20] -// CK22: [[MTYPE14:@.+]] = private {{.*}}constant [1 x i64] [i64 51] +// CK22: [[SIZE14:@.+]] = private {{.*}}constant [2 x i64] [i64 20, i64 {{4|8}}] +// CK22: [[MTYPE14:@.+]] = private {{.*}}constant [2 x i64] [i64 35, i64 16384] int a; int c[100]; @@ -192,6 +192,10 @@ int explicit_maps_globals(void){ { c[3]+=1; } // Region 04 + +// &d[0], &d[2], 5 * sizeof(d[0]), TO | FROM | PARAM +// &d, &d[2], sizeof(d), ATTACH + // CK22-DAG: call i32 @__tgt_target_kernel(ptr @{{.+}}, i64 -1, i32 -1, i32 0, ptr @.{{.+}}.region_id, ptr [[ARGS:%.+]]) // CK22-DAG: [[BPARG:%.+]] = getelementptr inbounds {{.+}}[[ARGS]], i32 0, i32 2 // CK22-DAG: store ptr [[BPGEP:%.+]], ptr [[BPARG]] @@ -202,11 +206,19 @@ int explicit_maps_globals(void){ // CK22-DAG: [[BP0:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 0 // CK22-DAG: [[P0:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 0 -// CK22-DAG: store ptr @d, ptr [[BP0]] +// CK22-DAG: store ptr [[RVAR0:%.+]], ptr [[BP0]] // CK22-DAG: store ptr [[SEC0:%.+]], ptr [[P0]] +// CK22-DAG: [[RVAR0]] = load ptr, ptr @d // CK22-DAG: [[SEC0]] = getelementptr {{.*}}ptr [[RVAR00:%.+]], i{{.+}} 2 // CK22-DAG: [[RVAR00]] = load ptr, ptr @d +// CK22-DAG: [[BP1:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 1 +// CK22-DAG: [[P1:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 1 +// CK22-DAG: store ptr @d, ptr [[BP1]] +// CK22-DAG: store ptr [[SEC1:%.+]], ptr [[P1]] +// CK22-DAG: [[SEC1]] = getelementptr {{.*}}ptr [[RVAR1:%.+]], i{{.+}} 2 +// CK22-DAG: [[RVAR1]] = load ptr, ptr @d + // CK22: call void [[CALL04:@.+]](ptr {{[^,]+}}) #pragma omp target map(d [2:5]) { d[3]+=1; } @@ -284,6 +296,10 @@ int explicit_maps_globals(void){ { sc[3].fa+=1; } // Region 09 + +// &sd[0], &sd[2], 5 * sizeof(sd[0]), TO | FROM | ATTACH +// &sd, &sd[2], sizeof(sd), ATTACH + // CK22-DAG: call i32 @__tgt_target_kernel(ptr @{{.+}}, i64 -1, i32 -1, i32 0, ptr @.{{.+}}.region_id, ptr [[ARGS:%.+]]) // CK22-DAG: [[BPARG:%.+]] = getelementptr inbounds {{.+}}[[ARGS]], i32 0, i32 2 // CK22-DAG: store ptr [[BPGEP:%.+]], ptr [[BPARG]] @@ -294,11 +310,19 @@ int explicit_maps_globals(void){ // CK22-DAG: [[BP0:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 0 // CK22-DAG: [[P0:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 0 -// CK22-DAG: store ptr @sd, ptr [[BP0]] +// CK22-DAG: store ptr [[RVAR0:%.+]], ptr [[BP0]] // CK22-DAG: store ptr [[SEC0:%.+]], ptr [[P0]] +// CK22-DAG: [[RVAR0]] = load ptr, ptr @sd // CK22-DAG: [[SEC0]] = getelementptr {{.*}}ptr [[RVAR00:%.+]], i{{.+}} 2 // CK22-DAG: [[RVAR00]] = load ptr, ptr @sd +// CK22-DAG: [[BP1:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 1 +// CK22-DAG: [[P1:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 1 +// CK22-DAG: store ptr @sd, ptr [[BP1]] +// CK22-DAG: store ptr [[SEC1:%.+]], ptr [[P1]] +// CK22-DAG: [[SEC1]] = getelementptr {{.*}}ptr [[RVAR1:%.+]], i{{.+}} 2 +// CK22-DAG: [[RVAR1]] = load ptr, ptr @sd + // CK22: call void [[CALL09:@.+]](ptr {{[^,]+}}) #pragma omp target map(sd [2:5]) { sd[3].fa+=1; } @@ -376,6 +400,10 @@ int explicit_maps_globals(void){ { stc[3].fa+=1; } // Region 14 + +// &std[0], &std[2], 5 * sizeof(std[0]), TO | FROM | ATTACH +// &std, &std[2], sizeof(std), ATTACH + // CK22-DAG: call i32 @__tgt_target_kernel(ptr @{{.+}}, i64 -1, i32 -1, i32 0, ptr @.{{.+}}.region_id, ptr [[ARGS:%.+]]) // CK22-DAG: [[BPARG:%.+]] = getelementptr inbounds {{.+}}[[ARGS]], i32 0, i32 2 // CK22-DAG: store ptr [[BPGEP:%.+]], ptr [[BPARG]] @@ -386,11 +414,19 @@ int explicit_maps_globals(void){ // CK22-DAG: [[BP0:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 0 // CK22-DAG: [[P0:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 0 -// CK22-DAG: store ptr @std, ptr [[BP0]] +// CK22-DAG: store ptr [[RVAR0:%.+]], ptr [[BP0]] // CK22-DAG: store ptr [[SEC0:%.+]], ptr [[P0]] +// CK22-DAG: [[RVAR0]] = load ptr, ptr @std // CK22-DAG: [[SEC0]] = getelementptr {{.*}}ptr [[RVAR00:%.+]], i{{.+}} 2 // CK22-DAG: [[RVAR00]] = load ptr, ptr @std +// CK22-DAG: [[BP1:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 1 +// CK22-DAG: [[P1:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 1 +// CK22-DAG: store ptr @std, ptr [[BP1]] +// CK22-DAG: store ptr [[SEC1:%.+]], ptr [[P1]] +// CK22-DAG: [[SEC1]] = getelementptr {{.*}}ptr [[RVAR1:%.+]], i{{.+}} 2 +// CK22-DAG: [[RVAR1]] = load ptr, ptr @std + // CK22: call void [[CALL14:@.+]](ptr {{[^,]+}}) #pragma omp target map(std [2:5]) { std[3].fa+=1; } diff --git a/clang/test/OpenMP/target_map_codegen_22.cpp b/clang/test/OpenMP/target_map_codegen_22.cpp index 06028b23e9378..5663fb0e8bc6a 100644 --- a/clang/test/OpenMP/target_map_codegen_22.cpp +++ b/clang/test/OpenMP/target_map_codegen_22.cpp @@ -54,8 +54,8 @@ // CK23: [[MTYPE04:@.+]] = private {{.*}}constant [1 x i64] [i64 35] // CK23-LABEL: @.__omp_offloading_{{.*}}explicit_maps_inside_captured{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 -// CK23: [[SIZE05:@.+]] = private {{.*}}constant [1 x i64] [i64 16] -// CK23: [[MTYPE05:@.+]] = private {{.*}}constant [1 x i64] [i64 35] +// CK23: [[SIZE05:@.+]] = private {{.*}}constant [2 x i64] [i64 16, i64 {{4|8}}] +// CK23: [[MTYPE05:@.+]] = private {{.*}}constant [2 x i64] [i64 35, i64 16384] // CK23-LABEL: explicit_maps_inside_captured{{.*}}( int explicit_maps_inside_captured(int a){ @@ -175,6 +175,10 @@ int explicit_maps_inside_captured(int a){ { c[3]+=1; } // Region 05 + +// &d[0], &d[2], 4 * sizeof(d[0]), TO | FROM +// &d, &d[2], sizeof(d), ATTACH + // CK23-DAG: call i32 @__tgt_target_kernel(ptr @{{.+}}, i64 -1, i32 -1, i32 0, ptr @.{{.+}}.region_id, ptr [[ARGS:%.+]]) // CK23-DAG: [[BPARG:%.+]] = getelementptr inbounds {{.+}}[[ARGS]], i32 0, i32 2 // CK23-DAG: store ptr [[BPGEP:%.+]], ptr [[BPARG]] @@ -195,6 +199,16 @@ int explicit_maps_inside_captured(int a){ // CK23-DAG: [[VAR00]] = load ptr, ptr [[CAP00:%[^,]+]] // CK23-DAG: [[CAP00]] = getelementptr inbounds nuw %class.anon, +// CK23-DAG: [[BP1:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 1 +// CK23-DAG: [[P1:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 1 +// CK23-DAG: store ptr [[VAR1:%.+]], ptr [[BP1]] +// CK23-DAG: store ptr [[SEC1:%.+]], ptr [[P1]] +// CK23-DAG: [[VAR1]] = load ptr, ptr [[CAP1:%[^,]+]] +// CK23-DAG: [[CAP1]] = getelementptr inbounds nuw %class.anon, +// CK23-DAG: [[SEC1]] = getelementptr {{.*}}ptr [[RVAR1:%.+]], i{{.+}} 2 +// CK23-DAG: [[RVAR1]] = load ptr, ptr [[VAR11:%[^,]+]] +// CK23-DAG: [[VAR11]] = load ptr, ptr [[CAP11:%[^,]+]] +// CK23-DAG: [[CAP11]] = getelementptr inbounds nuw %class.anon, // CK23: call void [[CALL05:@.+]](ptr {{[^,]+}}) #pragma omp target map(d [2:4]) { d[3]+=1; } diff --git a/clang/test/OpenMP/target_map_codegen_23.cpp b/clang/test/OpenMP/target_map_codegen_23.cpp index 7e9acdafad2f8..3801af995455a 100644 --- a/clang/test/OpenMP/target_map_codegen_23.cpp +++ b/clang/test/OpenMP/target_map_codegen_23.cpp @@ -61,28 +61,28 @@ struct SC{ // CK24: [[MTYPE01:@.+]] = private {{.*}}constant [1 x i64] [i64 35] // CK24-LABEL: @.__omp_offloading_{{.*}}explicit_maps_struct_fields{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 -// CK24: [[SIZE13:@.+]] = private {{.*}}constant [1 x i64] [i64 4] -// CK24: [[MTYPE13:@.+]] = private {{.*}}constant [1 x i64] [i64 35] +// CK24: [[SIZE13:@.+]] = private {{.*}}constant [2 x i64] [i64 4, i64 {{4|8}}] +// CK24: [[MTYPE13:@.+]] = private {{.*}}constant [2 x i64] [i64 35, i64 16384] // CK24-LABEL: @.__omp_offloading_{{.*}}explicit_maps_struct_fields{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 -// CK24: [[SIZE14:@.+]] = private {{.*}}constant [1 x i64] [i64 {{48|56}}] -// CK24: [[MTYPE14:@.+]] = private {{.*}}constant [1 x i64] [i64 35] +// CK24: [[SIZE14:@.+]] = private {{.*}}constant [2 x i64] [i64 {{48|56}}, i64 {{4|8}}] +// CK24: [[MTYPE14:@.+]] = private {{.*}}constant [2 x i64] [i64 35, i64 16384] // CK24-LABEL: @.__omp_offloading_{{.*}}explicit_maps_struct_fields{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 -// CK24: [[SIZE15:@.+]] = private {{.*}}constant [1 x i64] [i64 4] -// CK24: [[MTYPE15:@.+]] = private {{.*}}constant [1 x i64] [i64 35] +// CK24: [[SIZE15:@.+]] = private {{.*}}constant [2 x i64] [i64 4, i64 {{4|8}}] +// CK24: [[MTYPE15:@.+]] = private {{.*}}constant [2 x i64] [i64 35, i64 16384] // CK24-LABEL: @.__omp_offloading_{{.*}}explicit_maps_struct_fields{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 -// CK24: [[SIZE16:@.+]] = private {{.*}}constant [2 x i64] [i64 0, i64 20] -// CK24: [[MTYPE16:@.+]] = private {{.*}}constant [2 x i64] [i64 32, i64 281474976710659] +// CK24: [[SIZE16:@.+]] = private {{.*}}constant [3 x i64] [i64 0, i64 20, i64 {{4|8}}] +// CK24: [[MTYPE16:@.+]] = private {{.*}}constant [3 x i64] [i64 32, i64 281474976710659, i64 16384] // CK24-LABEL: @.__omp_offloading_{{.*}}explicit_maps_struct_fields{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 // CK24: [[SIZE17:@.+]] = private {{.*}}constant [2 x i64] [i64 0, i64 {{3560|2880}}] // CK24: [[MTYPE17:@.+]] = private {{.*}}constant [2 x i64] [i64 32, i64 281474976710675] // CK24-LABEL: @.__omp_offloading_{{.*}}explicit_maps_struct_fields{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 -// CK24: [[SIZE18:@.+]] = private {{.*}}constant [1 x i64] [i64 4] -// CK24: [[MTYPE18:@.+]] = private {{.*}}constant [1 x i64] [i64 35] +// CK24: [[SIZE18:@.+]] = private {{.*}}constant [2 x i64] [i64 4, i64 {{4|8}}] +// CK24: [[MTYPE18:@.+]] = private {{.*}}constant [2 x i64] [i64 35, i64 16384] // CK24-LABEL: @.__omp_offloading_{{.*}}explicit_maps_struct_fields{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 // CK24: [[SIZE19:@.+]] = private {{.*}}constant [3 x i64] [i64 0, i64 {{8|4}}, i64 4] @@ -97,8 +97,8 @@ struct SC{ // CK24: [[MTYPE21:@.+]] = private {{.*}}constant [3 x i64] [i64 32, i64 281474976710659, i64 281474976710675] // CK24-LABEL: @.__omp_offloading_{{.*}}explicit_maps_struct_fields{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 -// CK24: [[SIZE22:@.+]] = private {{.*}}constant [2 x i64] [i64 0, i64 8] -// CK24: [[MTYPE22:@.+]] = private {{.*}}constant [2 x i64] [i64 32, i64 281474976710659] +// CK24: [[SIZE22:@.+]] = private {{.*}}constant [3 x i64] [i64 0, i64 8, i64 {{4|8}}] +// CK24: [[MTYPE22:@.+]] = private {{.*}}constant [3 x i64] [i64 32, i64 281474976710659, i64 16384] // CK24-LABEL: @.__omp_offloading_{{.*}}explicit_maps_struct_fields{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 // CK24: [[SIZE23:@.+]] = private {{.*}}constant [3 x i64] [i64 0, i64 {{8|4}}, i64 8] @@ -134,8 +134,12 @@ int explicit_maps_struct_fields(int a){ // // Same thing but starting from a pointer. -// + // Region 13 + +// &p[0], &p->a, sizeof(p->a), TO | FROM | PARAM +// &p, &p->a, sizeof(p), ATTACH + // CK24-DAG: call i32 @__tgt_target_kernel(ptr @{{.+}}, i64 -1, i32 -1, i32 0, ptr @.{{.+}}.region_id, ptr [[ARGS:%.+]]) // CK24-DAG: [[BPARG:%.+]] = getelementptr inbounds {{.+}}[[ARGS]], i32 0, i32 2 // CK24-DAG: store ptr [[BPGEP:%.+]], ptr [[BPARG]] @@ -150,14 +154,26 @@ int explicit_maps_struct_fields(int a){ // CK24-DAG: store ptr [[SEC0:%.+]], ptr [[P0]] // CK24-DAG: [[SEC0]] = getelementptr {{.*}}ptr [[VAR00:%.+]], i{{.+}} 0, i{{.+}} 0 -// CK24-DAG: [[VAR0]] = load ptr, ptr %{{.+}} -// CK24-DAG: [[VAR00]] = load ptr, ptr %{{.+}} +// CK24-DAG: [[BP1:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 1 +// CK24-DAG: [[P1:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 1 +// CK24-DAG: store ptr [[VAR:[^,]+]], ptr [[BP1]] +// CK24-DAG: store ptr [[SEC1:%.+]], ptr [[P1]] +// CK24-DAG: [[SEC1]] = getelementptr {{.*}}ptr [[VAR1:%.+]], i{{.+}} 0, i{{.+}} 0 + +// CK24-DAG: [[VAR0]] = load ptr, ptr [[VAR]] +// CK24-DAG: [[VAR00]] = load ptr, ptr [[VAR]] +// CK24-DAG: [[VAR1]] = load ptr, ptr [[VAR]] + // CK24: call void [[CALL13:@.+]](ptr {{[^,]+}}) #pragma omp target map(p->a) { p->a++; } // Region 14 + +// &p[0], &p->s.s, sizeof(p->s.s), TO | FROM | PARAM +// &p, &p->s.s, sizeof(p), ATTACH + // CK24-DAG: call i32 @__tgt_target_kernel(ptr @{{.+}}, i64 -1, i32 -1, i32 0, ptr @.{{.+}}.region_id, ptr [[ARGS:%.+]]) // CK24-DAG: [[BPARG:%.+]] = getelementptr inbounds {{.+}}[[ARGS]], i32 0, i32 2 // CK24-DAG: store ptr [[BPGEP:%.+]], ptr [[BPARG]] @@ -173,14 +189,25 @@ int explicit_maps_struct_fields(int a){ // CK24-DAG: [[SEC0]] = getelementptr {{.*}}ptr [[SEC00:%[^,]+]], i{{.+}} 0, i{{.+}} 1 // CK24-DAG: [[SEC00]] = getelementptr {{.*}}ptr [[VAR00:%.+]], i{{.+}} 0, i{{.+}} 1 -// CK24-DAG: [[VAR0]] = load ptr, ptr %{{.+}} -// CK24-DAG: [[VAR00]] = load ptr, ptr %{{.+}} +// CK24-DAG: [[BP1:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 1 +// CK24-DAG: [[P1:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 1 +// CK24-DAG: store ptr [[VAR:%[^,]+]], ptr [[BP1]] +// CK24-DAG: store ptr [[SEC1:%.+]], ptr [[P1]] +// CK24-DAG: [[SEC1]] = getelementptr {{.*}}ptr [[SEC11:%[^,]+]], i{{.+}} 0, i{{.+}} 1 +// CK24-DAG: [[SEC11]] = getelementptr {{.*}}ptr [[VAR1:%.+]], i{{.+}} 0, i{{.+}} 1 +// CK24-DAG: [[VAR0]] = load ptr, ptr [[VAR]] +// CK24-DAG: [[VAR00]] = load ptr, ptr [[VAR]] +// CK24-DAG: [[VAR1]] = load ptr, ptr [[VAR]] // CK24: call void [[CALL14:@.+]](ptr {{[^,]+}}) #pragma omp target map(p->s.s) { p->a++; } // Region 15 + +// &p[0], &p->s.s.a, sizeof(p->s.s.a), TO | FROM | PARAM +// &p, &p->s.s.a, sizeof(p), ATTACH + // CK24-DAG: call i32 @__tgt_target_kernel(ptr @{{.+}}, i64 -1, i32 -1, i32 0, ptr @.{{.+}}.region_id, ptr [[ARGS:%.+]]) // CK24-DAG: [[BPARG:%.+]] = getelementptr inbounds {{.+}}[[ARGS]], i32 0, i32 2 // CK24-DAG: store ptr [[BPGEP:%.+]], ptr [[BPARG]] @@ -197,14 +224,28 @@ int explicit_maps_struct_fields(int a){ // CK24-DAG: [[SEC00]] = getelementptr {{.*}}ptr [[SEC000:%[^,]+]], i{{.+}} 0, i{{.+}} 1 // CK24-DAG: [[SEC000]] = getelementptr {{.*}}ptr [[VAR00:%.+]], i{{.+}} 0, i{{.+}} 1 -// CK24-DAG: [[VAR0]] = load ptr, ptr %{{.+}} -// CK24-DAG: [[VAR00]] = load ptr, ptr %{{.+}} +// CK24-DAG: [[BP1:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 1 +// CK24-DAG: [[P1:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 1 +// CK24-DAG: store ptr [[VAR:%[^,]+]], ptr [[BP1]] +// CK24-DAG: store ptr [[SEC1:%.+]], ptr [[P1]] +// CK24-DAG: [[SEC1]] = getelementptr {{.*}}ptr [[SEC11:%[^,]+]], i{{.+}} 0, i{{.+}} 0 +// CK24-DAG: [[SEC11]] = getelementptr {{.*}}ptr [[SEC111:%[^,]+]], i{{.+}} 0, i{{.+}} 1 +// CK24-DAG: [[SEC111]] = getelementptr {{.*}}ptr [[VAR1:%.+]], i{{.+}} 0, i{{.+}} 1 + +// CK24-DAG: [[VAR0]] = load ptr, ptr [[VAR]] +// CK24-DAG: [[VAR00]] = load ptr, ptr [[VAR]] +// CK24-DAG: [[VAR1]] = load ptr, ptr [[VAR]] // CK24: call void [[CALL15:@.+]](ptr {{[^,]+}}) #pragma omp target map(p->s.s.a) { p->a++; } // Region 16 + +// &p[0], &p->b[0], sizeof(p->b[0:5]), ALLOC | PARAM +// &p[0], &p->b[0], sizeof(p->b[0:5]), TO | FROM +// &p, &p->b[0], sizeof(p), ATTACH + // CK24-DAG: call i32 @__tgt_target_kernel(ptr @{{.+}}, i64 -1, i32 -1, i32 0, ptr @.{{.+}}.region_id, ptr [[ARGS:%.+]]) // CK24-DAG: [[BPARG:%.+]] = getelementptr inbounds {{.+}}[[ARGS]], i32 0, i32 2 // CK24-DAG: store ptr [[BPGEP:%.+]], ptr [[BPARG]] @@ -230,8 +271,13 @@ int explicit_maps_struct_fields(int a){ // CK24-DAG: store ptr [[VAR0]], ptr [[BP1]] // CK24-DAG: store ptr [[SEC0]], ptr [[P1]] -// CK24-DAG: [[VAR0]] = load ptr, ptr %{{.+}} -// CK24-DAG: [[VAR00]] = load ptr, ptr %{{.+}} +// CK24-DAG: [[BP2:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 2 +// CK24-DAG: [[P2:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 2 +// CK24-DAG: store ptr [[VAR:%[^,]+]], ptr [[BP2]] +// CK24-DAG: store ptr [[SEC0]], ptr [[P2]] + +// CK24-DAG: [[VAR0]] = load ptr, ptr [[VAR]] +// CK24-DAG: [[VAR00]] = load ptr, ptr [[VAR]] // CK24: call void [[CALL16:@.+]](ptr {{[^,]+}}) #pragma omp target map(p->b[:5]) @@ -274,6 +320,10 @@ int explicit_maps_struct_fields(int a){ { p->a++; } // Region 18 + +// &p[0], &p->s.sa[3].a, sizeof(p->s.sa[3].a), TO | FROM | PARAM +// &p, &p->s.sa[3].a sizeof(p), ATTACH + // CK24-DAG: call i32 @__tgt_target_kernel(ptr @{{.+}}, i64 -1, i32 -1, i32 0, ptr @.{{.+}}.region_id, ptr [[ARGS:%.+]]) // CK24-DAG: [[BPARG:%.+]] = getelementptr inbounds {{.+}}[[ARGS]], i32 0, i32 2 // CK24-DAG: store ptr [[BPGEP:%.+]], ptr [[BPARG]] @@ -291,8 +341,18 @@ int explicit_maps_struct_fields(int a){ // CK24-DAG: [[SEC000]] = getelementptr {{.*}}ptr [[SEC0000:%[^,]+]], i{{.+}} 0, i{{.+}} 2 // CK24-DAG: [[SEC0000]] = getelementptr {{.*}}ptr [[VAR00:%.+]], i{{.+}} 0, i{{.+}} 1 -// CK24-DAG: [[VAR0]] = load ptr, ptr %{{.+}} -// CK24-DAG: [[VAR00]] = load ptr, ptr %{{.+}} +// CK24-DAG: [[BP1:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 1 +// CK24-DAG: [[P1:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 1 +// CK24-DAG: store ptr [[VAR:%[^,]+]], ptr [[BP1]] +// CK24-DAG: store ptr [[SEC1:%.+]], ptr [[P1]] +// CK24-DAG: [[SEC1]] = getelementptr {{.*}}ptr [[SEC11:%[^,]+]], i{{.+}} 0, i{{.+}} 0 +// CK24-DAG: [[SEC11]] = getelementptr {{.*}}ptr [[SEC111:%[^,]+]], i{{.+}} 0, i{{.+}} 3 +// CK24-DAG: [[SEC111]] = getelementptr {{.*}}ptr [[SEC1111:%[^,]+]], i{{.+}} 0, i{{.+}} 2 +// CK24-DAG: [[SEC1111]] = getelementptr {{.*}}ptr [[VAR11:%.+]], i{{.+}} 0, i{{.+}} 1 + +// CK24-DAG: [[VAR0]] = load ptr, ptr [[VAR]] +// CK24-DAG: [[VAR00]] = load ptr, ptr [[VAR]] +// CK24-DAG: [[VAR11]] = load ptr, ptr [[VAR]] // CK24: call void [[CALL18:@.+]](ptr {{[^,]+}}) #pragma omp target map(p->s.sa[3].a) @@ -423,6 +483,11 @@ int explicit_maps_struct_fields(int a){ { p->a++; } // Region 22 + +// &p[0], &p->s.s.b[0], sizeof(p->s.s.bb[0:2]), ALLOC | PARAM +// &p[0], &p->s.s.bb[0], sizeof(p->s.s.bb[0:2]), TO | FROM +// &p, &p->s.s.b[0], sizeof(p), ATTACH + // CK24-DAG: call i32 @__tgt_target_kernel(ptr @{{.+}}, i64 -1, i32 -1, i32 0, ptr @.{{.+}}.region_id, ptr [[ARGS:%.+]]) // CK24-DAG: [[BPARG:%.+]] = getelementptr inbounds {{.+}}[[ARGS]], i32 0, i32 2 // CK24-DAG: store ptr [[BPGEP:%.+]], ptr [[BPARG]] @@ -450,8 +515,13 @@ int explicit_maps_struct_fields(int a){ // CK24-DAG: store ptr [[VAR0]], ptr [[BP1]] // CK24-DAG: store ptr [[SEC0]], ptr [[P1]] -// CK24-DAG: [[VAR0]] = load ptr, ptr %{{.+}} -// CK24-DAG: [[VAR00]] = load ptr, ptr %{{.+}} +// CK24-DAG: [[BP2:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 2 +// CK24-DAG: [[P2:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 2 +// CK24-DAG: store ptr [[VAR:%[^,]+]], ptr [[BP2]] +// CK24-DAG: store ptr [[SEC0]], ptr [[P2]] + +// CK24-DAG: [[VAR0]] = load ptr, ptr [[VAR]] +// CK24-DAG: [[VAR00]] = load ptr, ptr [[VAR]] // CK24: call void [[CALL22:@.+]](ptr {{[^,]+}}) #pragma omp target map(p->s.s.b[:2]) diff --git a/clang/test/OpenMP/target_map_codegen_26.cpp b/clang/test/OpenMP/target_map_codegen_26.cpp index 2bc1092685ac3..832f04674b40b 100644 --- a/clang/test/OpenMP/target_map_codegen_26.cpp +++ b/clang/test/OpenMP/target_map_codegen_26.cpp @@ -38,16 +38,16 @@ // CK27: [[MTYPE00:@.+]] = private {{.*}}constant [1 x i64] [i64 544] // CK27-LABEL: @.__omp_offloading_{{.*}}zero_size_section_and_private_maps{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 -// CK27: [[SIZE01:@.+]] = private {{.*}}constant [1 x i64] zeroinitializer -// CK27: [[MTYPE01:@.+]] = private {{.*}}constant [1 x i64] [i64 35] +// CK27: [[SIZE01:@.+]] = private {{.*}}constant [2 x i64] [i64 0, i64 {{8|4}}] +// CK27: [[MTYPE01:@.+]] = private {{.*}}constant [2 x i64] [i64 35, i64 16384] // CK27-LABEL: @.__omp_offloading_{{.*}}zero_size_section_and_private_maps{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 -// CK27: [[SIZE02:@.+]] = private {{.*}}constant [1 x i64] zeroinitializer -// CK27: [[MTYPE02:@.+]] = private {{.*}}constant [1 x i64] [i64 35] +// CK27: [[SIZE02:@.+]] = private {{.*}}constant [2 x i64] [i64 0, i64 {{8|4}}] +// CK27: [[MTYPE02:@.+]] = private {{.*}}constant [2 x i64] [i64 35, i64 16384] // CK27-LABEL: @.__omp_offloading_{{.*}}zero_size_section_and_private_maps{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 -// CK27: [[SIZE03:@.+]] = private {{.*}}constant [1 x i64] zeroinitializer -// CK27: [[MTYPE03:@.+]] = private {{.*}}constant [1 x i64] [i64 35] +// CK27: [[SIZE03:@.+]] = private {{.*}}constant [2 x i64] [i64 0, i64 {{8|4}}] +// CK27: [[MTYPE03:@.+]] = private {{.*}}constant [2 x i64] [i64 35, i64 16384] // CK27-LABEL: @.__omp_offloading_{{.*}}zero_size_section_and_private_maps{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 // CK27-LABEL: @.__omp_offloading_{{.*}}zero_size_section_and_private_maps{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 @@ -71,6 +71,12 @@ void zero_size_section_and_private_maps (int ii){ int *pa; // Region 00 + +// &pa, &pa, sizeof(pa), IMPLICIT | PARAM +// +// FIXME: This looks like a bug. The implicit map on a pointer +// should be identical to pa[0:0] + // CK27-DAG: call i32 @__tgt_target_kernel(ptr @{{.+}}, i64 -1, i32 -1, i32 0, ptr @.{{.+}}.region_id, ptr [[ARGS:%.+]]) // CK27-DAG: [[BPARG:%.+]] = getelementptr inbounds {{.+}}[[ARGS]], i32 0, i32 2 // CK27-DAG: store ptr [[BPGEP:%.+]], ptr [[BPARG]] @@ -91,6 +97,13 @@ void zero_size_section_and_private_maps (int ii){ } // Region 01 + +// &(pa[0]), &pa[/*lb=*/0], /*size=*/0, TO | FROM | PARAM +// &pa, &pa[/*lb=*/0], sizeof(pa), ATTACH +// +// Can be optimized to: +// &pa[0], &pa[0], /*size=*/0, TO | FROM | PARAM + // CK27-DAG: call i32 @__tgt_target_kernel(ptr @{{.+}}, i64 -1, i32 -1, i32 0, ptr @.{{.+}}.region_id, ptr [[ARGS:%.+]]) // CK27-DAG: [[BPARG:%.+]] = getelementptr inbounds {{.+}}[[ARGS]], i32 0, i32 2 // CK27-DAG: store ptr [[BPGEP:%.+]], ptr [[BPARG]] @@ -107,6 +120,13 @@ void zero_size_section_and_private_maps (int ii){ // CK27-DAG: [[SEC0]] = getelementptr {{.*}}ptr [[RVAR00:%.+]], i{{.+}} 0 // CK27-DAG: [[RVAR00]] = load ptr, ptr [[VAR0]] +// CK27-DAG: [[BP1:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 1 +// CK27-DAG: [[P1:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 1 +// CK27-DAG: store ptr [[VAR0]], ptr [[BP1]] +// CK27-DAG: store ptr [[SEC1:%.+]], ptr [[P1]] +// CK27-DAG: [[SEC1]] = getelementptr {{.*}}ptr [[RVAR1:%.+]], i{{.+}} 0 +// CK27-DAG: [[RVAR1]] = load ptr, ptr [[VAR0]] + // CK27: call void [[CALL01:@.+]](ptr {{[^,]+}}) #pragma omp target map(pa[:0]) { @@ -114,6 +134,13 @@ void zero_size_section_and_private_maps (int ii){ } // Region 02 + +// &(pa[0]), &pa[/*lb=*/0], /*size=*/0, TO | FROM | PARAM +// &pa, &pa[/*lb=*/0], sizeof(pa), ATTACH +// +// Can be optimized to: +// &pa[0], &pa[0], /*size=*/0, TO | FROM | PARAM + // CK27-DAG: call i32 @__tgt_target_kernel(ptr @{{.+}}, i64 -1, i32 -1, i32 0, ptr @.{{.+}}.region_id, ptr [[ARGS:%.+]]) // CK27-DAG: [[BPARG:%.+]] = getelementptr inbounds {{.+}}[[ARGS]], i32 0, i32 2 // CK27-DAG: store ptr [[BPGEP:%.+]], ptr [[BPARG]] @@ -130,6 +157,13 @@ void zero_size_section_and_private_maps (int ii){ // CK27-DAG: [[SEC0]] = getelementptr {{.*}}ptr [[RVAR00:%.+]], i{{.+}} 0 // CK27-DAG: [[RVAR00]] = load ptr, ptr [[VAR0]] +// CK27-DAG: [[BP1:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 1 +// CK27-DAG: [[P1:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 1 +// CK27-DAG: store ptr [[VAR0]], ptr [[BP1]] +// CK27-DAG: store ptr [[SEC1:%.+]], ptr [[P1]] +// CK27-DAG: [[SEC1]] = getelementptr {{.*}}ptr [[RVAR1:%.+]], i{{.+}} 0 +// CK27-DAG: [[RVAR1]] = load ptr, ptr [[VAR0]] + // CK27: call void [[CALL02:@.+]](ptr {{[^,]+}}) #pragma omp target map(pa [0:0]) { @@ -137,6 +171,13 @@ void zero_size_section_and_private_maps (int ii){ } // Region 03 + +// &pa[0], &pa[ii], /*size=*/0, TO | FROM | PARAM +// &pa, &pa[ii], sizeof(pa), ATTACH +// +// Can be optimized to: +// &pa[ii], &pa[ii], /*size=*/0, TO | FROM | PARAM + // CK27-DAG: call i32 @__tgt_target_kernel(ptr @{{.+}}, i64 -1, i32 -1, i32 0, ptr @.{{.+}}.region_id, ptr [[ARGS:%.+]]) // CK27-DAG: [[BPARG:%.+]] = getelementptr inbounds {{.+}}[[ARGS]], i32 0, i32 2 // CK27-DAG: store ptr [[BPGEP:%.+]], ptr [[BPARG]] @@ -153,6 +194,13 @@ void zero_size_section_and_private_maps (int ii){ // CK27-DAG: [[SEC0]] = getelementptr {{.*}}ptr [[RVAR00:%.+]], i{{.+}} %{{.+}} // CK27-DAG: [[RVAR00]] = load ptr, ptr [[VAR0]] +// CK27-DAG: [[BP1:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 1 +// CK27-DAG: [[P1:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 1 +// CK27-DAG: store ptr [[VAR0]], ptr [[BP1]] +// CK27-DAG: store ptr [[SEC1:%.+]], ptr [[P1]] +// CK27-DAG: [[SEC1]] = getelementptr {{.*}}ptr [[RVAR1:%.+]], i{{.+}} %{{.+}} +// CK27-DAG: [[RVAR1]] = load ptr, ptr [[VAR0]] + // CK27: call void [[CALL03:@.+]](ptr {{[^,]+}}) #pragma omp target map(pa [ii:0]) { diff --git a/clang/test/OpenMP/target_map_codegen_27.cpp b/clang/test/OpenMP/target_map_codegen_27.cpp index bfe75bca481be..d0720fa6a4066 100644 --- a/clang/test/OpenMP/target_map_codegen_27.cpp +++ b/clang/test/OpenMP/target_map_codegen_27.cpp @@ -38,8 +38,8 @@ // CK28: [[MTYPE00:@.+]] = private {{.*}}constant [1 x i64] [i64 35] // CK28-LABEL: @.__omp_offloading_{{.*}}explicit_maps_pointer_references{{.*}}_l{{[0-9]+}}.region_id = weak constant i8 0 -// CK28: [[SIZE01:@.+]] = private {{.*}}constant [1 x i64] [i64 400] -// CK28: [[MTYPE01:@.+]] = private {{.*}}constant [1 x i64] [i64 35] +// CK28: [[SIZE01:@.+]] = private {{.*}}constant [2 x i64] [i64 400, i64 {{4|8}}] +// CK28: [[MTYPE01:@.+]] = private {{.*}}constant [2 x i64] [i64 35, i64 16384] // CK28-LABEL: explicit_maps_pointer_references{{.*}}( void explicit_maps_pointer_references (int *p){ @@ -68,6 +68,10 @@ void explicit_maps_pointer_references (int *p){ } // Region 01 + +// &(ref_ptee(a)[0]), &(ref_ptee(a)[2]), 100 * sizeof(int), TO | FROM | PARAM +// &(ref_ptee(a)), &(ref_ptee(a)[2]), sizeof(ref_ptee(a)), ATTACH + // CK28-DAG: call i32 @__tgt_target_kernel(ptr @{{.+}}, i64 -1, i32 -1, i32 0, ptr @.{{.+}}.region_id, ptr [[ARGS:%.+]]) // CK28-DAG: [[BPARG:%.+]] = getelementptr inbounds {{.+}}[[ARGS]], i32 0, i32 2 // CK28-DAG: store ptr [[BPGEP:%.+]], ptr [[BPARG]] @@ -78,13 +82,22 @@ void explicit_maps_pointer_references (int *p){ // CK28-DAG: [[BP0:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 0 // CK28-DAG: [[P0:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 0 -// CK28-DAG: store ptr [[VAR0:%.+]], ptr [[BP0]] -// CK28-DAG: store ptr [[VAR1:%.+]], ptr [[P0]] -// CK28-DAG: [[VAR0]] = load ptr, ptr [[VAR00:%.+]], -// CK28-DAG: [[VAR00]] = load ptr, ptr [[VAR000:%.+]], -// CK28-DAG: [[VAR1]] = getelementptr inbounds nuw i32, ptr [[VAR11:%.+]], i{{64|32}} 2 -// CK28-DAG: [[VAR11]] = load ptr, ptr [[VAR111:%.+]], -// CK28-DAG: [[VAR111]] = load ptr, ptr [[VAR1111:%.+]], +// CK28-DAG: store ptr [[RRA:%.+]], ptr [[BP0]] +// CK28-DAG: store ptr [[RRA2:%.+]], ptr [[P0]] +// CK28-DAG: [[RRA]] = load ptr, ptr [[RA:%.+]], +// CK28-DAG: [[RA]] = load ptr, ptr [[A:%.+]], +// CK28-DAG: [[RRA2]] = getelementptr inbounds nuw i32, ptr [[RRA_1:%.+]], i{{64|32}} 2 +// CK28-DAG: [[RRA_1]] = load ptr, ptr [[RA_1:%.+]], +// CK28-DAG: [[RA_1]] = load ptr, ptr [[A]] + +// CK28-DAG: [[BP1:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 1 +// CK28-DAG: [[P1:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 1 +// CK28-DAG: store ptr [[RA_2:%.+]], ptr [[BP1]] +// CK28-DAG: store ptr [[RRA2_2:%.+]], ptr [[P1]] +// CK28-DAG: [[RA_2]] = load ptr, ptr [[A]] +// CK28-DAG: [[RRA2_2]] = getelementptr inbounds nuw i32, ptr [[RRA_2:%.+]], i{{64|32}} 2 +// CK28-DAG: [[RRA_2]] = load ptr, ptr [[RA_3:%.+]], +// CK28-DAG: [[RA_3]] = load ptr, ptr [[A]] // CK28: call void [[CALL01:@.+]](ptr {{[^,]+}}) #pragma omp target map(a [2:100]) diff --git a/clang/test/OpenMP/target_map_codegen_33.cpp b/clang/test/OpenMP/target_map_codegen_33.cpp index 7d4f7fa2e7483..5ac0da6b79b70 100644 --- a/clang/test/OpenMP/target_map_codegen_33.cpp +++ b/clang/test/OpenMP/target_map_codegen_33.cpp @@ -19,11 +19,15 @@ // SIMD-ONLY32-NOT: {{__kmpc|__tgt}} #ifdef CK32 -// CK32-DAG: [[MTYPE_TO:@.+]] = {{.+}}constant [1 x i64] [i64 33] -// CK32-DAG: [[MTYPE_FROM:@.+]] = {{.+}}constant [1 x i64] [i64 34] +// CK32-DAG: [[MTYPE_TO:@.+]] = {{.+}}constant [2 x i64] [i64 33, i64 16384] +// CK32-DAG: [[MTYPE_FROM:@.+]] = {{.+}}constant [2 x i64] [i64 34, i64 16384] void array_shaping(float *f, int sa) { +// Region 01 +// &f[0], &f[0], , PARAM | TO +// &f, &f[0], sizeof(f), ATTACH +// // CK32-DAG: call i32 @__tgt_target_kernel(ptr @{{.+}}, i64 -1, i32 -1, i32 0, ptr @.{{.+}}.region_id, ptr [[ARGS:%.+]]) // CK32-DAG: [[BPARG:%.+]] = getelementptr inbounds {{.+}}[[ARGS]], i32 0, i32 2 // CK32-DAG: store ptr [[BPGEP:%.+]], ptr [[BPARG]] @@ -39,12 +43,17 @@ void array_shaping(float *f, int sa) { // CK32-DAG: [[P0:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 0 // CK32-DAG: [[S0:%.+]] = getelementptr inbounds {{.+}}[[S]], i{{.+}} 0, i{{.+}} 0 - // CK32-DAG: store ptr [[F1:%.+]], ptr [[BP0]], // CK32-DAG: store ptr [[F2:%.+]], ptr [[P0]], // CK32-DAG: store i64 [[SIZE:%.+]], ptr [[S0]], -// CK32-DAG: [[F1]] = load ptr, ptr [[F_ADDR:%.+]], +// CK32-DAG: [[BP1:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 1 +// CK32-DAG: [[P1:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 1 + +// CK32-DAG: store ptr [[F_ADDR:%.+]], ptr [[BP1]], +// CK32-DAG: store ptr [[F2]], ptr [[P1]], + +// CK32-DAG: [[F1]] = load ptr, ptr [[F_ADDR]], // CK32-DAG: [[F2]] = load ptr, ptr [[F_ADDR]], // CK32-64-DAG: [[SIZE]] = mul nuw i64 [[SZ1:%.+]], 4 // CK32-64-DAG: [[SZ1]] = mul nuw i64 12, %{{.+}} @@ -55,6 +64,11 @@ void array_shaping(float *f, int sa) { : ([3][sa][4])f) f[0] = 1; sa = 1; + +// Region 02 +// &f[0], &f[0], , PARAM | FROM +// &f, &f[0], sizeof(f), ATTACH +// // CK32-DAG: call i32 @__tgt_target_kernel(ptr @{{.+}}, i64 -1, i32 -1, i32 0, ptr @.{{.+}}.region_id, ptr [[ARGS:%.+]]) // CK32-DAG: [[BPARG:%.+]] = getelementptr inbounds {{.+}}[[ARGS]], i32 0, i32 2 // CK32-DAG: store ptr [[BPGEP:%.+]], ptr [[BPARG]] @@ -70,12 +84,17 @@ void array_shaping(float *f, int sa) { // CK32-DAG: [[P0:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 0 // CK32-DAG: [[S0:%.+]] = getelementptr inbounds {{.+}}[[S]], i{{.+}} 0, i{{.+}} 0 - // CK32-DAG: store ptr [[F1:%.+]], ptr [[BP0]], // CK32-DAG: store ptr [[F2:%.+]], ptr [[P0]], // CK32-DAG: store i64 [[SIZE:%.+]], ptr [[S0]], -// CK32-DAG: [[F1]] = load ptr, ptr [[F_ADDR:%.+]], +// CK32-DAG: [[BP1:%.+]] = getelementptr inbounds {{.+}}[[BP]], i{{.+}} 0, i{{.+}} 1 +// CK32-DAG: [[P1:%.+]] = getelementptr inbounds {{.+}}[[P]], i{{.+}} 0, i{{.+}} 1 + +// CK32-DAG: store ptr [[F_ADDR:%.+]], ptr [[BP1]], +// CK32-DAG: store ptr [[F2]], ptr [[P1]], + +// CK32-DAG: [[F1]] = load ptr, ptr [[F_ADDR]], // CK32-DAG: [[F2]] = load ptr, ptr [[F_ADDR]], // CK32-64-DAG: [[SIZE]] = mul nuw i64 [[SZ1:%.+]], 5 // CK32-64-DAG: [[SZ1]] = mul nuw i64 4, %{{.+}} diff --git a/clang/test/OpenMP/target_map_pointer_defalut_mapper_codegen.cpp b/clang/test/OpenMP/target_map_pointer_defalut_mapper_codegen.cpp index 6ab10c45beb25..db569bfa6cf44 100644 --- a/clang/test/OpenMP/target_map_pointer_defalut_mapper_codegen.cpp +++ b/clang/test/OpenMP/target_map_pointer_defalut_mapper_codegen.cpp @@ -44,7 +44,7 @@ void foo() { // CHECK-NOT: @.offload_sizes = private unnamed_addr constant [6 x i64] [i64 8, i64 0, i64 0, i64 0, i64 8, i64 4] // CHECK: @.offload_maptypes = private unnamed_addr constant [5 x i64] [i64 35, i64 16, i64 562949953421315, i64 562949953421315, i64 562949953421827] // CHECK-NOT: .offload_maptypes = private unnamed_addr constant [6 x i64] [i64 35, i64 0, i64 562949953421315, i64 562949953421315, i64 562949953421827, i64 562949953421843] -// CHECK: @.offload_sizes.1 = private unnamed_addr constant [4 x i64] [i64 0, i64 0, i64 0, i64 4] -// CHECK: @.offload_maptypes.2 = private unnamed_addr constant [4 x i64] [i64 32, i64 281474976710659, i64 281474976710659, i64 281474976711171] +// CHECK: @.offload_sizes.1 = private unnamed_addr constant [5 x i64] [i64 0, i64 0, i64 0, i64 4, i64 8] +// CHECK: @.offload_maptypes.2 = private unnamed_addr constant [5 x i64] [i64 32, i64 281474976710659, i64 281474976710659, i64 281474976711171, i64 16384] // CHECK: @.offload_sizes.3 = private unnamed_addr constant [6 x i64] [i64 8, i64 8, i64 0, i64 0, i64 0, i64 4] // CHECK: @.offload_maptypes.4 = private unnamed_addr constant [6 x i64] [i64 35, i64 16, i64 16, i64 844424930131971, i64 844424930131971, i64 844424930132483] diff --git a/clang/test/OpenMP/target_map_ptr_and_star_global.cpp b/clang/test/OpenMP/target_map_ptr_and_star_global.cpp index 40d3cd24ac08f..910c9f00d72e9 100644 --- a/clang/test/OpenMP/target_map_ptr_and_star_global.cpp +++ b/clang/test/OpenMP/target_map_ptr_and_star_global.cpp @@ -15,21 +15,24 @@ void f1() { } void f2() { - // &ptr, &ptr[0], sizeof(ptr[0]), TO | FROM | PARAM | PTR_AND_OBJ + // &ptr[0], &ptr[0], sizeof(ptr[0]), TO | FROM | PARAM + // &ptr, &ptr[0], sizeof(ptr), ATTACH #pragma omp target map(*ptr) ptr[1] = 6; } void f3() { // &ptr, &ptr, sizeof(ptr), TO | FROM | PARAM - // &ptr, &ptr[0], sizeof(ptr[0]), TO | FROM | PTR_AND_OBJ + // &ptr[0], &ptr[0], sizeof(ptr[0]), TO | FROM + // &ptr, &ptr[0], sizeof(ptr), ATTACH #pragma omp target map(ptr, *ptr) ptr[1] = 6; } void f4() { // &ptr, &ptr, sizeof(ptr), TO | FROM | PARAM - // &ptr, &ptr[0], sizeof(ptr[0]), TO | FROM | PTR_AND_OBJ + // &ptr[0], &ptr[0], sizeof(ptr[0]), TO | FROM + // &ptr, &ptr[0], sizeof(ptr), ATTACH #pragma omp target map(*ptr, ptr) ptr[2] = 8; } @@ -38,12 +41,12 @@ void f4() { //. // CHECK: @.offload_sizes = private unnamed_addr constant [1 x i64] [i64 8] // CHECK: @.offload_maptypes = private unnamed_addr constant [1 x i64] [i64 [[#0x23]]] -// CHECK: @.offload_sizes.1 = private unnamed_addr constant [1 x i64] [i64 4] -// CHECK: @.offload_maptypes.2 = private unnamed_addr constant [1 x i64] [i64 [[#0x33]]] -// CHECK: @.offload_sizes.3 = private unnamed_addr constant [2 x i64] [i64 8, i64 4] -// CHECK: @.offload_maptypes.4 = private unnamed_addr constant [2 x i64] [i64 [[#0x23]], i64 [[#0x13]]] -// CHECK: @.offload_sizes.5 = private unnamed_addr constant [2 x i64] [i64 8, i64 4] -// CHECK: @.offload_maptypes.6 = private unnamed_addr constant [2 x i64] [i64 [[#0x23]], i64 [[#0x13]]] +// CHECK: @.offload_sizes.1 = private unnamed_addr constant [2 x i64] [i64 4, i64 8] +// CHECK: @.offload_maptypes.2 = private unnamed_addr constant [2 x i64] [i64 [[#0x23]], i64 [[#0x4000]]] +// CHECK: @.offload_sizes.3 = private unnamed_addr constant [3 x i64] [i64 8, i64 4, i64 8] +// CHECK: @.offload_maptypes.4 = private unnamed_addr constant [3 x i64] [i64 [[#0x23]], i64 [[#0x3]], i64 [[#0x4000]]] +// CHECK: @.offload_sizes.5 = private unnamed_addr constant [3 x i64] [i64 8, i64 4, i64 8] +// CHECK: @.offload_maptypes.6 = private unnamed_addr constant [3 x i64] [i64 [[#0x23]], i64 [[#0x3]], i64 [[#0x4000]]] //. // CHECK-LABEL: define {{[^@]+}}@_Z2f1v // CHECK-SAME: () #[[ATTR0:[0-9]+]] { @@ -75,18 +78,25 @@ void f4() { // CHECK: entry: // CHECK: [[TMP0:%.*]] = load ptr, ptr @ptr, align 8 // CHECK: [[TMP1:%.*]] = load ptr, ptr @ptr, align 8 -// CHECK: [[TMP2:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 -// CHECK: store ptr @ptr, ptr [[TMP2]], align 8 -// CHECK: [[TMP3:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP2:%.*]] = load ptr, ptr @ptr, align 8 +// CHECK: [[TMP3:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 // CHECK: store ptr [[TMP1]], ptr [[TMP3]], align 8 -// CHECK: [[TMP4:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 -// CHECK: store ptr null, ptr [[TMP4]], align 8 -// CHECK: [[TMP5:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP6:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: [[TMP7:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 +// CHECK: [[TMP4:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: store ptr [[TMP2]], ptr [[TMP4]], align 8 +// CHECK: [[TMP5:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 +// CHECK: store ptr null, ptr [[TMP5]], align 8 +// CHECK: [[TMP6:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK: store ptr @ptr, ptr [[TMP6]], align 8 +// CHECK: [[TMP7:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: store ptr [[TMP2]], ptr [[TMP7]], align 8 +// CHECK: [[TMP8:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK: store ptr null, ptr [[TMP8]], align 8 +// CHECK: [[TMP9:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP10:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: [[TMP11:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 // // -// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f2v_l19 +// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f2v_l20 // CHECK-SAME: (ptr noundef [[PTR:%.*]]) #[[ATTR1]] { // CHECK: entry: // CHECK: store ptr [[PTR]], ptr [[PTR_ADDR:%.*]], align 8 @@ -100,24 +110,31 @@ void f4() { // CHECK-SAME: () #[[ATTR0]] { // CHECK: entry: // CHECK: [[TMP0:%.*]] = load ptr, ptr @ptr, align 8 -// CHECK: [[TMP1:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 -// CHECK: store ptr @ptr, ptr [[TMP1]], align 8 -// CHECK: [[TMP2:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP1:%.*]] = load ptr, ptr @ptr, align 8 +// CHECK: [[TMP2:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 // CHECK: store ptr @ptr, ptr [[TMP2]], align 8 -// CHECK: [[TMP3:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 -// CHECK: store ptr null, ptr [[TMP3]], align 8 -// CHECK: [[TMP4:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 -// CHECK: store ptr @ptr, ptr [[TMP4]], align 8 -// CHECK: [[TMP5:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: [[TMP3:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: store ptr @ptr, ptr [[TMP3]], align 8 +// CHECK: [[TMP4:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 +// CHECK: store ptr null, ptr [[TMP4]], align 8 +// CHECK: [[TMP5:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 // CHECK: store ptr [[TMP0]], ptr [[TMP5]], align 8 -// CHECK: [[TMP6:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 -// CHECK: store ptr null, ptr [[TMP6]], align 8 -// CHECK: [[TMP7:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP8:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: [[TMP9:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 +// CHECK: [[TMP6:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: store ptr [[TMP1]], ptr [[TMP6]], align 8 +// CHECK: [[TMP7:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK: store ptr null, ptr [[TMP7]], align 8 +// CHECK: [[TMP8:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 2 +// CHECK: store ptr @ptr, ptr [[TMP8]], align 8 +// CHECK: [[TMP9:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 2 +// CHECK: store ptr [[TMP1]], ptr [[TMP9]], align 8 +// CHECK: [[TMP10:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 2 +// CHECK: store ptr null, ptr [[TMP10]], align 8 +// CHECK: [[TMP11:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP12:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: [[TMP13:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 // // -// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f3v_l26 +// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f3v_l28 // CHECK-SAME: (ptr noundef nonnull align 8 dereferenceable(8) [[PTR:%.*]]) #[[ATTR1]] { // CHECK: entry: // CHECK: store ptr [[PTR]], ptr [[PTR_ADDR:%.*]], align 8 @@ -132,24 +149,31 @@ void f4() { // CHECK-SAME: () #[[ATTR0]] { // CHECK: entry: // CHECK: [[TMP0:%.*]] = load ptr, ptr @ptr, align 8 -// CHECK: [[TMP1:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 -// CHECK: store ptr @ptr, ptr [[TMP1]], align 8 -// CHECK: [[TMP2:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP1:%.*]] = load ptr, ptr @ptr, align 8 +// CHECK: [[TMP2:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 // CHECK: store ptr @ptr, ptr [[TMP2]], align 8 -// CHECK: [[TMP3:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 -// CHECK: store ptr null, ptr [[TMP3]], align 8 -// CHECK: [[TMP4:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 -// CHECK: store ptr @ptr, ptr [[TMP4]], align 8 -// CHECK: [[TMP5:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: [[TMP3:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: store ptr @ptr, ptr [[TMP3]], align 8 +// CHECK: [[TMP4:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 +// CHECK: store ptr null, ptr [[TMP4]], align 8 +// CHECK: [[TMP5:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 // CHECK: store ptr [[TMP0]], ptr [[TMP5]], align 8 -// CHECK: [[TMP6:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 -// CHECK: store ptr null, ptr [[TMP6]], align 8 -// CHECK: [[TMP7:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP8:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: [[TMP9:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 +// CHECK: [[TMP6:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: store ptr [[TMP1]], ptr [[TMP6]], align 8 +// CHECK: [[TMP7:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK: store ptr null, ptr [[TMP7]], align 8 +// CHECK: [[TMP8:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 2 +// CHECK: store ptr @ptr, ptr [[TMP8]], align 8 +// CHECK: [[TMP9:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 2 +// CHECK: store ptr [[TMP1]], ptr [[TMP9]], align 8 +// CHECK: [[TMP10:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 2 +// CHECK: store ptr null, ptr [[TMP10]], align 8 +// CHECK: [[TMP11:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP12:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: [[TMP13:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 // // -// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f4v_l33 +// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f4v_l36 // CHECK-SAME: (ptr noundef nonnull align 8 dereferenceable(8) [[PTR:%.*]]) #[[ATTR1]] { // CHECK: entry: // CHECK: store ptr [[PTR]], ptr [[PTR_ADDR:%.*]], align 8 diff --git a/clang/test/OpenMP/target_map_ptr_and_star_local.cpp b/clang/test/OpenMP/target_map_ptr_and_star_local.cpp index 2eff1727e0e46..c70a7c8d8adf1 100644 --- a/clang/test/OpenMP/target_map_ptr_and_star_local.cpp +++ b/clang/test/OpenMP/target_map_ptr_and_star_local.cpp @@ -17,6 +17,7 @@ void f1() { void f2() { int *ptr; // &ptr[0], &ptr[0], sizeof(ptr[0]), TO | FROM | PARAM + // &ptr, &ptr[0], sizeof(ptr), ATTACH #pragma omp target map(*ptr) ptr[1] = 6; } @@ -25,6 +26,7 @@ void f3() { int *ptr; // &ptr, &ptr, sizeof(ptr), TO | FROM | PARAM // &ptr[0], &ptr[0], sizeof(ptr[0]), TO | FROM + // &ptr, &ptr[0], sizeof(ptr), ATTACH #pragma omp target map(ptr, *ptr) ptr[1] = 6; } @@ -33,6 +35,7 @@ void f4() { int *ptr; // &ptr, &ptr, sizeof(ptr), TO | FROM | PARAM // &ptr[0], &ptr[0], sizeof(ptr[0]), TO | FROM + // &ptr, &ptr[0], sizeof(ptr), ATTACH #pragma omp target map(*ptr, ptr) ptr[2] = 8; } @@ -41,12 +44,12 @@ void f4() { //. // CHECK: @.offload_sizes = private unnamed_addr constant [1 x i64] [i64 8] // CHECK: @.offload_maptypes = private unnamed_addr constant [1 x i64] [i64 [[#0x23]]] -// CHECK: @.offload_sizes.1 = private unnamed_addr constant [1 x i64] [i64 4] -// CHECK: @.offload_maptypes.2 = private unnamed_addr constant [1 x i64] [i64 [[#0x23]]] -// CHECK: @.offload_sizes.3 = private unnamed_addr constant [2 x i64] [i64 8, i64 4] -// CHECK: @.offload_maptypes.4 = private unnamed_addr constant [2 x i64] [i64 [[#0x23]], i64 [[#0x3]]] -// CHECK: @.offload_sizes.5 = private unnamed_addr constant [2 x i64] [i64 8, i64 4] -// CHECK: @.offload_maptypes.6 = private unnamed_addr constant [2 x i64] [i64 [[#0x23]], i64 [[#0x3]]] +// CHECK: @.offload_sizes.1 = private unnamed_addr constant [2 x i64] [i64 4, i64 8] +// CHECK: @.offload_maptypes.2 = private unnamed_addr constant [2 x i64] [i64 [[#0x23]], i64 [[#0x4000]]] +// CHECK: @.offload_sizes.3 = private unnamed_addr constant [3 x i64] [i64 8, i64 4, i64 8] +// CHECK: @.offload_maptypes.4 = private unnamed_addr constant [3 x i64] [i64 [[#0x23]], i64 [[#0x3]], i64 [[#0x4000]]] +// CHECK: @.offload_sizes.5 = private unnamed_addr constant [3 x i64] [i64 8, i64 4, i64 8] +// CHECK: @.offload_maptypes.6 = private unnamed_addr constant [3 x i64] [i64 [[#0x23]], i64 [[#0x3]], i64 [[#0x4000]]] //. // CHECK-LABEL: define {{[^@]+}}@_Z2f1v // CHECK-SAME: () #[[ATTR0:[0-9]+]] { @@ -79,18 +82,24 @@ void f4() { // CHECK: [[TMP0:%.*]] = load ptr, ptr [[PTR:%.*]], align 8 // CHECK: [[TMP1:%.*]] = load ptr, ptr [[PTR]], align 8 // CHECK: [[TMP2:%.*]] = load ptr, ptr [[PTR]], align 8 -// CHECK: [[TMP3:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP3:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 // CHECK: store ptr [[TMP1]], ptr [[TMP3]], align 8 -// CHECK: [[TMP4:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP4:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 // CHECK: store ptr [[TMP2]], ptr [[TMP4]], align 8 -// CHECK: [[TMP5:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 +// CHECK: [[TMP5:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 // CHECK: store ptr null, ptr [[TMP5]], align 8 -// CHECK: [[TMP6:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP7:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: [[TMP8:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 +// CHECK: [[TMP6:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK: store ptr [[PTR]], ptr [[TMP6]], align 8 +// CHECK: [[TMP7:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: store ptr [[TMP2]], ptr [[TMP7]], align 8 +// CHECK: [[TMP8:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK: store ptr null, ptr [[TMP8]], align 8 +// CHECK: [[TMP9:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP10:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: [[TMP11:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 // // -// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f2v_l20 +// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f2v_l21 // CHECK-SAME: (ptr noundef [[PTR:%.*]]) #[[ATTR1]] { // CHECK: entry: // CHECK: store ptr [[PTR]], ptr [[PTR_ADDR:%.*]], align 8 @@ -105,24 +114,30 @@ void f4() { // CHECK: entry: // CHECK: [[TMP0:%.*]] = load ptr, ptr [[PTR:%.*]], align 8 // CHECK: [[TMP1:%.*]] = load ptr, ptr [[PTR]], align 8 -// CHECK: [[TMP2:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP2:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 // CHECK: store ptr [[PTR]], ptr [[TMP2]], align 8 -// CHECK: [[TMP3:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP3:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 // CHECK: store ptr [[PTR]], ptr [[TMP3]], align 8 -// CHECK: [[TMP4:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 +// CHECK: [[TMP4:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 // CHECK: store ptr null, ptr [[TMP4]], align 8 -// CHECK: [[TMP5:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK: [[TMP5:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 // CHECK: store ptr [[TMP0]], ptr [[TMP5]], align 8 -// CHECK: [[TMP6:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: [[TMP6:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 // CHECK: store ptr [[TMP1]], ptr [[TMP6]], align 8 -// CHECK: [[TMP7:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK: [[TMP7:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 // CHECK: store ptr null, ptr [[TMP7]], align 8 -// CHECK: [[TMP8:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP9:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: [[TMP10:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 +// CHECK: [[TMP8:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 2 +// CHECK: store ptr [[PTR]], ptr [[TMP8]], align 8 +// CHECK: [[TMP9:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 2 +// CHECK: store ptr [[TMP1]], ptr [[TMP9]], align 8 +// CHECK: [[TMP10:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 2 +// CHECK: store ptr null, ptr [[TMP10]], align 8 +// CHECK: [[TMP11:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP12:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: [[TMP13:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 // // -// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f3v_l28 +// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f3v_l30 // CHECK-SAME: (ptr noundef nonnull align 8 dereferenceable(8) [[PTR:%.*]]) #[[ATTR1]] { // CHECK: entry: // CHECK: store ptr [[PTR]], ptr [[PTR_ADDR:%.*]], align 8 @@ -138,24 +153,30 @@ void f4() { // CHECK: entry: // CHECK: [[TMP0:%.*]] = load ptr, ptr [[PTR:%.*]], align 8 // CHECK: [[TMP1:%.*]] = load ptr, ptr [[PTR]], align 8 -// CHECK: [[TMP2:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP2:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 // CHECK: store ptr [[PTR]], ptr [[TMP2]], align 8 -// CHECK: [[TMP3:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP3:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 // CHECK: store ptr [[PTR]], ptr [[TMP3]], align 8 -// CHECK: [[TMP4:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 +// CHECK: [[TMP4:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 // CHECK: store ptr null, ptr [[TMP4]], align 8 -// CHECK: [[TMP5:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK: [[TMP5:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 // CHECK: store ptr [[TMP0]], ptr [[TMP5]], align 8 -// CHECK: [[TMP6:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: [[TMP6:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 // CHECK: store ptr [[TMP1]], ptr [[TMP6]], align 8 -// CHECK: [[TMP7:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK: [[TMP7:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 // CHECK: store ptr null, ptr [[TMP7]], align 8 -// CHECK: [[TMP8:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP9:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: [[TMP10:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 +// CHECK: [[TMP8:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 2 +// CHECK: store ptr [[PTR]], ptr [[TMP8]], align 8 +// CHECK: [[TMP9:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 2 +// CHECK: store ptr [[TMP1]], ptr [[TMP9]], align 8 +// CHECK: [[TMP10:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 2 +// CHECK: store ptr null, ptr [[TMP10]], align 8 +// CHECK: [[TMP11:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP12:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: [[TMP13:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 // // -// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f4v_l36 +// CHECK-LABEL: define {{[^@]+}}@{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f4v_l39 // CHECK-SAME: (ptr noundef nonnull align 8 dereferenceable(8) [[PTR:%.*]]) #[[ATTR1]] { // CHECK: entry: // CHECK: store ptr [[PTR]], ptr [[PTR_ADDR:%.*]], align 8 diff --git a/clang/test/OpenMP/target_map_structptr_and_member_global.cpp b/clang/test/OpenMP/target_map_structptr_and_member_global.cpp index dc2df3849f299..4c15b0259aeeb 100644 --- a/clang/test/OpenMP/target_map_structptr_and_member_global.cpp +++ b/clang/test/OpenMP/target_map_structptr_and_member_global.cpp @@ -23,6 +23,7 @@ void f1() { void f2() { // &ps[0], &ps->y, sizeof(ps->y), TO | PARAM + // &ps, &ps->y, sizeof(ps), ATTACH #pragma omp target map(to: ps->y) ps->y = 6; } @@ -30,6 +31,7 @@ void f2() { void f3() { // &ps, &ps, sizeof(ps), TO | PARAM // &ps[0], &ps->y, sizeof(ps->y), TO + // &ps, &ps->y, sizeof(ps), ATTACH #pragma omp target map(to: ps, ps->y) ps->y = 7; } @@ -37,6 +39,7 @@ void f3() { void f4() { // &ps, &ps, sizeof(ps), TO | PARAM // &ps[0], &ps->y, sizeof(ps->y), TO + // &ps, &ps->y, sizeof(ps), ATTACH #pragma omp target map(to: ps->y, ps) ps->y = 8; } @@ -46,6 +49,7 @@ void f5() { // &ps[0], &ps[0].x, ((&ps[0].y + 1) - &ps[0].x)/8, ALLOC // &ps[0], &ps->y, sizeof(ps->y), TO | MEMBER_OF(2) // &ps[0], &ps->x, sizeof(ps->x), TO | MEMBER_OF(2) + // &ps, &ps[0].x, sizeof(ps), ATTACH #pragma omp target map(to: ps->y, ps, ps->x) ps->y = 9; } @@ -54,14 +58,14 @@ void f5() { //. // CHECK: @.offload_sizes = private unnamed_addr constant [1 x i64] [i64 8] // CHECK: @.offload_maptypes = private unnamed_addr constant [1 x i64] [i64 [[#0x21]]] -// CHECK: @.offload_sizes.1 = private unnamed_addr constant [1 x i64] [i64 4] -// CHECK: @.offload_maptypes.2 = private unnamed_addr constant [1 x i64] [i64 [[#0x21]]] -// CHECK: @.offload_sizes.3 = private unnamed_addr constant [2 x i64] [i64 8, i64 4] -// CHECK: @.offload_maptypes.4 = private unnamed_addr constant [2 x i64] [i64 [[#0x21]], i64 [[#0x1]]] -// CHECK: @.offload_sizes.5 = private unnamed_addr constant [2 x i64] [i64 8, i64 4] -// CHECK: @.offload_maptypes.6 = private unnamed_addr constant [2 x i64] [i64 [[#0x21]], i64 [[#0x1]]] -// CHECK: @.offload_sizes.7 = private unnamed_addr constant [4 x i64] [i64 8, i64 0, i64 4, i64 2] -// CHECK: @.offload_maptypes.8 = private unnamed_addr constant [4 x i64] [i64 [[#0x21]], i64 [[#0x0]], i64 [[#0x2000000000001]], i64 [[#0x2000000000001]]] +// CHECK: @.offload_sizes.1 = private unnamed_addr constant [2 x i64] [i64 4, i64 8] +// CHECK: @.offload_maptypes.2 = private unnamed_addr constant [2 x i64] [i64 [[#0x21]], i64 [[#0x4000]]] +// CHECK: @.offload_sizes.3 = private unnamed_addr constant [3 x i64] [i64 8, i64 4, i64 8] +// CHECK: @.offload_maptypes.4 = private unnamed_addr constant [3 x i64] [i64 [[#0x21]], i64 [[#0x1]], i64 [[#0x4000]]] +// CHECK: @.offload_sizes.5 = private unnamed_addr constant [3 x i64] [i64 8, i64 4, i64 8] +// CHECK: @.offload_maptypes.6 = private unnamed_addr constant [3 x i64] [i64 [[#0x21]], i64 [[#0x1]], i64 [[#0x4000]]] +// CHECK: @.offload_sizes.7 = private unnamed_addr constant [5 x i64] [i64 8, i64 0, i64 4, i64 2, i64 8] +// CHECK: @.offload_maptypes.8 = private unnamed_addr constant [5 x i64] [i64 [[#0x21]], i64 [[#0x0]], i64 [[#0x2000000000001]], i64 [[#0x2000000000001]], i64 [[#0x4000]]] //. // CHECK-LABEL: define dso_local void @_Z2f1v( // CHECK-SAME: ) #[[ATTR0:[0-9]+]] { @@ -95,18 +99,24 @@ void f5() { // CHECK: [[TMP1:%.*]] = load ptr, ptr @ps, align 8 // CHECK: [[TMP2:%.*]] = load ptr, ptr @ps, align 8 // CHECK: [[Y:%.*]] = getelementptr inbounds nuw [[STRUCT_S:%.*]], ptr [[TMP2]], i32 0, i32 1 -// CHECK: [[TMP3:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP3:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 // CHECK: store ptr [[TMP1]], ptr [[TMP3]], align 8 -// CHECK: [[TMP4:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP4:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 // CHECK: store ptr [[Y]], ptr [[TMP4]], align 8 -// CHECK: [[TMP5:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 +// CHECK: [[TMP5:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 // CHECK: store ptr null, ptr [[TMP5]], align 8 -// CHECK: [[TMP6:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP7:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: [[TMP8:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 +// CHECK: [[TMP6:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK: store ptr @ps, ptr [[TMP6]], align 8 +// CHECK: [[TMP7:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: store ptr [[Y]], ptr [[TMP7]], align 8 +// CHECK: [[TMP8:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK: store ptr null, ptr [[TMP8]], align 8 +// CHECK: [[TMP9:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP10:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: [[TMP11:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 // // -// CHECK-LABEL: define internal void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f2v_l26( +// CHECK-LABEL: define internal void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f2v_l27( // CHECK-SAME: ptr noundef [[PS:%.*]]) #[[ATTR1]] { // CHECK: [[ENTRY:.*:]] // CHECK: store ptr [[PS]], ptr [[PS_ADDR:%.*]], align 8 @@ -122,24 +132,30 @@ void f5() { // CHECK: [[TMP0:%.*]] = load ptr, ptr @ps, align 8 // CHECK: [[TMP1:%.*]] = load ptr, ptr @ps, align 8 // CHECK: [[Y:%.*]] = getelementptr inbounds nuw [[STRUCT_S:%.*]], ptr [[TMP1]], i32 0, i32 1 -// CHECK: [[TMP2:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP2:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 // CHECK: store ptr @ps, ptr [[TMP2]], align 8 -// CHECK: [[TMP3:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP3:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 // CHECK: store ptr @ps, ptr [[TMP3]], align 8 -// CHECK: [[TMP4:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 +// CHECK: [[TMP4:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 // CHECK: store ptr null, ptr [[TMP4]], align 8 -// CHECK: [[TMP5:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK: [[TMP5:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 // CHECK: store ptr [[TMP0]], ptr [[TMP5]], align 8 -// CHECK: [[TMP6:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: [[TMP6:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 // CHECK: store ptr [[Y]], ptr [[TMP6]], align 8 -// CHECK: [[TMP7:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK: [[TMP7:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 // CHECK: store ptr null, ptr [[TMP7]], align 8 -// CHECK: [[TMP8:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP9:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: [[TMP10:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 +// CHECK: [[TMP8:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 2 +// CHECK: store ptr @ps, ptr [[TMP8]], align 8 +// CHECK: [[TMP9:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 2 +// CHECK: store ptr [[Y]], ptr [[TMP9]], align 8 +// CHECK: [[TMP10:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 2 +// CHECK: store ptr null, ptr [[TMP10]], align 8 +// CHECK: [[TMP11:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP12:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: [[TMP13:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 // // -// CHECK-LABEL: define internal void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f3v_l33( +// CHECK-LABEL: define internal void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f3v_l35( // CHECK-SAME: ptr noundef nonnull align 8 dereferenceable(8) [[PS:%.*]]) #[[ATTR1]] { // CHECK: [[ENTRY:.*:]] // CHECK: store ptr [[PS]], ptr [[PS_ADDR:%.*]], align 8 @@ -156,24 +172,30 @@ void f5() { // CHECK: [[TMP0:%.*]] = load ptr, ptr @ps, align 8 // CHECK: [[TMP1:%.*]] = load ptr, ptr @ps, align 8 // CHECK: [[Y:%.*]] = getelementptr inbounds nuw [[STRUCT_S:%.*]], ptr [[TMP1]], i32 0, i32 1 -// CHECK: [[TMP2:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP2:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 // CHECK: store ptr @ps, ptr [[TMP2]], align 8 -// CHECK: [[TMP3:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP3:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 // CHECK: store ptr @ps, ptr [[TMP3]], align 8 -// CHECK: [[TMP4:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 +// CHECK: [[TMP4:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 // CHECK: store ptr null, ptr [[TMP4]], align 8 -// CHECK: [[TMP5:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK: [[TMP5:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 // CHECK: store ptr [[TMP0]], ptr [[TMP5]], align 8 -// CHECK: [[TMP6:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: [[TMP6:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 // CHECK: store ptr [[Y]], ptr [[TMP6]], align 8 -// CHECK: [[TMP7:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK: [[TMP7:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 // CHECK: store ptr null, ptr [[TMP7]], align 8 -// CHECK: [[TMP8:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP9:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: [[TMP10:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 +// CHECK: [[TMP8:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 2 +// CHECK: store ptr @ps, ptr [[TMP8]], align 8 +// CHECK: [[TMP9:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 2 +// CHECK: store ptr [[Y]], ptr [[TMP9]], align 8 +// CHECK: [[TMP10:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 2 +// CHECK: store ptr null, ptr [[TMP10]], align 8 +// CHECK: [[TMP11:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP12:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: [[TMP13:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 // // -// CHECK-LABEL: define internal void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f4v_l40( +// CHECK-LABEL: define internal void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f4v_l43( // CHECK-SAME: ptr noundef nonnull align 8 dereferenceable(8) [[PS:%.*]]) #[[ATTR1]] { // CHECK: [[ENTRY:.*:]] // CHECK: store ptr [[PS]], ptr [[PS_ADDR:%.*]], align 8 @@ -198,40 +220,46 @@ void f5() { // CHECK: [[TMP6:%.*]] = ptrtoint ptr [[X]] to i64 // CHECK: [[TMP7:%.*]] = sub i64 [[TMP5]], [[TMP6]] // CHECK: [[TMP8:%.*]] = sdiv exact i64 [[TMP7]], ptrtoint (ptr getelementptr (i8, ptr null, i32 1) to i64) -// CHECK: call void @llvm.memcpy.p0.p0.i64(ptr align 8 [[DOTOFFLOAD_SIZES:%.*]], ptr align 8 @.offload_sizes.7, i64 32, i1 false) -// CHECK: [[TMP9:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 +// CHECK: call void @llvm.memcpy.p0.p0.i64(ptr align 8 [[DOTOFFLOAD_SIZES:%.*]], ptr align 8 @.offload_sizes.7, i64 40, i1 false) +// CHECK: [[TMP9:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 // CHECK: store ptr @ps, ptr [[TMP9]], align 8 -// CHECK: [[TMP10:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP10:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 // CHECK: store ptr @ps, ptr [[TMP10]], align 8 -// CHECK: [[TMP11:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 +// CHECK: [[TMP11:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 // CHECK: store ptr null, ptr [[TMP11]], align 8 -// CHECK: [[TMP12:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK: [[TMP12:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 // CHECK: store ptr [[TMP0]], ptr [[TMP12]], align 8 -// CHECK: [[TMP13:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: [[TMP13:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 // CHECK: store ptr [[X]], ptr [[TMP13]], align 8 -// CHECK: [[TMP14:%.*]] = getelementptr inbounds [4 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 1 +// CHECK: [[TMP14:%.*]] = getelementptr inbounds [5 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 1 // CHECK: store i64 [[TMP8]], ptr [[TMP14]], align 8 -// CHECK: [[TMP15:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK: [[TMP15:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 // CHECK: store ptr null, ptr [[TMP15]], align 8 -// CHECK: [[TMP16:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 2 +// CHECK: [[TMP16:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 2 // CHECK: store ptr [[TMP0]], ptr [[TMP16]], align 8 -// CHECK: [[TMP17:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 2 +// CHECK: [[TMP17:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 2 // CHECK: store ptr [[Y]], ptr [[TMP17]], align 8 -// CHECK: [[TMP18:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 2 +// CHECK: [[TMP18:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 2 // CHECK: store ptr null, ptr [[TMP18]], align 8 -// CHECK: [[TMP19:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 3 +// CHECK: [[TMP19:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 3 // CHECK: store ptr [[TMP2]], ptr [[TMP19]], align 8 -// CHECK: [[TMP20:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 3 +// CHECK: [[TMP20:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 3 // CHECK: store ptr [[X]], ptr [[TMP20]], align 8 -// CHECK: [[TMP21:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 3 +// CHECK: [[TMP21:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 3 // CHECK: store ptr null, ptr [[TMP21]], align 8 -// CHECK: [[TMP22:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP23:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: [[TMP24:%.*]] = getelementptr inbounds [4 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 0 -// CHECK: [[TMP25:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 +// CHECK: [[TMP22:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 4 +// CHECK: store ptr @ps, ptr [[TMP22]], align 8 +// CHECK: [[TMP23:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 4 +// CHECK: store ptr [[X]], ptr [[TMP23]], align 8 +// CHECK: [[TMP24:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 4 +// CHECK: store ptr null, ptr [[TMP24]], align 8 +// CHECK: [[TMP25:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP26:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: [[TMP27:%.*]] = getelementptr inbounds [5 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 0 +// CHECK: [[TMP28:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 // // -// CHECK-LABEL: define internal void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f5v_l49( +// CHECK-LABEL: define internal void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f5v_l53( // CHECK-SAME: ptr noundef nonnull align 8 dereferenceable(8) [[PS:%.*]]) #[[ATTR1]] { // CHECK: [[ENTRY:.*:]] // CHECK: store ptr [[PS]], ptr [[PS_ADDR:%.*]], align 8 diff --git a/clang/test/OpenMP/target_map_structptr_and_member_local.cpp b/clang/test/OpenMP/target_map_structptr_and_member_local.cpp index 44a982680bb8b..1adc069f407c0 100644 --- a/clang/test/OpenMP/target_map_structptr_and_member_local.cpp +++ b/clang/test/OpenMP/target_map_structptr_and_member_local.cpp @@ -23,6 +23,7 @@ void f1() { void f2() { S s, *ps; // &ps[0], &ps->y, sizeof(ps->y), TO | PARAM + // &ps, &ps->y, sizeof(ps), ATTACH #pragma omp target map(to: ps->y) ps->y = 6; } @@ -31,6 +32,7 @@ void f3() { S s, *ps; // &ps, &ps, sizeof(ps), TO | PARAM // &ps[0], &ps->y, sizeof(ps->y), TO + // &ps, &ps->y, sizeof(ps), ATTACH #pragma omp target map(to: ps, ps->y) ps->y = 7; } @@ -39,6 +41,7 @@ void f4() { S s, *ps; // &ps, &ps, sizeof(ps), TO | PARAM // &ps[0], &ps->y, sizeof(ps->y), TO + // &ps, &ps->y, sizeof(ps), ATTACH #pragma omp target map(to: ps->y, ps) ps->y = 8; } @@ -49,6 +52,7 @@ void f5() { // &ps[0], &ps[0].x, ((&ps[0].y + 1) - &ps[0].x)/8, ALLOC // &ps[0], &ps->y, sizeof(ps->y), TO | MEMBER_OF(2) // &ps[0], &ps->x, sizeof(ps->x), TO | MEMBER_OF(2) + // &ps, &ps[0].x, sizeof(ps), ATTACH #pragma omp target map(to: ps->y, ps, ps->x) ps->y = 9; } @@ -57,14 +61,14 @@ void f5() { //. // CHECK: @.offload_sizes = private unnamed_addr constant [1 x i64] [i64 8] // CHECK: @.offload_maptypes = private unnamed_addr constant [1 x i64] [i64 [[#0x21]]] -// CHECK: @.offload_sizes.1 = private unnamed_addr constant [1 x i64] [i64 4] -// CHECK: @.offload_maptypes.2 = private unnamed_addr constant [1 x i64] [i64 [[#0x21]]] -// CHECK: @.offload_sizes.3 = private unnamed_addr constant [2 x i64] [i64 8, i64 4] -// CHECK: @.offload_maptypes.4 = private unnamed_addr constant [2 x i64] [i64 [[#0x21]], i64 [[#0x1]]] -// CHECK: @.offload_sizes.5 = private unnamed_addr constant [2 x i64] [i64 8, i64 4] -// CHECK: @.offload_maptypes.6 = private unnamed_addr constant [2 x i64] [i64 [[#0x21]], i64 [[#0x1]]] -// CHECK: @.offload_sizes.7 = private unnamed_addr constant [4 x i64] [i64 8, i64 0, i64 4, i64 2] -// CHECK: @.offload_maptypes.8 = private unnamed_addr constant [4 x i64] [i64 [[#0x21]], i64 [[#0x0]], i64 [[#0x2000000000001]], i64 [[#0x2000000000001]]] +// CHECK: @.offload_sizes.1 = private unnamed_addr constant [2 x i64] [i64 4, i64 8] +// CHECK: @.offload_maptypes.2 = private unnamed_addr constant [2 x i64] [i64 [[#0x21]], i64 [[#0x4000]]] +// CHECK: @.offload_sizes.3 = private unnamed_addr constant [3 x i64] [i64 8, i64 4, i64 8] +// CHECK: @.offload_maptypes.4 = private unnamed_addr constant [3 x i64] [i64 [[#0x21]], i64 [[#0x1]], i64 [[#0x4000]]] +// CHECK: @.offload_sizes.5 = private unnamed_addr constant [3 x i64] [i64 8, i64 4, i64 8] +// CHECK: @.offload_maptypes.6 = private unnamed_addr constant [3 x i64] [i64 [[#0x21]], i64 [[#0x1]], i64 [[#0x4000]]] +// CHECK: @.offload_sizes.7 = private unnamed_addr constant [5 x i64] [i64 8, i64 0, i64 4, i64 2, i64 8] +// CHECK: @.offload_maptypes.8 = private unnamed_addr constant [5 x i64] [i64 [[#0x21]], i64 [[#0x0]], i64 [[#0x2000000000001]], i64 [[#0x2000000000001]], i64 [[#0x4000]]] //. // CHECK-LABEL: define dso_local void @_Z2f1v( // CHECK-SAME: ) #[[ATTR0:[0-9]+]] { @@ -98,18 +102,24 @@ void f5() { // CHECK: [[TMP1:%.*]] = load ptr, ptr [[PS]], align 8 // CHECK: [[TMP2:%.*]] = load ptr, ptr [[PS]], align 8 // CHECK: [[Y:%.*]] = getelementptr inbounds nuw [[STRUCT_S:%.*]], ptr [[TMP2]], i32 0, i32 1 -// CHECK: [[TMP3:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP3:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 // CHECK: store ptr [[TMP1]], ptr [[TMP3]], align 8 -// CHECK: [[TMP4:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP4:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 // CHECK: store ptr [[Y]], ptr [[TMP4]], align 8 -// CHECK: [[TMP5:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 +// CHECK: [[TMP5:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 // CHECK: store ptr null, ptr [[TMP5]], align 8 -// CHECK: [[TMP6:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP7:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: [[TMP8:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 +// CHECK: [[TMP6:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK: store ptr [[PS]], ptr [[TMP6]], align 8 +// CHECK: [[TMP7:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: store ptr [[Y]], ptr [[TMP7]], align 8 +// CHECK: [[TMP8:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK: store ptr null, ptr [[TMP8]], align 8 +// CHECK: [[TMP9:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP10:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: [[TMP11:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 // // -// CHECK-LABEL: define internal void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f2v_l26( +// CHECK-LABEL: define internal void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f2v_l27( // CHECK-SAME: ptr noundef [[PS:%.*]]) #[[ATTR1]] { // CHECK: [[ENTRY:.*:]] // CHECK: store ptr [[PS]], ptr [[PS_ADDR:%.*]], align 8 @@ -125,24 +135,30 @@ void f5() { // CHECK: [[TMP0:%.*]] = load ptr, ptr [[PS:%.*]], align 8 // CHECK: [[TMP1:%.*]] = load ptr, ptr [[PS]], align 8 // CHECK: [[Y:%.*]] = getelementptr inbounds nuw [[STRUCT_S:%.*]], ptr [[TMP1]], i32 0, i32 1 -// CHECK: [[TMP2:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP2:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 // CHECK: store ptr [[PS]], ptr [[TMP2]], align 8 -// CHECK: [[TMP3:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP3:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 // CHECK: store ptr [[PS]], ptr [[TMP3]], align 8 -// CHECK: [[TMP4:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 +// CHECK: [[TMP4:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 // CHECK: store ptr null, ptr [[TMP4]], align 8 -// CHECK: [[TMP5:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK: [[TMP5:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 // CHECK: store ptr [[TMP0]], ptr [[TMP5]], align 8 -// CHECK: [[TMP6:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: [[TMP6:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 // CHECK: store ptr [[Y]], ptr [[TMP6]], align 8 -// CHECK: [[TMP7:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK: [[TMP7:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 // CHECK: store ptr null, ptr [[TMP7]], align 8 -// CHECK: [[TMP8:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP9:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: [[TMP10:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 +// CHECK: [[TMP8:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 2 +// CHECK: store ptr [[PS]], ptr [[TMP8]], align 8 +// CHECK: [[TMP9:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 2 +// CHECK: store ptr [[Y]], ptr [[TMP9]], align 8 +// CHECK: [[TMP10:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 2 +// CHECK: store ptr null, ptr [[TMP10]], align 8 +// CHECK: [[TMP11:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP12:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: [[TMP13:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 // // -// CHECK-LABEL: define internal void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f3v_l34( +// CHECK-LABEL: define internal void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f3v_l36( // CHECK-SAME: ptr noundef nonnull align 8 dereferenceable(8) [[PS:%.*]]) #[[ATTR1]] { // CHECK: [[ENTRY:.*:]] // CHECK: store ptr [[PS]], ptr [[PS_ADDR:%.*]], align 8 @@ -159,24 +175,30 @@ void f5() { // CHECK: [[TMP0:%.*]] = load ptr, ptr [[PS:%.*]], align 8 // CHECK: [[TMP1:%.*]] = load ptr, ptr [[PS]], align 8 // CHECK: [[Y:%.*]] = getelementptr inbounds nuw [[STRUCT_S:%.*]], ptr [[TMP1]], i32 0, i32 1 -// CHECK: [[TMP2:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP2:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 // CHECK: store ptr [[PS]], ptr [[TMP2]], align 8 -// CHECK: [[TMP3:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP3:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 // CHECK: store ptr [[PS]], ptr [[TMP3]], align 8 -// CHECK: [[TMP4:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 +// CHECK: [[TMP4:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 // CHECK: store ptr null, ptr [[TMP4]], align 8 -// CHECK: [[TMP5:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK: [[TMP5:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 // CHECK: store ptr [[TMP0]], ptr [[TMP5]], align 8 -// CHECK: [[TMP6:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: [[TMP6:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 // CHECK: store ptr [[Y]], ptr [[TMP6]], align 8 -// CHECK: [[TMP7:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK: [[TMP7:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 // CHECK: store ptr null, ptr [[TMP7]], align 8 -// CHECK: [[TMP8:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP9:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: [[TMP10:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 +// CHECK: [[TMP8:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 2 +// CHECK: store ptr [[PS]], ptr [[TMP8]], align 8 +// CHECK: [[TMP9:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 2 +// CHECK: store ptr [[Y]], ptr [[TMP9]], align 8 +// CHECK: [[TMP10:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 2 +// CHECK: store ptr null, ptr [[TMP10]], align 8 +// CHECK: [[TMP11:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP12:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: [[TMP13:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 // // -// CHECK-LABEL: define internal void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f4v_l42( +// CHECK-LABEL: define internal void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f4v_l45( // CHECK-SAME: ptr noundef nonnull align 8 dereferenceable(8) [[PS:%.*]]) #[[ATTR1]] { // CHECK: [[ENTRY:.*:]] // CHECK: store ptr [[PS]], ptr [[PS_ADDR:%.*]], align 8 @@ -201,40 +223,46 @@ void f5() { // CHECK: [[TMP6:%.*]] = ptrtoint ptr [[X]] to i64 // CHECK: [[TMP7:%.*]] = sub i64 [[TMP5]], [[TMP6]] // CHECK: [[TMP8:%.*]] = sdiv exact i64 [[TMP7]], ptrtoint (ptr getelementptr (i8, ptr null, i32 1) to i64) -// CHECK: call void @llvm.memcpy.p0.p0.i64(ptr align 8 [[DOTOFFLOAD_SIZES:%.*]], ptr align 8 @.offload_sizes.7, i64 32, i1 false) -// CHECK: [[TMP9:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 +// CHECK: call void @llvm.memcpy.p0.p0.i64(ptr align 8 [[DOTOFFLOAD_SIZES:%.*]], ptr align 8 @.offload_sizes.7, i64 40, i1 false) +// CHECK: [[TMP9:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS:%.*]], i32 0, i32 0 // CHECK: store ptr [[PS]], ptr [[TMP9]], align 8 -// CHECK: [[TMP10:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 +// CHECK: [[TMP10:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS:%.*]], i32 0, i32 0 // CHECK: store ptr [[PS]], ptr [[TMP10]], align 8 -// CHECK: [[TMP11:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 +// CHECK: [[TMP11:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS:%.*]], i64 0, i64 0 // CHECK: store ptr null, ptr [[TMP11]], align 8 -// CHECK: [[TMP12:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK: [[TMP12:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 // CHECK: store ptr [[TMP0]], ptr [[TMP12]], align 8 -// CHECK: [[TMP13:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK: [[TMP13:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 // CHECK: store ptr [[X]], ptr [[TMP13]], align 8 -// CHECK: [[TMP14:%.*]] = getelementptr inbounds [4 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 1 +// CHECK: [[TMP14:%.*]] = getelementptr inbounds [5 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 1 // CHECK: store i64 [[TMP8]], ptr [[TMP14]], align 8 -// CHECK: [[TMP15:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK: [[TMP15:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 // CHECK: store ptr null, ptr [[TMP15]], align 8 -// CHECK: [[TMP16:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 2 +// CHECK: [[TMP16:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 2 // CHECK: store ptr [[TMP0]], ptr [[TMP16]], align 8 -// CHECK: [[TMP17:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 2 +// CHECK: [[TMP17:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 2 // CHECK: store ptr [[Y]], ptr [[TMP17]], align 8 -// CHECK: [[TMP18:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 2 +// CHECK: [[TMP18:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 2 // CHECK: store ptr null, ptr [[TMP18]], align 8 -// CHECK: [[TMP19:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 3 +// CHECK: [[TMP19:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 3 // CHECK: store ptr [[TMP2]], ptr [[TMP19]], align 8 -// CHECK: [[TMP20:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 3 +// CHECK: [[TMP20:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 3 // CHECK: store ptr [[X]], ptr [[TMP20]], align 8 -// CHECK: [[TMP21:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 3 +// CHECK: [[TMP21:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 3 // CHECK: store ptr null, ptr [[TMP21]], align 8 -// CHECK: [[TMP22:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK: [[TMP23:%.*]] = getelementptr inbounds [4 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK: [[TMP24:%.*]] = getelementptr inbounds [4 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 0 -// CHECK: [[TMP25:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 +// CHECK: [[TMP22:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 4 +// CHECK: store ptr [[PS]], ptr [[TMP22]], align 8 +// CHECK: [[TMP23:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 4 +// CHECK: store ptr [[X]], ptr [[TMP23]], align 8 +// CHECK: [[TMP24:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 4 +// CHECK: store ptr null, ptr [[TMP24]], align 8 +// CHECK: [[TMP25:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK: [[TMP26:%.*]] = getelementptr inbounds [5 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK: [[TMP27:%.*]] = getelementptr inbounds [5 x i64], ptr [[DOTOFFLOAD_SIZES]], i32 0, i32 0 +// CHECK: [[TMP28:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], ptr [[KERNEL_ARGS:%.*]], i32 0, i32 0 // // -// CHECK-LABEL: define internal void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f5v_l52( +// CHECK-LABEL: define internal void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}__Z2f5v_l56( // CHECK-SAME: ptr noundef nonnull align 8 dereferenceable(8) [[PS:%.*]]) #[[ATTR1]] { // CHECK: [[ENTRY:.*:]] // CHECK: store ptr [[PS]], ptr [[PS_ADDR:%.*]], align 8 diff --git a/clang/test/OpenMP/target_task_affinity_codegen.cpp b/clang/test/OpenMP/target_task_affinity_codegen.cpp index 53960cee4b730..48e2c5e403880 100644 --- a/clang/test/OpenMP/target_task_affinity_codegen.cpp +++ b/clang/test/OpenMP/target_task_affinity_codegen.cpp @@ -1,4 +1,4 @@ -// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --function-signature --include-generated-funcs --replace-value-regex "__omp_offloading_[0-9a-z]+_[0-9a-z]+" "reduction_size[.].+[.]" "pl_cond[.].+[.|,]" --prefix-filecheck-ir-name _ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --function-signature --check-globals --include-generated-funcs --replace-value-regex "__omp_offloading_[0-9a-z]+_[0-9a-z]+" "reduction_size[.].+[.]" "pl_cond[.].+[.|,]" --prefix-filecheck-ir-name _ --global-value-regex "\.offload_.*" // Test host codegen. // RUN: %clang_cc1 -verify -fopenmp -x c++ -triple powerpc64le-unknown-unknown -fopenmp-targets=powerpc64le-ibm-linux-gnu -emit-llvm %s -o - | FileCheck %s --check-prefix=CHECK1 // RUN: %clang_cc1 -fopenmp -x c++ -std=c++11 -triple powerpc64le-unknown-unknown -fopenmp-targets=powerpc64le-ibm-linux-gnu -emit-pch -o %t %s @@ -37,11 +37,11 @@ int main() { int *A; int *B; - #pragma omp target data map(tofrom: A[0:1024]) + #pragma omp target data map(tofrom: A[0:1024]) // (1) -#pragma omp target data use_device_ptr(A) + #pragma omp target data use_device_ptr(A) // (2) { - #pragma omp target defaultmap(none) is_device_ptr(A) map(tofrom: B[0:1024]) + #pragma omp target defaultmap(none) is_device_ptr(A) map(tofrom: B[0:1024]) // (3) { #pragma omp task shared(B) affinity(A[0:1024]) { @@ -56,106 +56,145 @@ int main() { } #endif + +// Expected Maps: +// (1): +// &A[0], &A[/*lb=*/0], 1024 * sizeof(A[0]), TO | FROM +// &A, &A[/*lb=*/0], sizeof(A), ATTACH +// (2): +// &A[0], &A[0], sizeof(A), RETURN_PARAM +// (3): +// &B[0], &B[/*lb=*/0], 1024 * sizeof(B[0]), TO | FROM | PARAM +// &B, &B[/*lb=*/0], sizeof(B), ATTACH +// &A[0], &A[0], sizeof(A[0]), LITERAL | PARAM + +//. +// CHECK1: @.offload_sizes = private unnamed_addr constant [2 x i64] [i64 4096, i64 8] +// CHECK1: @.offload_maptypes = private unnamed_addr constant [2 x i64] [i64 3, i64 16384] +// CHECK1: @.offload_sizes.1 = private unnamed_addr constant [1 x i64] zeroinitializer +// CHECK1: @.offload_maptypes.2 = private unnamed_addr constant [1 x i64] [i64 64] +// CHECK1: @.offload_sizes.3 = private unnamed_addr constant [3 x i64] [i64 4096, i64 8, i64 8] +// CHECK1: @.offload_maptypes.4 = private unnamed_addr constant [3 x i64] [i64 35, i64 16384, i64 288] +//. +// CHECK3: @.offload_sizes = private unnamed_addr constant [2 x i64] [i64 4096, i64 4] +// CHECK3: @.offload_maptypes = private unnamed_addr constant [2 x i64] [i64 3, i64 16384] +// CHECK3: @.offload_sizes.1 = private unnamed_addr constant [1 x i64] zeroinitializer +// CHECK3: @.offload_maptypes.2 = private unnamed_addr constant [1 x i64] [i64 64] +// CHECK3: @.offload_sizes.3 = private unnamed_addr constant [3 x i64] [i64 4096, i64 4, i64 4] +// CHECK3: @.offload_maptypes.4 = private unnamed_addr constant [3 x i64] [i64 35, i64 16384, i64 288] +//. // CHECK1-LABEL: define {{[^@]+}}@main // CHECK1-SAME: () #[[ATTR0:[0-9]+]] { // CHECK1-NEXT: entry: // CHECK1-NEXT: [[RETVAL:%.*]] = alloca i32, align 4 // CHECK1-NEXT: [[A:%.*]] = alloca ptr, align 8 // CHECK1-NEXT: [[B:%.*]] = alloca ptr, align 8 -// CHECK1-NEXT: [[DOTOFFLOAD_BASEPTRS:%.*]] = alloca [1 x ptr], align 8 -// CHECK1-NEXT: [[DOTOFFLOAD_PTRS:%.*]] = alloca [1 x ptr], align 8 -// CHECK1-NEXT: [[DOTOFFLOAD_MAPPERS:%.*]] = alloca [1 x ptr], align 8 +// CHECK1-NEXT: [[DOTOFFLOAD_BASEPTRS:%.*]] = alloca [2 x ptr], align 8 +// CHECK1-NEXT: [[DOTOFFLOAD_PTRS:%.*]] = alloca [2 x ptr], align 8 +// CHECK1-NEXT: [[DOTOFFLOAD_MAPPERS:%.*]] = alloca [2 x ptr], align 8 // CHECK1-NEXT: [[DOTOFFLOAD_BASEPTRS1:%.*]] = alloca [1 x ptr], align 8 // CHECK1-NEXT: [[DOTOFFLOAD_PTRS2:%.*]] = alloca [1 x ptr], align 8 // CHECK1-NEXT: [[DOTOFFLOAD_MAPPERS3:%.*]] = alloca [1 x ptr], align 8 // CHECK1-NEXT: [[TMP0:%.*]] = alloca ptr, align 8 -// CHECK1-NEXT: [[DOTOFFLOAD_BASEPTRS5:%.*]] = alloca [2 x ptr], align 8 -// CHECK1-NEXT: [[DOTOFFLOAD_PTRS6:%.*]] = alloca [2 x ptr], align 8 -// CHECK1-NEXT: [[DOTOFFLOAD_MAPPERS7:%.*]] = alloca [2 x ptr], align 8 +// CHECK1-NEXT: [[DOTOFFLOAD_BASEPTRS5:%.*]] = alloca [3 x ptr], align 8 +// CHECK1-NEXT: [[DOTOFFLOAD_PTRS6:%.*]] = alloca [3 x ptr], align 8 +// CHECK1-NEXT: [[DOTOFFLOAD_MAPPERS7:%.*]] = alloca [3 x ptr], align 8 // CHECK1-NEXT: [[KERNEL_ARGS:%.*]] = alloca [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], align 8 // CHECK1-NEXT: store i32 0, ptr [[RETVAL]], align 4 // CHECK1-NEXT: [[TMP1:%.*]] = load ptr, ptr [[A]], align 8 // CHECK1-NEXT: [[TMP2:%.*]] = load ptr, ptr [[A]], align 8 // CHECK1-NEXT: [[ARRAYIDX:%.*]] = getelementptr inbounds nuw i32, ptr [[TMP2]], i64 0 -// CHECK1-NEXT: [[TMP3:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK1-NEXT: [[TMP3:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 // CHECK1-NEXT: store ptr [[TMP1]], ptr [[TMP3]], align 8 -// CHECK1-NEXT: [[TMP4:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK1-NEXT: [[TMP4:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 // CHECK1-NEXT: store ptr [[ARRAYIDX]], ptr [[TMP4]], align 8 -// CHECK1-NEXT: [[TMP5:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 0 +// CHECK1-NEXT: [[TMP5:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 0 // CHECK1-NEXT: store ptr null, ptr [[TMP5]], align 8 -// CHECK1-NEXT: [[TMP6:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK1-NEXT: [[TMP7:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK1-NEXT: call void @__tgt_target_data_begin_mapper(ptr @[[GLOB1:[0-9]+]], i64 -1, i32 1, ptr [[TMP6]], ptr [[TMP7]], ptr @.offload_sizes, ptr @.offload_maptypes, ptr null, ptr null) -// CHECK1-NEXT: [[TMP8:%.*]] = load ptr, ptr [[A]], align 8 -// CHECK1-NEXT: [[TMP9:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS1]], i32 0, i32 0 -// CHECK1-NEXT: store ptr [[TMP8]], ptr [[TMP9]], align 8 -// CHECK1-NEXT: [[TMP10:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS2]], i32 0, i32 0 -// CHECK1-NEXT: store ptr [[TMP8]], ptr [[TMP10]], align 8 -// CHECK1-NEXT: [[TMP11:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_MAPPERS3]], i64 0, i64 0 -// CHECK1-NEXT: store ptr null, ptr [[TMP11]], align 8 +// CHECK1-NEXT: [[TMP6:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK1-NEXT: store ptr [[A]], ptr [[TMP6]], align 8 +// CHECK1-NEXT: [[TMP7:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK1-NEXT: store ptr [[ARRAYIDX]], ptr [[TMP7]], align 8 +// CHECK1-NEXT: [[TMP8:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i64 0, i64 1 +// CHECK1-NEXT: store ptr null, ptr [[TMP8]], align 8 +// CHECK1-NEXT: [[TMP9:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK1-NEXT: [[TMP10:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK1-NEXT: call void @__tgt_target_data_begin_mapper(ptr @[[GLOB1:[0-9]+]], i64 -1, i32 2, ptr [[TMP9]], ptr [[TMP10]], ptr @.offload_sizes, ptr @.offload_maptypes, ptr null, ptr null) +// CHECK1-NEXT: [[TMP11:%.*]] = load ptr, ptr [[A]], align 8 // CHECK1-NEXT: [[TMP12:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS1]], i32 0, i32 0 +// CHECK1-NEXT: store ptr [[TMP11]], ptr [[TMP12]], align 8 // CHECK1-NEXT: [[TMP13:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS2]], i32 0, i32 0 -// CHECK1-NEXT: call void @__tgt_target_data_begin_mapper(ptr @[[GLOB1]], i64 -1, i32 1, ptr [[TMP12]], ptr [[TMP13]], ptr @.offload_sizes.1, ptr @.offload_maptypes.2, ptr null, ptr null) -// CHECK1-NEXT: [[TMP14:%.*]] = load ptr, ptr [[TMP9]], align 8 -// CHECK1-NEXT: store ptr [[TMP14]], ptr [[TMP0]], align 8 -// CHECK1-NEXT: [[TMP15:%.*]] = load ptr, ptr [[B]], align 8 -// CHECK1-NEXT: [[TMP16:%.*]] = load ptr, ptr [[TMP0]], align 8 -// CHECK1-NEXT: [[TMP17:%.*]] = load ptr, ptr [[B]], align 8 +// CHECK1-NEXT: store ptr [[TMP11]], ptr [[TMP13]], align 8 +// CHECK1-NEXT: [[TMP14:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_MAPPERS3]], i64 0, i64 0 +// CHECK1-NEXT: store ptr null, ptr [[TMP14]], align 8 +// CHECK1-NEXT: [[TMP15:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS1]], i32 0, i32 0 +// CHECK1-NEXT: [[TMP16:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS2]], i32 0, i32 0 +// CHECK1-NEXT: call void @__tgt_target_data_begin_mapper(ptr @[[GLOB1]], i64 -1, i32 1, ptr [[TMP15]], ptr [[TMP16]], ptr @.offload_sizes.1, ptr @.offload_maptypes.2, ptr null, ptr null) +// CHECK1-NEXT: [[TMP17:%.*]] = load ptr, ptr [[TMP12]], align 8 +// CHECK1-NEXT: store ptr [[TMP17]], ptr [[TMP0]], align 8 // CHECK1-NEXT: [[TMP18:%.*]] = load ptr, ptr [[B]], align 8 -// CHECK1-NEXT: [[ARRAYIDX4:%.*]] = getelementptr inbounds nuw i32, ptr [[TMP18]], i64 0 -// CHECK1-NEXT: [[TMP19:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS5]], i32 0, i32 0 -// CHECK1-NEXT: store ptr [[TMP17]], ptr [[TMP19]], align 8 -// CHECK1-NEXT: [[TMP20:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS6]], i32 0, i32 0 -// CHECK1-NEXT: store ptr [[ARRAYIDX4]], ptr [[TMP20]], align 8 -// CHECK1-NEXT: [[TMP21:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS7]], i64 0, i64 0 -// CHECK1-NEXT: store ptr null, ptr [[TMP21]], align 8 -// CHECK1-NEXT: [[TMP22:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS5]], i32 0, i32 1 -// CHECK1-NEXT: store ptr [[TMP16]], ptr [[TMP22]], align 8 -// CHECK1-NEXT: [[TMP23:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS6]], i32 0, i32 1 -// CHECK1-NEXT: store ptr [[TMP16]], ptr [[TMP23]], align 8 -// CHECK1-NEXT: [[TMP24:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS7]], i64 0, i64 1 +// CHECK1-NEXT: [[TMP19:%.*]] = load ptr, ptr [[TMP0]], align 8 +// CHECK1-NEXT: [[TMP20:%.*]] = load ptr, ptr [[B]], align 8 +// CHECK1-NEXT: [[TMP21:%.*]] = load ptr, ptr [[B]], align 8 +// CHECK1-NEXT: [[ARRAYIDX4:%.*]] = getelementptr inbounds nuw i32, ptr [[TMP21]], i64 0 +// CHECK1-NEXT: [[TMP22:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS5]], i32 0, i32 0 +// CHECK1-NEXT: store ptr [[TMP20]], ptr [[TMP22]], align 8 +// CHECK1-NEXT: [[TMP23:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS6]], i32 0, i32 0 +// CHECK1-NEXT: store ptr [[ARRAYIDX4]], ptr [[TMP23]], align 8 +// CHECK1-NEXT: [[TMP24:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS7]], i64 0, i64 0 // CHECK1-NEXT: store ptr null, ptr [[TMP24]], align 8 -// CHECK1-NEXT: [[TMP25:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS5]], i32 0, i32 0 -// CHECK1-NEXT: [[TMP26:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS6]], i32 0, i32 0 -// CHECK1-NEXT: [[TMP27:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 0 -// CHECK1-NEXT: store i32 3, ptr [[TMP27]], align 4 -// CHECK1-NEXT: [[TMP28:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 1 -// CHECK1-NEXT: store i32 2, ptr [[TMP28]], align 4 -// CHECK1-NEXT: [[TMP29:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 2 -// CHECK1-NEXT: store ptr [[TMP25]], ptr [[TMP29]], align 8 -// CHECK1-NEXT: [[TMP30:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 3 -// CHECK1-NEXT: store ptr [[TMP26]], ptr [[TMP30]], align 8 -// CHECK1-NEXT: [[TMP31:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 4 -// CHECK1-NEXT: store ptr @.offload_sizes.3, ptr [[TMP31]], align 8 -// CHECK1-NEXT: [[TMP32:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 5 -// CHECK1-NEXT: store ptr @.offload_maptypes.4, ptr [[TMP32]], align 8 -// CHECK1-NEXT: [[TMP33:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 6 -// CHECK1-NEXT: store ptr null, ptr [[TMP33]], align 8 -// CHECK1-NEXT: [[TMP34:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 7 -// CHECK1-NEXT: store ptr null, ptr [[TMP34]], align 8 -// CHECK1-NEXT: [[TMP35:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 8 -// CHECK1-NEXT: store i64 0, ptr [[TMP35]], align 8 -// CHECK1-NEXT: [[TMP36:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 9 -// CHECK1-NEXT: store i64 0, ptr [[TMP36]], align 8 -// CHECK1-NEXT: [[TMP37:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 10 -// CHECK1-NEXT: store [3 x i32] [i32 -1, i32 0, i32 0], ptr [[TMP37]], align 4 -// CHECK1-NEXT: [[TMP38:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 11 -// CHECK1-NEXT: store [3 x i32] zeroinitializer, ptr [[TMP38]], align 4 -// CHECK1-NEXT: [[TMP39:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 12 -// CHECK1-NEXT: store i32 0, ptr [[TMP39]], align 4 -// CHECK1-NEXT: [[TMP40:%.*]] = call i32 @__tgt_target_kernel(ptr @[[GLOB1]], i64 -1, i32 -1, i32 0, ptr @.{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}_main_l44.region_id, ptr [[KERNEL_ARGS]]) -// CHECK1-NEXT: [[TMP41:%.*]] = icmp ne i32 [[TMP40]], 0 -// CHECK1-NEXT: br i1 [[TMP41]], label [[OMP_OFFLOAD_FAILED:%.*]], label [[OMP_OFFLOAD_CONT:%.*]] +// CHECK1-NEXT: [[TMP25:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS5]], i32 0, i32 1 +// CHECK1-NEXT: store ptr [[B]], ptr [[TMP25]], align 8 +// CHECK1-NEXT: [[TMP26:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS6]], i32 0, i32 1 +// CHECK1-NEXT: store ptr [[ARRAYIDX4]], ptr [[TMP26]], align 8 +// CHECK1-NEXT: [[TMP27:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS7]], i64 0, i64 1 +// CHECK1-NEXT: store ptr null, ptr [[TMP27]], align 8 +// CHECK1-NEXT: [[TMP28:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS5]], i32 0, i32 2 +// CHECK1-NEXT: store ptr [[TMP19]], ptr [[TMP28]], align 8 +// CHECK1-NEXT: [[TMP29:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS6]], i32 0, i32 2 +// CHECK1-NEXT: store ptr [[TMP19]], ptr [[TMP29]], align 8 +// CHECK1-NEXT: [[TMP30:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS7]], i64 0, i64 2 +// CHECK1-NEXT: store ptr null, ptr [[TMP30]], align 8 +// CHECK1-NEXT: [[TMP31:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS5]], i32 0, i32 0 +// CHECK1-NEXT: [[TMP32:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS6]], i32 0, i32 0 +// CHECK1-NEXT: [[TMP33:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 0 +// CHECK1-NEXT: store i32 3, ptr [[TMP33]], align 4 +// CHECK1-NEXT: [[TMP34:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 1 +// CHECK1-NEXT: store i32 3, ptr [[TMP34]], align 4 +// CHECK1-NEXT: [[TMP35:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 2 +// CHECK1-NEXT: store ptr [[TMP31]], ptr [[TMP35]], align 8 +// CHECK1-NEXT: [[TMP36:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 3 +// CHECK1-NEXT: store ptr [[TMP32]], ptr [[TMP36]], align 8 +// CHECK1-NEXT: [[TMP37:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 4 +// CHECK1-NEXT: store ptr @.offload_sizes.3, ptr [[TMP37]], align 8 +// CHECK1-NEXT: [[TMP38:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 5 +// CHECK1-NEXT: store ptr @.offload_maptypes.4, ptr [[TMP38]], align 8 +// CHECK1-NEXT: [[TMP39:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 6 +// CHECK1-NEXT: store ptr null, ptr [[TMP39]], align 8 +// CHECK1-NEXT: [[TMP40:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 7 +// CHECK1-NEXT: store ptr null, ptr [[TMP40]], align 8 +// CHECK1-NEXT: [[TMP41:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 8 +// CHECK1-NEXT: store i64 0, ptr [[TMP41]], align 8 +// CHECK1-NEXT: [[TMP42:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 9 +// CHECK1-NEXT: store i64 0, ptr [[TMP42]], align 8 +// CHECK1-NEXT: [[TMP43:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 10 +// CHECK1-NEXT: store [3 x i32] [i32 -1, i32 0, i32 0], ptr [[TMP43]], align 4 +// CHECK1-NEXT: [[TMP44:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 11 +// CHECK1-NEXT: store [3 x i32] zeroinitializer, ptr [[TMP44]], align 4 +// CHECK1-NEXT: [[TMP45:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 12 +// CHECK1-NEXT: store i32 0, ptr [[TMP45]], align 4 +// CHECK1-NEXT: [[TMP46:%.*]] = call i32 @__tgt_target_kernel(ptr @[[GLOB1]], i64 -1, i32 -1, i32 0, ptr @.{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}_main_l44.region_id, ptr [[KERNEL_ARGS]]) +// CHECK1-NEXT: [[TMP47:%.*]] = icmp ne i32 [[TMP46]], 0 +// CHECK1-NEXT: br i1 [[TMP47]], label [[OMP_OFFLOAD_FAILED:%.*]], label [[OMP_OFFLOAD_CONT:%.*]] // CHECK1: omp_offload.failed: -// CHECK1-NEXT: call void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}_main_l44(ptr [[TMP15]], ptr [[TMP16]]) #[[ATTR1:[0-9]+]] +// CHECK1-NEXT: call void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}_main_l44(ptr [[TMP18]], ptr [[TMP19]]) #[[ATTR1:[0-9]+]] // CHECK1-NEXT: br label [[OMP_OFFLOAD_CONT]] // CHECK1: omp_offload.cont: -// CHECK1-NEXT: [[TMP42:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS1]], i32 0, i32 0 -// CHECK1-NEXT: [[TMP43:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS2]], i32 0, i32 0 -// CHECK1-NEXT: call void @__tgt_target_data_end_mapper(ptr @[[GLOB1]], i64 -1, i32 1, ptr [[TMP42]], ptr [[TMP43]], ptr @.offload_sizes.1, ptr @.offload_maptypes.2, ptr null, ptr null) -// CHECK1-NEXT: [[TMP44:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK1-NEXT: [[TMP45:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK1-NEXT: call void @__tgt_target_data_end_mapper(ptr @[[GLOB1]], i64 -1, i32 1, ptr [[TMP44]], ptr [[TMP45]], ptr @.offload_sizes, ptr @.offload_maptypes, ptr null, ptr null) +// CHECK1-NEXT: [[TMP48:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS1]], i32 0, i32 0 +// CHECK1-NEXT: [[TMP49:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS2]], i32 0, i32 0 +// CHECK1-NEXT: call void @__tgt_target_data_end_mapper(ptr @[[GLOB1]], i64 -1, i32 1, ptr [[TMP48]], ptr [[TMP49]], ptr @.offload_sizes.1, ptr @.offload_maptypes.2, ptr null, ptr null) +// CHECK1-NEXT: [[TMP50:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK1-NEXT: [[TMP51:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK1-NEXT: call void @__tgt_target_data_end_mapper(ptr @[[GLOB1]], i64 -1, i32 2, ptr [[TMP50]], ptr [[TMP51]], ptr @.offload_sizes, ptr @.offload_maptypes, ptr null, ptr null) // CHECK1-NEXT: ret i32 0 // // @@ -237,44 +276,44 @@ int main() { // CHECK1-NEXT: [[TMP6:%.*]] = getelementptr inbounds nuw [[STRUCT_KMP_TASK_T]], ptr [[TMP4]], i32 0, i32 0 // CHECK1-NEXT: [[TMP7:%.*]] = load ptr, ptr [[TMP6]], align 8 // CHECK1-NEXT: [[TMP8:%.*]] = getelementptr inbounds nuw [[STRUCT_KMP_TASK_T_WITH_PRIVATES]], ptr [[TMP3]], i32 0, i32 1 -// CHECK1-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META4:![0-9]+]]) -// CHECK1-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META7:![0-9]+]]) -// CHECK1-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META9:![0-9]+]]) -// CHECK1-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META11:![0-9]+]]) -// CHECK1-NEXT: store i32 [[TMP2]], ptr [[DOTGLOBAL_TID__ADDR_I]], align 4, !noalias [[META13:![0-9]+]] -// CHECK1-NEXT: store ptr [[TMP5]], ptr [[DOTPART_ID__ADDR_I]], align 8, !noalias [[META13]] -// CHECK1-NEXT: store ptr [[TMP8]], ptr [[DOTPRIVATES__ADDR_I]], align 8, !noalias [[META13]] -// CHECK1-NEXT: store ptr @.omp_task_privates_map., ptr [[DOTCOPY_FN__ADDR_I]], align 8, !noalias [[META13]] -// CHECK1-NEXT: store ptr [[TMP3]], ptr [[DOTTASK_T__ADDR_I]], align 8, !noalias [[META13]] -// CHECK1-NEXT: store ptr [[TMP7]], ptr [[__CONTEXT_ADDR_I]], align 8, !noalias [[META13]] -// CHECK1-NEXT: [[TMP9:%.*]] = load ptr, ptr [[__CONTEXT_ADDR_I]], align 8, !noalias [[META13]] -// CHECK1-NEXT: [[TMP10:%.*]] = load ptr, ptr [[DOTCOPY_FN__ADDR_I]], align 8, !noalias [[META13]] -// CHECK1-NEXT: [[TMP11:%.*]] = load ptr, ptr [[DOTPRIVATES__ADDR_I]], align 8, !noalias [[META13]] +// CHECK1-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META5:![0-9]+]]) +// CHECK1-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META8:![0-9]+]]) +// CHECK1-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META10:![0-9]+]]) +// CHECK1-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META12:![0-9]+]]) +// CHECK1-NEXT: store i32 [[TMP2]], ptr [[DOTGLOBAL_TID__ADDR_I]], align 4, !noalias [[META14:![0-9]+]] +// CHECK1-NEXT: store ptr [[TMP5]], ptr [[DOTPART_ID__ADDR_I]], align 8, !noalias [[META14]] +// CHECK1-NEXT: store ptr [[TMP8]], ptr [[DOTPRIVATES__ADDR_I]], align 8, !noalias [[META14]] +// CHECK1-NEXT: store ptr @.omp_task_privates_map., ptr [[DOTCOPY_FN__ADDR_I]], align 8, !noalias [[META14]] +// CHECK1-NEXT: store ptr [[TMP3]], ptr [[DOTTASK_T__ADDR_I]], align 8, !noalias [[META14]] +// CHECK1-NEXT: store ptr [[TMP7]], ptr [[__CONTEXT_ADDR_I]], align 8, !noalias [[META14]] +// CHECK1-NEXT: [[TMP9:%.*]] = load ptr, ptr [[__CONTEXT_ADDR_I]], align 8, !noalias [[META14]] +// CHECK1-NEXT: [[TMP10:%.*]] = load ptr, ptr [[DOTCOPY_FN__ADDR_I]], align 8, !noalias [[META14]] +// CHECK1-NEXT: [[TMP11:%.*]] = load ptr, ptr [[DOTPRIVATES__ADDR_I]], align 8, !noalias [[META14]] // CHECK1-NEXT: call void [[TMP10]](ptr [[TMP11]], ptr [[DOTFIRSTPRIV_PTR_ADDR_I]]) #[[ATTR1]] -// CHECK1-NEXT: [[TMP12:%.*]] = load ptr, ptr [[DOTFIRSTPRIV_PTR_ADDR_I]], align 8, !noalias [[META13]] -// CHECK1-NEXT: store i32 0, ptr [[I_I]], align 4, !noalias [[META13]] +// CHECK1-NEXT: [[TMP12:%.*]] = load ptr, ptr [[DOTFIRSTPRIV_PTR_ADDR_I]], align 8, !noalias [[META14]] +// CHECK1-NEXT: store i32 0, ptr [[I_I]], align 4, !noalias [[META14]] // CHECK1-NEXT: br label [[FOR_COND_I:%.*]] // CHECK1: for.cond.i: -// CHECK1-NEXT: [[TMP13:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META13]] +// CHECK1-NEXT: [[TMP13:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META14]] // CHECK1-NEXT: [[CMP_I:%.*]] = icmp slt i32 [[TMP13]], 1024 // CHECK1-NEXT: br i1 [[CMP_I]], label [[FOR_BODY_I:%.*]], label [[DOTOMP_OUTLINED__EXIT:%.*]] // CHECK1: for.body.i: // CHECK1-NEXT: [[TMP14:%.*]] = load ptr, ptr [[TMP12]], align 8 -// CHECK1-NEXT: [[TMP15:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META13]] +// CHECK1-NEXT: [[TMP15:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META14]] // CHECK1-NEXT: [[IDXPROM_I:%.*]] = sext i32 [[TMP15]] to i64 // CHECK1-NEXT: [[ARRAYIDX_I:%.*]] = getelementptr inbounds i32, ptr [[TMP14]], i64 [[IDXPROM_I]] // CHECK1-NEXT: [[TMP16:%.*]] = load i32, ptr [[ARRAYIDX_I]], align 4 // CHECK1-NEXT: [[MUL_I:%.*]] = mul nsw i32 2, [[TMP16]] -// CHECK1-NEXT: [[TMP17:%.*]] = load ptr, ptr [[TMP9]], align 8 +// CHECK1-NEXT: [[TMP17:%.*]] = load ptr, ptr [[TMP9]], align 8, !nonnull [[META15:![0-9]+]], !align [[META16:![0-9]+]] // CHECK1-NEXT: [[TMP18:%.*]] = load ptr, ptr [[TMP17]], align 8 -// CHECK1-NEXT: [[TMP19:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META13]] +// CHECK1-NEXT: [[TMP19:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META14]] // CHECK1-NEXT: [[IDXPROM1_I:%.*]] = sext i32 [[TMP19]] to i64 // CHECK1-NEXT: [[ARRAYIDX2_I:%.*]] = getelementptr inbounds i32, ptr [[TMP18]], i64 [[IDXPROM1_I]] // CHECK1-NEXT: store i32 [[MUL_I]], ptr [[ARRAYIDX2_I]], align 4 -// CHECK1-NEXT: [[TMP20:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META13]] +// CHECK1-NEXT: [[TMP20:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META14]] // CHECK1-NEXT: [[INC_I:%.*]] = add nsw i32 [[TMP20]], 1 -// CHECK1-NEXT: store i32 [[INC_I]], ptr [[I_I]], align 4, !noalias [[META13]] -// CHECK1-NEXT: br label [[FOR_COND_I]], !llvm.loop [[LOOP14:![0-9]+]] +// CHECK1-NEXT: store i32 [[INC_I]], ptr [[I_I]], align 4, !noalias [[META14]] +// CHECK1-NEXT: br label [[FOR_COND_I]], !llvm.loop [[LOOP17:![0-9]+]] // CHECK1: .omp_outlined..exit: // CHECK1-NEXT: ret i32 0 // @@ -285,100 +324,112 @@ int main() { // CHECK3-NEXT: [[RETVAL:%.*]] = alloca i32, align 4 // CHECK3-NEXT: [[A:%.*]] = alloca ptr, align 4 // CHECK3-NEXT: [[B:%.*]] = alloca ptr, align 4 -// CHECK3-NEXT: [[DOTOFFLOAD_BASEPTRS:%.*]] = alloca [1 x ptr], align 4 -// CHECK3-NEXT: [[DOTOFFLOAD_PTRS:%.*]] = alloca [1 x ptr], align 4 -// CHECK3-NEXT: [[DOTOFFLOAD_MAPPERS:%.*]] = alloca [1 x ptr], align 4 +// CHECK3-NEXT: [[DOTOFFLOAD_BASEPTRS:%.*]] = alloca [2 x ptr], align 4 +// CHECK3-NEXT: [[DOTOFFLOAD_PTRS:%.*]] = alloca [2 x ptr], align 4 +// CHECK3-NEXT: [[DOTOFFLOAD_MAPPERS:%.*]] = alloca [2 x ptr], align 4 // CHECK3-NEXT: [[DOTOFFLOAD_BASEPTRS1:%.*]] = alloca [1 x ptr], align 4 // CHECK3-NEXT: [[DOTOFFLOAD_PTRS2:%.*]] = alloca [1 x ptr], align 4 // CHECK3-NEXT: [[DOTOFFLOAD_MAPPERS3:%.*]] = alloca [1 x ptr], align 4 // CHECK3-NEXT: [[TMP0:%.*]] = alloca ptr, align 4 -// CHECK3-NEXT: [[DOTOFFLOAD_BASEPTRS5:%.*]] = alloca [2 x ptr], align 4 -// CHECK3-NEXT: [[DOTOFFLOAD_PTRS6:%.*]] = alloca [2 x ptr], align 4 -// CHECK3-NEXT: [[DOTOFFLOAD_MAPPERS7:%.*]] = alloca [2 x ptr], align 4 +// CHECK3-NEXT: [[DOTOFFLOAD_BASEPTRS5:%.*]] = alloca [3 x ptr], align 4 +// CHECK3-NEXT: [[DOTOFFLOAD_PTRS6:%.*]] = alloca [3 x ptr], align 4 +// CHECK3-NEXT: [[DOTOFFLOAD_MAPPERS7:%.*]] = alloca [3 x ptr], align 4 // CHECK3-NEXT: [[KERNEL_ARGS:%.*]] = alloca [[STRUCT___TGT_KERNEL_ARGUMENTS:%.*]], align 8 // CHECK3-NEXT: store i32 0, ptr [[RETVAL]], align 4 // CHECK3-NEXT: [[TMP1:%.*]] = load ptr, ptr [[A]], align 4 // CHECK3-NEXT: [[TMP2:%.*]] = load ptr, ptr [[A]], align 4 // CHECK3-NEXT: [[ARRAYIDX:%.*]] = getelementptr inbounds nuw i32, ptr [[TMP2]], i32 0 -// CHECK3-NEXT: [[TMP3:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK3-NEXT: [[TMP3:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 // CHECK3-NEXT: store ptr [[TMP1]], ptr [[TMP3]], align 4 -// CHECK3-NEXT: [[TMP4:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK3-NEXT: [[TMP4:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 // CHECK3-NEXT: store ptr [[ARRAYIDX]], ptr [[TMP4]], align 4 -// CHECK3-NEXT: [[TMP5:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i32 0, i32 0 +// CHECK3-NEXT: [[TMP5:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i32 0, i32 0 // CHECK3-NEXT: store ptr null, ptr [[TMP5]], align 4 -// CHECK3-NEXT: [[TMP6:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK3-NEXT: [[TMP7:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK3-NEXT: call void @__tgt_target_data_begin_mapper(ptr @[[GLOB1:[0-9]+]], i64 -1, i32 1, ptr [[TMP6]], ptr [[TMP7]], ptr @.offload_sizes, ptr @.offload_maptypes, ptr null, ptr null) -// CHECK3-NEXT: [[TMP8:%.*]] = load ptr, ptr [[A]], align 4 -// CHECK3-NEXT: [[TMP9:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS1]], i32 0, i32 0 -// CHECK3-NEXT: store ptr [[TMP8]], ptr [[TMP9]], align 4 -// CHECK3-NEXT: [[TMP10:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS2]], i32 0, i32 0 -// CHECK3-NEXT: store ptr [[TMP8]], ptr [[TMP10]], align 4 -// CHECK3-NEXT: [[TMP11:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_MAPPERS3]], i32 0, i32 0 -// CHECK3-NEXT: store ptr null, ptr [[TMP11]], align 4 +// CHECK3-NEXT: [[TMP6:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 1 +// CHECK3-NEXT: store ptr [[A]], ptr [[TMP6]], align 4 +// CHECK3-NEXT: [[TMP7:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 1 +// CHECK3-NEXT: store ptr [[ARRAYIDX]], ptr [[TMP7]], align 4 +// CHECK3-NEXT: [[TMP8:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS]], i32 0, i32 1 +// CHECK3-NEXT: store ptr null, ptr [[TMP8]], align 4 +// CHECK3-NEXT: [[TMP9:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK3-NEXT: [[TMP10:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK3-NEXT: call void @__tgt_target_data_begin_mapper(ptr @[[GLOB1:[0-9]+]], i64 -1, i32 2, ptr [[TMP9]], ptr [[TMP10]], ptr @.offload_sizes, ptr @.offload_maptypes, ptr null, ptr null) +// CHECK3-NEXT: [[TMP11:%.*]] = load ptr, ptr [[A]], align 4 // CHECK3-NEXT: [[TMP12:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS1]], i32 0, i32 0 +// CHECK3-NEXT: store ptr [[TMP11]], ptr [[TMP12]], align 4 // CHECK3-NEXT: [[TMP13:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS2]], i32 0, i32 0 -// CHECK3-NEXT: call void @__tgt_target_data_begin_mapper(ptr @[[GLOB1]], i64 -1, i32 1, ptr [[TMP12]], ptr [[TMP13]], ptr @.offload_sizes.1, ptr @.offload_maptypes.2, ptr null, ptr null) -// CHECK3-NEXT: [[TMP14:%.*]] = load ptr, ptr [[TMP9]], align 4 -// CHECK3-NEXT: store ptr [[TMP14]], ptr [[TMP0]], align 4 -// CHECK3-NEXT: [[TMP15:%.*]] = load ptr, ptr [[B]], align 4 -// CHECK3-NEXT: [[TMP16:%.*]] = load ptr, ptr [[TMP0]], align 4 -// CHECK3-NEXT: [[TMP17:%.*]] = load ptr, ptr [[B]], align 4 +// CHECK3-NEXT: store ptr [[TMP11]], ptr [[TMP13]], align 4 +// CHECK3-NEXT: [[TMP14:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_MAPPERS3]], i32 0, i32 0 +// CHECK3-NEXT: store ptr null, ptr [[TMP14]], align 4 +// CHECK3-NEXT: [[TMP15:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS1]], i32 0, i32 0 +// CHECK3-NEXT: [[TMP16:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS2]], i32 0, i32 0 +// CHECK3-NEXT: call void @__tgt_target_data_begin_mapper(ptr @[[GLOB1]], i64 -1, i32 1, ptr [[TMP15]], ptr [[TMP16]], ptr @.offload_sizes.1, ptr @.offload_maptypes.2, ptr null, ptr null) +// CHECK3-NEXT: [[TMP17:%.*]] = load ptr, ptr [[TMP12]], align 4 +// CHECK3-NEXT: store ptr [[TMP17]], ptr [[TMP0]], align 4 // CHECK3-NEXT: [[TMP18:%.*]] = load ptr, ptr [[B]], align 4 -// CHECK3-NEXT: [[ARRAYIDX4:%.*]] = getelementptr inbounds nuw i32, ptr [[TMP18]], i32 0 -// CHECK3-NEXT: [[TMP19:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS5]], i32 0, i32 0 -// CHECK3-NEXT: store ptr [[TMP17]], ptr [[TMP19]], align 4 -// CHECK3-NEXT: [[TMP20:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS6]], i32 0, i32 0 -// CHECK3-NEXT: store ptr [[ARRAYIDX4]], ptr [[TMP20]], align 4 -// CHECK3-NEXT: [[TMP21:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS7]], i32 0, i32 0 -// CHECK3-NEXT: store ptr null, ptr [[TMP21]], align 4 -// CHECK3-NEXT: [[TMP22:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS5]], i32 0, i32 1 -// CHECK3-NEXT: store ptr [[TMP16]], ptr [[TMP22]], align 4 -// CHECK3-NEXT: [[TMP23:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS6]], i32 0, i32 1 -// CHECK3-NEXT: store ptr [[TMP16]], ptr [[TMP23]], align 4 -// CHECK3-NEXT: [[TMP24:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_MAPPERS7]], i32 0, i32 1 +// CHECK3-NEXT: [[TMP19:%.*]] = load ptr, ptr [[TMP0]], align 4 +// CHECK3-NEXT: [[TMP20:%.*]] = load ptr, ptr [[B]], align 4 +// CHECK3-NEXT: [[TMP21:%.*]] = load ptr, ptr [[B]], align 4 +// CHECK3-NEXT: [[ARRAYIDX4:%.*]] = getelementptr inbounds nuw i32, ptr [[TMP21]], i32 0 +// CHECK3-NEXT: [[TMP22:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS5]], i32 0, i32 0 +// CHECK3-NEXT: store ptr [[TMP20]], ptr [[TMP22]], align 4 +// CHECK3-NEXT: [[TMP23:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS6]], i32 0, i32 0 +// CHECK3-NEXT: store ptr [[ARRAYIDX4]], ptr [[TMP23]], align 4 +// CHECK3-NEXT: [[TMP24:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS7]], i32 0, i32 0 // CHECK3-NEXT: store ptr null, ptr [[TMP24]], align 4 -// CHECK3-NEXT: [[TMP25:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS5]], i32 0, i32 0 -// CHECK3-NEXT: [[TMP26:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS6]], i32 0, i32 0 -// CHECK3-NEXT: [[TMP27:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 0 -// CHECK3-NEXT: store i32 3, ptr [[TMP27]], align 4 -// CHECK3-NEXT: [[TMP28:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 1 -// CHECK3-NEXT: store i32 2, ptr [[TMP28]], align 4 -// CHECK3-NEXT: [[TMP29:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 2 -// CHECK3-NEXT: store ptr [[TMP25]], ptr [[TMP29]], align 4 -// CHECK3-NEXT: [[TMP30:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 3 -// CHECK3-NEXT: store ptr [[TMP26]], ptr [[TMP30]], align 4 -// CHECK3-NEXT: [[TMP31:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 4 -// CHECK3-NEXT: store ptr @.offload_sizes.3, ptr [[TMP31]], align 4 -// CHECK3-NEXT: [[TMP32:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 5 -// CHECK3-NEXT: store ptr @.offload_maptypes.4, ptr [[TMP32]], align 4 -// CHECK3-NEXT: [[TMP33:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 6 -// CHECK3-NEXT: store ptr null, ptr [[TMP33]], align 4 -// CHECK3-NEXT: [[TMP34:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 7 -// CHECK3-NEXT: store ptr null, ptr [[TMP34]], align 4 -// CHECK3-NEXT: [[TMP35:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 8 -// CHECK3-NEXT: store i64 0, ptr [[TMP35]], align 8 -// CHECK3-NEXT: [[TMP36:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 9 -// CHECK3-NEXT: store i64 0, ptr [[TMP36]], align 8 -// CHECK3-NEXT: [[TMP37:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 10 -// CHECK3-NEXT: store [3 x i32] [i32 -1, i32 0, i32 0], ptr [[TMP37]], align 4 -// CHECK3-NEXT: [[TMP38:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 11 -// CHECK3-NEXT: store [3 x i32] zeroinitializer, ptr [[TMP38]], align 4 -// CHECK3-NEXT: [[TMP39:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 12 -// CHECK3-NEXT: store i32 0, ptr [[TMP39]], align 4 -// CHECK3-NEXT: [[TMP40:%.*]] = call i32 @__tgt_target_kernel(ptr @[[GLOB1]], i64 -1, i32 -1, i32 0, ptr @.{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}_main_l44.region_id, ptr [[KERNEL_ARGS]]) -// CHECK3-NEXT: [[TMP41:%.*]] = icmp ne i32 [[TMP40]], 0 -// CHECK3-NEXT: br i1 [[TMP41]], label [[OMP_OFFLOAD_FAILED:%.*]], label [[OMP_OFFLOAD_CONT:%.*]] +// CHECK3-NEXT: [[TMP25:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS5]], i32 0, i32 1 +// CHECK3-NEXT: store ptr [[B]], ptr [[TMP25]], align 4 +// CHECK3-NEXT: [[TMP26:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS6]], i32 0, i32 1 +// CHECK3-NEXT: store ptr [[ARRAYIDX4]], ptr [[TMP26]], align 4 +// CHECK3-NEXT: [[TMP27:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS7]], i32 0, i32 1 +// CHECK3-NEXT: store ptr null, ptr [[TMP27]], align 4 +// CHECK3-NEXT: [[TMP28:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS5]], i32 0, i32 2 +// CHECK3-NEXT: store ptr [[TMP19]], ptr [[TMP28]], align 4 +// CHECK3-NEXT: [[TMP29:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS6]], i32 0, i32 2 +// CHECK3-NEXT: store ptr [[TMP19]], ptr [[TMP29]], align 4 +// CHECK3-NEXT: [[TMP30:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_MAPPERS7]], i32 0, i32 2 +// CHECK3-NEXT: store ptr null, ptr [[TMP30]], align 4 +// CHECK3-NEXT: [[TMP31:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_BASEPTRS5]], i32 0, i32 0 +// CHECK3-NEXT: [[TMP32:%.*]] = getelementptr inbounds [3 x ptr], ptr [[DOTOFFLOAD_PTRS6]], i32 0, i32 0 +// CHECK3-NEXT: [[TMP33:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 0 +// CHECK3-NEXT: store i32 3, ptr [[TMP33]], align 4 +// CHECK3-NEXT: [[TMP34:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 1 +// CHECK3-NEXT: store i32 3, ptr [[TMP34]], align 4 +// CHECK3-NEXT: [[TMP35:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 2 +// CHECK3-NEXT: store ptr [[TMP31]], ptr [[TMP35]], align 4 +// CHECK3-NEXT: [[TMP36:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 3 +// CHECK3-NEXT: store ptr [[TMP32]], ptr [[TMP36]], align 4 +// CHECK3-NEXT: [[TMP37:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 4 +// CHECK3-NEXT: store ptr @.offload_sizes.3, ptr [[TMP37]], align 4 +// CHECK3-NEXT: [[TMP38:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 5 +// CHECK3-NEXT: store ptr @.offload_maptypes.4, ptr [[TMP38]], align 4 +// CHECK3-NEXT: [[TMP39:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 6 +// CHECK3-NEXT: store ptr null, ptr [[TMP39]], align 4 +// CHECK3-NEXT: [[TMP40:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 7 +// CHECK3-NEXT: store ptr null, ptr [[TMP40]], align 4 +// CHECK3-NEXT: [[TMP41:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 8 +// CHECK3-NEXT: store i64 0, ptr [[TMP41]], align 8 +// CHECK3-NEXT: [[TMP42:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 9 +// CHECK3-NEXT: store i64 0, ptr [[TMP42]], align 8 +// CHECK3-NEXT: [[TMP43:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 10 +// CHECK3-NEXT: store [3 x i32] [i32 -1, i32 0, i32 0], ptr [[TMP43]], align 4 +// CHECK3-NEXT: [[TMP44:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 11 +// CHECK3-NEXT: store [3 x i32] zeroinitializer, ptr [[TMP44]], align 4 +// CHECK3-NEXT: [[TMP45:%.*]] = getelementptr inbounds nuw [[STRUCT___TGT_KERNEL_ARGUMENTS]], ptr [[KERNEL_ARGS]], i32 0, i32 12 +// CHECK3-NEXT: store i32 0, ptr [[TMP45]], align 4 +// CHECK3-NEXT: [[TMP46:%.*]] = call i32 @__tgt_target_kernel(ptr @[[GLOB1]], i64 -1, i32 -1, i32 0, ptr @.{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}_main_l44.region_id, ptr [[KERNEL_ARGS]]) +// CHECK3-NEXT: [[TMP47:%.*]] = icmp ne i32 [[TMP46]], 0 +// CHECK3-NEXT: br i1 [[TMP47]], label [[OMP_OFFLOAD_FAILED:%.*]], label [[OMP_OFFLOAD_CONT:%.*]] // CHECK3: omp_offload.failed: -// CHECK3-NEXT: call void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}_main_l44(ptr [[TMP15]], ptr [[TMP16]]) #[[ATTR1:[0-9]+]] +// CHECK3-NEXT: call void @{{__omp_offloading_[0-9a-z]+_[0-9a-z]+}}_main_l44(ptr [[TMP18]], ptr [[TMP19]]) #[[ATTR1:[0-9]+]] // CHECK3-NEXT: br label [[OMP_OFFLOAD_CONT]] // CHECK3: omp_offload.cont: -// CHECK3-NEXT: [[TMP42:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS1]], i32 0, i32 0 -// CHECK3-NEXT: [[TMP43:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS2]], i32 0, i32 0 -// CHECK3-NEXT: call void @__tgt_target_data_end_mapper(ptr @[[GLOB1]], i64 -1, i32 1, ptr [[TMP42]], ptr [[TMP43]], ptr @.offload_sizes.1, ptr @.offload_maptypes.2, ptr null, ptr null) -// CHECK3-NEXT: [[TMP44:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 -// CHECK3-NEXT: [[TMP45:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 -// CHECK3-NEXT: call void @__tgt_target_data_end_mapper(ptr @[[GLOB1]], i64 -1, i32 1, ptr [[TMP44]], ptr [[TMP45]], ptr @.offload_sizes, ptr @.offload_maptypes, ptr null, ptr null) +// CHECK3-NEXT: [[TMP48:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_BASEPTRS1]], i32 0, i32 0 +// CHECK3-NEXT: [[TMP49:%.*]] = getelementptr inbounds [1 x ptr], ptr [[DOTOFFLOAD_PTRS2]], i32 0, i32 0 +// CHECK3-NEXT: call void @__tgt_target_data_end_mapper(ptr @[[GLOB1]], i64 -1, i32 1, ptr [[TMP48]], ptr [[TMP49]], ptr @.offload_sizes.1, ptr @.offload_maptypes.2, ptr null, ptr null) +// CHECK3-NEXT: [[TMP50:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_BASEPTRS]], i32 0, i32 0 +// CHECK3-NEXT: [[TMP51:%.*]] = getelementptr inbounds [2 x ptr], ptr [[DOTOFFLOAD_PTRS]], i32 0, i32 0 +// CHECK3-NEXT: call void @__tgt_target_data_end_mapper(ptr @[[GLOB1]], i64 -1, i32 2, ptr [[TMP50]], ptr [[TMP51]], ptr @.offload_sizes, ptr @.offload_maptypes, ptr null, ptr null) // CHECK3-NEXT: ret i32 0 // // @@ -460,42 +511,42 @@ int main() { // CHECK3-NEXT: [[TMP6:%.*]] = getelementptr inbounds nuw [[STRUCT_KMP_TASK_T]], ptr [[TMP4]], i32 0, i32 0 // CHECK3-NEXT: [[TMP7:%.*]] = load ptr, ptr [[TMP6]], align 4 // CHECK3-NEXT: [[TMP8:%.*]] = getelementptr inbounds nuw [[STRUCT_KMP_TASK_T_WITH_PRIVATES]], ptr [[TMP3]], i32 0, i32 1 -// CHECK3-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META5:![0-9]+]]) -// CHECK3-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META8:![0-9]+]]) -// CHECK3-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META10:![0-9]+]]) -// CHECK3-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META12:![0-9]+]]) -// CHECK3-NEXT: store i32 [[TMP2]], ptr [[DOTGLOBAL_TID__ADDR_I]], align 4, !noalias [[META14:![0-9]+]] -// CHECK3-NEXT: store ptr [[TMP5]], ptr [[DOTPART_ID__ADDR_I]], align 4, !noalias [[META14]] -// CHECK3-NEXT: store ptr [[TMP8]], ptr [[DOTPRIVATES__ADDR_I]], align 4, !noalias [[META14]] -// CHECK3-NEXT: store ptr @.omp_task_privates_map., ptr [[DOTCOPY_FN__ADDR_I]], align 4, !noalias [[META14]] -// CHECK3-NEXT: store ptr [[TMP3]], ptr [[DOTTASK_T__ADDR_I]], align 4, !noalias [[META14]] -// CHECK3-NEXT: store ptr [[TMP7]], ptr [[__CONTEXT_ADDR_I]], align 4, !noalias [[META14]] -// CHECK3-NEXT: [[TMP9:%.*]] = load ptr, ptr [[__CONTEXT_ADDR_I]], align 4, !noalias [[META14]] -// CHECK3-NEXT: [[TMP10:%.*]] = load ptr, ptr [[DOTCOPY_FN__ADDR_I]], align 4, !noalias [[META14]] -// CHECK3-NEXT: [[TMP11:%.*]] = load ptr, ptr [[DOTPRIVATES__ADDR_I]], align 4, !noalias [[META14]] +// CHECK3-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META6:![0-9]+]]) +// CHECK3-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META9:![0-9]+]]) +// CHECK3-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META11:![0-9]+]]) +// CHECK3-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META13:![0-9]+]]) +// CHECK3-NEXT: store i32 [[TMP2]], ptr [[DOTGLOBAL_TID__ADDR_I]], align 4, !noalias [[META15:![0-9]+]] +// CHECK3-NEXT: store ptr [[TMP5]], ptr [[DOTPART_ID__ADDR_I]], align 4, !noalias [[META15]] +// CHECK3-NEXT: store ptr [[TMP8]], ptr [[DOTPRIVATES__ADDR_I]], align 4, !noalias [[META15]] +// CHECK3-NEXT: store ptr @.omp_task_privates_map., ptr [[DOTCOPY_FN__ADDR_I]], align 4, !noalias [[META15]] +// CHECK3-NEXT: store ptr [[TMP3]], ptr [[DOTTASK_T__ADDR_I]], align 4, !noalias [[META15]] +// CHECK3-NEXT: store ptr [[TMP7]], ptr [[__CONTEXT_ADDR_I]], align 4, !noalias [[META15]] +// CHECK3-NEXT: [[TMP9:%.*]] = load ptr, ptr [[__CONTEXT_ADDR_I]], align 4, !noalias [[META15]] +// CHECK3-NEXT: [[TMP10:%.*]] = load ptr, ptr [[DOTCOPY_FN__ADDR_I]], align 4, !noalias [[META15]] +// CHECK3-NEXT: [[TMP11:%.*]] = load ptr, ptr [[DOTPRIVATES__ADDR_I]], align 4, !noalias [[META15]] // CHECK3-NEXT: call void [[TMP10]](ptr [[TMP11]], ptr [[DOTFIRSTPRIV_PTR_ADDR_I]]) #[[ATTR1]] -// CHECK3-NEXT: [[TMP12:%.*]] = load ptr, ptr [[DOTFIRSTPRIV_PTR_ADDR_I]], align 4, !noalias [[META14]] -// CHECK3-NEXT: store i32 0, ptr [[I_I]], align 4, !noalias [[META14]] +// CHECK3-NEXT: [[TMP12:%.*]] = load ptr, ptr [[DOTFIRSTPRIV_PTR_ADDR_I]], align 4, !noalias [[META15]] +// CHECK3-NEXT: store i32 0, ptr [[I_I]], align 4, !noalias [[META15]] // CHECK3-NEXT: br label [[FOR_COND_I:%.*]] // CHECK3: for.cond.i: -// CHECK3-NEXT: [[TMP13:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META14]] +// CHECK3-NEXT: [[TMP13:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META15]] // CHECK3-NEXT: [[CMP_I:%.*]] = icmp slt i32 [[TMP13]], 1024 // CHECK3-NEXT: br i1 [[CMP_I]], label [[FOR_BODY_I:%.*]], label [[DOTOMP_OUTLINED__EXIT:%.*]] // CHECK3: for.body.i: // CHECK3-NEXT: [[TMP14:%.*]] = load ptr, ptr [[TMP12]], align 4 -// CHECK3-NEXT: [[TMP15:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META14]] +// CHECK3-NEXT: [[TMP15:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META15]] // CHECK3-NEXT: [[ARRAYIDX_I:%.*]] = getelementptr inbounds i32, ptr [[TMP14]], i32 [[TMP15]] // CHECK3-NEXT: [[TMP16:%.*]] = load i32, ptr [[ARRAYIDX_I]], align 4 // CHECK3-NEXT: [[MUL_I:%.*]] = mul nsw i32 2, [[TMP16]] -// CHECK3-NEXT: [[TMP17:%.*]] = load ptr, ptr [[TMP9]], align 4 +// CHECK3-NEXT: [[TMP17:%.*]] = load ptr, ptr [[TMP9]], align 4, !nonnull [[META16:![0-9]+]], !align [[META17:![0-9]+]] // CHECK3-NEXT: [[TMP18:%.*]] = load ptr, ptr [[TMP17]], align 4 -// CHECK3-NEXT: [[TMP19:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META14]] +// CHECK3-NEXT: [[TMP19:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META15]] // CHECK3-NEXT: [[ARRAYIDX1_I:%.*]] = getelementptr inbounds i32, ptr [[TMP18]], i32 [[TMP19]] // CHECK3-NEXT: store i32 [[MUL_I]], ptr [[ARRAYIDX1_I]], align 4 -// CHECK3-NEXT: [[TMP20:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META14]] +// CHECK3-NEXT: [[TMP20:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META15]] // CHECK3-NEXT: [[INC_I:%.*]] = add nsw i32 [[TMP20]], 1 -// CHECK3-NEXT: store i32 [[INC_I]], ptr [[I_I]], align 4, !noalias [[META14]] -// CHECK3-NEXT: br label [[FOR_COND_I]], !llvm.loop [[LOOP15:![0-9]+]] +// CHECK3-NEXT: store i32 [[INC_I]], ptr [[I_I]], align 4, !noalias [[META15]] +// CHECK3-NEXT: br label [[FOR_COND_I]], !llvm.loop [[LOOP18:![0-9]+]] // CHECK3: .omp_outlined..exit: // CHECK3-NEXT: ret i32 0 // @@ -650,44 +701,44 @@ int main() { // CHECK9-NEXT: [[TMP6:%.*]] = getelementptr inbounds nuw [[STRUCT_KMP_TASK_T]], ptr [[TMP4]], i32 0, i32 0 // CHECK9-NEXT: [[TMP7:%.*]] = load ptr, ptr [[TMP6]], align 8 // CHECK9-NEXT: [[TMP8:%.*]] = getelementptr inbounds nuw [[STRUCT_KMP_TASK_T_WITH_PRIVATES]], ptr [[TMP3]], i32 0, i32 1 -// CHECK9-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META5:![0-9]+]]) -// CHECK9-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META8:![0-9]+]]) -// CHECK9-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META10:![0-9]+]]) -// CHECK9-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META12:![0-9]+]]) -// CHECK9-NEXT: store i32 [[TMP2]], ptr [[DOTGLOBAL_TID__ADDR_I]], align 4, !noalias [[META14:![0-9]+]] -// CHECK9-NEXT: store ptr [[TMP5]], ptr [[DOTPART_ID__ADDR_I]], align 8, !noalias [[META14]] -// CHECK9-NEXT: store ptr [[TMP8]], ptr [[DOTPRIVATES__ADDR_I]], align 8, !noalias [[META14]] -// CHECK9-NEXT: store ptr @.omp_task_privates_map., ptr [[DOTCOPY_FN__ADDR_I]], align 8, !noalias [[META14]] -// CHECK9-NEXT: store ptr [[TMP3]], ptr [[DOTTASK_T__ADDR_I]], align 8, !noalias [[META14]] -// CHECK9-NEXT: store ptr [[TMP7]], ptr [[__CONTEXT_ADDR_I]], align 8, !noalias [[META14]] -// CHECK9-NEXT: [[TMP9:%.*]] = load ptr, ptr [[__CONTEXT_ADDR_I]], align 8, !noalias [[META14]] -// CHECK9-NEXT: [[TMP10:%.*]] = load ptr, ptr [[DOTCOPY_FN__ADDR_I]], align 8, !noalias [[META14]] -// CHECK9-NEXT: [[TMP11:%.*]] = load ptr, ptr [[DOTPRIVATES__ADDR_I]], align 8, !noalias [[META14]] +// CHECK9-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META6:![0-9]+]]) +// CHECK9-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META9:![0-9]+]]) +// CHECK9-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META11:![0-9]+]]) +// CHECK9-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META13:![0-9]+]]) +// CHECK9-NEXT: store i32 [[TMP2]], ptr [[DOTGLOBAL_TID__ADDR_I]], align 4, !noalias [[META15:![0-9]+]] +// CHECK9-NEXT: store ptr [[TMP5]], ptr [[DOTPART_ID__ADDR_I]], align 8, !noalias [[META15]] +// CHECK9-NEXT: store ptr [[TMP8]], ptr [[DOTPRIVATES__ADDR_I]], align 8, !noalias [[META15]] +// CHECK9-NEXT: store ptr @.omp_task_privates_map., ptr [[DOTCOPY_FN__ADDR_I]], align 8, !noalias [[META15]] +// CHECK9-NEXT: store ptr [[TMP3]], ptr [[DOTTASK_T__ADDR_I]], align 8, !noalias [[META15]] +// CHECK9-NEXT: store ptr [[TMP7]], ptr [[__CONTEXT_ADDR_I]], align 8, !noalias [[META15]] +// CHECK9-NEXT: [[TMP9:%.*]] = load ptr, ptr [[__CONTEXT_ADDR_I]], align 8, !noalias [[META15]] +// CHECK9-NEXT: [[TMP10:%.*]] = load ptr, ptr [[DOTCOPY_FN__ADDR_I]], align 8, !noalias [[META15]] +// CHECK9-NEXT: [[TMP11:%.*]] = load ptr, ptr [[DOTPRIVATES__ADDR_I]], align 8, !noalias [[META15]] // CHECK9-NEXT: call void [[TMP10]](ptr [[TMP11]], ptr [[DOTFIRSTPRIV_PTR_ADDR_I]]) #[[ATTR3:[0-9]+]] -// CHECK9-NEXT: [[TMP12:%.*]] = load ptr, ptr [[DOTFIRSTPRIV_PTR_ADDR_I]], align 8, !noalias [[META14]] -// CHECK9-NEXT: store i32 0, ptr [[I_I]], align 4, !noalias [[META14]] +// CHECK9-NEXT: [[TMP12:%.*]] = load ptr, ptr [[DOTFIRSTPRIV_PTR_ADDR_I]], align 8, !noalias [[META15]] +// CHECK9-NEXT: store i32 0, ptr [[I_I]], align 4, !noalias [[META15]] // CHECK9-NEXT: br label [[FOR_COND_I:%.*]] // CHECK9: for.cond.i: -// CHECK9-NEXT: [[TMP13:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META14]] +// CHECK9-NEXT: [[TMP13:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META15]] // CHECK9-NEXT: [[CMP_I:%.*]] = icmp slt i32 [[TMP13]], 1024 // CHECK9-NEXT: br i1 [[CMP_I]], label [[FOR_BODY_I:%.*]], label [[DOTOMP_OUTLINED__EXIT:%.*]] // CHECK9: for.body.i: // CHECK9-NEXT: [[TMP14:%.*]] = load ptr, ptr [[TMP12]], align 8 -// CHECK9-NEXT: [[TMP15:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META14]] +// CHECK9-NEXT: [[TMP15:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META15]] // CHECK9-NEXT: [[IDXPROM_I:%.*]] = sext i32 [[TMP15]] to i64 // CHECK9-NEXT: [[ARRAYIDX_I:%.*]] = getelementptr inbounds i32, ptr [[TMP14]], i64 [[IDXPROM_I]] // CHECK9-NEXT: [[TMP16:%.*]] = load i32, ptr [[ARRAYIDX_I]], align 4 // CHECK9-NEXT: [[MUL_I:%.*]] = mul nsw i32 2, [[TMP16]] -// CHECK9-NEXT: [[TMP17:%.*]] = load ptr, ptr [[TMP9]], align 8 +// CHECK9-NEXT: [[TMP17:%.*]] = load ptr, ptr [[TMP9]], align 8, !nonnull [[META16:![0-9]+]], !align [[META17:![0-9]+]] // CHECK9-NEXT: [[TMP18:%.*]] = load ptr, ptr [[TMP17]], align 8 -// CHECK9-NEXT: [[TMP19:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META14]] +// CHECK9-NEXT: [[TMP19:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META15]] // CHECK9-NEXT: [[IDXPROM1_I:%.*]] = sext i32 [[TMP19]] to i64 // CHECK9-NEXT: [[ARRAYIDX2_I:%.*]] = getelementptr inbounds i32, ptr [[TMP18]], i64 [[IDXPROM1_I]] // CHECK9-NEXT: store i32 [[MUL_I]], ptr [[ARRAYIDX2_I]], align 4 -// CHECK9-NEXT: [[TMP20:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META14]] +// CHECK9-NEXT: [[TMP20:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META15]] // CHECK9-NEXT: [[INC_I:%.*]] = add nsw i32 [[TMP20]], 1 -// CHECK9-NEXT: store i32 [[INC_I]], ptr [[I_I]], align 4, !noalias [[META14]] -// CHECK9-NEXT: br label [[FOR_COND_I]], !llvm.loop [[LOOP15:![0-9]+]] +// CHECK9-NEXT: store i32 [[INC_I]], ptr [[I_I]], align 4, !noalias [[META15]] +// CHECK9-NEXT: br label [[FOR_COND_I]], !llvm.loop [[LOOP18:![0-9]+]] // CHECK9: .omp_outlined..exit: // CHECK9-NEXT: ret i32 0 // @@ -772,42 +823,42 @@ int main() { // CHECK11-NEXT: [[TMP6:%.*]] = getelementptr inbounds nuw [[STRUCT_KMP_TASK_T]], ptr [[TMP4]], i32 0, i32 0 // CHECK11-NEXT: [[TMP7:%.*]] = load ptr, ptr [[TMP6]], align 4 // CHECK11-NEXT: [[TMP8:%.*]] = getelementptr inbounds nuw [[STRUCT_KMP_TASK_T_WITH_PRIVATES]], ptr [[TMP3]], i32 0, i32 1 -// CHECK11-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META6:![0-9]+]]) -// CHECK11-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META9:![0-9]+]]) -// CHECK11-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META11:![0-9]+]]) -// CHECK11-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META13:![0-9]+]]) -// CHECK11-NEXT: store i32 [[TMP2]], ptr [[DOTGLOBAL_TID__ADDR_I]], align 4, !noalias [[META15:![0-9]+]] -// CHECK11-NEXT: store ptr [[TMP5]], ptr [[DOTPART_ID__ADDR_I]], align 4, !noalias [[META15]] -// CHECK11-NEXT: store ptr [[TMP8]], ptr [[DOTPRIVATES__ADDR_I]], align 4, !noalias [[META15]] -// CHECK11-NEXT: store ptr @.omp_task_privates_map., ptr [[DOTCOPY_FN__ADDR_I]], align 4, !noalias [[META15]] -// CHECK11-NEXT: store ptr [[TMP3]], ptr [[DOTTASK_T__ADDR_I]], align 4, !noalias [[META15]] -// CHECK11-NEXT: store ptr [[TMP7]], ptr [[__CONTEXT_ADDR_I]], align 4, !noalias [[META15]] -// CHECK11-NEXT: [[TMP9:%.*]] = load ptr, ptr [[__CONTEXT_ADDR_I]], align 4, !noalias [[META15]] -// CHECK11-NEXT: [[TMP10:%.*]] = load ptr, ptr [[DOTCOPY_FN__ADDR_I]], align 4, !noalias [[META15]] -// CHECK11-NEXT: [[TMP11:%.*]] = load ptr, ptr [[DOTPRIVATES__ADDR_I]], align 4, !noalias [[META15]] +// CHECK11-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META7:![0-9]+]]) +// CHECK11-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META10:![0-9]+]]) +// CHECK11-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META12:![0-9]+]]) +// CHECK11-NEXT: call void @llvm.experimental.noalias.scope.decl(metadata [[META14:![0-9]+]]) +// CHECK11-NEXT: store i32 [[TMP2]], ptr [[DOTGLOBAL_TID__ADDR_I]], align 4, !noalias [[META16:![0-9]+]] +// CHECK11-NEXT: store ptr [[TMP5]], ptr [[DOTPART_ID__ADDR_I]], align 4, !noalias [[META16]] +// CHECK11-NEXT: store ptr [[TMP8]], ptr [[DOTPRIVATES__ADDR_I]], align 4, !noalias [[META16]] +// CHECK11-NEXT: store ptr @.omp_task_privates_map., ptr [[DOTCOPY_FN__ADDR_I]], align 4, !noalias [[META16]] +// CHECK11-NEXT: store ptr [[TMP3]], ptr [[DOTTASK_T__ADDR_I]], align 4, !noalias [[META16]] +// CHECK11-NEXT: store ptr [[TMP7]], ptr [[__CONTEXT_ADDR_I]], align 4, !noalias [[META16]] +// CHECK11-NEXT: [[TMP9:%.*]] = load ptr, ptr [[__CONTEXT_ADDR_I]], align 4, !noalias [[META16]] +// CHECK11-NEXT: [[TMP10:%.*]] = load ptr, ptr [[DOTCOPY_FN__ADDR_I]], align 4, !noalias [[META16]] +// CHECK11-NEXT: [[TMP11:%.*]] = load ptr, ptr [[DOTPRIVATES__ADDR_I]], align 4, !noalias [[META16]] // CHECK11-NEXT: call void [[TMP10]](ptr [[TMP11]], ptr [[DOTFIRSTPRIV_PTR_ADDR_I]]) #[[ATTR3:[0-9]+]] -// CHECK11-NEXT: [[TMP12:%.*]] = load ptr, ptr [[DOTFIRSTPRIV_PTR_ADDR_I]], align 4, !noalias [[META15]] -// CHECK11-NEXT: store i32 0, ptr [[I_I]], align 4, !noalias [[META15]] +// CHECK11-NEXT: [[TMP12:%.*]] = load ptr, ptr [[DOTFIRSTPRIV_PTR_ADDR_I]], align 4, !noalias [[META16]] +// CHECK11-NEXT: store i32 0, ptr [[I_I]], align 4, !noalias [[META16]] // CHECK11-NEXT: br label [[FOR_COND_I:%.*]] // CHECK11: for.cond.i: -// CHECK11-NEXT: [[TMP13:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META15]] +// CHECK11-NEXT: [[TMP13:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META16]] // CHECK11-NEXT: [[CMP_I:%.*]] = icmp slt i32 [[TMP13]], 1024 // CHECK11-NEXT: br i1 [[CMP_I]], label [[FOR_BODY_I:%.*]], label [[DOTOMP_OUTLINED__EXIT:%.*]] // CHECK11: for.body.i: // CHECK11-NEXT: [[TMP14:%.*]] = load ptr, ptr [[TMP12]], align 4 -// CHECK11-NEXT: [[TMP15:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META15]] +// CHECK11-NEXT: [[TMP15:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META16]] // CHECK11-NEXT: [[ARRAYIDX_I:%.*]] = getelementptr inbounds i32, ptr [[TMP14]], i32 [[TMP15]] // CHECK11-NEXT: [[TMP16:%.*]] = load i32, ptr [[ARRAYIDX_I]], align 4 // CHECK11-NEXT: [[MUL_I:%.*]] = mul nsw i32 2, [[TMP16]] -// CHECK11-NEXT: [[TMP17:%.*]] = load ptr, ptr [[TMP9]], align 4 +// CHECK11-NEXT: [[TMP17:%.*]] = load ptr, ptr [[TMP9]], align 4, !nonnull [[META17:![0-9]+]], !align [[META18:![0-9]+]] // CHECK11-NEXT: [[TMP18:%.*]] = load ptr, ptr [[TMP17]], align 4 -// CHECK11-NEXT: [[TMP19:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META15]] +// CHECK11-NEXT: [[TMP19:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META16]] // CHECK11-NEXT: [[ARRAYIDX1_I:%.*]] = getelementptr inbounds i32, ptr [[TMP18]], i32 [[TMP19]] // CHECK11-NEXT: store i32 [[MUL_I]], ptr [[ARRAYIDX1_I]], align 4 -// CHECK11-NEXT: [[TMP20:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META15]] +// CHECK11-NEXT: [[TMP20:%.*]] = load i32, ptr [[I_I]], align 4, !noalias [[META16]] // CHECK11-NEXT: [[INC_I:%.*]] = add nsw i32 [[TMP20]], 1 -// CHECK11-NEXT: store i32 [[INC_I]], ptr [[I_I]], align 4, !noalias [[META15]] -// CHECK11-NEXT: br label [[FOR_COND_I]], !llvm.loop [[LOOP16:![0-9]+]] +// CHECK11-NEXT: store i32 [[INC_I]], ptr [[I_I]], align 4, !noalias [[META16]] +// CHECK11-NEXT: br label [[FOR_COND_I]], !llvm.loop [[LOOP19:![0-9]+]] // CHECK11: .omp_outlined..exit: // CHECK11-NEXT: ret i32 0 // diff --git a/llvm/include/llvm/Frontend/OpenMP/OMPConstants.h b/llvm/include/llvm/Frontend/OpenMP/OMPConstants.h index 6e1bce12af8e4..7bec7e0c6736d 100644 --- a/llvm/include/llvm/Frontend/OpenMP/OMPConstants.h +++ b/llvm/include/llvm/Frontend/OpenMP/OMPConstants.h @@ -239,6 +239,9 @@ enum class OpenMPOffloadMappingFlags : uint64_t { // dynamic. // This is an OpenMP extension for the sake of OpenACC support. OMP_MAP_OMPX_HOLD = 0x2000, + // Attach pointer and pointee, after processing all other maps. + // Applicable to map-entering directives. Does not change ref-count. + OMP_MAP_ATTACH = 0x4000, /// Signal that the runtime library should use args as an array of /// descriptor_dim pointers and use args_size as dims. Used when we have /// non-contiguous list items in target update directive diff --git a/llvm/lib/Frontend/OpenMP/OMPIRBuilder.cpp b/llvm/lib/Frontend/OpenMP/OMPIRBuilder.cpp index db792a3b52d24..ff9317f42e54c 100644 --- a/llvm/lib/Frontend/OpenMP/OMPIRBuilder.cpp +++ b/llvm/lib/Frontend/OpenMP/OMPIRBuilder.cpp @@ -9861,6 +9861,12 @@ void OpenMPIRBuilder::setCorrectMemberOfFlag( omp::OpenMPOffloadMappingFlags::OMP_MAP_MEMBER_OF)) return; + // Entries with ATTACH are not members-of anything. They are handled + // separately by the runtime after other maps have been handled. + if (static_cast>( + Flags & omp::OpenMPOffloadMappingFlags::OMP_MAP_ATTACH)) + return; + // Reset the placeholder value to prepare the flag for the assignment of the // proper MEMBER_OF value. Flags &= ~omp::OpenMPOffloadMappingFlags::OMP_MAP_MEMBER_OF; diff --git a/offload/include/OpenMP/Mapping.h b/offload/include/OpenMP/Mapping.h index b9f5c16582931..93c1e56905ae4 100644 --- a/offload/include/OpenMP/Mapping.h +++ b/offload/include/OpenMP/Mapping.h @@ -417,12 +417,42 @@ struct MapperComponentsTy { typedef void (*MapperFuncPtrTy)(void *, void *, void *, int64_t, int64_t, void *); +/// Structure to store information about a single ATTACH map entry. +struct AttachMapInfo { + void *PointerBase; + void *PointeeBegin; + int64_t PointerSize; + int64_t MapType; + map_var_info_t Pointername; + + AttachMapInfo(void *PointerBase, void *PointeeBegin, int64_t Size, + int64_t Type, map_var_info_t Name) + : PointerBase(PointerBase), PointeeBegin(PointeeBegin), PointerSize(Size), + MapType(Type), Pointername(Name) {} +}; + +/// Structure to track ATTACH entries and new allocations across recursive calls +/// (for handling mappers) to targetDataBegin for a given construct. +struct AttachInfoTy { + /// ATTACH map entries for deferred processing. + llvm::SmallVector AttachEntries; + + /// Key: host pointer, Value: allocation size. + llvm::DenseMap NewAllocations; + + AttachInfoTy() = default; + + // Delete copy constructor and copy assignment operator to prevent copying + AttachInfoTy(const AttachInfoTy &) = delete; + AttachInfoTy &operator=(const AttachInfoTy &) = delete; +}; + // Function pointer type for targetData* functions (targetDataBegin, // targetDataEnd and targetDataUpdate). typedef int (*TargetDataFuncPtrTy)(ident_t *, DeviceTy &, int32_t, void **, void **, int64_t *, int64_t *, map_var_info_t *, void **, AsyncInfoTy &, - bool); + AttachInfoTy *, bool); void dumpTargetPointerMappings(const ident_t *Loc, DeviceTy &Device, bool toStdOut = false); @@ -431,20 +461,26 @@ int targetDataBegin(ident_t *Loc, DeviceTy &Device, int32_t ArgNum, void **ArgsBase, void **Args, int64_t *ArgSizes, int64_t *ArgTypes, map_var_info_t *ArgNames, void **ArgMappers, AsyncInfoTy &AsyncInfo, + AttachInfoTy *AttachInfo = nullptr, bool FromMapper = false); int targetDataEnd(ident_t *Loc, DeviceTy &Device, int32_t ArgNum, void **ArgBases, void **Args, int64_t *ArgSizes, int64_t *ArgTypes, map_var_info_t *ArgNames, void **ArgMappers, AsyncInfoTy &AsyncInfo, - bool FromMapper = false); + AttachInfoTy *AttachInfo = nullptr, bool FromMapper = false); int targetDataUpdate(ident_t *Loc, DeviceTy &Device, int32_t ArgNum, void **ArgsBase, void **Args, int64_t *ArgSizes, int64_t *ArgTypes, map_var_info_t *ArgNames, void **ArgMappers, AsyncInfoTy &AsyncInfo, + AttachInfoTy *AttachInfo = nullptr, bool FromMapper = false); +// Process deferred ATTACH map entries collected during targetDataBegin. +int processAttachEntries(DeviceTy &Device, AttachInfoTy &AttachInfo, + AsyncInfoTy &AsyncInfo); + struct MappingInfoTy { MappingInfoTy(DeviceTy &Device) : Device(Device) {} diff --git a/offload/include/omptarget.h b/offload/include/omptarget.h index 6971780c7bdb5..9e4bfd2f9cfbe 100644 --- a/offload/include/omptarget.h +++ b/offload/include/omptarget.h @@ -80,6 +80,9 @@ enum tgt_map_type { // the structured region // This is an OpenMP extension for the sake of OpenACC support. OMP_TGT_MAPTYPE_OMPX_HOLD = 0x2000, + // Attach pointer and pointee, after processing all other maps. + // Applicable to map-entering directives. Does not change ref-count. + OMP_TGT_MAPTYPE_ATTACH = 0x4000, // descriptor for non-contiguous target-update OMP_TGT_MAPTYPE_NON_CONTIG = 0x100000000000, // member of struct, member given by [16 MSBs] - 1 diff --git a/offload/libomptarget/interface.cpp b/offload/libomptarget/interface.cpp index ea354400f2e99..16e46e6d23872 100644 --- a/offload/libomptarget/interface.cpp +++ b/offload/libomptarget/interface.cpp @@ -165,12 +165,28 @@ targetData(ident_t *Loc, int64_t DeviceId, int32_t ArgNum, void **ArgsBase, OMPT_GET_RETURN_ADDRESS);) int Rc = OFFLOAD_SUCCESS; + + // Only allocate AttachInfo for targetDataBegin + AttachInfoTy *AttachInfo = nullptr; + if (TargetDataFunction == targetDataBegin) { + AttachInfo = new AttachInfoTy(); + } + Rc = TargetDataFunction(Loc, *DeviceOrErr, ArgNum, ArgsBase, Args, ArgSizes, ArgTypes, ArgNames, ArgMappers, AsyncInfo, - false /*FromMapper=*/); + AttachInfo, false /*FromMapper=*/); - if (Rc == OFFLOAD_SUCCESS) - Rc = AsyncInfo.synchronize(); + if (Rc == OFFLOAD_SUCCESS) { + // Process deferred ATTACH entries BEFORE synchronization + if (AttachInfo && !AttachInfo->AttachEntries.empty()) + Rc = processAttachEntries(*DeviceOrErr, *AttachInfo, AsyncInfo); + + if (Rc == OFFLOAD_SUCCESS) + Rc = AsyncInfo.synchronize(); + } + + if (AttachInfo) + delete AttachInfo; handleTargetOutcome(Rc == OFFLOAD_SUCCESS, Loc); } diff --git a/offload/libomptarget/omptarget.cpp b/offload/libomptarget/omptarget.cpp index 5b25d955dd320..aa142814e8384 100644 --- a/offload/libomptarget/omptarget.cpp +++ b/offload/libomptarget/omptarget.cpp @@ -293,7 +293,8 @@ void targetUnlockExplicit(void *HostPtr, int DeviceNum, const char *Name) { int targetDataMapper(ident_t *Loc, DeviceTy &Device, void *ArgBase, void *Arg, int64_t ArgSize, int64_t ArgType, map_var_info_t ArgNames, void *ArgMapper, AsyncInfoTy &AsyncInfo, - TargetDataFuncPtrTy TargetDataFunction) { + TargetDataFuncPtrTy TargetDataFunction, + AttachInfoTy *AttachInfo = nullptr) { DP("Calling the mapper function " DPxMOD "\n", DPxPTR(ArgMapper)); // The mapper function fills up Components. @@ -324,17 +325,196 @@ int targetDataMapper(ident_t *Loc, DeviceTy &Device, void *ArgBase, void *Arg, MapperArgsBase.data(), MapperArgs.data(), MapperArgSizes.data(), MapperArgTypes.data(), MapperArgNames.data(), /*arg_mappers*/ nullptr, - AsyncInfo, /*FromMapper=*/true); + AsyncInfo, AttachInfo, /*FromMapper=*/true); return Rc; } +/// Utility function to perform a pointer attachment operation. +/// +/// For something like: +/// \code +/// int *p; +/// ... +/// #pragma omp target enter data map(to:p[10:10]) +/// \endcode +/// +/// for which the attachment operation gets represented using: +/// \code +/// &p, &p[10], sizeof(p), ATTACH +/// \endcode +/// +/// (Hst|Tgt)PtrAddr represents &p +/// (Hst|Tgt)PteeBase represents &p[0] +/// (Hst|Tgt)PteeBegin represents &p[10] +/// +/// This function first computes the expected TgtPteeBase using: +/// TgtPteeBase = TgtPteeBegin - (HstPteeBegin - HstPteeBase) +/// +/// and then attaches TgtPteeBase to TgtPtrAddr. +/// +/// \p HstPtrSize represents the size of the pointer p. For C/C++, this +/// should be same as "sizeof(void*)" (say 8). +/// +/// However, for Fortran, pointers/allocatables, which are also eligible for +/// "pointer-attachment", may be implemented using descriptors that contain the +/// address of the pointee in the first 8 bytes, but also contain other +/// information such as lower-bound/upper-bound etc in their subsequent fields. +/// +/// For example, for the following: +/// \code +/// integer, allocatable :: x(:) +/// integer, pointer :: p(:) +/// ... +/// p => x(10: 19) +/// ... +/// !$omp target enter data map(to:p(:)) +/// \endcode +/// +/// The map should trigger a pointer-attachment (assuming the pointer-attachment +/// conditions as noted on processAttachEntries are met) between the descriptor +/// for p, and its pointee data. +/// +/// Since only the first 8 bytes of the descriptor contain the address of the +/// pointee, an attachment operation on device descriptors involves: +/// * Setting the first 8 bytes of the device descriptor to point the device +/// address of the pointee. +/// * Copying the remaining information about bounds/offset etc. from the host +/// descriptor to the device descriptor. +/// +/// The function also handles pointer-attachment portion of PTR_AND_OBJ maps, +/// like: +/// \code +/// &p, &p[10], 10 * sizeof(p[10]), PTR_AND_OBJ +/// \endcoe +/// by using "sizeof(void*)" as \p HstPtrSize. +static int performPointerAttachment(DeviceTy &Device, AsyncInfoTy &AsyncInfo, + void **HstPtrAddr, void *HstPteeBase, + void *HstPteeBegin, void **TgtPtrAddr, + void *TgtPteeBegin, int64_t HstPtrSize, + TargetPointerResultTy &PtrTPR) { + assert(PtrTPR.getEntry() && + "Need a valid pointer entry to perform pointer-attachment"); + + int64_t VoidPtrSize = sizeof(void *); + assert(HstPtrSize >= VoidPtrSize && "PointerSize is too small"); + + uint64_t Delta = (uint64_t)HstPteeBegin - (uint64_t)HstPteeBase; + void *TgtPteeBase = (void *)((uint64_t)TgtPteeBegin - Delta); + + // Add shadow pointer tracking + // TODO: Support shadow-tracking of larger than VoidPtrSize pointers, + // to support restoration of Fortran descriptors. Currently, this check + // would return false, even if the host Fortran descriptor was, and we + // should have done an update of the device descriptor. e.g. + // + // !$omp target enter data map(x(1:100)) ! (1) + // p => x(10: 19) + // !$omp target enter data map(p, p(:)) ! (2) + // p => x(5: 9) + // !$omp target enter data map(attach(always): p(:)) ! (3) + // + // While PtrAddr(&desc_p) and PteeBase(&p(1)) are same for (2) and (3), the + // pointer attachment for (3) needs to update the bounds information + // in the descriptor of p on device. + if (!PtrTPR.getEntry()->addShadowPointer( + ShadowPtrInfoTy{HstPtrAddr, HstPteeBase, TgtPtrAddr, TgtPteeBase})) + return OFFLOAD_SUCCESS; + + DP("Update pointer (" DPxMOD ") -> [" DPxMOD "]\n", DPxPTR(TgtPtrAddr), + DPxPTR(TgtPteeBase)); + + // Lambda to handle submitData result and perform final steps. + auto HandleSubmitResult = [&](int SubmitResult) -> int { + if (SubmitResult != OFFLOAD_SUCCESS) { + REPORT("Failed to update pointer on device.\n"); + return OFFLOAD_FAIL; + } + + if (PtrTPR.getEntry()->addEventIfNecessary(Device, AsyncInfo) != + OFFLOAD_SUCCESS) + return OFFLOAD_FAIL; + + return OFFLOAD_SUCCESS; + }; + + bool IsPtrAFortranDescriptor = HstPtrSize > VoidPtrSize; + if (!IsPtrAFortranDescriptor) { + // For "regular" pointers, we can use the VoidPtrLocation from AsyncInfo as + // the buffer space for the submission. + void *&BufferElement = AsyncInfo.getVoidPtrLocation(); + BufferElement = TgtPteeBase; + + // Submit the updated pointer value to device + return HandleSubmitResult(Device.submitData( + TgtPtrAddr, &BufferElement, VoidPtrSize, AsyncInfo, PtrTPR.getEntry())); + } + + // For larger "pointers" (like Fortran's descriptors), we create a dynamic + // buffer, which will be eventually destroyed by AsyncInfo's post-processing + // callback. + char *DataBuffer = new char[HstPtrSize]; + + // For such descriptors, to the first VoidPtrSize bytes, we store the + // pointee's device address. + std::memcpy(DataBuffer, &TgtPteeBase, sizeof(void *)); + + // And to the remaining bytes, we copy the remaining contents of the host + // descriptor after the initial VoidPtrSize bytes. + uint64_t HstDescriptorFieldsSize = HstPtrSize - VoidPtrSize; + void *HstDescriptorFieldsAddr = (char *)HstPtrAddr + VoidPtrSize; + std::memcpy(DataBuffer + VoidPtrSize, HstDescriptorFieldsAddr, + HstDescriptorFieldsSize); + + DP("Updating %" PRId64 " bytes of descriptor (" DPxMOD ") (pointer + %" PRId64 + " additional bytes from host descriptor " DPxMOD ")\n", + HstPtrSize, DPxPTR(TgtPtrAddr), HstDescriptorFieldsSize, + DPxPTR(HstDescriptorFieldsAddr)); + + // Submit the entire buffer to device + // FIXME: When handling ATTACH map-type, pointer attachment needs to happen + // after the other mapping operations are done, to avoid possibility of + // pending transfers clobbering the attachment, for example: + // + // int *p = ...; + // int **pp = &p; + // map(to: pp[0], p[0]) + // + // Which would be represented by: + // &pp[0], &pp[0], sizeof(pp[0]), TO (1) + // &p[0], &p[0], sizeof(p[0]), TO (2) + // + // &pp, &pp[0], sizeof(pp), ATTACH (3) + // &p, &p[0], sizeof(p), ATTACH (4) + // + // (4) and (1) are both trying to modify the device memory corresponding to + // &p. We need to ensure that (4) happens last. + // + // One possible solution to this could be to insert a "device barrier" before + // the first ATTACH submitData call, so that every subsequent submitData waits + // for any prior operations to finish. Like: + // Device.submitData(..., /*InOrder=*/IsFirstAttachEntry) + // Where the boolean InOrder being true means that this submission should + // wait for prior memory submissions to finish. + int SubmitResult = + Device.submitData(TgtPtrAddr, DataBuffer, HstPtrSize, AsyncInfo, + PtrTPR.getEntry()); + + AsyncInfo.addPostProcessingFunction([DataBuffer]() -> int { + delete[] DataBuffer; + return OFFLOAD_SUCCESS; + }); + return HandleSubmitResult(SubmitResult); +} + /// Internal function to do the mapping and transfer the data to the device int targetDataBegin(ident_t *Loc, DeviceTy &Device, int32_t ArgNum, void **ArgsBase, void **Args, int64_t *ArgSizes, int64_t *ArgTypes, map_var_info_t *ArgNames, void **ArgMappers, AsyncInfoTy &AsyncInfo, - bool FromMapper) { + AttachInfoTy *AttachInfo, bool FromMapper) { + assert(AttachInfo && "AttachInfo must be available for targetDataBegin for " + "handling ATTACH map-types."); // process each input. for (int32_t I = 0; I < ArgNum; ++I) { // Ignore private variables and arrays - there is no mapping for them. @@ -352,7 +532,7 @@ int targetDataBegin(ident_t *Loc, DeviceTy &Device, int32_t ArgNum, map_var_info_t ArgName = (!ArgNames) ? nullptr : ArgNames[I]; int Rc = targetDataMapper(Loc, Device, ArgsBase[I], Args[I], ArgSizes[I], ArgTypes[I], ArgName, ArgMappers[I], AsyncInfo, - targetDataBegin); + targetDataBegin, AttachInfo); if (Rc != OFFLOAD_SUCCESS) { REPORT("Call to targetDataBegin via targetDataMapper for custom mapper" @@ -369,6 +549,18 @@ int targetDataBegin(ident_t *Loc, DeviceTy &Device, int32_t ArgNum, int64_t DataSize = ArgSizes[I]; map_var_info_t HstPtrName = (!ArgNames) ? nullptr : ArgNames[I]; + // ATTACH map-types are supposed to be handled after all mapping for the + // construct is done. Defer their processing. + if (ArgTypes[I] & OMP_TGT_MAPTYPE_ATTACH) { + AttachInfo->AttachEntries.emplace_back( + /*PointerBase=*/HstPtrBase, /*PointeeBegin=*/HstPtrBegin, + /*PointerSize=*/DataSize, /*MapType=*/ArgTypes[I], + /*PointeeName=*/HstPtrName); + + DP("Deferring ATTACH map-type processing for argument %d\n", I); + continue; + } + // Adjust for proper alignment if this is a combined entry (for structs). // Look at the next argument - if that is MEMBER_OF this one, then this one // is a combined entry. @@ -434,6 +626,11 @@ int targetDataBegin(ident_t *Loc, DeviceTy &Device, int32_t ArgNum, : "device failure or illegal mapping"); return OFFLOAD_FAIL; } + + // Track new allocation, for eventual use in attachment decision-making. + if (PointerTpr.Flags.IsNewEntry && !IsHostPtr) + AttachInfo->NewAllocations[HstPtrBase] = sizeof(void *); + DP("There are %zu bytes allocated at target address " DPxMOD " - is%s new" "\n", sizeof(void *), DPxPTR(PointerTgtPtrBegin), @@ -464,6 +661,11 @@ int targetDataBegin(ident_t *Loc, DeviceTy &Device, int32_t ArgNum, : "device failure or illegal mapping"); return OFFLOAD_FAIL; } + + // Track new allocation, for eventual use in attachment decision-making. + if (TPR.Flags.IsNewEntry && !IsHostPtr && TgtPtrBegin) + AttachInfo->NewAllocations[HstPtrBegin] = DataSize; + DP("There are %" PRId64 " bytes allocated at target address " DPxMOD " - is%s new\n", DataSize, DPxPTR(TgtPtrBegin), (TPR.Flags.IsNewEntry ? "" : " not")); @@ -476,30 +678,12 @@ int targetDataBegin(ident_t *Loc, DeviceTy &Device, int32_t ArgNum, } if (ArgTypes[I] & OMP_TGT_MAPTYPE_PTR_AND_OBJ && !IsHostPtr) { - - uint64_t Delta = (uint64_t)HstPtrBegin - (uint64_t)HstPtrBase; - void *ExpectedTgtPtrBase = (void *)((uint64_t)TgtPtrBegin - Delta); - - if (PointerTpr.getEntry()->addShadowPointer(ShadowPtrInfoTy{ - (void **)PointerHstPtrBegin, HstPtrBase, - (void **)PointerTgtPtrBegin, ExpectedTgtPtrBase})) { - DP("Update pointer (" DPxMOD ") -> [" DPxMOD "]\n", - DPxPTR(PointerTgtPtrBegin), DPxPTR(TgtPtrBegin)); - - void *&TgtPtrBase = AsyncInfo.getVoidPtrLocation(); - TgtPtrBase = ExpectedTgtPtrBase; - - int Ret = - Device.submitData(PointerTgtPtrBegin, &TgtPtrBase, sizeof(void *), - AsyncInfo, PointerTpr.getEntry()); - if (Ret != OFFLOAD_SUCCESS) { - REPORT("Copying data to device failed.\n"); - return OFFLOAD_FAIL; - } - if (PointerTpr.getEntry()->addEventIfNecessary(Device, AsyncInfo) != - OFFLOAD_SUCCESS) - return OFFLOAD_FAIL; - } + int Ret = performPointerAttachment(Device, AsyncInfo, + (void **)PointerHstPtrBegin, HstPtrBase, HstPtrBegin, + (void **)PointerTgtPtrBegin, TgtPtrBegin, + sizeof(void *), PointerTpr); + if (Ret != OFFLOAD_SUCCESS) + return OFFLOAD_FAIL; } // Check if variable can be used on the device: @@ -515,6 +699,145 @@ int targetDataBegin(ident_t *Loc, DeviceTy &Device, int32_t ArgNum, return OFFLOAD_SUCCESS; } +/// Process deferred ATTACH map entries collected during targetDataBegin. +/// +/// From OpenMP's perspective, when mapping something that has a base pointer, +/// such as: +/// \code +/// int *p; +/// #pragma omp enter target data map(to: p[10:20]) +/// \endcode +/// +/// a pointer-attachment between p and &p[10] should occur if both p and +/// p[10] are present on the device after doing all allocations for all maps +/// on the construct, and one of the following is true: +/// +/// * The pointer p was newly allocated while handling the construct +/// * The pointee p[10:20] was newly allocated while handling the construct +/// * attach(always) map-type modifier was specified (OpenMP 6.1) +/// +/// That's why we collect all attach entries and new memory allocations during +/// targetDataBegin, and use that information to make the decision of whether +/// to perform a pointer-attachment or not here, after maps have been handled. +int processAttachEntries(DeviceTy &Device, AttachInfoTy &AttachInfo, + AsyncInfoTy &AsyncInfo) { + // Report all tracked allocations from both main loop and ATTACH processing + if (!AttachInfo.NewAllocations.empty()) { + DP("Tracked %u total new allocations:\n", + (unsigned)AttachInfo.NewAllocations.size()); + for (const auto &Alloc : AttachInfo.NewAllocations) { + DP(" Host ptr: " DPxMOD ", Size: %" PRId64 " bytes\n", + DPxPTR(Alloc.first), Alloc.second); + } + } + + if (AttachInfo.AttachEntries.empty()) + return OFFLOAD_SUCCESS; + + DP("Processing %zu deferred ATTACH map entries\n", + AttachInfo.AttachEntries.size()); + + for (size_t EntryIdx = 0; EntryIdx < AttachInfo.AttachEntries.size(); + ++EntryIdx) { + const auto &AttachEntry = AttachInfo.AttachEntries[EntryIdx]; + + void **HstPtr = (void **)AttachEntry.PointerBase; + + void *HstPteeBase = *HstPtr; + void *HstPteeBegin = AttachEntry.PointeeBegin; + + int64_t PtrSize = AttachEntry.PointerSize; + int64_t MapType = AttachEntry.MapType; + + DP("Processing ATTACH entry %zu: HstPtr=" DPxMOD ", HstPteeBegin=" DPxMOD + ", Size=%" PRId64 ", Type=0x%" PRIx64 "\n", + EntryIdx, DPxPTR(HstPtr), DPxPTR(HstPteeBegin), PtrSize, MapType); + + const bool IsAttachAlways = MapType & OMP_TGT_MAPTYPE_ALWAYS; + + // Lambda to check if a pointer was newly allocated + auto WasNewlyAllocated = [&](void *Ptr, const char *PtrName) { + bool IsNewlyAllocated = + llvm::any_of(AttachInfo.NewAllocations, [&](const auto &Alloc) { + void *AllocPtr = Alloc.first; + int64_t AllocSize = Alloc.second; + return Ptr >= AllocPtr && + Ptr < (void *)((char *)AllocPtr + AllocSize); + }); + DP("ATTACH entry %zu: %s pointer " DPxMOD " was newly allocated: %s\n", + EntryIdx, PtrName, DPxPTR(Ptr), IsNewlyAllocated ? "yes" : "no"); + return IsNewlyAllocated; + }; + + // Only process ATTACH if base/begin was newly allocated OR ALWAYS flag is + // set + if (!IsAttachAlways && !WasNewlyAllocated(HstPtr, "pointer") && + !WasNewlyAllocated(HstPteeBegin, "pointee")) { + DP("Skipping ATTACH entry %zu: neither pointer nor pointee was newly " + "allocated and no ALWAYS flag\n", + EntryIdx); + continue; + } + + DP("Processing ATTACH entry %zu: Always=%s\n", EntryIdx, + IsAttachAlways ? "yes" : "no"); + + // Lambda to perform target pointer lookup and validation + auto LookupTargetPointer = [&](void *Ptr, int64_t Size, const char *PtrType) + -> std::optional { + // ATTACH map-type does not change ref-count, or do any allocation + // We just need to do a lookup for the pointer/pointee. + TargetPointerResultTy TPR = Device.getMappingInfo().getTgtPtrBegin( + Ptr, Size, /*UpdateRefCount=*/false, + /*UseHoldRefCount=*/false, /*MustContain=*/true); + + DP("ATTACH entry %zu: %s lookup - HstPtr=" DPxMOD ", TgtPtr=" DPxMOD + ", IsPresent=%s, IsHostPtr=%s\n", + EntryIdx, PtrType, DPxPTR(Ptr), DPxPTR(TPR.TargetPointer), + TPR.isPresent() ? "yes" : "no", + TPR.Flags.IsHostPointer ? "yes" : "no"); + + if (!TPR.isPresent()) { + DP("Skipping ATTACH entry %zu: %s not present on device\n", EntryIdx, + PtrType); + return std::nullopt; + } + if (TPR.Flags.IsHostPointer) { + DP("Skipping ATTACH entry %zu: device version of the %s is a host " + "pointer.\n", + EntryIdx, PtrType); + return std::nullopt; + } + + return TPR; + }; + + // Get device version of the pointer (e.g., &p) + auto PtrTPROpt = LookupTargetPointer(HstPtr, PtrSize, "pointer"); + if (!PtrTPROpt) + continue; + TargetPointerResultTy &PtrTPR = *PtrTPROpt; + void **TgtPtrBase = (void **)PtrTPR.TargetPointer; + + // Get device version of the pointee (e.g., &p[10]) + auto PteeTPROpt = LookupTargetPointer(HstPteeBegin, 0, "pointee"); + if (!PteeTPROpt) + continue; + void *TgtPteeBegin = PteeTPROpt->TargetPointer; + + // Update the device pointer to point to device pointee. + int Ret = performPointerAttachment(Device, AsyncInfo, HstPtr, HstPteeBase, + HstPteeBegin, TgtPtrBase, TgtPteeBegin, + PtrSize, PtrTPR); + if (Ret != OFFLOAD_SUCCESS) + return OFFLOAD_FAIL; + + DP("ATTACH entry %zu processed successfully\n", EntryIdx); + } + + return OFFLOAD_SUCCESS; +} + namespace { /// This structure contains information to deallocate a target pointer, aka. /// used to fix up the shadow map and potentially delete the entry from the @@ -624,7 +947,8 @@ postProcessingTargetDataEnd(DeviceTy *Device, int targetDataEnd(ident_t *Loc, DeviceTy &Device, int32_t ArgNum, void **ArgBases, void **Args, int64_t *ArgSizes, int64_t *ArgTypes, map_var_info_t *ArgNames, - void **ArgMappers, AsyncInfoTy &AsyncInfo, bool FromMapper) { + void **ArgMappers, AsyncInfoTy &AsyncInfo, + AttachInfoTy *AttachInfo, bool FromMapper) { int Ret = OFFLOAD_SUCCESS; auto *PostProcessingPtrs = new SmallVector(); // process each input. @@ -635,6 +959,14 @@ int targetDataEnd(ident_t *Loc, DeviceTy &Device, int32_t ArgNum, (ArgTypes[I] & OMP_TGT_MAPTYPE_PRIVATE)) continue; + // Ignore ATTACH entries - they should only be honored on map-entering + // directives. They may be encountered here while handling the "end" part of + // "#pragma omp target". + if (ArgTypes[I] & OMP_TGT_MAPTYPE_ATTACH) { + DP("Ignoring ATTACH entry %d in targetDataEnd\n", I); + continue; + } + if (ArgMappers && ArgMappers[I]) { // Instead of executing the regular path of targetDataEnd, call the // targetDataMapper variant which will call targetDataEnd again @@ -900,7 +1232,8 @@ static int getNonContigMergedDimension(__tgt_target_non_contig *NonContig, int targetDataUpdate(ident_t *Loc, DeviceTy &Device, int32_t ArgNum, void **ArgsBase, void **Args, int64_t *ArgSizes, int64_t *ArgTypes, map_var_info_t *ArgNames, - void **ArgMappers, AsyncInfoTy &AsyncInfo, bool) { + void **ArgMappers, AsyncInfoTy &AsyncInfo, + AttachInfoTy *AttachInfo, bool FromMapper) { // process each input. for (int32_t I = 0; I < ArgNum; ++I) { if ((ArgTypes[I] & OMP_TGT_MAPTYPE_LITERAL) || @@ -1213,13 +1546,27 @@ static int processDataBefore(ident_t *Loc, int64_t DeviceId, void *HostPtr, if (!DeviceOrErr) FATAL_MESSAGE(DeviceId, "%s", toString(DeviceOrErr.takeError()).c_str()); + // Create AttachInfo for tracking any ATTACH entries, or new-allocations + // when handling the "begin" mapping for a target constructs. + AttachInfoTy AttachInfo; + int Ret = targetDataBegin(Loc, *DeviceOrErr, ArgNum, ArgBases, Args, ArgSizes, - ArgTypes, ArgNames, ArgMappers, AsyncInfo); + ArgTypes, ArgNames, ArgMappers, AsyncInfo, + &AttachInfo, false /*FromMapper=*/); if (Ret != OFFLOAD_SUCCESS) { REPORT("Call to targetDataBegin failed, abort target.\n"); return OFFLOAD_FAIL; } + // Process collected ATTACH entries + if (!AttachInfo.AttachEntries.empty()) { + Ret = processAttachEntries(*DeviceOrErr, AttachInfo, AsyncInfo); + if (Ret != OFFLOAD_SUCCESS) { + REPORT("Failed to process ATTACH entries.\n"); + return OFFLOAD_FAIL; + } + } + // List of (first-)private arrays allocated for this target region SmallVector TgtArgsPositions(ArgNum, -1); diff --git a/offload/test/mapping/map_ptr_and_star_local.c b/offload/test/mapping/map_ptr_and_star_local.c index 0d2d689ec9912..ca7c4d0f98f7e 100644 --- a/offload/test/mapping/map_ptr_and_star_local.c +++ b/offload/test/mapping/map_ptr_and_star_local.c @@ -46,8 +46,7 @@ void f1() { { printf("%d %d %d %d\n", p[0], p_mappedptr == &p, x0_mappedptr == &p[0], x0_hostaddr == &p[0]); - // EXPECTED: 111 1 1 0 - // CHECK: 111 1 0 1 + // CHECK: 111 1 1 0 p++; } @@ -56,8 +55,7 @@ void f1() { { printf("%d %d %d %d\n", p[0], p_mappedptr == &p, x0_mappedptr == &p[-1], x0_hostaddr == &p[-1]); - // EXPECTED: 222 1 1 0 - // CHECK: 222 1 0 1 + // CHECK: 222 1 1 0 p++; } @@ -66,8 +64,7 @@ void f1() { { printf("%d %d %d %d\n", p[0], p_mappedptr == &p, x0_mappedptr == &p[-2], x0_hostaddr == &p[-2]); - // EXPECTED: 333 1 1 0 - // CHECK: 333 1 0 1 + // CHECK: 333 1 1 0 } // The following map(from:p) should not bring back p, because p is an @@ -75,8 +72,7 @@ void f1() { // location, &x[0], on host. #pragma omp target exit data map(always, from : p) printf("%d %d\n", p[0], p == &x[0]); - // EXPECTED: 111 1 - // CHECK: 333 0 + // CHECK: 111 1 #pragma omp target exit data map(delete : p[0 : 5], p) } diff --git a/offload/test/mapping/map_structptr_and_member_global.c b/offload/test/mapping/map_structptr_and_member_global.c index f2fae005b79ab..9789a7f2f4882 100644 --- a/offload/test/mapping/map_structptr_and_member_global.c +++ b/offload/test/mapping/map_structptr_and_member_global.c @@ -51,8 +51,7 @@ void f1() { { printf("%d %d %d %d\n", ps->x, ps_mappedptr == &ps, s0_mappedptr == &ps->x, s0_hostaddr == &ps->x); - // EXPECTED: 111 1 1 0 - // CHECK: 111 1 0 1 + // CHECK: 111 1 1 0 ps++; } @@ -61,8 +60,7 @@ void f1() { { printf("%d %d %d %d\n", ps->x, ps_mappedptr == &ps, s0_mappedptr == &ps[-1].x, s0_hostaddr == &ps[-1].x); - // EXPECTED: 222 1 1 0 - // CHECK: 222 1 0 1 + // CHECK: 222 1 1 0 ps++; } @@ -72,7 +70,7 @@ void f1() { printf("%d %d %d %d\n", ps->x, ps_mappedptr == &ps, s0_mappedptr == &ps[-2].x, s0_hostaddr == &ps[-2].x); // EXPECTED: 333 1 1 0 - // CHECK: 333 1 0 1 + // CHECK: 333 1 1 0 } // The following map(from:ps) should not bring back ps, because ps is an @@ -80,8 +78,7 @@ void f1() { // location, &s[0], on host. #pragma omp target exit data map(always, from : ps) printf("%d %d\n", ps->x, ps == &s[0]); - // EXPECTED: 111 1 - // CHECK: 333 0 + // CHECK: 111 1 #pragma omp target exit data map(delete : ps, s) } diff --git a/offload/test/mapping/map_structptr_and_member_local.c b/offload/test/mapping/map_structptr_and_member_local.c index a9db3eefbc54f..850e04db81e62 100644 --- a/offload/test/mapping/map_structptr_and_member_local.c +++ b/offload/test/mapping/map_structptr_and_member_local.c @@ -50,8 +50,7 @@ void f1() { { printf("%d %d %d %d\n", ps->x, ps_mappedptr == &ps, s0_mappedptr == &ps->x, s0_hostaddr == &ps->x); - // EXPECTED: 111 1 1 0 - // CHECK: 111 1 0 1 + // CHECK: 111 1 1 0 ps++; } @@ -60,8 +59,7 @@ void f1() { { printf("%d %d %d %d\n", ps->x, ps_mappedptr == &ps, s0_mappedptr == &ps[-1].x, s0_hostaddr == &ps[-1].x); - // EXPECTED: 222 1 1 0 - // CHECK: 222 1 0 1 + // CHECK: 222 1 1 0 ps++; } @@ -70,8 +68,7 @@ void f1() { { printf("%d %d %d %d\n", ps->x, ps_mappedptr == &ps, s0_mappedptr == &ps[-2].x, s0_hostaddr == &ps[-2].x); - // EXPECTED: 333 1 1 0 - // CHECK: 333 1 0 1 + // CHECK: 333 1 1 0 } // The following map(from:ps) should not bring back ps, because ps is an @@ -79,8 +76,7 @@ void f1() { // location, &s[0], on host. #pragma omp target exit data map(always, from : ps) printf("%d %d\n", ps->x, ps == &s[0]); - // EXPECTED: 111 1 - // CHECK: 333 0 + // CHECK: 111 1 #pragma omp target exit data map(delete : ps, s) }