[Qemu-devel] forking a virtual machine

2016-07-26 Thread Tim Newsham
Hi,  We've got an unusual use case for our qemu virtual machines.
We're using a qemu-based system to run a bunch of instrumented
test cases. QEMU provides the instrumented execution environment.
Before we start testing we setup the test environment, which includes
booting an operating system as a guest.  Once everything is ready, we
fork the qemu process once for each test case, with the parent controlling
the test operation while the child performs a test.  (For more details,
see our blog post:
https://www.nccgroup.trust/us/about-us/newsroom-and-events/blog/2016/june/project-triforce-run-afl-on-everything/,
full code
can be found at https://github.com/nccgroup/TriforceAFL)

Right now our fork process is very hacky and gross, because linux
fork() intentionally does not handle forking a multithreaded program.
 We have a special
cpu instruction which triggers the forking to go into test mode.  It sets a
flag, which causes the one and only cpu thread to exit.  Right before it
exits, it sends a signal to the iothread by writing over a pipe.  The
iothread
gets woken up and starts controlling test cases by forking children.
After each fork, it starts up a new cpu to replace the one that exited
before the fork.

This is less than ideal for several reasons.  Most importantly for us, we
would like to be able to communicate informatoin about new JITs that
occur from the child back to the parent so that the parent can reproduce
the JIT and save future children from having to keep JITting the same
thing.  This doesnt currently work (I think because the cpu has exited,
and there is no cpu left in the parent process).

We would also like to have more elegant forking code.

And so my question here -- Is there a better solution that we could use
to support forking a qemu VM?  Are there any single-threaded variants of
qemu that would work well here?  Are there any interesting tricks to pause
and resume a cpu across forks in a clean fashion?  Has anyone else
already worked on this problem?

-- 
Tim Newsham | www.thenewsh.com/~newsham | @newshtwit | thenewsh.blogspot.com


[Qemu-devel] basic block tracing question

2016-03-19 Thread Tim Newsham
Hi,  I would like to create an accurate trace of basic blocks that get
executed.  I'm interested in a trace of what a CPU would execute, and not
for the purposes of studying qemu itself.

I'm currently emitting trace data from cpu_tb_exec
https://github.com/qemu/qemu/blob/master/cpu-exec.c#L136
by printing out the env->eip (x86_64 only).  This seems to be roughly
the right place -- there's already cpu tracing in this function.
I do notice that some basic blocks get printed twice here though, and
I tracked it down to basic blocks being rescheduled if execution returns
with TB_EXIT_* flags set
https://github.com/qemu/qemu/blob/master/cpu-exec.c#L163
So I capture the PC before execution and only emit them if this is
not the case, after execution.  This gets rid of the duplicate edges in
the trace, but there is still one problem left that I don't understand!

Sometimes, when running the same program twice in a situation that
should give the exact same trace, I see differences:

 exec 8100450a
 exec 81091130
-exec 812f2930
+ basic block ff812f2930 returned with flag 3, setting pc to
812f285d
+exec 812f285d
 exec 812f293d
 exec 81091142

In this case the basic block wasn't merely restarted.  The PC was updated
to a different value after the next_tb had the TB_EXIT_REQUESTED flag set.
The particular basic block in question at 812f2930 ends with a callq
to 0x812f2850 and then falls through to 0x812f293d.  So I
would
expect to see the "..2930" and "..293d" in the trace, but not the "..285d"
in
the trace, unless it was just continuing mid-basic block after the exit?

What exactly is going on here.  What is the purpose of the TB_EXIT_REQUESTED
here?  What is causing execution to resume at "...285d" afterwards?  Is
there
a simple way to filter out any extraneous basic blocks that get started
midpoint (if
that is the case) and keep the true basic block starts?

Thank you in advance for any insights.

-- 
Tim Newsham | www.thenewsh.com/~newsham | @newshtwit | thenewsh.blogspot.com


Re: [Qemu-devel] basic block tracing question

2016-03-18 Thread Tim Newsham
On Wed, Mar 16, 2016 at 10:52 AM, Peter Maydell <peter.mayd...@linaro.org>
wrote:

>
> If you only emit tracing information after the TB has executed and
> returned then you will miss the case where we execute half a TB
> and take an exception (eg load/store that page faulted, or system call),
> because in that case we'll longjmp() out of the generated code. That's
> one of the reasons why the tracing we have in upstream traces before
> TB execution.
>

What happens when the basic block gets interrupted mid execution
and restarted?  Will execution jump to the middle of the translated
basic block, or will a new translation be performed starting at the
midpoint?

Firstly, are you running with -d nochain to disable QEMU's chaining
> of TBs? (If not, then when we chain TBs together you'll only get
> exec tracing for the first one, which is a good way to get confused.
> The default tracing will tell you when we chain TBs together so you
> can sort of unconfuse yourself, but it's easier to just turn it off
> if you care about the TB logging.)
>

I was not using "-d nochain".  Thank you!


> thanks
> -- PMM
>


-- 
Tim Newsham | www.thenewsh.com/~newsham | @newshtwit | thenewsh.blogspot.com