1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
use error::NoiseError;
use handshakestate::HandshakeState;
use std::convert::{TryFrom, TryInto};
use transportstate::*;
pub trait NoiseSessionState {
fn is_payload_encrypted(&self) -> bool;
fn write_message(&mut self, payload: &[u8], output: &mut [u8]) -> Result<usize, NoiseError>;
fn read_message(&mut self, input: &[u8], payload: &mut [u8]) -> Result<usize, NoiseError>;
}
pub struct NoiseSession<S> where S: NoiseSessionState {
state: S,
}
impl TryFrom<NoiseSession<HandshakeState>> for NoiseSession<TransportState> {
type Err = NoiseError;
fn try_from(old: NoiseSession<HandshakeState>) -> Result<Self, Self::Err> {
let initiator = old.state.is_initiator();
let cipherstates = old.state.finish()?;
Ok(NoiseSession {
state: TransportState::new(cipherstates, initiator)
})
}
}
impl From<HandshakeState> for NoiseSession<HandshakeState> {
fn from(handshake_state: HandshakeState) -> Self {
Self {
state: handshake_state
}
}
}
impl NoiseSessionState for HandshakeState {
fn is_payload_encrypted(&self) -> bool {
self.is_write_encrypted()
}
fn write_message(&mut self, payload: &[u8], output: &mut [u8]) -> Result<usize, NoiseError> {
self.write_handshake_message(payload, output)
}
fn read_message(&mut self, input: &[u8], payload: &mut [u8]) -> Result<usize, NoiseError> {
self.read_handshake_message(input, payload)
}
}
impl NoiseSessionState for TransportState {
fn is_payload_encrypted(&self) -> bool {
true
}
fn write_message(&mut self, payload: &[u8], output: &mut [u8]) -> Result<usize, NoiseError> {
self.write_transport_message(payload, output)
}
fn read_message(&mut self, input: &[u8], payload: &mut [u8]) -> Result<usize, NoiseError> {
self.read_transport_message(input, payload)
}
}
impl NoiseSession<HandshakeState> {
pub fn is_handshake_finished(&self) -> bool {
self.state.is_finished()
}
pub fn into_transport_mode(self) -> Result<NoiseSession<TransportState>, NoiseError> {
if !self.state.is_finished() {
Err(NoiseError::StateError("handshake not yet finished"))
} else {
self.try_into()
}
}
}
impl<S: NoiseSessionState> NoiseSessionState for NoiseSession<S> {
fn is_payload_encrypted(&self) -> bool {
self.state.is_payload_encrypted()
}
fn write_message(&mut self, payload: &[u8], output: &mut [u8]) -> Result<usize, NoiseError> {
self.state.write_message(payload, output)
}
fn read_message(&mut self, input: &[u8], payload: &mut [u8]) -> Result<usize, NoiseError> {
self.state.read_message(input, payload)
}
}