testing, gdbstub and plugin updates

- update MAINTAINERS with pointers to foo/next
   - add NOFETCH to help test custom docker builds
   - update microblaze toolchain with atomic fixes
   - update tsan build and documentation
   - don't restrict build-environment by arch unless needed
   - add cross-modifying code test
   - add tracepoints for cpu_step_atomic fallbacks
   - fix defaults for loongarch cross build
   - make check-[dco|patch] a little more verbose
   - fix gdbstub bug preventing aarch64_be-linux-user starting
   - add basic test for aarch64_be
   - clean up some gdbstub test scripts
   - fix qemu_plugin_reset
 -----BEGIN PGP SIGNATURE-----
 
 iQEzBAABCgAdFiEEZoWumedRZ7yvyN81+9DbCVqeKkQFAmcaDeQACgkQ+9DbCVqe
 KkRTlQgAlFaP1Nxa8y6pRZSL0WY9J3Znf5e2GDnVN3nJbfx1wZg7oZ4/dWieDF/Y
 /9jLfMi8nDJ51tzH24PSASbHQ1xnblhuUfhRMwqAFhSwsZUb0VzdeGdq+FIyXQ5w
 Cy2Ubz7g81qP/x9JRCCUGFfXaM1LSizsY1lNioRsDd533WJLkvxWucmpSN3XhxHJ
 rEa3xI/qAcUah4G3yww47L+DmlKnJQcsihShRBC6Am2tWqxbz+1kBUaVfaVVo1if
 IPN+bBk4eI1EHdRRyWJSsq3nELzqW4FJ3+9V0ifsOFW2KGsnkhbl0qUxqDmW5aBb
 P9flEdpTfSiCbqp+IKG9vxJKuf/BGw==
 =5Wui
 -----END PGP SIGNATURE-----

Merge tag 'pull-maintainer-oct-misc-241024-1' of https://gitlab.com/stsquad/qemu into staging

testing, gdbstub and plugin updates

  - update MAINTAINERS with pointers to foo/next
  - add NOFETCH to help test custom docker builds
  - update microblaze toolchain with atomic fixes
  - update tsan build and documentation
  - don't restrict build-environment by arch unless needed
  - add cross-modifying code test
  - add tracepoints for cpu_step_atomic fallbacks
  - fix defaults for loongarch cross build
  - make check-[dco|patch] a little more verbose
  - fix gdbstub bug preventing aarch64_be-linux-user starting
  - add basic test for aarch64_be
  - clean up some gdbstub test scripts
  - fix qemu_plugin_reset

# -----BEGIN PGP SIGNATURE-----
#
# iQEzBAABCgAdFiEEZoWumedRZ7yvyN81+9DbCVqeKkQFAmcaDeQACgkQ+9DbCVqe
# KkRTlQgAlFaP1Nxa8y6pRZSL0WY9J3Znf5e2GDnVN3nJbfx1wZg7oZ4/dWieDF/Y
# /9jLfMi8nDJ51tzH24PSASbHQ1xnblhuUfhRMwqAFhSwsZUb0VzdeGdq+FIyXQ5w
# Cy2Ubz7g81qP/x9JRCCUGFfXaM1LSizsY1lNioRsDd533WJLkvxWucmpSN3XhxHJ
# rEa3xI/qAcUah4G3yww47L+DmlKnJQcsihShRBC6Am2tWqxbz+1kBUaVfaVVo1if
# IPN+bBk4eI1EHdRRyWJSsq3nELzqW4FJ3+9V0ifsOFW2KGsnkhbl0qUxqDmW5aBb
# P9flEdpTfSiCbqp+IKG9vxJKuf/BGw==
# =5Wui
# -----END PGP SIGNATURE-----
# gpg: Signature made Thu 24 Oct 2024 10:05:40 BST
# gpg:                using RSA key 6685AE99E75167BCAFC8DF35FBD0DB095A9E2A44
# gpg: Good signature from "Alex Bennée (Master Work Key) <alex.bennee@linaro.org>" [full]
# Primary key fingerprint: 6685 AE99 E751 67BC AFC8  DF35 FBD0 DB09 5A9E 2A44

* tag 'pull-maintainer-oct-misc-241024-1' of https://gitlab.com/stsquad/qemu:
  plugins: fix qemu_plugin_reset
  MAINTAINERS: mention my plugins/next tree
  testing: Enhance gdb probe script
  tests/tcg/aarch64: Use raw strings for regexes in test-mte.py
  tests/tcg: enable basic testing for aarch64_be-linux-user
  config/targets: update aarch64_be-linux-user gdb XML list
  MAINTAINERS: mention my gdbstub/next tree
  gitlab: make check-[dco|patch] a little more verbose
  dockerfiles: fix default targets for debian-loongarch-cross
  accel/tcg: add tracepoints for cpu_loop_exit_atomic
  tests/tcg/x86_64: Add cross-modifying code test
  scripts/ci: remove architecture checks for build-environment updates
  docs/devel: update tsan build documentation
  meson: hide tsan related warnings
  MAINTAINERS: mention my testing/next tree
  tests/docker: add NOFETCH env variable for testing
  tests/docker: Fix microblaze atomics

Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
This commit is contained in:
Peter Maydell 2024-10-25 19:12:06 +01:00
commit fdf250e5a3
23 changed files with 273 additions and 58 deletions

