mirror of
https://github.com/llvm/llvm-project.git
synced 2025-04-16 00:16:30 +00:00
Revert "[Flang] [FlangRT] Introduce FlangRT project as solution to Flang's runtime LLVM integration"
This reverts commit 6403287eff71a3d6f6c862346d6ed3f0f000eb70. This is failing on all but 1 of Linaro's flang builders. CMake Error at /home/tcwg-buildbot/worker/clang-aarch64-full-2stage/llvm/flang-rt/unittests/CMakeLists.txt:37 (message): Target llvm_gtest not found.
This commit is contained in:
parent
43198b0aa2
commit
ffc67bb360
@ -969,41 +969,29 @@ void tools::addFortranRuntimeLibs(const ToolChain &TC,
|
||||
llvm::opt::ArgStringList &CmdArgs) {
|
||||
if (TC.getTriple().isKnownWindowsMSVCEnvironment()) {
|
||||
CmdArgs.push_back("Fortran_main.lib");
|
||||
CmdArgs.push_back("flang-rt.lib");
|
||||
CmdArgs.push_back("FortranRuntime.lib");
|
||||
CmdArgs.push_back("FortranDecimal.lib");
|
||||
} else {
|
||||
CmdArgs.push_back("-lFortran_main");
|
||||
CmdArgs.push_back("-lflang-rt");
|
||||
CmdArgs.push_back("-lFortranRuntime");
|
||||
CmdArgs.push_back("-lFortranDecimal");
|
||||
}
|
||||
}
|
||||
|
||||
void tools::addFortranRuntimeLibraryPath(const ToolChain &TC,
|
||||
const llvm::opt::ArgList &Args,
|
||||
ArgStringList &CmdArgs) {
|
||||
// Default to the <driver-path>/../lib, <driver-path>/../flang-rt/lib, and
|
||||
// <driver-path>/../runtimes/runtimes-bins/flang-rt/lib directories. This
|
||||
// works fine on the platforms that we have tested so far. We will probably
|
||||
// have to re-fine this in the future. In particular, on some platforms, we
|
||||
// may need to use lib64 instead of lib.
|
||||
SmallString<256> BuildLibPath =
|
||||
// Default to the <driver-path>/../lib directory. This works fine on the
|
||||
// platforms that we have tested so far. We will probably have to re-fine
|
||||
// this in the future. In particular, on some platforms, we may need to use
|
||||
// lib64 instead of lib.
|
||||
SmallString<256> DefaultLibPath =
|
||||
llvm::sys::path::parent_path(TC.getDriver().Dir);
|
||||
SmallString<256> FlangRTLibPath =
|
||||
llvm::sys::path::parent_path(TC.getDriver().Dir);
|
||||
SmallString<256> RuntimesLibPath =
|
||||
llvm::sys::path::parent_path(TC.getDriver().Dir);
|
||||
// Search path for Fortran_main and Flang-rt libraries.
|
||||
llvm::sys::path::append(BuildLibPath, "lib");
|
||||
llvm::sys::path::append(FlangRTLibPath, "flang-rt/lib");
|
||||
llvm::sys::path::append(RuntimesLibPath,
|
||||
"runtimes/runtimes-bins/flang-rt/lib");
|
||||
if (TC.getTriple().isKnownWindowsMSVCEnvironment()) {
|
||||
CmdArgs.push_back(Args.MakeArgString("-libpath:" + BuildLibPath));
|
||||
CmdArgs.push_back(Args.MakeArgString("-libpath:" + FlangRTLibPath));
|
||||
CmdArgs.push_back(Args.MakeArgString("-libpath:" + RuntimesLibPath));
|
||||
} else {
|
||||
CmdArgs.push_back(Args.MakeArgString("-L" + BuildLibPath));
|
||||
CmdArgs.push_back(Args.MakeArgString("-L" + FlangRTLibPath));
|
||||
CmdArgs.push_back(Args.MakeArgString("-L" + RuntimesLibPath));
|
||||
}
|
||||
llvm::sys::path::append(DefaultLibPath, "lib");
|
||||
if (TC.getTriple().isKnownWindowsMSVCEnvironment())
|
||||
CmdArgs.push_back(Args.MakeArgString("-libpath:" + DefaultLibPath));
|
||||
else
|
||||
CmdArgs.push_back(Args.MakeArgString("-L" + DefaultLibPath));
|
||||
}
|
||||
|
||||
static void addSanitizerRuntime(const ToolChain &TC, const ArgList &Args,
|
||||
|
@ -1,148 +0,0 @@
|
||||
# CMake build for the Flang runtime libraries
|
||||
# The source for the flang runtime libraries (FortranDecimalRT, FortranRuntime)
|
||||
# exist in the flang top-level directory.
|
||||
# Flang-rt is only scaffolding and does not provide any additional source files.
|
||||
|
||||
cmake_minimum_required(VERSION 3.20.0)
|
||||
|
||||
#===============================================================================
|
||||
# Configure CMake
|
||||
#===============================================================================
|
||||
set(LLVM_COMMON_CMAKE_UTILS "${CMAKE_CURRENT_SOURCE_DIR}/../cmake")
|
||||
include(${LLVM_COMMON_CMAKE_UTILS}/Modules/CMakePolicy.cmake
|
||||
NO_POLICY_SCOPE)
|
||||
|
||||
set(CMAKE_BUILD_WITH_INSTALL_NAME_DIR ON)
|
||||
set(CMAKE_INCLUDE_CURRENT_DIR ON)
|
||||
|
||||
set(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/flang-rt/bin)
|
||||
set(CMAKE_LIBRARY_OUTPUT_DIRECTORY
|
||||
${CMAKE_BINARY_DIR}/flang-rt/lib)
|
||||
set(CMAKE_ARCHIVE_OUTPUT_DIRECTORY
|
||||
${CMAKE_BINARY_DIR}/flang-rt/lib)
|
||||
set(CMAKE_CURRENT_BINARY_DIR ${CMAKE_BINARY_DIR}/flang-rt)
|
||||
|
||||
set(FLANG_RT_SOURCE_DIR "${CMAKE_CURRENT_SOURCE_DIR}")
|
||||
set(FLANG_RT_BINARY_DIR "${CMAKE_CURRENT_BINARY_DIR}")
|
||||
|
||||
#===============================================================================
|
||||
# Setup Options and Defaults
|
||||
#===============================================================================
|
||||
option(FLANG_RT_ENABLE_SHARED "Build flang-rt as a shared library." OFF)
|
||||
option(FLANG_RT_ENABLE_STATIC "Build flang-rt as a static library." OFF)
|
||||
|
||||
option(FLANG_RT_INCLUDE_TESTS
|
||||
"Generate build targets for the Flang-rt unit tests." ${LLVM_INCLUDE_TESTS})
|
||||
|
||||
# MLIR_DIR must be passed on invocation of flang-rt because it is needed for the Flang package.
|
||||
if(NOT DEFINED MLIR_DIR OR MLIR_DIR STREQUAL "")
|
||||
message(FATAL_ERROR "MLIR_DIR must be set to the directory of the MLIRConfig cmake file in order to find the MLIR package.")
|
||||
endif()
|
||||
# Flang-rt requires a pre-built/installed version of flang that requires MLIR.
|
||||
find_package(MLIR REQUIRED HINTS "${MLIR_DIR}")
|
||||
|
||||
# FLANG_DIR must be passed on invocation of flang-rt.
|
||||
if(NOT DEFINED FLANG_DIR OR FLANG_DIR STREQUAL "")
|
||||
message(FATAL_ERROR "FLANG_DIR must be set to the directory of the FlangConfig cmake file in order to find the Flang package.")
|
||||
endif()
|
||||
# Flang-rt requires a pre-built/installed version of flang.
|
||||
# Flang-rt uses flang/Common headers.
|
||||
# Finding this package exposes FLANG_SOURCE_DIR, FLANG_BINARY_DIR, and FLANG_INCLUDE_DIRS to Flang-rt
|
||||
find_package(Flang REQUIRED HINTS "${FLANG_DIR}")
|
||||
# If the user specifies a relative path to LLVM_DIR, the calls to include
|
||||
# LLVM modules fail. Append the absolute path to LLVM_DIR instead.
|
||||
get_filename_component(FLANG_DIR_ABSOLUTE ${FLANG_DIR} REALPATH)
|
||||
list(APPEND CMAKE_MODULE_PATH ${FLANG_DIR_ABSOLUTE})
|
||||
|
||||
set(LLVM_COMMON_CMAKE_UTILS "${FLANG_RT_SOURCE_DIR}/../cmake")
|
||||
set(LLVM_CMAKE_UTILS "${LLVM_BUILD_MAIN_SOURCE_DIR}/cmake")
|
||||
set(CLANG_CMAKE_UTILS "${FLANG_RT_SOURCE_DIR}/../clang/cmake")
|
||||
|
||||
if (FLANG_RT_INCLUDE_TESTS)
|
||||
# LLVM_DIR must be passed on invocation of flang-rt when tests are enabled.
|
||||
if(NOT DEFINED LLVM_DIR OR LLVM_DIR STREQUAL "")
|
||||
message(FATAL_ERROR "LLVM_DIR must be set to the directory of the LLVMConfig cmake file in order to find the LLVM package.")
|
||||
endif()
|
||||
# We need a pre-built/installed version of LLVM for gtest.
|
||||
find_package(LLVM REQUIRED HINTS "${LLVM_DIR}")
|
||||
# If the user specifies a relative path to LLVM_DIR, the calls to include
|
||||
# LLVM modules fail. Append the absolute path to LLVM_DIR instead.
|
||||
get_filename_component(LLVM_DIR_ABSOLUTE ${LLVM_DIR} REALPATH)
|
||||
list(APPEND CMAKE_MODULE_PATH ${LLVM_DIR_ABSOLUTE})
|
||||
|
||||
add_compile_definitions(FLANG_RT_INCLUDE_TESTS=1)
|
||||
|
||||
if (DEFINED FLANG_BINARY_DIR)
|
||||
set(FLANG_BINARY_DIR ${FLANG_BINARY_DIR} CACHE PATH "Path to the Flang build directory" FORCE)
|
||||
else()
|
||||
message(FATAL_ERROR "FLANG_BINARY_DIR must be defined or passed by the user when building tests.")
|
||||
endif()
|
||||
set(FLANG_RT_TEST_COMPILER ${FLANG_BINARY_DIR}/bin/flang-new
|
||||
CACHE PATH "Compiler to use for testing")
|
||||
set(FLANG_RT_GTEST_AVAIL 1)
|
||||
endif()
|
||||
|
||||
# Add path for custom modules
|
||||
list(INSERT CMAKE_MODULE_PATH 0
|
||||
"${FLANG_SOURCE_DIR}/cmake"
|
||||
"${FLANG_SOURCE_DIR}/cmake/modules"
|
||||
"${CLANG_CMAKE_UTILS}/modules"
|
||||
"${LLVM_CMAKE_UTILS}/modules"
|
||||
)
|
||||
|
||||
include(AddClang)
|
||||
include(AddFlang)
|
||||
include(TestBigEndian)
|
||||
test_big_endian(IS_BIGENDIAN)
|
||||
if (IS_BIGENDIAN)
|
||||
add_compile_definitions(FLANG_BIG_ENDIAN=1)
|
||||
else ()
|
||||
add_compile_definitions(FLANG_LITTLE_ENDIAN=1)
|
||||
endif ()
|
||||
|
||||
# Flang's include directories are needed for flang/Common.
|
||||
include_directories(SYSTEM ${FLANG_INCLUDE_DIRS})
|
||||
|
||||
# LLVM's include directories are needed for gtest.
|
||||
include_directories(SYSTEM ${LLVM_INCLUDE_DIRS})
|
||||
|
||||
#===============================================================================
|
||||
# Add Subdirectories
|
||||
#===============================================================================
|
||||
set(FORTRAN_DECIMAL_SRC "${FLANG_SOURCE_DIR}/lib/Decimal")
|
||||
set(FORTRAN_RUNTIME_SRC "${FLANG_SOURCE_DIR}/runtime")
|
||||
set(FORTRAN_MAIN_SRC "${FLANG_SOURCE_DIR}/runtime/FortranMain")
|
||||
|
||||
add_subdirectory(${FORTRAN_DECIMAL_SRC} FortranDecimalRT)
|
||||
add_subdirectory(${FORTRAN_RUNTIME_SRC} FortranRuntime)
|
||||
add_subdirectory(${FORTRAN_MAIN_SRC} FortranMain)
|
||||
|
||||
if (FLANG_RT_INCLUDE_TESTS)
|
||||
add_subdirectory(test)
|
||||
if (FLANG_RT_GTEST_AVAIL)
|
||||
add_subdirectory(unittests)
|
||||
endif()
|
||||
endif()
|
||||
|
||||
#===============================================================================
|
||||
# Create Flang-rt wrapper library
|
||||
#===============================================================================
|
||||
# Build as shared by default if no linkage type option set.
|
||||
if (NOT FLANG_RT_ENABLE_SHARED AND NOT FLANG_RT_ENABLE_STATIC)
|
||||
add_library(flang-rt SHARED $<TARGET_OBJECTS:obj.FortranDecimalRT>
|
||||
$<TARGET_OBJECTS:obj.FortranRuntime>)
|
||||
endif()
|
||||
if (FLANG_RT_ENABLE_SHARED)
|
||||
add_library(flang-rt SHARED $<TARGET_OBJECTS:obj.FortranDecimalRT>
|
||||
$<TARGET_OBJECTS:obj.FortranRuntime>)
|
||||
endif()
|
||||
if (FLANG_RT_ENABLE_STATIC AND NOT FLANG_RT_ENABLE_SHARED)
|
||||
add_library(flang-rt STATIC $<TARGET_OBJECTS:obj.FortranDecimalRT>
|
||||
$<TARGET_OBJECTS:obj.FortranRuntime>)
|
||||
endif()
|
||||
# When building both static and shared, we need to append _static to the name
|
||||
# to avoid naming conflicts.
|
||||
if (FLANG_RT_ENABLE_STATIC AND FLANG_RT_ENABLE_SHARED)
|
||||
add_library(flang-rt_static STATIC $<TARGET_OBJECTS:obj.FortranDecimalRT>
|
||||
$<TARGET_OBJECTS:obj.FortranRuntime>)
|
||||
endif()
|
@ -1,156 +0,0 @@
|
||||
<!--===- docs/GettingStarted.md
|
||||
|
||||
Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
|
||||
See https://llvm.org/LICENSE.txt for license information.
|
||||
SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
|
||||
|
||||
-->
|
||||
|
||||
# Flang-rt Runtime Library
|
||||
|
||||
```eval_rst
|
||||
.. contents::
|
||||
:local:
|
||||
```
|
||||
## What is Flang-rt
|
||||
Flang-rt is the runtime library project for Flang. The Flang driver requires
|
||||
the Fortran_main and Flang-rt libraries at runtime in order to generate
|
||||
user executables. Building this Flang-rt project will build both Fortran_main
|
||||
and the Flang-rt library, which is comprised of the FortranRuntime and
|
||||
FortranDecimalRT libraries.
|
||||
|
||||
### Fortran_main
|
||||
Fortran_main is left out of the Flang-rt library because it is required to
|
||||
always be static unlike the link type of the Flang-rt library which can be
|
||||
configured. Fortran_main implements the main entry point into Fortran's
|
||||
`PROGRAM` in Flang by being the bridge between object files generated by Flang
|
||||
and the C runtime that takes care of program set-up at system-level. For
|
||||
every Fortran `PROGRAM`, Flang generates the `_QQmain` function.
|
||||
Fortran_main implements the C `main` function that simply calls
|
||||
`_QQmain`.
|
||||
|
||||
### FortranDecimalRT
|
||||
In order to decouple the common dependency between compiler and runtime,
|
||||
[FortranDecimal's sources](../../flang/lib/Decimal/CMakeLists.txt) are built
|
||||
separately for the compiler and the runtime. When the library is built for
|
||||
Flang-rt, the name FortranDecimalRT is used to avoid naming conflicts and
|
||||
confusion.
|
||||
|
||||
### FortranRuntime
|
||||
This is the core runtime library in Flang-rt. The sources for this library
|
||||
currently still exist in the
|
||||
[Flang source directory](../../flang/runtime/CMakeLists.txt). We hope to
|
||||
migrate the sources to the Flang-rt directory in the future in order to further
|
||||
decouple the runtime from the Flang compiler.
|
||||
|
||||
## Building Flang-rt
|
||||
Like other LLVM runtimes, Flang-rt can be built by targetting the
|
||||
[runtimes LLVM target](../../runtimes/CMakelists.txt). It can also be built
|
||||
when targetting the [llvm target](../../llvm/CMakeLists.txt) as an enabled
|
||||
runtime. Flang-rt will implicitly be added as an enabled runtime when Flang
|
||||
is an enabled project built by llvm. Flang-rt does not support standalone
|
||||
builds.
|
||||
|
||||
In the future, we may be interested in supporting in optionally building
|
||||
Flang-rt when doing a Flang standalone build.
|
||||
|
||||
### Building with the llvm target
|
||||
Assuming you are building Flang-rt to use with Flang, see
|
||||
[Flang's Getting Started guide](../../flang/docs/GettingStarted.md) for more
|
||||
information. To build Flang-rt when building the Flang compiler, once you have
|
||||
the llvm-project source ready, make a clean build directory. Let root be the
|
||||
root directory that you cloned llvm-project into.
|
||||
```bash
|
||||
cd root
|
||||
rm -rf build
|
||||
mkdir build
|
||||
cd build
|
||||
```
|
||||
Now invoke the cmake configuration command for llvm that would build Flang with
|
||||
Flang-rt.
|
||||
```bash
|
||||
cmake \
|
||||
-G Ninja \
|
||||
-DLLVM_ENABLE_RUNTIMES="compiler-rt;flang-rt" \
|
||||
-DCMAKE_CXX_STANDARD=17 \
|
||||
-DLLVM_INSTALL_UTILS=On \
|
||||
# New Flang-rt flags for enabled link types
|
||||
-DFLANG_RT_ENABLE_STATIC=On \
|
||||
-DFLANG_RT_ENABLE_SHARED=On \
|
||||
# We need to enable GTest if we want to run Flang-rt's testsuites
|
||||
-DLLVM_INSTALL_GTEST=On \
|
||||
-DFLANG_ENABLE_WERROR=On \
|
||||
-DLLVM_LIT_ARGS=-v \
|
||||
-DCMAKE_BUILD_TYPE=Release \
|
||||
-DLLVM_ENABLE_PROJECTS="clang;flang;lld;mlir;openmp" \
|
||||
../llvm-project/llvm
|
||||
```
|
||||
Flang requires other llvm projects (see LLVM_ENABLE_PROJECTS and the [Flang
|
||||
Getting Started Guide](../../flang/docs/GettingStarted.md) for more specifics
|
||||
on building Flang.
|
||||
|
||||
By targetting the LLVM project, we are letting LLVM infrastructure handle
|
||||
invoking the runtimes target that will build Flang-rt. This includes finding
|
||||
the cmake packages for Clang, LLVM, Flang and MLIR that Flang-rt depends on.
|
||||
|
||||
### Building with the runtimes target
|
||||
If you already have a pre-built/installed version of LLVM, Flang, Clang and
|
||||
MLIR, and would like to build Flang-rt without rebuilding the sources for these
|
||||
other projects. You can simply target the runtimes project directly and passing
|
||||
the paths to the directories of these files. If you built LLVM as we did above
|
||||
with default build directories, your runtimes invocation should look something
|
||||
like:
|
||||
```bash
|
||||
cd build
|
||||
BUILDDIR=`pwd`
|
||||
|
||||
cmake \
|
||||
-G Ninja \
|
||||
-DCMAKE_CXX_STANDARD=17 \
|
||||
# New Flang-rt flags for enabled link types
|
||||
-DFLANG_RT_ENABLE_SHARED=On \
|
||||
-DFLANG_RT_ENABLE_STATIC=On \
|
||||
-DLLVM_LIT_ARGS=-v \
|
||||
-DCMAKE_BUILD_TYPE=Release \
|
||||
-DCMAKE_CXX_LINK_FLAGS="-Wl,-rpath,$LD_LIBRARY_PATH" \
|
||||
-DLLVM_TARGETS_TO_BUILD=host \
|
||||
-DLLVM_EXTERNAL_LIT=$BUILD_DIR/bin/llvm-lit \
|
||||
# We need to specify the paths to the cmake packages of the dependencies
|
||||
-DLLVM_DIR=$BUILD_DIR/lib/cmake/llvm \
|
||||
-DMLIR_DIR=$BUILD_DIR/lib/cmake/mlir \
|
||||
-DFLANG_DIR=$BUILD_DIR/lib/cmake/flang \
|
||||
-DLLVM_ENABLE_RUNTIMES="flang-rt" \
|
||||
../llvm-project/runtimes/
|
||||
```
|
||||
|
||||
## Library locations
|
||||
When building the llvm target with flang as an enabled project, the Flang-rt
|
||||
library will be built to `$BUILDDIR/runtimes/runtimes-bins/flang-rt/lib`. When
|
||||
building the runtimes target with flang-rt as an enabled runtime, the libraries
|
||||
will be built to `$BUILDDIR/flang-rt/lib` by default. In either configuration,
|
||||
the Fortran_main library will be built to `$BUILDDIR/lib` by default.
|
||||
|
||||
## Using Flang-rt
|
||||
The two build paths mentioned above get implicitly added as library paths at the
|
||||
invocation of the driver. If Flang-rt is a shared library, you must make the
|
||||
dynamic linker aware of where to look. One method to do so is to set the
|
||||
environment variable `LD_LIBRARY_PATH` include the path to Flang-rt's directory.
|
||||
|
||||
## Options
|
||||
Flang-rt introduces 2 CMake options used to configure the library's link type:
|
||||
```
|
||||
option(FLANG_RT_ENABLE_SHARED "Build flang-rt as a shared library." OFF)
|
||||
option(FLANG_RT_ENABLE_STATIC "Build flang-rt as a static library." OFF)
|
||||
```
|
||||
Both can be specified if you want to build both shared and static versions of
|
||||
the Flang-rt runtime. If both are specified, the static library will be named
|
||||
Flang-rt_static.a to avoid naming conflicts, as per the LLVM standard.
|
||||
|
||||
## Usage Examples
|
||||
```bash
|
||||
# Example of using Flang with the shared Flang-rt runtime
|
||||
# First we need to explicitly tell the dynamic linker where to find Flang-rt
|
||||
# since it was built as shared.
|
||||
$ $ export LD_LIBRARY_PATH="$LD_LIBRARY_PATH:$BUILDDIR/runtimes/runtimes-bins/flang-rt/lib"
|
||||
$ flang-new -ffree-form hello.f95 -o hello
|
||||
```
|
@ -1,73 +0,0 @@
|
||||
# Test runner infrastructure for Flang-rt. This configures the Flang-rt test
|
||||
# trees for use by Lit, and delegates to LLVM's lit test handlers.
|
||||
|
||||
llvm_canonicalize_cmake_booleans(
|
||||
FLANG_STANDALONE_BUILD
|
||||
LLVM_BUILD_EXAMPLES
|
||||
LLVM_BYE_LINK_INTO_TOOLS
|
||||
LLVM_ENABLE_PLUGINS
|
||||
)
|
||||
|
||||
set(FLANG_TOOLS_DIR ${FLANG_BINARY_DIR}/bin)
|
||||
|
||||
configure_lit_site_cfg(
|
||||
${CMAKE_CURRENT_SOURCE_DIR}/lit.site.cfg.py.in
|
||||
${CMAKE_CURRENT_BINARY_DIR}/lit.site.cfg.py
|
||||
MAIN_CONFIG
|
||||
${CMAKE_CURRENT_SOURCE_DIR}/lit.cfg.py
|
||||
PATHS
|
||||
${PATHS_FOR_PLUGINS}
|
||||
)
|
||||
|
||||
configure_lit_site_cfg(
|
||||
${CMAKE_CURRENT_SOURCE_DIR}/Unit/lit.site.cfg.py.in
|
||||
${CMAKE_CURRENT_BINARY_DIR}/Unit/lit.site.cfg.py
|
||||
MAIN_CONFIG
|
||||
${CMAKE_CURRENT_SOURCE_DIR}/Unit/lit.cfg.py
|
||||
)
|
||||
|
||||
configure_lit_site_cfg(
|
||||
${CMAKE_CURRENT_SOURCE_DIR}/NonGtestUnit/lit.site.cfg.py.in
|
||||
${CMAKE_CURRENT_BINARY_DIR}/NonGtestUnit/lit.site.cfg.py
|
||||
MAIN_CONFIG
|
||||
${CMAKE_CURRENT_SOURCE_DIR}/NonGtestUnit/lit.cfg.py
|
||||
)
|
||||
|
||||
set(FLANG_RT_TEST_PARAMS
|
||||
flang_rt_site_config=${CMAKE_CURRENT_BINARY_DIR}/lit.site.cfg.py)
|
||||
|
||||
set(FLANG_RT_TEST_DEPENDS
|
||||
LLVMSupport
|
||||
flang-rt
|
||||
Fortran_main
|
||||
)
|
||||
if (LLVM_ENABLE_PLUGINS AND NOT WIN32)
|
||||
list(APPEND FLANG_RT_TEST_DEPENDS Bye)
|
||||
endif()
|
||||
|
||||
if (FLANG_RT_INCLUDE_TESTS)
|
||||
if (FLANG_RT_GTEST_AVAIL)
|
||||
list(APPEND FLANG_RT_TEST_DEPENDS FlangRTUnitTests)
|
||||
endif()
|
||||
endif()
|
||||
|
||||
add_custom_target(flang-rt-test-depends DEPENDS ${FLANG_RT_TEST_DEPENDS})
|
||||
|
||||
add_lit_testsuite(check-flang-rt "Running the Flang-rt regression tests"
|
||||
${CMAKE_CURRENT_BINARY_DIR}
|
||||
PARAMS ${FLANG_RT_TEST_PARAMS}
|
||||
DEPENDS ${FLANG_RT_TEST_DEPENDS}
|
||||
)
|
||||
set_target_properties(check-flang-rt PROPERTIES FOLDER "Tests")
|
||||
|
||||
add_lit_testsuites(FLANG_RT ${CMAKE_CURRENT_SOURCE_DIR}
|
||||
PARAMS ${FLANG_RT_TEST_PARAMS}
|
||||
DEPENDS ${FLANG_RT_TEST_DEPENDS})
|
||||
|
||||
# To modify the default target triple for flang-rt tests.
|
||||
if (DEFINED FLANG_RT_TEST_TARGET_TRIPLE)
|
||||
if (NOT DEFINED LLVM_TARGET_TRIPLE_ENV OR LLVM_TARGET_TRIPLE_ENV STREQUAL "")
|
||||
message(FATAL_ERROR "LLVM_TARGET_TRIPLE_ENV must also be defined in order "
|
||||
"to use FLANG_RT_TEST_TARGET_TRIPLE.")
|
||||
endif()
|
||||
endif()
|
@ -1,38 +0,0 @@
|
||||
/*
|
||||
This test makes sure that flang's runtime does not depend on the C++ runtime
|
||||
library. It tries to link this simple file against libFortranRuntime.a with
|
||||
a C compiler.
|
||||
|
||||
REQUIRES: c-compiler
|
||||
|
||||
RUN: %cc -std=c99 %s -I%include %libruntime -lm -o /dev/null
|
||||
*/
|
||||
|
||||
#include "flang/Runtime/entry-names.h"
|
||||
#include <stdint.h>
|
||||
|
||||
/*
|
||||
Manually add declarations for the runtime functions that we want to make sure
|
||||
we're testing. We can't include any headers directly since they likely contain
|
||||
C++ code that would explode here.
|
||||
*/
|
||||
struct EnvironmentDefaultList;
|
||||
struct Descriptor;
|
||||
|
||||
double RTNAME(CpuTime)();
|
||||
|
||||
void RTNAME(ProgramStart)(
|
||||
int, const char *[], const char *[], const struct EnvironmentDefaultList *);
|
||||
int32_t RTNAME(ArgumentCount)();
|
||||
int32_t RTNAME(GetCommandArgument)(int32_t, const struct Descriptor *,
|
||||
const struct Descriptor *, const struct Descriptor *);
|
||||
int32_t RTNAME(GetEnvVariable)();
|
||||
|
||||
int main() {
|
||||
double x = RTNAME(CpuTime)();
|
||||
RTNAME(ProgramStart)(0, 0, 0, 0);
|
||||
int32_t c = RTNAME(ArgumentCount)();
|
||||
int32_t v = RTNAME(GetCommandArgument)(0, 0, 0, 0);
|
||||
int32_t e = RTNAME(GetEnvVariable)("FOO", 0, 0);
|
||||
return x + c + v + e;
|
||||
}
|
@ -1,22 +0,0 @@
|
||||
import os
|
||||
|
||||
import lit.Test
|
||||
|
||||
config.name = "flang-rt-OldUnit"
|
||||
|
||||
config.suffixes = [".test"]
|
||||
|
||||
config.test_source_root = os.path.join(config.flang_rt_obj_root, "unittests")
|
||||
config.test_exec_root = config.test_source_root
|
||||
|
||||
config.test_format = lit.formats.ExecutableTest()
|
||||
|
||||
path = os.path.pathsep.join(
|
||||
(
|
||||
config.flang_rt_lib_dir,
|
||||
config.flang_bin_dir,
|
||||
config.flang_libs_dir,
|
||||
config.environment.get("LD_LIBRARY_PATH", ""),
|
||||
)
|
||||
)
|
||||
config.environment["LD_LIBRARY_PATH"] = path
|
@ -1,23 +0,0 @@
|
||||
@LIT_SITE_CFG_IN_HEADER@
|
||||
|
||||
config.llvm_src_root = "@LLVM_SOURCE_DIR@"
|
||||
config.llvm_obj_root = "@LLVM_BINARY_DIR@"
|
||||
config.llvm_tools_dir = lit_config.substitute("@LLVM_TOOLS_DIR@")
|
||||
config.llvm_libs_dir = lit_config.substitute("@LLVM_LIBS_DIR@")
|
||||
config.llvm_build_mode = lit_config.substitute("@LLVM_BUILD_MODE@")
|
||||
config.lit_tools_dir = "@LLVM_LIT_TOOLS_DIR@"
|
||||
config.flang_src_dir = "@FLANG_SOURCE_DIR@"
|
||||
config.flang_bin_dir = "@FLANG_BINARY_DIR@/bin"
|
||||
config.flang_libs_dir = "@FLANG_BINARY_DIR@/lib"
|
||||
config.flang_rt_obj_root = "@FLANG_RT_BINARY_DIR@"
|
||||
config.flang_tools_dir = lit_config.substitute("@FLANG_TOOLS_DIR@")
|
||||
config.flang_llvm_tools_dir = "@CMAKE_BINARY_DIR@/bin"
|
||||
config.flang_rt_src_dir = "@FLANG_RT_SOURCE_DIR@"
|
||||
config.flang_rt_lib_dir = "@FLANG_RT_BINARY_DIR@/lib"
|
||||
config.flang_rt_test_compiler = "@FLANG_RT_TEST_COMPILER@"
|
||||
config.flang_rt_test_triple = "@FLANG_RT_TEST_TARGET_TRIPLE@"
|
||||
config.target_triple = "@LLVM_TARGET_TRIPLE@"
|
||||
config.python_executable = "@Python3_EXECUTABLE@"
|
||||
|
||||
# Let the main config do the real work.
|
||||
lit_config.load_config(config, "@FLANG_RT_SOURCE_DIR@/test/NonGtestUnit/lit.cfg.py")
|
@ -1,58 +0,0 @@
|
||||
# -*- Python -*-
|
||||
|
||||
# Configuration file for the 'lit' test runner.
|
||||
|
||||
import os
|
||||
import platform
|
||||
import re
|
||||
import subprocess
|
||||
import sys
|
||||
|
||||
import lit.formats
|
||||
import lit.util
|
||||
|
||||
from lit.llvm import llvm_config
|
||||
from lit.llvm.subst import ToolSubst
|
||||
from lit.llvm.subst import FindTool
|
||||
|
||||
# name: The name of this test suite.
|
||||
config.name = "flang-rt-Unit"
|
||||
|
||||
# suffixes: A list of file extensions to treat as test files.
|
||||
config.suffixes = []
|
||||
|
||||
# test_source_root: The root path where unit test binaries are located.
|
||||
# test_exec_root: The root path where tests should be run.
|
||||
config.test_source_root = os.path.join(config.flang_rt_obj_root, "unittests")
|
||||
config.test_exec_root = config.test_source_root
|
||||
|
||||
# testFormat: The test format to use to interpret tests.
|
||||
config.test_format = lit.formats.GoogleTest(config.llvm_build_mode, "Tests")
|
||||
|
||||
# Tweak the PATH to include the flang bin and libs dirs.
|
||||
path = os.path.pathsep.join(
|
||||
(
|
||||
config.flang_bin_dir,
|
||||
config.llvm_tools_dir,
|
||||
config.environment["PATH"]
|
||||
)
|
||||
)
|
||||
config.environment["PATH"] = path
|
||||
|
||||
path = os.path.pathsep.join(
|
||||
(
|
||||
config.flang_rt_lib_dir,
|
||||
config.flang_libs_dir,
|
||||
config.flang_bin_dir,
|
||||
config.environment.get("LD_LIBRARY_PATH", ""),
|
||||
)
|
||||
)
|
||||
config.environment["LD_LIBRARY_PATH"] = path
|
||||
|
||||
# Propagate PYTHON_EXECUTABLE into the environment
|
||||
# config.environment['PYTHON_EXECUTABLE'] = sys.executable
|
||||
|
||||
# To modify the default target triple for flang-rt tests.
|
||||
if config.flang_rt_test_triple:
|
||||
config.target_triple = config.flang_rt_test_triple
|
||||
config.environment[config.llvm_target_triple_env] = config.flang_rt_test_triple
|
@ -1,22 +0,0 @@
|
||||
@LIT_SITE_CFG_IN_HEADER@
|
||||
|
||||
config.llvm_src_root = "@LLVM_SOURCE_DIR@"
|
||||
config.llvm_obj_root = "@LLVM_BINARY_DIR@"
|
||||
config.llvm_target_triple_env = "@LLVM_TARGET_TRIPLE_ENV@"
|
||||
config.llvm_tools_dir = lit_config.substitute("@LLVM_TOOLS_DIR@")
|
||||
config.llvm_build_mode = lit_config.substitute("@LLVM_BUILD_MODE@")
|
||||
config.lit_tools_dir = "@LLVM_LIT_TOOLS_DIR@"
|
||||
config.flang_bin_dir = "@FLANG_BINARY_DIR@/bin"
|
||||
config.flang_src_dir = "@FLANG_SOURCE_DIR@"
|
||||
config.flang_libs_dir = "@FLANG_BINARY_DIR@/lib"
|
||||
config.flang_rt_obj_root = "@FLANG_RT_BINARY_DIR@"
|
||||
config.flang_rt_src_dir = "@FLANG_RT_SOURCE_DIR@"
|
||||
config.flang_rt_lib_dir = "@FLANG_RT_BINARY_DIR@/lib"
|
||||
config.flang_rt_test_compiler = "@FLANG_RT_TEST_COMPILER@"
|
||||
config.flang_rt_test_triple = "@FLANG_RT_TEST_TARGET_TRIPLE@"
|
||||
config.flang_tools_dir = lit_config.substitute("@FLANG_TOOLS_DIR@")
|
||||
config.target_triple = "@LLVM_TARGET_TRIPLE@"
|
||||
config.python_executable = "@Python3_EXECUTABLE@"
|
||||
|
||||
# Let the main config do the real work.
|
||||
lit_config.load_config(config, "@FLANG_RT_SOURCE_DIR@/test/Unit/lit.cfg.py")
|
@ -1,173 +0,0 @@
|
||||
# -*- Python -*-
|
||||
|
||||
import os
|
||||
import platform
|
||||
import re
|
||||
import subprocess
|
||||
import sys
|
||||
|
||||
import lit.formats
|
||||
import lit.util
|
||||
|
||||
from lit.llvm import llvm_config
|
||||
from lit.llvm.subst import ToolSubst
|
||||
from lit.llvm.subst import FindTool
|
||||
|
||||
# Configuration file for the 'lit' test runner.
|
||||
|
||||
# name: The name of this test suite.
|
||||
config.name = "flang-rt"
|
||||
|
||||
# testFormat: The test format to use to interpret tests.
|
||||
#
|
||||
# For now we require '&&' between commands, until they get globally killed and
|
||||
# the test runner updated.
|
||||
config.test_format = lit.formats.ShTest(not llvm_config.use_lit_shell)
|
||||
|
||||
# suffixes: A list of file extensions to treat as test files.
|
||||
config.suffixes = [
|
||||
".c",
|
||||
".cpp",
|
||||
".f",
|
||||
".F",
|
||||
".ff",
|
||||
".FOR",
|
||||
".for",
|
||||
".f77",
|
||||
".f90",
|
||||
".F90",
|
||||
".ff90",
|
||||
".f95",
|
||||
".F95",
|
||||
".ff95",
|
||||
".fpp",
|
||||
".FPP",
|
||||
".cuf",
|
||||
".CUF",
|
||||
".f18",
|
||||
".F18",
|
||||
".f03",
|
||||
".F03",
|
||||
".f08",
|
||||
".F08",
|
||||
".ll",
|
||||
".fir",
|
||||
".mlir",
|
||||
]
|
||||
|
||||
config.substitutions.append(("%PATH%", config.environment["PATH"]))
|
||||
config.substitutions.append(("%pluginext", config.llvm_plugin_ext))
|
||||
|
||||
llvm_config.use_default_substitutions()
|
||||
|
||||
# ask llvm-config about asserts
|
||||
llvm_config.feature_config([("--assertion-mode", {"ON": "asserts"})])
|
||||
|
||||
# Targets
|
||||
config.targets = frozenset(config.targets_to_build.split())
|
||||
for arch in config.targets_to_build.split():
|
||||
config.available_features.add(arch.lower() + "-registered-target")
|
||||
|
||||
# To modify the default target triple for flang-rt tests.
|
||||
if config.flang_rt_test_triple:
|
||||
config.target_triple = config.flang_rt_test_triple
|
||||
config.environment[config.llvm_target_triple_env] = config.flang_rt_test_triple
|
||||
|
||||
# excludes: A list of directories to exclude from the testsuite. The 'Inputs'
|
||||
# subdirectories contain auxiliary inputs for various tests in their parent
|
||||
# directories.
|
||||
config.excludes = ["Inputs", "CMakeLists.txt", "README.txt", "LICENSE.txt"]
|
||||
|
||||
# Plugins (loadable modules)
|
||||
if config.has_plugins:
|
||||
config.available_features.add("plugins")
|
||||
|
||||
if config.linked_bye_extension:
|
||||
config.substitutions.append(("%loadbye", ""))
|
||||
else:
|
||||
config.substitutions.append(
|
||||
(
|
||||
"%loadbye",
|
||||
"-fpass-plugin={}/Bye{}".format(
|
||||
config.llvm_shlib_dir, config.llvm_plugin_ext
|
||||
),
|
||||
)
|
||||
)
|
||||
|
||||
# test_source_root: The root path where tests are located.
|
||||
config.test_source_root = os.path.dirname(__file__)
|
||||
|
||||
# test_exec_root: The root path where tests should be run.
|
||||
config.test_exec_root = os.path.join(config.flang_rt_obj_root, "test")
|
||||
|
||||
llvm_config.with_environment("PATH", config.flang_bin_dir, append_path=True)
|
||||
llvm_config.with_environment("PATH", config.flang_rt_obj_root, append_path=True)
|
||||
llvm_config.with_environment("PATH", config.flang_libs_dir, append_path=True)
|
||||
llvm_config.with_environment("PATH", config.flang_rt_lib_dir, append_path=True)
|
||||
|
||||
# For each occurrence of a flang tool name, replace it with the full path to
|
||||
# the build directory holding that tool.
|
||||
tools = [
|
||||
ToolSubst("%flang", command=FindTool("flang-new"), unresolved="fatal"),
|
||||
ToolSubst(
|
||||
"%flang_fc1",
|
||||
command=FindTool("flang-new"),
|
||||
extra_args=["-fc1"],
|
||||
unresolved="fatal",
|
||||
),
|
||||
]
|
||||
|
||||
# Flang has several unimplemented features. TODO messages are used to mark
|
||||
# and fail if these features are exercised. Some TODOs exit with a non-zero
|
||||
# exit code, but others abort the execution in assert builds.
|
||||
# To catch aborts, the `--crash` option for the `not` command has to be used.
|
||||
tools.append(ToolSubst("%not_todo_cmd", command=FindTool("not"), unresolved="fatal"))
|
||||
if "asserts" in config.available_features:
|
||||
tools.append(
|
||||
ToolSubst(
|
||||
"%not_todo_abort_cmd",
|
||||
command=FindTool("not"),
|
||||
extra_args=["--crash"],
|
||||
unresolved="fatal",
|
||||
)
|
||||
)
|
||||
else:
|
||||
tools.append(
|
||||
ToolSubst("%not_todo_abort_cmd", command=FindTool("not"), unresolved="fatal")
|
||||
)
|
||||
|
||||
# Define some variables to help us test that the flang runtime doesn't depend on
|
||||
# the C++ runtime libraries. For this we need a C compiler. If for some reason
|
||||
# we don't have one, we can just disable the test.
|
||||
if config.cc:
|
||||
libruntime_static = os.path.join(config.flang_rt_lib_dir, "libflang-rt.a")
|
||||
libruntime_shared = os.path.join(config.flang_rt_lib_dir, "libflang-rt.so")
|
||||
include = os.path.join(config.flang_src_dir, "include")
|
||||
|
||||
if (
|
||||
os.path.isfile(libruntime_static)
|
||||
and os.path.isdir(include)
|
||||
):
|
||||
config.available_features.add("c-compiler")
|
||||
tools.append(ToolSubst("%cc", command=config.cc, unresolved="fatal"))
|
||||
tools.append(ToolSubst("%libruntime", command=libruntime_static, unresolved="fatal"))
|
||||
tools.append(ToolSubst("%include", command=include, unresolved="fatal"))
|
||||
|
||||
elif (
|
||||
os.path.isfile(libruntime_shared)
|
||||
and os.path.isdir(include)
|
||||
):
|
||||
config.available_features.add("c-compiler")
|
||||
tools.append(ToolSubst("%cc", command=config.cc, unresolved="fatal"))
|
||||
tools.append(ToolSubst("%libruntime", command=libruntime_shared, unresolved="fatal"))
|
||||
tools.append(ToolSubst("%include", command=include, unresolved="fatal"))
|
||||
|
||||
|
||||
# Add all the tools and their substitutions (if applicable). Use the search paths provided for
|
||||
# finding the tools.
|
||||
llvm_config.add_tool_substitutions(tools, config.llvm_tools_dir)
|
||||
|
||||
# Enable libpgmath testing
|
||||
result = lit_config.params.get("LIBPGMATH")
|
||||
if result:
|
||||
config.environment["LIBPGMATH"] = True
|
@ -1,31 +0,0 @@
|
||||
@LIT_SITE_CFG_IN_HEADER@
|
||||
|
||||
import sys
|
||||
|
||||
config.llvm_tools_dir = lit_config.substitute("@LLVM_TOOLS_DIR@")
|
||||
config.llvm_shlib_dir = lit_config.substitute(path(r"@SHLIBDIR@"))
|
||||
config.llvm_plugin_ext = "@LLVM_PLUGIN_EXT@"
|
||||
config.target_triple = "@LLVM_TARGET_TRIPLE@"
|
||||
config.llvm_target_triple_env = "@LLVM_TARGET_TRIPLE_ENV@"
|
||||
config.lit_tools_dir = "@LLVM_LIT_TOOLS_DIR@"
|
||||
config.errc_messages = "@LLVM_LIT_ERRC_MESSAGES@"
|
||||
config.flang_src_dir = "@FLANG_SOURCE_DIR@"
|
||||
config.flang_bin_dir = "@FLANG_BINARY_DIR@/bin"
|
||||
config.flang_libs_dir = "@FLANG_BINARY_DIR@/lib"
|
||||
config.flang_tools_dir = lit_config.substitute("@FLANG_TOOLS_DIR@")
|
||||
config.flang_llvm_tools_dir = "@CMAKE_BINARY_DIR@/bin"
|
||||
config.flang_rt_obj_root = "@FLANG_RT_BINARY_DIR@"
|
||||
config.flang_rt_src_dir = "@FLANG_RT_SOURCE_DIR@"
|
||||
config.flang_rt_lib_dir = "@FLANG_RT_BINARY_DIR@/lib"
|
||||
config.flang_rt_test_triple = "@FLANG_RT_TEST_TARGET_TRIPLE@"
|
||||
config.python_executable = "@PYTHON_EXECUTABLE@"
|
||||
config.has_plugins = @LLVM_ENABLE_PLUGINS@
|
||||
config.linked_bye_extension = @LLVM_BYE_LINK_INTO_TOOLS@
|
||||
config.cc = "@CMAKE_C_COMPILER@"
|
||||
config.targets_to_build = "@TARGETS_TO_BUILD@"
|
||||
|
||||
import lit.llvm
|
||||
lit.llvm.initialize(lit_config, config)
|
||||
|
||||
# Let the main config do the real work.
|
||||
lit_config.load_config(config, "@FLANG_RT_SOURCE_DIR@/test/lit.cfg.py")
|
@ -1,81 +0,0 @@
|
||||
if (FLANG_EXPERIMENTAL_CUDA_RUNTIME)
|
||||
# If Fortran runtime is built as CUDA library, the linking
|
||||
# of targets that link FortranRuntime must be done
|
||||
# with CUDA_RESOLVE_DEVICE_SYMBOLS.
|
||||
# CUDA language must be enabled for CUDA_RESOLVE_DEVICE_SYMBOLS
|
||||
# to take effect.
|
||||
enable_language(CUDA)
|
||||
endif()
|
||||
|
||||
add_custom_target(FlangRTUnitTests)
|
||||
set_target_properties(FlangRTUnitTests PROPERTIES FOLDER "Flang-rt Unit Tests")
|
||||
|
||||
function(add_flang_rt_unittest_offload_properties target)
|
||||
# Set CUDA_RESOLVE_DEVICE_SYMBOLS.
|
||||
if (FLANG_EXPERIMENTAL_CUDA_RUNTIME)
|
||||
set_target_properties(${target}
|
||||
PROPERTIES CUDA_RESOLVE_DEVICE_SYMBOLS ON
|
||||
)
|
||||
endif()
|
||||
# Enable OpenMP offload during linking. We may need to replace
|
||||
# LINK_OPTIONS with COMPILE_OPTIONS when there are OpenMP offload
|
||||
# unittests.
|
||||
#
|
||||
# FIXME: replace 'native' in --offload-arch option with the list
|
||||
# of targets that Fortran Runtime was built for.
|
||||
# Common code must be moved from flang/runtime/CMakeLists.txt.
|
||||
# TODO: Revisit this because of Flang-rt. runtime is no longer an added subdirectory of flang.
|
||||
if (NOT FLANG_EXPERIMENTAL_OMP_OFFLOAD_BUILD STREQUAL "off")
|
||||
set_target_properties(${target}
|
||||
PROPERTIES LINK_OPTIONS
|
||||
"-fopenmp;--offload-arch=native"
|
||||
)
|
||||
endif()
|
||||
endfunction()
|
||||
|
||||
if(NOT TARGET llvm_gtest)
|
||||
message(FATAL_ERROR "Target llvm_gtest not found.")
|
||||
endif()
|
||||
|
||||
function(add_flang_rt_unittest test_dirname)
|
||||
add_unittest(FlangRTUnitTests ${test_dirname} ${ARGN})
|
||||
add_flang_rt_unittest_offload_properties(${test_dirname})
|
||||
endfunction()
|
||||
|
||||
if (CXX_SUPPORTS_SUGGEST_OVERRIDE_FLAG)
|
||||
add_compile_options("-Wno-suggest-override")
|
||||
endif()
|
||||
|
||||
function(add_flang_rt_nongtest_unittest test_name)
|
||||
cmake_parse_arguments(ARG
|
||||
"SLOW_TEST"
|
||||
""
|
||||
""
|
||||
${ARGN})
|
||||
|
||||
list(APPEND LLVM_COMPILE_FLAGS "-L${LLVM_BINARY_DIR}/lib")
|
||||
if(ARG_SLOW_TEST)
|
||||
set(suffix .slow)
|
||||
else()
|
||||
set(suffix .test)
|
||||
endif()
|
||||
|
||||
add_executable(${test_name}${suffix} ${test_name}.cpp)
|
||||
|
||||
if (LLVM_LINK_LLVM_DYLIB AND NOT ARG_DISABLE_LLVM_LINK_LLVM_DYLIB)
|
||||
set(llvm_libs LLVM)
|
||||
else()
|
||||
llvm_map_components_to_libnames(llvm_libs Support)
|
||||
endif()
|
||||
target_link_libraries(${test_name}${suffix} ${llvm_libs} ${ARG_UNPARSED_ARGUMENTS})
|
||||
|
||||
if(NOT ARG_SLOW_TEST)
|
||||
add_dependencies(FlangRTUnitTests ${test_name}${suffix})
|
||||
endif()
|
||||
|
||||
add_flang_rt_unittest_offload_properties(${test_name}${suffix})
|
||||
endfunction()
|
||||
|
||||
add_subdirectory(FortranRuntime)
|
||||
# TODO: We may want to find a better location for these tests that use the runtime
|
||||
add_subdirectory(FortranEvaluate)
|
@ -1,21 +0,0 @@
|
||||
set(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR})
|
||||
add_library(FlangRTFortranEvaluateTesting
|
||||
testing.cpp
|
||||
)
|
||||
if (LLVM_LINK_LLVM_DYLIB)
|
||||
set(llvm_libs LLVM)
|
||||
else()
|
||||
llvm_map_components_to_libnames(llvm_libs Support)
|
||||
endif()
|
||||
target_link_libraries(FlangRTFortranEvaluateTesting
|
||||
${llvm_libs})
|
||||
|
||||
add_flang_rt_nongtest_unittest(reshape
|
||||
FlangRTFortranEvaluateTesting
|
||||
flang-rt
|
||||
)
|
||||
|
||||
add_flang_rt_nongtest_unittest(ISO-Fortran-binding
|
||||
FlangRTFortranEvaluateTesting
|
||||
flang-rt
|
||||
)
|
@ -1,128 +0,0 @@
|
||||
#include "testing.h"
|
||||
#include <cstdarg>
|
||||
#include <cstdio>
|
||||
#include <cstdlib>
|
||||
|
||||
namespace testing {
|
||||
|
||||
namespace {
|
||||
int passes{0};
|
||||
int failures{0};
|
||||
} // namespace
|
||||
|
||||
static void BitBucket(const char *, ...) {}
|
||||
|
||||
static void PrintFailureDetails(const char *format, ...) {
|
||||
va_list ap;
|
||||
va_start(ap, format);
|
||||
fputs("\t", stderr);
|
||||
vfprintf(stderr, format, ap);
|
||||
va_end(ap);
|
||||
fputc('\n', stderr);
|
||||
}
|
||||
|
||||
FailureDetailPrinter Test(const char *file, int line, const char *predicate,
|
||||
bool pass) {
|
||||
if (pass) {
|
||||
++passes;
|
||||
return BitBucket;
|
||||
} else {
|
||||
++failures;
|
||||
fprintf(stderr, "%s:%d: FAIL: %s\n", file, line, predicate);
|
||||
return PrintFailureDetails;
|
||||
}
|
||||
}
|
||||
|
||||
FailureDetailPrinter Match(const char *file, int line, std::uint64_t want,
|
||||
const char *gots, std::uint64_t got) {
|
||||
if (want == got) {
|
||||
++passes;
|
||||
return BitBucket;
|
||||
} else {
|
||||
++failures;
|
||||
fprintf(stderr, "%s:%d: FAIL: %s == 0x%jx, not 0x%jx\n", file, line, gots,
|
||||
static_cast<std::uintmax_t>(got),
|
||||
static_cast<std::uintmax_t>(want));
|
||||
return PrintFailureDetails;
|
||||
}
|
||||
}
|
||||
|
||||
FailureDetailPrinter Match(const char *file, int line, const char *want,
|
||||
const char *gots, const std::string &got) {
|
||||
if (want == got) {
|
||||
++passes;
|
||||
return BitBucket;
|
||||
} else {
|
||||
++failures;
|
||||
fprintf(stderr, "%s:%d: FAIL: %s == \"%s\", not \"%s\"\n", file, line, gots,
|
||||
got.data(), want);
|
||||
return PrintFailureDetails;
|
||||
}
|
||||
}
|
||||
|
||||
FailureDetailPrinter Match(const char *file, int line, const std::string &want,
|
||||
const char *gots, const std::string &got) {
|
||||
return Match(file, line, want.data(), gots, got);
|
||||
}
|
||||
|
||||
FailureDetailPrinter Compare(const char *file, int line, const char *xs,
|
||||
const char *rel, const char *ys, std::uint64_t x,
|
||||
std::uint64_t y) {
|
||||
while (*rel == ' ') {
|
||||
++rel;
|
||||
}
|
||||
bool pass{false};
|
||||
if (*rel == '<') {
|
||||
if (rel[1] == '=') {
|
||||
pass = x <= y;
|
||||
} else {
|
||||
pass = x < y;
|
||||
}
|
||||
} else if (*rel == '>') {
|
||||
if (rel[1] == '=') {
|
||||
pass = x >= y;
|
||||
} else {
|
||||
pass = x > y;
|
||||
}
|
||||
} else if (*rel == '=') {
|
||||
pass = x == y;
|
||||
} else if (*rel == '!') {
|
||||
pass = x != y;
|
||||
}
|
||||
if (pass) {
|
||||
++passes;
|
||||
return BitBucket;
|
||||
} else {
|
||||
++failures;
|
||||
fprintf(stderr, "%s:%d: FAIL: %s[0x%jx] %s %s[0x%jx]\n", file, line, xs,
|
||||
static_cast<std::uintmax_t>(x), rel, ys,
|
||||
static_cast<std::uintmax_t>(y));
|
||||
return PrintFailureDetails;
|
||||
}
|
||||
}
|
||||
|
||||
int Complete() {
|
||||
if (failures == 0) {
|
||||
if (passes == 1) {
|
||||
fprintf(stdout, "single test PASSES\n");
|
||||
} else {
|
||||
fprintf(stdout, "all %d tests PASS\n", passes);
|
||||
}
|
||||
passes = 0;
|
||||
return EXIT_SUCCESS;
|
||||
} else {
|
||||
if (passes == 1) {
|
||||
fprintf(stderr, "1 test passes, ");
|
||||
} else {
|
||||
fprintf(stderr, "%d tests pass, ", passes);
|
||||
}
|
||||
if (failures == 1) {
|
||||
fprintf(stderr, "1 test FAILS\n");
|
||||
} else {
|
||||
fprintf(stderr, "%d tests FAIL\n", failures);
|
||||
}
|
||||
passes = failures = 0;
|
||||
return EXIT_FAILURE;
|
||||
}
|
||||
}
|
||||
} // namespace testing
|
@ -1,37 +0,0 @@
|
||||
#ifndef FORTRAN_EVALUATE_TESTING_H_
|
||||
#define FORTRAN_EVALUATE_TESTING_H_
|
||||
|
||||
#include <cinttypes>
|
||||
#include <string>
|
||||
|
||||
namespace testing {
|
||||
|
||||
// Returns EXIT_SUCCESS or EXIT_FAILURE, so a test's main() should end
|
||||
// with "return testing::Complete()".
|
||||
int Complete();
|
||||
|
||||
// Pass/fail testing. These macros return a pointer to a printf-like
|
||||
// function that can be optionally called to print more detail, e.g.
|
||||
// COMPARE(x, ==, y)("z is 0x%llx", z);
|
||||
// will also print z after the usual failure message if x != y.
|
||||
#define TEST(predicate) \
|
||||
testing::Test(__FILE__, __LINE__, #predicate, (predicate))
|
||||
#define MATCH(want, got) testing::Match(__FILE__, __LINE__, (want), #got, (got))
|
||||
#define COMPARE(x, rel, y) \
|
||||
testing::Compare(__FILE__, __LINE__, #x, #rel, #y, (x), (y))
|
||||
|
||||
// Functions called by these macros; do not call directly.
|
||||
using FailureDetailPrinter = void (*)(const char *, ...);
|
||||
FailureDetailPrinter Test(const char *file, int line, const char *predicate,
|
||||
bool pass);
|
||||
FailureDetailPrinter Match(const char *file, int line, std::uint64_t want,
|
||||
const char *gots, std::uint64_t got);
|
||||
FailureDetailPrinter Match(const char *file, int line, const char *want,
|
||||
const char *gots, const std::string &got);
|
||||
FailureDetailPrinter Match(const char *file, int line, const std::string &want,
|
||||
const char *gots, const std::string &got);
|
||||
FailureDetailPrinter Compare(const char *file, int line, const char *xs,
|
||||
const char *rel, const char *ys, std::uint64_t x,
|
||||
std::uint64_t y);
|
||||
} // namespace testing
|
||||
#endif // FORTRAN_EVALUATE_TESTING_H_
|
@ -188,7 +188,7 @@ if (FLANG_STANDALONE_BUILD)
|
||||
if (FLANG_GTEST_AVAIL)
|
||||
add_custom_target(check-all DEPENDS check-flang FlangUnitTests)
|
||||
else()
|
||||
add_custom_target(check-all DEPENDS check-flang)
|
||||
add_custom_target(check-all DEPENDS check-flang )
|
||||
endif()
|
||||
if (LLVM_BUILD_DOCS)
|
||||
add_custom_target(doxygen ALL)
|
||||
@ -421,11 +421,6 @@ if (FLANG_INCLUDE_TESTS)
|
||||
add_compile_definitions(FLANG_INCLUDE_TESTS=1)
|
||||
endif()
|
||||
|
||||
# Add Flang subdirectories.
|
||||
# NOTE: The runtime subdirectory is no longer added here.
|
||||
# Sources for the runtime are added in Flang-rt.
|
||||
# TODO: Move the runtime sources to the flang-rt top level directory.
|
||||
|
||||
add_subdirectory(include)
|
||||
add_subdirectory(lib)
|
||||
add_subdirectory(cmake/modules)
|
||||
@ -435,6 +430,7 @@ option(FLANG_BUILD_TOOLS
|
||||
if (FLANG_BUILD_TOOLS)
|
||||
add_subdirectory(tools)
|
||||
endif()
|
||||
add_subdirectory(runtime)
|
||||
|
||||
if (LLVM_INCLUDE_EXAMPLES)
|
||||
add_subdirectory(examples)
|
||||
|
@ -17,7 +17,7 @@ macro(add_flang_subdirectory name)
|
||||
endmacro()
|
||||
|
||||
function(add_flang_library name)
|
||||
set(options SHARED STATIC INSTALL_WITH_TOOLCHAIN PIC)
|
||||
set(options SHARED STATIC INSTALL_WITH_TOOLCHAIN)
|
||||
set(multiValueArgs ADDITIONAL_HEADERS CLANG_LIBS)
|
||||
cmake_parse_arguments(ARG
|
||||
"${options}"
|
||||
@ -65,9 +65,6 @@ function(add_flang_library name)
|
||||
endif()
|
||||
|
||||
llvm_add_library(${name} ${LIBTYPE} ${ARG_UNPARSED_ARGUMENTS} ${srcs})
|
||||
if (ARG_PIC)
|
||||
set_target_properties(${name} PROPERTIES POSITION_INDEPENDENT_CODE ON)
|
||||
endif()
|
||||
|
||||
clang_target_link_libraries(${name} PRIVATE ${ARG_CLANG_LIBS})
|
||||
|
||||
|
@ -9,8 +9,6 @@ find_package(LLVM ${LLVM_VERSION} EXACT REQUIRED CONFIG
|
||||
set(FLANG_EXPORTED_TARGETS "@FLANG_EXPORTS@")
|
||||
set(FLANG_CMAKE_DIR "@FLANG_CONFIG_CMAKE_DIR@")
|
||||
set(FLANG_INCLUDE_DIRS "@FLANG_CONFIG_INCLUDE_DIRS@")
|
||||
set(FLANG_SOURCE_DIR "@FLANG_SOURCE_DIR@")
|
||||
set(FLANG_BINARY_DIR "@FLANG_BINARY_DIR@")
|
||||
|
||||
# Provide all our library targets to users.
|
||||
@FLANG_CONFIG_INCLUDE_EXPORTS@
|
||||
|
@ -49,19 +49,7 @@ endif()
|
||||
# avoid an unwanted dependency on libstdc++.so.
|
||||
add_definitions(-U_GLIBCXX_ASSERTIONS)
|
||||
|
||||
# Build FortranDecimal when the build target is Flang or LLVM.
|
||||
if (CMAKE_SOURCE_DIR STREQUAL FLANG_SOURCE_DIR OR CMAKE_SOURCE_DIR STREQUAL LLVM_MAIN_SRC_DIR)
|
||||
add_flang_library(FortranDecimal
|
||||
binary-to-decimal.cpp
|
||||
decimal-to-binary.cpp
|
||||
)
|
||||
# Build FortranDecimalRT for FlangRT when the build target is Runtimes.
|
||||
# Standalone builds of FlangRT is not supported.
|
||||
elseif (CMAKE_SOURCE_DIR STREQUAL Runtimes_SOURCE_DIR)
|
||||
add_flang_library(FortranDecimalRT STATIC INSTALL_WITH_TOOLCHAIN PIC
|
||||
binary-to-decimal.cpp
|
||||
decimal-to-binary.cpp
|
||||
)
|
||||
else()
|
||||
message(FATAL_ERROR "CMAKE_SOURCE_DIR of target points to neither Flang or Flang-rt, no library added for FortranDecimal.")
|
||||
endif()
|
||||
add_flang_library(FortranDecimal INSTALL_WITH_TOOLCHAIN
|
||||
binary-to-decimal.cpp
|
||||
decimal-to-binary.cpp
|
||||
)
|
||||
|
@ -6,14 +6,10 @@
|
||||
#
|
||||
#===------------------------------------------------------------------------===#
|
||||
|
||||
# TODO: Maybe this file should still be added by flang/CMakeLists.txt and
|
||||
# when FLANG_STANDALONE_BUILD=On and a new variable FLANG_BUILD_RUNTIME=On
|
||||
# we should invoke an ExternalProject_Add(flang-rt ...) from here?
|
||||
|
||||
if (CMAKE_SOURCE_DIR STREQUAL CMAKE_CURRENT_SOURCE_DIR)
|
||||
cmake_minimum_required(VERSION 3.20.0)
|
||||
|
||||
project(FortranRuntime C CXX)
|
||||
project(FlangRuntime C CXX)
|
||||
|
||||
set(CMAKE_CXX_STANDARD 17)
|
||||
set(CMAKE_CXX_STANDARD_REQUIRED TRUE)
|
||||
@ -86,6 +82,8 @@ append(${NO_LTO_FLAGS} CMAKE_CXX_FLAGS)
|
||||
add_definitions(-U_GLIBCXX_ASSERTIONS)
|
||||
add_definitions(-U_LIBCPP_ENABLE_ASSERTIONS)
|
||||
|
||||
add_subdirectory(FortranMain)
|
||||
|
||||
set(sources
|
||||
ISO_Fortran_binding.cpp
|
||||
allocatable.cpp
|
||||
@ -270,13 +268,10 @@ if (NOT FLANG_EXPERIMENTAL_OMP_OFFLOAD_BUILD STREQUAL "off")
|
||||
endif()
|
||||
endif()
|
||||
|
||||
add_compile_options(-fPIC)
|
||||
|
||||
add_flang_library(FortranRuntime STATIC
|
||||
add_flang_library(FortranRuntime
|
||||
${sources}
|
||||
LINK_LIBS
|
||||
FortranDecimalRT
|
||||
FortranDecimal
|
||||
|
||||
INSTALL_WITH_TOOLCHAIN
|
||||
PIC
|
||||
)
|
||||
|
@ -138,15 +138,10 @@ CppTypeFor<TypeCategory::Real, 10> RTNAME(SumReal10)(const Descriptor &x,
|
||||
}
|
||||
#endif
|
||||
#if LDBL_MANT_DIG == 113 || HAS_FLOAT128
|
||||
#if HAS_FLOAT128
|
||||
using AccumType = __float128;
|
||||
#else // if LDBL_MANT_DIG == 113
|
||||
using AccumType = long double;
|
||||
#endif
|
||||
CppTypeFor<TypeCategory::Real, 16> RTNAME(SumReal16)(const Descriptor &x,
|
||||
const char *source, int line, int dim, const Descriptor *mask) {
|
||||
return GetTotalReduction<TypeCategory::Real, 16>(
|
||||
x, source, line, dim, mask, RealSumAccumulator<AccumType>{x}, "SUM");
|
||||
x, source, line, dim, mask, RealSumAccumulator<long double>{x}, "SUM");
|
||||
}
|
||||
#endif
|
||||
|
||||
|
@ -61,6 +61,9 @@ set(FLANG_TEST_DEPENDS
|
||||
llvm-objdump
|
||||
llvm-readobj
|
||||
split-file
|
||||
FortranRuntime
|
||||
Fortran_main
|
||||
FortranDecimal
|
||||
)
|
||||
if (LLVM_ENABLE_PLUGINS AND NOT WIN32)
|
||||
list(APPEND FLANG_TEST_DEPENDS Bye)
|
||||
|
@ -24,18 +24,21 @@
|
||||
! GNU-LABEL: "{{.*}}ld{{(\.exe)?}}"
|
||||
! GNU-SAME: "[[object_file]]"
|
||||
! GNU-SAME: -lFortran_main
|
||||
! GNU-SAME: -lflang-rt
|
||||
! GNU-SAME: -lFortranRuntime
|
||||
! GNU-SAME: -lFortranDecimal
|
||||
! GNU-SAME: -lm
|
||||
|
||||
! DARWIN-LABEL: "{{.*}}ld{{(\.exe)?}}"
|
||||
! DARWIN-SAME: "[[object_file]]"
|
||||
! DARWIN-SAME: -lFortran_main
|
||||
! DARWIN-SAME: -lflang-rt
|
||||
! DARWIN-SAME: -lFortranRuntime
|
||||
! DARWIN-SAME: -lFortranDecimal
|
||||
|
||||
! MINGW-LABEL: "{{.*}}ld{{(\.exe)?}}"
|
||||
! MINGW-SAME: "[[object_file]]"
|
||||
! MINGW-SAME: -lFortran_main
|
||||
! MINGW-SAME: -lflang-rt
|
||||
! MINGW-SAME: -lFortranRuntime
|
||||
! MINGW-SAME: -lFortranDecimal
|
||||
|
||||
! NOTE: This also matches lld-link (when CLANG_DEFAULT_LINKER=lld) and
|
||||
! any .exe suffix that is added when resolving to the full path of
|
||||
@ -43,6 +46,7 @@
|
||||
! when the executable is not found or on non-Windows platforms.
|
||||
! MSVC-LABEL: link
|
||||
! MSVC-SAME: Fortran_main.lib
|
||||
! MSVC-SAME: flang-rt.lib
|
||||
! MSVC-SAME: FortranRuntime.lib
|
||||
! MSVC-SAME: FortranDecimal.lib
|
||||
! MSVC-SAME: /subsystem:console
|
||||
! MSVC-SAME: "[[object_file]]"
|
||||
|
@ -153,16 +153,19 @@ else:
|
||||
# the C++ runtime libraries. For this we need a C compiler. If for some reason
|
||||
# we don't have one, we can just disable the test.
|
||||
if config.cc:
|
||||
libruntime = os.path.join(config.flang_lib_dir, "libflang-rt.a")
|
||||
libruntime = os.path.join(config.flang_lib_dir, "libFortranRuntime.a")
|
||||
libdecimal = os.path.join(config.flang_lib_dir, "libFortranDecimal.a")
|
||||
include = os.path.join(config.flang_src_dir, "include")
|
||||
|
||||
if (
|
||||
os.path.isfile(libruntime)
|
||||
and os.path.isfile(libdecimal)
|
||||
and os.path.isdir(include)
|
||||
):
|
||||
config.available_features.add("c-compiler")
|
||||
tools.append(ToolSubst("%cc", command=config.cc, unresolved="fatal"))
|
||||
tools.append(ToolSubst("%libruntime", command=libruntime, unresolved="fatal"))
|
||||
tools.append(ToolSubst("%libdecimal", command=libdecimal, unresolved="fatal"))
|
||||
tools.append(ToolSubst("%include", command=include, unresolved="fatal"))
|
||||
|
||||
# Add all the tools and their substitutions (if applicable). Use the search paths provided for
|
||||
|
@ -14,6 +14,14 @@ set( LLVM_LINK_COMPONENTS
|
||||
add_flang_tool(flang-new
|
||||
driver.cpp
|
||||
fc1_main.cpp
|
||||
|
||||
DEPENDS
|
||||
# These libraries are used in the linker invocation generated by the driver
|
||||
# (i.e. when constructing the linker job). Without them the driver would be
|
||||
# unable to generate executables.
|
||||
FortranRuntime
|
||||
FortranDecimal
|
||||
Fortran_main
|
||||
)
|
||||
|
||||
target_link_libraries(flang-new
|
||||
|
@ -24,15 +24,11 @@ function(add_flang_unittest_offload_properties target)
|
||||
# FIXME: replace 'native' in --offload-arch option with the list
|
||||
# of targets that Fortran Runtime was built for.
|
||||
# Common code must be moved from flang/runtime/CMakeLists.txt.
|
||||
# TODO: Revisit this because of Flang-rt. runtime is no longer an added subdirectory of flang. So we temporarily duplicated the option definition to here. This is not a permanent solution.
|
||||
set(FLANG_EXPERIMENTAL_OMP_OFFLOAD_BUILD "off" CACHE STRING
|
||||
"Compile Fortran runtime as OpenMP target offload sources (experimental). Valid options are 'off', 'host_device', 'nohost'")
|
||||
|
||||
if (NOT FLANG_EXPERIMENTAL_OMP_OFFLOAD_BUILD STREQUAL "off")
|
||||
set_target_properties(${target}
|
||||
PROPERTIES LINK_OPTIONS
|
||||
"-fopenmp;--offload-arch=native"
|
||||
)
|
||||
PROPERTIES LINK_OPTIONS
|
||||
"-fopenmp;--offload-arch=native"
|
||||
)
|
||||
endif()
|
||||
endfunction()
|
||||
|
||||
@ -78,4 +74,5 @@ add_subdirectory(Optimizer)
|
||||
add_subdirectory(Common)
|
||||
add_subdirectory(Decimal)
|
||||
add_subdirectory(Evaluate)
|
||||
add_subdirectory(Runtime)
|
||||
add_subdirectory(Frontend)
|
||||
|
@ -45,6 +45,7 @@ add_flang_nongtest_unittest(intrinsics
|
||||
FortranDecimal
|
||||
FortranSemantics
|
||||
FortranParser
|
||||
FortranRuntime
|
||||
)
|
||||
|
||||
add_flang_nongtest_unittest(logical
|
||||
@ -67,6 +68,20 @@ add_flang_nongtest_unittest(real
|
||||
)
|
||||
llvm_update_compile_flags(real.test)
|
||||
|
||||
add_flang_nongtest_unittest(reshape
|
||||
FortranEvaluateTesting
|
||||
FortranSemantics
|
||||
FortranEvaluate
|
||||
FortranRuntime
|
||||
)
|
||||
|
||||
add_flang_nongtest_unittest(ISO-Fortran-binding
|
||||
FortranEvaluateTesting
|
||||
FortranEvaluate
|
||||
FortranSemantics
|
||||
FortranRuntime
|
||||
)
|
||||
|
||||
add_flang_nongtest_unittest(folding
|
||||
FortranCommon
|
||||
FortranEvaluateTesting
|
||||
|
@ -19,6 +19,16 @@ add_flang_unittest(FlangOptimizerTests
|
||||
Builder/DoLoopHelperTest.cpp
|
||||
Builder/FIRBuilderTest.cpp
|
||||
Builder/HLFIRToolsTest.cpp
|
||||
Builder/Runtime/AllocatableTest.cpp
|
||||
Builder/Runtime/AssignTest.cpp
|
||||
Builder/Runtime/CommandTest.cpp
|
||||
Builder/Runtime/CharacterTest.cpp
|
||||
Builder/Runtime/DerivedTest.cpp
|
||||
Builder/Runtime/NumericTest.cpp
|
||||
Builder/Runtime/RaggedTest.cpp
|
||||
Builder/Runtime/ReductionTest.cpp
|
||||
Builder/Runtime/StopTest.cpp
|
||||
Builder/Runtime/TransformationalTest.cpp
|
||||
FIRContextTest.cpp
|
||||
FIRTypesTest.cpp
|
||||
FortranVariableTest.cpp
|
||||
|
@ -6,7 +6,7 @@
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#include "flang/../../runtime/buffer.h"
|
||||
#include "../../runtime/buffer.h"
|
||||
#include "CrashHandlerFixture.h"
|
||||
#include "gtest/gtest.h"
|
||||
#include <algorithm>
|
||||
@ -30,16 +30,15 @@ public:
|
||||
void set_expect(FileOffset to) { expect_ = to; }
|
||||
|
||||
std::size_t Read(FileOffset at, char *to, std::size_t minBytes,
|
||||
std::size_t maxBytes, IoErrorHandler &handler) {
|
||||
std::size_t maxBytes, IoErrorHandler &handler) {
|
||||
if (enforceSequence_ && at != expect_) {
|
||||
handler.SignalError("Read(%d,%d,%d) not at expected %d",
|
||||
static_cast<int>(at), static_cast<int>(minBytes),
|
||||
static_cast<int>(maxBytes),
|
||||
static_cast<int>(expect_));
|
||||
static_cast<int>(at), static_cast<int>(minBytes),
|
||||
static_cast<int>(maxBytes), static_cast<int>(expect_));
|
||||
} else if (at < 0 || at + minBytes > bytes_) {
|
||||
handler.SignalError("Read(%d,%d,%d) is out of bounds",
|
||||
static_cast<int>(at), static_cast<int>(minBytes),
|
||||
static_cast<int>(maxBytes));
|
||||
static_cast<int>(at), static_cast<int>(minBytes),
|
||||
static_cast<int>(maxBytes));
|
||||
}
|
||||
auto result{std::min<std::size_t>(maxBytes, bytes_ - at)};
|
||||
std::memcpy(to, &data_[at], result);
|
||||
@ -47,14 +46,14 @@ public:
|
||||
return result;
|
||||
}
|
||||
std::size_t Write(FileOffset at, const char *from, std::size_t bytes,
|
||||
IoErrorHandler &handler) {
|
||||
IoErrorHandler &handler) {
|
||||
if (enforceSequence_ && at != expect_) {
|
||||
handler.SignalError("Write(%d,%d) not at expected %d",
|
||||
static_cast<int>(at), static_cast<int>(bytes),
|
||||
static_cast<int>(expect_));
|
||||
static_cast<int>(at), static_cast<int>(bytes),
|
||||
static_cast<int>(expect_));
|
||||
} else if (at < 0 || at + bytes > bytes_) {
|
||||
handler.SignalError("Write(%d,%d) is out of bounds", static_cast<int>(at),
|
||||
static_cast<int>(bytes));
|
||||
static_cast<int>(bytes));
|
||||
}
|
||||
std::memcpy(&data_[at], from, bytes);
|
||||
expect_ = at + bytes;
|
||||
@ -71,8 +70,8 @@ private:
|
||||
inline int ChunkSize(int j, int most) {
|
||||
// 31, 1, 29, 3, 27, ...
|
||||
j %= tinyBufferSize;
|
||||
auto chunk{static_cast<int>(((j % 2) ? j : (tinyBufferSize - 1 - j)) %
|
||||
tinyBufferSize)};
|
||||
auto chunk{static_cast<int>(
|
||||
((j % 2) ? j : (tinyBufferSize - 1 - j)) % tinyBufferSize)};
|
||||
return std::min(chunk, most);
|
||||
}
|
||||
|
@ -1,4 +1,4 @@
|
||||
add_flang_rt_unittest(FortranRuntimeTests
|
||||
add_flang_unittest(FlangRuntimeTests
|
||||
Allocatable.cpp
|
||||
ArrayConstructor.cpp
|
||||
BufferTest.cpp
|
||||
@ -29,7 +29,7 @@ add_flang_rt_unittest(FortranRuntimeTests
|
||||
Transformational.cpp
|
||||
)
|
||||
|
||||
target_link_libraries(FortranRuntimeTests
|
||||
target_link_libraries(FlangRuntimeTests
|
||||
PRIVATE
|
||||
flang-rt
|
||||
FortranRuntime
|
||||
)
|
@ -6,13 +6,13 @@
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
#include "CrashHandlerFixture.h"
|
||||
#include "flang/../../runtime/terminator.h"
|
||||
#include "../../runtime/terminator.h"
|
||||
#include <cstdarg>
|
||||
#include <cstdlib>
|
||||
|
||||
// Replaces Fortran runtime's crash handler so we can verify the crash message
|
||||
[[noreturn]] static void CatchCrash(const char *sourceFile, int sourceLine,
|
||||
const char *message, va_list &ap) {
|
||||
[[noreturn]] static void CatchCrash(
|
||||
const char *sourceFile, int sourceLine, const char *message, va_list &ap) {
|
||||
char buffer[1000];
|
||||
std::vsnprintf(buffer, sizeof buffer, message, ap);
|
||||
va_end(ap);
|
@ -7,7 +7,7 @@
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#include "CrashHandlerFixture.h"
|
||||
#include "flang/../../runtime/io-error.h"
|
||||
#include "../../runtime/io-error.h"
|
||||
#include "flang/Runtime/descriptor.h"
|
||||
#include "flang/Runtime/io-api.h"
|
||||
|
||||
@ -36,15 +36,15 @@ TEST(InputTest, TestListInputAlphabet) {
|
||||
// Use _two_ input buffers and _three_ output buffers. Note the `3*` in the
|
||||
// _inputBuffers_.
|
||||
SetCharacter(inputBuffers[j++], maxInputBufferLength,
|
||||
"3*'abcdefghijklmnopqrstuvwxyzABC");
|
||||
SetCharacter(inputBuffers[j++], maxInputBufferLength,
|
||||
"DEFGHIJKLMNOPQRSTUVWXYZ'");
|
||||
"3*'abcdefghijklmnopqrstuvwxyzABC");
|
||||
SetCharacter(
|
||||
inputBuffers[j++], maxInputBufferLength, "DEFGHIJKLMNOPQRSTUVWXYZ'");
|
||||
|
||||
StaticDescriptor<1> staticDescriptor;
|
||||
Descriptor &whole{staticDescriptor.descriptor()};
|
||||
SubscriptValue extent[]{numInputBuffers};
|
||||
whole.Establish(TypeCode{CFI_type_char}, maxInputBufferLength, &inputBuffers,
|
||||
1, extent, CFI_attribute_pointer);
|
||||
1, extent, CFI_attribute_pointer);
|
||||
whole.Check();
|
||||
auto *cookie{IONAME(BeginInternalArrayListInput)(whole)};
|
||||
|
||||
@ -79,7 +79,7 @@ TEST(InputTest, TestListInputIntegerList) {
|
||||
Descriptor &whole{staticDescriptor.descriptor()};
|
||||
SubscriptValue extent[]{numBuffers};
|
||||
whole.Establish(TypeCode{CFI_type_char}, maxBufferLength, &buffer, 1, extent,
|
||||
CFI_attribute_pointer);
|
||||
CFI_attribute_pointer);
|
||||
whole.Check();
|
||||
auto *cookie{IONAME(BeginInternalArrayListInput)(whole)};
|
||||
|
||||
@ -88,10 +88,10 @@ TEST(InputTest, TestListInputIntegerList) {
|
||||
// Negative numbers will be overwritten by _expectedOutput_, and positive
|
||||
// numbers will not be as their indices are "Null values" of the Fortran 2018
|
||||
// standard 13.10.3.2 in the format strings _buffer_
|
||||
std::int64_t actualOutput[listInputLength]{-1, -2, -3, -4, 5,
|
||||
-6, 7, -8, 9, 10};
|
||||
const std::int64_t expectedOutput[listInputLength]{1, 2, 3, 3, 5,
|
||||
6, 7, 8, 9, 10};
|
||||
std::int64_t actualOutput[listInputLength]{
|
||||
-1, -2, -3, -4, 5, -6, 7, -8, 9, 10};
|
||||
const std::int64_t expectedOutput[listInputLength]{
|
||||
1, 2, 3, 3, 5, 6, 7, 8, 9, 10};
|
||||
for (j = 0; j < listInputLength; ++j) {
|
||||
IONAME(InputInteger)(cookie, actualOutput[j]);
|
||||
}
|
||||
@ -116,7 +116,7 @@ TEST(InputTest, TestListInputInvalidFormatWithSingleSuccess) {
|
||||
Descriptor &whole{staticDescriptor.descriptor()};
|
||||
SubscriptValue extent[]{numBuffers};
|
||||
whole.Establish(TypeCode{CFI_type_char}, formatBuffer.size(),
|
||||
formatBuffer.data(), 1, extent, CFI_attribute_pointer);
|
||||
formatBuffer.data(), 1, extent, CFI_attribute_pointer);
|
||||
whole.Check();
|
||||
|
||||
auto *cookie{IONAME(BeginInternalArrayListInput)(whole)};
|
||||
@ -127,7 +127,7 @@ TEST(InputTest, TestListInputInvalidFormatWithSingleSuccess) {
|
||||
|
||||
// Perform failing InputInteger
|
||||
ASSERT_DEATH(IONAME(InputInteger)(cookie, dummy),
|
||||
"Bad character 'g' in INTEGER input field");
|
||||
"Bad character 'g' in INTEGER input field");
|
||||
}
|
||||
|
||||
// Same test as _TestListInputInvalidFormatWithSingleSuccess_, however no
|
||||
@ -140,7 +140,7 @@ TEST(InputTest, TestListInputInvalidFormat) {
|
||||
Descriptor &whole{staticDescriptor.descriptor()};
|
||||
SubscriptValue extent[]{numBuffers};
|
||||
whole.Establish(TypeCode{CFI_type_char}, formatBuffer.size(),
|
||||
formatBuffer.data(), 1, extent, CFI_attribute_pointer);
|
||||
formatBuffer.data(), 1, extent, CFI_attribute_pointer);
|
||||
whole.Check();
|
||||
|
||||
auto *cookie{IONAME(BeginInternalArrayListInput)(whole)};
|
||||
@ -148,7 +148,7 @@ TEST(InputTest, TestListInputInvalidFormat) {
|
||||
|
||||
// Perform failing InputInteger
|
||||
ASSERT_DEATH(IONAME(InputInteger)(cookie, dummy),
|
||||
"Bad character 'g' in INTEGER input field");
|
||||
"Bad character 'g' in INTEGER input field");
|
||||
}
|
||||
|
||||
using ParamTy = std::tuple<std::string, std::vector<int>>;
|
||||
@ -163,7 +163,7 @@ TEST_P(SimpleListInputTest, TestListInput) {
|
||||
Descriptor &whole{staticDescriptor.descriptor()};
|
||||
SubscriptValue extent[]{numBuffers};
|
||||
whole.Establish(TypeCode{CFI_type_char}, formatBuffer.size(),
|
||||
formatBuffer.data(), 1, extent, CFI_attribute_pointer);
|
||||
formatBuffer.data(), 1, extent, CFI_attribute_pointer);
|
||||
whole.Check();
|
||||
auto *cookie{IONAME(BeginInternalArrayListInput)(whole)};
|
||||
|
||||
@ -185,10 +185,9 @@ TEST_P(SimpleListInputTest, TestListInput) {
|
||||
}
|
||||
}
|
||||
|
||||
INSTANTIATE_TEST_SUITE_P(
|
||||
SimpleListInputTestInstantiation, SimpleListInputTest,
|
||||
INSTANTIATE_TEST_SUITE_P(SimpleListInputTestInstantiation, SimpleListInputTest,
|
||||
testing::Values(std::make_tuple("", std::vector<int>{}),
|
||||
std::make_tuple("0", std::vector<int>{}),
|
||||
std::make_tuple("1", std::vector<int>{1}),
|
||||
std::make_tuple("1, 2", std::vector<int>{1, 2}),
|
||||
std::make_tuple("3*2", std::vector<int>{2, 2, 2})));
|
||||
std::make_tuple("0", std::vector<int>{}),
|
||||
std::make_tuple("1", std::vector<int>{1}),
|
||||
std::make_tuple("1, 2", std::vector<int>{1, 2}),
|
||||
std::make_tuple("3*2", std::vector<int>{2, 2, 2})));
|
@ -6,11 +6,11 @@
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#include "flang/../../runtime/namelist.h"
|
||||
#include "../../runtime/namelist.h"
|
||||
#include "CrashHandlerFixture.h"
|
||||
#include "tools.h"
|
||||
#include "flang/Runtime/descriptor.h"
|
||||
#include "flang/Runtime/io-api.h"
|
||||
#include "tools.h"
|
||||
#include <algorithm>
|
||||
#include <cinttypes>
|
||||
#include <complex>
|
||||
@ -27,7 +27,7 @@ struct NamelistTests : CrashHandlerFixture {};
|
||||
|
||||
static void ClearDescriptorStorage(const Descriptor &descriptor) {
|
||||
std::memset(descriptor.raw().base_addr, 0,
|
||||
descriptor.Elements() * descriptor.ElementBytes());
|
||||
descriptor.Elements() * descriptor.ElementBytes());
|
||||
}
|
||||
|
||||
TEST(NamelistTests, BasicSanity) {
|
||||
@ -38,20 +38,17 @@ TEST(NamelistTests, BasicSanity) {
|
||||
Descriptor &internalDesc{statDescs[0].descriptor()};
|
||||
SubscriptValue extent[]{numLines};
|
||||
internalDesc.Establish(TypeCode{CFI_type_char}, /*elementBytes=*/lineLength,
|
||||
&buffer, 1, extent, CFI_attribute_pointer);
|
||||
&buffer, 1, extent, CFI_attribute_pointer);
|
||||
// Set up data arrays
|
||||
std::vector<int> ints;
|
||||
for (int j{0}; j < 20; ++j) {
|
||||
ints.push_back(j % 2 == 0 ? (1 << j) : -(1 << j));
|
||||
}
|
||||
std::vector<double> reals{0.0,
|
||||
-0.0,
|
||||
std::numeric_limits<double>::infinity(),
|
||||
-std::numeric_limits<double>::infinity(),
|
||||
std::numeric_limits<double>::quiet_NaN(),
|
||||
std::numeric_limits<double>::max(),
|
||||
std::numeric_limits<double>::lowest(),
|
||||
std::numeric_limits<double>::epsilon()};
|
||||
std::vector<double> reals{0.0, -0.0, std::numeric_limits<double>::infinity(),
|
||||
-std::numeric_limits<double>::infinity(),
|
||||
std::numeric_limits<double>::quiet_NaN(),
|
||||
std::numeric_limits<double>::max(), std::numeric_limits<double>::lowest(),
|
||||
std::numeric_limits<double>::epsilon()};
|
||||
std::vector<std::uint8_t> logicals;
|
||||
logicals.push_back(false);
|
||||
logicals.push_back(true);
|
||||
@ -79,14 +76,12 @@ TEST(NamelistTests, BasicSanity) {
|
||||
// Create a NAMELIST group
|
||||
static constexpr int items{5};
|
||||
const NamelistGroup::Item itemArray[items]{{"ints", *intDesc},
|
||||
{"reals", *realDesc},
|
||||
{"logicals", *logicalDesc},
|
||||
{"complexes", *complexDesc},
|
||||
{"characters", *characterDesc}};
|
||||
{"reals", *realDesc}, {"logicals", *logicalDesc},
|
||||
{"complexes", *complexDesc}, {"characters", *characterDesc}};
|
||||
const NamelistGroup group{"group1", items, itemArray};
|
||||
// Do an internal NAMELIST write and check results
|
||||
auto outCookie1{IONAME(BeginInternalArrayListOutput)(internalDesc, nullptr, 0,
|
||||
__FILE__, __LINE__)};
|
||||
auto outCookie1{IONAME(BeginInternalArrayListOutput)(
|
||||
internalDesc, nullptr, 0, __FILE__, __LINE__)};
|
||||
ASSERT_TRUE(IONAME(SetDelim)(outCookie1, "APOSTROPHE", 10));
|
||||
ASSERT_TRUE(IONAME(OutputNamelist)(outCookie1, group));
|
||||
auto outStatus1{IONAME(EndIoStatement)(outCookie1)};
|
||||
@ -114,14 +109,14 @@ TEST(NamelistTests, BasicSanity) {
|
||||
ClearDescriptorStorage(*logicalDesc);
|
||||
ClearDescriptorStorage(*complexDesc);
|
||||
ClearDescriptorStorage(*characterDesc);
|
||||
auto inCookie{IONAME(BeginInternalArrayListInput)(internalDesc, nullptr, 0,
|
||||
__FILE__, __LINE__)};
|
||||
auto inCookie{IONAME(BeginInternalArrayListInput)(
|
||||
internalDesc, nullptr, 0, __FILE__, __LINE__)};
|
||||
ASSERT_TRUE(IONAME(InputNamelist)(inCookie, group));
|
||||
auto inStatus{IONAME(EndIoStatement)(inCookie)};
|
||||
ASSERT_EQ(inStatus, 0) << "Failed namelist input sanity, status "
|
||||
<< static_cast<int>(inStatus);
|
||||
auto outCookie2{IONAME(BeginInternalArrayListOutput)(internalDesc, nullptr, 0,
|
||||
__FILE__, __LINE__)};
|
||||
auto outCookie2{IONAME(BeginInternalArrayListOutput)(
|
||||
internalDesc, nullptr, 0, __FILE__, __LINE__)};
|
||||
ASSERT_TRUE(IONAME(SetDelim)(outCookie2, "APOSTROPHE", 10));
|
||||
ASSERT_TRUE(IONAME(OutputNamelist)(outCookie2, group));
|
||||
auto outStatus2{IONAME(EndIoStatement)(outCookie2)};
|
||||
@ -144,19 +139,18 @@ TEST(NamelistTests, Subscripts) {
|
||||
StaticDescriptor<1, true> statDesc;
|
||||
Descriptor &internalDesc{statDesc.descriptor()};
|
||||
internalDesc.Establish(TypeCode{CFI_type_char},
|
||||
/*elementBytes=*/std::strlen(t1), t1, 0, nullptr,
|
||||
CFI_attribute_pointer);
|
||||
auto inCookie{IONAME(BeginInternalArrayListInput)(internalDesc, nullptr, 0,
|
||||
__FILE__, __LINE__)};
|
||||
/*elementBytes=*/std::strlen(t1), t1, 0, nullptr, CFI_attribute_pointer);
|
||||
auto inCookie{IONAME(BeginInternalArrayListInput)(
|
||||
internalDesc, nullptr, 0, __FILE__, __LINE__)};
|
||||
ASSERT_TRUE(IONAME(InputNamelist)(inCookie, group));
|
||||
auto inStatus{IONAME(EndIoStatement)(inCookie)};
|
||||
ASSERT_EQ(inStatus, 0) << "Failed namelist input subscripts, status "
|
||||
<< static_cast<int>(inStatus);
|
||||
char out[40];
|
||||
internalDesc.Establish(TypeCode{CFI_type_char}, /*elementBytes=*/sizeof out,
|
||||
out, 0, nullptr, CFI_attribute_pointer);
|
||||
auto outCookie{IONAME(BeginInternalArrayListOutput)(internalDesc, nullptr, 0,
|
||||
__FILE__, __LINE__)};
|
||||
out, 0, nullptr, CFI_attribute_pointer);
|
||||
auto outCookie{IONAME(BeginInternalArrayListOutput)(
|
||||
internalDesc, nullptr, 0, __FILE__, __LINE__)};
|
||||
ASSERT_TRUE(IONAME(OutputNamelist)(outCookie, group));
|
||||
auto outStatus{IONAME(EndIoStatement)(outCookie)};
|
||||
ASSERT_EQ(outStatus, 0)
|
||||
@ -183,8 +177,8 @@ TEST(NamelistTests, ShortArrayInput) {
|
||||
Descriptor &internalDesc{statDesc.descriptor()};
|
||||
SubscriptValue shape{2};
|
||||
internalDesc.Establish(1, 12, t1, 1, &shape, CFI_attribute_pointer);
|
||||
auto inCookie{IONAME(BeginInternalArrayListInput)(internalDesc, nullptr, 0,
|
||||
__FILE__, __LINE__)};
|
||||
auto inCookie{IONAME(BeginInternalArrayListInput)(
|
||||
internalDesc, nullptr, 0, __FILE__, __LINE__)};
|
||||
ASSERT_TRUE(IONAME(InputNamelist)(inCookie, group));
|
||||
auto inStatus{IONAME(EndIoStatement)(inCookie)};
|
||||
ASSERT_EQ(inStatus, 0) << "Failed namelist input subscripts, status "
|
||||
@ -204,18 +198,17 @@ TEST(NamelistTests, ScalarSubstring) {
|
||||
StaticDescriptor<1, true> statDesc;
|
||||
Descriptor &internalDesc{statDesc.descriptor()};
|
||||
internalDesc.Establish(TypeCode{CFI_type_char},
|
||||
/*elementBytes=*/std::strlen(t1), t1, 0, nullptr,
|
||||
CFI_attribute_pointer);
|
||||
auto inCookie{IONAME(BeginInternalArrayListInput)(internalDesc, nullptr, 0,
|
||||
__FILE__, __LINE__)};
|
||||
/*elementBytes=*/std::strlen(t1), t1, 0, nullptr, CFI_attribute_pointer);
|
||||
auto inCookie{IONAME(BeginInternalArrayListInput)(
|
||||
internalDesc, nullptr, 0, __FILE__, __LINE__)};
|
||||
ASSERT_TRUE(IONAME(InputNamelist)(inCookie, group));
|
||||
ASSERT_EQ(IONAME(EndIoStatement)(inCookie), IostatOk)
|
||||
<< "namelist scalar substring input";
|
||||
char out[32];
|
||||
internalDesc.Establish(TypeCode{CFI_type_char}, /*elementBytes=*/sizeof out,
|
||||
out, 0, nullptr, CFI_attribute_pointer);
|
||||
auto outCookie{IONAME(BeginInternalArrayListOutput)(internalDesc, nullptr, 0,
|
||||
__FILE__, __LINE__)};
|
||||
out, 0, nullptr, CFI_attribute_pointer);
|
||||
auto outCookie{IONAME(BeginInternalArrayListOutput)(
|
||||
internalDesc, nullptr, 0, __FILE__, __LINE__)};
|
||||
ASSERT_TRUE(IONAME(SetDelim)(outCookie, "apostrophe", 10));
|
||||
ASSERT_TRUE(IONAME(OutputNamelist)(outCookie, group));
|
||||
ASSERT_EQ(IONAME(EndIoStatement)(outCookie), IostatOk) << "namelist output";
|
||||
@ -225,27 +218,26 @@ TEST(NamelistTests, ScalarSubstring) {
|
||||
}
|
||||
|
||||
TEST(NamelistTests, ArraySubstring) {
|
||||
OwningPtr<Descriptor> scDesc{MakeArray<TypeCategory::Character, 1>(
|
||||
std::vector<int>{2}, std::vector<std::string>{"abcdefgh", "ijklmnop"},
|
||||
8)};
|
||||
OwningPtr<Descriptor> scDesc{
|
||||
MakeArray<TypeCategory::Character, 1>(std::vector<int>{2},
|
||||
std::vector<std::string>{"abcdefgh", "ijklmnop"}, 8)};
|
||||
const NamelistGroup::Item items[]{{"a", *scDesc}};
|
||||
const NamelistGroup group{"justa", 1, items};
|
||||
static char t1[]{"&justa A(:)(2:+5)='BCDE' 'JKLM'/"};
|
||||
StaticDescriptor<1, true> statDesc;
|
||||
Descriptor &internalDesc{statDesc.descriptor()};
|
||||
internalDesc.Establish(TypeCode{CFI_type_char},
|
||||
/*elementBytes=*/std::strlen(t1), t1, 0, nullptr,
|
||||
CFI_attribute_pointer);
|
||||
auto inCookie{IONAME(BeginInternalArrayListInput)(internalDesc, nullptr, 0,
|
||||
__FILE__, __LINE__)};
|
||||
/*elementBytes=*/std::strlen(t1), t1, 0, nullptr, CFI_attribute_pointer);
|
||||
auto inCookie{IONAME(BeginInternalArrayListInput)(
|
||||
internalDesc, nullptr, 0, __FILE__, __LINE__)};
|
||||
ASSERT_TRUE(IONAME(InputNamelist)(inCookie, group));
|
||||
ASSERT_EQ(IONAME(EndIoStatement)(inCookie), IostatOk)
|
||||
<< "namelist scalar substring input";
|
||||
char out[40];
|
||||
internalDesc.Establish(TypeCode{CFI_type_char}, /*elementBytes=*/sizeof out,
|
||||
out, 0, nullptr, CFI_attribute_pointer);
|
||||
auto outCookie{IONAME(BeginInternalArrayListOutput)(internalDesc, nullptr, 0,
|
||||
__FILE__, __LINE__)};
|
||||
out, 0, nullptr, CFI_attribute_pointer);
|
||||
auto outCookie{IONAME(BeginInternalArrayListOutput)(
|
||||
internalDesc, nullptr, 0, __FILE__, __LINE__)};
|
||||
ASSERT_TRUE(IONAME(SetDelim)(outCookie, "apostrophe", 10));
|
||||
ASSERT_TRUE(IONAME(OutputNamelist)(outCookie, group));
|
||||
ASSERT_EQ(IONAME(EndIoStatement)(outCookie), IostatOk) << "namelist output";
|
||||
@ -264,18 +256,17 @@ TEST(NamelistTests, Skip) {
|
||||
StaticDescriptor<1, true> statDesc;
|
||||
Descriptor &internalDesc{statDesc.descriptor()};
|
||||
internalDesc.Establish(TypeCode{CFI_type_char},
|
||||
/*elementBytes=*/std::strlen(t1), t1, 0, nullptr,
|
||||
CFI_attribute_pointer);
|
||||
auto inCookie{IONAME(BeginInternalArrayListInput)(internalDesc, nullptr, 0,
|
||||
__FILE__, __LINE__)};
|
||||
/*elementBytes=*/std::strlen(t1), t1, 0, nullptr, CFI_attribute_pointer);
|
||||
auto inCookie{IONAME(BeginInternalArrayListInput)(
|
||||
internalDesc, nullptr, 0, __FILE__, __LINE__)};
|
||||
ASSERT_TRUE(IONAME(InputNamelist)(inCookie, group));
|
||||
ASSERT_EQ(IONAME(EndIoStatement)(inCookie), IostatOk)
|
||||
<< "namelist input with skipping";
|
||||
char out[20];
|
||||
internalDesc.Establish(TypeCode{CFI_type_char}, /*elementBytes=*/sizeof out,
|
||||
out, 0, nullptr, CFI_attribute_pointer);
|
||||
auto outCookie{IONAME(BeginInternalArrayListOutput)(internalDesc, nullptr, 0,
|
||||
__FILE__, __LINE__)};
|
||||
out, 0, nullptr, CFI_attribute_pointer);
|
||||
auto outCookie{IONAME(BeginInternalArrayListOutput)(
|
||||
internalDesc, nullptr, 0, __FILE__, __LINE__)};
|
||||
ASSERT_TRUE(IONAME(OutputNamelist)(outCookie, group));
|
||||
ASSERT_EQ(IONAME(EndIoStatement)(outCookie), IostatOk) << "namelist output";
|
||||
std::string got{out, sizeof out};
|
||||
@ -294,19 +285,18 @@ TEST(NamelistTests, Comma) {
|
||||
StaticDescriptor<1, true> statDesc;
|
||||
Descriptor &internalDesc{statDesc.descriptor()};
|
||||
internalDesc.Establish(TypeCode{CFI_type_char},
|
||||
/*elementBytes=*/std::strlen(t1), t1, 0, nullptr,
|
||||
CFI_attribute_pointer);
|
||||
auto inCookie{IONAME(BeginInternalArrayListInput)(internalDesc, nullptr, 0,
|
||||
__FILE__, __LINE__)};
|
||||
/*elementBytes=*/std::strlen(t1), t1, 0, nullptr, CFI_attribute_pointer);
|
||||
auto inCookie{IONAME(BeginInternalArrayListInput)(
|
||||
internalDesc, nullptr, 0, __FILE__, __LINE__)};
|
||||
ASSERT_TRUE(IONAME(SetDecimal)(inCookie, "COMMA", 5));
|
||||
ASSERT_TRUE(IONAME(InputNamelist)(inCookie, group));
|
||||
ASSERT_EQ(IONAME(EndIoStatement)(inCookie), IostatOk)
|
||||
<< "namelist input with skipping";
|
||||
char out[30];
|
||||
internalDesc.Establish(TypeCode{CFI_type_char}, /*elementBytes=*/sizeof out,
|
||||
out, 0, nullptr, CFI_attribute_pointer);
|
||||
auto outCookie{IONAME(BeginInternalArrayListOutput)(internalDesc, nullptr, 0,
|
||||
__FILE__, __LINE__)};
|
||||
out, 0, nullptr, CFI_attribute_pointer);
|
||||
auto outCookie{IONAME(BeginInternalArrayListOutput)(
|
||||
internalDesc, nullptr, 0, __FILE__, __LINE__)};
|
||||
ASSERT_TRUE(IONAME(SetDecimal)(outCookie, "COMMA", 5));
|
||||
ASSERT_TRUE(IONAME(OutputNamelist)(outCookie, group));
|
||||
ASSERT_EQ(IONAME(EndIoStatement)(outCookie), IostatOk) << "namelist output";
|
@ -11,10 +11,10 @@
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
#include "CrashHandlerFixture.h"
|
||||
#include "flang/../../runtime/terminator.h"
|
||||
#include "tools.h"
|
||||
#include "../../runtime/terminator.h"
|
||||
#include "flang/Runtime/io-api.h"
|
||||
#include "flang/Runtime/transformational.h"
|
||||
#include "tools.h"
|
||||
#include <gtest/gtest.h>
|
||||
|
||||
using namespace Fortran::runtime;
|
||||
@ -26,7 +26,7 @@ using Fortran::common::TypeCategory;
|
||||
//------------------------------------------------------------------------------
|
||||
struct TestTerminator : CrashHandlerFixture {};
|
||||
|
||||
#define TEST_CRASH_HANDLER_MESSAGE \
|
||||
#define TEST_CRASH_HANDLER_MESSAGE \
|
||||
"Intentionally crashing runtime for unit test"
|
||||
|
||||
TEST(TestTerminator, CrashTest) {
|
||||
@ -39,13 +39,13 @@ TEST(TestTerminator, CrashTest) {
|
||||
TEST(TestTerminator, CheckFailedLocationTest) {
|
||||
static Fortran::runtime::Terminator t;
|
||||
ASSERT_DEATH(t.CheckFailed("predicate", "someFileName", 789),
|
||||
"RUNTIME_CHECK\\(predicate\\) failed at someFileName\\(789\\)");
|
||||
"RUNTIME_CHECK\\(predicate\\) failed at someFileName\\(789\\)");
|
||||
}
|
||||
|
||||
TEST(TestTerminator, CheckFailedTest) {
|
||||
static Fortran::runtime::Terminator t;
|
||||
ASSERT_DEATH(t.CheckFailed("predicate"),
|
||||
"RUNTIME_CHECK\\(predicate\\) failed at \\(null\\)\\(0\\)");
|
||||
"RUNTIME_CHECK\\(predicate\\) failed at \\(null\\)\\(0\\)");
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
@ -57,10 +57,9 @@ TEST(TestIOCrash, FormatDescriptorWriteMismatchTest) {
|
||||
static constexpr int bufferSize{4};
|
||||
static char buffer[bufferSize];
|
||||
static const char *format{"(A4)"};
|
||||
auto *cookie{IONAME(BeginInternalFormattedOutput)(buffer, bufferSize, format,
|
||||
std::strlen(format))};
|
||||
ASSERT_DEATH(
|
||||
IONAME(OutputLogical)(cookie, true),
|
||||
auto *cookie{IONAME(BeginInternalFormattedOutput)(
|
||||
buffer, bufferSize, format, std::strlen(format))};
|
||||
ASSERT_DEATH(IONAME(OutputLogical)(cookie, true),
|
||||
"Data edit descriptor 'A' may not be used with a LOGICAL data item");
|
||||
}
|
||||
|
||||
@ -68,10 +67,10 @@ TEST(TestIOCrash, InvalidFormatCharacterTest) {
|
||||
static constexpr int bufferSize{1};
|
||||
static char buffer[bufferSize];
|
||||
static const char *format{"(C1)"};
|
||||
auto *cookie{IONAME(BeginInternalFormattedOutput)(buffer, bufferSize, format,
|
||||
std::strlen(format))};
|
||||
auto *cookie{IONAME(BeginInternalFormattedOutput)(
|
||||
buffer, bufferSize, format, std::strlen(format))};
|
||||
ASSERT_DEATH(IONAME(OutputInteger64)(cookie, 0xfeedface),
|
||||
"Unknown 'C' edit descriptor in FORMAT");
|
||||
"Unknown 'C' edit descriptor in FORMAT");
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
@ -84,80 +83,80 @@ TEST(TestIOCrash, OverwriteBufferAsciiTest) {
|
||||
static constexpr int bufferSize{4};
|
||||
static char buffer[bufferSize];
|
||||
static const char *format{"(A4)"};
|
||||
auto *cookie{IONAME(BeginInternalFormattedOutput)(buffer, bufferSize, format,
|
||||
std::strlen(format))};
|
||||
auto *cookie{IONAME(BeginInternalFormattedOutput)(
|
||||
buffer, bufferSize, format, std::strlen(format))};
|
||||
IONAME(OutputAscii)(cookie, "four", bufferSize);
|
||||
ASSERT_DEATH(IONAME(OutputAscii)(cookie, "Too many characters!", 20),
|
||||
"Internal write overran available records");
|
||||
"Internal write overran available records");
|
||||
}
|
||||
|
||||
TEST(TestIOCrash, OverwriteBufferCharacterTest) {
|
||||
static constexpr int bufferSize{1};
|
||||
static char buffer[bufferSize];
|
||||
static const char *format{"(A1)"};
|
||||
auto *cookie{IONAME(BeginInternalFormattedOutput)(buffer, bufferSize, format,
|
||||
std::strlen(format))};
|
||||
auto *cookie{IONAME(BeginInternalFormattedOutput)(
|
||||
buffer, bufferSize, format, std::strlen(format))};
|
||||
IONAME(OutputCharacter)(cookie, "a", 1);
|
||||
ASSERT_DEATH(IONAME(OutputCharacter)(cookie, "a", 1),
|
||||
"Internal write overran available records");
|
||||
"Internal write overran available records");
|
||||
}
|
||||
|
||||
TEST(TestIOCrash, OverwriteBufferLogicalTest) {
|
||||
static constexpr int bufferSize{1};
|
||||
static char buffer[bufferSize];
|
||||
static const char *format{"(L1)"};
|
||||
auto *cookie{IONAME(BeginInternalFormattedOutput)(buffer, bufferSize, format,
|
||||
std::strlen(format))};
|
||||
auto *cookie{IONAME(BeginInternalFormattedOutput)(
|
||||
buffer, bufferSize, format, std::strlen(format))};
|
||||
IONAME(OutputLogical)(cookie, true);
|
||||
ASSERT_DEATH(IONAME(OutputLogical)(cookie, true),
|
||||
"Internal write overran available records");
|
||||
"Internal write overran available records");
|
||||
}
|
||||
|
||||
TEST(TestIOCrash, OverwriteBufferRealTest) {
|
||||
static constexpr int bufferSize{1};
|
||||
static char buffer[bufferSize];
|
||||
static const char *format{"(F1)"};
|
||||
auto *cookie{IONAME(BeginInternalFormattedOutput)(buffer, bufferSize, format,
|
||||
std::strlen(format))};
|
||||
auto *cookie{IONAME(BeginInternalFormattedOutput)(
|
||||
buffer, bufferSize, format, std::strlen(format))};
|
||||
IONAME(OutputReal32)(cookie, 1.);
|
||||
EXPECT_DEATH(IONAME(OutputReal32)(cookie, 1.),
|
||||
"Internal write overran available records");
|
||||
"Internal write overran available records");
|
||||
|
||||
std::memset(buffer, '\0', bufferSize);
|
||||
cookie = IONAME(BeginInternalFormattedOutput)(buffer, bufferSize, format,
|
||||
std::strlen(format));
|
||||
cookie = IONAME(BeginInternalFormattedOutput)(
|
||||
buffer, bufferSize, format, std::strlen(format));
|
||||
IONAME(OutputReal64)(cookie, 1.);
|
||||
EXPECT_DEATH(IONAME(OutputReal64)(cookie, 1.),
|
||||
"Internal write overran available records");
|
||||
"Internal write overran available records");
|
||||
}
|
||||
|
||||
TEST(TestIOCrash, OverwriteBufferComplexTest) {
|
||||
static constexpr int bufferSize{8};
|
||||
static char buffer[bufferSize];
|
||||
static const char *format{"(Z1,Z1)"};
|
||||
auto *cookie{IONAME(BeginInternalFormattedOutput)(buffer, bufferSize, format,
|
||||
std::strlen(format))};
|
||||
auto *cookie{IONAME(BeginInternalFormattedOutput)(
|
||||
buffer, bufferSize, format, std::strlen(format))};
|
||||
IONAME(OutputComplex32)(cookie, 1., 1.);
|
||||
EXPECT_DEATH(IONAME(OutputComplex32)(cookie, 1., 1.),
|
||||
"Internal write overran available records");
|
||||
"Internal write overran available records");
|
||||
|
||||
std::memset(buffer, '\0', bufferSize);
|
||||
cookie = IONAME(BeginInternalFormattedOutput)(buffer, bufferSize, format,
|
||||
std::strlen(format));
|
||||
cookie = IONAME(BeginInternalFormattedOutput)(
|
||||
buffer, bufferSize, format, std::strlen(format));
|
||||
IONAME(OutputComplex64)(cookie, 1., 1.);
|
||||
EXPECT_DEATH(IONAME(OutputComplex64)(cookie, 1., 1.),
|
||||
"Internal write overran available records");
|
||||
"Internal write overran available records");
|
||||
}
|
||||
|
||||
TEST(TestIOCrash, OverwriteBufferIntegerTest) {
|
||||
static constexpr int bufferSize{1};
|
||||
static char buffer[bufferSize];
|
||||
static const char *format{"(I1)"};
|
||||
auto *cookie{IONAME(BeginInternalFormattedOutput)(buffer, bufferSize, format,
|
||||
std::strlen(format))};
|
||||
auto *cookie{IONAME(BeginInternalFormattedOutput)(
|
||||
buffer, bufferSize, format, std::strlen(format))};
|
||||
IONAME(OutputInteger64)(cookie, 0xdeadbeef);
|
||||
ASSERT_DEATH(IONAME(OutputInteger64)(cookie, 0xdeadbeef),
|
||||
"Internal write overran available records");
|
||||
"Internal write overran available records");
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
@ -169,15 +168,13 @@ TEST(TestIntrinsicCrash, ConformityErrors) {
|
||||
// ARRAY(2,3) and MASK(2,4) should trigger a runtime error.
|
||||
auto array{MakeArray<TypeCategory::Integer, 4>(
|
||||
std::vector<int>{2, 3}, std::vector<std::int32_t>{1, 2, 3, 4, 5, 6})};
|
||||
auto mask{MakeArray<TypeCategory::Logical, 1>(
|
||||
std::vector<int>{2, 4},
|
||||
std::vector<std::uint8_t>{false, true, true, false, false, true, true,
|
||||
true})};
|
||||
auto mask{MakeArray<TypeCategory::Logical, 1>(std::vector<int>{2, 4},
|
||||
std::vector<std::uint8_t>{
|
||||
false, true, true, false, false, true, true, true})};
|
||||
StaticDescriptor<1, true> statDesc;
|
||||
Descriptor &result{statDesc.descriptor()};
|
||||
|
||||
ASSERT_DEATH(
|
||||
RTNAME(Pack)(result, *array, *mask, nullptr, __FILE__, __LINE__),
|
||||
ASSERT_DEATH(RTNAME(Pack)(result, *array, *mask, nullptr, __FILE__, __LINE__),
|
||||
"Incompatible array arguments to PACK: dimension 2 of ARRAY= has extent "
|
||||
"3 but MASK= has extent 4");
|
||||
}
|
@ -11,7 +11,7 @@
|
||||
//===----------------------------------------------------------------------===//
|
||||
#include "flang/Runtime/stop.h"
|
||||
#include "CrashHandlerFixture.h"
|
||||
#include "flang/../../runtime/environment.h"
|
||||
#include "../../runtime/environment.h"
|
||||
#include <cstdlib>
|
||||
#include <gtest/gtest.h>
|
||||
|
||||
@ -21,69 +21,67 @@ struct TestProgramEnd : CrashHandlerFixture {};
|
||||
|
||||
TEST(TestProgramEnd, StopTest) {
|
||||
EXPECT_EXIT(RTNAME(StopStatement)(), testing::ExitedWithCode(EXIT_SUCCESS),
|
||||
"Fortran STOP");
|
||||
"Fortran STOP");
|
||||
}
|
||||
|
||||
TEST(TestProgramEnd, StopTestNoStopMessage) {
|
||||
putenv(const_cast<char *>("NO_STOP_MESSAGE=1"));
|
||||
Fortran::runtime::executionEnvironment.Configure(0, nullptr, nullptr,
|
||||
nullptr);
|
||||
EXPECT_EXIT(RTNAME(StopStatement)(), testing::ExitedWithCode(EXIT_SUCCESS),
|
||||
"");
|
||||
Fortran::runtime::executionEnvironment.Configure(
|
||||
0, nullptr, nullptr, nullptr);
|
||||
EXPECT_EXIT(
|
||||
RTNAME(StopStatement)(), testing::ExitedWithCode(EXIT_SUCCESS), "");
|
||||
}
|
||||
|
||||
TEST(TestProgramEnd, StopMessageTest) {
|
||||
static const char *message{"bye bye"};
|
||||
EXPECT_EXIT(RTNAME(StopStatementText)(message, std::strlen(message),
|
||||
/*isErrorStop=*/false, /*quiet=*/false),
|
||||
testing::ExitedWithCode(EXIT_SUCCESS), "Fortran STOP: bye bye");
|
||||
/*isErrorStop=*/false, /*quiet=*/false),
|
||||
testing::ExitedWithCode(EXIT_SUCCESS), "Fortran STOP: bye bye");
|
||||
|
||||
EXPECT_EXIT(RTNAME(StopStatementText)(message, std::strlen(message),
|
||||
/*isErrorStop=*/false, /*quiet=*/true),
|
||||
testing::ExitedWithCode(EXIT_SUCCESS), "");
|
||||
/*isErrorStop=*/false, /*quiet=*/true),
|
||||
testing::ExitedWithCode(EXIT_SUCCESS), "");
|
||||
|
||||
EXPECT_EXIT(RTNAME(StopStatementText)(message, std::strlen(message),
|
||||
/*isErrorStop=*/true, /*quiet=*/false),
|
||||
testing::ExitedWithCode(EXIT_FAILURE),
|
||||
"Fortran ERROR STOP: bye bye");
|
||||
/*isErrorStop=*/true, /*quiet=*/false),
|
||||
testing::ExitedWithCode(EXIT_FAILURE), "Fortran ERROR STOP: bye bye");
|
||||
|
||||
EXPECT_EXIT(RTNAME(StopStatementText)(message, std::strlen(message),
|
||||
/*isErrorStop=*/true, /*quiet=*/true),
|
||||
testing::ExitedWithCode(EXIT_FAILURE), "");
|
||||
/*isErrorStop=*/true, /*quiet=*/true),
|
||||
testing::ExitedWithCode(EXIT_FAILURE), "");
|
||||
}
|
||||
|
||||
TEST(TestProgramEnd, NoStopMessageTest) {
|
||||
putenv(const_cast<char *>("NO_STOP_MESSAGE=1"));
|
||||
Fortran::runtime::executionEnvironment.Configure(0, nullptr, nullptr,
|
||||
nullptr);
|
||||
Fortran::runtime::executionEnvironment.Configure(
|
||||
0, nullptr, nullptr, nullptr);
|
||||
static const char *message{"bye bye"};
|
||||
EXPECT_EXIT(RTNAME(StopStatementText)(message, std::strlen(message),
|
||||
/*isErrorStop=*/false, /*quiet=*/false),
|
||||
testing::ExitedWithCode(EXIT_SUCCESS), "bye bye");
|
||||
/*isErrorStop=*/false, /*quiet=*/false),
|
||||
testing::ExitedWithCode(EXIT_SUCCESS), "bye bye");
|
||||
|
||||
EXPECT_EXIT(RTNAME(StopStatementText)(message, std::strlen(message),
|
||||
/*isErrorStop=*/false, /*quiet=*/true),
|
||||
testing::ExitedWithCode(EXIT_SUCCESS), "");
|
||||
/*isErrorStop=*/false, /*quiet=*/true),
|
||||
testing::ExitedWithCode(EXIT_SUCCESS), "");
|
||||
|
||||
EXPECT_EXIT(RTNAME(StopStatementText)(message, std::strlen(message),
|
||||
/*isErrorStop=*/true, /*quiet=*/false),
|
||||
testing::ExitedWithCode(EXIT_FAILURE),
|
||||
"Fortran ERROR STOP: bye bye");
|
||||
/*isErrorStop=*/true, /*quiet=*/false),
|
||||
testing::ExitedWithCode(EXIT_FAILURE), "Fortran ERROR STOP: bye bye");
|
||||
|
||||
EXPECT_EXIT(RTNAME(StopStatementText)(message, std::strlen(message),
|
||||
/*isErrorStop=*/true, /*quiet=*/true),
|
||||
testing::ExitedWithCode(EXIT_FAILURE), "");
|
||||
/*isErrorStop=*/true, /*quiet=*/true),
|
||||
testing::ExitedWithCode(EXIT_FAILURE), "");
|
||||
}
|
||||
|
||||
TEST(TestProgramEnd, FailImageTest) {
|
||||
EXPECT_EXIT(RTNAME(FailImageStatement)(),
|
||||
testing::ExitedWithCode(EXIT_FAILURE), "");
|
||||
EXPECT_EXIT(
|
||||
RTNAME(FailImageStatement)(), testing::ExitedWithCode(EXIT_FAILURE), "");
|
||||
}
|
||||
|
||||
TEST(TestProgramEnd, ExitTest) {
|
||||
EXPECT_EXIT(RTNAME(Exit)(), testing::ExitedWithCode(EXIT_SUCCESS), "");
|
||||
EXPECT_EXIT(RTNAME(Exit)(EXIT_FAILURE), testing::ExitedWithCode(EXIT_FAILURE),
|
||||
"");
|
||||
EXPECT_EXIT(
|
||||
RTNAME(Exit)(EXIT_FAILURE), testing::ExitedWithCode(EXIT_FAILURE), "");
|
||||
}
|
||||
|
||||
TEST(TestProgramEnd, AbortTest) { EXPECT_DEATH(RTNAME(Abort)(), ""); }
|
||||
@ -93,8 +91,8 @@ TEST(TestProgramEnd, CrashTest) {
|
||||
static const std::string fileName{"file name"};
|
||||
static const std::string headMessage{"fatal Fortran runtime error\\("};
|
||||
static const std::string tailMessage{":343\\): "};
|
||||
static const std::string fullMessage{headMessage + fileName + tailMessage +
|
||||
crashMessage};
|
||||
static const std::string fullMessage{
|
||||
headMessage + fileName + tailMessage + crashMessage};
|
||||
EXPECT_DEATH(
|
||||
RTNAME(ReportFatalUserError)(crashMessage.c_str(), fileName.c_str(), 343),
|
||||
fullMessage.c_str());
|
@ -50,7 +50,8 @@ AutoExporter::AutoExporter(
|
||||
"libc++",
|
||||
"libc++abi",
|
||||
"libFortran_main",
|
||||
"libflang-rt",
|
||||
"libFortranRuntime",
|
||||
"libFortranDecimal",
|
||||
"libunwind",
|
||||
"libmsvcrt",
|
||||
"libucrtbase",
|
||||
|
@ -156,10 +156,7 @@ endif()
|
||||
# As we migrate runtimes to using the bootstrapping build, the set of default runtimes
|
||||
# should grow as we remove those runtimes from LLVM_ENABLE_PROJECTS above.
|
||||
set(LLVM_DEFAULT_RUNTIMES "libcxx;libcxxabi;libunwind")
|
||||
if ("flang" IN_LIST LLVM_ENABLE_PROJECTS)
|
||||
set(LLVM_DEFAULT_RUNTIMES "libcxx;libcxxabi;libunwind;flang-rt")
|
||||
endif()
|
||||
set(LLVM_SUPPORTED_RUNTIMES "libc;libunwind;libcxxabi;pstl;libcxx;compiler-rt;openmp;llvm-libgcc;flang-rt")
|
||||
set(LLVM_SUPPORTED_RUNTIMES "libc;libunwind;libcxxabi;pstl;libcxx;compiler-rt;openmp;llvm-libgcc")
|
||||
set(LLVM_ENABLE_RUNTIMES "" CACHE STRING
|
||||
"Semicolon-separated list of runtimes to build, or \"all\" (${LLVM_DEFAULT_RUNTIMES}). Supported runtimes are ${LLVM_SUPPORTED_RUNTIMES}.")
|
||||
if(LLVM_ENABLE_RUNTIMES STREQUAL "all")
|
||||
@ -181,11 +178,6 @@ if ("libc" IN_LIST LLVM_ENABLE_RUNTIMES)
|
||||
endif()
|
||||
endif()
|
||||
|
||||
if ("flang" IN_LIST LLVM_ENABLE_PROJECTS AND NOT "flang-rt" IN_LIST LLVM_ENABLE_RUNTIMES)
|
||||
message(STATUS "Enabling Flang-rt to be built with the Flang project.")
|
||||
list(APPEND LLVM_ENABLE_RUNTIMES "flang-rt")
|
||||
endif()
|
||||
|
||||
# LLVM_ENABLE_PROJECTS_USED is `ON` if the user has ever used the
|
||||
# `LLVM_ENABLE_PROJECTS` CMake cache variable. This exists for
|
||||
# several reasons:
|
||||
|
@ -6,7 +6,6 @@ foreach(entry ${entries})
|
||||
if(IS_DIRECTORY ${entry} AND EXISTS ${entry}/CMakeLists.txt)
|
||||
if((NOT ${entry} STREQUAL ${CMAKE_CURRENT_SOURCE_DIR}/compiler-rt) AND
|
||||
(NOT ${entry} STREQUAL ${CMAKE_CURRENT_SOURCE_DIR}/dragonegg) AND
|
||||
(NOT ${entry} STREQUAL ${CMAKE_CURRENT_SOURCE_DIR}/flang-rt) AND
|
||||
(NOT ${entry} STREQUAL ${CMAKE_CURRENT_SOURCE_DIR}/libcxx) AND
|
||||
(NOT ${entry} STREQUAL ${CMAKE_CURRENT_SOURCE_DIR}/libcxxabi) AND
|
||||
(NOT ${entry} STREQUAL ${CMAKE_CURRENT_SOURCE_DIR}/libunwind) AND
|
||||
@ -38,8 +37,6 @@ if(${LLVM_BUILD_RUNTIME})
|
||||
if(NOT LLVM_BUILD_EXTERNAL_COMPILER_RT)
|
||||
add_llvm_external_project(compiler-rt)
|
||||
endif()
|
||||
|
||||
add_llvm_external_project(flang-rt)
|
||||
endif()
|
||||
|
||||
add_llvm_external_project(dragonegg)
|
||||
|
@ -401,24 +401,17 @@ if(runtimes)
|
||||
endforeach()
|
||||
endif()
|
||||
endif()
|
||||
set(EXTRA_CMAKE_ARGS "")
|
||||
if("flang-rt" IN_LIST LLVM_ENABLE_RUNTIMES)
|
||||
list(APPEND EXTRA_CMAKE_ARGS "-DLLVM_DIR=${LLVM_BINARY_DIR}/lib/cmake/llvm")
|
||||
list(APPEND EXTRA_CMAKE_ARGS "-DFLANG_DIR=${LLVM_BINARY_DIR}/lib/cmake/flang")
|
||||
list(APPEND EXTRA_CMAKE_ARGS "-DCLANG_DIR=${LLVM_BINARY_DIR}/lib/cmake/clang")
|
||||
list(APPEND EXTRA_CMAKE_ARGS "-DMLIR_DIR=${LLVM_BINARY_DIR}/lib/cmake/mlir")
|
||||
endif()
|
||||
if(NOT LLVM_RUNTIME_TARGETS)
|
||||
runtime_default_target(
|
||||
DEPENDS ${builtins_dep} ${extra_deps}
|
||||
CMAKE_ARGS ${libc_cmake_args} ${EXTRA_CMAKE_ARGS}
|
||||
CMAKE_ARGS ${libc_cmake_args}
|
||||
PREFIXES ${prefixes})
|
||||
set(test_targets check-runtimes)
|
||||
else()
|
||||
if("default" IN_LIST LLVM_RUNTIME_TARGETS)
|
||||
runtime_default_target(
|
||||
DEPENDS ${builtins_dep} ${extra_deps}
|
||||
CMAKE_ARGS ${libc_cmake_args} ${EXTRA_CMAKE_ARGS}
|
||||
CMAKE_ARGS ${libc_cmake_args}
|
||||
PREFIXES ${prefixes})
|
||||
list(REMOVE_ITEM LLVM_RUNTIME_TARGETS "default")
|
||||
else()
|
||||
@ -458,7 +451,7 @@ if(runtimes)
|
||||
|
||||
runtime_register_target(${name}
|
||||
DEPENDS ${builtins_dep_name} ${libc_tools}
|
||||
CMAKE_ARGS -DLLVM_DEFAULT_TARGET_TRIPLE=${name} ${libc_cmake_args} ${EXTRA_CMAKE_ARGS}
|
||||
CMAKE_ARGS -DLLVM_DEFAULT_TARGET_TRIPLE=${name} ${libc_cmake_args}
|
||||
EXTRA_ARGS TARGET_TRIPLE ${name})
|
||||
|
||||
add_dependencies(runtimes runtimes-${name})
|
||||
@ -488,7 +481,6 @@ if(runtimes)
|
||||
CMAKE_ARGS -DLLVM_DEFAULT_TARGET_TRIPLE=${name}
|
||||
-DLLVM_RUNTIMES_PREFIX=${name}/
|
||||
-DLLVM_RUNTIMES_LIBDIR_SUBDIR=${multilib}
|
||||
${EXTRA_CMAKE_ARGS}
|
||||
BASE_NAME ${name}
|
||||
EXTRA_ARGS TARGET_TRIPLE ${name})
|
||||
|
||||
|
@ -19,7 +19,7 @@ list(INSERT CMAKE_MODULE_PATH 0
|
||||
|
||||
# We order libraries to mirror roughly how they are layered, except that compiler-rt can depend
|
||||
# on libc++, so we put it after.
|
||||
set(LLVM_DEFAULT_RUNTIMES "libc;libunwind;libcxxabi;pstl;libcxx;compiler-rt;openmp;flang-rt")
|
||||
set(LLVM_DEFAULT_RUNTIMES "libc;libunwind;libcxxabi;pstl;libcxx;compiler-rt;openmp")
|
||||
set(LLVM_SUPPORTED_RUNTIMES "${LLVM_DEFAULT_RUNTIMES};llvm-libgcc")
|
||||
set(LLVM_ENABLE_RUNTIMES "" CACHE STRING
|
||||
"Semicolon-separated list of runtimes to build, or \"all\" (${LLVM_DEFAULT_RUNTIMES}). Supported runtimes are ${LLVM_SUPPORTED_RUNTIMES}.")
|
||||
|
Loading…
x
Reference in New Issue
Block a user