Add check-tcg machinary
This restores the ability to run TCG smoke tests by using our docker infrastructure to support cross building simple tests. It represents the first step to making better cross-architecture testing available straight from the source tree ;-) v2 - fix quoting of target_compiler - make docker.py Py3 safe - tweak .travis.yml recipe - don't probe docker when HAVE_USER_DOCKER not set -----BEGIN PGP SIGNATURE----- iQEzBAABCgAdFiEEZoWumedRZ7yvyN81+9DbCVqeKkQFAlsrRHEACgkQ+9DbCVqe KkSRhAf9EkJLIkB0uUs6NXu8ZKbMoAFlpQtbHZ36/YvTWHW+oDOBjYkZyrRlsTMR lIpm51wSAtVOJnScFASKbYQAD4ZTw2CUjwRqkCUhWI/vJOR7NvzZHfF+SHCNl8QE un7N/n3pWga7vY3j5Pd9cXz14im42Lcyl/xL5juh0lpCo+dw9OTdMT49sPF3YJGC N7uK3gIqFg24nofCAZq/YyUGzfftSkZ8x6D9k9fhHyPUGh+28sE2Ahptb6jGAYnr IcfHSUFkHpvliEJCJ50ho3iNF/JvV57gluW/LLQua35XBJ7sgiXHlhJP6Fnkobps Z8tzaEFGg96fFOreSs0PkqTrLhMO5w== =BIF8 -----END PGP SIGNATURE----- Merge remote-tracking branch 'remotes/stsquad/tags/pull-tcg-testing-revivial-210618-2' into staging Add check-tcg machinary This restores the ability to run TCG smoke tests by using our docker infrastructure to support cross building simple tests. It represents the first step to making better cross-architecture testing available straight from the source tree ;-) v2 - fix quoting of target_compiler - make docker.py Py3 safe - tweak .travis.yml recipe - don't probe docker when HAVE_USER_DOCKER not set # gpg: Signature made Thu 21 Jun 2018 07:23:45 BST # gpg: using RSA key FBD0DB095A9E2A44 # gpg: Good signature from "Alex Bennée (Master Work Key) <alex.bennee@linaro.org>" # Primary key fingerprint: 6685 AE99 E751 67BC AFC8 DF35 FBD0 DB09 5A9E 2A44 * remotes/stsquad/tags/pull-tcg-testing-revivial-210618-2: (57 commits) .travis.yml: add check-tcg test tests/docker/Makefile.include: only force SID to NOCACHE if old docker: docker.py adding age check command tests/Makefile: call sub-makes with SKIP_DOCKER_BUILD=1 docker: docker.py add check sub-command docker: docker.py don't conflate checksums for extra_files docker: docker.py use "version" to probe usage tests: add top-level make dependency for docker builds tests/tcg/i386: extend timeout for runcom test tests/tcg: override runners for broken tests tests/tcg: add run, diff, and skip helper macros tests/Makefile.include: add [build|clean|check]-tcg targets Makefile.target: add (clean-/build-)guest-tests targets tests/tcg/Makefile: update to be called from Makefile.target tests/tcg: enable building for PowerPC docker: move debian-powerpc-cross to sid based build tests/tcg: enable building for RISCV64 tests/tcg: enable building for mips64 tests/tcg: enable building for sparc64 tests/tcg: enable building for sh4 ... Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
This commit is contained in:
commit
de44c04442
|
@ -153,3 +153,11 @@ matrix:
|
|||
- TEST_CMD=""
|
||||
before_script:
|
||||
- ./configure ${CONFIG} --extra-cflags="-g3 -O0 -fsanitize=thread -fuse-ld=gold" || { cat config.log && exit 1; }
|
||||
- env:
|
||||
- CONFIG="--disable-system --disable-docs"
|
||||
- TEST_CMD="make check-tcg"
|
||||
script:
|
||||
- make ${MAKEFLAGS} && ${TEST_CMD} ${MAKEFLAGS}
|
||||
sudo: required
|
||||
dist: trusty
|
||||
compiler: gcc
|
||||
|
|
15
MAINTAINERS
15
MAINTAINERS
|
@ -135,6 +135,8 @@ M: Peter Maydell <peter.maydell@linaro.org>
|
|||
L: qemu-arm@nongnu.org
|
||||
S: Maintained
|
||||
F: target/arm/
|
||||
F: tests/tcg/arm/
|
||||
F: tests/tcg/aarch64/
|
||||
F: hw/arm/
|
||||
F: hw/cpu/a*mpcore.c
|
||||
F: include/hw/cpu/a*mpcore.h
|
||||
|
@ -283,6 +285,8 @@ M: Richard Henderson <rth@twiddle.net>
|
|||
M: Eduardo Habkost <ehabkost@redhat.com>
|
||||
S: Maintained
|
||||
F: target/i386/
|
||||
F: tests/tcg/i386/
|
||||
F: tests/tcg/x86_64/
|
||||
F: hw/i386/
|
||||
F: disas/i386.c
|
||||
T: git git://github.com/ehabkost/qemu.git x86-next
|
||||
|
@ -303,6 +307,10 @@ F: target/tricore/
|
|||
F: hw/tricore/
|
||||
F: include/hw/tricore/
|
||||
|
||||
Multiarch Linux User Tests
|
||||
M: Alex Bennée <alex.bennee@linaro.org>
|
||||
F: tests/tcg/multiarch/
|
||||
|
||||
Guest CPU Cores (KVM):
|
||||
----------------------
|
||||
|
||||
|
@ -2149,6 +2157,13 @@ W: https://travis-ci.org/qemu/qemu
|
|||
W: https://app.shippable.com/github/qemu/qemu
|
||||
W: http://patchew.org/QEMU/
|
||||
|
||||
Guest Test Compilation Support
|
||||
M: Alex Bennée <alex.bennee@linaro.org>
|
||||
R: Philippe Mathieu-Daudé <f4bug@amsat.org>
|
||||
F: tests/tcg/Makefile
|
||||
F: tests/tcg/Makefile.include
|
||||
L: qemu-devel@nongnu.org
|
||||
|
||||
Documentation
|
||||
-------------
|
||||
Build system architecture
|
||||
|
|
|
@ -36,6 +36,11 @@ endif
|
|||
PROGS=$(QEMU_PROG) $(QEMU_PROGW)
|
||||
STPFILES=
|
||||
|
||||
# Makefile Tests
|
||||
ifdef CONFIG_USER_ONLY
|
||||
include $(SRC_PATH)/tests/tcg/Makefile.include
|
||||
endif
|
||||
|
||||
config-target.h: config-target.h-timestamp
|
||||
config-target.h-timestamp: config-target.mak
|
||||
|
||||
|
|
133
configure
vendored
133
configure
vendored
|
@ -289,7 +289,6 @@ libs_softmmu=""
|
|||
libs_tools=""
|
||||
audio_pt_int=""
|
||||
audio_win_int=""
|
||||
cc_i386=i386-pc-linux-gnu-gcc
|
||||
libs_qga=""
|
||||
debug_info="yes"
|
||||
stack_protector=""
|
||||
|
@ -458,6 +457,19 @@ vxhs=""
|
|||
libxml2=""
|
||||
docker="no"
|
||||
|
||||
# cross compilers defaults, can be overridden with --cross-cc-ARCH
|
||||
cross_cc_aarch64="aarch64-linux-gnu-gcc"
|
||||
cross_cc_aarch64_be="$cross_cc_aarch64"
|
||||
cross_cc_cflags_aarch64_be="-mbig-endian"
|
||||
cross_cc_arm="arm-linux-gnueabihf-gcc"
|
||||
cross_cc_cflags_armeb="-mbig-endian"
|
||||
cross_cc_i386="i386-pc-linux-gnu-gcc"
|
||||
cross_cc_cflags_i386=""
|
||||
cross_cc_powerpc="powerpc-linux-gnu-gcc"
|
||||
cross_cc_powerpc="powerpc-linux-gnu-gcc"
|
||||
|
||||
enabled_cross_compilers=""
|
||||
|
||||
supported_cpu="no"
|
||||
supported_os="no"
|
||||
bogus_os="no"
|
||||
|
@ -488,6 +500,14 @@ for opt do
|
|||
;;
|
||||
--disable-debug-info) debug_info="no"
|
||||
;;
|
||||
--cross-cc-*[!a-zA-Z0-9_-]*=*) error_exit "Passed bad --cross-cc-FOO option"
|
||||
;;
|
||||
--cross-cc-cflags-*) cc_arch=${opt#--cross-cc-flags-}; cc_arch=${cc_arch%%=*}
|
||||
eval "cross_cc_cflags_${cc_arch}=\$optarg"
|
||||
;;
|
||||
--cross-cc-*) cc_arch=${opt#--cross-cc-}; cc_arch=${cc_arch%%=*}
|
||||
eval "cross_cc_${cc_arch}=\$optarg"
|
||||
;;
|
||||
esac
|
||||
done
|
||||
# OS specific
|
||||
|
@ -676,30 +696,37 @@ case "$cpu" in
|
|||
ppc|ppc64|s390|s390x|sparc64|x32)
|
||||
cpu="$cpu"
|
||||
supported_cpu="yes"
|
||||
eval "cross_cc_${cpu}=\$host_cc"
|
||||
;;
|
||||
i386|i486|i586|i686|i86pc|BePC)
|
||||
cpu="i386"
|
||||
supported_cpu="yes"
|
||||
cross_cc_i386=$host_cc
|
||||
;;
|
||||
x86_64|amd64)
|
||||
cpu="x86_64"
|
||||
supported_cpu="yes"
|
||||
cross_cc_x86_64=$host_cc
|
||||
;;
|
||||
armv*b|armv*l|arm)
|
||||
cpu="arm"
|
||||
supported_cpu="yes"
|
||||
cross_cc_arm=$host_cc
|
||||
;;
|
||||
aarch64)
|
||||
cpu="aarch64"
|
||||
supported_cpu="yes"
|
||||
cross_cc_aarch64=$host_cc
|
||||
;;
|
||||
mips*)
|
||||
cpu="mips"
|
||||
supported_cpu="yes"
|
||||
cross_cc_mips=$host_cc
|
||||
;;
|
||||
sparc|sun4[cdmuv])
|
||||
cpu="sparc"
|
||||
supported_cpu="yes"
|
||||
cross_cc_sparc=$host_cc
|
||||
;;
|
||||
*)
|
||||
# This will result in either an error or falling back to TCI later
|
||||
|
@ -917,6 +944,8 @@ for opt do
|
|||
;;
|
||||
--disable-debug-info)
|
||||
;;
|
||||
--cross-cc-*)
|
||||
;;
|
||||
--enable-modules)
|
||||
modules="yes"
|
||||
;;
|
||||
|
@ -1402,31 +1431,44 @@ case "$cpu" in
|
|||
ppc)
|
||||
CPU_CFLAGS="-m32"
|
||||
LDFLAGS="-m32 $LDFLAGS"
|
||||
cross_cc_powerpc=$cc
|
||||
cross_cc_cflags_powerpc=$CPU_CFLAGS
|
||||
;;
|
||||
ppc64)
|
||||
CPU_CFLAGS="-m64"
|
||||
LDFLAGS="-m64 $LDFLAGS"
|
||||
cross_cc_ppc64=$cc
|
||||
cross_cc_cflags_ppc64=$CPU_CFLAGS
|
||||
;;
|
||||
sparc)
|
||||
CPU_CFLAGS="-m32 -mv8plus -mcpu=ultrasparc"
|
||||
LDFLAGS="-m32 -mv8plus $LDFLAGS"
|
||||
cross_cc_sparc=$cc
|
||||
cross_cc_cflags_sparc=$CPU_CFLAGS
|
||||
;;
|
||||
sparc64)
|
||||
CPU_CFLAGS="-m64 -mcpu=ultrasparc"
|
||||
LDFLAGS="-m64 $LDFLAGS"
|
||||
cross_cc_sparc64=$cc
|
||||
cross_cc_cflags_sparc64=$CPU_CFLAGS
|
||||
;;
|
||||
s390)
|
||||
CPU_CFLAGS="-m31"
|
||||
LDFLAGS="-m31 $LDFLAGS"
|
||||
cross_cc_s390=$cc
|
||||
cross_cc_cflags_s390=$CPU_CFLAGS
|
||||
;;
|
||||
s390x)
|
||||
CPU_CFLAGS="-m64"
|
||||
LDFLAGS="-m64 $LDFLAGS"
|
||||
cross_cc_s390x=$cc
|
||||
cross_cc_cflags_s390x=$CPU_CFLAGS
|
||||
;;
|
||||
i386)
|
||||
CPU_CFLAGS="-m32"
|
||||
LDFLAGS="-m32 $LDFLAGS"
|
||||
cc_i386='$(CC) -m32'
|
||||
cross_cc_i386=$cc
|
||||
cross_cc_cflags_i386=$CPU_CFLAGS
|
||||
;;
|
||||
x86_64)
|
||||
# ??? Only extremely old AMD cpus do not have cmpxchg16b.
|
||||
|
@ -1434,12 +1476,14 @@ case "$cpu" in
|
|||
# runtime and generate the fallback to serial emulation.
|
||||
CPU_CFLAGS="-m64 -mcx16"
|
||||
LDFLAGS="-m64 $LDFLAGS"
|
||||
cc_i386='$(CC) -m32'
|
||||
cross_cc_x86_64=$cc
|
||||
cross_cc_cflags_x86_64=$CPU_CFLAGS
|
||||
;;
|
||||
x32)
|
||||
CPU_CFLAGS="-mx32"
|
||||
LDFLAGS="-mx32 $LDFLAGS"
|
||||
cc_i386='$(CC) -m32'
|
||||
cross_cc_i386=$cc
|
||||
cross_cc_cflags_i386=$CPU_CFLAGS
|
||||
;;
|
||||
# No special flags required for other host CPUs
|
||||
esac
|
||||
|
@ -1501,6 +1545,8 @@ Advanced options (experts only):
|
|||
--extra-cflags=CFLAGS append extra C compiler flags QEMU_CFLAGS
|
||||
--extra-cxxflags=CXXFLAGS append extra C++ compiler flags QEMU_CXXFLAGS
|
||||
--extra-ldflags=LDFLAGS append extra linker flags LDFLAGS
|
||||
--cross-cc-ARCH=CC use compiler when building ARCH guest test cases
|
||||
--cross-cc-flags-ARCH= use compiler flags when building ARCH guest tests
|
||||
--make=MAKE use specified make [$make]
|
||||
--install=INSTALL use specified install [$install]
|
||||
--python=PYTHON use specified python [$python]
|
||||
|
@ -6702,7 +6748,6 @@ echo "CC=$cc" >> $config_host_mak
|
|||
if $iasl -h > /dev/null 2>&1; then
|
||||
echo "IASL=$iasl" >> $config_host_mak
|
||||
fi
|
||||
echo "CC_I386=$cc_i386" >> $config_host_mak
|
||||
echo "HOST_CC=$host_cc" >> $config_host_mak
|
||||
echo "CXX=$cxx" >> $config_host_mak
|
||||
echo "OBJCC=$objcc" >> $config_host_mak
|
||||
|
@ -6821,6 +6866,10 @@ case "$target" in
|
|||
;;
|
||||
esac
|
||||
|
||||
target_compiler=""
|
||||
target_compiler_static=""
|
||||
target_compiler_cflags=""
|
||||
|
||||
mkdir -p $target_dir
|
||||
echo "# Automatically generated by configure - do not modify" > $config_target_mak
|
||||
|
||||
|
@ -6836,19 +6885,25 @@ TARGET_ABI_DIR=""
|
|||
case "$target_name" in
|
||||
i386)
|
||||
gdb_xml_files="i386-32bit.xml i386-32bit-core.xml i386-32bit-sse.xml"
|
||||
target_compiler=$cross_cc_i386
|
||||
target_compiler_cflags=$cross_cc_ccflags_i386
|
||||
;;
|
||||
x86_64)
|
||||
TARGET_BASE_ARCH=i386
|
||||
gdb_xml_files="i386-64bit.xml i386-64bit-core.xml i386-64bit-sse.xml"
|
||||
target_compiler=$cross_cc_x86_64
|
||||
;;
|
||||
alpha)
|
||||
mttcg="yes"
|
||||
target_compiler=$cross_cc_alpha
|
||||
;;
|
||||
arm|armeb)
|
||||
TARGET_ARCH=arm
|
||||
bflt="yes"
|
||||
mttcg="yes"
|
||||
gdb_xml_files="arm-core.xml arm-vfp.xml arm-vfp3.xml arm-neon.xml"
|
||||
target_compiler=$cross_cc_arm
|
||||
eval "target_compiler_cflags=\$cross_cc_cflags_${target_name}"
|
||||
;;
|
||||
aarch64|aarch64_be)
|
||||
TARGET_ARCH=aarch64
|
||||
|
@ -6856,59 +6911,75 @@ case "$target_name" in
|
|||
bflt="yes"
|
||||
mttcg="yes"
|
||||
gdb_xml_files="aarch64-core.xml aarch64-fpu.xml arm-core.xml arm-vfp.xml arm-vfp3.xml arm-neon.xml"
|
||||
target_compiler=$cross_cc_aarch64
|
||||
eval "target_compiler_cflags=\$cross_cc_cflags_${target_name}"
|
||||
;;
|
||||
cris)
|
||||
target_compiler=$cross_cc_cris
|
||||
;;
|
||||
hppa)
|
||||
mttcg="yes"
|
||||
target_compiler=$cross_cc_hppa
|
||||
;;
|
||||
lm32)
|
||||
target_compiler=$cross_cc_lm32
|
||||
;;
|
||||
m68k)
|
||||
bflt="yes"
|
||||
gdb_xml_files="cf-core.xml cf-fp.xml m68k-fp.xml"
|
||||
target_compiler=$cross_cc_m68k
|
||||
;;
|
||||
microblaze|microblazeel)
|
||||
TARGET_ARCH=microblaze
|
||||
bflt="yes"
|
||||
echo "TARGET_ABI32=y" >> $config_target_mak
|
||||
target_compiler=$cross_cc_microblaze
|
||||
;;
|
||||
mips|mipsel)
|
||||
TARGET_ARCH=mips
|
||||
target_compiler=$cross_cc_mips
|
||||
echo "TARGET_ABI_MIPSO32=y" >> $config_target_mak
|
||||
;;
|
||||
mipsn32|mipsn32el)
|
||||
TARGET_ARCH=mips64
|
||||
TARGET_BASE_ARCH=mips
|
||||
target_compiler=$cross_cc_mipsn32
|
||||
echo "TARGET_ABI_MIPSN32=y" >> $config_target_mak
|
||||
echo "TARGET_ABI32=y" >> $config_target_mak
|
||||
;;
|
||||
mips64|mips64el)
|
||||
TARGET_ARCH=mips64
|
||||
TARGET_BASE_ARCH=mips
|
||||
target_compiler=$cross_cc_mips64
|
||||
echo "TARGET_ABI_MIPSN64=y" >> $config_target_mak
|
||||
;;
|
||||
moxie)
|
||||
target_compiler=$cross_cc_moxie
|
||||
;;
|
||||
nios2)
|
||||
target_compiler=$cross_cc_nios2
|
||||
;;
|
||||
or1k)
|
||||
target_compiler=$cross_cc_or1k
|
||||
TARGET_ARCH=openrisc
|
||||
TARGET_BASE_ARCH=openrisc
|
||||
;;
|
||||
ppc)
|
||||
gdb_xml_files="power-core.xml power-fpu.xml power-altivec.xml power-spe.xml"
|
||||
target_compiler=$cross_cc_powerpc
|
||||
;;
|
||||
ppcemb)
|
||||
TARGET_BASE_ARCH=ppc
|
||||
TARGET_ABI_DIR=ppc
|
||||
gdb_xml_files="power-core.xml power-fpu.xml power-altivec.xml power-spe.xml"
|
||||
target_compiler=$cross_cc_ppcemb
|
||||
;;
|
||||
ppc64)
|
||||
TARGET_BASE_ARCH=ppc
|
||||
TARGET_ABI_DIR=ppc
|
||||
mttcg=yes
|
||||
gdb_xml_files="power64-core.xml power-fpu.xml power-altivec.xml power-spe.xml power-vsx.xml"
|
||||
target_compiler=$cross_cc_ppc64
|
||||
;;
|
||||
ppc64le)
|
||||
TARGET_ARCH=ppc64
|
||||
|
@ -6916,6 +6987,7 @@ case "$target_name" in
|
|||
TARGET_ABI_DIR=ppc
|
||||
mttcg=yes
|
||||
gdb_xml_files="power64-core.xml power-fpu.xml power-altivec.xml power-spe.xml power-vsx.xml"
|
||||
target_compiler=$cross_cc_ppc64le
|
||||
;;
|
||||
ppc64abi32)
|
||||
TARGET_ARCH=ppc64
|
||||
|
@ -6923,45 +6995,57 @@ case "$target_name" in
|
|||
TARGET_ABI_DIR=ppc
|
||||
echo "TARGET_ABI32=y" >> $config_target_mak
|
||||
gdb_xml_files="power64-core.xml power-fpu.xml power-altivec.xml power-spe.xml power-vsx.xml"
|
||||
target_compiler=$cross_cc_ppc64abi32
|
||||
;;
|
||||
riscv32)
|
||||
TARGET_BASE_ARCH=riscv
|
||||
TARGET_ABI_DIR=riscv
|
||||
mttcg=yes
|
||||
target_compiler=$cross_cc_riscv32
|
||||
;;
|
||||
riscv64)
|
||||
TARGET_BASE_ARCH=riscv
|
||||
TARGET_ABI_DIR=riscv
|
||||
mttcg=yes
|
||||
target_compiler=$cross_cc_riscv64
|
||||
;;
|
||||
sh4|sh4eb)
|
||||
TARGET_ARCH=sh4
|
||||
bflt="yes"
|
||||
target_compiler=$cross_cc_sh4
|
||||
;;
|
||||
sparc)
|
||||
target_compiler=$cross_cc_sparc
|
||||
;;
|
||||
sparc64)
|
||||
TARGET_BASE_ARCH=sparc
|
||||
target_compiler=$cross_cc_sparc64
|
||||
;;
|
||||
sparc32plus)
|
||||
TARGET_ARCH=sparc64
|
||||
TARGET_BASE_ARCH=sparc
|
||||
TARGET_ABI_DIR=sparc
|
||||
target_compiler=$cross_cc_sparc32plus
|
||||
echo "TARGET_ABI32=y" >> $config_target_mak
|
||||
;;
|
||||
s390x)
|
||||
mttcg=yes
|
||||
gdb_xml_files="s390x-core64.xml s390-acr.xml s390-fpr.xml s390-vx.xml s390-cr.xml s390-virt.xml s390-gs.xml"
|
||||
target_compiler=$cross_cc_s390x
|
||||
;;
|
||||
tilegx)
|
||||
target_compiler=$cross_cc_tilegx
|
||||
;;
|
||||
tricore)
|
||||
target_compiler=$cross_cc_tricore
|
||||
;;
|
||||
unicore32)
|
||||
target_compiler=$cross_cc_unicore32
|
||||
;;
|
||||
xtensa|xtensaeb)
|
||||
TARGET_ARCH=xtensa
|
||||
mttcg="yes"
|
||||
target_compiler=$cross_cc_xtensa
|
||||
;;
|
||||
*)
|
||||
error_exit "Unsupported target CPU"
|
||||
|
@ -6972,6 +7056,27 @@ if [ "$TARGET_BASE_ARCH" = "" ]; then
|
|||
TARGET_BASE_ARCH=$TARGET_ARCH
|
||||
fi
|
||||
|
||||
# Do we have a cross compiler for this target?
|
||||
if has $target_compiler; then
|
||||
|
||||
write_c_skeleton
|
||||
|
||||
if ! do_compiler "$target_compiler" $target_compiler_cflags -o $TMPE $TMPC -static ; then
|
||||
# For host systems we might get away with building without -static
|
||||
if ! do_compiler "$target_compiler" $target_compiler_cflags -o $TMPE $TMPC ; then
|
||||
target_compiler=""
|
||||
else
|
||||
enabled_cross_compilers="${enabled_cross_compilers} '${target_compiler}'"
|
||||
target_compiler_static="n"
|
||||
fi
|
||||
else
|
||||
enabled_cross_compilers="${enabled_cross_compilers} '${target_compiler}'"
|
||||
target_compiler_static="y"
|
||||
fi
|
||||
else
|
||||
target_compiler=""
|
||||
fi
|
||||
|
||||
symlink "$source_path/Makefile.target" "$target_dir/Makefile"
|
||||
|
||||
upper() {
|
||||
|
@ -7045,6 +7150,19 @@ if test "$target_bsd_user" = "yes" ; then
|
|||
echo "CONFIG_BSD_USER=y" >> $config_target_mak
|
||||
fi
|
||||
|
||||
if test -n "$target_compiler"; then
|
||||
echo "CROSS_CC_GUEST=\"$target_compiler\"" >> $config_target_mak
|
||||
|
||||
if test -n "$target_compiler_static"; then
|
||||
echo "CROSS_CC_GUEST_STATIC=$target_compiler_static" >> $config_target_mak
|
||||
fi
|
||||
|
||||
if test -n "$target_compiler_cflags"; then
|
||||
echo "CROSS_CC_GUEST_CFLAGS=$target_compiler_cflags" >> $config_target_mak
|
||||
fi
|
||||
fi
|
||||
|
||||
|
||||
# generate QEMU_CFLAGS/LDFLAGS for targets
|
||||
|
||||
cflags=""
|
||||
|
@ -7167,6 +7285,11 @@ echo "QEMU_CFLAGS+=$cflags" >> $config_target_mak
|
|||
|
||||
done # for target in $targets
|
||||
|
||||
if test -n "$enabled_cross_compilers"; then
|
||||
echo
|
||||
echo "NOTE: cross-compilers enabled: $enabled_cross_compilers"
|
||||
fi
|
||||
|
||||
if [ "$fdt" = "git" ]; then
|
||||
echo "config-host.h: subdir-dtc" >> $config_host_mak
|
||||
fi
|
||||
|
|
|
@ -10,6 +10,7 @@ check-help:
|
|||
@echo " $(MAKE) check-speed Run qobject speed tests"
|
||||
@echo " $(MAKE) check-qapi-schema Run QAPI schema tests"
|
||||
@echo " $(MAKE) check-block Run block tests"
|
||||
@echo " $(MAKE) check-tcg Run TCG tests"
|
||||
@echo " $(MAKE) check-report.html Generates an HTML test report"
|
||||
@echo " $(MAKE) check-clean Clean the tests"
|
||||
@echo
|
||||
|
@ -930,6 +931,42 @@ check-report.xml: $(patsubst %,check-report-qtest-%.xml, $(QTEST_TARGETS)) check
|
|||
check-report.html: check-report.xml
|
||||
$(call quiet-command,gtester-report $< > $@,"GEN","$@")
|
||||
|
||||
# Per guest TCG tests
|
||||
|
||||
LINUX_USER_TARGETS=$(filter %-linux-user,$(TARGET_LIST))
|
||||
BUILD_TCG_TARGET_RULES=$(patsubst %,build-tcg-tests-%, $(LINUX_USER_TARGETS))
|
||||
CLEAN_TCG_TARGET_RULES=$(patsubst %,clean-tcg-tests-%, $(LINUX_USER_TARGETS))
|
||||
RUN_TCG_TARGET_RULES=$(patsubst %,run-tcg-tests-%, $(LINUX_USER_TARGETS))
|
||||
|
||||
ifeq ($(HAVE_USER_DOCKER),y)
|
||||
# Probe for the Docker Builds needed for each build
|
||||
$(foreach PROBE_TARGET,$(TARGET_LIST), \
|
||||
$(eval -include $(SRC_PATH)/tests/tcg/Makefile.probe) \
|
||||
$(if $(DOCKER_PREREQ), \
|
||||
$(eval build-tcg-tests-$(PROBE_TARGET): $(DOCKER_PREREQ))))
|
||||
endif
|
||||
|
||||
build-tcg-tests-%:
|
||||
$(call quiet-command,$(MAKE) $(SUBDIR_MAKEFLAGS) -C $* V="$(V)" \
|
||||
SKIP_DOCKER_BUILD=1 TARGET_DIR="$*/" guest-tests, \
|
||||
"BUILD", "TCG tests for $*")
|
||||
|
||||
run-tcg-tests-%: % build-tcg-tests-%
|
||||
$(call quiet-command,$(MAKE) $(SUBDIR_MAKEFLAGS) -C $* V="$(V)" \
|
||||
SKIP_DOCKER_BUILD=1 TARGET_DIR="$*/" run-guest-tests, \
|
||||
"RUN", "TCG tests for $*")
|
||||
|
||||
clean-tcg-tests-%:
|
||||
$(call quiet-command,$(MAKE) $(SUBDIR_MAKEFLAGS) -C $* V="$(V)" TARGET_DIR="$*/" clean-guest-tests,)
|
||||
|
||||
.PHONY: build-tcg
|
||||
build-tcg: $(BUILD_TCG_TARGET_RULES)
|
||||
|
||||
.PHONY: check-tcg
|
||||
check-tcg: $(RUN_TCG_TARGET_RULES)
|
||||
|
||||
.PHONY: clean-tcg
|
||||
clean-tcg: $(CLEAN_TCG_TARGET_RULES)
|
||||
|
||||
# Other tests
|
||||
|
||||
|
@ -972,7 +1009,6 @@ check-speed: $(patsubst %,check-%, $(check-speed-y))
|
|||
check-block: $(patsubst %,check-%, $(check-block-y))
|
||||
check: check-qapi-schema check-unit check-qtest check-decodetree
|
||||
check-clean:
|
||||
$(MAKE) -C tests/tcg clean
|
||||
rm -rf $(check-unit-y) tests/*.o $(QEMU_IOTESTS_HELPERS-y)
|
||||
rm -rf $(sort $(foreach target,$(SYSEMU_TARGET_LIST), $(check-qtest-$(target)-y)) $(check-qtest-generic-y))
|
||||
rm -f tests/test-qapi-gen-timestamp
|
||||
|
|
|
@ -15,6 +15,8 @@ DOCKER_TESTS := $(notdir $(shell \
|
|||
|
||||
DOCKER_TOOLS := travis
|
||||
|
||||
DOCKER_SCRIPT=$(SRC_PATH)/tests/docker/docker.py
|
||||
|
||||
TESTS ?= %
|
||||
IMAGES ?= %
|
||||
|
||||
|
@ -32,20 +34,27 @@ docker-qemu-src: $(DOCKER_SRC_COPY)
|
|||
|
||||
docker-image: ${DOCKER_TARGETS}
|
||||
|
||||
# General rule for building docker images
|
||||
# General rule for building docker images. If we are a sub-make
|
||||
# invoked with SKIP_DOCKER_BUILD we still check the image is upto date
|
||||
# though
|
||||
ifdef SKIP_DOCKER_BUILD
|
||||
docker-image-%: $(DOCKER_FILES_DIR)/%.docker
|
||||
$(call quiet-command, \
|
||||
$(DOCKER_SCRIPT) check --quiet qemu:$* $<, \
|
||||
"CHECK", "$*")
|
||||
else
|
||||
docker-image-%: $(DOCKER_FILES_DIR)/%.docker
|
||||
@if test "$@" = docker-image-debian-bootstrap -a -z "$(EXECUTABLE)"; then \
|
||||
echo WARNING: EXECUTABLE is not set, debootstrap may fail. 2>&1 ; \
|
||||
fi
|
||||
$(call quiet-command,\
|
||||
$(SRC_PATH)/tests/docker/docker.py build qemu:$* $< \
|
||||
$(DOCKER_SCRIPT) build qemu:$* $< \
|
||||
$(if $V,,--quiet) $(if $(NOCACHE),--no-cache) \
|
||||
$(if $(NOUSER),,--add-current-user) \
|
||||
$(if $(EXTRA_FILES),--extra-files $(EXTRA_FILES))\
|
||||
$(if $(EXECUTABLE),--include-executable=$(EXECUTABLE)),\
|
||||
"BUILD","$*")
|
||||
|
||||
docker-image-debian-powerpc-cross: EXTRA_FILES:=$(SRC_PATH)/tests/docker/dockerfiles/debian-apt-fake.sh
|
||||
endif
|
||||
|
||||
# Enforce dependencies for composite images
|
||||
docker-image-debian: docker-image-debian9
|
||||
|
@ -55,12 +64,34 @@ docker-image-debian-armel-cross: docker-image-debian9
|
|||
docker-image-debian-armhf-cross: docker-image-debian9
|
||||
docker-image-debian-arm64-cross: docker-image-debian9
|
||||
docker-image-debian-mips-cross: docker-image-debian9
|
||||
docker-image-debian-mipsel-cross: docker-image-debian9
|
||||
docker-image-debian-mips64el-cross: docker-image-debian9
|
||||
docker-image-debian-powerpc-cross: docker-image-debian8
|
||||
docker-image-debian-ppc64el-cross: docker-image-debian9
|
||||
docker-image-debian-s390x-cross: docker-image-debian9
|
||||
docker-image-debian-win32-cross: docker-image-debian8-mxe
|
||||
docker-image-debian-win64-cross: docker-image-debian8-mxe
|
||||
|
||||
# Debian SID images - we are tracking a rolling distro so we want to
|
||||
# force a re-build of the base image if we ever need to build one of
|
||||
# its children.
|
||||
ifndef SKIP_DOCKER_BUILD
|
||||
ifeq ($(HAVE_USER_DOCKER),y)
|
||||
SID_AGE=$(shell $(DOCKER_SCRIPT) check --checktype=age --olderthan=180 --quiet qemu:debian-sid)
|
||||
ifeq ($(SID_AGE),)
|
||||
else
|
||||
docker-image-debian-sid: NOCACHE=1
|
||||
endif
|
||||
endif
|
||||
endif
|
||||
|
||||
docker-image-debian-alpha-cross: docker-image-debian-sid
|
||||
docker-image-debian-hppa-cross: docker-image-debian-sid
|
||||
docker-image-debian-m68k-cross: docker-image-debian-sid
|
||||
docker-image-debian-sh4-cross: docker-image-debian-sid
|
||||
docker-image-debian-sparc64-cross: docker-image-debian-sid
|
||||
docker-image-debian-mips64-cross: docker-image-debian-sid
|
||||
docker-image-debian-riscv64-cross: docker-image-debian-sid
|
||||
docker-image-debian-powerpc-cross: docker-image-debian-sid
|
||||
docker-image-travis: NOUSER=1
|
||||
|
||||
# Specialist build images, sometimes very limited tools
|
||||
|
@ -133,11 +164,11 @@ docker-run: docker-qemu-src
|
|||
fi
|
||||
$(if $(EXECUTABLE), \
|
||||
$(call quiet-command, \
|
||||
$(SRC_PATH)/tests/docker/docker.py update \
|
||||
$(DOCKER_SCRIPT) update \
|
||||
$(IMAGE) $(EXECUTABLE), \
|
||||
" COPYING $(EXECUTABLE) to $(IMAGE)"))
|
||||
$(call quiet-command, \
|
||||
$(SRC_PATH)/tests/docker/docker.py run \
|
||||
$(DOCKER_SCRIPT) run \
|
||||
$(if $(NOUSER),,-u $(shell id -u)) \
|
||||
--security-opt seccomp=unconfined \
|
||||
$(if $V,,--rm) \
|
||||
|
@ -167,4 +198,4 @@ docker-run-%:
|
|||
@$(MAKE) docker-run TEST=$(CMD) IMAGE=qemu:$(IMAGE)
|
||||
|
||||
docker-clean:
|
||||
$(call quiet-command, $(SRC_PATH)/tests/docker/docker.py clean)
|
||||
$(call quiet-command, $(DOCKER_SCRIPT) clean)
|
||||
|
|
|
@ -26,9 +26,13 @@ import tempfile
|
|||
import re
|
||||
import signal
|
||||
from tarfile import TarFile, TarInfo
|
||||
try:
|
||||
from StringIO import StringIO
|
||||
except ImportError:
|
||||
from io import StringIO
|
||||
from shutil import copy, rmtree
|
||||
from pwd import getpwuid
|
||||
from datetime import datetime,timedelta
|
||||
|
||||
|
||||
FILTERED_ENV_NAMES = ['ftp_proxy', 'http_proxy', 'https_proxy']
|
||||
|
@ -49,7 +53,9 @@ def _guess_docker_command():
|
|||
commands = [["docker"], ["sudo", "-n", "docker"]]
|
||||
for cmd in commands:
|
||||
try:
|
||||
if subprocess.call(cmd + ["images"],
|
||||
# docker version will return the client details in stdout
|
||||
# but still report a status of 1 if it can't contact the daemon
|
||||
if subprocess.call(cmd + ["version"],
|
||||
stdout=DEVNULL, stderr=DEVNULL) == 0:
|
||||
return cmd
|
||||
except OSError:
|
||||
|
@ -179,8 +185,17 @@ class Docker(object):
|
|||
stderr=subprocess.STDOUT,
|
||||
**kwargs)
|
||||
|
||||
def inspect_tag(self, tag):
|
||||
try:
|
||||
return self._output(["inspect", tag])
|
||||
except subprocess.CalledProcessError:
|
||||
return None
|
||||
|
||||
def get_image_creation_time(self, info):
|
||||
return json.loads(info)[0]["Created"]
|
||||
|
||||
def get_image_dockerfile_checksum(self, tag):
|
||||
resp = self._output(["inspect", tag])
|
||||
resp = self.inspect_tag(tag)
|
||||
labels = json.loads(resp)[0]["Config"].get("Labels", {})
|
||||
return labels.get("com.qemu.dockerfile-checksum", "")
|
||||
|
||||
|
@ -201,8 +216,10 @@ class Docker(object):
|
|||
|
||||
tmp_df.write("\n")
|
||||
tmp_df.write("LABEL com.qemu.dockerfile-checksum=%s" %
|
||||
_text_checksum("\n".join([dockerfile] +
|
||||
extra_files_cksum)))
|
||||
_text_checksum(_dockerfile_preprocess(dockerfile)))
|
||||
for f, c in extra_files_cksum:
|
||||
tmp_df.write("LABEL com.qemu.%s-checksum=%s" % (f, c))
|
||||
|
||||
tmp_df.flush()
|
||||
|
||||
self._do_check(["build", "-t", tag, "-f", tmp_df.name] + argv + \
|
||||
|
@ -317,7 +334,7 @@ class BuildCommand(SubCommand):
|
|||
_copy_binary_with_libs(args.include_executable, docker_dir)
|
||||
for filename in args.extra_files or []:
|
||||
_copy_with_mkdir(filename, docker_dir)
|
||||
cksum += [_file_checksum(filename)]
|
||||
cksum += [(filename, _file_checksum(filename))]
|
||||
|
||||
argv += ["--build-arg=" + k.lower() + "=" + v
|
||||
for k, v in os.environ.iteritems()
|
||||
|
@ -409,6 +426,89 @@ class ProbeCommand(SubCommand):
|
|||
return
|
||||
|
||||
|
||||
class CcCommand(SubCommand):
|
||||
"""Compile sources with cc in images"""
|
||||
name = "cc"
|
||||
|
||||
def args(self, parser):
|
||||
parser.add_argument("--image", "-i", required=True,
|
||||
help="The docker image in which to run cc")
|
||||
parser.add_argument("--cc", default="cc",
|
||||
help="The compiler executable to call")
|
||||
parser.add_argument("--user",
|
||||
help="The user-id to run under")
|
||||
parser.add_argument("--source-path", "-s", nargs="*", dest="paths",
|
||||
help="""Extra paths to (ro) mount into container for
|
||||
reading sources""")
|
||||
|
||||
def run(self, args, argv):
|
||||
if argv and argv[0] == "--":
|
||||
argv = argv[1:]
|
||||
cwd = os.getcwd()
|
||||
cmd = ["--rm", "-w", cwd,
|
||||
"-v", "%s:%s:rw" % (cwd, cwd)]
|
||||
if args.paths:
|
||||
for p in args.paths:
|
||||
cmd += ["-v", "%s:%s:ro,z" % (p, p)]
|
||||
if args.user:
|
||||
cmd += ["-u", args.user]
|
||||
cmd += [args.image, args.cc]
|
||||
cmd += argv
|
||||
return Docker().command("run", cmd, args.quiet)
|
||||
|
||||
|
||||
class CheckCommand(SubCommand):
|
||||
"""Check if we need to re-build a docker image out of a dockerfile.
|
||||
Arguments: <tag> <dockerfile>"""
|
||||
name = "check"
|
||||
|
||||
def args(self, parser):
|
||||
parser.add_argument("tag",
|
||||
help="Image Tag")
|
||||
parser.add_argument("dockerfile", default=None,
|
||||
help="Dockerfile name", nargs='?')
|
||||
parser.add_argument("--checktype", choices=["checksum", "age"],
|
||||
default="checksum", help="check type")
|
||||
parser.add_argument("--olderthan", default=60, type=int,
|
||||
help="number of minutes")
|
||||
|
||||
def run(self, args, argv):
|
||||
tag = args.tag
|
||||
|
||||
dkr = Docker()
|
||||
info = dkr.inspect_tag(tag)
|
||||
if info is None:
|
||||
print("Image does not exist")
|
||||
return 1
|
||||
|
||||
if args.checktype == "checksum":
|
||||
if not args.dockerfile:
|
||||
print("Need a dockerfile for tag:%s" % (tag))
|
||||
return 1
|
||||
|
||||
dockerfile = open(args.dockerfile, "rb").read()
|
||||
|
||||
if dkr.image_matches_dockerfile(tag, dockerfile):
|
||||
if not args.quiet:
|
||||
print("Image is up to date")
|
||||
return 0
|
||||
else:
|
||||
print("Image needs updating")
|
||||
return 1
|
||||
elif args.checktype == "age":
|
||||
timestr = dkr.get_image_creation_time(info).split(".")[0]
|
||||
created = datetime.strptime(timestr, "%Y-%m-%dT%H:%M:%S")
|
||||
past = datetime.now() - timedelta(minutes=args.olderthan)
|
||||
if created < past:
|
||||
print ("Image created @ %s more than %d minutes old" %
|
||||
(timestr, args.olderthan))
|
||||
return 1
|
||||
else:
|
||||
if not args.quiet:
|
||||
print ("Image less than %d minutes old" % (args.olderthan))
|
||||
return 0
|
||||
|
||||
|
||||
def main():
|
||||
parser = argparse.ArgumentParser(description="A Docker helper",
|
||||
usage="%s <subcommand> ..." % os.path.basename(sys.argv[0]))
|
||||
|
|
12
tests/docker/dockerfiles/debian-alpha-cross.docker
Normal file
12
tests/docker/dockerfiles/debian-alpha-cross.docker
Normal file
|
@ -0,0 +1,12 @@
|
|||
#
|
||||
# Docker cross-compiler target
|
||||
#
|
||||
# This docker target builds on the debian sid base image which
|
||||
# contains cross compilers for Debian "ports" targets.
|
||||
#
|
||||
FROM qemu:debian-sid
|
||||
|
||||
RUN DEBIAN_FRONTEND=noninteractive eatmydata \
|
||||
apt-get install -y --no-install-recommends \
|
||||
gcc-alpha-linux-gnu \
|
||||
libc6.1-dev-alpha-cross || { echo "Failed to build - see debian-sid.docker notes"; exit 1; }
|
|
@ -1,46 +0,0 @@
|
|||
#! /bin/sh
|
||||
#
|
||||
# Generate fake debian package to resolve unimportant unmet dependencies held
|
||||
# by upstream multiarch broken packages.
|
||||
#
|
||||
# Copyright (c) 2017 Philippe Mathieu-Daudé <f4bug@amsat.org>
|
||||
#
|
||||
# This work is licensed under the terms of the GNU GPL, version 2
|
||||
# or (at your option) any later version. See the COPYING file in
|
||||
# the top-level directory.
|
||||
|
||||
test $1 = "install" && shift 1
|
||||
|
||||
fake_install()
|
||||
{
|
||||
echo "Generating fake $2 $1 $3 ..."
|
||||
(cd /var/cache/apt/archives
|
||||
(cat << 'EOF'
|
||||
Section: misc
|
||||
Priority: optional
|
||||
Standards-Version: 3.9.2
|
||||
|
||||
Package: NAME
|
||||
Version: VERSION
|
||||
Maintainer: qemu-devel@nongnu.org
|
||||
Architecture: any
|
||||
Multi-Arch: same
|
||||
Description: fake NAME
|
||||
EOF
|
||||
) | sed s/NAME/$2/g | sed s/VERSION/$3/g > $2.control
|
||||
equivs-build -a $1 $2.control 1>/dev/null 2>/dev/null
|
||||
dpkg -i --force-overwrite $2_$3_$1.deb
|
||||
)
|
||||
}
|
||||
|
||||
try_install()
|
||||
{
|
||||
name=$(echo $1|sed "s/\(.*\):\(.*\)=\(.*\)/\1/")
|
||||
arch=$(echo $1|sed "s/\(.*\):\(.*\)=\(.*\)/\2/")
|
||||
vers=$(echo $1|sed "s/\(.*\):\(.*\)=\(.*\)/\3/")
|
||||
apt-get install -q -yy $1 || fake_install $arch $name $vers
|
||||
}
|
||||
|
||||
for package in $*; do
|
||||
try_install $package
|
||||
done
|
12
tests/docker/dockerfiles/debian-hppa-cross.docker
Normal file
12
tests/docker/dockerfiles/debian-hppa-cross.docker
Normal file
|
@ -0,0 +1,12 @@
|
|||
#
|
||||
# Docker cross-compiler target
|
||||
#
|
||||
# This docker target builds on the debian sid base image which
|
||||
# contains cross compilers for Debian "ports" targets.
|
||||
#
|
||||
FROM qemu:debian-sid
|
||||
|
||||
RUN DEBIAN_FRONTEND=noninteractive eatmydata \
|
||||
apt-get install -y --no-install-recommends \
|
||||
gcc-hppa-linux-gnu \
|
||||
libc6-dev-hppa-cross
|
12
tests/docker/dockerfiles/debian-m68k-cross.docker
Normal file
12
tests/docker/dockerfiles/debian-m68k-cross.docker
Normal file
|
@ -0,0 +1,12 @@
|
|||
#
|
||||
# Docker cross-compiler target
|
||||
#
|
||||
# This docker target builds on the debian sid base image which
|
||||
# contains cross compilers for Debian "ports" targets.
|
||||
#
|
||||
FROM qemu:debian-sid
|
||||
|
||||
RUN DEBIAN_FRONTEND=noninteractive eatmydata \
|
||||
apt-get install -y --no-install-recommends \
|
||||
gcc-m68k-linux-gnu \
|
||||
libc6-dev-m68k-cross
|
12
tests/docker/dockerfiles/debian-mips64-cross.docker
Normal file
12
tests/docker/dockerfiles/debian-mips64-cross.docker
Normal file
|
@ -0,0 +1,12 @@
|
|||
#
|
||||
# Docker cross-compiler target
|
||||
#
|
||||
# This docker target builds on the debian sid base image which
|
||||
# contains cross compilers for Debian "ports" targets.
|
||||
#
|
||||
FROM qemu:debian-sid
|
||||
|
||||
RUN DEBIAN_FRONTEND=noninteractive eatmydata \
|
||||
apt-get install -y --no-install-recommends \
|
||||
gcc-mips64-linux-gnuabi64 \
|
||||
libc6-dev-mips64-cross
|
|
@ -1,40 +1,13 @@
|
|||
#
|
||||
# Docker powerpc cross-compiler target
|
||||
#
|
||||
# This docker target builds on the debian Jessie base image.
|
||||
# This docker target builds on the debian sid base image which
|
||||
# contains cross compilers for Debian "ports" targets. The original
|
||||
# Jessie based no longer builds.
|
||||
#
|
||||
FROM qemu:debian8
|
||||
MAINTAINER Philippe Mathieu-Daudé <f4bug@amsat.org>
|
||||
|
||||
# Add the foreign architecture we want and install dependencies
|
||||
RUN dpkg --add-architecture powerpc
|
||||
RUN apt-get update
|
||||
RUN DEBIAN_FRONTEND=noninteractive eatmydata \
|
||||
apt-get install -y --no-install-recommends \
|
||||
crossbuild-essential-powerpc
|
||||
|
||||
# <kludge> to fix "following packages have unmet dependencies" ...
|
||||
ADD debian-apt-fake.sh /usr/local/bin/apt-fake
|
||||
RUN apt-get install -y --no-install-recommends \
|
||||
equivs \
|
||||
pkg-config
|
||||
RUN apt-fake install \
|
||||
pkg-config:powerpc=0.28-1.1-fake && \
|
||||
ln -s pkg-config /usr/bin/powerpc-linux-gnu-pkg-config
|
||||
ENV PKG_CONFIG_PATH /usr/lib/powerpc-linux-gnu/pkgconfig
|
||||
# </kludge>
|
||||
|
||||
# Specify the cross prefix for this image (see tests/docker/common.rc)
|
||||
ENV QEMU_CONFIGURE_OPTS --cross-prefix=powerpc-linux-gnu-
|
||||
FROM qemu:debian-sid
|
||||
|
||||
RUN DEBIAN_FRONTEND=noninteractive eatmydata \
|
||||
apt-get build-dep -yy -a powerpc qemu
|
||||
RUN DEBIAN_FRONTEND=noninteractive \
|
||||
apt-get install -y --no-install-recommends \
|
||||
glusterfs-common:powerpc \
|
||||
libbz2-dev:powerpc \
|
||||
liblzo2-dev:powerpc \
|
||||
libncursesw5-dev:powerpc \
|
||||
libnfs-dev:powerpc \
|
||||
librdmacm-dev:powerpc \
|
||||
libsnappy-dev:powerpc
|
||||
gcc-powerpc-linux-gnu \
|
||||
libc6-dev-powerpc-cross || { echo "Failed to build - see debian-sid.docker notes"; exit 1; }
|
||||
|
|
12
tests/docker/dockerfiles/debian-riscv64-cross.docker
Normal file
12
tests/docker/dockerfiles/debian-riscv64-cross.docker
Normal file
|
@ -0,0 +1,12 @@
|
|||
#
|
||||
# Docker cross-compiler target
|
||||
#
|
||||
# This docker target builds on the debian sid base image which
|
||||
# contains cross compilers for Debian "ports" targets.
|
||||
#
|
||||
FROM qemu:debian-sid
|
||||
|
||||
RUN DEBIAN_FRONTEND=noninteractive eatmydata \
|
||||
apt-get install -y --no-install-recommends \
|
||||
gcc-riscv64-linux-gnu \
|
||||
libc6-dev-riscv64-cross
|
12
tests/docker/dockerfiles/debian-sh4-cross.docker
Normal file
12
tests/docker/dockerfiles/debian-sh4-cross.docker
Normal file
|
@ -0,0 +1,12 @@
|
|||
#
|
||||
# Docker cross-compiler target
|
||||
#
|
||||
# This docker target builds on the debian sid base image which
|
||||
# contains cross compilers for Debian "ports" targets.
|
||||
#
|
||||
FROM qemu:debian-sid
|
||||
|
||||
RUN DEBIAN_FRONTEND=noninteractive eatmydata \
|
||||
apt-get install -y --no-install-recommends \
|
||||
gcc-sh4-linux-gnu \
|
||||
libc6-dev-sh4-cross
|
32
tests/docker/dockerfiles/debian-sid.docker
Normal file
32
tests/docker/dockerfiles/debian-sid.docker
Normal file
|
@ -0,0 +1,32 @@
|
|||
#
|
||||
# Debian Sid Base
|
||||
#
|
||||
# A number of our guests exist as ports only. We can either use the
|
||||
# ports repo or get everything from Sid. However Sid is a rolling
|
||||
# distro which may be broken at any particular time. If you are
|
||||
# unlucky and try and build your images while gcc is in the process of
|
||||
# being uploaded this can fail. Your only recourse is to try again in
|
||||
# a few hours when the repos have re-synced. Once built however you
|
||||
# won't be affected by repo changes unless the docker recipies are
|
||||
# updated and trigger a re-build.
|
||||
#
|
||||
|
||||
FROM debian:sid-slim
|
||||
|
||||
# Duplicate deb line as deb-src
|
||||
RUN cat /etc/apt/sources.list | sed "s/^deb\ /deb-src /" >> /etc/apt/sources.list
|
||||
|
||||
# Install common build utilities
|
||||
RUN apt update
|
||||
RUN DEBIAN_FRONTEND=noninteractive apt install -yy eatmydata
|
||||
RUN DEBIAN_FRONTEND=noninteractive eatmydata \
|
||||
apt install -y --no-install-recommends \
|
||||
bison \
|
||||
build-essential \
|
||||
ca-certificates \
|
||||
flex \
|
||||
git \
|
||||
pkg-config \
|
||||
psmisc \
|
||||
python \
|
||||
texinfo || { echo "Failed to build - see debian-sid.docker notes"; exit 1; }
|
12
tests/docker/dockerfiles/debian-sparc64-cross.docker
Normal file
12
tests/docker/dockerfiles/debian-sparc64-cross.docker
Normal file
|
@ -0,0 +1,12 @@
|
|||
#
|
||||
# Docker cross-compiler target
|
||||
#
|
||||
# This docker target builds on the debian sid base image which
|
||||
# contains cross compilers for Debian "ports" targets.
|
||||
#
|
||||
FROM qemu:debian-sid
|
||||
|
||||
RUN DEBIAN_FRONTEND=noninteractive eatmydata \
|
||||
apt-get install -y --no-install-recommends \
|
||||
gcc-sparc64-linux-gnu \
|
||||
libc6-dev-sparc64-cross
|
|
@ -32,6 +32,3 @@ RUN DEBIAN_FRONTEND=noninteractive eatmydata \
|
|||
pkg-config \
|
||||
python-minimal
|
||||
|
||||
# Setup Emdebian [emdebian-archive-keyring]
|
||||
RUN echo "deb http://emdebian.org/tools/debian/ jessie main" > /etc/apt/sources.list.d/emdebian.list && \
|
||||
curl http://emdebian.org/tools/debian/emdebian-toolchain-archive.key | apt-key add -
|
||||
|
|
|
@ -1,156 +1,101 @@
|
|||
# -*- Mode: makefile -*-
|
||||
#
|
||||
# TCG tests
|
||||
#
|
||||
# These are complicated by the fact we want to build them for guest
|
||||
# systems. This requires knowing what guests we are building and which
|
||||
# ones we have cross-compilers for or docker images with
|
||||
# cross-compilers.
|
||||
#
|
||||
# The tests themselves should be as minimal as possible as
|
||||
# cross-compilers don't always have a large amount of libraries
|
||||
# available.
|
||||
#
|
||||
# We only include the host build system for SRC_PATH and we don't
|
||||
# bother with the common rules.mk. We expect the following:
|
||||
#
|
||||
# CC - the C compiler command
|
||||
# EXTRA_CFLAGS - any extra CFLAGS
|
||||
# BUILD_STATIC - are we building static binaries
|
||||
#
|
||||
# By default all tests are statically compiled but some host systems
|
||||
# may not package static libraries by default. If an external
|
||||
# cross-compiler can only build dynamic libraries the user might need
|
||||
# to make extra efforts to ensure ld.so can link at runtime when the
|
||||
# tests are run.
|
||||
#
|
||||
# We also accept SPEED=slow to enable slower running tests
|
||||
#
|
||||
# We also expect to be in the tests build dir for the FOO-linux-user.
|
||||
#
|
||||
|
||||
-include ../../config-host.mak
|
||||
-include $(SRC_PATH)/rules.mak
|
||||
-include ../config-target.mak
|
||||
|
||||
$(call set-vpath, $(SRC_PATH)/tests/tcg)
|
||||
quiet-command = $(if $(V),$1,$(if $(2),@printf " %-7s %s\n" $2 $3 && $1, @$1))
|
||||
|
||||
QEMU=../../i386-linux-user/qemu-i386
|
||||
QEMU_X86_64=../../x86_64-linux-user/qemu-x86_64
|
||||
CC_X86_64=$(CC_I386) -m64
|
||||
# $1 = test name, $2 = cmd, $3 = desc
|
||||
run-test = $(call quiet-command, timeout $(TIMEOUT) $2 > $1.out,"TEST",$3)
|
||||
|
||||
QEMU_INCLUDES += -I../..
|
||||
CFLAGS=-Wall -O2 -g -fno-strict-aliasing
|
||||
#CFLAGS+=-msse2
|
||||
# $1 = test name, $2 = reference
|
||||
diff-out = $(call quiet-command, diff -u $1.out $2 | head -n 10,"DIFF","$1.out with $2")
|
||||
|
||||
# $1 = test name, $2 = reason
|
||||
skip-test = @printf " SKIPPED %s on $(TARGET_NAME) because %s\n" $1 $2
|
||||
|
||||
# Tests we are building
|
||||
TESTS=
|
||||
|
||||
# Start with a blank slate, the build targets get to add stuff first
|
||||
CFLAGS=
|
||||
QEMU_CFLAGS=
|
||||
LDFLAGS=
|
||||
|
||||
# TODO: automatically detect ARM and MIPS compilers, and run those too
|
||||
# The QEMU for this TARGET
|
||||
QEMU=../qemu-$(TARGET_NAME)
|
||||
|
||||
# runcom maps page 0, so it requires root privileges
|
||||
# also, pi_10.com runs indefinitely
|
||||
|
||||
I386_TESTS=hello-i386 \
|
||||
linux-test \
|
||||
testthread \
|
||||
sha1-i386 \
|
||||
test-i386 \
|
||||
test-i386-fprem \
|
||||
test-mmap \
|
||||
# runcom
|
||||
|
||||
# native i386 compilers sometimes are not biarch. assume cross-compilers are
|
||||
ifneq ($(ARCH),i386)
|
||||
I386_TESTS+=run-test-x86_64
|
||||
# If TCG debugging is enabled things are a lot slower
|
||||
ifeq ($(CONFIG_DEBUG_TCG),y)
|
||||
TIMEOUT=45
|
||||
else
|
||||
TIMEOUT=15
|
||||
endif
|
||||
|
||||
TESTS = test_path
|
||||
ifneq ($(call find-in-path, $(CC_I386)),)
|
||||
TESTS += $(I386_TESTS)
|
||||
# The order we include is important. We include multiarch, base arch
|
||||
# and finally arch if it's not the same as base arch.
|
||||
-include $(SRC_PATH)/tests/tcg/multiarch/Makefile.target
|
||||
-include $(SRC_PATH)/tests/tcg/$(TARGET_BASE_ARCH)/Makefile.target
|
||||
ifneq ($(TARGET_BASE_ARCH),$(TARGET_NAME))
|
||||
-include $(SRC_PATH)/tests/tcg/$(TARGET_NAME)/Makefile.target
|
||||
endif
|
||||
|
||||
all: $(patsubst %,run-%,$(TESTS))
|
||||
test: all
|
||||
# Add the common build options
|
||||
CFLAGS+=-Wall -O0 -g -fno-strict-aliasing
|
||||
ifeq ($(BUILD_STATIC),y)
|
||||
LDFLAGS+=-static
|
||||
endif
|
||||
|
||||
# rules to run tests
|
||||
%: %.c
|
||||
$(CC) $(CFLAGS) $(EXTRA_CFLAGS) $< -o $@ $(LDFLAGS)
|
||||
|
||||
.PHONY: $(patsubst %,run-%,$(TESTS))
|
||||
all: $(TESTS)
|
||||
|
||||
#
|
||||
# Test Runners
|
||||
#
|
||||
# By default we just run the test with the appropriate QEMU for the
|
||||
# target. More advanced tests may want to override the runner in their
|
||||
# specific make rules. Additional runners for the same binary should
|
||||
# be added to EXTRA_RUNS.
|
||||
#
|
||||
|
||||
RUN_TESTS=$(patsubst %,run-%, $(TESTS))
|
||||
RUN_TESTS+=$(EXTRA_RUNS)
|
||||
|
||||
run-%: %
|
||||
-$(QEMU) ./$*
|
||||
$(call run-test, $<, $(QEMU) $<, "$< on $(TARGET_NAME)")
|
||||
|
||||
run-hello-i386: hello-i386
|
||||
run-linux-test: linux-test
|
||||
run-testthread: testthread
|
||||
run-sha1-i386: sha1-i386
|
||||
.PHONY: run
|
||||
run: $(RUN_TESTS)
|
||||
|
||||
run-test-i386: test-i386
|
||||
./test-i386 > test-i386.ref
|
||||
-$(QEMU) test-i386 > test-i386.out
|
||||
@if diff -u test-i386.ref test-i386.out ; then echo "Auto Test OK"; fi
|
||||
|
||||
run-test-i386-fprem: test-i386-fprem
|
||||
./test-i386-fprem > test-i386-fprem.ref
|
||||
-$(QEMU) test-i386-fprem > test-i386-fprem.out
|
||||
@if diff -u test-i386-fprem.ref test-i386-fprem.out ; then echo "Auto Test OK"; fi
|
||||
|
||||
run-test-x86_64: test-x86_64
|
||||
./test-x86_64 > test-x86_64.ref
|
||||
-$(QEMU_X86_64) test-x86_64 > test-x86_64.out
|
||||
@if diff -u test-x86_64.ref test-x86_64.out ; then echo "Auto Test OK"; fi
|
||||
|
||||
run-test-mmap: test-mmap
|
||||
-$(QEMU) ./test-mmap
|
||||
-$(QEMU) -p 8192 ./test-mmap 8192
|
||||
-$(QEMU) -p 16384 ./test-mmap 16384
|
||||
-$(QEMU) -p 32768 ./test-mmap 32768
|
||||
|
||||
run-runcom: runcom
|
||||
-$(QEMU) ./runcom $(SRC_PATH)/tests/pi_10.com
|
||||
|
||||
run-test_path: test_path
|
||||
./test_path
|
||||
|
||||
# rules to compile tests
|
||||
|
||||
test_path: test_path.o
|
||||
|
||||
test_path.o: test_path.c
|
||||
|
||||
hello-i386: hello-i386.c
|
||||
$(CC_I386) -nostdlib $(CFLAGS) -static $(LDFLAGS) -o $@ $<
|
||||
strip $@
|
||||
|
||||
testthread: testthread.c
|
||||
$(CC_I386) $(CFLAGS) $(LDFLAGS) -o $@ $< -lpthread
|
||||
|
||||
# i386/x86_64 emulation test (test various opcodes) */
|
||||
test-i386: test-i386.c test-i386-code16.S test-i386-vm86.S \
|
||||
test-i386.h test-i386-shift.h test-i386-muldiv.h
|
||||
$(CC_I386) $(QEMU_INCLUDES) $(CFLAGS) $(LDFLAGS) -o $@ \
|
||||
$(<D)/test-i386.c $(<D)/test-i386-code16.S $(<D)/test-i386-vm86.S -lm
|
||||
|
||||
test-i386-fprem: test-i386-fprem.c
|
||||
$(CC_I386) $(QEMU_INCLUDES) $(CFLAGS) $(LDFLAGS) -o $@ $^
|
||||
|
||||
test-x86_64: test-i386.c \
|
||||
test-i386.h test-i386-shift.h test-i386-muldiv.h
|
||||
$(CC_X86_64) $(QEMU_INCLUDES) $(CFLAGS) $(LDFLAGS) -o $@ $(<D)/test-i386.c -lm
|
||||
|
||||
# generic Linux and CPU test
|
||||
linux-test: linux-test.c
|
||||
$(CC_I386) $(CFLAGS) $(LDFLAGS) -o $@ $< -lm
|
||||
|
||||
# vm86 test
|
||||
runcom: runcom.c
|
||||
$(CC_I386) $(CFLAGS) $(LDFLAGS) -o $@ $<
|
||||
|
||||
test-mmap: test-mmap.c
|
||||
$(CC_I386) -m32 $(CFLAGS) -Wall -O2 $(LDFLAGS) -o $@ $<
|
||||
|
||||
# speed test
|
||||
sha1-i386: sha1.c
|
||||
$(CC_I386) $(CFLAGS) $(LDFLAGS) -o $@ $<
|
||||
|
||||
sha1: sha1.c
|
||||
$(CC) $(CFLAGS) $(LDFLAGS) -o $@ $<
|
||||
|
||||
speed: sha1 sha1-i386
|
||||
time ./sha1
|
||||
time $(QEMU) ./sha1-i386
|
||||
|
||||
# arm test
|
||||
hello-arm: hello-arm.o
|
||||
arm-linux-ld -o $@ $<
|
||||
|
||||
hello-arm.o: hello-arm.c
|
||||
arm-linux-gcc -Wall -g -O2 -c -o $@ $<
|
||||
|
||||
test-arm-iwmmxt: test-arm-iwmmxt.s
|
||||
cpp < $< | arm-linux-gnu-gcc -Wall -static -march=iwmmxt -mabi=aapcs -x assembler - -o $@
|
||||
|
||||
# MIPS test
|
||||
hello-mips: hello-mips.c
|
||||
mips-linux-gnu-gcc -nostdlib -static -mno-abicalls -fno-PIC -mabi=32 -Wall -Wextra -g -O2 -o $@ $<
|
||||
|
||||
hello-mipsel: hello-mips.c
|
||||
mipsel-linux-gnu-gcc -nostdlib -static -mno-abicalls -fno-PIC -mabi=32 -Wall -Wextra -g -O2 -o $@ $<
|
||||
|
||||
# testsuite for the CRIS port.
|
||||
test-cris:
|
||||
$(MAKE) -C cris check
|
||||
|
||||
# testsuite for the LM32 port.
|
||||
test-lm32:
|
||||
$(MAKE) -C lm32 check
|
||||
|
||||
clean:
|
||||
rm -f *~ *.o test-i386.out test-i386.ref \
|
||||
test-x86_64.log test-x86_64.ref qruncom $(TESTS)
|
||||
# There is no clean target, the calling make just rm's the tests build dir
|
||||
|
|
88
tests/tcg/Makefile.include
Normal file
88
tests/tcg/Makefile.include
Normal file
|
@ -0,0 +1,88 @@
|
|||
# -*- Mode: makefile -*-
|
||||
#
|
||||
# TCG tests (per-target rules)
|
||||
#
|
||||
# This Makefile fragement is included from the per-target
|
||||
# Makefile.target so will be invoked for each linux-user program we
|
||||
# build. We have two options for compiling, either using a configured
|
||||
# guest compiler or calling one of our docker images to do it for us.
|
||||
#
|
||||
|
||||
# The per ARCH makefile, if it exists, holds extra information about
|
||||
# useful docker images or alternative compiler flags.
|
||||
|
||||
-include $(SRC_PATH)/tests/tcg/$(TARGET_BASE_ARCH)/Makefile.include
|
||||
-include $(SRC_PATH)/tests/tcg/$(TARGET_NAME)/Makefile.include
|
||||
|
||||
GUEST_BUILD=
|
||||
TCG_MAKE=$(SRC_PATH)/tests/tcg/Makefile
|
||||
# Support installed Cross Compilers
|
||||
|
||||
ifdef CROSS_CC_GUEST
|
||||
|
||||
.PHONY: cross-build-guest-tests
|
||||
cross-build-guest-tests:
|
||||
$(call quiet-command, \
|
||||
(mkdir -p tests && cd tests && \
|
||||
$(MAKE) -f $(TCG_MAKE) CC=$(CROSS_CC_GUEST) \
|
||||
BUILD_STATIC=$(CROSS_CC_GUEST_STATIC) \
|
||||
EXTRA_CFLAGS=$(CROSS_CC_GUEST_CFLAGS)), \
|
||||
"BUILD","$(TARGET_NAME) guest-tests with $(CROSS_CC_GUEST)")
|
||||
|
||||
GUEST_BUILD=cross-build-guest-tests
|
||||
|
||||
endif
|
||||
|
||||
# Support building with Docker
|
||||
|
||||
ifeq ($(HAVE_USER_DOCKER)$(GUEST_BUILD),y)
|
||||
ifneq ($(DOCKER_IMAGE),)
|
||||
|
||||
# We also need the Docker make rules to depend on
|
||||
include $(SRC_PATH)/tests/docker/Makefile.include
|
||||
|
||||
DOCKER_COMPILE_CMD="$(DOCKER_SCRIPT) cc --user $(shell id -u) \
|
||||
--cc $(DOCKER_CROSS_COMPILER) \
|
||||
-i qemu:$(DOCKER_IMAGE) \
|
||||
-s $(SRC_PATH) -- "
|
||||
DOCKER_PREREQ=docker-image-$(DOCKER_IMAGE)
|
||||
|
||||
.PHONY: docker-build-guest-tests
|
||||
docker-build-guest-tests: $(DOCKER_PREREQ)
|
||||
$(call quiet-command, \
|
||||
(mkdir -p tests && cd tests && \
|
||||
$(MAKE) -f $(TCG_MAKE) CC=$(DOCKER_COMPILE_CMD) \
|
||||
BUILD_STATIC=y \
|
||||
EXTRA_CFLAGS=$(DOCKER_CROSS_COMPILER_CFLAGS)), \
|
||||
"BUILD","$(TARGET_NAME) guest-tests with docker qemu:$(DOCKER_IMAGE)")
|
||||
|
||||
GUEST_BUILD=docker-build-guest-tests
|
||||
|
||||
endif
|
||||
endif
|
||||
|
||||
# Final targets
|
||||
.PHONY: guest-tests
|
||||
|
||||
ifneq ($(GUEST_BUILD),)
|
||||
guest-tests: $(GUEST_BUILD)
|
||||
|
||||
run-guest-tests: guest-tests qemu-$(TARGET_NAME)
|
||||
$(call quiet-command, \
|
||||
(cd tests && $(MAKE) -f $(TCG_MAKE) SPEED=$(SPEED) run), \
|
||||
"RUN", "tests for $(TARGET_NAME)")
|
||||
|
||||
else
|
||||
guest-tests:
|
||||
$(call quiet-command, /bin/true, "BUILD", \
|
||||
"$(TARGET_NAME) guest-tests SKIPPED")
|
||||
|
||||
run-guest-tests:
|
||||
$(call quiet-command, /bin/true, "RUN", \
|
||||
"tests for $(TARGET_NAME) SKIPPED")
|
||||
endif
|
||||
|
||||
# It doesn't matter if these don't exits
|
||||
.PHONY: clean-guest-tests
|
||||
clean-guest-tests:
|
||||
rm -rf tests || echo "no $(TARGET_NAME) tests to remove"
|
31
tests/tcg/Makefile.probe
Normal file
31
tests/tcg/Makefile.probe
Normal file
|
@ -0,0 +1,31 @@
|
|||
# -*- Mode: makefile -*-
|
||||
#
|
||||
# TCG Compiler Probe
|
||||
#
|
||||
# This Makefile fragement is included multiple times in the main make
|
||||
# script to probe for available compilers. This is used to build up a
|
||||
# selection of required docker targets before we invoke a sub-make for
|
||||
# each target.
|
||||
|
||||
# First we need the target makefile which tells us the target architecture
|
||||
-include $(BUILD_DIR)/$(PROBE_TARGET)/config-target.mak
|
||||
|
||||
# Then we load up the target architecture makefiles which tell us
|
||||
# about the compilers
|
||||
CROSS_CC_GUEST:=
|
||||
DOCKER_IMAGE:=
|
||||
DOCKER_PREREQ:=
|
||||
|
||||
-include $(SRC_PATH)/tests/tcg/$(TARGET_BASE_ARCH)/Makefile.include
|
||||
-include $(SRC_PATH)/tests/tcg/$(TARGET_NAME)/Makefile.include
|
||||
|
||||
ifndef CROSS_CC_GUEST
|
||||
ifneq ($(DOCKER_IMAGE),)
|
||||
DOCKER_PREREQ:=docker-image-$(DOCKER_IMAGE)
|
||||
endif
|
||||
endif
|
||||
|
||||
# Clean-up
|
||||
# undefine TARGET_NAME
|
||||
# undefine TARGET_BASE_ARCH
|
||||
# undefine TARGET_ABI_DIR
|
|
@ -1,68 +1,7 @@
|
|||
This directory contains various interesting programs for
|
||||
regression testing.
|
||||
|
||||
The target "make test" runs the programs and, if applicable,
|
||||
runs "diff" to detect mismatches between output on the host and
|
||||
output on QEMU.
|
||||
|
||||
i386
|
||||
====
|
||||
|
||||
test-i386
|
||||
---------
|
||||
|
||||
This program executes most of the 16 bit and 32 bit x86 instructions and
|
||||
generates a text output, for comparison with the output obtained with
|
||||
a real CPU or another emulator.
|
||||
|
||||
The Linux system call modify_ldt() is used to create x86 selectors
|
||||
to test some 16 bit addressing and 32 bit with segmentation cases.
|
||||
|
||||
The Linux system call vm86() is used to test vm86 emulation.
|
||||
|
||||
Various exceptions are raised to test most of the x86 user space
|
||||
exception reporting.
|
||||
|
||||
linux-test
|
||||
----------
|
||||
|
||||
This program tests various Linux system calls. It is used to verify
|
||||
that the system call parameters are correctly converted between target
|
||||
and host CPUs.
|
||||
|
||||
test-i386-fprem
|
||||
---------------
|
||||
|
||||
runcom
|
||||
------
|
||||
|
||||
test-mmap
|
||||
---------
|
||||
|
||||
sha1
|
||||
----
|
||||
|
||||
hello-i386
|
||||
----------
|
||||
|
||||
|
||||
ARM
|
||||
===
|
||||
|
||||
hello-arm
|
||||
---------
|
||||
|
||||
test-arm-iwmmxt
|
||||
---------------
|
||||
|
||||
MIPS
|
||||
====
|
||||
|
||||
hello-mips
|
||||
----------
|
||||
|
||||
hello-mipsel
|
||||
------------
|
||||
This directory contains various interesting guest programs for
|
||||
regression testing. Tests are either multi-arch, meaning they can be
|
||||
built for all guest architectures that support linux-user executable,
|
||||
or they are architecture specific.
|
||||
|
||||
CRIS
|
||||
====
|
||||
|
|
8
tests/tcg/aarch64/Makefile.include
Normal file
8
tests/tcg/aarch64/Makefile.include
Normal file
|
@ -0,0 +1,8 @@
|
|||
# Makefile.include for AArch64 targets
|
||||
#
|
||||
# We don't have any bigendian build tools so we only use this for AArch64
|
||||
|
||||
ifeq ($(TARGET_NAME),aarch64)
|
||||
DOCKER_IMAGE=debian-arm64-cross
|
||||
DOCKER_CROSS_COMPILER=aarch64-linux-gnu-gcc
|
||||
endif
|
17
tests/tcg/aarch64/Makefile.target
Normal file
17
tests/tcg/aarch64/Makefile.target
Normal file
|
@ -0,0 +1,17 @@
|
|||
# -*- Mode: makefile -*-
|
||||
#
|
||||
# AArch64 specific tweaks
|
||||
|
||||
AARCH64_SRC=$(SRC_PATH)/tests/tcg/aarch64
|
||||
VPATH += $(AARCH64_SRC)
|
||||
|
||||
# we don't build any of the ARM tests
|
||||
AARCH64_TESTS=$(filter-out $(ARM_TESTS), $(TESTS))
|
||||
AARCH64_TESTS+=fcvt
|
||||
TESTS:=$(AARCH64_TESTS)
|
||||
|
||||
fcvt: LDFLAGS+=-lm
|
||||
|
||||
run-fcvt: fcvt
|
||||
$(call run-test,$<,$(QEMU) $<, "$< on $(TARGET_NAME)")
|
||||
$(call diff-out,$<,$(AARCH64_SRC)/fcvt.ref)
|
3268
tests/tcg/aarch64/fcvt.ref
Normal file
3268
tests/tcg/aarch64/fcvt.ref
Normal file
File diff suppressed because it is too large
Load diff
|
@ -1,35 +0,0 @@
|
|||
CROSS=alpha-linux-gnu-
|
||||
CC=$(CROSS)gcc
|
||||
AS=$(CROSS)as
|
||||
|
||||
SIM=../../alpha-linux-user/qemu-alpha
|
||||
|
||||
CFLAGS=-O
|
||||
LINK=$(CC) -o $@ crt.o $< -nostdlib
|
||||
|
||||
TESTS=test-cond test-cmov
|
||||
|
||||
all: hello-alpha $(TESTS)
|
||||
|
||||
hello-alpha: hello-alpha.o crt.o
|
||||
$(LINK)
|
||||
|
||||
test-cond: test-cond.o crt.o
|
||||
$(LINK)
|
||||
|
||||
test-cmov.o: test-cond.c
|
||||
$(CC) -c $(CFLAGS) -DTEST_CMOV -o $@ $<
|
||||
|
||||
test-cmov: test-cmov.o crt.o
|
||||
$(LINK)
|
||||
|
||||
test-ovf: test-ovf.o crt.o
|
||||
$(LINK)
|
||||
|
||||
check: $(TESTS)
|
||||
for f in $(TESTS); do $(SIM) $$f || exit 1; done
|
||||
|
||||
clean:
|
||||
$(RM) *.o *~ hello-alpha $(TESTS)
|
||||
|
||||
.PHONY: clean all check
|
2
tests/tcg/alpha/Makefile.include
Normal file
2
tests/tcg/alpha/Makefile.include
Normal file
|
@ -0,0 +1,2 @@
|
|||
DOCKER_IMAGE=debian-alpha-cross
|
||||
DOCKER_CROSS_COMPILER=alpha-linux-gnu-gcc
|
18
tests/tcg/alpha/Makefile.target
Normal file
18
tests/tcg/alpha/Makefile.target
Normal file
|
@ -0,0 +1,18 @@
|
|||
# -*- Mode: makefile -*-
|
||||
#
|
||||
# Alpha specific tweaks
|
||||
|
||||
ALPHA_SRC=$(SRC_PATH)/tests/tcg/alpha
|
||||
VPATH+=$(ALPHA_SRC)
|
||||
|
||||
ALPHA_TESTS=hello-alpha test-cond test-cmov test-ovf
|
||||
TESTS+=$(ALPHA_TESTS)
|
||||
|
||||
test-cmov: EXTRA_CFLAGS=-DTEST_CMOV
|
||||
test-cmov: test-cond.c
|
||||
$(CC) $(CFLAGS) $(EXTRA_CFLAGS) $< -o $@ $(LDFLAGS)
|
||||
|
||||
run-test-cmov: test-cmov
|
||||
|
||||
# On Alpha Linux only supports 8k pages
|
||||
EXTRA_RUNS+=run-test-mmap-8192
|
|
@ -1,26 +0,0 @@
|
|||
.text
|
||||
|
||||
.globl _start
|
||||
.ent _start,0
|
||||
_start:
|
||||
.frame $15,0,$15
|
||||
br $29,1f
|
||||
1: ldgp $29, 0($29)
|
||||
.prologue 0
|
||||
ldq $27,main($29) !literal!1
|
||||
jsr $26,($27)
|
||||
or $0,$0,$16
|
||||
.end _start
|
||||
|
||||
.globl _exit
|
||||
_exit:
|
||||
lda $0,1
|
||||
callsys
|
||||
|
||||
call_pal 0
|
||||
|
||||
.globl write
|
||||
write:
|
||||
lda $0,4
|
||||
callsys
|
||||
ret
|
|
@ -1,3 +1,5 @@
|
|||
#include <unistd.h>
|
||||
|
||||
int main (void)
|
||||
{
|
||||
write (1, "hello\n", 6);
|
||||
|
|
|
@ -1,3 +1,4 @@
|
|||
#include <unistd.h>
|
||||
|
||||
#ifdef TEST_CMOV
|
||||
|
||||
|
|
|
@ -1,3 +1,5 @@
|
|||
#include <unistd.h>
|
||||
|
||||
static long test_subqv (long a, long b)
|
||||
{
|
||||
long res;
|
||||
|
|
8
tests/tcg/arm/Makefile.include
Normal file
8
tests/tcg/arm/Makefile.include
Normal file
|
@ -0,0 +1,8 @@
|
|||
# Makefile.include for all ARM targets
|
||||
#
|
||||
# We don't have any bigendian build tools so we only use this for armhf
|
||||
|
||||
ifeq ($(TARGET_NAME),arm)
|
||||
DOCKER_IMAGE=debian-armhf-cross
|
||||
DOCKER_CROSS_COMPILER=arm-linux-gnueabihf-gcc
|
||||
endif
|
32
tests/tcg/arm/Makefile.target
Normal file
32
tests/tcg/arm/Makefile.target
Normal file
|
@ -0,0 +1,32 @@
|
|||
# -*- Mode: makefile -*-
|
||||
#
|
||||
# ARM - included from tests/tcg/Makefile
|
||||
#
|
||||
|
||||
ARM_SRC=$(SRC_PATH)/tests/tcg/arm
|
||||
|
||||
# Set search path for all sources
|
||||
VPATH += $(ARM_SRC)
|
||||
|
||||
ARM_TESTS=hello-arm test-arm-iwmmxt
|
||||
|
||||
TESTS += $(ARM_TESTS) fcvt
|
||||
|
||||
hello-arm: CFLAGS+=-marm -ffreestanding
|
||||
hello-arm: LDFLAGS+=-nostdlib
|
||||
|
||||
test-arm-iwmmxt: CFLAGS+=-marm -march=iwmmxt -mabi=aapcs -mfpu=fpv4-sp-d16
|
||||
test-arm-iwmmxt: test-arm-iwmmxt.S
|
||||
$(CC) $(CFLAGS) $< -o $@ $(LDFLAGS)
|
||||
|
||||
ifeq ($(TARGET_NAME), arm)
|
||||
fcvt: LDFLAGS+=-lm
|
||||
# fcvt: CFLAGS+=-march=armv8.2-a+fp16 -mfpu=neon-fp-armv8
|
||||
|
||||
run-fcvt: fcvt
|
||||
$(call run-test,fcvt,$(QEMU) $<,"$< on $(TARGET_NAME)")
|
||||
$(call diff-out,fcvt,$(ARM_SRC)/fcvt.ref)
|
||||
endif
|
||||
|
||||
# On ARM Linux only supports 4k pages
|
||||
EXTRA_RUNS+=run-test-mmap-4096
|
11
tests/tcg/arm/README
Normal file
11
tests/tcg/arm/README
Normal file
|
@ -0,0 +1,11 @@
|
|||
These are ARM specific guest programs
|
||||
|
||||
hello-arm
|
||||
---------
|
||||
|
||||
A very simple inline assembly, write syscall based hello world
|
||||
|
||||
test-arm-iwmmxt
|
||||
---------------
|
||||
|
||||
A simple test case for older iwmmxt extended ARMs
|
458
tests/tcg/arm/fcvt.c
Normal file
458
tests/tcg/arm/fcvt.c
Normal file
|
@ -0,0 +1,458 @@
|
|||
/*
|
||||
* Test Floating Point Conversion
|
||||
*/
|
||||
|
||||
/* we want additional float type definitions */
|
||||
#define __STDC_WANT_IEC_60559_BFP_EXT__
|
||||
#define __STDC_WANT_IEC_60559_TYPES_EXT__
|
||||
|
||||
#include <stdio.h>
|
||||
#include <inttypes.h>
|
||||
#include <math.h>
|
||||
#include <float.h>
|
||||
#include <fenv.h>
|
||||
|
||||
#define ARRAY_SIZE(x) (sizeof(x) / sizeof((x)[0]))
|
||||
|
||||
static char flag_str[256];
|
||||
|
||||
static char *get_flag_state(int flags)
|
||||
{
|
||||
if (flags) {
|
||||
snprintf(flag_str, sizeof(flag_str), "%s %s %s %s %s",
|
||||
flags & FE_OVERFLOW ? "OVERFLOW" : "",
|
||||
flags & FE_UNDERFLOW ? "UNDERFLOW" : "",
|
||||
flags & FE_DIVBYZERO ? "DIV0" : "",
|
||||
flags & FE_INEXACT ? "INEXACT" : "",
|
||||
flags & FE_INVALID ? "INVALID" : "");
|
||||
} else {
|
||||
snprintf(flag_str, sizeof(flag_str), "OK");
|
||||
}
|
||||
|
||||
return flag_str;
|
||||
}
|
||||
|
||||
static void print_double_number(int i, double num)
|
||||
{
|
||||
uint64_t double_as_hex = *(uint64_t *) #
|
||||
int flags = fetestexcept(FE_ALL_EXCEPT);
|
||||
char *fstr = get_flag_state(flags);
|
||||
|
||||
printf("%02d DOUBLE: %02.20e / %#020" PRIx64 " (%#x => %s)\n",
|
||||
i, num, double_as_hex, flags, fstr);
|
||||
}
|
||||
|
||||
static void print_single_number(int i, float num)
|
||||
{
|
||||
uint32_t single_as_hex = *(uint32_t *) #
|
||||
int flags = fetestexcept(FE_ALL_EXCEPT);
|
||||
char *fstr = get_flag_state(flags);
|
||||
|
||||
printf("%02d SINGLE: %02.20e / %#010x (%#x => %s)\n",
|
||||
i, num, single_as_hex, flags, fstr);
|
||||
}
|
||||
|
||||
static void print_half_number(int i, uint16_t num)
|
||||
{
|
||||
int flags = fetestexcept(FE_ALL_EXCEPT);
|
||||
char *fstr = get_flag_state(flags);
|
||||
|
||||
printf("%02d HALF: %#04x (%#x => %s)\n",
|
||||
i, num, flags, fstr);
|
||||
}
|
||||
|
||||
static void print_int64(int i, int64_t num)
|
||||
{
|
||||
uint64_t int64_as_hex = *(uint64_t *) #
|
||||
int flags = fetestexcept(FE_ALL_EXCEPT);
|
||||
char *fstr = get_flag_state(flags);
|
||||
|
||||
printf("%02d INT64: %20" PRId64 "/%#020" PRIx64 " (%#x => %s)\n",
|
||||
i, num, int64_as_hex, flags, fstr);
|
||||
}
|
||||
|
||||
#ifndef SNANF
|
||||
/* Signaling NaN macros, if supported. */
|
||||
# if __GNUC_PREREQ(3, 3)
|
||||
# define SNANF (__builtin_nansf (""))
|
||||
# define SNAN (__builtin_nans (""))
|
||||
# define SNANL (__builtin_nansl (""))
|
||||
# endif
|
||||
#endif
|
||||
|
||||
float single_numbers[] = { -SNANF,
|
||||
-NAN,
|
||||
-INFINITY,
|
||||
-FLT_MAX,
|
||||
-1.111E+31,
|
||||
-1.111E+30,
|
||||
-1.08700982e-12,
|
||||
-1.78051176e-20,
|
||||
-FLT_MIN,
|
||||
0.0,
|
||||
FLT_MIN,
|
||||
2.98023224e-08,
|
||||
5.96046E-8, /* min positive FP16 subnormal */
|
||||
6.09756E-5, /* max subnormal FP16 */
|
||||
6.10352E-5, /* min positive normal FP16 */
|
||||
1.0,
|
||||
1.0009765625, /* smallest float after 1.0 FP16 */
|
||||
2.0,
|
||||
M_E, M_PI,
|
||||
65503.0,
|
||||
65504.0, /* max FP16 */
|
||||
65505.0,
|
||||
131007.0,
|
||||
131008.0, /* max AFP */
|
||||
131009.0,
|
||||
1.111E+30,
|
||||
FLT_MAX,
|
||||
INFINITY,
|
||||
NAN,
|
||||
SNANF };
|
||||
|
||||
static void convert_single_to_half(void)
|
||||
{
|
||||
int i;
|
||||
|
||||
printf("Converting single-precision to half-precision\n");
|
||||
|
||||
for (i = 0; i < ARRAY_SIZE(single_numbers); ++i) {
|
||||
float input = single_numbers[i];
|
||||
|
||||
feclearexcept(FE_ALL_EXCEPT);
|
||||
|
||||
print_single_number(i, input);
|
||||
#if defined(__arm__)
|
||||
uint32_t output;
|
||||
asm("vcvtb.f16.f32 %0, %1" : "=t" (output) : "x" (input));
|
||||
#else
|
||||
uint16_t output;
|
||||
asm("fcvt %h0, %s1" : "=w" (output) : "x" (input));
|
||||
#endif
|
||||
print_half_number(i, output);
|
||||
}
|
||||
}
|
||||
|
||||
static void convert_single_to_double(void)
|
||||
{
|
||||
int i;
|
||||
|
||||
printf("Converting single-precision to double-precision\n");
|
||||
|
||||
for (i = 0; i < ARRAY_SIZE(single_numbers); ++i) {
|
||||
float input = single_numbers[i];
|
||||
/* uint64_t output; */
|
||||
double output;
|
||||
|
||||
feclearexcept(FE_ALL_EXCEPT);
|
||||
|
||||
print_single_number(i, input);
|
||||
#if defined(__arm__)
|
||||
asm("vcvt.f64.f32 %P0, %1" : "=w" (output) : "t" (input));
|
||||
#else
|
||||
asm("fcvt %d0, %s1" : "=w" (output) : "x" (input));
|
||||
#endif
|
||||
print_double_number(i, output);
|
||||
}
|
||||
}
|
||||
|
||||
static void convert_single_to_integer(void)
|
||||
{
|
||||
int i;
|
||||
|
||||
printf("Converting single-precision to integer\n");
|
||||
|
||||
for (i = 0; i < ARRAY_SIZE(single_numbers); ++i) {
|
||||
float input = single_numbers[i];
|
||||
int64_t output;
|
||||
|
||||
feclearexcept(FE_ALL_EXCEPT);
|
||||
|
||||
print_single_number(i, input);
|
||||
#if defined(__arm__)
|
||||
/* asm("vcvt.s32.f32 %s0, %s1" : "=t" (output) : "t" (input)); */
|
||||
output = input;
|
||||
#else
|
||||
asm("fcvtzs %0, %s1" : "=r" (output) : "w" (input));
|
||||
#endif
|
||||
print_int64(i, output);
|
||||
}
|
||||
}
|
||||
|
||||
/* This allows us to initialise some doubles as pure hex */
|
||||
typedef union {
|
||||
double d;
|
||||
uint64_t h;
|
||||
} test_doubles;
|
||||
|
||||
test_doubles double_numbers[] = {
|
||||
{SNAN},
|
||||
{-NAN},
|
||||
{-INFINITY},
|
||||
{-DBL_MAX},
|
||||
{-FLT_MAX-1.0},
|
||||
{-FLT_MAX},
|
||||
{-1.111E+31},
|
||||
{-1.111E+30}, /* half prec */
|
||||
{-2.0}, {-1.0},
|
||||
{-DBL_MIN},
|
||||
{-FLT_MIN},
|
||||
{0.0},
|
||||
{FLT_MIN},
|
||||
{2.98023224e-08},
|
||||
{5.96046E-8}, /* min positive FP16 subnormal */
|
||||
{6.09756E-5}, /* max subnormal FP16 */
|
||||
{6.10352E-5}, /* min positive normal FP16 */
|
||||
{1.0},
|
||||
{1.0009765625}, /* smallest float after 1.0 FP16 */
|
||||
{DBL_MIN},
|
||||
{1.3789972848607228e-308},
|
||||
{1.4914738736681624e-308},
|
||||
{1.0}, {2.0},
|
||||
{M_E}, {M_PI},
|
||||
{65503.0},
|
||||
{65504.0}, /* max FP16 */
|
||||
{65505.0},
|
||||
{131007.0},
|
||||
{131008.0}, /* max AFP */
|
||||
{131009.0},
|
||||
{.h = 0x41dfffffffc00000 }, /* to int = 0x7fffffff */
|
||||
{FLT_MAX},
|
||||
{FLT_MAX + 1.0},
|
||||
{DBL_MAX},
|
||||
{INFINITY},
|
||||
{NAN},
|
||||
{.h = 0x7ff0000000000001}, /* SNAN */
|
||||
{SNAN},
|
||||
};
|
||||
|
||||
static void convert_double_to_half(void)
|
||||
{
|
||||
int i;
|
||||
|
||||
printf("Converting double-precision to half-precision\n");
|
||||
|
||||
for (i = 0; i < ARRAY_SIZE(double_numbers); ++i) {
|
||||
double input = double_numbers[i].d;
|
||||
uint16_t output;
|
||||
|
||||
feclearexcept(FE_ALL_EXCEPT);
|
||||
|
||||
print_double_number(i, input);
|
||||
|
||||
/* as we don't have _Float16 support */
|
||||
#if defined(__arm__)
|
||||
/* asm("vcvtb.f16.f64 %0, %P1" : "=t" (output) : "x" (input)); */
|
||||
output = input;
|
||||
#else
|
||||
asm("fcvt %h0, %d1" : "=w" (output) : "x" (input));
|
||||
#endif
|
||||
print_half_number(i, output);
|
||||
}
|
||||
}
|
||||
|
||||
static void convert_double_to_single(void)
|
||||
{
|
||||
int i;
|
||||
|
||||
printf("Converting double-precision to single-precision\n");
|
||||
|
||||
for (i = 0; i < ARRAY_SIZE(double_numbers); ++i) {
|
||||
double input = double_numbers[i].d;
|
||||
uint32_t output;
|
||||
|
||||
feclearexcept(FE_ALL_EXCEPT);
|
||||
|
||||
print_double_number(i, input);
|
||||
|
||||
#if defined(__arm__)
|
||||
asm("vcvt.f32.f64 %0, %P1" : "=w" (output) : "x" (input));
|
||||
#else
|
||||
asm("fcvt %s0, %d1" : "=w" (output) : "x" (input));
|
||||
#endif
|
||||
|
||||
print_single_number(i, output);
|
||||
}
|
||||
}
|
||||
|
||||
static void convert_double_to_integer(void)
|
||||
{
|
||||
int i;
|
||||
|
||||
printf("Converting double-precision to integer\n");
|
||||
|
||||
for (i = 0; i < ARRAY_SIZE(double_numbers); ++i) {
|
||||
double input = double_numbers[i].d;
|
||||
int64_t output;
|
||||
|
||||
feclearexcept(FE_ALL_EXCEPT);
|
||||
|
||||
print_double_number(i, input);
|
||||
#if defined(__arm__)
|
||||
/* asm("vcvt.s32.f32 %s0, %s1" : "=t" (output) : "t" (input)); */
|
||||
output = input;
|
||||
#else
|
||||
asm("fcvtzs %0, %d1" : "=r" (output) : "w" (input));
|
||||
#endif
|
||||
print_int64(i, output);
|
||||
}
|
||||
}
|
||||
|
||||
/* no handy defines for these numbers */
|
||||
uint16_t half_numbers[] = {
|
||||
0xffff, /* -NaN / AHP -Max */
|
||||
0xfcff, /* -NaN / AHP */
|
||||
0xfc01, /* -NaN / AHP */
|
||||
0xfc00, /* -Inf */
|
||||
0xfbff, /* -Max */
|
||||
0xc000, /* -2 */
|
||||
0xbc00, /* -1 */
|
||||
0x8001, /* -MIN subnormal */
|
||||
0x8000, /* -0 */
|
||||
0x0000, /* +0 */
|
||||
0x0001, /* MIN subnormal */
|
||||
0x3c00, /* 1 */
|
||||
0x7bff, /* Max */
|
||||
0x7c00, /* Inf */
|
||||
0x7c01, /* NaN / AHP */
|
||||
0x7cff, /* NaN / AHP */
|
||||
0x7fff, /* NaN / AHP +Max*/
|
||||
};
|
||||
|
||||
static void convert_half_to_double(void)
|
||||
{
|
||||
int i;
|
||||
|
||||
printf("Converting half-precision to double-precision\n");
|
||||
|
||||
for (i = 0; i < ARRAY_SIZE(half_numbers); ++i) {
|
||||
uint16_t input = half_numbers[i];
|
||||
double output;
|
||||
|
||||
feclearexcept(FE_ALL_EXCEPT);
|
||||
|
||||
print_half_number(i, input);
|
||||
#if defined(__arm__)
|
||||
/* asm("vcvtb.f64.f16 %P0, %1" : "=w" (output) : "t" (input)); */
|
||||
output = input;
|
||||
#else
|
||||
asm("fcvt %d0, %h1" : "=w" (output) : "x" (input));
|
||||
#endif
|
||||
print_double_number(i, output);
|
||||
}
|
||||
}
|
||||
|
||||
static void convert_half_to_single(void)
|
||||
{
|
||||
int i;
|
||||
|
||||
printf("Converting half-precision to single-precision\n");
|
||||
|
||||
for (i = 0; i < ARRAY_SIZE(half_numbers); ++i) {
|
||||
uint16_t input = half_numbers[i];
|
||||
float output;
|
||||
|
||||
feclearexcept(FE_ALL_EXCEPT);
|
||||
|
||||
print_half_number(i, input);
|
||||
#if defined(__arm__)
|
||||
asm("vcvtb.f32.f16 %0, %1" : "=w" (output) : "x" ((uint32_t)input));
|
||||
#else
|
||||
asm("fcvt %s0, %h1" : "=w" (output) : "x" (input));
|
||||
#endif
|
||||
print_single_number(i, output);
|
||||
}
|
||||
}
|
||||
|
||||
static void convert_half_to_integer(void)
|
||||
{
|
||||
int i;
|
||||
|
||||
printf("Converting half-precision to integer\n");
|
||||
|
||||
for (i = 0; i < ARRAY_SIZE(half_numbers); ++i) {
|
||||
uint16_t input = half_numbers[i];
|
||||
int64_t output;
|
||||
|
||||
feclearexcept(FE_ALL_EXCEPT);
|
||||
|
||||
print_half_number(i, input);
|
||||
#if defined(__arm__)
|
||||
/* asm("vcvt.s32.f16 %0, %1" : "=t" (output) : "t" (input)); v8.2*/
|
||||
output = input;
|
||||
#else
|
||||
asm("fcvt %s0, %h1" : "=w" (output) : "x" (input));
|
||||
#endif
|
||||
print_int64(i, output);
|
||||
}
|
||||
}
|
||||
|
||||
typedef struct {
|
||||
int flag;
|
||||
char *desc;
|
||||
} float_mapping;
|
||||
|
||||
float_mapping round_flags[] = {
|
||||
{ FE_TONEAREST, "to nearest" },
|
||||
{ FE_UPWARD, "upwards" },
|
||||
{ FE_DOWNWARD, "downwards" },
|
||||
{ FE_TOWARDZERO, "to zero" }
|
||||
};
|
||||
|
||||
int main(int argc, char *argv[argc])
|
||||
{
|
||||
int i;
|
||||
|
||||
printf("#### Enabling IEEE Half Precision\n");
|
||||
|
||||
for (i = 0; i < ARRAY_SIZE(round_flags); ++i) {
|
||||
fesetround(round_flags[i].flag);
|
||||
printf("### Rounding %s\n", round_flags[i].desc);
|
||||
convert_single_to_half();
|
||||
convert_single_to_double();
|
||||
convert_double_to_half();
|
||||
convert_double_to_single();
|
||||
convert_half_to_single();
|
||||
convert_half_to_double();
|
||||
}
|
||||
|
||||
/* convert to integer */
|
||||
convert_single_to_integer();
|
||||
convert_double_to_integer();
|
||||
convert_half_to_integer();
|
||||
|
||||
/* And now with ARM alternative FP16 */
|
||||
#if defined(__arm__)
|
||||
/* See glibc sysdeps/arm/fpu_control.h */
|
||||
asm("mrc p10, 7, r1, cr1, cr0, 0\n\t"
|
||||
"orr r1, r1, %[flags]\n\t"
|
||||
"mcr p10, 7, r1, cr1, cr0, 0\n\t"
|
||||
: /* no output */ : [flags] "n" (1 << 26) : "r1" );
|
||||
#else
|
||||
asm("mrs x1, fpcr\n\t"
|
||||
"orr x1, x1, %[flags]\n\t"
|
||||
"msr fpcr, x1\n\t"
|
||||
: /* no output */ : [flags] "n" (1 << 26) : "x1" );
|
||||
#endif
|
||||
|
||||
printf("#### Enabling ARM Alternative Half Precision\n");
|
||||
|
||||
for (i = 0; i < ARRAY_SIZE(round_flags); ++i) {
|
||||
fesetround(round_flags[i].flag);
|
||||
printf("### Rounding %s\n", round_flags[i].desc);
|
||||
convert_single_to_half();
|
||||
convert_single_to_double();
|
||||
convert_double_to_half();
|
||||
convert_double_to_single();
|
||||
convert_half_to_single();
|
||||
convert_half_to_double();
|
||||
}
|
||||
|
||||
/* convert to integer */
|
||||
convert_single_to_integer();
|
||||
convert_double_to_integer();
|
||||
convert_half_to_integer();
|
||||
|
||||
return 0;
|
||||
}
|
3268
tests/tcg/arm/fcvt.ref
Normal file
3268
tests/tcg/arm/fcvt.ref
Normal file
File diff suppressed because it is too large
Load diff
2
tests/tcg/hppa/Makefile.include
Normal file
2
tests/tcg/hppa/Makefile.include
Normal file
|
@ -0,0 +1,2 @@
|
|||
DOCKER_IMAGE=debian-hppa-cross
|
||||
DOCKER_CROSS_COMPILER=hppa-linux-gnu-gcc
|
6
tests/tcg/hppa/Makefile.target
Normal file
6
tests/tcg/hppa/Makefile.target
Normal file
|
@ -0,0 +1,6 @@
|
|||
# -*- Mode: makefile -*-
|
||||
#
|
||||
# HPPA specific tweaks - specifically masking out broken tests
|
||||
|
||||
# On parisc Linux supports 4K/16K/64K (but currently only 4k works)
|
||||
EXTRA_RUNS+=run-test-mmap-4096 # run-test-mmap-16384 run-test-mmap-65536
|
9
tests/tcg/i386/Makefile.include
Normal file
9
tests/tcg/i386/Makefile.include
Normal file
|
@ -0,0 +1,9 @@
|
|||
#
|
||||
# Makefile.include for all i386
|
||||
#
|
||||
# There is enough brokeness in x86_64 compilers that we don't default
|
||||
# to using the x86_64 system compiler for i386 binaries.
|
||||
#
|
||||
|
||||
DOCKER_IMAGE=fedora-i386-cross
|
||||
DOCKER_CROSS_COMPILER=gcc
|
52
tests/tcg/i386/Makefile.target
Normal file
52
tests/tcg/i386/Makefile.target
Normal file
|
@ -0,0 +1,52 @@
|
|||
# i386 cross compile notes
|
||||
|
||||
I386_SRC=$(SRC_PATH)/tests/tcg/i386
|
||||
|
||||
# Set search path for all sources
|
||||
VPATH += $(I386_SRC)
|
||||
|
||||
I386_SRCS=$(notdir $(wildcard $(I386_SRC)/*.c))
|
||||
I386_TESTS=$(I386_SRCS:.c=)
|
||||
I386_ONLY_TESTS=$(filter-out test-i386-ssse3, $(I386_TESTS))
|
||||
# Update TESTS
|
||||
TESTS+=$(I386_ONLY_TESTS)
|
||||
|
||||
ifneq ($(TARGET_NAME),x86_64)
|
||||
CFLAGS+=-m32
|
||||
endif
|
||||
|
||||
#
|
||||
# hello-i386 is a barebones app
|
||||
#
|
||||
hello-i386: CFLAGS+=-ffreestanding
|
||||
hello-i386: LDFLAGS+=-nostdlib
|
||||
|
||||
#
|
||||
# test-386 includes a couple of additional objects that need to be linked together
|
||||
#
|
||||
|
||||
test-i386: test-i386.c test-i386-code16.S test-i386-vm86.S test-i386.h test-i386-shift.h test-i386-muldiv.h
|
||||
$(CC) $(CFLAGS) $(LDFLAGS) -o $@ \
|
||||
$(<D)/test-i386.c $(<D)/test-i386-code16.S $(<D)/test-i386-vm86.S -lm
|
||||
|
||||
# Specialist test runners
|
||||
run-runcom: TIMEOUT=30
|
||||
run-runcom: runcom pi_10.com
|
||||
$(call run-test,$<,$(QEMU) ./runcom $(I386_SRC)/pi_10.com,"$< on $(TARGET_NAME)")
|
||||
|
||||
ifeq ($(SPEED), slow)
|
||||
|
||||
test-i386-fprem.ref: test-i386-fprem
|
||||
$(call quiet-command, ./$< > $@,"GENREF","generating $@")
|
||||
|
||||
run-test-i386-fprem: TIMEOUT=60
|
||||
run-test-i386-fprem: test-i386-fprem
|
||||
$(call run-test,test-i386-fprem, $(QEMU) $<,"$< on $(TARGET_NAME)")
|
||||
$(call diff-out,test-i386-fprem, $(I386_SRC)/$<.ref)
|
||||
else
|
||||
run-test-i386-fprem: test-i386-fprem
|
||||
$(call skip-test, $<, "SLOW")
|
||||
endif
|
||||
|
||||
# On i386 and x86_64 Linux only supports 4k pages (large pages are a different hack)
|
||||
EXTRA_RUNS+=run-test-mmap-4096
|
38
tests/tcg/i386/README
Normal file
38
tests/tcg/i386/README
Normal file
|
@ -0,0 +1,38 @@
|
|||
These are i386 specific guest programs
|
||||
|
||||
test-i386
|
||||
---------
|
||||
|
||||
This program executes most of the 16 bit and 32 bit x86 instructions and
|
||||
generates a text output, for comparison with the output obtained with
|
||||
a real CPU or another emulator.
|
||||
|
||||
The Linux system call modify_ldt() is used to create x86 selectors
|
||||
to test some 16 bit addressing and 32 bit with segmentation cases.
|
||||
|
||||
The Linux system call vm86() is used to test vm86 emulation.
|
||||
|
||||
Various exceptions are raised to test most of the x86 user space
|
||||
exception reporting.
|
||||
|
||||
linux-test
|
||||
----------
|
||||
|
||||
This program tests various Linux system calls. It is used to verify
|
||||
that the system call parameters are correctly converted between target
|
||||
and host CPUs.
|
||||
|
||||
test-i386-fprem
|
||||
---------------
|
||||
|
||||
runcom
|
||||
------
|
||||
|
||||
test-mmap
|
||||
---------
|
||||
|
||||
sha1
|
||||
----
|
||||
|
||||
hello-i386
|
||||
----------
|
|
@ -20,6 +20,7 @@ static inline int write(int fd, const char * buf, int len)
|
|||
return status;
|
||||
}
|
||||
|
||||
void _start(void);
|
||||
void _start(void)
|
||||
{
|
||||
write(1, "Hello World\n", 12);
|
|
@ -23,7 +23,10 @@
|
|||
* along with this program; if not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include "qemu/osdep.h"
|
||||
#include <stdio.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#define ARRAY_SIZE(x) (sizeof(x) / sizeof((x)[0]))
|
||||
|
||||
/*
|
||||
* Inspired by <ieee754.h>'s union ieee854_long_double, but with single
|
||||
|
@ -39,7 +42,7 @@ union float80u {
|
|||
unsigned int exponent:15;
|
||||
unsigned int negative:1;
|
||||
unsigned int empty:16;
|
||||
} QEMU_PACKED ieee;
|
||||
} __attribute__((packed)) ieee;
|
||||
|
||||
/* This is for NaNs in the IEEE 854 double-extended-precision format. */
|
||||
struct {
|
||||
|
@ -49,7 +52,7 @@ union float80u {
|
|||
unsigned int exponent:15;
|
||||
unsigned int negative:1;
|
||||
unsigned int empty:16;
|
||||
} QEMU_PACKED ieee_nan;
|
||||
} __attribute__((packed)) ieee_nan;
|
||||
};
|
||||
|
||||
#define IEEE854_LONG_DOUBLE_BIAS 0x3fff
|
||||
|
@ -229,6 +232,7 @@ static void test_fprem_cases(void)
|
|||
do_fprem_stack_underflow();
|
||||
|
||||
printf("= invalid operation =\n");
|
||||
do_fprem(q_nan.d, 1.0);
|
||||
do_fprem(s_nan.d, 1.0);
|
||||
do_fprem(1.0, 0.0);
|
||||
do_fprem(pos_inf.d, 1.0);
|
||||
|
@ -238,6 +242,8 @@ static void test_fprem_cases(void)
|
|||
do_fprem(pos_denorm.d, 1.0);
|
||||
do_fprem(1.0, pos_denorm.d);
|
||||
|
||||
do_fprem(smallest_positive_norm.d, smallest_positive_norm.d);
|
||||
|
||||
/* printf("= underflow =\n"); */
|
||||
/* TODO: Is there a case where FPREM raises underflow? */
|
||||
}
|
|
@ -17,7 +17,6 @@
|
|||
* along with this program; if not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
#define _GNU_SOURCE
|
||||
#include "qemu/compiler.h"
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
|
@ -2107,8 +2106,8 @@ static void test_enter(void)
|
|||
|
||||
#ifdef TEST_SSE
|
||||
|
||||
typedef int __m64 __attribute__ ((__mode__ (__V2SI__)));
|
||||
typedef float __m128 __attribute__ ((__mode__(__V4SF__)));
|
||||
typedef int __m64 __attribute__ ((vector_size(8)));
|
||||
typedef float __m128 __attribute__ ((vector_size(16)));
|
||||
|
||||
typedef union {
|
||||
double d[2];
|
||||
|
@ -2259,7 +2258,7 @@ SSE_OP(a ## sd);
|
|||
"pop %0\n"\
|
||||
: "=rm" (eflags)\
|
||||
: "x" (a.dq), "x" (b.dq));\
|
||||
printf("%-9s: a=%f b=%f cc=%04x\n",\
|
||||
printf("%-9s: a=%f b=%f cc=%04lx\n",\
|
||||
#op, a1, b1,\
|
||||
eflags & (CC_C | CC_P | CC_Z | CC_S | CC_O | CC_A));\
|
||||
}
|
2
tests/tcg/m68k/Makefile.include
Normal file
2
tests/tcg/m68k/Makefile.include
Normal file
|
@ -0,0 +1,2 @@
|
|||
DOCKER_IMAGE=debian-m68k-cross
|
||||
DOCKER_CROSS_COMPILER=m68k-linux-gnu-gcc
|
7
tests/tcg/m68k/Makefile.target
Normal file
7
tests/tcg/m68k/Makefile.target
Normal file
|
@ -0,0 +1,7 @@
|
|||
# -*- Mode: makefile -*-
|
||||
#
|
||||
# m68k specific tweaks - specifically masking out broken tests
|
||||
#
|
||||
|
||||
# On m68k Linux supports 4k and 8k pages (but 8k is currently broken)
|
||||
EXTRA_RUNS+=run-test-mmap-4096 # run-test-mmap-8192
|
20
tests/tcg/mips/Makefile.include
Normal file
20
tests/tcg/mips/Makefile.include
Normal file
|
@ -0,0 +1,20 @@
|
|||
#
|
||||
# Makefile.include for all MIPs targets
|
||||
#
|
||||
# As Debian doesn't support mip64 in big endian mode the only way to
|
||||
# build BE is to pass a working cross compiler to ./configure
|
||||
#
|
||||
|
||||
ifeq ($(TARGET_NAME),mips64el)
|
||||
DOCKER_IMAGE=debian-mips64el-cross
|
||||
DOCKER_CROSS_COMPILER=mips64el-linux-gnuabi64-gcc
|
||||
else ifeq ($(TARGET_NAME),mips64)
|
||||
DOCKER_IMAGE=debian-mips64-cross
|
||||
DOCKER_CROSS_COMPILER=mips64-linux-gnuabi64-gcc
|
||||
else ifeq ($(TARGET_NAME),mipsel)
|
||||
DOCKER_IMAGE=debian-mipsel-cross
|
||||
DOCKER_CROSS_COMPILER=mipsel-linux-gnu-gcc
|
||||
else ifeq ($(TARGET_NAME),mips)
|
||||
DOCKER_IMAGE=debian-mips-cross
|
||||
DOCKER_CROSS_COMPILER=mips-linux-gnu-gcc
|
||||
endif
|
22
tests/tcg/mips/Makefile.target
Normal file
22
tests/tcg/mips/Makefile.target
Normal file
|
@ -0,0 +1,22 @@
|
|||
# -*- Mode: makefile -*-
|
||||
#
|
||||
# MIPS - included from tests/tcg/Makefile.target
|
||||
#
|
||||
|
||||
MIPS_SRC=$(SRC_PATH)/tests/tcg/mips
|
||||
|
||||
# Set search path for all sources
|
||||
VPATH += $(MIPS_SRC)
|
||||
|
||||
MIPS_TESTS=hello-mips
|
||||
|
||||
TESTS += $(MIPS_TESTS)
|
||||
|
||||
hello-mips: CFLAGS+=-ffreestanding
|
||||
hello-mips: LDFLAGS+=-nostdlib
|
||||
|
||||
# For MIPS32 and 64 we have a bunch of extra tests in sub-directories
|
||||
# however they are intended for system tests.
|
||||
|
||||
run-hello-mips: hello-mips
|
||||
$(call skip-test, $<, "BROKEN")
|
7
tests/tcg/mips/README
Normal file
7
tests/tcg/mips/README
Normal file
|
@ -0,0 +1,7 @@
|
|||
MIPS
|
||||
====
|
||||
|
||||
hello-mips
|
||||
----------
|
||||
|
||||
A very simple inline assembly, write syscall based hello world
|
36
tests/tcg/multiarch/Makefile.target
Normal file
36
tests/tcg/multiarch/Makefile.target
Normal file
|
@ -0,0 +1,36 @@
|
|||
# -*- Mode: makefile -*-
|
||||
#
|
||||
# Multiarch Tests - included from tests/tcg/Makefile.target
|
||||
#
|
||||
# These tests are plain C and built without any architecture specific code.
|
||||
#
|
||||
|
||||
MULTIARCH_SRC=$(SRC_PATH)/tests/tcg/multiarch
|
||||
|
||||
# Set search path for all sources
|
||||
VPATH += $(MULTIARCH_SRC)
|
||||
MULTIARCH_SRCS =$(notdir $(wildcard $(MULTIARCH_SRC)/*.c))
|
||||
MULTIARCH_TESTS =$(MULTIARCH_SRCS:.c=)
|
||||
|
||||
# Update TESTS
|
||||
TESTS +=$(MULTIARCH_TESTS)
|
||||
|
||||
#
|
||||
# The following are any additional rules needed to build things
|
||||
#
|
||||
|
||||
testthread: LDFLAGS+=-lpthread
|
||||
|
||||
# We define the runner for test-mmap after the individual
|
||||
# architectures have defined their supported pages sizes. If no
|
||||
# additional page sizes are defined we only run the default test.
|
||||
|
||||
# default case (host page size)
|
||||
run-test-mmap: test-mmap
|
||||
$(call run-test, test-mmap, $(QEMU) $<, \
|
||||
"$< (default) on $(TARGET_NAME)")
|
||||
|
||||
# additional page sizes (defined by each architecture adding to EXTRA_RUNS)
|
||||
run-test-mmap-%: test-mmap
|
||||
$(call run-test, test-mmap-$*, $(QEMU) -p $* $<,\
|
||||
"$< ($* byte pages) on $(TARGET_NAME)")
|
1
tests/tcg/multiarch/README
Normal file
1
tests/tcg/multiarch/README
Normal file
|
@ -0,0 +1 @@
|
|||
Multi-architecture linux-user tests
|
|
@ -31,6 +31,7 @@
|
|||
#include <utime.h>
|
||||
#include <time.h>
|
||||
#include <sys/time.h>
|
||||
#include <sys/resource.h>
|
||||
#include <sys/uio.h>
|
||||
#include <sys/socket.h>
|
||||
#include <netinet/in.h>
|
||||
|
@ -39,13 +40,11 @@
|
|||
#include <dirent.h>
|
||||
#include <setjmp.h>
|
||||
#include <sys/shm.h>
|
||||
#include "qemu/cutils.h"
|
||||
#include <assert.h>
|
||||
|
||||
#define TESTPATH "/tmp/linux-test.tmp"
|
||||
#define TESTPORT 7654
|
||||
#define STACK_SIZE 16384
|
||||
|
||||
void error1(const char *filename, int line, const char *fmt, ...)
|
||||
static void error1(const char *filename, int line, const char *fmt, ...)
|
||||
{
|
||||
va_list ap;
|
||||
va_start(ap, fmt);
|
||||
|
@ -56,11 +55,11 @@ void error1(const char *filename, int line, const char *fmt, ...)
|
|||
exit(1);
|
||||
}
|
||||
|
||||
int __chk_error(const char *filename, int line, int ret)
|
||||
static int __chk_error(const char *filename, int line, int ret)
|
||||
{
|
||||
if (ret < 0) {
|
||||
error1(filename, line, "%m (ret=%d, errno=%d)",
|
||||
ret, errno);
|
||||
error1(filename, line, "%m (ret=%d, errno=%d/%s)",
|
||||
ret, errno, strerror(errno));
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
@ -73,7 +72,7 @@ int __chk_error(const char *filename, int line, int ret)
|
|||
|
||||
#define FILE_BUF_SIZE 300
|
||||
|
||||
void test_file(void)
|
||||
static void test_file(void)
|
||||
{
|
||||
int fd, i, len, ret;
|
||||
uint8_t buf[FILE_BUF_SIZE];
|
||||
|
@ -85,19 +84,16 @@ void test_file(void)
|
|||
struct iovec vecs[2];
|
||||
DIR *dir;
|
||||
struct dirent *de;
|
||||
/* TODO: make common tempdir creation for tcg tests */
|
||||
char template[] = "/tmp/linux-test-XXXXXX";
|
||||
char *tmpdir = mkdtemp(template);
|
||||
|
||||
/* clean up, just in case */
|
||||
unlink(TESTPATH "/file1");
|
||||
unlink(TESTPATH "/file2");
|
||||
unlink(TESTPATH "/file3");
|
||||
rmdir(TESTPATH);
|
||||
assert(tmpdir);
|
||||
|
||||
if (getcwd(cur_dir, sizeof(cur_dir)) == NULL)
|
||||
error("getcwd");
|
||||
|
||||
chk_error(mkdir(TESTPATH, 0755));
|
||||
|
||||
chk_error(chdir(TESTPATH));
|
||||
chk_error(chdir(tmpdir));
|
||||
|
||||
/* open/read/write/close/readv/writev/lseek */
|
||||
|
||||
|
@ -163,7 +159,7 @@ void test_file(void)
|
|||
st.st_mtime != 1000)
|
||||
error("stat time");
|
||||
|
||||
chk_error(stat(TESTPATH, &st));
|
||||
chk_error(stat(tmpdir, &st));
|
||||
if (!S_ISDIR(st.st_mode))
|
||||
error("stat mode");
|
||||
|
||||
|
@ -185,7 +181,7 @@ void test_file(void)
|
|||
error("stat mode");
|
||||
|
||||
/* getdents */
|
||||
dir = opendir(TESTPATH);
|
||||
dir = opendir(tmpdir);
|
||||
if (!dir)
|
||||
error("opendir");
|
||||
len = 0;
|
||||
|
@ -207,16 +203,17 @@ void test_file(void)
|
|||
chk_error(unlink("file3"));
|
||||
chk_error(unlink("file2"));
|
||||
chk_error(chdir(cur_dir));
|
||||
chk_error(rmdir(TESTPATH));
|
||||
chk_error(rmdir(tmpdir));
|
||||
}
|
||||
|
||||
void test_fork(void)
|
||||
static void test_fork(void)
|
||||
{
|
||||
int pid, status;
|
||||
|
||||
pid = chk_error(fork());
|
||||
if (pid == 0) {
|
||||
/* child */
|
||||
sleep(2);
|
||||
exit(2);
|
||||
}
|
||||
chk_error(waitpid(pid, &status, 0));
|
||||
|
@ -224,7 +221,7 @@ void test_fork(void)
|
|||
error("waitpid status=0x%x", status);
|
||||
}
|
||||
|
||||
void test_time(void)
|
||||
static void test_time(void)
|
||||
{
|
||||
struct timeval tv, tv2;
|
||||
struct timespec ts, rem;
|
||||
|
@ -251,34 +248,7 @@ void test_time(void)
|
|||
error("getrusage");
|
||||
}
|
||||
|
||||
void pstrcpy(char *buf, int buf_size, const char *str)
|
||||
{
|
||||
int c;
|
||||
char *q = buf;
|
||||
|
||||
if (buf_size <= 0)
|
||||
return;
|
||||
|
||||
for(;;) {
|
||||
c = *str++;
|
||||
if (c == 0 || q >= buf + buf_size - 1)
|
||||
break;
|
||||
*q++ = c;
|
||||
}
|
||||
*q = '\0';
|
||||
}
|
||||
|
||||
/* strcat and truncate. */
|
||||
char *pstrcat(char *buf, int buf_size, const char *s)
|
||||
{
|
||||
int len;
|
||||
len = strlen(buf);
|
||||
if (len < buf_size)
|
||||
pstrcpy(buf + len, buf_size - len, s);
|
||||
return buf;
|
||||
}
|
||||
|
||||
int server_socket(void)
|
||||
static int server_socket(void)
|
||||
{
|
||||
int val, fd;
|
||||
struct sockaddr_in sockaddr;
|
||||
|
@ -290,7 +260,7 @@ int server_socket(void)
|
|||
chk_error(setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, &val, sizeof(val)));
|
||||
|
||||
sockaddr.sin_family = AF_INET;
|
||||
sockaddr.sin_port = htons(TESTPORT);
|
||||
sockaddr.sin_port = htons(0); /* choose random ephemeral port) */
|
||||
sockaddr.sin_addr.s_addr = 0;
|
||||
chk_error(bind(fd, (struct sockaddr *)&sockaddr, sizeof(sockaddr)));
|
||||
chk_error(listen(fd, 0));
|
||||
|
@ -298,7 +268,7 @@ int server_socket(void)
|
|||
|
||||
}
|
||||
|
||||
int client_socket(void)
|
||||
static int client_socket(uint16_t port)
|
||||
{
|
||||
int fd;
|
||||
struct sockaddr_in sockaddr;
|
||||
|
@ -306,22 +276,29 @@ int client_socket(void)
|
|||
/* server socket */
|
||||
fd = chk_error(socket(PF_INET, SOCK_STREAM, 0));
|
||||
sockaddr.sin_family = AF_INET;
|
||||
sockaddr.sin_port = htons(TESTPORT);
|
||||
sockaddr.sin_port = htons(port);
|
||||
inet_aton("127.0.0.1", &sockaddr.sin_addr);
|
||||
chk_error(connect(fd, (struct sockaddr *)&sockaddr, sizeof(sockaddr)));
|
||||
return fd;
|
||||
}
|
||||
|
||||
const char socket_msg[] = "hello socket\n";
|
||||
static const char socket_msg[] = "hello socket\n";
|
||||
|
||||
void test_socket(void)
|
||||
static void test_socket(void)
|
||||
{
|
||||
int server_fd, client_fd, fd, pid, ret, val;
|
||||
struct sockaddr_in sockaddr;
|
||||
socklen_t len;
|
||||
struct sockaddr_in server_addr;
|
||||
socklen_t len, socklen;
|
||||
uint16_t server_port;
|
||||
char buf[512];
|
||||
|
||||
server_fd = server_socket();
|
||||
/* find out what port we got */
|
||||
socklen = sizeof(server_addr);
|
||||
ret = getsockname(server_fd, &server_addr, &socklen);
|
||||
chk_error(ret);
|
||||
server_port = ntohs(server_addr.sin_port);
|
||||
|
||||
/* test a few socket options */
|
||||
len = sizeof(val);
|
||||
|
@ -331,7 +308,7 @@ void test_socket(void)
|
|||
|
||||
pid = chk_error(fork());
|
||||
if (pid == 0) {
|
||||
client_fd = client_socket();
|
||||
client_fd = client_socket(server_port);
|
||||
send(client_fd, socket_msg, sizeof(socket_msg), 0);
|
||||
close(client_fd);
|
||||
exit(0);
|
||||
|
@ -350,7 +327,7 @@ void test_socket(void)
|
|||
|
||||
#define WCOUNT_MAX 512
|
||||
|
||||
void test_pipe(void)
|
||||
static void test_pipe(void)
|
||||
{
|
||||
fd_set rfds, wfds;
|
||||
int fds[2], fd_max, ret;
|
||||
|
@ -382,7 +359,7 @@ void test_pipe(void)
|
|||
}
|
||||
if (FD_ISSET(fds[1], &wfds)) {
|
||||
ch = 'a';
|
||||
chk_error(write(fds[0], &ch, 1));
|
||||
chk_error(write(fds[1], &ch, 1));
|
||||
wcount++;
|
||||
}
|
||||
}
|
||||
|
@ -391,10 +368,10 @@ void test_pipe(void)
|
|||
chk_error(close(fds[1]));
|
||||
}
|
||||
|
||||
int thread1_res;
|
||||
int thread2_res;
|
||||
static int thread1_res;
|
||||
static int thread2_res;
|
||||
|
||||
int thread1_func(void *arg)
|
||||
static int thread1_func(void *arg)
|
||||
{
|
||||
int i;
|
||||
for(i=0;i<5;i++) {
|
||||
|
@ -404,7 +381,7 @@ int thread1_func(void *arg)
|
|||
return 0;
|
||||
}
|
||||
|
||||
int thread2_func(void *arg)
|
||||
static int thread2_func(void *arg)
|
||||
{
|
||||
int i;
|
||||
for(i=0;i<6;i++) {
|
||||
|
@ -414,23 +391,37 @@ int thread2_func(void *arg)
|
|||
return 0;
|
||||
}
|
||||
|
||||
void test_clone(void)
|
||||
static void wait_for_child(pid_t pid)
|
||||
{
|
||||
int status;
|
||||
chk_error(waitpid(pid, &status, 0));
|
||||
}
|
||||
|
||||
/* For test_clone we must match the clone flags used by glibc, see
|
||||
* CLONE_THREAD_FLAGS in the QEMU source code.
|
||||
*/
|
||||
static void test_clone(void)
|
||||
{
|
||||
uint8_t *stack1, *stack2;
|
||||
int pid1, pid2, status1, status2;
|
||||
pid_t pid1, pid2;
|
||||
|
||||
stack1 = malloc(STACK_SIZE);
|
||||
pid1 = chk_error(clone(thread1_func, stack1 + STACK_SIZE,
|
||||
CLONE_VM | CLONE_FS | CLONE_FILES | SIGCHLD, "hello1"));
|
||||
CLONE_VM | CLONE_FS | CLONE_FILES |
|
||||
CLONE_SIGHAND | CLONE_THREAD | CLONE_SYSVSEM,
|
||||
"hello1"));
|
||||
|
||||
stack2 = malloc(STACK_SIZE);
|
||||
pid2 = chk_error(clone(thread2_func, stack2 + STACK_SIZE,
|
||||
CLONE_VM | CLONE_FS | CLONE_FILES | SIGCHLD, "hello2"));
|
||||
CLONE_VM | CLONE_FS | CLONE_FILES |
|
||||
CLONE_SIGHAND | CLONE_THREAD | CLONE_SYSVSEM,
|
||||
"hello2"));
|
||||
|
||||
while (waitpid(pid1, &status1, 0) != pid1);
|
||||
wait_for_child(pid1);
|
||||
free(stack1);
|
||||
while (waitpid(pid2, &status2, 0) != pid2);
|
||||
wait_for_child(pid2);
|
||||
free(stack2);
|
||||
|
||||
if (thread1_res != 5 ||
|
||||
thread2_res != 6)
|
||||
error("clone");
|
||||
|
@ -441,21 +432,21 @@ void test_clone(void)
|
|||
volatile int alarm_count;
|
||||
jmp_buf jmp_env;
|
||||
|
||||
void sig_alarm(int sig)
|
||||
static void sig_alarm(int sig)
|
||||
{
|
||||
if (sig != SIGALRM)
|
||||
error("signal");
|
||||
alarm_count++;
|
||||
}
|
||||
|
||||
void sig_segv(int sig, siginfo_t *info, void *puc)
|
||||
static void sig_segv(int sig, siginfo_t *info, void *puc)
|
||||
{
|
||||
if (sig != SIGSEGV)
|
||||
error("signal");
|
||||
longjmp(jmp_env, 1);
|
||||
}
|
||||
|
||||
void test_signal(void)
|
||||
static void test_signal(void)
|
||||
{
|
||||
struct sigaction act;
|
||||
struct itimerval it, oit;
|
||||
|
@ -475,12 +466,10 @@ void test_signal(void)
|
|||
it.it_value.tv_usec = 10 * 1000;
|
||||
chk_error(setitimer(ITIMER_REAL, &it, NULL));
|
||||
chk_error(getitimer(ITIMER_REAL, &oit));
|
||||
if (oit.it_value.tv_sec != it.it_value.tv_sec ||
|
||||
oit.it_value.tv_usec != it.it_value.tv_usec)
|
||||
error("itimer");
|
||||
|
||||
while (alarm_count < 5) {
|
||||
usleep(10 * 1000);
|
||||
getitimer(ITIMER_REAL, &oit);
|
||||
}
|
||||
|
||||
it.it_interval.tv_sec = 0;
|
||||
|
@ -489,9 +478,6 @@ void test_signal(void)
|
|||
it.it_value.tv_usec = 0;
|
||||
memset(&oit, 0xff, sizeof(oit));
|
||||
chk_error(setitimer(ITIMER_REAL, &it, &oit));
|
||||
if (oit.it_value.tv_sec != 0 ||
|
||||
oit.it_value.tv_usec != 10 * 1000)
|
||||
error("setitimer");
|
||||
|
||||
/* SIGSEGV test */
|
||||
act.sa_sigaction = sig_segv;
|
||||
|
@ -510,7 +496,7 @@ void test_signal(void)
|
|||
|
||||
#define SHM_SIZE 32768
|
||||
|
||||
void test_shm(void)
|
||||
static void test_shm(void)
|
||||
{
|
||||
void *ptr;
|
||||
int shmid;
|
||||
|
@ -529,10 +515,16 @@ void test_shm(void)
|
|||
int main(int argc, char **argv)
|
||||
{
|
||||
test_file();
|
||||
test_pipe();
|
||||
test_fork();
|
||||
test_time();
|
||||
test_socket();
|
||||
// test_clone();
|
||||
|
||||
if (argc > 1) {
|
||||
printf("test_clone still considered buggy\n");
|
||||
test_clone();
|
||||
}
|
||||
|
||||
test_signal();
|
||||
test_shm();
|
||||
return 0;
|
|
@ -57,7 +57,7 @@ void check_aligned_anonymous_unfixed_mmaps(void)
|
|||
uintptr_t p;
|
||||
int i;
|
||||
|
||||
fprintf (stderr, "%s", __func__);
|
||||
fprintf(stdout, "%s", __func__);
|
||||
for (i = 0; i < 0x1fff; i++)
|
||||
{
|
||||
size_t len;
|
||||
|
@ -106,7 +106,7 @@ void check_aligned_anonymous_unfixed_mmaps(void)
|
|||
munmap (p4, len);
|
||||
munmap (p5, len);
|
||||
}
|
||||
fprintf (stderr, " passed\n");
|
||||
fprintf(stdout, " passed\n");
|
||||
}
|
||||
|
||||
void check_large_anonymous_unfixed_mmap(void)
|
||||
|
@ -115,7 +115,7 @@ void check_large_anonymous_unfixed_mmap(void)
|
|||
uintptr_t p;
|
||||
size_t len;
|
||||
|
||||
fprintf (stderr, "%s", __func__);
|
||||
fprintf(stdout, "%s", __func__);
|
||||
|
||||
len = 0x02000000;
|
||||
p1 = mmap(NULL, len, PROT_READ,
|
||||
|
@ -130,7 +130,7 @@ void check_large_anonymous_unfixed_mmap(void)
|
|||
/* Make sure we can read from the entire area. */
|
||||
memcpy (dummybuf, p1, pagesize);
|
||||
munmap (p1, len);
|
||||
fprintf (stderr, " passed\n");
|
||||
fprintf(stdout, " passed\n");
|
||||
}
|
||||
|
||||
void check_aligned_anonymous_unfixed_colliding_mmaps(void)
|
||||
|
@ -141,7 +141,7 @@ void check_aligned_anonymous_unfixed_colliding_mmaps(void)
|
|||
uintptr_t p;
|
||||
int i;
|
||||
|
||||
fprintf (stderr, "%s", __func__);
|
||||
fprintf(stdout, "%s", __func__);
|
||||
for (i = 0; i < 0x2fff; i++)
|
||||
{
|
||||
int nlen;
|
||||
|
@ -180,7 +180,7 @@ void check_aligned_anonymous_unfixed_colliding_mmaps(void)
|
|||
munmap (p2, pagesize);
|
||||
munmap (p3, nlen);
|
||||
}
|
||||
fprintf (stderr, " passed\n");
|
||||
fprintf(stdout, " passed\n");
|
||||
}
|
||||
|
||||
void check_aligned_anonymous_fixed_mmaps(void)
|
||||
|
@ -194,7 +194,7 @@ void check_aligned_anonymous_fixed_mmaps(void)
|
|||
addr = mmap(NULL, pagesize * 40, PROT_READ | PROT_WRITE,
|
||||
MAP_PRIVATE | MAP_ANONYMOUS,
|
||||
-1, 0);
|
||||
fprintf (stderr, "%s addr=%p", __func__, addr);
|
||||
fprintf(stdout, "%s addr=%p", __func__, addr);
|
||||
fail_unless (addr != MAP_FAILED);
|
||||
|
||||
for (i = 0; i < 40; i++)
|
||||
|
@ -212,7 +212,7 @@ void check_aligned_anonymous_fixed_mmaps(void)
|
|||
munmap (p1, pagesize);
|
||||
addr += pagesize;
|
||||
}
|
||||
fprintf (stderr, " passed\n");
|
||||
fprintf(stdout, " passed\n");
|
||||
}
|
||||
|
||||
void check_aligned_anonymous_fixed_mmaps_collide_with_host(void)
|
||||
|
@ -225,8 +225,8 @@ void check_aligned_anonymous_fixed_mmaps_collide_with_host(void)
|
|||
/* Find a suitable address to start with. Right were the x86 hosts
|
||||
stack is. */
|
||||
addr = ((void *)0x80000000);
|
||||
fprintf (stderr, "%s addr=%p", __func__, addr);
|
||||
fprintf (stderr, "FIXME: QEMU fails to track pages used by the host.");
|
||||
fprintf(stdout, "%s addr=%p", __func__, addr);
|
||||
fprintf(stdout, "FIXME: QEMU fails to track pages used by the host.");
|
||||
|
||||
for (i = 0; i < 20; i++)
|
||||
{
|
||||
|
@ -243,7 +243,7 @@ void check_aligned_anonymous_fixed_mmaps_collide_with_host(void)
|
|||
munmap (p1, pagesize);
|
||||
addr += pagesize;
|
||||
}
|
||||
fprintf (stderr, " passed\n");
|
||||
fprintf(stdout, " passed\n");
|
||||
}
|
||||
|
||||
void check_file_unfixed_mmaps(void)
|
||||
|
@ -252,7 +252,7 @@ void check_file_unfixed_mmaps(void)
|
|||
uintptr_t p;
|
||||
int i;
|
||||
|
||||
fprintf (stderr, "%s", __func__);
|
||||
fprintf(stdout, "%s", __func__);
|
||||
for (i = 0; i < 0x10; i++)
|
||||
{
|
||||
size_t len;
|
||||
|
@ -294,7 +294,7 @@ void check_file_unfixed_mmaps(void)
|
|||
munmap (p2, len);
|
||||
munmap (p3, len);
|
||||
}
|
||||
fprintf (stderr, " passed\n");
|
||||
fprintf(stdout, " passed\n");
|
||||
}
|
||||
|
||||
void check_file_unfixed_eof_mmaps(void)
|
||||
|
@ -304,7 +304,7 @@ void check_file_unfixed_eof_mmaps(void)
|
|||
uintptr_t p;
|
||||
int i;
|
||||
|
||||
fprintf (stderr, "%s", __func__);
|
||||
fprintf(stdout, "%s", __func__);
|
||||
for (i = 0; i < 0x10; i++)
|
||||
{
|
||||
p1 = mmap(NULL, pagesize, PROT_READ,
|
||||
|
@ -327,7 +327,7 @@ void check_file_unfixed_eof_mmaps(void)
|
|||
fail_unless (cp[pagesize - 4] == 0);
|
||||
munmap (p1, pagesize);
|
||||
}
|
||||
fprintf (stderr, " passed\n");
|
||||
fprintf(stdout, " passed\n");
|
||||
}
|
||||
|
||||
void check_file_fixed_eof_mmaps(void)
|
||||
|
@ -343,7 +343,7 @@ void check_file_fixed_eof_mmaps(void)
|
|||
MAP_PRIVATE | MAP_ANONYMOUS,
|
||||
-1, 0);
|
||||
|
||||
fprintf (stderr, "%s addr=%p", __func__, (void *)addr);
|
||||
fprintf(stdout, "%s addr=%p", __func__, (void *)addr);
|
||||
fail_unless (addr != MAP_FAILED);
|
||||
|
||||
for (i = 0; i < 0x10; i++)
|
||||
|
@ -371,7 +371,7 @@ void check_file_fixed_eof_mmaps(void)
|
|||
munmap (p1, pagesize);
|
||||
addr += pagesize;
|
||||
}
|
||||
fprintf (stderr, " passed\n");
|
||||
fprintf(stdout, " passed\n");
|
||||
}
|
||||
|
||||
void check_file_fixed_mmaps(void)
|
||||
|
@ -384,7 +384,7 @@ void check_file_fixed_mmaps(void)
|
|||
addr = mmap(NULL, pagesize * 40 * 4, PROT_READ,
|
||||
MAP_PRIVATE | MAP_ANONYMOUS,
|
||||
-1, 0);
|
||||
fprintf (stderr, "%s addr=%p", __func__, (void *)addr);
|
||||
fprintf(stdout, "%s addr=%p", __func__, (void *)addr);
|
||||
fail_unless (addr != MAP_FAILED);
|
||||
|
||||
for (i = 0; i < 40; i++)
|
||||
|
@ -426,7 +426,7 @@ void check_file_fixed_mmaps(void)
|
|||
munmap (p4, pagesize);
|
||||
addr += pagesize * 4;
|
||||
}
|
||||
fprintf (stderr, " passed\n");
|
||||
fprintf(stdout, " passed\n");
|
||||
}
|
||||
|
||||
void checked_write(int fd, const void *buf, size_t count)
|
7
tests/tcg/ppc/Makefile.include
Normal file
7
tests/tcg/ppc/Makefile.include
Normal file
|
@ -0,0 +1,7 @@
|
|||
ifeq ($(TARGET_NAME),ppc)
|
||||
DOCKER_IMAGE=debian-powerpc-cross
|
||||
DOCKER_CROSS_COMPILER=powerpc-linux-gnu-gcc
|
||||
else ifeq ($(TARGET_NAME),ppc64le)
|
||||
DOCKER_IMAGE=debian-ppc64el-cross
|
||||
DOCKER_CROSS_COMPILER=powerpc64le-linux-gnu-gcc
|
||||
endif
|
12
tests/tcg/ppc/Makefile.target
Normal file
12
tests/tcg/ppc/Makefile.target
Normal file
|
@ -0,0 +1,12 @@
|
|||
# -*- Mode: makefile -*-
|
||||
#
|
||||
# PPC - included from tests/tcg/Makefile
|
||||
#
|
||||
|
||||
ifneq (,$(findstring 64,$(TARGET_NAME)))
|
||||
# On PPC64 Linux can be configured with 4k (default) or 64k pages (currently broken)
|
||||
EXTRA_RUNS+=run-test-mmap-4096 #run-test-mmap-65536
|
||||
else
|
||||
# On PPC32 Linux supports 4K/16K/64K/256K (but currently only 4k works)
|
||||
EXTRA_RUNS+=run-test-mmap-4096 #run-test-mmap-16384 run-test-mmap-65536 run-test-mmap-262144
|
||||
endif
|
10
tests/tcg/riscv/Makefile.include
Normal file
10
tests/tcg/riscv/Makefile.include
Normal file
|
@ -0,0 +1,10 @@
|
|||
#
|
||||
# Makefile.include for all RISCV targets
|
||||
#
|
||||
# Debian only really cares about 64 bit going forward
|
||||
#
|
||||
|
||||
ifeq ($(TARGET_NAME),riscv64)
|
||||
DOCKER_IMAGE=debian-riscv64-cross
|
||||
DOCKER_CROSS_COMPILER=riscv64-linux-gnu-gcc
|
||||
endif
|
2
tests/tcg/s390x/Makefile.include
Normal file
2
tests/tcg/s390x/Makefile.include
Normal file
|
@ -0,0 +1,2 @@
|
|||
DOCKER_IMAGE=debian-s390x-cross
|
||||
DOCKER_CROSS_COMPILER=s390x-linux-gnu-gcc
|
4
tests/tcg/sh4/Makefile.include
Normal file
4
tests/tcg/sh4/Makefile.include
Normal file
|
@ -0,0 +1,4 @@
|
|||
ifneq ($(TARGET_NAME), sh4eb)
|
||||
DOCKER_IMAGE=debian-sh4-cross
|
||||
DOCKER_CROSS_COMPILER=sh4-linux-gnu-gcc
|
||||
endif
|
7
tests/tcg/sh4/Makefile.target
Normal file
7
tests/tcg/sh4/Makefile.target
Normal file
|
@ -0,0 +1,7 @@
|
|||
# -*- Mode: makefile -*-
|
||||
#
|
||||
# SuperH specific tweaks
|
||||
#
|
||||
|
||||
# On sh Linux supports 4k, 8k, 16k and 64k pages (but only 4k currently works)
|
||||
EXTRA_RUNS+=run-test-mmap-4096 # run-test-mmap-8192 run-test-mmap-16384 run-test-mmap-65536
|
2
tests/tcg/sparc64/Makefile.include
Normal file
2
tests/tcg/sparc64/Makefile.include
Normal file
|
@ -0,0 +1,2 @@
|
|||
DOCKER_IMAGE=debian-sparc64-cross
|
||||
DOCKER_CROSS_COMPILER=sparc64-linux-gnu-gcc
|
11
tests/tcg/sparc64/Makefile.target
Normal file
11
tests/tcg/sparc64/Makefile.target
Normal file
|
@ -0,0 +1,11 @@
|
|||
# -*- Mode: makefile -*-
|
||||
#
|
||||
# sparc specific tweaks and masking out broken tests
|
||||
|
||||
# different from the other hangs:
|
||||
# tests/tcg/multiarch/linux-test.c:264: Value too large for defined data type (ret=-1, errno=92/Value too large for defined data type)
|
||||
run-linux-test: linux-test
|
||||
$(call skip-test, $<, "BROKEN")
|
||||
|
||||
# On Sparc64 Linux support 8k pages
|
||||
EXTRA_RUNS+=run-test-mmap-8192
|
|
@ -1,157 +0,0 @@
|
|||
/* Test path override code */
|
||||
#include "config-host.h"
|
||||
#include "util/cutils.c"
|
||||
#include "util/hexdump.c"
|
||||
#include "util/iov.c"
|
||||
#include "util/path.c"
|
||||
#include "util/qemu-timer-common.c"
|
||||
#include <stdarg.h>
|
||||
#include <sys/stat.h>
|
||||
#include <fcntl.h>
|
||||
|
||||
void qemu_log(const char *fmt, ...);
|
||||
|
||||
/* Any log message kills the test. */
|
||||
void qemu_log(const char *fmt, ...)
|
||||
{
|
||||
va_list ap;
|
||||
|
||||
fprintf(stderr, "FATAL: ");
|
||||
va_start(ap, fmt);
|
||||
vfprintf(stderr, fmt, ap);
|
||||
va_end(ap);
|
||||
exit(1);
|
||||
}
|
||||
|
||||
#define NO_CHANGE(_path) \
|
||||
do { \
|
||||
if (strcmp(path(_path), _path) != 0) return __LINE__; \
|
||||
} while(0)
|
||||
|
||||
#define CHANGE_TO(_path, _newpath) \
|
||||
do { \
|
||||
if (strcmp(path(_path), _newpath) != 0) return __LINE__; \
|
||||
} while(0)
|
||||
|
||||
static void cleanup(void)
|
||||
{
|
||||
unlink("/tmp/qemu-test_path/DIR1/DIR2/FILE");
|
||||
unlink("/tmp/qemu-test_path/DIR1/DIR2/FILE2");
|
||||
unlink("/tmp/qemu-test_path/DIR1/DIR2/FILE3");
|
||||
unlink("/tmp/qemu-test_path/DIR1/DIR2/FILE4");
|
||||
unlink("/tmp/qemu-test_path/DIR1/DIR2/FILE5");
|
||||
rmdir("/tmp/qemu-test_path/DIR1/DIR2");
|
||||
rmdir("/tmp/qemu-test_path/DIR1/DIR3");
|
||||
rmdir("/tmp/qemu-test_path/DIR1");
|
||||
rmdir("/tmp/qemu-test_path");
|
||||
}
|
||||
|
||||
static unsigned int do_test(void)
|
||||
{
|
||||
if (mkdir("/tmp/qemu-test_path", 0700) != 0)
|
||||
return __LINE__;
|
||||
|
||||
if (mkdir("/tmp/qemu-test_path/DIR1", 0700) != 0)
|
||||
return __LINE__;
|
||||
|
||||
if (mkdir("/tmp/qemu-test_path/DIR1/DIR2", 0700) != 0)
|
||||
return __LINE__;
|
||||
|
||||
if (mkdir("/tmp/qemu-test_path/DIR1/DIR3", 0700) != 0)
|
||||
return __LINE__;
|
||||
|
||||
if (close(creat("/tmp/qemu-test_path/DIR1/DIR2/FILE", 0600)) != 0)
|
||||
return __LINE__;
|
||||
|
||||
if (close(creat("/tmp/qemu-test_path/DIR1/DIR2/FILE2", 0600)) != 0)
|
||||
return __LINE__;
|
||||
|
||||
if (close(creat("/tmp/qemu-test_path/DIR1/DIR2/FILE3", 0600)) != 0)
|
||||
return __LINE__;
|
||||
|
||||
if (close(creat("/tmp/qemu-test_path/DIR1/DIR2/FILE4", 0600)) != 0)
|
||||
return __LINE__;
|
||||
|
||||
if (close(creat("/tmp/qemu-test_path/DIR1/DIR2/FILE5", 0600)) != 0)
|
||||
return __LINE__;
|
||||
|
||||
init_paths("/tmp/qemu-test_path");
|
||||
|
||||
NO_CHANGE("/tmp");
|
||||
NO_CHANGE("/tmp/");
|
||||
NO_CHANGE("/tmp/qemu-test_path");
|
||||
NO_CHANGE("/tmp/qemu-test_path/");
|
||||
NO_CHANGE("/tmp/qemu-test_path/D");
|
||||
NO_CHANGE("/tmp/qemu-test_path/DI");
|
||||
NO_CHANGE("/tmp/qemu-test_path/DIR");
|
||||
NO_CHANGE("/tmp/qemu-test_path/DIR1");
|
||||
NO_CHANGE("/tmp/qemu-test_path/DIR1/");
|
||||
|
||||
NO_CHANGE("/D");
|
||||
NO_CHANGE("/DI");
|
||||
NO_CHANGE("/DIR");
|
||||
NO_CHANGE("/DIR2");
|
||||
NO_CHANGE("/DIR1.");
|
||||
|
||||
CHANGE_TO("/DIR1", "/tmp/qemu-test_path/DIR1");
|
||||
CHANGE_TO("/DIR1/", "/tmp/qemu-test_path/DIR1");
|
||||
|
||||
NO_CHANGE("/DIR1/D");
|
||||
NO_CHANGE("/DIR1/DI");
|
||||
NO_CHANGE("/DIR1/DIR");
|
||||
NO_CHANGE("/DIR1/DIR1");
|
||||
|
||||
CHANGE_TO("/DIR1/DIR2", "/tmp/qemu-test_path/DIR1/DIR2");
|
||||
CHANGE_TO("/DIR1/DIR2/", "/tmp/qemu-test_path/DIR1/DIR2");
|
||||
|
||||
CHANGE_TO("/DIR1/DIR3", "/tmp/qemu-test_path/DIR1/DIR3");
|
||||
CHANGE_TO("/DIR1/DIR3/", "/tmp/qemu-test_path/DIR1/DIR3");
|
||||
|
||||
NO_CHANGE("/DIR1/DIR2/F");
|
||||
NO_CHANGE("/DIR1/DIR2/FI");
|
||||
NO_CHANGE("/DIR1/DIR2/FIL");
|
||||
NO_CHANGE("/DIR1/DIR2/FIL.");
|
||||
|
||||
CHANGE_TO("/DIR1/DIR2/FILE", "/tmp/qemu-test_path/DIR1/DIR2/FILE");
|
||||
CHANGE_TO("/DIR1/DIR2/FILE2", "/tmp/qemu-test_path/DIR1/DIR2/FILE2");
|
||||
CHANGE_TO("/DIR1/DIR2/FILE3", "/tmp/qemu-test_path/DIR1/DIR2/FILE3");
|
||||
CHANGE_TO("/DIR1/DIR2/FILE4", "/tmp/qemu-test_path/DIR1/DIR2/FILE4");
|
||||
CHANGE_TO("/DIR1/DIR2/FILE5", "/tmp/qemu-test_path/DIR1/DIR2/FILE5");
|
||||
|
||||
NO_CHANGE("/DIR1/DIR2/FILE6");
|
||||
NO_CHANGE("/DIR1/DIR2/FILE/X");
|
||||
|
||||
CHANGE_TO("/DIR1/../DIR1", "/tmp/qemu-test_path/DIR1");
|
||||
CHANGE_TO("/DIR1/../DIR1/", "/tmp/qemu-test_path/DIR1");
|
||||
CHANGE_TO("/../DIR1", "/tmp/qemu-test_path/DIR1");
|
||||
CHANGE_TO("/../DIR1/", "/tmp/qemu-test_path/DIR1");
|
||||
CHANGE_TO("/DIR1/DIR2/../DIR2", "/tmp/qemu-test_path/DIR1/DIR2");
|
||||
CHANGE_TO("/DIR1/DIR2/../DIR2/../../DIR1/DIR2/FILE", "/tmp/qemu-test_path/DIR1/DIR2/FILE");
|
||||
CHANGE_TO("/DIR1/DIR2/../DIR2/FILE", "/tmp/qemu-test_path/DIR1/DIR2/FILE");
|
||||
|
||||
NO_CHANGE("/DIR1/DIR2/../DIR1");
|
||||
NO_CHANGE("/DIR1/DIR2/../FILE");
|
||||
|
||||
CHANGE_TO("/./DIR1/DIR2/FILE", "/tmp/qemu-test_path/DIR1/DIR2/FILE");
|
||||
CHANGE_TO("/././DIR1/DIR2/FILE", "/tmp/qemu-test_path/DIR1/DIR2/FILE");
|
||||
CHANGE_TO("/DIR1/./DIR2/FILE", "/tmp/qemu-test_path/DIR1/DIR2/FILE");
|
||||
CHANGE_TO("/DIR1/././DIR2/FILE", "/tmp/qemu-test_path/DIR1/DIR2/FILE");
|
||||
CHANGE_TO("/DIR1/DIR2/./FILE", "/tmp/qemu-test_path/DIR1/DIR2/FILE");
|
||||
CHANGE_TO("/DIR1/DIR2/././FILE", "/tmp/qemu-test_path/DIR1/DIR2/FILE");
|
||||
CHANGE_TO("/./DIR1/./DIR2/./FILE", "/tmp/qemu-test_path/DIR1/DIR2/FILE");
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
int ret;
|
||||
|
||||
ret = do_test();
|
||||
cleanup();
|
||||
if (ret) {
|
||||
fprintf(stderr, "test_path: failed on line %i\n", ret);
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
15
tests/tcg/x86_64/Makefile.target
Normal file
15
tests/tcg/x86_64/Makefile.target
Normal file
|
@ -0,0 +1,15 @@
|
|||
# -*- Mode: makefile -*-
|
||||
#
|
||||
# x86_64 tests - included from tests/tcg/Makefile.target
|
||||
#
|
||||
# Currently we only build test-x86_64 and test-i386-ssse3 from
|
||||
# $(SRC)/tests/tcg/i386/
|
||||
#
|
||||
|
||||
X86_64_TESTS=$(filter-out $(I386_ONLY_TESTS), $(TESTS))
|
||||
X86_64_TESTS+=test-x86_64
|
||||
TESTS:=$(X86_64_TESTS)
|
||||
|
||||
test-x86_64: LDFLAGS+=-lm -lc
|
||||
test-x86_64: test-i386.c test-i386.h test-i386-shift.h test-i386-muldiv.h
|
||||
$(CC) $(CFLAGS) $< -o $@ $(LDFLAGS)
|
Loading…
Reference in a new issue