View File

@ -19,10 +19,9 @@ cwd = os.getcwd()
reponame = os.path.basename(cwd) reponame = os.path.basename(cwd)
repourl = "https://gitlab.com/%s/%s.git" % (namespace, reponame) repourl = "https://gitlab.com/%s/%s.git" % (namespace, reponame)
print(f"adding upstream git repo @ {repourl}")
subprocess.check_call(["git", "remote", "add", "check-dco", repourl]) subprocess.check_call(["git", "remote", "add", "check-dco", repourl])
subprocess.check_call(["git", "fetch", "check-dco", "master"], subprocess.check_call(["git", "fetch", "check-dco", "master"])
stdout=subprocess.DEVNULL,
stderr=subprocess.DEVNULL)
ancestor = subprocess.check_output(["git", "merge-base", ancestor = subprocess.check_output(["git", "merge-base",
"check-dco/master", "HEAD"], "check-dco/master", "HEAD"],

View File

@ -19,13 +19,12 @@ cwd = os.getcwd()
reponame = os.path.basename(cwd) reponame = os.path.basename(cwd)
repourl = "https://gitlab.com/%s/%s.git" % (namespace, reponame) repourl = "https://gitlab.com/%s/%s.git" % (namespace, reponame)
print(f"adding upstream git repo @ {repourl}")
# GitLab CI environment does not give us any direct info about the # GitLab CI environment does not give us any direct info about the
# base for the user's branch. We thus need to figure out a common # base for the user's branch. We thus need to figure out a common
# ancestor between the user's branch and current git master. # ancestor between the user's branch and current git master.
subprocess.check_call(["git", "remote", "add", "check-patch", repourl]) subprocess.check_call(["git", "remote", "add", "check-patch", repourl])
subprocess.check_call(["git", "fetch", "check-patch", "master"], subprocess.check_call(["git", "fetch", "check-patch", "master"])
stdout=subprocess.DEVNULL,
stderr=subprocess.DEVNULL)
ancestor = subprocess.check_output(["git", "merge-base", ancestor = subprocess.check_output(["git", "merge-base",
"check-patch/master", "HEAD"], "check-patch/master", "HEAD"],

View File

@ -2985,6 +2985,7 @@ F: gdb-xml/
F: tests/tcg/multiarch/gdbstub/* F: tests/tcg/multiarch/gdbstub/*
F: scripts/feature_to_c.py F: scripts/feature_to_c.py
F: scripts/probe-gdb-support.py F: scripts/probe-gdb-support.py
T: git https://gitlab.com/stsquad/qemu gdbstub/next
Memory API Memory API
M: Paolo Bonzini <pbonzini@redhat.com> M: Paolo Bonzini <pbonzini@redhat.com>
@ -3708,6 +3709,7 @@ F: include/tcg/
TCG Plugins TCG Plugins
M: Alex Bennée <alex.bennee@linaro.org> M: Alex Bennée <alex.bennee@linaro.org>
T: git https://gitlab.com/stsquad/qemu plugins/next
R: Alexandre Iooss <erdnaxe@crans.org> R: Alexandre Iooss <erdnaxe@crans.org>
R: Mahmoud Mandour <ma.mandourr@gmail.com> R: Mahmoud Mandour <ma.mandourr@gmail.com>
R: Pierrick Bouvier <pierrick.bouvier@linaro.org> R: Pierrick Bouvier <pierrick.bouvier@linaro.org>
@ -4081,6 +4083,7 @@ Build and test automation
------------------------- -------------------------
Build and test automation, general continuous integration Build and test automation, general continuous integration
M: Alex Bennée <alex.bennee@linaro.org> M: Alex Bennée <alex.bennee@linaro.org>
T: git https://gitlab.com/stsquad/qemu testing/next
M: Philippe Mathieu-Daudé <philmd@linaro.org> M: Philippe Mathieu-Daudé <philmd@linaro.org>
M: Thomas Huth <thuth@redhat.com> M: Thomas Huth <thuth@redhat.com>
R: Wainer dos Santos Moschetta <wainersm@redhat.com> R: Wainer dos Santos Moschetta <wainersm@redhat.com>

View File

@ -168,6 +168,7 @@ static uint64_t load_atomic8_or_exit(CPUState *cpu, uintptr_t ra, void *pv)
#endif #endif
/* Ultimate fallback: re-execute in serial context. */ /* Ultimate fallback: re-execute in serial context. */
trace_load_atom8_or_exit_fallback(ra);
cpu_loop_exit_atomic(cpu, ra); cpu_loop_exit_atomic(cpu, ra);
} }
@ -212,6 +213,7 @@ static Int128 load_atomic16_or_exit(CPUState *cpu, uintptr_t ra, void *pv)
} }
/* Ultimate fallback: re-execute in serial context. */ /* Ultimate fallback: re-execute in serial context. */
trace_load_atom16_or_exit_fallback(ra);
cpu_loop_exit_atomic(cpu, ra); cpu_loop_exit_atomic(cpu, ra);
} }
@ -519,6 +521,7 @@ static uint64_t load_atom_8(CPUState *cpu, uintptr_t ra,
if (HAVE_al8) { if (HAVE_al8) {
return load_atom_extract_al8x2(pv); return load_atom_extract_al8x2(pv);
} }
trace_load_atom8_fallback(memop, ra);
cpu_loop_exit_atomic(cpu, ra); cpu_loop_exit_atomic(cpu, ra);
default: default:
g_assert_not_reached(); g_assert_not_reached();
@ -563,6 +566,7 @@ static Int128 load_atom_16(CPUState *cpu, uintptr_t ra,
break; break;
case MO_64: case MO_64:
if (!HAVE_al8) { if (!HAVE_al8) {
trace_load_atom16_fallback(memop, ra);
cpu_loop_exit_atomic(cpu, ra); cpu_loop_exit_atomic(cpu, ra);
} }
a = load_atomic8(pv); a = load_atomic8(pv);
@ -570,6 +574,7 @@ static Int128 load_atom_16(CPUState *cpu, uintptr_t ra,
break; break;
case -MO_64: case -MO_64:
if (!HAVE_al8) { if (!HAVE_al8) {
trace_load_atom16_fallback(memop, ra);
cpu_loop_exit_atomic(cpu, ra); cpu_loop_exit_atomic(cpu, ra);
} }
a = load_atom_extract_al8x2(pv); a = load_atom_extract_al8x2(pv);
@ -897,6 +902,7 @@ static void store_atom_2(CPUState *cpu, uintptr_t ra,
g_assert_not_reached(); g_assert_not_reached();
} }
trace_store_atom2_fallback(memop, ra);
cpu_loop_exit_atomic(cpu, ra); cpu_loop_exit_atomic(cpu, ra);
} }
@ -961,6 +967,7 @@ static void store_atom_4(CPUState *cpu, uintptr_t ra,
return; return;
} }
} }
trace_store_atom4_fallback(memop, ra);
cpu_loop_exit_atomic(cpu, ra); cpu_loop_exit_atomic(cpu, ra);
default: default:
g_assert_not_reached(); g_assert_not_reached();
@ -1029,6 +1036,7 @@ static void store_atom_8(CPUState *cpu, uintptr_t ra,
default: default:
g_assert_not_reached(); g_assert_not_reached();
} }
trace_store_atom8_fallback(memop, ra);
cpu_loop_exit_atomic(cpu, ra); cpu_loop_exit_atomic(cpu, ra);
} }
@ -1107,5 +1115,6 @@ static void store_atom_16(CPUState *cpu, uintptr_t ra,
default: default:
g_assert_not_reached(); g_assert_not_reached();
} }
trace_store_atom16_fallback(memop, ra);
cpu_loop_exit_atomic(cpu, ra); cpu_loop_exit_atomic(cpu, ra);
} }

