Fix acid test-bench issues

This commit is contained in:
jD91mZM2
2020-06-15 17:14:52 +02:00
parent 3420339c04
commit 727217ad42
3 changed files with 32 additions and 24 deletions

View File

@@ -48,13 +48,12 @@ interrupt_stack!(non_maskable, stack, {
});
interrupt_stack!(breakpoint, stack, {
println!("Breakpoint trap");
let guard = ptrace::set_process_regs(stack);
if ptrace::breakpoint_callback(PTRACE_STOP_BREAKPOINT, None).is_none() {
drop(guard);
println!("Breakpoint trap");
stack.dump();
ksignal(SIGTRAP);
}

View File

@@ -191,8 +191,8 @@ struct Breakpoint {
flags: PtraceFlags
}
/// Continue the process with the specified ID
pub fn cont(pid: ContextId) {
/// Clear any breakpoints for the process with the specified ID
pub fn clear_breakpoint(pid: ContextId) {
let sessions = sessions();
let session = match sessions.get(&pid) {
Some(session) => session,
@@ -203,6 +203,15 @@ pub fn cont(pid: ContextId) {
// Remove the breakpoint to make sure any yet unreached but
// obsolete breakpoints don't stop the program.
data.breakpoint = None;
}
// TODO: All these small functions should be moved to be on the session instance
pub fn notify(pid: ContextId) {
let sessions = sessions();
let session = match sessions.get(&pid) {
Some(session) => session,
None => return
};
session.tracee.notify();
}
@@ -218,10 +227,6 @@ pub fn set_breakpoint(pid: ContextId, flags: PtraceFlags, should_continue: bool)
reached: false,
flags
});
if should_continue {
session.tracee.notify();
}
}
/// Wait for the tracee to stop. If an event occurs, it returns a copy

View File

@@ -47,8 +47,9 @@ fn with_context_mut<F, T>(pid: ContextId, callback: F) -> Result<T>
}
callback(&mut context)
}
fn try_stop_context<F, T>(pid: ContextId, restart_after: bool, mut callback: F) -> Result<T>
where F: FnMut(&mut Context) -> Result<T>
fn try_stop_context<F, T>(pid: ContextId, mut callback: F) -> Result<T>
where
F: FnMut(&mut Context) -> Result<T>,
{
// Stop process
let (was_stopped, mut running) = with_context_mut(pid, |context| {
@@ -72,9 +73,7 @@ fn try_stop_context<F, T>(pid: ContextId, restart_after: bool, mut callback: F)
let ret = callback(context);
if !was_stopped || restart_after {
context.ptrace_stop = false;
}
context.ptrace_stop = was_stopped;
ret
})
@@ -342,7 +341,7 @@ impl Scheme for ProcScheme {
let fx = context.arch.get_fx_regs().unwrap_or_default();
Ok((Output { float: fx }, mem::size_of::<FloatRegisters>()))
})?,
RegsKind::Int => try_stop_context(info.pid, false, |context| match unsafe { ptrace::regs_for(&context) } {
RegsKind::Int => try_stop_context(info.pid, |context| match unsafe { ptrace::regs_for(&context) } {
None => {
println!("{}:{}: Couldn't read registers from stopped process", file!(), line!());
Err(Error::new(ENOTRECOVERABLE))
@@ -443,7 +442,7 @@ impl Scheme for ProcScheme {
*(buf as *const _ as *const IntRegisters)
};
try_stop_context(info.pid, false, |context| match unsafe { ptrace::regs_for_mut(context) } {
try_stop_context(info.pid, |context| match unsafe { ptrace::regs_for_mut(context) } {
None => {
println!("{}:{}: Couldn't read registers from stopped process", file!(), line!());
Err(Error::new(ENOTRECOVERABLE))
@@ -470,9 +469,7 @@ impl Scheme for ProcScheme {
let should_continue = !op.contains(PTRACE_FLAG_WAIT) || op.intersects(PTRACE_STOP_MASK);
if op.contains(PTRACE_STOP_SINGLESTEP) {
// `true` to `try_stop_context` means we restart after, no
// matter if it was or wasn't stopped before
try_stop_context(info.pid, true, |context| {
try_stop_context(info.pid, |context| {
match unsafe { ptrace::regs_for_mut(context) } {
None => {
println!("{}:{}: Couldn't read registers from stopped process", file!(), line!());
@@ -484,17 +481,24 @@ impl Scheme for ProcScheme {
}
}
})?;
} else {
// disable ptrace stop
with_context_mut(info.pid, |context| {
context.ptrace_stop = false;
Ok(())
})?;
}
// Set next breakpoint, and potentially restart tracee
if op.intersects(PTRACE_STOP_MASK) {
ptrace::set_breakpoint(info.pid, op, should_continue);
} else if should_continue {
ptrace::clear_breakpoint(info.pid);
}
if should_continue {
// disable the ptrace_stop flag, which is used in some cases
with_context_mut(info.pid, |context| {
context.ptrace_stop = false;
Ok(())
})?;
// and notify the tracee's WaitCondition, which is used in other cases
ptrace::notify(info.pid);
}
// And await the tracee, if requested to