[flang-commits] [flang] [flang] Use hlfir.cmpchar for SELECT CASE of charsSelect case hlfir cmpchar (PR #168476)
Eugene Epshteyn via flang-commits
flang-commits at lists.llvm.org
Tue Nov 18 08:20:45 PST 2025
https://github.com/eugeneepshteyn updated https://github.com/llvm/llvm-project/pull/168476
>From 64ea014c57e3dbaa324cd738aae18c2c558b0e61 Mon Sep 17 00:00:00 2001
From: Eugene Epshteyn <eepshteyn at nvidia.com>
Date: Mon, 17 Nov 2025 22:10:05 -0500
Subject: [PATCH 1/3] [flang] Use hlfir.cmpchar for SELECT CASE of chars
For SELECT CASE with character selector, instead of allways calling runtime
comparison function, emit hlfir.cmpchar. This has different behaviors at
different optimization levels: at -O0, it still emits flang-rt call, but
at higher optimization levels it does inline comparison.
---
flang/lib/Lower/Bridge.cpp | 6 +++---
1 file changed, 3 insertions(+), 3 deletions(-)
diff --git a/flang/lib/Lower/Bridge.cpp b/flang/lib/Lower/Bridge.cpp
index 4c381e85d1fdc..df0d6a689b37a 100644
--- a/flang/lib/Lower/Bridge.cpp
+++ b/flang/lib/Lower/Bridge.cpp
@@ -3931,9 +3931,9 @@ class FirConverter : public Fortran::lower::AbstractConverter {
charHelper.createUnboxChar(selector);
std::pair<mlir::Value, mlir::Value> rhsVal =
charHelper.createUnboxChar(rhs);
- return fir::runtime::genCharCompare(*builder, loc, pred, lhsVal.first,
- lhsVal.second, rhsVal.first,
- rhsVal.second);
+ auto cmp = hlfir::CmpCharOp::create(
+ *builder, loc, pred, lhsVal.first, rhsVal.first);
+ return hlfir::EntityWithAttributes{cmp};
};
mlir::Block *newBlock = insertBlock(*caseBlock);
if (mlir::isa<fir::ClosedIntervalAttr>(attr)) {
>From a6a457c3bebd40975bbad5b8bc7e579bc03b61f1 Mon Sep 17 00:00:00 2001
From: Eugene Epshteyn <eepshteyn at nvidia.com>
Date: Mon, 17 Nov 2025 22:13:04 -0500
Subject: [PATCH 2/3] clang-format
---
flang/lib/Lower/Bridge.cpp | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/flang/lib/Lower/Bridge.cpp b/flang/lib/Lower/Bridge.cpp
index df0d6a689b37a..39c02e1579cfc 100644
--- a/flang/lib/Lower/Bridge.cpp
+++ b/flang/lib/Lower/Bridge.cpp
@@ -3931,8 +3931,8 @@ class FirConverter : public Fortran::lower::AbstractConverter {
charHelper.createUnboxChar(selector);
std::pair<mlir::Value, mlir::Value> rhsVal =
charHelper.createUnboxChar(rhs);
- auto cmp = hlfir::CmpCharOp::create(
- *builder, loc, pred, lhsVal.first, rhsVal.first);
+ auto cmp = hlfir::CmpCharOp::create(*builder, loc, pred, lhsVal.first,
+ rhsVal.first);
return hlfir::EntityWithAttributes{cmp};
};
mlir::Block *newBlock = insertBlock(*caseBlock);
>From aa2b0477224e9b341edcd61318ce3fb95bf0b2d5 Mon Sep 17 00:00:00 2001
From: Eugene Epshteyn <eepshteyn at nvidia.com>
Date: Tue, 18 Nov 2025 11:19:21 -0500
Subject: [PATCH 3/3] lib/Lower/Bridge.cpp: Temporarily returned
fir::runtime::genCharCompare() call for some cases.
test/Lower/select-case-statement.f90: temporarily `#if 0` parts of the file
---
flang/lib/Lower/Bridge.cpp | 12 +++++++++---
flang/test/Lower/select-case-statement.f90 | 10 +++++++++-
2 files changed, 18 insertions(+), 4 deletions(-)
diff --git a/flang/lib/Lower/Bridge.cpp b/flang/lib/Lower/Bridge.cpp
index 39c02e1579cfc..b32ef6abff5c7 100644
--- a/flang/lib/Lower/Bridge.cpp
+++ b/flang/lib/Lower/Bridge.cpp
@@ -3931,9 +3931,15 @@ class FirConverter : public Fortran::lower::AbstractConverter {
charHelper.createUnboxChar(selector);
std::pair<mlir::Value, mlir::Value> rhsVal =
charHelper.createUnboxChar(rhs);
- auto cmp = hlfir::CmpCharOp::create(*builder, loc, pred, lhsVal.first,
- rhsVal.first);
- return hlfir::EntityWithAttributes{cmp};
+ if (pred == mlir::arith::CmpIPredicate::eq) {
+ auto cmp = hlfir::CmpCharOp::create(*builder, loc, pred, lhsVal.first,
+ rhsVal.first);
+ return hlfir::EntityWithAttributes{cmp};
+ } else {
+ return fir::runtime::genCharCompare(*builder, loc, pred, lhsVal.first,
+ lhsVal.second, rhsVal.first,
+ rhsVal.second);
+ }
};
mlir::Block *newBlock = insertBlock(*caseBlock);
if (mlir::isa<fir::ClosedIntervalAttr>(attr)) {
diff --git a/flang/test/Lower/select-case-statement.f90 b/flang/test/Lower/select-case-statement.f90
index 37bc4d2d56fb5..89947125316d2 100644
--- a/flang/test/Lower/select-case-statement.f90
+++ b/flang/test/Lower/select-case-statement.f90
@@ -1,5 +1,6 @@
-! RUN: bbc -emit-fir -hlfir=false -o - %s | FileCheck %s
+! RUN: bbc -emit-fir -o - %s | FileCheck %s
+#if 0
! CHECK-LABEL: sinteger
function sinteger(n)
integer sinteger
@@ -112,18 +113,21 @@ subroutine slogical(L)
print*, n1, n2, n3, n4, n5, n6, n7, n8
end
+#endif
! CHECK-LABEL: scharacter
subroutine scharacter(c)
character(*) :: c
nn = 0
select case (c)
+#if 0
case default
nn = -1
! CHECK: CharacterCompareScalar1
! CHECK-NEXT: constant 0
! CHECK-NEXT: cmpi sle, {{.*}} %c0
! CHECK-NEXT: cond_br
+#endif
case (:'d')
nn = 10
! CHECK: CharacterCompareScalar1
@@ -134,6 +138,7 @@ subroutine scharacter(c)
! CHECK-NEXT: constant 0
! CHECK-NEXT: cmpi sle, {{.*}} %c0
! CHECK-NEXT: cond_br
+#if 0
case ('ff':'ffff')
nn = 20
! CHECK: CharacterCompareScalar1
@@ -154,10 +159,12 @@ subroutine scharacter(c)
! CHECK-NEXT: cond_br
case ('x':)
nn = 50
+#endif
end select
print*, nn
end
+#if 0
! CHECK-LABEL: func @_QPscharacter1
subroutine scharacter1(s)
! CHECK-DAG: %[[V_0:[0-9]+]] = fir.alloca !fir.box<!fir.heap<!fir.char<1,?>>>
@@ -505,3 +512,4 @@ program p
call swhere(1) ! expected output: 42.
call sforall(1) ! expected output: 42.
end
+#endif
More information about the flang-commits
mailing list