View File

@ -467,4 +467,8 @@ void plugin_gen_tb_end(CPUState *cpu, size_t num_insns)
/* inject the instrumentation at the appropriate places */ /* inject the instrumentation at the appropriate places */
plugin_gen_inject(ptb); plugin_gen_inject(ptb);
/* reset plugin translation state (plugin_tb is reused between blocks) */
tcg_ctx->plugin_db = NULL;
tcg_ctx->plugin_insn = NULL;
} }

View File

@ -12,3 +12,15 @@ memory_notdirty_set_dirty(uint64_t vaddr) "0x%" PRIx64
# translate-all.c # translate-all.c
translate_block(void *tb, uintptr_t pc, const void *tb_code) "tb:%p, pc:0x%"PRIxPTR", tb_code:%p" translate_block(void *tb, uintptr_t pc, const void *tb_code) "tb:%p, pc:0x%"PRIxPTR", tb_code:%p"
# ldst_atomicity
load_atom2_fallback(uint32_t memop, uintptr_t ra) "mop:0x%"PRIx32", ra:0x%"PRIxPTR""
load_atom4_fallback(uint32_t memop, uintptr_t ra) "mop:0x%"PRIx32", ra:0x%"PRIxPTR""
load_atom8_or_exit_fallback(uintptr_t ra) "ra:0x%"PRIxPTR""
load_atom8_fallback(uint32_t memop, uintptr_t ra) "mop:0x%"PRIx32", ra:0x%"PRIxPTR""
load_atom16_fallback(uint32_t memop, uintptr_t ra) "mop:0x%"PRIx32", ra:0x%"PRIxPTR""
load_atom16_or_exit_fallback(uintptr_t ra) "ra:0x%"PRIxPTR""
store_atom2_fallback(uint32_t memop, uintptr_t ra) "mop:0x%"PRIx32", ra:0x%"PRIxPTR""
store_atom4_fallback(uint32_t memop, uintptr_t ra) "mop:0x%"PRIx32", ra:0x%"PRIxPTR""
store_atom8_fallback(uint32_t memop, uintptr_t ra) "mop:0x%"PRIx32", ra:0x%"PRIxPTR""
store_atom16_fallback(uint32_t memop, uintptr_t ra) "mop:0x%"PRIx32", ra:0x%"PRIxPTR""

