Index: include/polly/ScopInfo.h =================================================================== --- include/polly/ScopInfo.h +++ include/polly/ScopInfo.h @@ -278,29 +278,27 @@ unsigned getNumberOfDimensions() const { if (Kind == MK_PHI || Kind == MK_ExitPHI || Kind == MK_Value) return 0; - return DimensionSizes.size() + 1; + return DimensionSizes.size(); } /// @brief Return the size of dimension @p dim as SCEV*. // // Scalars do not have array dimensions and the first dimension of // a (possibly multi-dimensional) array also does not carry any size - // information. + // information, in case the array is not newly created. const SCEV *getDimensionSize(unsigned Dim) const { - assert(Dim > 0 && "Only dimensions larger than zero are sized."); assert(Dim < getNumberOfDimensions() && "Invalid dimension"); - return DimensionSizes[Dim - 1]; + return DimensionSizes[Dim]; } /// @brief Return the size of dimension @p dim as isl_pw_aff. // // Scalars do not have array dimensions and the first dimension of // a (possibly multi-dimensional) array also does not carry any size - // information. + // information, in case the array is not newly created. __isl_give isl_pw_aff *getDimensionSizePw(unsigned Dim) const { - assert(Dim > 0 && "Only dimensions larger than zero are sized."); assert(Dim < getNumberOfDimensions() && "Invalid dimension"); - return isl_pw_aff_copy(DimensionSizesPw[Dim - 1]); + return isl_pw_aff_copy(DimensionSizesPw[Dim]); } /// @brief Get the canonical element type of this array. Index: lib/Analysis/ScopInfo.cpp =================================================================== --- lib/Analysis/ScopInfo.cpp +++ lib/Analysis/ScopInfo.cpp @@ -218,7 +218,7 @@ int SharedDims = std::min(NewSizes.size(), DimensionSizes.size()); int ExtraDimsNew = NewSizes.size() - SharedDims; int ExtraDimsOld = DimensionSizes.size() - SharedDims; - for (int i = 0; i < SharedDims; i++) + for (int i = 1; i < SharedDims; i++) if (NewSizes[i + ExtraDimsNew] != DimensionSizes[i + ExtraDimsOld]) return false; @@ -232,6 +232,10 @@ isl_pw_aff_free(Size); DimensionSizesPw.clear(); for (const SCEV *Expr : DimensionSizes) { + if (!Expr) { + DimensionSizesPw.push_back(nullptr); + continue; + } isl_pw_aff *Size = S.getPwAffOnly(Expr); DimensionSizesPw.push_back(Size); } @@ -258,9 +262,12 @@ void ScopArrayInfo::print(raw_ostream &OS, bool SizeAsPwAff) const { OS.indent(8) << *getElementType() << " " << getName(); - if (getNumberOfDimensions() > 0) + unsigned u = 0; + if (getNumberOfDimensions() > 0 && !getDimensionSize(0)) { OS << "[*]"; - for (unsigned u = 1; u < getNumberOfDimensions(); u++) { + u++; + } + for (; u < getNumberOfDimensions(); u++) { OS << "["; if (SizeAsPwAff) { @@ -622,7 +629,7 @@ void MemoryAccess::buildMemIntrinsicAccessRelation() { assert(isa(getAccessInstruction())); - assert(Subscripts.size() == 2 && Sizes.size() == 0); + assert(Subscripts.size() == 2 && Sizes.size() == 1); auto *SubscriptPWA = getPwAff(Subscripts[0]); auto *SubscriptMap = isl_map_from_pw_aff(SubscriptPWA); @@ -690,7 +697,7 @@ for (int i = Size - 2; i >= 0; --i) { isl_space *Space; isl_map *MapOne, *MapTwo; - isl_pw_aff *DimSize = getPwAff(Sizes[i]); + isl_pw_aff *DimSize = getPwAff(Sizes[i + 1]); isl_space *SpaceSize = isl_pw_aff_get_space(DimSize); isl_pw_aff_free(DimSize); @@ -799,7 +806,7 @@ AccessRelation = isl_map_flat_range_product(AccessRelation, SubscriptMap); } - if (Sizes.size() >= 1 && !isa(Sizes[0])) + if (Sizes.size() >= 2 && !isa(Sizes[1])) AccessRelation = foldAccess(AccessRelation, Statement); Space = Statement->getDomainSpace(); @@ -827,6 +834,9 @@ static const std::string TypeStrings[] = {"", "_Read", "_Write", "_MayWrite"}; const std::string Access = TypeStrings[AccType] + utostr(Stmt->size()) + "_"; + if (Kind == ScopArrayInfo::MK_Array) + MemoryAccess::Sizes.insert(MemoryAccess::Sizes.begin(), nullptr); + std::string IdName = getIslCompatibleName(Stmt->getBaseName(), Access, BaseName); Id = isl_id_alloc(Stmt->getParent()->getIslCtx(), IdName.c_str(), this); @@ -3516,7 +3526,10 @@ std::vector SCEVSizes; for (auto size : Sizes) - SCEVSizes.push_back(getSE()->getConstant(DimSizeType, size, false)); + if (size) + SCEVSizes.push_back(getSE()->getConstant(DimSizeType, size, false)); + else + SCEVSizes.push_back(nullptr); auto *SAI = getOrCreateScopArrayInfo(nullptr, ElementType, SCEVSizes, Index: lib/CodeGen/IslNodeBuilder.cpp =================================================================== --- lib/CodeGen/IslNodeBuilder.cpp +++ lib/CodeGen/IslNodeBuilder.cpp @@ -1154,8 +1154,12 @@ if (SAI->getBasePtr()) continue; + assert(SAI->getNumberOfDimensions() > 0 && SAI->getDimensionSize(0) && + "The size of the outermost dimension is used to declare newly " + "created arrays that require memory allocation."); + Type *NewArrayType = nullptr; - for (unsigned i = SAI->getNumberOfDimensions() - 1; i >= 1; i--) { + for (int i = SAI->getNumberOfDimensions() - 1; i >= 0; i--) { auto *DimSize = SAI->getDimensionSize(i); unsigned UnsignedDimSize = static_cast(DimSize) ->getAPInt() Index: lib/CodeGen/PPCGCodeGeneration.cpp =================================================================== --- lib/CodeGen/PPCGCodeGeneration.cpp +++ lib/CodeGen/PPCGCodeGeneration.cpp @@ -1200,6 +1200,7 @@ SmallVector Sizes; isl_ast_build *Build = isl_ast_build_from_context(isl_set_copy(Prog->context)); + Sizes.push_back(nullptr); for (long j = 1; j < Kernel->array[i].array->n_index; j++) { isl_ast_expr *DimSize = isl_ast_build_expr_from_pw_aff( Build, isl_pw_aff_copy(Kernel->array[i].array->bound[j])); @@ -1309,6 +1310,7 @@ Type *ArrayTy = EleTy; SmallVector Sizes; + Sizes.push_back(nullptr); for (unsigned int j = 1; j < Var.array->n_index; ++j) { isl_val *Val = isl_vec_get_element_val(Var.size, j); long Bound = isl_val_get_num_si(Val); Index: lib/Exchange/JSONExporter.cpp =================================================================== --- lib/Exchange/JSONExporter.cpp +++ lib/Exchange/JSONExporter.cpp @@ -152,7 +152,12 @@ Json::Value Array; Array["name"] = SAI->getName(); - for (unsigned i = 1; i < SAI->getNumberOfDimensions(); i++) { + unsigned i = 0; + if (!SAI->getDimensionSize(i)) { + Array["sizes"].append("*"); + i++; + } + for (; i < SAI->getNumberOfDimensions(); i++) { SAI->getDimensionSize(i)->print(RawStringOstream); Array["sizes"].append(RawStringOstream.str()); Buffer.clear(); @@ -471,11 +476,11 @@ if (SAI->getName() != Array["name"].asCString()) return false; - if (SAI->getNumberOfDimensions() != Array["sizes"].size() + 1) + if (SAI->getNumberOfDimensions() != Array["sizes"].size()) return false; - for (unsigned i = 0; i < Array["sizes"].size(); i++) { - SAI->getDimensionSize(i + 1)->print(RawStringOstream); + for (unsigned i = 1; i < Array["sizes"].size(); i++) { + SAI->getDimensionSize(i)->print(RawStringOstream); if (RawStringOstream.str() != Array["sizes"][i].asCString()) return false; Buffer.clear(); Index: lib/Transform/ScheduleOptimizer.cpp =================================================================== --- lib/Transform/ScheduleOptimizer.cpp +++ lib/Transform/ScheduleOptimizer.cpp @@ -719,7 +719,7 @@ /// the matrix multiplication pattern. /// /// Create an access relation of the following form: -/// [O0, O1, O2, O3, O4, O5, O6, O7, O8] -> [0, O5 + K * OI, OJ], +/// [O0, O1, O2, O3, O4, O5, O6, O7, O8] -> [O5 + K * OI, OJ], /// where K is @p Coeff, I is @p FirstDim, J is @p SecondDim. /// /// It can be used, for example, to create relations that helps to consequently @@ -747,17 +747,16 @@ unsigned Coeff, unsigned FirstDim, unsigned SecondDim) { auto *Ctx = isl_map_get_ctx(MapOldIndVar); - auto *AccessRelSpace = isl_space_alloc(Ctx, 0, 9, 3); + auto *AccessRelSpace = isl_space_alloc(Ctx, 0, 9, 2); auto *AccessRel = isl_map_universe(isl_space_copy(AccessRelSpace)); auto *ConstrSpace = isl_local_space_from_space(AccessRelSpace); auto *Constr = isl_constraint_alloc_equality(ConstrSpace); - Constr = isl_constraint_set_coefficient_si(Constr, isl_dim_out, 1, -1); + Constr = isl_constraint_set_coefficient_si(Constr, isl_dim_out, 0, -1); Constr = isl_constraint_set_coefficient_si(Constr, isl_dim_in, 5, 1); Constr = isl_constraint_set_coefficient_si(Constr, isl_dim_in, FirstDim, Coeff); AccessRel = isl_map_add_constraint(AccessRel, Constr); - AccessRel = isl_map_fix_si(AccessRel, isl_dim_out, 0, 0); - AccessRel = isl_map_equate(AccessRel, isl_dim_in, SecondDim, isl_dim_out, 2); + AccessRel = isl_map_equate(AccessRel, isl_dim_in, SecondDim, isl_dim_out, 1); return isl_map_apply_range(MapOldIndVar, AccessRel); } Index: test/Isl/CodeGen/MemAccess/create_arrays.ll =================================================================== --- test/Isl/CodeGen/MemAccess/create_arrays.ll +++ test/Isl/CodeGen/MemAccess/create_arrays.ll @@ -11,11 +11,11 @@ ; CHECK: double MemRef_B[*][1024]; // Element size 8 ; CHECK: double MemRef_beta; // Element size 8 ; CHECK: double MemRef_A[*][1056]; // Element size 8 -; CHECK: double D[*][270336]; // Element size 8 -; CHECK: double E[*][270336][200000]; // Element size 8 -; CHECK: i64 F[*][270336]; // Element size 8 +; CHECK: double D[270336]; // Element size 8 +; CHECK: double E[270336][200000]; // Element size 8 +; CHECK: i64 F[270336]; // Element size 8 ; -; CHECK:New access function '{ Stmt_bb12[i0, i1, i2] -> E[0, i2, i0] }'detected in JSCOP file +; CHECK:New access function '{ Stmt_bb12[i0, i1, i2] -> E[i2, i0] }'detected in JSCOP file ; ; CODEGEN:define internal void @create_arrays(i32 %arg, i32 %arg1, i32 %arg2, double %arg3, double %beta, [1056 x double]* %A, [1024 x double]* %B, [1056 x double]* %arg7) #0 { ; CODEGEN:bb: @@ -27,9 +27,8 @@ ; ; CODEGEN: %beta.s2a.reload = load double, double* %beta.s2a ; CODEGEN: %polly.access.cast.E = bitcast [270336 x [200000 x double]]* %E to double* -; CODEGEN: %polly.access.add.E = add nsw i64 0, %polly.indvar33 -; CODEGEN: %polly.access.mul.E = mul nsw i64 %polly.access.add.E, 200000 -; CODEGEN: %polly.access.add.E36 = add nsw i64 %polly.access.mul.E, %polly.indvar +; CODEGEN: %polly.access.mul.E = mul nsw i64 %polly.indvar33, 200000 +; CODEGEN: %polly.access.add.E = add nsw i64 %polly.access.mul.E, %polly.indvar ; target datalayout = "e-m:e-i64:64-f80:128-n8:16:32:64-S128" target triple = "x86_64-unknown-unknown" Index: test/Isl/CodeGen/MemAccess/create_arrays___%bb9---%bb26.jscop =================================================================== --- test/Isl/CodeGen/MemAccess/create_arrays___%bb9---%bb26.jscop +++ test/Isl/CodeGen/MemAccess/create_arrays___%bb9---%bb26.jscop @@ -1,13 +1,13 @@ { "arrays" : [ - { + { "name" : "MemRef_B", - "sizes" : [ "1024" ], + "sizes" : [ "*", "1024" ], "type" : "double" }, { "name" : "MemRef_A", - "sizes" : [ "1056" ], + "sizes" : [ "*", "1056" ], "type" : "double" } ], Index: test/Isl/CodeGen/MemAccess/create_arrays___%bb9---%bb26.jscop.transformed =================================================================== --- test/Isl/CodeGen/MemAccess/create_arrays___%bb9---%bb26.jscop.transformed +++ test/Isl/CodeGen/MemAccess/create_arrays___%bb9---%bb26.jscop.transformed @@ -2,12 +2,12 @@ "arrays" : [ { "name" : "MemRef_B", - "sizes" : [ "1024" ], + "sizes" : [ "*", "1024" ], "type" : "double" }, { "name" : "MemRef_A", - "sizes" : [ "1056" ], + "sizes" : [ "*", "1056" ], "type" : "double" }, { @@ -33,7 +33,7 @@ "accesses" : [ { "kind" : "read", - "relation" : "{ Stmt_bb12[i0, i1, i2] -> E[0, i2, i0] }" + "relation" : "{ Stmt_bb12[i0, i1, i2] -> E[i2, i0] }" }, { "kind" : "read", Index: test/ScheduleOptimizer/mat_mul_pattern_data_layout.ll =================================================================== --- test/ScheduleOptimizer/mat_mul_pattern_data_layout.ll +++ test/ScheduleOptimizer/mat_mul_pattern_data_layout.ll @@ -9,8 +9,8 @@ ; C[i][j] += alpha * A[i][k] * B[k][j]; ; } ; -; CHECK: double Packed_A[*][ { [] -> [(4)] } ]; // Element size 8 -; CHECK: double Packed_B[*][ { [] -> [(8)] } ]; // Element size 8 +; CHECK: double Packed_A[ { [] -> [(1024)] } ][ { [] -> [(4)] } ]; // Element size 8 +; CHECK: double Packed_B[ { [] -> [(3072)] } ][ { [] -> [(8)] } ]; // Element size 8 ; ; CHECK: { Stmt_bb14[i0, i1, i2] -> MemRef_arg6[i0, i2] }; ; CHECK: new: { Stmt_bb14[i0, i1, i2] -> Packed_A[o0, o1] : 256*floor((-i2 + o0)/256) = -i2 + o0 and 4*floor((-i0 + o1)/4) = -i0 + o1 and 0 <= o1 <= 3 and -3 + i0 - 16*floor((i0)/16) <= 4*floor((o0)/256) <= i0 - 16*floor((i0)/16) };