xref: /llvm-project/flang/include/flang/Lower/ConvertExprToHLFIR.h (revision d1aa9bac3c8ecc30fcc5d4d80a1f70c729aec909)
1 //===-- Lower/ConvertExprToHLFIR.h -- lowering of expressions ----*- C++-*-===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 //
9 // Coding style: https://mlir.llvm.org/getting_started/DeveloperGuide/
10 //
11 //===----------------------------------------------------------------------===//
12 ///
13 /// Implements the conversion from Fortran::evaluate::Expr trees to HLFIR.
14 ///
15 //===----------------------------------------------------------------------===//
16 
17 #ifndef FORTRAN_LOWER_CONVERTEXPRTOHLFIR_H
18 #define FORTRAN_LOWER_CONVERTEXPRTOHLFIR_H
19 
20 #include "flang/Lower/StatementContext.h"
21 #include "flang/Lower/Support/Utils.h"
22 #include "flang/Optimizer/Builder/FIRBuilder.h"
23 #include "flang/Optimizer/Builder/HLFIRTools.h"
24 #include "flang/Optimizer/Dialect/FIRDialect.h"
25 
26 namespace mlir {
27 class Location;
28 } // namespace mlir
29 
30 namespace hlfir {
31 class ElementalAddrOp;
32 }
33 
34 namespace Fortran::lower {
35 
36 class AbstractConverter;
37 class SymMap;
38 
39 hlfir::EntityWithAttributes
40 convertExprToHLFIR(mlir::Location loc, Fortran::lower::AbstractConverter &,
41                    const Fortran::lower::SomeExpr &, Fortran::lower::SymMap &,
42                    Fortran::lower::StatementContext &);
43 
44 inline fir::ExtendedValue translateToExtendedValue(
45     mlir::Location loc, fir::FirOpBuilder &builder, hlfir::Entity entity,
46     Fortran::lower::StatementContext &context, bool contiguityHint = false) {
47   auto [exv, exvCleanup] =
48       hlfir::translateToExtendedValue(loc, builder, entity, contiguityHint);
49   if (exvCleanup)
50     context.attachCleanup(*exvCleanup);
51   return exv;
52 }
53 
54 /// Lower an evaluate::Expr object to a fir.box, and a procedure designator to a
55 /// fir.boxproc<>
56 fir::ExtendedValue convertExprToBox(mlir::Location loc,
57                                     Fortran::lower::AbstractConverter &,
58                                     const Fortran::lower::SomeExpr &,
59                                     Fortran::lower::SymMap &,
60                                     Fortran::lower::StatementContext &);
61 fir::ExtendedValue convertToBox(mlir::Location loc,
62                                 Fortran::lower::AbstractConverter &,
63                                 hlfir::Entity entity,
64                                 Fortran::lower::StatementContext &,
65                                 mlir::Type fortranType);
66 
67 /// Lower an evaluate::Expr to fir::ExtendedValue address.
68 /// The address may be a raw fir.ref<T>, or a fir.box<T>/fir.class<T>, or a
69 /// fir.boxproc<>. Pointers and allocatable are dereferenced.
70 /// - If the expression is a procedure designator, it is lowered to fir.boxproc
71 /// (with an extra length for character function procedure designators).
72 /// - If expression is not a variable, or is a designator with vector
73 ///   subscripts, a temporary is created to hold the expression value and
74 ///   is returned as:
75 ///   - a fir.class<T> if the expression is polymorphic.
76 ///   - otherwise, a fir.box<T> if it is a derived type with length
77 ///     parameters (not yet implemented).
78 ///   - otherwise, a fir.ref<T>
79 /// - If the expression is a variable that is not a designator with
80 ///   vector subscripts, it is lowered without creating a temporary and
81 ///   is returned as:
82 ///   - a fir.class<T> if the variable is polymorphic.
83 ///   - otherwise, a fir.box<T> if it is a derived type with length
84 ///     parameters (not yet implemented), or if it is not a simply
85 ///     contiguous.
86 ///   - otherwise, a fir.ref<T>
87 ///
88 /// Beware that this is different from the previous createSomeExtendedAddress
89 /// that had a non-trivial behaviour and would create contiguous temporary for
90 /// array sections `x(:, :)`, but not for `x` even if x is not simply
91 /// contiguous.
92 fir::ExtendedValue convertExprToAddress(mlir::Location loc,
93                                         Fortran::lower::AbstractConverter &,
94                                         const Fortran::lower::SomeExpr &,
95                                         Fortran::lower::SymMap &,
96                                         Fortran::lower::StatementContext &);
97 fir::ExtendedValue convertToAddress(mlir::Location loc,
98                                     Fortran::lower::AbstractConverter &,
99                                     hlfir::Entity entity,
100                                     Fortran::lower::StatementContext &,
101                                     mlir::Type fortranType);
102 
103 /// Lower an evaluate::Expr to a fir::ExtendedValue value.
104 fir::ExtendedValue convertExprToValue(mlir::Location loc,
105                                       Fortran::lower::AbstractConverter &,
106                                       const Fortran::lower::SomeExpr &,
107                                       Fortran::lower::SymMap &,
108                                       Fortran::lower::StatementContext &);
109 fir::ExtendedValue convertToValue(mlir::Location loc,
110                                   Fortran::lower::AbstractConverter &,
111                                   hlfir::Entity entity,
112                                   Fortran::lower::StatementContext &);
113 
114 fir::ExtendedValue convertDataRefToValue(mlir::Location loc,
115                                          Fortran::lower::AbstractConverter &,
116                                          const Fortran::evaluate::DataRef &,
117                                          Fortran::lower::SymMap &,
118                                          Fortran::lower::StatementContext &);
119 
120 /// Lower an evaluate::Expr to a fir::MutableBoxValue value.
121 /// This can only be called if the Expr is a POINTER or ALLOCATABLE,
122 /// otherwise, this will crash.
123 fir::MutableBoxValue
124 convertExprToMutableBox(mlir::Location loc, Fortran::lower::AbstractConverter &,
125                         const Fortran::lower::SomeExpr &,
126                         Fortran::lower::SymMap &);
127 /// Lower a designator containing vector subscripts into an
128 /// hlfir::ElementalAddrOp that will allow looping on the elements to assign
129 /// them values. This only intends to cover the cases where such designator
130 /// appears on the left-hand side of an assignment or appears in an input IO
131 /// statement. These are the only contexts in Fortran where a vector subscripted
132 /// entity may be modified. Otherwise, there is no need to do anything special
133 /// about vector subscripts, they are automatically turned into array expression
134 /// values via an hlfir.elemental in the convertExprToXXX calls.
135 hlfir::ElementalAddrOp convertVectorSubscriptedExprToElementalAddr(
136     mlir::Location loc, Fortran::lower::AbstractConverter &,
137     const Fortran::lower::SomeExpr &, Fortran::lower::SymMap &,
138     Fortran::lower::StatementContext &);
139 
140 } // namespace Fortran::lower
141 
142 #endif // FORTRAN_LOWER_CONVERTEXPRTOHLFIR_H
143