Skip to content

Commit 60833da

Browse files
committed
Context<S>, generic over io
* Update wrapper macros to support generic arg(s), not just lifetimes * Make Context generic over the underlying IO
1 parent cef4e69 commit 60833da

File tree

5 files changed

+152
-45
lines changed

5 files changed

+152
-45
lines changed

mbedtls-sys/vendor/library/ssl_tls.c

+1
Original file line numberDiff line numberDiff line change
@@ -3330,6 +3330,7 @@ static void ssl_calc_finished_tls_sha384(
33303330
* However, to avoid stringop-overflow warning in gcc, we have to cast
33313331
* mbedtls_sha512_finish_ret().
33323332
*/
3333+
// this still emits the warning on clang...
33333334
finish_sha384_t finish = (finish_sha384_t)mbedtls_sha512_finish_ret;
33343335
finish( &sha512, padbuf );
33353336

mbedtls/examples/client.rs

+2
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,9 @@ fn result_main(addr: &str) -> TlsResult<()> {
3333
config.set_ca_list(cert, None);
3434
let mut ctx = Context::new(Arc::new(config));
3535

36+
println!("connecting..");
3637
let conn = TcpStream::connect(addr).unwrap();
38+
println!("establishing SSL connection...");
3739
ctx.establish(conn, None)?;
3840

3941
let mut line = String::new();

mbedtls/src/ssl/config.rs

+1
Original file line numberDiff line numberDiff line change
@@ -320,6 +320,7 @@ impl Config {
320320
// - We can pointer cast to it to allow storing additional objects.
321321
//
322322
let cb = &mut *(closure as *mut F);
323+
// TODO is this cast still safe?
323324
let context = UnsafeFrom::from(ctx).unwrap();
324325

325326
let mut ctx = HandshakeContext::init(context);

mbedtls/src/ssl/context.rs

+38-36
Original file line numberDiff line numberDiff line change
@@ -70,12 +70,12 @@ impl<IO: Read + Write + 'static> IoCallback for IO {
7070
define!(
7171
#[c_ty(ssl_context)]
7272
#[repr(C)]
73-
struct Context {
73+
struct Context<S> {
7474
// config is used read-only for mutliple contexts and is immutable once configured.
7575
config: Arc<Config>,
7676

7777
// Must be held in heap and pointer to it as pointer is sent to MbedSSL and can't be re-allocated.
78-
io: Option<Box<dyn Any>>,
78+
io: Option<Box<S>>,
7979

8080
handshake_ca_cert: Option<Arc<MbedtlsList<Certificate>>>,
8181
handshake_crl: Option<Arc<Crl>>,
@@ -89,29 +89,8 @@ define!(
8989
impl<'a> UnsafeFrom<ptr> {}
9090
);
9191

92-
impl Context {
93-
pub fn new(config: Arc<Config>) -> Self {
94-
let mut inner = ssl_context::default();
95-
96-
unsafe {
97-
ssl_init(&mut inner);
98-
ssl_setup(&mut inner, (&*config).into());
99-
};
100-
101-
Context {
102-
inner,
103-
config: config.clone(),
104-
io: None,
105-
106-
handshake_ca_cert: None,
107-
handshake_crl: None,
108-
109-
handshake_cert: vec![],
110-
handshake_pk: vec![],
111-
}
112-
}
113-
114-
pub fn establish<T: IoCallback + Send + Sync + 'static>(&mut self, io: T, hostname: Option<&str>) -> Result<()> {
92+
impl<S: IoCallback> Context<S> {
93+
pub fn establish(&mut self, io: S, hostname: Option<&str>) -> Result<()> {
11594
unsafe {
11695
let mut io = Box::new(io);
11796
ssl_session_reset(self.into()).into_result()?;
@@ -121,8 +100,8 @@ impl Context {
121100
ssl_set_bio(
122101
self.into(),
123102
ptr,
124-
Some(T::call_send),
125-
Some(T::call_recv),
103+
Some(S::call_send),
104+
Some(S::call_recv),
126105
None,
127106
);
128107

@@ -146,6 +125,29 @@ impl Context {
146125
}
147126
}
148127
}
128+
}
129+
130+
impl<S> Context<S> {
131+
pub fn new(config: Arc<Config>) -> Self {
132+
let mut inner = ssl_context::default();
133+
134+
unsafe {
135+
ssl_init(&mut inner);
136+
ssl_setup(&mut inner, (&*config).into());
137+
};
138+
139+
Context {
140+
inner,
141+
config: config.clone(),
142+
io: None,
143+
144+
handshake_ca_cert: None,
145+
handshake_crl: None,
146+
147+
handshake_cert: vec![],
148+
handshake_pk: vec![],
149+
}
150+
}
149151

150152
#[cfg(not(feature = "std"))]
151153
fn set_hostname(&mut self, hostname: Option<&str>) -> Result<()> {
@@ -188,11 +190,11 @@ impl Context {
188190
}
189191
}
190192

191-
pub fn io(&self) -> Option<&dyn Any> {
192-
self.io.as_ref().map(|v| &**v)
193+
pub fn io(&self) -> Option<&Box<S>> {
194+
self.io.as_ref()
193195
}
194-
pub fn io_mut(&mut self) -> Option<&mut dyn Any> {
195-
self.io.as_mut().map(|v| &mut **v)
196+
pub fn io_mut(&mut self) -> Option<&mut Box<S>> {
197+
self.io.as_mut()
196198
}
197199

198200
/// Return the minor number of the negotiated TLS version
@@ -251,7 +253,7 @@ impl Context {
251253
}
252254
}
253255

254-
impl Drop for Context {
256+
impl<S> Drop for Context<S> {
255257
fn drop(&mut self) {
256258
unsafe {
257259
self.close();
@@ -260,7 +262,7 @@ impl Drop for Context {
260262
}
261263
}
262264

263-
impl Read for Context {
265+
impl<S> Read for Context<S> {
264266
fn read(&mut self, buf: &mut [u8]) -> IoResult<usize> {
265267
match unsafe { ssl_read(self.into(), buf.as_mut_ptr(), buf.len()).into_result() } {
266268
Err(Error::SslPeerCloseNotify) => Ok(0),
@@ -270,7 +272,7 @@ impl Read for Context {
270272
}
271273
}
272274

273-
impl Write for Context {
275+
impl<S> Write for Context<S> {
274276
fn write(&mut self, buf: &[u8]) -> IoResult<usize> {
275277
match unsafe { ssl_write(self.into(), buf.as_ptr(), buf.len()).into_result() } {
276278
Err(Error::SslPeerCloseNotify) => Ok(0),
@@ -286,7 +288,7 @@ impl Write for Context {
286288

287289

288290
pub struct HandshakeContext<'ctx> {
289-
pub context: &'ctx mut Context,
291+
pub context: &'ctx mut Context<Box<dyn Any>>,
290292
}
291293

292294
//
@@ -303,7 +305,7 @@ pub struct HandshakeContext<'ctx> {
303305
//
304306
impl<'ctx> HandshakeContext<'ctx> {
305307

306-
pub(crate) fn init(context: &'ctx mut Context) -> Self {
308+
pub(crate) fn init(context: &'ctx mut Context<Box<dyn Any>>) -> Self {
307309
HandshakeContext { context }
308310
}
309311

mbedtls/src/wrapper_macros.rs

+110-9
Original file line numberDiff line numberDiff line change
@@ -57,10 +57,15 @@ macro_rules! callback {
5757

5858
macro_rules! define {
5959
// When using members, careful with UnsafeFrom, the data casted back must have been allocated on rust side.
60-
{ #[c_ty($inner:ident)] $(#[$m:meta])* struct $name:ident$(<$l:tt>)* $({ $($(#[$mm:meta])* $member:ident: $member_type:ty,)* })?; $($defs:tt)* } => {
60+
{ #[c_ty($inner:ident)] $(#[$m:meta])* struct $name:ident$(<$l:lifetime>)* $({ $($(#[$mm:meta])* $member:ident: $member_type:ty,)* })?; $($defs:tt)* } => {
6161
define_struct!(define $(#[$m])* struct $name $(lifetime $l)* inner $inner members $($($(#[$mm])* $member: $member_type,)*)*);
6262
define_struct!(<< $name $(lifetime $l)* inner $inner >> $($defs)*);
6363
};
64+
// case for generic type
65+
{ #[c_ty($inner:ident)] $(#[$m:meta])* struct $name:ident$(<$g:tt>)* $({ $($(#[$mm:meta])* $member:ident: $member_type:ty,)* })?; $($defs:tt)* } => {
66+
define_struct!(define $(#[$m])* struct $name $(generic $g)* inner $inner members $($($(#[$mm])* $member: $member_type,)*)*);
67+
define_struct!(<< $name $(generic $g)* inner $inner >> $($defs)*);
68+
};
6469
// Do not use UnsafeFrom with 'c_box_ty'. That is currently not supported as its not needed anywhere, support may be added in the future if needed anywhere.
6570
{ #[c_box_ty($inner:ident)] $(#[$m:meta])* struct $name:ident$(<$l:tt>)* $({ $($(#[$mm:meta])* $member:ident: $member_type:ty,)* })?; $($defs:tt)* } => {
6671
define_struct!(define_box $(#[$m])* struct $name $(lifetime $l)* inner $inner members $($($(#[$mm])* $member: $member_type,)*)*);
@@ -109,7 +114,7 @@ macro_rules! define_enum {
109114
}
110115

111116
macro_rules! define_struct {
112-
{ define $(#[$m:meta])* struct $name:ident $(lifetime $l:tt)* inner $inner:ident members $($(#[$mm:meta])* $member:ident: $member_type:ty,)* } => {
117+
{ define $(#[$m:meta])* struct $name:ident $(lifetime $l:lifetime)* inner $inner:ident members $($(#[$mm:meta])* $member:ident: $member_type:ty,)* } => {
113118
as_item!(
114119
#[allow(dead_code)]
115120
$(#[$m])*
@@ -144,6 +149,40 @@ macro_rules! define_struct {
144149
);
145150
};
146151

152+
{ define $(#[$m:meta])* struct $name:ident $(generic $g:tt)* inner $inner:ident members $($(#[$mm:meta])* $member:ident: $member_type:ty,)* } => {
153+
as_item!(
154+
#[allow(dead_code)]
155+
$(#[$m])*
156+
pub struct $name<$($g)*> {
157+
inner: ::mbedtls_sys::$inner,
158+
$($(#[$mm])* $member: $member_type,)*
159+
}
160+
);
161+
162+
as_item!(
163+
#[allow(dead_code)]
164+
impl<$($g)*> $name<$($g)*> {
165+
pub(crate) fn into_inner(self) -> ::mbedtls_sys::$inner {
166+
let inner = self.inner;
167+
::core::mem::forget(self);
168+
inner
169+
}
170+
171+
pub(crate) fn handle(&self) -> &::mbedtls_sys::$inner {
172+
&self.inner
173+
}
174+
175+
pub(crate) fn handle_mut(&mut self) -> &mut ::mbedtls_sys::$inner {
176+
&mut self.inner
177+
}
178+
}
179+
);
180+
181+
as_item!(
182+
unsafe impl<$($g)*> Send for $name<$($g)*> {}
183+
);
184+
};
185+
147186
{ define_box $(#[$m:meta])* struct $name:ident $(lifetime $l:tt)* inner $inner:ident members $($(#[$mm:meta])* $member:ident: $member_type:ty,)* } => {
148187
as_item!(
149188
#[allow(dead_code)]
@@ -173,14 +212,22 @@ macro_rules! define_struct {
173212
);
174213
};
175214

176-
{ << $name:ident $(lifetime $l:tt)* inner $inner:ident >> const init: fn() -> Self = $ctor:ident $({ $($member:ident: $member_init:expr,)* })?; $($defs:tt)* } => {
215+
{ << $name:ident $(lifetime $l:lifetime)* inner $inner:ident >> const init: fn() -> Self = $ctor:ident $({ $($member:ident: $member_init:expr,)* })?; $($defs:tt)* } => {
177216
define_struct!(init $name () init $ctor $(lifetime $l)* members $($($member: $member_init,)*)* );
178217
define_struct!(<< $name $(lifetime $l)* inner $inner >> $($defs)*);
179218
};
180-
{ << $name:ident $(lifetime $l:tt)* inner $inner:ident >> pub const new: fn() -> Self = $ctor:ident $({ $($member:ident: $member_init:expr,)* })?; $($defs:tt)* } => {
219+
{ << $name:ident $(generic $g:tt)* inner $inner:ident >> const init: fn() -> Self = $ctor:ident $({ $($member:ident: $member_init:expr,)* })?; $($defs:tt)* } => {
220+
define_struct!(init $name () init $ctor $(generic $g)* members $($($member: $member_init,)*)* );
221+
define_struct!(<< $name $(generic $g)* inner $inner >> $($defs)*);
222+
};
223+
{ << $name:ident $(lifetime $l:lifetime)* inner $inner:ident >> pub const new: fn() -> Self = $ctor:ident $({ $($member:ident: $member_init:expr,)* })?; $($defs:tt)* } => {
181224
define_struct!(init $name (pub) new $ctor $(lifetime $l)* members $($($member: $member_init,)*)* );
182225
define_struct!(<< $name $(lifetime $l)* inner $inner >> $($defs)*);
183226
};
227+
{ << $name:ident $(generic $g:tt)* inner $inner:ident >> pub const new: fn() -> Self = $ctor:ident $({ $($member:ident: $member_init:expr,)* })?; $($defs:tt)* } => {
228+
define_struct!(init $name (pub) new $ctor $(generic $g)* members $($($member: $member_init,)*)* );
229+
define_struct!(<< $name $(generic $g)* inner $inner >> $($defs)*);
230+
};
184231
{ init $name:ident ($($vis:tt)*) $new:ident $ctor:ident $(lifetime $l:tt)* members $($member:ident: $member_init:expr,)* } => {
185232
as_item!(
186233
#[allow(dead_code)]
@@ -215,10 +262,14 @@ macro_rules! define_struct {
215262
);
216263
};
217264

218-
{ << $name:ident $(lifetime $l:tt)* inner $inner:ident >> impl<$l2:tt> Into<ptr> {} $($defs:tt)* } => {
265+
{ << $name:ident $(lifetime $l:lifetime)* inner $inner:ident >> impl<$l2:tt> Into<ptr> {} $($defs:tt)* } => {
219266
define_struct!(into $name inner $inner $(lifetime $l)* lifetime2 $l2 );
220267
define_struct!(<< $name $(lifetime $l)* inner $inner >> $($defs)*);
221268
};
269+
{ << $name:ident $(generic $g:tt)* inner $inner:ident >> impl<$l2:tt> Into<ptr> {} $($defs:tt)* } => {
270+
define_struct!(into $name inner $inner $(generic $g)* lifetime2 $l2 );
271+
define_struct!(<< $name $(generic $g)* inner $inner >> $($defs)*);
272+
};
222273
{ into $name:ident inner $inner:ident $(lifetime $l:tt)* lifetime2 $l2:tt } => {
223274
as_item!(
224275
impl<$l2,$($l),*> Into<*const $inner> for &$l2 $name<$($l)*> {
@@ -246,12 +297,43 @@ macro_rules! define_struct {
246297
}
247298
);
248299
};
300+
{ into $name:ident inner $inner:ident $(generic $g:tt)* lifetime2 $l2:tt } => {
301+
as_item!(
302+
impl<$l2,$($g),*> Into<*const $inner> for &$l2 $name<$($g)*> {
303+
fn into(self) -> *const $inner {
304+
self.handle()
305+
}
306+
}
307+
);
308+
309+
as_item!(
310+
impl<$l2,$($g),*> Into<*mut $inner> for &$l2 mut $name<$($g)*> {
311+
fn into(self) -> *mut $inner {
312+
self.handle_mut()
313+
}
314+
}
315+
);
316+
as_item!(
317+
impl<$($g),*> $name<$($g)*> {
318+
/// Needed for compatibility with mbedtls - where we could pass
319+
/// `*const` but function signature requires `*mut`
320+
#[allow(dead_code)]
321+
pub(crate) unsafe fn inner_ffi_mut(&self) -> *mut $inner {
322+
self.handle() as *const _ as *mut $inner
323+
}
324+
}
325+
);
326+
};
249327

250-
{ << $name:ident $(lifetime $l:tt)* inner $inner:ident >> impl<$l2:tt> UnsafeFrom<ptr> {} $($defs:tt)* } => {
328+
{ << $name:ident $(lifetime $l:lifetime)* inner $inner:ident >> impl<$l2:tt> UnsafeFrom<ptr> {} $($defs:tt)* } => {
251329
define_struct!(unsafe_from $name inner $inner $(lifetime $l)* lifetime2 $l2 );
252330
define_struct!(<< $name $(lifetime $l)* inner $inner >> $($defs)*);
253331
};
254-
{ unsafe_from $name:ident inner $inner:ident $(lifetime $l:tt)* lifetime2 $l2:tt } => {
332+
{ << $name:ident $(generic $g:tt)* inner $inner:ident >> impl<$l2:tt> UnsafeFrom<ptr> {} $($defs:tt)* } => {
333+
define_struct!(unsafe_from $name inner $inner $(generic $g)* lifetime2 $l2 );
334+
define_struct!(<< $name $(generic $g)* inner $inner >> $($defs)*);
335+
};
336+
{ unsafe_from $name:ident inner $inner:ident $(lifetime $l:lifetime)* lifetime2 $l2:tt } => {
255337
as_item!(
256338
impl<$l2,$($l),*> crate::private::UnsafeFrom<*const $inner> for &$l2 $name<$($l)*> {
257339
unsafe fn from(ptr: *const $inner) -> Option<Self> {
@@ -268,9 +350,28 @@ macro_rules! define_struct {
268350
}
269351
);
270352
};
353+
{ unsafe_from $name:ident inner $inner:ident $(generic $g:tt)* lifetime2 $l2:tt } => {
354+
as_item!(
355+
impl<$l2,$($g),*> crate::private::UnsafeFrom<*const $inner> for &$l2 $name<$($g)*> {
356+
unsafe fn from(ptr: *const $inner) -> Option<Self> {
357+
(ptr as *const $name<$($g),*>).as_ref()
358+
}
359+
}
360+
);
361+
362+
as_item!(
363+
impl<$l2,$($g),*> crate::private::UnsafeFrom<*mut $inner> for &$l2 mut $name<$($g)*> {
364+
unsafe fn from(ptr: *mut $inner) -> Option<Self> {
365+
(ptr as *mut $name<$($g),*>).as_mut()
366+
}
367+
}
368+
);
369+
};
271370

272-
{ << $name:ident $(lifetime $l:tt)* inner $inner:ident >> } => {};
273-
{ lifetime $l:tt } => {};
371+
{ << $name:ident $(lifetime $l:lifetime)* inner $inner:ident >> } => {};
372+
{ << $name:ident $(generic $g:tt)* inner $inner:ident >> } => {};
373+
{ lifetime $l:lifetime } => {};
374+
{ generic $g:tt } => {};
274375
}
275376

276377
macro_rules! setter {

0 commit comments

Comments
 (0)