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

Remove lockdown workflow #35

Closed
Closed
Show file tree
Hide file tree
Changes from all 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
41 changes: 41 additions & 0 deletions .github/workflows/build.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
name: Build target user

on: [pull_request, workflow_dispatch]

jobs:
build:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- name: Set up Python 3.x
uses: actions/setup-python@v4
with:
python-version: '3.x'
- name: Copy source.list file to include deb-src
run: |
sudo cp /etc/apt/sources.list /etc/apt/sources.list.d/tmp.list
sudo sed -i "s/# deb-src/deb-src/g" /etc/apt/sources.list.d/tmp.list
- name: Install deps
run: |
sudo apt-get update
sudo apt-get --no-install-recommends -y build-dep qemu
sudo apt-get install -y autoconf libtool protobuf-c-compiler
pip3 install --user ninja
- name: Install OCaml
uses: ocaml/setup-ocaml@v2
with:
ocaml-compiler: 4.14.x
dune-cache: true
opam-disable-sandboxing: true
- name: Install piqi
run: |
opam install piqi
- name: Clone qemu and bap-frames
run: |
git clone --depth 1 http://github.com/BinaryAnalysisPlatform/bap-frames.git
git clone --depth 1 http://github.com/BinaryAnalysisPlatform/qemu.git
- name: Build without tracewrap
run: |
cd qemu
./configure --prefix=$HOME --target-list=arm-linux-user
ninja -C build
30 changes: 0 additions & 30 deletions .github/workflows/lockdown.yml

This file was deleted.

98 changes: 98 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,98 @@
# Overview