View File

@ -29,7 +29,7 @@
#include "exec/page-protection.h" #include "exec/page-protection.h"
#include "exec/helper-proto.h" #include "exec/helper-proto.h"
#include "qemu/atomic128.h" #include "qemu/atomic128.h"
#include "trace/trace-root.h" #include "trace.h"
#include "tcg/tcg-ldst.h" #include "tcg/tcg-ldst.h"
#include "internal-common.h" #include "internal-common.h"
#include "internal-target.h" #include "internal-target.h"

View File

@ -1,7 +1,7 @@
TARGET_ARCH=aarch64 TARGET_ARCH=aarch64
TARGET_BASE_ARCH=arm TARGET_BASE_ARCH=arm
TARGET_BIG_ENDIAN=y TARGET_BIG_ENDIAN=y
TARGET_XML_FILES= gdb-xml/aarch64-core.xml gdb-xml/aarch64-fpu.xml gdb-xml/aarch64-pauth.xml TARGET_XML_FILES= gdb-xml/aarch64-core.xml gdb-xml/aarch64-fpu.xml gdb-xml/aarch64-pauth.xml gdb-xml/aarch64-mte.xml
TARGET_HAS_BFLT=y TARGET_HAS_BFLT=y
CONFIG_SEMIHOSTING=y CONFIG_SEMIHOSTING=y
CONFIG_ARM_COMPATIBLE_SEMIHOSTING=y CONFIG_ARM_COMPATIBLE_SEMIHOSTING=y

5
configure vendored
View File

@ -1418,6 +1418,7 @@ probe_target_compiler() {
target_arch=${1%%-*} target_arch=${1%%-*}
case $target_arch in case $target_arch in
aarch64) container_hosts="x86_64 aarch64" ;; aarch64) container_hosts="x86_64 aarch64" ;;
aarch64_be) container_hosts="x86_64 aarch64" ;;
alpha) container_hosts=x86_64 ;; alpha) container_hosts=x86_64 ;;
arm) container_hosts="x86_64 aarch64" ;; arm) container_hosts="x86_64 aarch64" ;;
hexagon) container_hosts=x86_64 ;; hexagon) container_hosts=x86_64 ;;
@ -1447,6 +1448,10 @@ probe_target_compiler() {
case $target_arch in case $target_arch in
# debian-all-test-cross architectures # debian-all-test-cross architectures
aarch64_be)
container_image=debian-all-test-cross
container_cross_prefix=aarch64-linux-gnu-
;;
hppa|m68k|mips|riscv64|sparc64) hppa|m68k|mips|riscv64|sparc64)
container_image=debian-all-test-cross container_image=debian-all-test-cross
;; ;;

View File

@ -628,20 +628,38 @@ Building and Testing with TSan
It is possible to build and test with TSan, with a few additional steps. It is possible to build and test with TSan, with a few additional steps.
These steps are normally done automatically in the docker. These steps are normally done automatically in the docker.
There is a one time patch needed in clang-9 or clang-10 at this time: TSan is supported for clang and gcc.
One particularity of sanitizers is that all the code, including shared objects
dependencies, should be built with it.
In the case of TSan, any synchronization primitive from glib (GMutex for
instance) will not be recognized, and will lead to false positives.
To build a tsan version of glib:
.. code:: .. code::
sed -i 's/^const/static const/g' \ $ git clone --depth=1 --branch=2.81.0 https://github.com/GNOME/glib.git
/usr/lib/llvm-10/lib/clang/10.0.0/include/sanitizer/tsan_interface.h $ cd glib
$ CFLAGS="-O2 -g -fsanitize=thread" meson build
$ ninja -C build
To configure the build for TSan: To configure the build for TSan:
.. code:: .. code::
../configure --enable-tsan --cc=clang-10 --cxx=clang++-10 \ ../configure --enable-tsan \
--disable-werror --extra-cflags="-O0" --disable-werror --extra-cflags="-O0"
When executing qemu, don't forget to point to tsan glib:
.. code::
$ glib_dir=/path/to/glib
$ export LD_LIBRARY_PATH=$glib_dir/build/gio:$glib_dir/build/glib:$glib_dir/build/gmodule:$glib_dir/build/gobject:$glib_dir/build/gthread
# check correct version is used
$ ldd build/qemu-x86_64 | grep glib
$ qemu-system-x86_64 ...
The runtime behavior of TSAN is controlled by the TSAN_OPTIONS environment The runtime behavior of TSAN is controlled by the TSAN_OPTIONS environment
variable. variable.

