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
93
94
95
96
97
98
99
100
use std::collections::BTreeMap;
use std::str;
use decode;
use dictionary::Dictionary;
use error::{BencodeParseResult, BencodeParseError, BencodeParseErrorKind};
use encode;
pub enum BencodeKind<'b, 'a: 'b> {
Int(i64),
Bytes(&'a [u8]),
List(&'b [Bencode<'a>]),
Dict(&'b Dictionary<'a, Bencode<'a>>),
}
#[derive(Debug, Eq, PartialEq, Clone, Hash)]
pub enum Bencode<'a> {
Int(i64),
Bytes(&'a [u8]),
List(Vec<Bencode<'a>>),
Dict(BTreeMap<&'a [u8], Bencode<'a>>),
}
impl<'a> Bencode<'a> {
pub fn decode(bytes: &'a [u8]) -> BencodeParseResult<Bencode<'a>> {
let (bencode, end_pos) = try!(decode::decode(bytes, 0));
if end_pos != bytes.len() {
return Err(BencodeParseError::from_kind(BencodeParseErrorKind::BytesEmpty {
pos: Some(end_pos),
}));
}
Ok(bencode)
}
pub fn encode(&self) -> Vec<u8> {
encode::encode(self)
}
pub fn kind<'b>(&'b self) -> BencodeKind<'b, 'a> {
match self {
&Bencode::Int(n) => BencodeKind::Int(n),
&Bencode::Bytes(ref n) => BencodeKind::Bytes(n),
&Bencode::List(ref n) => BencodeKind::List(n),
&Bencode::Dict(ref n) => BencodeKind::Dict(n),
}
}
pub fn str(&self) -> Option<&'a str> {
let bytes = match self.bytes() {
Some(n) => n,
None => return None,
};
match str::from_utf8(bytes) {
Ok(n) => Some(n),
Err(_) => None,
}
}
pub fn int(&self) -> Option<i64> {
match self {
&Bencode::Int(n) => Some(n),
_ => None,
}
}
pub fn bytes(&self) -> Option<&'a [u8]> {
match self {
&Bencode::Bytes(ref n) => Some(&n[0..]),
_ => None,
}
}
pub fn list(&self) -> Option<&[Bencode<'a>]> {
match self {
&Bencode::List(ref n) => Some(n),
_ => None,
}
}
pub fn dict(&self) -> Option<&Dictionary<'a, Bencode<'a>>> {
match self {
&Bencode::Dict(ref n) => Some(n),
_ => None,
}
}
}