diff options
author | Carlos Seo <carlos.seo@linaro.org> | 2025-07-23 11:16:11 -0300 |
---|---|---|
committer | GitHub <noreply@github.com> | 2025-07-23 11:16:11 -0300 |
commit | fc0a978327215aa8883ae6f18d1e316f3c04520a (patch) | |
tree | 33826bf65ad15a2441adc2ff99347d2b39db9ab8 /flang/lib | |
parent | 594b6f7b3f70b26bf9c7b34d54340797e3e07a1d (diff) | |
download | llvm-fc0a978327215aa8883ae6f18d1e316f3c04520a.zip llvm-fc0a978327215aa8883ae6f18d1e316f3c04520a.tar.gz llvm-fc0a978327215aa8883ae6f18d1e316f3c04520a.tar.bz2 |
[Flang] Fix ASSIGN statement (#149941)
Handle the case where the assigned variable also has a pointer
attribute.
Fixes #121721
Diffstat (limited to 'flang/lib')
-rw-r--r-- | flang/lib/Lower/Bridge.cpp | 28 |
1 files changed, 26 insertions, 2 deletions
diff --git a/flang/lib/Lower/Bridge.cpp b/flang/lib/Lower/Bridge.cpp index 13420f3..37f2475 100644 --- a/flang/lib/Lower/Bridge.cpp +++ b/flang/lib/Lower/Bridge.cpp @@ -5509,10 +5509,34 @@ private: void genFIR(const Fortran::parser::AssignStmt &stmt) { const Fortran::semantics::Symbol &symbol = *std::get<Fortran::parser::Name>(stmt.t).symbol; + mlir::Location loc = toLocation(); + mlir::Type symbolType = genType(symbol); + mlir::Value addr = getSymbolAddress(symbol); + + // Handle the case where the assigned variable is declared as a pointer + if (auto eleTy = fir::dyn_cast_ptrOrBoxEleTy(symbolType)) { + if (auto ptrType = mlir::dyn_cast<fir::PointerType>(eleTy)) { + symbolType = ptrType.getEleTy(); + } else { + symbolType = eleTy; + } + } else if (auto ptrType = mlir::dyn_cast<fir::PointerType>(symbolType)) { + symbolType = ptrType.getEleTy(); + } + mlir::Value labelValue = builder->createIntegerConstant( - loc, genType(symbol), std::get<Fortran::parser::Label>(stmt.t)); - builder->create<fir::StoreOp>(loc, labelValue, getSymbolAddress(symbol)); + loc, symbolType, std::get<Fortran::parser::Label>(stmt.t)); + + // If the address points to a boxed pointer, we need to dereference it + if (auto refType = mlir::dyn_cast<fir::ReferenceType>(addr.getType())) { + if (auto boxType = mlir::dyn_cast<fir::BoxType>(refType.getEleTy())) { + mlir::Value boxValue = builder->create<fir::LoadOp>(loc, addr); + addr = builder->create<fir::BoxAddrOp>(loc, boxValue); + } + } + + builder->create<fir::StoreOp>(loc, labelValue, addr); } void genFIR(const Fortran::parser::FormatStmt &) { |