Skip to content

Commit 6fd4608

Browse files
authored
[flang][debug] Allow non default array lower bounds. (#104467)
As mentioned in #98877, we currently always use 1 as lower bound for fixed size arrays. This PR removes this restriction. It passes along `DeclareOp` to type conversion functions and uses the shift information (if present) to get the lower bound value. This was suggested by @jeanPerier in #96746 (comment) This PR also adds a small cleanup that type conversion functions don't take Location now. It was initially added so that location of derived types can be passed. But that information can be extracted from typeInfo objects and we don't need to pass it along. This PR will handle the problem for local and global variable. We may need a bit more work for derived type once the support for derived types lands. Fixes #98877.
1 parent 278fc8e commit 6fd4608

File tree

5 files changed

+87
-61
lines changed

5 files changed

+87
-61
lines changed

flang/lib/Optimizer/Transforms/AddDebugInfo.cpp

Lines changed: 13 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -65,7 +65,8 @@ class AddDebugInfoPass : public fir::impl::AddDebugInfoBase<AddDebugInfoPass> {
6565

6666
void handleGlobalOp(fir::GlobalOp glocalOp, mlir::LLVM::DIFileAttr fileAttr,
6767
mlir::LLVM::DIScopeAttr scope,
68-
mlir::SymbolTable *symbolTable);
68+
mlir::SymbolTable *symbolTable,
69+
fir::cg::XDeclareOp declOp);
6970
void handleFuncOp(mlir::func::FuncOp funcOp, mlir::LLVM::DIFileAttr fileAttr,
7071
mlir::LLVM::DICompileUnitAttr cuAttr,
7172
mlir::SymbolTable *symbolTable);
@@ -100,10 +101,9 @@ void AddDebugInfoPass::handleDeclareOp(fir::cg::XDeclareOp declOp,
100101

101102
if (result.first != fir::NameUniquer::NameKind::VARIABLE)
102103
return;
103-
104104
// If this DeclareOp actually represents a global then treat it as such.
105105
if (auto global = symbolTable->lookup<fir::GlobalOp>(declOp.getUniqName())) {
106-
handleGlobalOp(global, fileAttr, scopeAttr, symbolTable);
106+
handleGlobalOp(global, fileAttr, scopeAttr, symbolTable, declOp);
107107
return;
108108
}
109109

@@ -127,7 +127,7 @@ void AddDebugInfoPass::handleDeclareOp(fir::cg::XDeclareOp declOp,
127127
}
128128

129129
auto tyAttr = typeGen.convertType(fir::unwrapRefType(declOp.getType()),
130-
fileAttr, scopeAttr, declOp.getLoc());
130+
fileAttr, scopeAttr, declOp);
131131

132132
auto localVarAttr = mlir::LLVM::DILocalVariableAttr::get(
133133
context, scopeAttr, mlir::StringAttr::get(context, result.second.name),
@@ -160,7 +160,8 @@ mlir::LLVM::DIModuleAttr AddDebugInfoPass::getOrCreateModuleAttr(
160160
void AddDebugInfoPass::handleGlobalOp(fir::GlobalOp globalOp,
161161
mlir::LLVM::DIFileAttr fileAttr,
162162
mlir::LLVM::DIScopeAttr scope,
163-
mlir::SymbolTable *symbolTable) {
163+
mlir::SymbolTable *symbolTable,
164+
fir::cg::XDeclareOp declOp) {
164165
if (debugInfoIsAlreadySet(globalOp.getLoc()))
165166
return;
166167
mlir::ModuleOp module = getOperation();
@@ -200,8 +201,8 @@ void AddDebugInfoPass::handleGlobalOp(fir::GlobalOp globalOp,
200201
scope = getOrCreateModuleAttr(result.second.modules[0], fileAttr, scope,
201202
line - 1, !globalOp.isInitialized());
202203
}
203-
mlir::LLVM::DITypeAttr diType = typeGen.convertType(
204-
globalOp.getType(), fileAttr, scope, globalOp.getLoc());
204+
mlir::LLVM::DITypeAttr diType =
205+
typeGen.convertType(globalOp.getType(), fileAttr, scope, declOp);
205206
auto gvAttr = mlir::LLVM::DIGlobalVariableAttr::get(
206207
context, scope, mlir::StringAttr::get(context, result.second.name),
207208
mlir::StringAttr::get(context, globalOp.getName()), fileAttr, line,
@@ -246,12 +247,13 @@ void AddDebugInfoPass::handleFuncOp(mlir::func::FuncOp funcOp,
246247
llvm::SmallVector<mlir::LLVM::DITypeAttr> types;
247248
fir::DebugTypeGenerator typeGen(module);
248249
for (auto resTy : funcOp.getResultTypes()) {
249-
auto tyAttr = typeGen.convertType(resTy, fileAttr, cuAttr, funcOp.getLoc());
250+
auto tyAttr =
251+
typeGen.convertType(resTy, fileAttr, cuAttr, /*declOp=*/nullptr);
250252
types.push_back(tyAttr);
251253
}
252254
for (auto inTy : funcOp.getArgumentTypes()) {
253255
auto tyAttr = typeGen.convertType(fir::unwrapRefType(inTy), fileAttr,
254-
cuAttr, funcOp.getLoc());
256+
cuAttr, /*declOp=*/nullptr);
255257
types.push_back(tyAttr);
256258
}
257259

@@ -358,7 +360,8 @@ void AddDebugInfoPass::runOnOperation() {
358360
if (debugLevel == mlir::LLVM::DIEmissionKind::Full) {
359361
// Process 'GlobalOp' only if full debug info is requested.
360362
for (auto globalOp : module.getOps<fir::GlobalOp>())
361-
handleGlobalOp(globalOp, fileAttr, cuAttr, &symbolTable);
363+
handleGlobalOp(globalOp, fileAttr, cuAttr, &symbolTable,
364+
/*declOp=*/nullptr);
362365
}
363366
}
364367

flang/lib/Optimizer/Transforms/DebugTypeGenerator.cpp

Lines changed: 28 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -83,8 +83,8 @@ static mlir::LLVM::DITypeAttr genPlaceholderType(mlir::MLIRContext *context) {
8383

8484
mlir::LLVM::DITypeAttr DebugTypeGenerator::convertBoxedSequenceType(
8585
fir::SequenceType seqTy, mlir::LLVM::DIFileAttr fileAttr,
86-
mlir::LLVM::DIScopeAttr scope, mlir::Location loc, bool genAllocated,
87-
bool genAssociated) {
86+
mlir::LLVM::DIScopeAttr scope, fir::cg::XDeclareOp declOp,
87+
bool genAllocated, bool genAssociated) {
8888

8989
mlir::MLIRContext *context = module.getContext();
9090
// FIXME: Assumed rank arrays not supported yet
@@ -114,7 +114,7 @@ mlir::LLVM::DITypeAttr DebugTypeGenerator::convertBoxedSequenceType(
114114

115115
llvm::SmallVector<mlir::LLVM::DINodeAttr> elements;
116116
mlir::LLVM::DITypeAttr elemTy =
117-
convertType(seqTy.getEleTy(), fileAttr, scope, loc);
117+
convertType(seqTy.getEleTy(), fileAttr, scope, declOp);
118118
unsigned offset = dimsOffset;
119119
const unsigned indexSize = dimsSize / 3;
120120
for ([[maybe_unused]] auto _ : seqTy.getShape()) {
@@ -156,13 +156,14 @@ mlir::LLVM::DITypeAttr DebugTypeGenerator::convertBoxedSequenceType(
156156

157157
mlir::LLVM::DITypeAttr DebugTypeGenerator::convertSequenceType(
158158
fir::SequenceType seqTy, mlir::LLVM::DIFileAttr fileAttr,
159-
mlir::LLVM::DIScopeAttr scope, mlir::Location loc) {
159+
mlir::LLVM::DIScopeAttr scope, fir::cg::XDeclareOp declOp) {
160160
mlir::MLIRContext *context = module.getContext();
161161

162162
llvm::SmallVector<mlir::LLVM::DINodeAttr> elements;
163163
mlir::LLVM::DITypeAttr elemTy =
164-
convertType(seqTy.getEleTy(), fileAttr, scope, loc);
164+
convertType(seqTy.getEleTy(), fileAttr, scope, declOp);
165165

166+
unsigned index = 0;
166167
for (fir::SequenceType::Extent dim : seqTy.getShape()) {
167168
if (dim == seqTy.getUnknownExtent()) {
168169
// FIXME: This path is taken for assumed size arrays but also for arrays
@@ -174,20 +175,20 @@ mlir::LLVM::DITypeAttr DebugTypeGenerator::convertSequenceType(
174175
elements.push_back(subrangeTy);
175176
} else {
176177
auto intTy = mlir::IntegerType::get(context, 64);
177-
// FIXME: Only supporting lower bound of 1 at the moment. The
178-
// 'SequenceType' has information about the shape but not the shift. In
179-
// cases where the conversion originated during the processing of
180-
// 'DeclareOp', it may be possible to pass on this information. But the
181-
// type conversion should ideally be based on what information present in
182-
// the type class so that it works from everywhere (e.g. when it is part
183-
// of a module or a derived type.)
178+
int64_t shift = 1;
179+
if (declOp && declOp.getShift().size() > index) {
180+
if (std::optional<std::int64_t> optint =
181+
getIntIfConstant(declOp.getShift()[index]))
182+
shift = *optint;
183+
}
184184
auto countAttr = mlir::IntegerAttr::get(intTy, llvm::APInt(64, dim));
185-
auto lowerAttr = mlir::IntegerAttr::get(intTy, llvm::APInt(64, 1));
185+
auto lowerAttr = mlir::IntegerAttr::get(intTy, llvm::APInt(64, shift));
186186
auto subrangeTy = mlir::LLVM::DISubrangeAttr::get(
187187
context, countAttr, lowerAttr, /*upperBound=*/nullptr,
188188
/*stride=*/nullptr);
189189
elements.push_back(subrangeTy);
190190
}
191+
++index;
191192
}
192193
// Apart from arrays, the `DICompositeTypeAttr` is used for other things like
193194
// structure types. Many of its fields which are not applicable to arrays
@@ -203,7 +204,8 @@ mlir::LLVM::DITypeAttr DebugTypeGenerator::convertSequenceType(
203204

204205
mlir::LLVM::DITypeAttr DebugTypeGenerator::convertCharacterType(
205206
fir::CharacterType charTy, mlir::LLVM::DIFileAttr fileAttr,
206-
mlir::LLVM::DIScopeAttr scope, mlir::Location loc, bool hasDescriptor) {
207+
mlir::LLVM::DIScopeAttr scope, fir::cg::XDeclareOp declOp,
208+
bool hasDescriptor) {
207209
mlir::MLIRContext *context = module.getContext();
208210

209211
// DWARF 5 says the following about the character encoding in 5.1.1.2.
@@ -250,21 +252,21 @@ mlir::LLVM::DITypeAttr DebugTypeGenerator::convertCharacterType(
250252

251253
mlir::LLVM::DITypeAttr DebugTypeGenerator::convertPointerLikeType(
252254
mlir::Type elTy, mlir::LLVM::DIFileAttr fileAttr,
253-
mlir::LLVM::DIScopeAttr scope, mlir::Location loc, bool genAllocated,
254-
bool genAssociated) {
255+
mlir::LLVM::DIScopeAttr scope, fir::cg::XDeclareOp declOp,
256+
bool genAllocated, bool genAssociated) {
255257
mlir::MLIRContext *context = module.getContext();
256258

257259
// Arrays and character need different treatment because DWARF have special
258260
// constructs for them to get the location from the descriptor. Rest of
259261
// types are handled like pointer to underlying type.
260262
if (auto seqTy = mlir::dyn_cast_or_null<fir::SequenceType>(elTy))
261-
return convertBoxedSequenceType(seqTy, fileAttr, scope, loc, genAllocated,
262-
genAssociated);
263+
return convertBoxedSequenceType(seqTy, fileAttr, scope, declOp,
264+
genAllocated, genAssociated);
263265
if (auto charTy = mlir::dyn_cast_or_null<fir::CharacterType>(elTy))
264-
return convertCharacterType(charTy, fileAttr, scope, loc,
266+
return convertCharacterType(charTy, fileAttr, scope, declOp,
265267
/*hasDescriptor=*/true);
266268

267-
mlir::LLVM::DITypeAttr elTyAttr = convertType(elTy, fileAttr, scope, loc);
269+
mlir::LLVM::DITypeAttr elTyAttr = convertType(elTy, fileAttr, scope, declOp);
268270

269271
return mlir::LLVM::DIDerivedTypeAttr::get(
270272
context, llvm::dwarf::DW_TAG_pointer_type,
@@ -276,7 +278,7 @@ mlir::LLVM::DITypeAttr DebugTypeGenerator::convertPointerLikeType(
276278
mlir::LLVM::DITypeAttr
277279
DebugTypeGenerator::convertType(mlir::Type Ty, mlir::LLVM::DIFileAttr fileAttr,
278280
mlir::LLVM::DIScopeAttr scope,
279-
mlir::Location loc) {
281+
fir::cg::XDeclareOp declOp) {
280282
mlir::MLIRContext *context = module.getContext();
281283
if (Ty.isInteger()) {
282284
return genBasicType(context, mlir::StringAttr::get(context, "integer"),
@@ -306,22 +308,22 @@ DebugTypeGenerator::convertType(mlir::Type Ty, mlir::LLVM::DIFileAttr fileAttr,
306308
return genBasicType(context, mlir::StringAttr::get(context, "complex"),
307309
bitWidth * 2, llvm::dwarf::DW_ATE_complex_float);
308310
} else if (auto seqTy = mlir::dyn_cast_or_null<fir::SequenceType>(Ty)) {
309-
return convertSequenceType(seqTy, fileAttr, scope, loc);
311+
return convertSequenceType(seqTy, fileAttr, scope, declOp);
310312
} else if (auto charTy = mlir::dyn_cast_or_null<fir::CharacterType>(Ty)) {
311-
return convertCharacterType(charTy, fileAttr, scope, loc,
313+
return convertCharacterType(charTy, fileAttr, scope, declOp,
312314
/*hasDescriptor=*/false);
313315
} else if (auto boxTy = mlir::dyn_cast_or_null<fir::BoxType>(Ty)) {
314316
auto elTy = boxTy.getElementType();
315317
if (auto seqTy = mlir::dyn_cast_or_null<fir::SequenceType>(elTy))
316-
return convertBoxedSequenceType(seqTy, fileAttr, scope, loc, false,
318+
return convertBoxedSequenceType(seqTy, fileAttr, scope, declOp, false,
317319
false);
318320
if (auto heapTy = mlir::dyn_cast_or_null<fir::HeapType>(elTy))
319321
return convertPointerLikeType(heapTy.getElementType(), fileAttr, scope,
320-
loc, /*genAllocated=*/true,
322+
declOp, /*genAllocated=*/true,
321323
/*genAssociated=*/false);
322324
if (auto ptrTy = mlir::dyn_cast_or_null<fir::PointerType>(elTy))
323325
return convertPointerLikeType(ptrTy.getElementType(), fileAttr, scope,
324-
loc, /*genAllocated=*/false,
326+
declOp, /*genAllocated=*/false,
325327
/*genAssociated=*/true);
326328
return genPlaceholderType(context);
327329
} else {

flang/lib/Optimizer/Transforms/DebugTypeGenerator.h

Lines changed: 14 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@
1313
#ifndef FORTRAN_OPTIMIZER_TRANSFORMS_DEBUGTYPEGENERATOR_H
1414
#define FORTRAN_OPTIMIZER_TRANSFORMS_DEBUGTYPEGENERATOR_H
1515

16+
#include "flang/Optimizer/CodeGen/CGOps.h"
1617
#include "flang/Optimizer/Dialect/FIRType.h"
1718
#include "flang/Optimizer/Dialect/Support/FIRContext.h"
1819
#include "flang/Optimizer/Dialect/Support/KindMapping.h"
@@ -28,33 +29,34 @@ class DebugTypeGenerator {
2829
mlir::LLVM::DITypeAttr convertType(mlir::Type Ty,
2930
mlir::LLVM::DIFileAttr fileAttr,
3031
mlir::LLVM::DIScopeAttr scope,
31-
mlir::Location loc);
32+
fir::cg::XDeclareOp declOp);
3233

3334
private:
3435
mlir::LLVM::DITypeAttr convertSequenceType(fir::SequenceType seqTy,
3536
mlir::LLVM::DIFileAttr fileAttr,
3637
mlir::LLVM::DIScopeAttr scope,
37-
mlir::Location loc);
38+
fir::cg::XDeclareOp declOp);
3839

3940
/// The 'genAllocated' is true when we want to generate 'allocated' field
4041
/// in the DICompositeType. It is needed for the allocatable arrays.
4142
/// Similarly, 'genAssociated' is used with 'pointer' type to generate
4243
/// 'associated' field.
43-
mlir::LLVM::DITypeAttr
44-
convertBoxedSequenceType(fir::SequenceType seqTy,
45-
mlir::LLVM::DIFileAttr fileAttr,
46-
mlir::LLVM::DIScopeAttr scope, mlir::Location loc,
47-
bool genAllocated, bool genAssociated);
44+
mlir::LLVM::DITypeAttr convertBoxedSequenceType(
45+
fir::SequenceType seqTy, mlir::LLVM::DIFileAttr fileAttr,
46+
mlir::LLVM::DIScopeAttr scope, fir::cg::XDeclareOp declOp,
47+
bool genAllocated, bool genAssociated);
4848
mlir::LLVM::DITypeAttr convertCharacterType(fir::CharacterType charTy,
4949
mlir::LLVM::DIFileAttr fileAttr,
5050
mlir::LLVM::DIScopeAttr scope,
51-
mlir::Location loc,
51+
fir::cg::XDeclareOp declOp,
5252
bool hasDescriptor);
5353

54-
mlir::LLVM::DITypeAttr
55-
convertPointerLikeType(mlir::Type elTy, mlir::LLVM::DIFileAttr fileAttr,
56-
mlir::LLVM::DIScopeAttr scope, mlir::Location loc,
57-
bool genAllocated, bool genAssociated);
54+
mlir::LLVM::DITypeAttr convertPointerLikeType(mlir::Type elTy,
55+
mlir::LLVM::DIFileAttr fileAttr,
56+
mlir::LLVM::DIScopeAttr scope,
57+
fir::cg::XDeclareOp declOp,
58+
bool genAllocated,
59+
bool genAssociated);
5860

5961
mlir::ModuleOp module;
6062
KindMapping kindMapping;
Lines changed: 25 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1,19 +1,22 @@
11
! RUN: %flang_fc1 -emit-llvm -debug-info-kind=standalone %s -o - | FileCheck %s
22

3-
program mn
4-
3+
module test
54
integer d1(3)
6-
integer d2(2, 5)
7-
real d3(6, 8, 7)
5+
integer d2(1:4, -1:3)
6+
real d3(-2:6, 0:5, 3:7)
7+
end
8+
9+
program mn
10+
use test
811

912
i8 = fn1(d1, d2, d3)
1013
contains
1114
function fn1(a1, b1, c1) result (res)
1215
integer a1(3)
13-
integer b1(2, 5)
14-
real c1(6, 8, 7)
16+
integer b1(-1:0, 5:9)
17+
real c1(-2:6, 0:5, 3:7)
1518
integer res
16-
res = a1(1) + b1(1,2) + c1(3, 3, 4)
19+
res = a1(1) + b1(0,6) + c1(3, 3, 4)
1720
end function
1821

1922
end program
@@ -24,17 +27,26 @@ function fn1(a1, b1, c1) result (res)
2427
! CHECK-DAG: ![[SUB1:.*]] = !{![[R1]]}
2528
! CHECK-DAG: ![[D1TY:.*]] = !DICompositeType(tag: DW_TAG_array_type, baseType: ![[INT]], elements: ![[SUB1]])
2629

27-
! CHECK-DAG: ![[R21:.*]] = !DISubrange(count: 2, lowerBound: 1)
28-
! CHECK-DAG: ![[R22:.*]] = !DISubrange(count: 5, lowerBound: 1)
30+
! CHECK-DAG: ![[R21:.*]] = !DISubrange(count: 4, lowerBound: 1)
31+
! CHECK-DAG: ![[R22:.*]] = !DISubrange(count: 5, lowerBound: -1)
2932
! CHECK-DAG: ![[SUB2:.*]] = !{![[R21]], ![[R22]]}
3033
! CHECK-DAG: ![[D2TY:.*]] = !DICompositeType(tag: DW_TAG_array_type, baseType: ![[INT]], elements: ![[SUB2]])
3134

32-
! CHECK-DAG: ![[R31:.*]] = !DISubrange(count: 6, lowerBound: 1)
33-
! CHECK-DAG: ![[R32:.*]] = !DISubrange(count: 8, lowerBound: 1)
34-
! CHECK-DAG: ![[R33:.*]] = !DISubrange(count: 7, lowerBound: 1)
35+
! CHECK-DAG: ![[R31:.*]] = !DISubrange(count: 9, lowerBound: -2)
36+
! CHECK-DAG: ![[R32:.*]] = !DISubrange(count: 6, lowerBound: 0)
37+
! CHECK-DAG: ![[R33:.*]] = !DISubrange(count: 5, lowerBound: 3)
3538
! CHECK-DAG: ![[SUB3:.*]] = !{![[R31]], ![[R32]], ![[R33]]}
3639
! CHECK-DAG: ![[D3TY:.*]] = !DICompositeType(tag: DW_TAG_array_type, baseType: ![[REAL]], elements: ![[SUB3]])
3740

41+
! CHECK-DAG: ![[B11:.*]] = !DISubrange(count: 2, lowerBound: -1)
42+
! CHECK-DAG: ![[B12:.*]] = !DISubrange(count: 5, lowerBound: 5)
43+
! CHECK-DAG: ![[B1:.*]] = !{![[B11]], ![[B12]]}
44+
! CHECK-DAG: ![[B1TY:.*]] = !DICompositeType(tag: DW_TAG_array_type, baseType: ![[INT]], elements: ![[B1]])
45+
46+
! CHECK-DAG: {{.*}}!DIGlobalVariable(name: "d1"{{.*}}type: ![[D1TY]]{{.*}})
47+
! CHECK-DAG: {{.*}}!DIGlobalVariable(name: "d2"{{.*}}type: ![[D2TY]]{{.*}})
48+
! CHECK-DAG: {{.*}}!DIGlobalVariable(name: "d3"{{.*}}type: ![[D3TY]]{{.*}})
49+
3850
! CHECK-DAG: !DILocalVariable(name: "a1", arg: 1{{.*}}type: ![[D1TY]])
39-
! CHECK-DAG: !DILocalVariable(name: "b1", arg: 2{{.*}}type: ![[D2TY]])
51+
! CHECK-DAG: !DILocalVariable(name: "b1", arg: 2{{.*}}type: ![[B1TY]])
4052
! CHECK-DAG: !DILocalVariable(name: "c1", arg: 3{{.*}}type: ![[D3TY]])

flang/test/Transforms/debug-fixed-array-type.fir

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,12 +8,16 @@ module attributes {dlti.dl_spec = #dlti.dl_spec<>} {
88
%c5 = arith.constant 5 : index
99
%c2 = arith.constant 2 : index
1010
%c3 = arith.constant 3 : index
11+
%c-2 = arith.constant -2 : index loc(#loc3)
12+
%c4 = arith.constant 4 : index loc(#loc3)
1113
%0 = fir.alloca !fir.array<3xi32> {bindc_name = "d1", uniq_name = "_QFEd1"}
1214
%1 = fircg.ext_declare %0(%c3) {uniq_name = "_QFEd1"} : (!fir.ref<!fir.array<3xi32>>, index) -> !fir.ref<!fir.array<3xi32>> loc(#loc1)
1315
%2 = fir.address_of(@_QFEd2) : !fir.ref<!fir.array<2x5xi32>>
1416
%3 = fircg.ext_declare %2(%c2, %c5) {uniq_name = "_QFEd2"} : (!fir.ref<!fir.array<2x5xi32>>, index, index) -> !fir.ref<!fir.array<2x5xi32>> loc(#loc2)
1517
%4 = fir.address_of(@_QFEd3) : !fir.ref<!fir.array<6x8x7xf32>>
1618
%5 = fircg.ext_declare %4(%c6, %c8, %c7) {uniq_name = "_QFEd3"} : (!fir.ref<!fir.array<6x8x7xf32>>, index, index, index) -> !fir.ref<!fir.array<6x8x7xf32>> loc(#loc3)
19+
%6 = fir.address_of(@_QFEd4) : !fir.ref<!fir.array<6x7xi32>>
20+
%7 = fircg.ext_declare %6(%c6, %c7) origin %c-2, %c4 {uniq_name = "_QFEd4"} : (!fir.ref<!fir.array<6x7xi32>>, index, index, index, index) -> !fir.ref<!fir.array<6x7xi32>> loc(#loc5)
1721
return
1822
} loc(#loc4)
1923
}
@@ -22,13 +26,16 @@ module attributes {dlti.dl_spec = #dlti.dl_spec<>} {
2226
#loc2 = loc("test.f90":6:11)
2327
#loc3 = loc("test.f90":7:11)
2428
#loc4 = loc("test.f90":2:8)
29+
#loc5 = loc("test.f90":8:11)
2530

2631

2732
// CHECK-DAG: #[[INT:.*]] = #llvm.di_basic_type<tag = DW_TAG_base_type, name = "integer", sizeInBits = 32, encoding = DW_ATE_signed>
2833
// CHECK-DAG: #[[REAL:.*]] = #llvm.di_basic_type<tag = DW_TAG_base_type, name = "real", sizeInBits = 32, encoding = DW_ATE_float>
2934
// CHECK-DAG: #[[D1TY:.*]] = #llvm.di_composite_type<tag = DW_TAG_array_type{{.*}}baseType = #[[INT]], elements = #llvm.di_subrange<count = 3 : i64, lowerBound = 1 : i64>>
3035
// CHECK-DAG: #[[D2TY:.*]] = #llvm.di_composite_type<tag = DW_TAG_array_type{{.*}}baseType = #[[INT]], elements = #llvm.di_subrange<count = 2 : i64, lowerBound = 1 : i64>, #llvm.di_subrange<count = 5 : i64, lowerBound = 1 : i64>>
3136
// CHECK-DAG: #[[D3TY:.*]] = #llvm.di_composite_type<tag = DW_TAG_array_type{{.*}}baseType = #[[REAL]], elements = #llvm.di_subrange<count = 6 : i64, lowerBound = 1 : i64>, #llvm.di_subrange<count = 8 : i64, lowerBound = 1 : i64>, #llvm.di_subrange<count = 7 : i64, lowerBound = 1 : i64>>
37+
// CHECK-DAG: #[[D4TY:.*]] = #llvm.di_composite_type<tag = DW_TAG_array_type, baseType = #di_basic_type, elements = #llvm.di_subrange<count = 6 : i64, lowerBound = -2 : i64>, #llvm.di_subrange<count = 7 : i64, lowerBound = 4 : i64>>
3238
// CHECK-DAG: #llvm.di_local_variable<{{.*}}name = "d1"{{.*}}type = #[[D1TY]]>
3339
// CHECK-DAG: #llvm.di_local_variable<{{.*}}name = "d2"{{.*}}type = #[[D2TY]]>
3440
// CHECK-DAG: #llvm.di_local_variable<{{.*}}name = "d3"{{.*}}type = #[[D3TY]]>
41+
// CHECK-DAG: #llvm.di_local_variable<{{.*}}name = "d4"{{.*}}type = #[[D4TY]]>

0 commit comments

Comments
 (0)