Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

SymCC Runtime Integration #55

Merged
merged 19 commits into from
Apr 9, 2024
Merged
Show file tree
Hide file tree
Changes from 2 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 4 additions & 3 deletions .gitmodules
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,7 @@
[submodule "tests/lcitool/libvirt-ci"]
path = tests/lcitool/libvirt-ci
url = https://gitlab.com/libvirt/libvirt-ci.git
[submodule "symcc"]
path = symcc
url = https://github.com/eurecom-s3/symcc.git
[submodule "subprojects/symcc-rt"]
path = subprojects/symcc-rt
url = https://github.com/eurecom-s3/symcc-rt.git
branch = export_symcc_runtime
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should this be main?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Once merged I guess yes.

42 changes: 12 additions & 30 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,28 +8,16 @@ changes to happen there, but PR may be accepted.

## How to build

SymQEMU requires [SymCC](https://github.com/eurecom-s3/symcc), so please
download and build SymCC first. For best results, configure it with the QSYM
backend as explained in the README. For the impatient, here's a quick summary of
the required steps that may or may not work on your system:

First of all, make sure the [symcc-rt](https://github.com/eurecom-s3/symcc-rt.git) submodule is initialized:
``` shell
$ git clone https://github.com/eurecom-s3/symcc.git
$ cd symcc
$ git submodule update --init
$ mkdir build
$ cd build
$ cmake -G Ninja -DQSYM_BACKEND=ON ..
$ ninja
$ git submodule update --init --recursive subprojects/symcc-rt
```

Next, make sure that QEMU's build dependencies are installed. Most package
Make sure that QEMU's build dependencies are installed. Most package
managers provide a command to get them, e.g., `apt build-dep qemu` on Debian and
Ubuntu, or `dnf builddep qemu` on Fedora and CentOS.

We've extended QEMU's configuration script to accept pointers to SymCC's source
and binaries. The following invocation is known to work on Debian 10, Arch and
Fedora 33:
The following invocation is known to work on Debian 10, Arch and Fedora 33:
rmalmain marked this conversation as resolved.
Show resolved Hide resolved

``` shell
$ mkdir build
Expand All @@ -42,9 +30,7 @@ $ ../configure \
--disable-opengl \
--disable-virglrenderer \
--disable-werror \
--target-list=x86_64-linux-user \
--symcc-source=../symcc \
--symcc-build=../symcc/build
--target-list=x86_64-linux-user
$ make -j
```

Expand All @@ -54,6 +40,12 @@ target architectures is possible in principle but will require a bit of work
because the current implementation assumes that we can pass around host pointers
in guest registers.

## SymQEMU compilation options

Several compilation options are available:
- `enable-symcc-shared`: Compile SymQEMU with the shared library of `SymCC Runtime` instead of a static library
- `symcc-backend`: Choose a specific backend from `SymCC Runtime`. Please have a look to [symcc-rt](https://github.com/eurecom-s3/symcc-rt.git) to get an exhaustive list of available backends.
rmalmain marked this conversation as resolved.
Show resolved Hide resolved

## Running SymQEMU

If you built SymQEMU as described above, the binary will be in
Expand Down Expand Up @@ -90,17 +82,7 @@ you'll have to run AFL in QEMU mode by adding `-Q` to its command line; the
fuzzing helper will automatically pick up the setting and use QEMU mode too.)

## Build with Docker
First, make sure to have an up-to-date Docker image of SymCC. If you
don't have one, either in the submodule, run:

``` shell
git submodule update --init --recursive symcc
cd symcc
docker build -t symcc .
cd ..
```

Then build the SymQEMU image with (this will also run the tests):
Build the SymQEMU image with (this will also run the tests):
```shell
docker build -t symqemu .
```
Expand Down
21 changes: 0 additions & 21 deletions configure
Original file line number Diff line number Diff line change
Expand Up @@ -242,8 +242,6 @@ default_cflags='-O2 -g'
git_submodules_action="update"
docs="auto"
EXESUF=""
symcc_source=""
symcc_build=""
system="yes"
linux_user=""
bsd_user=""
Expand Down Expand Up @@ -696,10 +694,6 @@ for opt do
;;
--static) static="yes"
;;
--symcc-source=*) symcc_source="$optarg"
;;
--symcc-build=*) symcc_build="$optarg"
;;
--host=*|--build=*|\
--disable-dependency-tracking|\
--sbindir=*|--sharedstatedir=*|\
Expand Down Expand Up @@ -880,8 +874,6 @@ Advanced options (experts only):
start the emulator (only use if you are including
desired devices in configs/devices/)
--with-devices-ARCH=NAME override default configs/devices
--symcc-source=PATH PATH to SymCC source code
--symcc-build=PATH PATH to the build directory of SymCC with Qsym backend
--enable-debug enable common debug build options
--cpu=CPU Build for host CPU [$cpu]
--disable-containers don't use containers for cross-building
Expand Down Expand Up @@ -1678,19 +1670,6 @@ if test "$targetos" = windows; then
echo "CONFIG_WIN32=y" >> contrib/plugins/$config_host_mak
fi