View File

@ -538,7 +538,15 @@ if get_option('tsan')
prefix: '#include <sanitizer/tsan_interface.h>') prefix: '#include <sanitizer/tsan_interface.h>')
error('Cannot enable TSAN due to missing fiber annotation interface') error('Cannot enable TSAN due to missing fiber annotation interface')
endif endif
qemu_cflags = ['-fsanitize=thread'] + qemu_cflags tsan_warn_suppress = []
# gcc (>=11) will report constructions not supported by tsan:
# "error: atomic_thread_fence is not supported with -fsanitize=thread"
# https://gcc.gnu.org/gcc-11/changes.html
# However, clang does not support this warning and this triggers an error.
if cc.has_argument('-Wno-tsan')
tsan_warn_suppress = ['-Wno-tsan']
endif
qemu_cflags = ['-fsanitize=thread'] + tsan_warn_suppress + qemu_cflags
qemu_ldflags = ['-fsanitize=thread'] + qemu_ldflags qemu_ldflags = ['-fsanitize=thread'] + qemu_ldflags
endif endif

View File

@ -39,7 +39,6 @@
when: when:
- ansible_facts['distribution'] == 'Ubuntu' - ansible_facts['distribution'] == 'Ubuntu'
- ansible_facts['distribution_version'] == '22.04' - ansible_facts['distribution_version'] == '22.04'
- ansible_facts['architecture'] == 'aarch64' or ansible_facts['architecture'] == 'x86_64'
- name: Install packages for QEMU on Ubuntu 22.04 - name: Install packages for QEMU on Ubuntu 22.04
package: package:
@ -47,7 +46,6 @@
when: when:
- ansible_facts['distribution'] == 'Ubuntu' - ansible_facts['distribution'] == 'Ubuntu'
- ansible_facts['distribution_version'] == '22.04' - ansible_facts['distribution_version'] == '22.04'
- ansible_facts['architecture'] == 'aarch64' or ansible_facts['architecture'] == 'x86_64'
- name: Install armhf cross-compile packages to build QEMU on AArch64 Ubuntu 22.04 - name: Install armhf cross-compile packages to build QEMU on AArch64 Ubuntu 22.04
package: package:

View File

@ -19,58 +19,61 @@
import argparse import argparse
import re import re
from subprocess import check_output, STDOUT from subprocess import check_output, STDOUT, CalledProcessError
import sys
# mappings from gdb arch to QEMU target # Mappings from gdb arch to QEMU target
mappings = { MAP = {
"alpha" : "alpha", "alpha" : ["alpha"],
"aarch64" : ["aarch64", "aarch64_be"], "aarch64" : ["aarch64", "aarch64_be"],
"armv7": "arm", "armv7": ["arm"],
"armv8-a" : ["aarch64", "aarch64_be"], "armv8-a" : ["aarch64", "aarch64_be"],
"avr" : "avr", "avr" : ["avr"],
# no hexagon in upstream gdb # no hexagon in upstream gdb
"hppa1.0" : "hppa", "hppa1.0" : ["hppa"],
"i386" : "i386", "i386" : ["i386"],
"i386:x86-64" : "x86_64", "i386:x86-64" : ["x86_64"],
"Loongarch64" : "loongarch64", "Loongarch64" : ["loongarch64"],
"m68k" : "m68k", "m68k" : ["m68k"],
"MicroBlaze" : "microblaze", "MicroBlaze" : ["microblaze"],
"mips:isa64" : ["mips64", "mips64el"], "mips:isa64" : ["mips64", "mips64el"],
"or1k" : "or1k", "or1k" : ["or1k"],
"powerpc:common" : "ppc", "powerpc:common" : ["ppc"],
"powerpc:common64" : ["ppc64", "ppc64le"], "powerpc:common64" : ["ppc64", "ppc64le"],
"riscv:rv32" : "riscv32", "riscv:rv32" : ["riscv32"],
"riscv:rv64" : "riscv64", "riscv:rv64" : ["riscv64"],
"s390:64-bit" : "s390x", "s390:64-bit" : ["s390x"],
"sh4" : ["sh4", "sh4eb"], "sh4" : ["sh4", "sh4eb"],
"sparc": "sparc", "sparc": ["sparc"],
"sparc:v8plus": "sparc32plus", "sparc:v8plus": ["sparc32plus"],
"sparc:v9a" : "sparc64", "sparc:v9a" : ["sparc64"],
# no tricore in upstream gdb # no tricore in upstream gdb
"xtensa" : ["xtensa", "xtensaeb"] "xtensa" : ["xtensa", "xtensaeb"]
} }
def do_probe(gdb): def do_probe(gdb):
gdb_out = check_output([gdb, try:
"-ex", "set architecture", gdb_out = check_output([gdb,
"-ex", "quit"], stderr=STDOUT) "-ex", "set architecture",
"-ex", "quit"], stderr=STDOUT, encoding="utf-8")
except (OSError) as e:
sys.exit(e)
except CalledProcessError as e:
sys.exit(f'{e}. Output:\n\n{e.output}')
m = re.search(r"Valid arguments are (.*)", found_gdb_archs = re.search(r'Valid arguments are (.*)', gdb_out)
gdb_out.decode("utf-8"))
valid_arches = set() targets = set()
if found_gdb_archs:
gdb_archs = found_gdb_archs.group(1).split(", ")
mapped_gdb_archs = [arch for arch in gdb_archs if arch in MAP]
if m.group(1): targets = {target for arch in mapped_gdb_archs for target in MAP[arch]}
for arch in m.group(1).split(", "):
if arch in mappings: # QEMU targets
mapping = mappings[arch] return targets
if isinstance(mapping, str):
valid_arches.add(mapping)
else:
for entry in mapping:
valid_arches.add(entry)
return valid_arches
def main() -> None: def main() -> None:
parser = argparse.ArgumentParser(description='Probe GDB Architectures') parser = argparse.ArgumentParser(description='Probe GDB Architectures')

