diff --git a/flang/lib/Optimizer/Analysis/AliasAnalysis.cpp b/flang/lib/Optimizer/Analysis/AliasAnalysis.cpp index 2bc79100b03b6..2ff8ec05782c1 100644 --- a/flang/lib/Optimizer/Analysis/AliasAnalysis.cpp +++ b/flang/lib/Optimizer/Analysis/AliasAnalysis.cpp @@ -51,40 +51,6 @@ static bool hasGlobalOpTargetAttr(mlir::Value v, fir::AddrOfOp op) { v, fir::GlobalOp::getTargetAttrName(globalOpName)); } -static mlir::Value -getOriginalDef(mlir::Value v, - fir::AliasAnalysis::Source::Attributes &attributes, - bool &isCapturedInInternalProcedure, bool &approximateSource) { - mlir::Operation *defOp; - bool breakFromLoop = false; - while (!breakFromLoop && (defOp = v.getDefiningOp())) { - mlir::Type ty = defOp->getResultTypes()[0]; - llvm::TypeSwitch(defOp) - .Case([&](fir::ConvertOp op) { v = op.getValue(); }) - .Case([&](auto op) { - v = op.getMemref(); - auto varIf = llvm::cast(defOp); - attributes |= getAttrsFromVariable(varIf); - isCapturedInInternalProcedure |= - varIf.isCapturedInInternalProcedure(); - }) - .Case([&](auto op) { - if (fir::AliasAnalysis::isPointerReference(ty)) - attributes.set(fir::AliasAnalysis::Attribute::Pointer); - v = op->getOperand(0); - approximateSource = true; - }) - .Case([&](hlfir::DesignateOp op) { - auto varIf = llvm::cast(defOp); - attributes |= getAttrsFromVariable(varIf); - v = op.getMemref(); - approximateSource = true; - }) - .Default([&](auto op) { breakFromLoop = true; }); - } - return v; -} - static bool isEvaluateInMemoryBlockArg(mlir::Value v) { if (auto evalInMem = llvm::dyn_cast_or_null( v.getParentRegion()->getParentOp())) @@ -621,38 +587,34 @@ AliasAnalysis::Source AliasAnalysis::getSource(mlir::Value v, if (mlir::isa(boxTy.getEleTy())) attributes.set(Attribute::Pointer); - auto def = getOriginalDef(op.getMemref(), attributes, - isCapturedInInternalProcedure, - approximateSource); - if (auto addrOfOp = def.template getDefiningOp()) { - global = addrOfOp.getSymbol(); - - if (hasGlobalOpTargetAttr(def, addrOfOp)) - attributes.set(Attribute::Target); + auto boxSrc = getSource(op.getMemref()); + attributes |= boxSrc.attributes; + approximateSource |= boxSrc.approximateSource; + isCapturedInInternalProcedure |= + boxSrc.isCapturedInInternalProcedure; + global = llvm::dyn_cast(boxSrc.origin.u); + if (global) { type = SourceKind::Global; - } - // TODO: Add support to fir.allocmem - else if (auto allocOp = - def.template getDefiningOp()) { - v = def; - defOp = v.getDefiningOp(); - type = SourceKind::Allocate; - } else if (isDummyArgument(def)) { - defOp = nullptr; - v = def; } else { - type = SourceKind::Indirect; + auto def = llvm::cast(boxSrc.origin.u); + // TODO: Add support to fir.allocmem + if (auto allocOp = def.template getDefiningOp()) { + v = def; + defOp = v.getDefiningOp(); + type = SourceKind::Allocate; + } else if (isDummyArgument(def)) { + defOp = nullptr; + v = def; + } else { + type = SourceKind::Indirect; + } } - // TODO: This assignment is redundant but somehow works around an - // apparent MSVC bug reporting "undeclared identifier" at the next - // "breakFromLoop = true;". See - // . breakFromLoop = true; - } else { - // No further tracking for addresses loaded from memory for now. - type = SourceKind::Indirect; + return; } + // No further tracking for addresses loaded from memory for now. + type = SourceKind::Indirect; breakFromLoop = true; }) .Case([&](auto op) { diff --git a/flang/test/Analysis/AliasAnalysis/source-kind.fir b/flang/test/Analysis/AliasAnalysis/source-kind.fir new file mode 100644 index 0000000000000..2b1384163dbde --- /dev/null +++ b/flang/test/Analysis/AliasAnalysis/source-kind.fir @@ -0,0 +1,25 @@ +// RUN: fir-opt %s -pass-pipeline='builtin.module(func.func(test-fir-alias-analysis))' -debug-only=fir-alias-analysis 2>&1 | FileCheck %s + +// CHECK-LABEL: Testing : "_QFPtest" + +// Checking that the source kind of a load of a load is SourceKind::Indirect +// CHECK: {test.ptr = "load_load"} +// CHECK-NEXT: SourceKind: Indirect + +// Checking that the source kind of a load of an arg is SourceKind::Argument +// CHECK: {test.ptr = "load_arg"} +// CHECK-NEXT: SourceKind: Argument + +func.func @_QFPtest(%arg0: !fir.ref>> ) attributes {test.ptr = "func"} { + + %0 = fir.alloca !fir.llvm_ptr>> + %1 = fir.convert %arg0 : (!fir.ref>>) -> !fir.llvm_ptr>> + fir.store %1 to %0 : !fir.ref>>> + %2 = fir.load %0 : !fir.ref>>> + %3 = fir.convert %2 : (!fir.llvm_ptr>>) -> !fir.ref>> + %15 = fir.load %3 : !fir.ref>> + %16 = fir.box_addr %15 {test.ptr = "load_load"} : (!fir.box>) -> !fir.ptr + %17 = fir.load %arg0 : !fir.ref>> + %18 = fir.box_addr %17 {test.ptr = "load_arg"} : (!fir.box>) -> !fir.ptr + return +} \ No newline at end of file