From 9588c754db9725be2860c0bf9bee82085ec51a0f Mon Sep 17 00:00:00 2001 From: Tom Eccles Date: Wed, 28 Aug 2024 16:33:39 +0100 Subject: [PATCH 1/2] [flang] Warn when F128 is unsupported (#102147) This generates `warning: REAL(KIND=16) is not an enabled type for this target` if that type is used in a build not correctly configured to support this type. Uses of `selected_real_kind(30)` return -1. --- flang/include/flang/Tools/TargetSetup.h | 19 ++++++- flang/module/ieee_arithmetic.f90 | 49 +++++++++++++++++++ flang/test/CMakeLists.txt | 10 ++++ flang/test/Evaluate/fold-out_of_range.f90 | 1 + flang/test/Evaluate/folding07.f90 | 1 + .../Lower/Intrinsics/ieee_class_queries.f90 | 1 + .../test/Lower/Intrinsics/ieee_unordered.f90 | 1 + flang/test/Lower/common-block.f90 | 2 +- flang/test/Semantics/kinds03.f90 | 1 + flang/test/Semantics/modfile26.f90 | 1 + flang/test/Semantics/realkinds-aarch64-01.f90 | 1 + flang/test/lit.cfg.py | 3 +- flang/test/lit.site.cfg.py.in | 1 + flang/tools/f18/CMakeLists.txt | 25 +++++++++- 14 files changed, 112 insertions(+), 4 deletions(-) diff --git a/flang/include/flang/Tools/TargetSetup.h b/flang/include/flang/Tools/TargetSetup.h index 238d66c9241dd..60609de8809cf 100644 --- a/flang/include/flang/Tools/TargetSetup.h +++ b/flang/include/flang/Tools/TargetSetup.h @@ -11,6 +11,7 @@ #include "flang/Evaluate/target.h" #include "llvm/Target/TargetMachine.h" +#include namespace Fortran::tools { @@ -21,9 +22,25 @@ namespace Fortran::tools { const llvm::Triple &targetTriple{targetMachine.getTargetTriple()}; // FIXME: Handle real(3) ? - if (targetTriple.getArch() != llvm::Triple::ArchType::x86_64) + if (targetTriple.getArch() != llvm::Triple::ArchType::x86_64) { targetCharacteristics.DisableType( Fortran::common::TypeCategory::Real, /*kind=*/10); + } + + // Figure out if we can support F128: see + // flang/runtime/Float128Math/math-entries.h +#ifdef FLANG_RUNTIME_F128_MATH_LIB + // we can use libquadmath wrappers + constexpr bool f128Support = true; +#elif LDBL_MANT_DIG == 113 + // we can use libm wrappers + constexpr bool f128Support = true; +#else + constexpr bool f128Support = false; +#endif + + if constexpr (!f128Support) + targetCharacteristics.DisableType(Fortran::common::TypeCategory::Real, 16); targetCharacteristics.set_compilerOptionsString(compilerOptions) .set_compilerVersionString(compilerVersion); diff --git a/flang/module/ieee_arithmetic.f90 b/flang/module/ieee_arithmetic.f90 index 7c7721d78c1ed..32e640b9e2457 100644 --- a/flang/module/ieee_arithmetic.f90 +++ b/flang/module/ieee_arithmetic.f90 @@ -161,6 +161,8 @@ end function ieee_round_ne G(1) G(2) G(4) G(8) G(16) #define SPECIFICS_L(G) \ G(1) G(2) G(4) G(8) + +#if FLANG_SUPPORT_R16 #if __x86_64__ #define SPECIFICS_R(G) \ G(2) G(3) G(4) G(8) G(10) G(16) @@ -168,12 +170,24 @@ end function ieee_round_ne #define SPECIFICS_R(G) \ G(2) G(3) G(4) G(8) G(16) #endif +#else +#if __x86_64__ +#define SPECIFICS_R(G) \ + G(2) G(3) G(4) G(8) G(10) +#else +#define SPECIFICS_R(G) \ + G(2) G(3) G(4) G(8) +#endif +#endif + #define SPECIFICS_II(G) \ G(1,1) G(1,2) G(1,4) G(1,8) G(1,16) \ G(2,1) G(2,2) G(2,4) G(2,8) G(2,16) \ G(4,1) G(4,2) G(4,4) G(4,8) G(4,16) \ G(8,1) G(8,2) G(8,4) G(8,8) G(8,16) \ G(16,1) G(16,2) G(16,4) G(16,8) G(16,16) + +#if FLANG_SUPPORT_R16 #if __x86_64__ #define SPECIFICS_RI(G) \ G(2,1) G(2,2) G(2,4) G(2,8) G(2,16) \ @@ -190,7 +204,24 @@ end function ieee_round_ne G(8,1) G(8,2) G(8,4) G(8,8) G(8,16) \ G(16,1) G(16,2) G(16,4) G(16,8) G(16,16) #endif +#else +#if __x86_64__ +#define SPECIFICS_RI(G) \ + G(2,1) G(2,2) G(2,4) G(2,8) \ + G(3,1) G(3,2) G(3,4) G(3,8) \ + G(4,1) G(4,2) G(4,4) G(4,8) \ + G(8,1) G(8,2) G(8,4) G(8,8) \ + G(10,1) G(10,2) G(10,4) G(10,8) +#else +#define SPECIFICS_RI(G) \ + G(2,1) G(2,2) G(2,4) G(2,8) \ + G(3,1) G(3,2) G(3,4) G(3,8) \ + G(4,1) G(4,2) G(4,4) G(4,8) \ + G(8,1) G(8,2) G(8,4) G(8,8) +#endif +#endif +#if FLANG_SUPPORT_R16 #if __x86_64__ #define SPECIFICS_RR(G) \ G(2,2) G(2,3) G(2,4) G(2,8) G(2,10) G(2,16) \ @@ -207,6 +238,22 @@ end function ieee_round_ne G(8,2) G(8,3) G(8,4) G(8,8) G(8,16) \ G(16,2) G(16,3) G(16,4) G(16,8) G(16,16) #endif +#else +#if __x86_64__ +#define SPECIFICS_RR(G) \ + G(2,2) G(2,3) G(2,4) G(2,8) G(2,10) \ + G(3,2) G(3,3) G(3,4) G(3,8) G(3,10) \ + G(4,2) G(4,3) G(4,4) G(4,8) G(4,10) \ + G(8,2) G(8,3) G(8,4) G(8,8) G(8,10) \ + G(10,2) G(10,3) G(10,4) G(10,8) G(10,10) +#else +#define SPECIFICS_RR(G) \ + G(2,2) G(2,3) G(2,4) G(2,8) \ + G(3,2) G(3,3) G(3,4) G(3,8) \ + G(4,2) G(4,3) G(4,4) G(4,8) \ + G(8,2) G(8,3) G(8,4) G(8,8) +#endif +#endif #define IEEE_CLASS_R(XKIND) \ elemental type(ieee_class_type) function ieee_class_a##XKIND(x); \ @@ -462,8 +509,10 @@ end function ieee_real_a##AKIND##_i##KKIND; interface ieee_real SPECIFICS_I(IEEE_REAL_I) SPECIFICS_R(IEEE_REAL_R) +#if FLANG_SUPPORT_R16 SPECIFICS_II(IEEE_REAL_II) SPECIFICS_RI(IEEE_REAL_RI) +#endif end interface ieee_real public :: ieee_real #undef IEEE_REAL_I diff --git a/flang/test/CMakeLists.txt b/flang/test/CMakeLists.txt index 43ad1e3312b64..a18a5c6519eda 100644 --- a/flang/test/CMakeLists.txt +++ b/flang/test/CMakeLists.txt @@ -11,6 +11,16 @@ llvm_canonicalize_cmake_booleans( set(FLANG_TOOLS_DIR ${FLANG_BINARY_DIR}/bin) +# Check if 128-bit float computations can be done via long double +check_cxx_source_compiles( + "#include + #if LDBL_MANT_DIG != 113 + #error LDBL_MANT_DIG != 113 + #endif + int main() { return 0; } + " + HAVE_LDBL_MANT_DIG_113) + # FIXME In out-of-tree builds, "SHLIBDIR" is undefined and passing it to # `configure_lit_site_cfg` leads to a configuration error. This is currently # only required by plugins/examples, which are not supported in out-of-tree diff --git a/flang/test/Evaluate/fold-out_of_range.f90 b/flang/test/Evaluate/fold-out_of_range.f90 index 5a9f900beb2d5..6360eee5322bb 100644 --- a/flang/test/Evaluate/fold-out_of_range.f90 +++ b/flang/test/Evaluate/fold-out_of_range.f90 @@ -1,6 +1,7 @@ ! RUN: %python %S/test_folding.py %s %flang_fc1 -pedantic -triple x86_64-unknown-linux-gnu ! UNSUPPORTED: system-windows ! REQUIRES: target=x86_64{{.*}} +! REQUIRES: flang-supports-f128-math ! Tests folding of OUT_OF_RANGE(). module m integer(1), parameter :: i1v(*) = [ -huge(1_1) - 1_1, huge(1_1) ] diff --git a/flang/test/Evaluate/folding07.f90 b/flang/test/Evaluate/folding07.f90 index 3b6a99df38826..d51df7acf7b8a 100644 --- a/flang/test/Evaluate/folding07.f90 +++ b/flang/test/Evaluate/folding07.f90 @@ -1,3 +1,4 @@ +! REQUIRES: flang-supports-f128-math ! RUN: %python %S/test_folding.py %s %flang_fc1 ! Test numeric model inquiry intrinsics diff --git a/flang/test/Lower/Intrinsics/ieee_class_queries.f90 b/flang/test/Lower/Intrinsics/ieee_class_queries.f90 index bb7787ea903e2..b2f9df83a902a 100644 --- a/flang/test/Lower/Intrinsics/ieee_class_queries.f90 +++ b/flang/test/Lower/Intrinsics/ieee_class_queries.f90 @@ -1,3 +1,4 @@ +! REQUIRES: flang-supports-f128-math ! RUN: bbc -emit-fir -o - %s | FileCheck %s ! CHECK-LABEL: func @_QQmain diff --git a/flang/test/Lower/Intrinsics/ieee_unordered.f90 b/flang/test/Lower/Intrinsics/ieee_unordered.f90 index a6146eff7f06e..b7e81d53a2d75 100644 --- a/flang/test/Lower/Intrinsics/ieee_unordered.f90 +++ b/flang/test/Lower/Intrinsics/ieee_unordered.f90 @@ -1,3 +1,4 @@ +! REQUIRES: flang-supports-f128-math ! RUN: bbc -emit-fir -hlfir=false -o - %s | FileCheck %s ! CHECK-LABEL: func @_QQmain diff --git a/flang/test/Lower/common-block.f90 b/flang/test/Lower/common-block.f90 index 94e61b8bcc33d..b5c1389df45d3 100644 --- a/flang/test/Lower/common-block.f90 +++ b/flang/test/Lower/common-block.f90 @@ -1,3 +1,4 @@ +! REQUIRES: flang-supports-f128-math ! RUN: bbc %s -o - | tco | FileCheck %s ! RUN: %flang -emit-llvm -S -mmlir -disable-external-name-interop %s -o - | FileCheck %s @@ -78,4 +79,3 @@ subroutine s7() real(16) r16 common /co1/ r16 end subroutine - diff --git a/flang/test/Semantics/kinds03.f90 b/flang/test/Semantics/kinds03.f90 index 751d4a9ffa3cb..a15a4a9baa731 100644 --- a/flang/test/Semantics/kinds03.f90 +++ b/flang/test/Semantics/kinds03.f90 @@ -1,3 +1,4 @@ +! REQUIRES: flang-supports-f128-math ! RUN: %python %S/test_symbols.py %s %flang_fc1 !DEF: /MainProgram1/ipdt DerivedType !DEF: /MainProgram1/ipdt/k TypeParam INTEGER(4) diff --git a/flang/test/Semantics/modfile26.f90 b/flang/test/Semantics/modfile26.f90 index 09dc8b0954d63..9c5d0015d9163 100644 --- a/flang/test/Semantics/modfile26.f90 +++ b/flang/test/Semantics/modfile26.f90 @@ -1,3 +1,4 @@ +! REQUIRES: flang-supports-f128-math ! RUN: %python %S/test_modfile.py %s %flang_fc1 ! Intrinsics SELECTED_INT_KIND, SELECTED_REAL_KIND, PRECISION, RANGE, ! RADIX, DIGITS diff --git a/flang/test/Semantics/realkinds-aarch64-01.f90 b/flang/test/Semantics/realkinds-aarch64-01.f90 index e22920ff991e9..2520c0b84c0e6 100644 --- a/flang/test/Semantics/realkinds-aarch64-01.f90 +++ b/flang/test/Semantics/realkinds-aarch64-01.f90 @@ -1,4 +1,5 @@ ! REQUIRES: aarch64-registered-target +! REQUIRES: flang-supports-f128-math ! RUN: %python %S/test_modfile.py %s %flang_fc1 -triple aarch64-unknown-linux-gnu module m1 diff --git a/flang/test/lit.cfg.py b/flang/test/lit.cfg.py index 37869e7e2ecd7..4acbc0606d197 100644 --- a/flang/test/lit.cfg.py +++ b/flang/test/lit.cfg.py @@ -216,8 +216,9 @@ # Add features and substitutions to test F128 math support. # %f128-lib substitution may be used to generate check prefixes # for LIT tests checking for F128 library support. -if config.flang_runtime_f128_math_lib: +if config.flang_runtime_f128_math_lib or config.have_ldbl_mant_dig_113: config.available_features.add("flang-supports-f128-math") +if config.flang_runtime_f128_math_lib: config.available_features.add( "flang-f128-math-lib-" + config.flang_runtime_f128_math_lib ) diff --git a/flang/test/lit.site.cfg.py.in b/flang/test/lit.site.cfg.py.in index fe6186d714071..d1a0ac763cf8a 100644 --- a/flang/test/lit.site.cfg.py.in +++ b/flang/test/lit.site.cfg.py.in @@ -31,6 +31,7 @@ if "openmp" in "@LLVM_ENABLE_RUNTIMES@".lower().split(";"): else: config.openmp_module_dir = None config.flang_runtime_f128_math_lib = "@FLANG_RUNTIME_F128_MATH_LIB@" +config.have_ldbl_mant_dig_113 = "@HAVE_LDBL_MANT_DIG_113@" import lit.llvm lit.llvm.initialize(lit_config, config) diff --git a/flang/tools/f18/CMakeLists.txt b/flang/tools/f18/CMakeLists.txt index cec4e2d810720..344a781c41e95 100644 --- a/flang/tools/f18/CMakeLists.txt +++ b/flang/tools/f18/CMakeLists.txt @@ -31,6 +31,25 @@ set(MODULES_WITHOUT_IMPLEMENTATION set(MODULES ${MODULES_WITH_IMPLEMENTATION} ${MODULES_WITHOUT_IMPLEMENTATION}) +# Check if 128-bit float computations can be done via long double. +check_cxx_source_compiles( + "#include + #if LDBL_MANT_DIG != 113 + #error LDBL_MANT_DIG != 113 + #endif + int main() { return 0; } + " + HAVE_LDBL_MANT_DIG_113) + +# Figure out whether we can support REAL(KIND=16) +if (FLANG_RUNTIME_F128_MATH_LIB) + set(FLANG_SUPPORT_R16 "1") +elseif (HAVE_LDBL_MANT_DIG_113) + set(FLANG_SUPPORT_R16 "1") +else() + set(FLANG_SUPPORT_R16 "0") +endif() + # Init variable to hold extra object files coming from the Fortran modules; # these module files will be contributed from the CMakeLists in flang/tools/f18. set(module_objects "") @@ -76,6 +95,10 @@ if (NOT CMAKE_CROSSCOMPILING) endif() endif() + set(decls "") + if (FLANG_SUPPORT_R16) + set(decls "-DFLANG_SUPPORT_R16") + endif() # Some modules have an implementation part that needs to be added to the # FortranRuntime library. @@ -92,7 +115,7 @@ if (NOT CMAKE_CROSSCOMPILING) # TODO: We may need to flag this with conditional, in case Flang is built w/o OpenMP support add_custom_command(OUTPUT ${base}.mod ${object_output} COMMAND ${CMAKE_COMMAND} -E make_directory ${FLANG_INTRINSIC_MODULES_DIR} - COMMAND flang-new ${opts} -cpp ${compile_with} -module-dir ${FLANG_INTRINSIC_MODULES_DIR} + COMMAND flang-new ${opts} ${decls} -cpp ${compile_with} -module-dir ${FLANG_INTRINSIC_MODULES_DIR} ${FLANG_SOURCE_DIR}/module/${filename}.f90 DEPENDS flang-new ${FLANG_SOURCE_DIR}/module/${filename}.f90 ${FLANG_SOURCE_DIR}/module/__fortran_builtins.f90 ${depends} ) From 67b1f42b7d70a0e19d9ac0390cb9a7ef5804080a Mon Sep 17 00:00:00 2001 From: Tom Eccles Date: Wed, 4 Sep 2024 10:43:54 +0000 Subject: [PATCH 2/2] Add TODO message --- flang/include/flang/Tools/TargetSetup.h | 2 ++ 1 file changed, 2 insertions(+) diff --git a/flang/include/flang/Tools/TargetSetup.h b/flang/include/flang/Tools/TargetSetup.h index 60609de8809cf..a3b9045b80805 100644 --- a/flang/include/flang/Tools/TargetSetup.h +++ b/flang/include/flang/Tools/TargetSetup.h @@ -29,6 +29,8 @@ namespace Fortran::tools { // Figure out if we can support F128: see // flang/runtime/Float128Math/math-entries.h + // TODO: this should be taken from TargetInfo::getLongDoubleFormat to support + // cross-compilation #ifdef FLANG_RUNTIME_F128_MATH_LIB // we can use libquadmath wrappers constexpr bool f128Support = true;