added serializer for database. removed unused code.
This commit is contained in:
parent
f356201323
commit
703dfbb57d
1
Cargo.lock
generated
1
Cargo.lock
generated
|
@ -1447,6 +1447,7 @@ dependencies = [
|
||||||
"num_cpus 1.8.0 (registry+https://github.com/rust-lang/crates.io-index)",
|
"num_cpus 1.8.0 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
"serde 1.0.80 (registry+https://github.com/rust-lang/crates.io-index)",
|
"serde 1.0.80 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
"serde_derive 1.0.80 (registry+https://github.com/rust-lang/crates.io-index)",
|
"serde_derive 1.0.80 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
|
"serde_json 1.0.32 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
"toml 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)",
|
"toml 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
|
@ -18,3 +18,4 @@ clap = "2.32.0"
|
||||||
log = "0.4.5"
|
log = "0.4.5"
|
||||||
fern = "0.5.6"
|
fern = "0.5.6"
|
||||||
num_cpus = "1.8.0"
|
num_cpus = "1.8.0"
|
||||||
|
serde_json = "1.0.32"
|
||||||
|
|
|
@ -10,12 +10,12 @@ extern crate toml;
|
||||||
#[macro_use] extern crate log;
|
#[macro_use] extern crate log;
|
||||||
extern crate fern;
|
extern crate fern;
|
||||||
extern crate num_cpus;
|
extern crate num_cpus;
|
||||||
|
extern crate serde_json;
|
||||||
|
|
||||||
mod server;
|
mod server;
|
||||||
mod tracker;
|
mod tracker;
|
||||||
mod stackvec;
|
mod stackvec;
|
||||||
mod webserver;
|
mod webserver;
|
||||||
mod service;
|
|
||||||
mod config;
|
mod config;
|
||||||
|
|
||||||
use std::process::exit;
|
use std::process::exit;
|
||||||
|
|
118
src/tracker.rs
118
src/tracker.rs
|
@ -1,4 +1,6 @@
|
||||||
use std;
|
use std;
|
||||||
|
use binascii;
|
||||||
|
use serde::{self, Serialize, Deserialize};
|
||||||
|
|
||||||
use server::Events;
|
use server::Events;
|
||||||
|
|
||||||
|
@ -30,69 +32,16 @@ struct TorrentPeer {
|
||||||
pub type PeerId = [u8; 20];
|
pub type PeerId = [u8; 20];
|
||||||
pub type InfoHash = [u8; 20];
|
pub type InfoHash = [u8; 20];
|
||||||
|
|
||||||
pub trait HexConv {
|
#[derive(Serialize, Deserialize)]
|
||||||
fn to_hex(&self) -> String;
|
|
||||||
fn from_hex(hex: &str) -> Option<InfoHash>;
|
|
||||||
}
|
|
||||||
|
|
||||||
impl HexConv for InfoHash {
|
|
||||||
fn to_hex(&self) -> String {
|
|
||||||
const HEX: &[char] = &['0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'a', 'b', 'c', 'd', 'e', 'f'];
|
|
||||||
let data = self;
|
|
||||||
let mut res = String::with_capacity(data.len() * 2);
|
|
||||||
for b in data {
|
|
||||||
res.push(HEX[((b >> 4) & 0x0fu8) as usize]);
|
|
||||||
res.push(HEX[(b & 0x0fu8) as usize]);
|
|
||||||
}
|
|
||||||
return res;
|
|
||||||
}
|
|
||||||
|
|
||||||
fn from_hex(hex: &str) -> Option<InfoHash> {
|
|
||||||
let mut res : InfoHash = [0u8; 20];
|
|
||||||
if hex.len() != 2 * res.len() {
|
|
||||||
return None;
|
|
||||||
}
|
|
||||||
|
|
||||||
let mut tmp = 0;
|
|
||||||
let mut idx = 0;
|
|
||||||
|
|
||||||
for ch in hex.chars() {
|
|
||||||
if idx % 2 == 1 {
|
|
||||||
tmp <<= 4;
|
|
||||||
}
|
|
||||||
|
|
||||||
let mut num = ch as u32;
|
|
||||||
if ch >= '0' && ch <= '9' {
|
|
||||||
num -= '0' as u32;
|
|
||||||
} else if ch >= 'a' && ch <= 'f' {
|
|
||||||
num -= 'a' as u32;
|
|
||||||
num += 10;
|
|
||||||
} else if ch >= 'A' && ch <= 'F' {
|
|
||||||
num -= 'A' as u32;
|
|
||||||
num += 10;
|
|
||||||
} else {
|
|
||||||
return None;
|
|
||||||
}
|
|
||||||
|
|
||||||
tmp |= num & 0x0f;
|
|
||||||
|
|
||||||
if idx % 2 == 1 {
|
|
||||||
res[(idx - 1) / 2] = tmp as u8;
|
|
||||||
tmp = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
idx += 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
return Some(res);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
pub struct TorrentEntry {
|
pub struct TorrentEntry {
|
||||||
is_flagged: bool,
|
is_flagged: bool,
|
||||||
|
|
||||||
|
#[serde(skip)]
|
||||||
peers: std::collections::BTreeMap<PeerId, TorrentPeer>,
|
peers: std::collections::BTreeMap<PeerId, TorrentPeer>,
|
||||||
|
|
||||||
completed: u32,
|
completed: u32,
|
||||||
|
|
||||||
|
#[serde(skip)]
|
||||||
seeders: u32,
|
seeders: u32,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -163,6 +112,45 @@ struct TorrentDatabase {
|
||||||
torrent_peers: std::sync::RwLock<std::collections::BTreeMap<InfoHash, TorrentEntry>>,
|
torrent_peers: std::sync::RwLock<std::collections::BTreeMap<InfoHash, TorrentEntry>>,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl Default for TorrentDatabase {
|
||||||
|
fn default() -> Self {
|
||||||
|
TorrentDatabase{
|
||||||
|
torrent_peers: std::sync::RwLock::new(std::collections::BTreeMap::new()),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Serialize for TorrentDatabase {
|
||||||
|
fn serialize<S: serde::Serializer>(&self, serializer: S) -> Result<S::Ok, S::Error> {
|
||||||
|
use serde::ser::SerializeMap;
|
||||||
|
use binascii::bin2hex;
|
||||||
|
|
||||||
|
let db = match self.torrent_peers.read() {
|
||||||
|
Ok(v) => v,
|
||||||
|
Err(err) => {
|
||||||
|
error!("Failed to lock database for reading. {}", err);
|
||||||
|
panic!("fatal error. check logs.");
|
||||||
|
}
|
||||||
|
};
|
||||||
|
let mut info_hash_buffer = [0u8; 40];
|
||||||
|
|
||||||
|
let mut map = serializer.serialize_map(None)?;
|
||||||
|
|
||||||
|
for entry in db.iter() {
|
||||||
|
let info_hash = match bin2hex(entry.0, &mut info_hash_buffer) {
|
||||||
|
Ok(v) => std::str::from_utf8(v).unwrap(),
|
||||||
|
Err(err) => {
|
||||||
|
error!("Failed to serialize database key.");
|
||||||
|
panic!("fatal error. check logs.")
|
||||||
|
}
|
||||||
|
};
|
||||||
|
map.serialize_entry(info_hash, entry.1)?;
|
||||||
|
}
|
||||||
|
|
||||||
|
map.end()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
pub struct TorrentTracker {
|
pub struct TorrentTracker {
|
||||||
mode: TrackerMode,
|
mode: TrackerMode,
|
||||||
database: TorrentDatabase,
|
database: TorrentDatabase,
|
||||||
|
@ -299,18 +287,4 @@ mod tests {
|
||||||
fn tracker_sync() {
|
fn tracker_sync() {
|
||||||
is_sync::<TorrentTracker>();
|
is_sync::<TorrentTracker>();
|
||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
|
||||||
fn test_ih2hex() {
|
|
||||||
let ih: InfoHash = [1u8, 2, 3, 4, 5, 6, 7, 8, 9, 0xa,
|
|
||||||
0xb, 0xc, 0xd, 0xe, 0xf, 0x10, 0x11, 0x12, 0x13, 0xff];
|
|
||||||
assert!(ih.to_hex() == "0102030405060708090a0b0c0d0e0f10111213ff");
|
|
||||||
}
|
|
||||||
|
|
||||||
#[test]
|
|
||||||
fn test_hex2ih() {
|
|
||||||
let ih = InfoHash::from_hex("0102030405060708090a0b0c0d0e0f10111213ff").unwrap();
|
|
||||||
assert_eq!(ih, [1u8, 2, 3, 4, 5, 6, 7, 8, 9, 0xa,
|
|
||||||
0xb, 0xc, 0xd, 0xe, 0xf, 0x10, 0x11, 0x12, 0x13, 0xff]);
|
|
||||||
}
|
|
||||||
}
|
}
|
Loading…
Reference in a new issue