View File

@ -92,10 +92,10 @@ endif
docker-image-alpine: NOUSER=1 docker-image-alpine: NOUSER=1
debian-toolchain-run = \ debian-toolchain-run = \
$(if $(NOCACHE), \ $(if $(NOCACHE)$(NOFETCH), \
$(call quiet-command, \ $(call quiet-command, \
$(DOCKER_SCRIPT) build -t qemu/$1 -f $< \ $(DOCKER_SCRIPT) build -t qemu/$1 -f $< \
$(if $V,,--quiet) --no-cache \ $(if $V,,--quiet) $(if $(NOCACHE),--no-cache) \
--registry $(DOCKER_REGISTRY) --extra-files \ --registry $(DOCKER_REGISTRY) --extra-files \
$(DOCKER_FILES_DIR)/$1.d/build-toolchain.sh, \ $(DOCKER_FILES_DIR)/$1.d/build-toolchain.sh, \
"BUILD", $1), \ "BUILD", $1), \
@ -177,6 +177,7 @@ docker:
@echo ' NETWORK=$$BACKEND Enable virtual network interface with $$BACKEND.' @echo ' NETWORK=$$BACKEND Enable virtual network interface with $$BACKEND.'
@echo ' NOUSER=1 Define to disable adding current user to containers passwd.' @echo ' NOUSER=1 Define to disable adding current user to containers passwd.'
@echo ' NOCACHE=1 Ignore cache when build images.' @echo ' NOCACHE=1 Ignore cache when build images.'
@echo ' NOFETCH=1 Do not fetch from the registry.'
@echo ' EXECUTABLE=<path> Include executable in image.' @echo ' EXECUTABLE=<path> Include executable in image.'
@echo ' EXTRA_FILES="<path> [... <path>]"' @echo ' EXTRA_FILES="<path> [... <path>]"'
@echo ' Include extra files in image.' @echo ' Include extra files in image.'

View File

@ -43,8 +43,8 @@ RUN curl -#SL https://github.com/loongson/build-tools/releases/download/2023.08.
ENV PATH $PATH:/opt/cross-tools/bin ENV PATH $PATH:/opt/cross-tools/bin
ENV LD_LIBRARY_PATH /opt/cross-tools/lib:/opt/cross-tools/loongarch64-unknown-linux-gnu/lib:$LD_LIBRARY_PATH ENV LD_LIBRARY_PATH /opt/cross-tools/lib:/opt/cross-tools/loongarch64-unknown-linux-gnu/lib:$LD_LIBRARY_PATH
ENV QEMU_CONFIGURE_OPTS --disable-system --disable-docs --disable-tools ENV QEMU_CONFIGURE_OPTS --disable-docs --disable-tools
ENV DEF_TARGET_LIST loongarch64-linux-user,loongarch-softmmu ENV DEF_TARGET_LIST loongarch64-linux-user,loongarch64-softmmu
ENV MAKE /usr/bin/make ENV MAKE /usr/bin/make
# As a final step configure the user (if env is defined) # As a final step configure the user (if env is defined)

View File

@ -10,6 +10,8 @@ TOOLCHAIN_INSTALL=/usr/local
TOOLCHAIN_BIN=${TOOLCHAIN_INSTALL}/bin TOOLCHAIN_BIN=${TOOLCHAIN_INSTALL}/bin
CROSS_SYSROOT=${TOOLCHAIN_INSTALL}/$TARGET/sys-root CROSS_SYSROOT=${TOOLCHAIN_INSTALL}/$TARGET/sys-root
GCC_PATCH0_URL=https://raw.githubusercontent.com/Xilinx/meta-xilinx/refs/tags/xlnx-rel-v2024.1/meta-microblaze/recipes-devtools/gcc/gcc-12/0009-Patch-microblaze-Fix-atomic-boolean-return-value.patch
export PATH=${TOOLCHAIN_BIN}:$PATH export PATH=${TOOLCHAIN_BIN}:$PATH
# #
@ -31,6 +33,12 @@ mv gcc-11.2.0 src-gcc
mv musl-1.2.2 src-musl mv musl-1.2.2 src-musl
mv linux-5.10.70 src-linux mv linux-5.10.70 src-linux
#
# Patch gcc
#
wget -O - ${GCC_PATCH0_URL} | patch -d src-gcc -p1
mkdir -p bld-hdr bld-binu bld-gcc bld-musl mkdir -p bld-hdr bld-binu bld-gcc bld-musl
mkdir -p ${CROSS_SYSROOT}/usr/include mkdir -p ${CROSS_SYSROOT}/usr/include

View File

@ -10,6 +10,8 @@ FROM docker.io/library/debian:11-slim
# ??? The build-dep isn't working, missing a number of # ??? The build-dep isn't working, missing a number of
# minimal build dependiencies, e.g. libmpc. # minimal build dependiencies, e.g. libmpc.
RUN sed 's/^deb /deb-src /' </etc/apt/sources.list >/etc/apt/sources.list.d/deb-src.list
RUN apt update && \ RUN apt update && \
DEBIAN_FRONTEND=noninteractive apt install -yy eatmydata && \ DEBIAN_FRONTEND=noninteractive apt install -yy eatmydata && \
DEBIAN_FRONTEND=noninteractive eatmydata \ DEBIAN_FRONTEND=noninteractive eatmydata \
@ -33,6 +35,11 @@ RUN cd /root && ./build-toolchain.sh
# and the build trees by restoring the original image, # and the build trees by restoring the original image,
# then copying the built toolchain from stage 0. # then copying the built toolchain from stage 0.
FROM docker.io/library/debian:11-slim FROM docker.io/library/debian:11-slim
RUN apt update && \
DEBIAN_FRONTEND=noninteractive apt install -yy eatmydata && \
DEBIAN_FRONTEND=noninteractive eatmydata \
apt install -y --no-install-recommends \
libmpc3
COPY --from=0 /usr/local /usr/local COPY --from=0 /usr/local /usr/local
# As a final step configure the user (if env is defined) # As a final step configure the user (if env is defined)
ARG USER ARG USER

View File

@ -103,9 +103,14 @@ ifeq ($(filter %-softmmu, $(TARGET)),)
# then the target. If there are common tests shared between # then the target. If there are common tests shared between
# sub-targets (e.g. ARM & AArch64) then it is up to # sub-targets (e.g. ARM & AArch64) then it is up to
# $(TARGET_NAME)/Makefile.target to include the common parent # $(TARGET_NAME)/Makefile.target to include the common parent
# architecture in its VPATH. # architecture in its VPATH. However some targets are so minimal we
# can't even build the multiarch tests.
ifneq ($(filter $(TARGET_NAME),aarch64_be),)
-include $(SRC_PATH)/tests/tcg/$(TARGET_NAME)/Makefile.target
else
-include $(SRC_PATH)/tests/tcg/multiarch/Makefile.target -include $(SRC_PATH)/tests/tcg/multiarch/Makefile.target
-include $(SRC_PATH)/tests/tcg/$(TARGET_NAME)/Makefile.target -include $(SRC_PATH)/tests/tcg/$(TARGET_NAME)/Makefile.target
endif
# Add the common build options # Add the common build options
CFLAGS+=-Wall -Werror -O0 -g -fno-strict-aliasing CFLAGS+=-Wall -Werror -O0 -g -fno-strict-aliasing

View File

@ -23,8 +23,8 @@ from sys import argv
from test_gdbstub import arg_parser, main, report from test_gdbstub import arg_parser, main, report
PATTERN_0 = "Memory tags for address 0x[0-9a-f]+ match \\(0x[0-9a-f]+\\)." PATTERN_0 = r"Memory tags for address 0x[0-9a-f]+ match \(0x[0-9a-f]+\)."
PATTERN_1 = ".*(0x[0-9a-f]+)" PATTERN_1 = r".*(0x[0-9a-f]+)"
def run_test(): def run_test():

View File

@ -0,0 +1,17 @@
# -*- Mode: makefile -*-
#
# A super basic AArch64 BE makefile. As we don't have any big-endian
# libc available the best we can do is a basic Hello World.
AARCH64BE_SRC=$(SRC_PATH)/tests/tcg/aarch64_be
VPATH += $(AARCH64BE_SRC)
AARCH64BE_TEST_SRCS=$(notdir $(wildcard $(AARCH64BE_SRC)/*.c))
AARCH64BE_TESTS=$(AARCH64BE_TEST_SRCS:.c=)
#MULTIARCH_TESTS = $(MULTIARCH_SRCS:.c=)
# We need to specify big-endian cflags
CFLAGS +=-mbig-endian -ffreestanding
LDFLAGS +=-nostdlib
TESTS += $(AARCH64BE_TESTS)

View File

@ -0,0 +1,35 @@
/*
* Non-libc syscall hello world for Aarch64 BE
*
* SPDX-License-Identifier: GPL-2.0-or-later
*/
#define __NR_write 64
#define __NR_exit 93
int write(int fd, char *buf, int len)
{
register int x0 __asm__("x0") = fd;
register char *x1 __asm__("x1") = buf;
register int x2 __asm__("x2") = len;
register int x8 __asm__("x8") = __NR_write;
asm volatile("svc #0" : : "r"(x0), "r"(x1), "r"(x2), "r"(x8));
return len;
}
void exit(int ret)
{
register int x0 __asm__("x0") = ret;
register int x8 __asm__("x8") = __NR_exit;
asm volatile("svc #0" : : "r"(x0), "r"(x8));
__builtin_unreachable();
}
void _start(void)
{
write(1, "Hello World\n", 12);
exit(0);
}

View File

@ -17,6 +17,7 @@ X86_64_TESTS += cmpxchg
X86_64_TESTS += adox X86_64_TESTS += adox
X86_64_TESTS += test-1648 X86_64_TESTS += test-1648
X86_64_TESTS += test-2175 X86_64_TESTS += test-2175
X86_64_TESTS += cross-modifying-code
TESTS=$(MULTIARCH_TESTS) $(X86_64_TESTS) test-x86_64 TESTS=$(MULTIARCH_TESTS) $(X86_64_TESTS) test-x86_64
else else
TESTS=$(MULTIARCH_TESTS) TESTS=$(MULTIARCH_TESTS)
@ -27,6 +28,9 @@ adox: CFLAGS=-O2
run-test-i386-ssse3: QEMU_OPTS += -cpu max run-test-i386-ssse3: QEMU_OPTS += -cpu max
run-plugin-test-i386-ssse3-%: QEMU_OPTS += -cpu max run-plugin-test-i386-ssse3-%: QEMU_OPTS += -cpu max
cross-modifying-code: CFLAGS+=-pthread
cross-modifying-code: LDFLAGS+=-pthread
test-x86_64: LDFLAGS+=-lm -lc test-x86_64: LDFLAGS+=-lm -lc
test-x86_64: test-i386.c test-i386.h test-i386-shift.h test-i386-muldiv.h test-x86_64: test-i386.c test-i386.h test-i386-shift.h test-i386-muldiv.h
$(CC) $(CFLAGS) $< -o $@ $(LDFLAGS) $(CC) $(CFLAGS) $< -o $@ $(LDFLAGS)

View File

@ -0,0 +1,80 @@
/*
* Test patching code, running in one thread, from another thread.
*
* Intel SDM calls this "cross-modifying code" and recommends a special
* sequence, which requires both threads to cooperate.
*
* Linux kernel uses a different sequence that does not require cooperation and
* involves patching the first byte with int3.
*
* Finally, there is user-mode software out there that simply uses atomics, and
* that seems to be good enough in practice. Test that QEMU has no problems
* with this as well.
*/
#include <assert.h>
#include <pthread.h>
#include <stdbool.h>
#include <stdlib.h>
void add1_or_nop(long *x);
asm(".pushsection .rwx,\"awx\",@progbits\n"
".globl add1_or_nop\n"
/* addq $0x1,(%rdi) */
"add1_or_nop: .byte 0x48, 0x83, 0x07, 0x01\n"
"ret\n"
".popsection\n");
#define THREAD_WAIT 0
#define THREAD_PATCH 1
#define THREAD_STOP 2
static void *thread_func(void *arg)
{
int val = 0x0026748d; /* nop */
while (true) {
switch (__atomic_load_n((int *)arg, __ATOMIC_SEQ_CST)) {
case THREAD_WAIT:
break;
case THREAD_PATCH:
val = __atomic_exchange_n((int *)&add1_or_nop, val,
__ATOMIC_SEQ_CST);
break;
case THREAD_STOP:
return NULL;
default:
assert(false);
__builtin_unreachable();
}
}
}
#define INITIAL 42
#define COUNT 1000000
int main(void)
{
int command = THREAD_WAIT;
pthread_t thread;
long x = 0;
int err;
int i;
err = pthread_create(&thread, NULL, &thread_func, &command);
assert(err == 0);
__atomic_store_n(&command, THREAD_PATCH, __ATOMIC_SEQ_CST);
for (i = 0; i < COUNT; i++) {
add1_or_nop(&x);
}
__atomic_store_n(&command, THREAD_STOP, __ATOMIC_SEQ_CST);
err = pthread_join(thread, NULL);
assert(err == 0);
assert(x >= INITIAL);
assert(x <= INITIAL + COUNT);
return EXIT_SUCCESS;
}