|
23 | 23 |
|
24 | 24 | namespace fir {
|
25 | 25 |
|
| 26 | +/// Calculate offset of any field in the descriptor. |
| 27 | +template <int DescriptorField> |
| 28 | +std::uint64_t getComponentOffset(const mlir::DataLayout &dl, |
| 29 | + mlir::MLIRContext *context, |
| 30 | + mlir::Type llvmFieldType) { |
| 31 | + assert(DescriptorField > 0 && DescriptorField < 10); |
| 32 | + mlir::Type previousFieldType = |
| 33 | + getDescFieldTypeModel<DescriptorField - 1>()(context); |
| 34 | + std::uint64_t previousOffset = |
| 35 | + getComponentOffset<DescriptorField - 1>(dl, context, previousFieldType); |
| 36 | + std::uint64_t offset = previousOffset + dl.getTypeSize(previousFieldType); |
| 37 | + std::uint64_t fieldAlignment = dl.getTypeABIAlignment(llvmFieldType); |
| 38 | + return llvm::alignTo(offset, fieldAlignment); |
| 39 | +} |
| 40 | +template <> |
| 41 | +std::uint64_t getComponentOffset<0>(const mlir::DataLayout &dl, |
| 42 | + mlir::MLIRContext *context, |
| 43 | + mlir::Type llvmFieldType) { |
| 44 | + return 0; |
| 45 | +} |
| 46 | + |
26 | 47 | DebugTypeGenerator::DebugTypeGenerator(mlir::ModuleOp m)
|
27 | 48 | : module(m), kindMapping(getKindMapping(m)) {
|
28 | 49 | LLVM_DEBUG(llvm::dbgs() << "DITypeAttr generator\n");
|
29 | 50 |
|
30 | 51 | std::optional<mlir::DataLayout> dl =
|
31 | 52 | fir::support::getOrSetDataLayout(module, /*allowDefaultLayout=*/true);
|
32 |
| - if (!dl) |
| 53 | + if (!dl) { |
33 | 54 | mlir::emitError(module.getLoc(), "Missing data layout attribute in module");
|
| 55 | + return; |
| 56 | + } |
34 | 57 |
|
35 | 58 | mlir::MLIRContext *context = module.getContext();
|
36 | 59 |
|
37 | 60 | // The debug information requires the offset of certain fields in the
|
38 |
| - // descriptors like lower_bound and extent for each dimension. The code |
39 |
| - // below uses getDescFieldTypeModel to get the type representing each field |
40 |
| - // and then use data layout to get its size. It adds the size to get the |
41 |
| - // offset. |
42 |
| - // As has been mentioned in DescriptorModel.h that code may be confusing |
43 |
| - // host for the target in calculating the type of the descriptor fields. But |
44 |
| - // debug info is using similar logic to what codegen is doing so it will |
45 |
| - // atleast be representing the generated code correctly. |
46 |
| - // My testing for a 32-bit shows that base_addr* is correctly given as a |
47 |
| - // 32-bit entity. The index types are 64-bit so I am a bit uncertain how |
48 |
| - // the alignment will effect the calculation of offsets in that case. |
49 |
| - |
50 |
| - // base_addr* |
51 |
| - dimsOffset = |
52 |
| - dl->getTypeSizeInBits(getDescFieldTypeModel<kAddrPosInBox>()(context)); |
53 |
| - |
54 |
| - // elem_len |
55 |
| - dimsOffset += |
56 |
| - dl->getTypeSizeInBits(getDescFieldTypeModel<kElemLenPosInBox>()(context)); |
57 |
| - |
58 |
| - // version |
59 |
| - dimsOffset += |
60 |
| - dl->getTypeSizeInBits(getDescFieldTypeModel<kVersionPosInBox>()(context)); |
61 |
| - |
62 |
| - // rank |
63 |
| - dimsOffset += |
64 |
| - dl->getTypeSizeInBits(getDescFieldTypeModel<kRankPosInBox>()(context)); |
65 |
| - |
66 |
| - // type |
67 |
| - dimsOffset += |
68 |
| - dl->getTypeSizeInBits(getDescFieldTypeModel<kTypePosInBox>()(context)); |
69 |
| - |
70 |
| - // attribute |
71 |
| - dimsOffset += dl->getTypeSizeInBits( |
72 |
| - getDescFieldTypeModel<kAttributePosInBox>()(context)); |
73 |
| - |
74 |
| - // f18Addendum |
75 |
| - dimsOffset += dl->getTypeSizeInBits( |
76 |
| - getDescFieldTypeModel<kF18AddendumPosInBox>()(context)); |
77 |
| - |
78 |
| - // dims |
79 |
| - dimsSize = |
80 |
| - dl->getTypeSizeInBits(getDescFieldTypeModel<kDimsPosInBox>()(context)); |
81 |
| - dimsOffset /= 8; |
82 |
| - dimsSize /= 8; |
| 61 | + // descriptors like lower_bound and extent for each dimension. |
| 62 | + mlir::Type llvmDimsType = getDescFieldTypeModel<kDimsPosInBox>()(context); |
| 63 | + dimsOffset = getComponentOffset<kDimsPosInBox>(*dl, context, llvmDimsType); |
| 64 | + dimsSize = dl->getTypeSize(getDescFieldTypeModel<kDimsPosInBox>()(context)); |
83 | 65 | }
|
84 | 66 |
|
85 | 67 | static mlir::LLVM::DITypeAttr genBasicType(mlir::MLIRContext *context,
|
|
0 commit comments