Skip to content

Commit b7d5920

Browse files
committed
Merge pull request #424 from reem/stable-downcasting
chore(all): Move downcasting to a stable implementation.
2 parents 3dc8e7d + 320d10d commit b7d5920

File tree

4 files changed

+20
-17
lines changed

4 files changed

+20
-17
lines changed

Cargo.toml

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,8 @@ rustc-serialize = "*"
2222
time = "*"
2323
unicase = "*"
2424
url = "*"
25+
traitobject = "*"
26+
typeable = "*"
2527

2628
[dev-dependencies]
2729
env_logger = "*"

src/header/mod.rs

Lines changed: 4 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -6,14 +6,12 @@
66
//! are already provided, such as `Host`, `ContentType`, `UserAgent`, and others.
77
use std::any::Any;
88
use std::borrow::{Cow, ToOwned};
9-
use std::fmt;
109
use std::collections::HashMap;
1110
use std::collections::hash_map::{Iter, Entry};
1211
use std::iter::{FromIterator, IntoIterator};
13-
use std::raw::TraitObject;
14-
use std::{mem, raw};
12+
use std::{mem, fmt};
1513

16-
use httparse;
14+
use {httparse, traitobject};
1715
use unicase::UniCase;
1816

1917
use self::internals::Item;
@@ -76,12 +74,12 @@ impl<T: HeaderFormat + Send + Sync + Clone> HeaderClone for T {
7674
impl HeaderFormat + Send + Sync {
7775
#[inline]
7876
unsafe fn downcast_ref_unchecked<T: 'static>(&self) -> &T {
79-
mem::transmute(mem::transmute::<&HeaderFormat, raw::TraitObject>(self).data)
77+
mem::transmute(traitobject::data(self))
8078
}
8179

8280
#[inline]
8381
unsafe fn downcast_mut_unchecked<T: 'static>(&mut self) -> &mut T {
84-
mem::transmute(mem::transmute::<&mut HeaderFormat, raw::TraitObject>(self).data)
82+
mem::transmute(traitobject::data_mut(self))
8583
}
8684
}
8785

src/lib.rs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
#![cfg_attr(test, feature(test))]
66

77
//! # Hyper
8+
//!
89
//! Hyper is a fast, modern HTTP implementation written in and for Rust. It
910
//! is a low-level typesafe abstraction over raw HTTP, providing an elegant
1011
//! layer over "stringly-typed" HTTP.
@@ -134,6 +135,8 @@ extern crate cookie;
134135
extern crate unicase;
135136
extern crate httparse;
136137
extern crate num_cpus;
138+
extern crate traitobject;
139+
extern crate typeable;
137140

138141
#[macro_use]
139142
extern crate log;

src/net.rs

Lines changed: 11 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,6 @@ use std::io::{self, Read, Write};
55
use std::net::{SocketAddr, ToSocketAddrs, TcpStream, TcpListener};
66
use std::mem;
77
use std::path::Path;
8-
use std::raw::{self, TraitObject};
98
use std::sync::Arc;
109
use std::marker::Reflect;
1110

@@ -15,6 +14,9 @@ use openssl::ssl::SslMethod::Sslv23;
1514
use openssl::ssl::error::{SslError, StreamError, OpenSslErrors, SslSessionClosed};
1615
use openssl::x509::X509FileType;
1716

17+
use typeable::Typeable;
18+
use {traitobject};
19+
1820
macro_rules! try_some {
1921
($expr:expr) => (match $expr {
2022
Some(val) => { return Err(val); },
@@ -62,7 +64,7 @@ impl<'a, N: NetworkListener + 'a> Iterator for NetworkConnections<'a, N> {
6264

6365

6466
/// An abstraction over streams that a Server can utilize.
65-
pub trait NetworkStream: Read + Write + Any + StreamClone + Send {
67+
pub trait NetworkStream: Read + Write + Any + StreamClone + Send + Typeable {
6668
/// Get the remote address of the underlying connection.
6769
fn peer_addr(&mut self) -> io::Result<SocketAddr>;
6870
}
@@ -100,31 +102,29 @@ impl Clone for Box<NetworkStream + Send> {
100102

101103
impl NetworkStream + Send {
102104
unsafe fn downcast_ref_unchecked<T: 'static>(&self) -> &T {
103-
mem::transmute(mem::transmute::<&NetworkStream,
104-
raw::TraitObject>(self).data)
105+
mem::transmute(traitobject::data(self))
105106
}
106107

107108
unsafe fn downcast_mut_unchecked<T: 'static>(&mut self) -> &mut T {
108-
mem::transmute(mem::transmute::<&mut NetworkStream,
109-
raw::TraitObject>(self).data)
109+
mem::transmute(traitobject::data_mut(self))
110110
}
111111

112112
unsafe fn downcast_unchecked<T: 'static>(self: Box<NetworkStream + Send>) -> Box<T> {
113-
mem::transmute(mem::transmute::<Box<NetworkStream + Send>,
114-
raw::TraitObject>(self).data)
113+
let raw: *mut NetworkStream = mem::transmute(self);
114+
mem::transmute(traitobject::data_mut(raw))
115115
}
116116
}
117117

118118
impl NetworkStream + Send {
119119
/// Is the underlying type in this trait object a T?
120120
#[inline]
121-
pub fn is<T: Reflect + 'static>(&self) -> bool {
122-
self.get_type_id() == TypeId::of::<T>()
121+
pub fn is<T: Any>(&self) -> bool {
122+
(*self).get_type() == TypeId::of::<T>()
123123
}
124124

125125
/// If the underlying type is T, get a reference to the contained data.
126126
#[inline]
127-
pub fn downcast_ref<T: Reflect + 'static>(&self) -> Option<&T> {
127+
pub fn downcast_ref<T: Any>(&self) -> Option<&T> {
128128
if self.is::<T>() {
129129
Some(unsafe { self.downcast_ref_unchecked() })
130130
} else {

0 commit comments

Comments
 (0)