echo "# SymQEMU config" >> $config_host_mak
if test -e "$symcc_source/runtime/RuntimeCommon.h"; then
echo "SYMCC_INC=$symcc_source/runtime" >> $config_host_mak
else
error_exit "SymCC (source)" "Point --symcc-source to the SymCC source code"
fi
if test -e "$symcc_build/SymRuntime-prefix/src/SymRuntime-build/libSymRuntime.so"; then
echo "SYMCC_BUILD=$symcc_build/SymRuntime-prefix/src/SymRuntime-build" >> $config_host_mak
echo "SYMCC_LIBS=$symcc_build/SymRuntime-prefix/src/SymRuntime-build/libSymRuntime.so" >> $config_host_mak
else
error_exit "SymCC (runtime)" "Point --symcc-build to the SymCC build directory"
fi

# tests/tcg configuration
(config_host_mak=tests/tcg/config-host.mak
mkdir -p tests/tcg
Expand Down
38 changes: 32 additions & 6 deletions meson.build
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
project('qemu', ['c'], meson_version: '>=0.63.0',
default_options: ['warning_level=1', 'c_std=gnu11', 'cpp_std=gnu++11', 'b_colorout=auto',
default_options: ['warning_level=1', 'c_std=gnu11', 'cpp_std=gnu++17', 'b_colorout=auto',
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is it ok to keep this? I couldn't get rid of this modification in the end

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is it required because the SymCC runtime uses C++17? Fine for me to keep it 🤷‍♂️

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It should not be necessary in theory.
Subprojects in meson should not rely on the options of the root project by default. I suspect the parsing of cmake by meson is doing something wrong, I will check

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

After investigation, I don't think we can do much about this.
Apparently, a few things are being hardcoded in the default options of the meson file generated from the cmake project that cannot be avoided (https://github.com/mesonbuild/meson/blob/master/mesonbuild/cmake/interpreter.py).
Maybe I missed something. If someone finds a way, we can change. Otherwise, I'll keep things that way.

'b_staticpic=false', 'stdsplit=false', 'optimization=2', 'b_pie=true'],
version: files('VERSION'))

Expand All @@ -13,6 +13,7 @@ not_found = dependency('', required: false)
keyval = import('keyval')
ss = import('sourceset')
fs = import('fs')
cmake = import('cmake')

targetos = host_machine.system()
sh = find_program('sh')
Expand Down Expand Up @@ -1080,6 +1081,26 @@ if targetos == 'linux' and (have_system or have_tools)
required: get_option('libudev'))
endif

symcc_backend = get_option('symcc_backend')

if not fs.is_file('subprojects/symcc-rt/RuntimeCommon.h')
error_msg='''The SymCC source path "@0@" is incorrect.
Did you initialize symcc-rt subrepository? (git submodule update --init --recursive subprojects/symcc-rt)'''.format('subprojects/symcc')
rmalmain marked this conversation as resolved.
Show resolved Hide resolved
error(error_msg)
endif

symcc_rt = not_found

symcc_var = cmake.subproject_options()
symcc_var.add_cmake_defines({ 'SYMCC_RT_BACKEND': symcc_backend })

symcc_rt_proj = cmake.subproject('symcc-rt', options: symcc_var)
if get_option('symcc_shared')
symcc_rt = symcc_rt_proj.dependency('SymccRtShared')
else
symcc_rt = symcc_rt_proj.dependency('SymccRtStatic')
endif

mpathlibs = [libudev]
mpathpersist = not_found
if targetos == 'linux' and have_tools and get_option('mpath').allowed()
Expand Down Expand Up @@ -3508,7 +3529,6 @@ subdir('plugins')
subdir('ebpf')

common_user_inc = []
common_user_inc += config_host['SYMCC_INC'].split()

subdir('common-user')
subdir('bsd-user')
Expand Down Expand Up @@ -3738,6 +3758,9 @@ common_ss.add(qom, qemuutil)
common_ss.add_all(when: 'CONFIG_SYSTEM_ONLY', if_true: [system_ss])
common_ss.add_all(when: 'CONFIG_USER_ONLY', if_true: user_ss)

common_ss.add(symcc_rt)
specific_ss.add(symcc_rt)

common_all = common_ss.apply(config_all, strict: false)
common_all = static_library('common',
build_by_default: false,
Expand Down Expand Up @@ -3885,16 +3908,13 @@ foreach target : target_dirs
exe_name += '-unsigned'
endif

symcc_libs = files(config_host['SYMCC_LIBS'].split())

emulator = executable(exe_name, exe['sources'],
install: true,
c_args: c_args,
dependencies: arch_deps + deps + exe['dependencies'],
objects: [lib.extract_all_objects(recursive: true), symcc_libs],
objects: lib.extract_all_objects(recursive: true),
link_depends: [block_syms, qemu_syms] + exe.get('link_depends', []),
link_args: link_args,
build_rpath: config_host['SYMCC_BUILD'],
win_subsystem: exe['win_subsystem'])

if targetos == 'darwin'
Expand Down Expand Up @@ -4341,6 +4361,12 @@ summary_info += {'netmap support': have_netmap}
summary_info += {'l2tpv3 support': have_l2tpv3}
summary(summary_info, bool_yn: true, section: 'Network backends')

# SymQEMU
summary_info = {}
summary_info += {'SymCC Backend': symcc_backend}
summary_info += {'SymCC Shared Library': get_option('symcc_shared')}
summary(summary_info, bool_yn: true, section: 'SymQEMU')

# Libraries
summary_info = {}
summary_info += {'libtasn1': tasn1}
Expand Down
6 changes: 6 additions & 0 deletions meson_options.txt
Original file line number Diff line number Diff line change
Expand Up @@ -368,3 +368,9 @@ option('qemu_ga_version', type: 'string', value: '',

option('hexagon_idef_parser', type : 'boolean', value : true,
description: 'use idef-parser to automatically generate TCG code for the Hexagon frontend')

# SymQEMU related options
option('symcc_backend', type: 'string', value: 'qsym',
description: 'SymCC backend to use. Please check SymCC Runtime for a list of available backends.')
option('symcc_shared', type: 'boolean', value: false,
description: 'Compile SymCC Runtime dynamically instead of statically.')
7 changes: 7 additions & 0 deletions scripts/meson-buildoptions.sh
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,8 @@ meson_options_help() {
printf "%s\n" ' clang/llvm and coroutine backend ucontext)'
printf "%s\n" ' --enable-sanitizers enable default sanitizers'
printf "%s\n" ' --enable-strip Strip targets on install'
printf "%s\n" ' --enable-symcc-shared Compile SymCC Runtime dynamically instead of'
printf "%s\n" ' statically.'
printf "%s\n" ' --enable-tcg-interpreter TCG with bytecode interpreter (slow)'
printf "%s\n" ' --enable-trace-backends=CHOICES'
printf "%s\n" ' Set available tracing backends [log] (choices:'
Expand All @@ -71,6 +73,8 @@ meson_options_help() {
printf "%s\n" ' [QEMU]'
printf "%s\n" ' --qemu-ga-version=VALUE version number for qemu-ga installer'
printf "%s\n" ' --smbd=VALUE Path to smbd for slirp networking'
printf "%s\n" ' --symcc-backend=VALUE SymCC backend to use. Please check SymCC Runtime'
printf "%s\n" ' for a list of available backends. [qsym]'
printf "%s\n" ' --sysconfdir=VALUE Sysconf data directory [etc]'
printf "%s\n" ' --tls-priority=VALUE Default TLS protocol/cipher priority string'
printf "%s\n" ' [NORMAL]'
Expand Down Expand Up @@ -488,6 +492,9 @@ _meson_option_parse() {
--disable-stack-protector) printf "%s" -Dstack_protector=disabled ;;
--enable-strip) printf "%s" -Dstrip=true ;;
--disable-strip) printf "%s" -Dstrip=false ;;
--symcc-backend=*) quote_sh "-Dsymcc_backend=$2" ;;
--enable-symcc-shared) printf "%s" -Dsymcc_shared=true ;;
--disable-symcc-shared) printf "%s" -Dsymcc_shared=false ;;
--sysconfdir=*) quote_sh "-Dsysconfdir=$2" ;;
--enable-tcg) printf "%s" -Dtcg=enabled ;;
--disable-tcg) printf "%s" -Dtcg=disabled ;;
Expand Down
1 change: 1 addition & 0 deletions subprojects/symcc-rt
Submodule symcc-rt added at 95a950
1 change: 0 additions & 1 deletion symcc
Submodule symcc deleted from d04d5b
Loading