Qemu tracer - a tracer based on [qemu](https://github.com/qemu/qemu)
project. It executes a binary executable and saves trace data using
[Protocol Buffer](https://developers.google.com/protocol-buffers/)
format. The contents of the trace data is defined in
[bap-traces](https://github.com/BinaryAnalysisPlatform/bap-traces)
project.

# Installing released binaries

If you don't want to mess with the source and building, then you can just
dowload a tarball with prebuilt binaries. Look at the latest release and
it might happen, that we have built binaries for your linux distribution,
if it is not the case, then create an issue, and we will build it for you.

Let's pretend, that you're using Ubuntu Trusty, and install it. First
download it with your favorite downloader:

```
wget https://github.com/BinaryAnalysisPlatform/qemu/releases/download/v2.0.0-tracewrap-2.0.0-rc1/qemu-tracewrap-ubuntu-14.04.4-LTS.tgz
```

Install it in the specified prefix with a command like `tar -C <prefix> -xf qemu-tracewrap-ubuntu-14.04.4-LTS.tgz`, e.g.,
to install in your home directory:
```
tar -C $HOME -xf qemu-tracewrap-ubuntu-14.04.4-LTS.tgz
```



# Build

## Preparation

Note: the instructions assume that you're using Ubuntu, but it
may work on other systems, that uses apt-get.

Before building the qemu-tracewrap, you need to install the following packages:
* qemu build dependencies
* autoconf, libtool, protobuf-c-compiler
* [piqi library](http://piqi.org/doc/ocaml)

To install qemu build dependencies, use the following command

```bash
$ sudo apt-get --no-install-recommends -y build-dep qemu
```

To install autoconf, libtool, protobuf-c-compiler, use the
following command

```bash
$ sudo apt-get install autoconf libtool protobuf-c-compiler
```

To install [piqi library](http://piqi.org/doc/ocaml) with
[opam](https://opam.ocaml.org/doc/Install.html), use the following command
```bash
$ opam install piqi
```

## Building

Download [bap-frames](https://github.com/BinaryAnalysisPlatform/bap-frames) with
following command

```bash
$ git clone https://github.com/BinaryAnalysisPlatform/bap-frames.git
```

Download qemu tracer with following command

```bash
$ git clone [email protected]:BinaryAnalysisPlatform/qemu.git
```

Change folder to qemu and build tracer:
```bash
$ cd qemu
$ ./configure --prefix=$HOME --with-tracewrap=<absolute-path-to>/bap-frames --target-list=<ARCH>-linux-user
$ ninja -C build
$ ninja -C build install
```

# Usage

To run executable `exec` compiled for `arch`, use `qemu-arch exec` command, e.g.,
`qemu-x86_64 /bin/ls`. It will dump the trace into `ls.frames` file. You can configure
the filename with `-tracefile` option, e.g., `qemu-arm -tracefile arm.ls.frames ls`


Hints: use option -L to set the elf interpreter prefix to 'path'. Use
[fetchlibs.sh](https://raw.githubusercontent.com/BinaryAnalysisPlatform/bap-frames/master/test/fetchlibs.sh)
to download arm and x86 libraries.

# Notes
Only ARM, X86, X86-64, MIPS targets are supported in this branch.
2 changes: 2 additions & 0 deletions accel/tcg/cpu-exec.c
Original file line number Diff line number Diff line change
Expand Up @@ -1032,10 +1032,12 @@ cpu_exec_loop(CPUState *cpu, SyncClocks *sc)
last_tb = NULL;
}
#endif
#ifndef HAS_TRACEWRAP
/* See if we can patch the calling TB. */
if (last_tb) {
tb_add_jump(last_tb, tb_exit, tb);
}
#endif

cpu_loop_exec_tb(cpu, tb, pc, &last_tb, &tb_exit);

Expand Down
16 changes: 16 additions & 0 deletions configure
Original file line number Diff line number Diff line change
Expand Up @@ -202,6 +202,16 @@ EXTRA_LDFLAGS=""
# is impossible without a --enable-foo that exits if a feature is not found.
default_feature=""

# 3. Automatically enable/disable other options
tcg="enabled"
cfi="false"

# 4. Detection partly done in configure
xen=${default_feature:+disabled}

tracewrap="false"

# parse CC options second
for opt do
optarg=$(expr "x$opt" : 'x[^=]*=\(.*\)')
case "$opt" in
Expand Down Expand Up @@ -728,6 +738,10 @@ for opt do
;;
--without-default-devices) meson_option_add -Ddefault_devices=false
;;
--with-tracewrap=*)
tracewrap="true"
tracewrap_dir="$optarg"
;;
--with-devices-*[!a-zA-Z0-9_-]*=*) error_exit "Passed bad --with-devices-FOO option"
;;
--with-devices-*) device_arch=${opt#--with-devices-};
Expand Down Expand Up @@ -1937,6 +1951,8 @@ if test "$skip_meson" = no; then
test "$qemu_suffix" != qemu && meson_option_add "-Dqemu_suffix=$qemu_suffix"
test "$smbd" != '' && meson_option_add "-Dsmbd=$smbd"
test "$tcg" != enabled && meson_option_add "-Dtcg=$tcg"
test "$tracewrap" != '' && meson_option_add "-Dtracewrap=$tracewrap"
test "$tracewrap_dir" != '' && meson_option_add "-Dtracewrap_dir=$tracewrap_dir"
run_meson() {
NINJA=$ninja $meson setup --prefix "$prefix" "$@" $cross_arg "$PWD" "$source_path"
}
Expand Down
13 changes: 13 additions & 0 deletions include/trace_consts.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
#pragma once

#include "trace_info.h"

const uint64_t magic_number = 7456879624156307493LL;
const uint64_t magic_number_offset = 0LL;
const uint64_t trace_version_offset = 8LL;
const uint64_t bfd_arch_offset = 16LL;
const uint64_t bfd_machine_offset = 24LL;
const uint64_t num_trace_frames_offset = 32LL;
const uint64_t toc_offset_offset = 40LL;
const uint64_t first_frame_offset = 48LL;
const uint64_t out_trace_version = 2LL;
65 changes: 65 additions & 0 deletions include/tracewrap.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,65 @@
#pragma once

#include <stdint.h>
#include <stdio.h>
#include <stdlib.h>

#include "qemu/osdep.h"
#include "cpu.h"

#include "frame.piqi.pb-c.h"


/** initializes trace subsystem.

All pointers are owned by the caller.

@param filename a name of filesystem entry where trace will be dumpled,
if NULL then the name is basename(argv[0]).frames

@param targetname a path to the executable, must be non NULL


@param argv a full list of arguments passed to the tracer, NULL terminated.
Can be NULL or empty (i.e., contain only a NULL element).
The list may include target arguments.

@param envp a null terminated list of environment parameters,
can be NULL or empty.

@param target_argv a null terminated list of target arguments,
can be NULL or empty.

@param target_envp a null terminated list of target environment,
can be NULL or empty.
*/
void qemu_trace_init(const char *filename, const char *targetname,
char **argv, char **envp,
char **target_argv,
char **target_envp);
void qemu_trace_newframe(target_ulong addr, int tread_id);
void qemu_trace_add_operand(OperandInfo *oi, int inout);
void qemu_trace_endframe(CPUArchState *env, target_ulong pc, target_ulong size);
void qemu_trace_finish(uint32_t exit_code);

OperandInfo * load_store_reg(target_ulong reg, target_ulong val, int ls);
OperandInfo * load_store_mem(target_ulong addr, target_ulong val, int ls, int len);

#define REG_EFLAGS 66
#define REG_LO 33
#define REG_HI 34

#define REG_CPSR 64
#define REG_APSR 65
#define REG_SP 13
#define REG_LR 14
#define REG_PC 15

#define REG_NF 94
#define REG_ZF 95
#define REG_CF 96
#define REG_VF 97
#define REG_QF 98
#define REG_GE 99

#define SEG_BIT 8
6 changes: 6 additions & 0 deletions linux-user/arm/trace_info.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
#pragma once

#include "frame_arch.h"

const uint64_t frame_arch = frame_arch_arm;
const uint64_t frame_mach = frame_mach_arm_unknown;
6 changes: 6 additions & 0 deletions linux-user/i386/trace_info.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
#pragma once

#include "frame_arch.h"

const uint64_t frame_arch = frame_arch_i386;
const uint64_t frame_mach = frame_mach_i386_i386;
21 changes: 21 additions & 0 deletions linux-user/main.c
Original file line number Diff line number Diff line change
Expand Up @@ -65,6 +65,11 @@
#define AT_FLAGS_PRESERVE_ARGV0 (1 << AT_FLAGS_PRESERVE_ARGV0_BIT)
#endif

#ifdef HAS_TRACEWRAP
#include "tracewrap.h"
const char * qemu_tracefilename = NULL;
#endif //HAS_TRACEWRAP

char *exec_path;
char real_exec_path[PATH_MAX];

Expand Down Expand Up @@ -416,6 +421,13 @@ static void handle_arg_strace(const char *arg)
enable_strace = true;
}

#ifdef HAS_TRACEWRAP
static void handle_trace_filename(const char *arg)
{
qemu_tracefilename = arg;
}
#endif //HAS_TRACEWRAP

static void handle_arg_version(const char *arg)
{
printf("qemu-" TARGET_NAME " version " QEMU_FULL_VERSION
Expand Down Expand Up @@ -522,6 +534,10 @@ static const struct qemu_argument arg_table[] = {
"", "Generate a /tmp/perf-${pid}.map file for perf"},
{"jitdump", "QEMU_JITDUMP", false, handle_arg_jitdump,
"", "Generate a jit-${pid}.dump file for perf"},
#ifdef HAS_TRACEWRAP
{"tracefile", "", true, handle_trace_filename,
"file", "path to trace file (defaults to <target>.frames)"},
#endif //HAS_TRACEWRAP
{NULL, NULL, false, NULL, NULL, NULL}
};

Expand Down Expand Up @@ -933,6 +949,11 @@ int main(int argc, char **argv, char **envp)
}
target_argv[target_argc] = NULL;

#ifdef HAS_TRACEWRAP
qemu_trace_init(qemu_tracefilename, exec_path,
argv, environ, target_argv, target_environ);
#endif //HAS_TRACEWRAP

ts = g_new0(TaskState, 1);
init_task_state(ts);
/* build Task State */
Expand Down
6 changes: 6 additions & 0 deletions linux-user/mips/trace_info.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
#pragma once

#include "frame_arch.h"

const uint64_t frame_arch = frame_arch_mips;
const uint64_t frame_mach = frame_mach_mipsisa32 ;
8 changes: 8 additions & 0 deletions linux-user/signal.c
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,10 @@
#include "host-signal.h"
#include "user/safe-syscall.h"

#ifdef HAS_TRACEWRAP
#include "tracewrap.h"
#endif //HAS_TRACEWRAP

static struct target_sigaction sigact_table[TARGET_NSIG];

static void host_signal_handler(int host_signum, siginfo_t *info,
Expand Down Expand Up @@ -707,6 +711,10 @@ void dump_core_and_abort(CPUArchState *cpu_env, int target_sig)
trace_user_dump_core_and_abort(env, target_sig, host_sig);
gdb_signalled(env, target_sig);

#ifdef HAS_TRACEWRAP
qemu_trace_finish(-target_sig);
#endif //HAS_TRACEWRAP

/* dump core if supported by target binary format */
if (core_dump_signal(target_sig) && (ts->bprm->core_dump != NULL)) {
stop_all_tasks();
Expand Down
Loading
Loading