blob: 0c440700578a71afb09315b2b088f25595c0b4c8 [file] [log] [blame]
# Copyright (C) 2007-2022 Free Software Foundation, Inc.
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 3 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with GCC; see the file COPYING3. If not see
# <http://www.gnu.org/licenses/>.
# GCC testsuite that uses the `dg.exp' driver.
global torture_current_flags
set torture_current_flags ""
# Exit immediately if this isn't a s390 target.
if ![istarget s390*-*-*] then {
return
}
# Load support procs.
load_lib gcc-dg.exp
load_lib target-supports.exp
load_lib gfortran-dg.exp
load_lib atomic-dg.exp
# Return 1 if the the assembler understands .machine and .machinemode. The
# target attribute needs that feature to work.
proc check_effective_target_target_attribute { } {
if { ![check_runtime s390_check_machine_machinemode [subst {
int main (void)
{
asm (".machine push" : : );
asm (".machine pop" : : );
asm (".machinemode push" : : );
asm (".machinemode pop" : : );
return 0;
}
}] "" ] } { return 0 } else { return 1 }
}
# Return 1 if htm (etnd - extract nesting depth) instructions are
# understood by the assembler and can be executed.
proc check_effective_target_htm { } {
if { ![check_runtime s390_check_htm [subst {
int main (void)
{
unsigned int nd;
asm ("etnd %0" : "=d" (nd));
return nd;
}
}] "-march=zEC12 -mzarch" ] } { return 0 } else { return 1 }
}
global s390_cached_flags
set s390_cached_flags ""
global s390_cached_value
set s390_cached_value ""
global s390_cached_value_noflags
set s390_cached_value_noflags ""
# Return 1 if a program using the full instruction set allowed by
# the compiler option can be executed.
proc check_effective_target_s390_useable_hw { } {
global torture_current_flags
global s390_cached_flags
global s390_cached_value
global s390_cached_value_noflags
# Remove -Ox options and whitespace.
set flags [regsub -all {[-]O[0-9s]} "$torture_current_flags" ""]
set flags [regsub -all {[ \\t\\n]+} "$flags" " "]
set flags [regsub -all {(^ )|( $)} "$flags" ""]
if { "$s390_cached_flags" != "" && "$flags" == "$s390_cached_flags" } {
return $s390_cached_value
}
# Extra cache for (frequent) calls with empty torture_current_flags.
if { "$flags" == "" && $s390_cached_value_noflags != "" } {
return $s390_cached_value_noflags
}
if { ![check_runtime_nocache s390_check_useable_hw [subst {
int main (void)
{
asm (".machinemode zarch" : : );
#if __ARCH__ >= 13
asm ("ncrk %%r2,%%r2,%%r2" : : : "r2");
#elif __ARCH__ >= 12
asm ("agh %%r2,0(%%r15)" : : : "r2");
#elif __ARCH__ >= 11
asm ("lochiz %%r2,42" : : : "r2");
#elif __ARCH__ >= 10
asm ("risbgn %%r2,%%r2,0,0,0" : : : "r2");
#elif __ARCH__ >= 9
asm ("sgrk %%r2,%%r2,%%r2" : : : "r2");
#elif __ARCH__ >= 8
asm ("rosbg %%r2,%%r2,0,0,0" : : : "r2");
#elif __ARCH__ >= 7
asm ("nilf %%r2,0" : : : "r2");
#elif __ARCH__ >= 6
asm ("lay %%r2,0(%%r15)" : : : "r2");
#elif __ARCH__ >= 5
asm ("tam" : : );
#endif
#ifdef __HTM__
{
unsigned int nd;
asm ("etnd %0" : "=d" (nd));
}
#endif
#if defined (__VX__) && defined (__zarch__)
asm ("vzero %%v0" : : : "v0");
#endif
return 0;
}
}] "$flags" ] } { set result 0 } else { set result 1 }
if { "$flags" == "" } {
set s390_cached_value_noflags "$result"
} else {
set s390_cached_flags "$flags"
set s390_cached_value "$result"
}
return $result
}
# Return 1 if -march=... specific instructions are understood by
# the assembler and can be executed.
proc check_effective_target_s390_z900_hw { } {
if { ![check_runtime s390_check_s390_z900_hw [subst {
int main (void)
{
asm ("tam" : : );
return 0;
}
}] "-march=z900 -m64 -mzarch" ] } { return 0 } else { return 1 }
}
proc check_effective_target_s390_z990_hw { } {
if { ![check_runtime s390_check_s390_z990_hw [subst {
int main (void)
{
asm ("lay %%r2,0(%%r15)" : : );
return 0;
}
}] "-march=z990 -m64 -mzarch" ] } { return 0 } else { return 1 }
}
proc check_effective_target_s390_z9_ec_hw { } {
if { ![check_runtime s390_check_s390_z9_ec_hw [subst {
int main (void)
{
asm ("nilf %%r2,0" : : );
return 0;
}
}] "-march=z9-ec -m64 -mzarch" ] } { return 0 } else { return 1 }
}
proc check_effective_target_s390_z10_hw { } {
if { ![check_runtime s390_check_s390_z10_hw [subst {
int main (void)
{
asm ("rosbg %%r2,%%r2,0,0,0" : : );
return 0;
}
}] "-march=z10 -m64 -mzarch" ] } { return 0 } else { return 1 }
}
proc check_effective_target_s390_z196_hw { } {
if { ![check_runtime s390_check_s390_z196_hw [subst {
int main (void)
{
asm ("sgrk %%r2,%%r2,%%r2" : : );
return 0;
}
}] "-march=z196 -m64 -mzarch" ] } { return 0 } else { return 1 }
}
proc check_effective_target_s390_zEC12_hw { } {
if { ![check_runtime s390_check_s390_zEC12_hw [subst {
int main (void)
{
asm ("risbgn %%r2,%%r2,0,0,0" : : );
return 0;
}
}] "-march=zEC12 -m64 -mzarch" ] } { return 0 } else { return 1 }
}
proc check_effective_target_s390_z13_hw { } {
if { ![check_runtime s390_check_s390_z13_hw [subst {
int main (void)
{
asm ("lcbb %%r2,0(%%r15),0" : : );
return 0;
}
}] "-march=z13 -m64 -mzarch" ] } { return 0 } else { return 1 }
}
proc check_effective_target_s390_z14_hw { } {
if { ![check_runtime s390_check_s390_z14_hw [subst {
int main (void)
{
int x = 0;
asm ("msgrkc %0,%0,%0" : "+r" (x) : );
return x;
}
}] "-march=z14 -m64 -mzarch" ] } { return 0 } else { return 1 }
}
# Return 1 if the default compiler options enable z/Architecture mode
proc check_effective_target_s390_zarch { } {
return [check_no_compiler_messages s390_zarch object {
int dummy[sizeof (int __attribute__((__mode__(__word__)))) == 8
? 1 : -1];
}]
}
# If a testcase doesn't have special options, use these.
global DEFAULT_CFLAGS
if ![info exists DEFAULT_CFLAGS] then {
set DEFAULT_CFLAGS " -ansi -pedantic-errors"
}
global DEFAULT_FFLAGS
if ![info exists DEFAULT_FFLAGS] then {
set DEFAULT_FFLAGS " -pedantic-errors"
}
# Initialize `dg'.
dg-init
set md_tests $srcdir/$subdir/md/*.c
# C++ tests belong into g++.dg with a target check. Do NOT add C to
# these regexps!
# Main loop.
dg-runtest [lsort [prune [glob -nocomplain $srcdir/$subdir/*.{c,S}] \
$md_tests]] "" $DEFAULT_CFLAGS
dg-runtest [lsort [glob -nocomplain $srcdir/$subdir/*vector*/*.{c,S}]] \
"" $DEFAULT_CFLAGS
gfortran-dg-runtest [lsort [glob -nocomplain $srcdir/$subdir/*vector*/*.F90]] \
"" $DEFAULT_FFLAGS
dg-runtest [lsort [glob -nocomplain $srcdir/$subdir/target-attribute/*.{c,S}]] \
"" $DEFAULT_CFLAGS
dg-runtest [lsort [glob -nocomplain $srcdir/$subdir/arch12/*.{c,S}]] \
"" "-O3 -march=arch12 -mzarch"
dg-runtest [lsort [glob -nocomplain $srcdir/$subdir/arch13/*.{c,S}]] \
"" "-O3 -march=arch13 -mzarch"
dg-runtest [lsort [glob -nocomplain $srcdir/$subdir/vxe/*.{c,S}]] \
"" "-O3 -march=arch12 -mzarch"
# Some md tests require libatomic
atomic_init
dg-runtest [lsort [glob -nocomplain $srcdir/$subdir/md/*.{c,S}]] \
"" $DEFAULT_CFLAGS
# Additional hotpatch torture tests.
torture-init
set-torture-options [list -Os -O1 -O2 -O3]
gcc-dg-runtest [lsort [glob -nocomplain $srcdir/$subdir/hotpatch-\[0-9\]*.c]] \
"" $DEFAULT_CFLAGS
torture-finish
# Additional md torture tests.
# (Note: Split into a separate torture test for each -march= option to improve
# cacheability.)
torture-init
set MD_TEST_OPTS [list \
{-Os} {-Os -march=z900} \
{-O0} {-O0 -march=z900} \
{-O1} {-O1 -march=z900} \
{-O2} {-O2 -march=z900} \
{-O3} {-O3 -march=z900} ]
set-torture-options $MD_TEST_OPTS
gcc-dg-runtest [lsort [glob -nocomplain $md_tests]] "" "$DEFAULT_CFLAGS"
torture-finish
torture-init
set MD_TEST_OPTS [list \
{-Os -march=z13} \
{-O0 -march=z13} \
{-O1 -march=z13} \
{-O2 -march=z13} \
{-O3 -march=z13} ]
set-torture-options $MD_TEST_OPTS
gcc-dg-runtest [lsort [glob -nocomplain $md_tests]] "" "$DEFAULT_CFLAGS"
torture-finish
# Tests that should pass on all optimization levels.
foreach t [list $srcdir/$subdir/pr80080-3.c] {
torture-init
set-torture-options [list -O1 -O2 -O3 -O0 -Os -Ofast -Og]
gcc-dg-runtest [list $t] \
"" $DEFAULT_CFLAGS
torture-finish
}
# All done.
atomic_finish
dg-finish