aboutsummaryrefslogtreecommitdiff
path: root/src/ssl/lib.rs
diff options
context:
space:
mode:
Diffstat (limited to 'src/ssl/lib.rs')
-rw-r--r--src/ssl/lib.rs49
1 files changed, 32 insertions, 17 deletions
diff --git a/src/ssl/lib.rs b/src/ssl/lib.rs
index 5cc59330..4d79152b 100644
--- a/src/ssl/lib.rs
+++ b/src/ssl/lib.rs
@@ -1,3 +1,5 @@
+#[link(name="ssl")];
+
use std::rt::io::{Reader, Writer, Stream, Decorator};
use std::unstable::atomics::{AtomicBool, INIT_ATOMIC_BOOL, Acquire, Release};
use std::task;
@@ -60,16 +62,6 @@ impl SslCtx {
}
}
-struct Ssl {
- ssl: *ffi::SSL
-}
-
-impl Drop for Ssl {
- fn drop(&mut self) {
- unsafe { ffi::SSL_free(self.ssl); }
- }
-}
-
#[deriving(Eq, TotalEq, ToStr)]
enum SslError {
ErrorNone,
@@ -77,11 +69,22 @@ enum SslError {
ErrorWantRead,
ErrorWantWrite,
ErrorWantX509Lookup,
+ ErrorSyscall,
ErrorZeroReturn,
ErrorWantConnect,
ErrorWantAccept,
}
+struct Ssl {
+ ssl: *ffi::SSL
+}
+
+impl Drop for Ssl {
+ fn drop(&mut self) {
+ unsafe { ffi::SSL_free(self.ssl); }
+ }
+}
+
impl Ssl {
fn new(ctx: &SslCtx) -> Ssl {
let ssl = unsafe { ffi::SSL_new(ctx.ctx) };
@@ -109,10 +112,11 @@ impl Ssl {
ffi::SSL_ERROR_WANT_READ => ErrorWantRead,
ffi::SSL_ERROR_WANT_WRITE => ErrorWantWrite,
ffi::SSL_ERROR_WANT_X509_LOOKUP => ErrorWantX509Lookup,
+ ffi::SSL_ERROR_SYSCALL => ErrorSyscall,
ffi::SSL_ERROR_ZERO_RETURN => ErrorZeroReturn,
ffi::SSL_ERROR_WANT_CONNECT => ErrorWantConnect,
ffi::SSL_ERROR_WANT_ACCEPT => ErrorWantAccept,
- _ => unreachable!()
+ err => fail2!("Unknown error {}", err)
}
}
@@ -129,18 +133,17 @@ impl Ssl {
buf.len() as c_int) as int
}
}
+
+ fn shutdown(&self) -> int {
+ unsafe { ffi::SSL_shutdown(self.ssl) as int }
+ }
}
+// BIOs are freed by SSL_free
struct MemBio {
bio: *ffi::BIO
}
-impl Drop for MemBio {
- fn drop(&mut self) {
- unsafe { ffi::BIO_free(self.bio); }
- }
-}
-
impl MemBio {
fn new() -> MemBio {
let bio = unsafe { ffi::BIO_new(ffi::BIO_s_mem()) };
@@ -240,6 +243,18 @@ impl<S: Stream> SslStream<S> {
self.stream.write(self.buf.slice_to(len));
}
}
+
+ pub fn shutdown(&mut self) {
+ loop {
+ let ret = do self.in_retry_wrapper |ssl| {
+ ssl.ssl.shutdown()
+ };
+
+ if ret != Ok(0) {
+ break;
+ }
+ }
+ }
}
impl<S: Stream> Reader for SslStream<S> {