Skip to content

Commit 4a800f7

Browse files
committed
Wrap raw read_register callback, and introduce a weird compiler error
1 parent 272090e commit 4a800f7

3 files changed

Lines changed: 29 additions & 9 deletions

File tree

src/gdbstub_impl/ext/single_register_access.rs

Lines changed: 9 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ use super::prelude::*;
22
use crate::protocol::commands::ext::SingleRegisterAccess;
33

44
use crate::arch::{Arch, RegId};
5-
use crate::target::ext::base::BaseOps;
5+
use crate::target::ext::base::{BaseOps, SendRegisterOutput};
66

77
impl<T: Target, C: Connection> GdbStubImpl<T, C> {
88
fn inner<Id>(
@@ -20,15 +20,17 @@ impl<T: Target, C: Connection> GdbStubImpl<T, C> {
2020
Some(v) => v,
2121
};
2222

23-
// TODO: Limit the number of bytes transferred on the wire to the register size
24-
// (if specified). Maybe pad the register if the callee does not
25-
// send enough data?
2623
let mut err = Ok(());
27-
ops.read_register(id, reg_id, &mut |buf| match res.write_hex_buf(buf) {
24+
let mut send_output = |buf| match res.write_hex_buf(buf) {
2825
Ok(_) => {}
2926
Err(e) => err = Err(e),
30-
})
31-
.handle_error()?;
27+
};
28+
29+
// TODO: Limit the number of bytes transferred on the wire to the register size
30+
// (if specified). Maybe pad the register if the callee does not
31+
// send enough data?
32+
ops.read_register(id, reg_id, SendRegisterOutput::new(&mut send_output))
33+
.handle_error()?;
3234

3335
err?;
3436

src/target/ext/base/mod.rs

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,9 @@ pub mod singlethread;
1010

1111
mod single_register_access;
1212

13-
pub use single_register_access::{SingleRegisterAccess, SingleRegisterAccessOps};
13+
pub use single_register_access::{
14+
SendRegisterOutput, SingleRegisterAccess, SingleRegisterAccessOps,
15+
};
1416

1517
/// Base operations for single/multi threaded targets.
1618
pub enum BaseOps<'a, A, E> {

src/target/ext/base/single_register_access.rs

Lines changed: 17 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,7 @@ pub trait SingleRegisterAccess<Id>: Target {
3535
&mut self,
3636
tid: Id,
3737
reg_id: <Self::Arch as Arch>::RegId,
38-
output: &mut dyn FnMut(&[u8]),
38+
output: SendRegisterOutput<'_>,
3939
) -> TargetResult<(), Self>;
4040

4141
/// Write from a single register on the target.
@@ -65,3 +65,19 @@ pub trait SingleRegisterAccess<Id>: Target {
6565
/// See [`SingleRegisterAccess`]
6666
pub type SingleRegisterAccessOps<'a, Id, T> =
6767
&'a mut dyn SingleRegisterAccess<Id, Arch = <T as Target>::Arch, Error = <T as Target>::Error>;
68+
69+
/// An interface to send register data to the GDB remote debugger.
70+
pub struct SendRegisterOutput<'a> {
71+
inner: &'a mut dyn FnMut(&[u8]),
72+
}
73+
74+
impl<'a> SendRegisterOutput<'a> {
75+
pub(crate) fn new(inner: &'a mut dyn FnMut(&[u8])) -> Self {
76+
Self { inner }
77+
}
78+
79+
/// Write out raw register bytes to the GDB debugger.
80+
pub fn write(&mut self, data: &[u8]) {
81+
(self.inner)(data)
82+
}
83+
}

0 commit comments

Comments
 (0)