From cc9f0788aabebb6e55102bc98edf21fca9f5b043 Mon Sep 17 00:00:00 2001 From: Greg Fitzgerald Date: Fri, 9 Mar 2018 16:16:29 -0700 Subject: [PATCH 1/4] Batch events It's now a Tick that locks down event order. Before this change, the event order would be locked down in the order the server sees it. Fixes #59 Fixes #61 --- Cargo.lock | 2 +- src/accountant.rs | 6 +++-- src/accountant_stub.rs | 10 ++++---- src/bin/genesis-demo.rs | 16 ++++++------- src/entry.rs | 51 ++++++++++++++++++++++++----------------- src/log.rs | 49 ++++++++++++++++++--------------------- src/logger.rs | 22 ++++++++++++------ src/mint.rs | 11 ++++----- 8 files changed, 91 insertions(+), 76 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index a38d95457e..9de0b7c05f 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -355,7 +355,7 @@ dependencies = [ [[package]] name = "silk" -version = "0.3.3" +version = "0.4.0" dependencies = [ "bincode 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)", "chrono 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", diff --git a/src/accountant.rs b/src/accountant.rs index d63672adfb..efb80f3499 100644 --- a/src/accountant.rs +++ b/src/accountant.rs @@ -61,10 +61,12 @@ impl Accountant { // fields are the same. That entry should be treated as a deposit, not a // transfer to oneself. let entry1 = entries.next().unwrap(); - acc.process_verified_event(&entry1.event, true).unwrap(); + acc.process_verified_event(&entry1.events[0], true).unwrap(); for entry in entries { - acc.process_verified_event(&entry.event, false).unwrap(); + for event in entry.events { + acc.process_verified_event(&event, false).unwrap(); + } } acc } diff --git a/src/accountant_stub.rs b/src/accountant_stub.rs index bc842474f5..cc8740d455 100644 --- a/src/accountant_stub.rs +++ b/src/accountant_stub.rs @@ -93,11 +93,13 @@ impl AccountantStub { self.socket.recv_from(&mut buf)?; let resp = deserialize(&buf).expect("deserialize signature"); if let Response::Entries { entries } = resp { - for Entry { id, event, .. } in entries { + for Entry { id, events, .. } in entries { self.last_id = Some(id); - if let Some(sig) = event.get_signature() { - if sig == *wait_sig { - return Ok(()); + for event in events { + if let Some(sig) = event.get_signature() { + if sig == *wait_sig { + return Ok(()); + } } } } diff --git a/src/bin/genesis-demo.rs b/src/bin/genesis-demo.rs index ad3772d53c..ca53378a9b 100644 --- a/src/bin/genesis-demo.rs +++ b/src/bin/genesis-demo.rs @@ -4,7 +4,7 @@ extern crate silk; use silk::mint::Mint; use silk::event::Event; use silk::transaction::Transaction; -use silk::log::create_entries; +use silk::entry::create_entry; use silk::signature::{KeyPair, KeyPairUtil, PublicKey}; use silk::hash::Hash; use std::io::stdin; @@ -14,17 +14,17 @@ fn transfer(from: &KeyPair, (to, tokens): (PublicKey, i64), last_id: Hash) -> Ev } fn main() { - let alice = (KeyPair::new().pubkey(), 200); - let bob = (KeyPair::new().pubkey(), 100); - let mint: Mint = serde_json::from_reader(stdin()).unwrap(); + let mut entries = mint.create_entries(); + let from = mint.keypair(); let seed = mint.seed(); - let mut events = mint.create_events(); - events.push(transfer(&from, alice, seed)); - events.push(transfer(&from, bob, seed)); + let alice = (KeyPair::new().pubkey(), 200); + let bob = (KeyPair::new().pubkey(), 100); + let events = vec![transfer(&from, alice, seed), transfer(&from, bob, seed)]; + entries.push(create_entry(&seed, 0, events)); - for entry in create_entries(&seed, events) { + for entry in entries { println!("{}", serde_json::to_string(&entry).unwrap()); } } diff --git a/src/entry.rs b/src/entry.rs index 67a6ea7ae8..14bc6e8c71 100644 --- a/src/entry.rs +++ b/src/entry.rs @@ -5,7 +5,7 @@ use event::Event; pub struct Entry { pub num_hashes: u64, pub id: Hash, - pub event: Event, + pub events: Vec, } impl Entry { @@ -15,51 +15,61 @@ impl Entry { Entry { num_hashes, id: *id, - event: Event::Tick, + events: vec![], } } /// Verifies self.id is the result of hashing a 'start_hash' 'self.num_hashes' times. /// If the event is not a Tick, then hash that as well. pub fn verify(&self, start_hash: &Hash) -> bool { - if !self.event.verify() { - return false; + for event in &self.events { + if !event.verify() { + return false; + } } - self.id == next_hash(start_hash, self.num_hashes, &self.event) + self.id == next_hash(start_hash, self.num_hashes, &self.events) } } /// Creates the hash 'num_hashes' after start_hash. If the event contains /// signature, the final hash will be a hash of both the previous ID and /// the signature. -pub fn next_hash(start_hash: &Hash, num_hashes: u64, event: &Event) -> Hash { +pub fn next_hash(start_hash: &Hash, num_hashes: u64, events: &[Event]) -> Hash { let mut id = *start_hash; - let sig = event.get_signature(); - let start_index = if sig.is_some() { 1 } else { 0 }; - for _ in start_index..num_hashes { + for _ in 1..num_hashes { id = hash(&id); } - if let Some(sig) = sig { - id = extend_and_hash(&id, &sig); + + // Hash all the event data + let mut hash_data = vec![]; + for event in events { + let sig = event.get_signature(); + if let Some(sig) = sig { + hash_data.extend_from_slice(&sig); + } } + + if !hash_data.is_empty() { + return extend_and_hash(&id, &hash_data); + } + id } /// Creates the next Entry 'num_hashes' after 'start_hash'. -pub fn create_entry(start_hash: &Hash, cur_hashes: u64, event: Event) -> Entry { - let sig = event.get_signature(); - let num_hashes = cur_hashes + if sig.is_some() { 1 } else { 0 }; - let id = next_hash(start_hash, 0, &event); +pub fn create_entry(start_hash: &Hash, cur_hashes: u64, events: Vec) -> Entry { + let num_hashes = cur_hashes + if events.is_empty() { 0 } else { 1 }; + let id = next_hash(start_hash, 0, &events); Entry { num_hashes, id, - event, + events, } } /// Creates the next Tick Entry 'num_hashes' after 'start_hash'. -pub fn create_entry_mut(start_hash: &mut Hash, cur_hashes: &mut u64, event: Event) -> Entry { - let entry = create_entry(start_hash, *cur_hashes, event); +pub fn create_entry_mut(start_hash: &mut Hash, cur_hashes: &mut u64, events: Vec) -> Entry { + let entry = create_entry(start_hash, *cur_hashes, events); *start_hash = entry.id; *cur_hashes = 0; entry @@ -67,11 +77,10 @@ pub fn create_entry_mut(start_hash: &mut Hash, cur_hashes: &mut u64, event: Even /// Creates the next Tick Entry 'num_hashes' after 'start_hash'. pub fn next_tick(start_hash: &Hash, num_hashes: u64) -> Entry { - let event = Event::Tick; Entry { num_hashes, - id: next_hash(start_hash, num_hashes, &event), - event, + id: next_hash(start_hash, num_hashes, &[]), + events: vec![], } } diff --git a/src/log.rs b/src/log.rs index b01450cb50..9632714639 100644 --- a/src/log.rs +++ b/src/log.rs @@ -14,23 +14,19 @@ /// was generated by the fastest processor at the time the entry was logged. use hash::Hash; -use entry::{create_entry_mut, next_tick, Entry}; +use entry::{create_entry, next_tick, Entry}; use event::Event; use rayon::prelude::*; /// Verifies the hashes and counts of a slice of events are all consistent. -pub fn verify_slice(events: &[Entry], start_hash: &Hash) -> bool { +pub fn verify_slice(entries: &[Entry], start_hash: &Hash) -> bool { let genesis = [Entry::new_tick(Default::default(), start_hash)]; - let event_pairs = genesis.par_iter().chain(events).zip(events); + let event_pairs = genesis.par_iter().chain(entries).zip(entries); event_pairs.all(|(x0, x1)| x1.verify(&x0.id)) } pub fn create_entries(start_hash: &Hash, events: Vec) -> Vec { - let mut id = *start_hash; - events - .into_iter() - .map(|event| create_entry_mut(&mut id, &mut 0, event)) - .collect() + vec![create_entry(start_hash, 0, events)] } /// Create a vector of Ticks of length 'len' from 'start_hash' hash and 'num_hashes'. @@ -48,8 +44,6 @@ pub fn next_ticks(start_hash: &Hash, num_hashes: u64, len: usize) -> Vec #[cfg(test)] mod tests { use super::*; - use signature::{KeyPair, KeyPairUtil}; - use transaction::Transaction; use hash::hash; #[test] @@ -66,25 +60,26 @@ mod tests { assert!(!verify_slice(&bad_ticks, &zero)); // inductive step, bad } - #[test] - fn test_reorder_attack() { - let zero = Hash::default(); + // TODO: This is no longer relevant. Instead, test for reordered ticks. + //#[test] + //fn test_reorder_attack() { + // let zero = Hash::default(); - // First, verify entries - let keypair = KeyPair::new(); - let tr0 = Transaction::new(&keypair, keypair.pubkey(), 0, zero); - let tr1 = Transaction::new(&keypair, keypair.pubkey(), 1, zero); - let events = vec![Event::Transaction(tr0), Event::Transaction(tr1)]; - let mut entries = create_entries(&zero, events); - assert!(verify_slice(&entries, &zero)); + // // First, verify entries + // let keypair = KeyPair::new(); + // let tr0 = Transaction::new(&keypair, keypair.pubkey(), 0, zero); + // let tr1 = Transaction::new(&keypair, keypair.pubkey(), 1, zero); + // let events = vec![Event::Transaction(tr0), Event::Transaction(tr1)]; + // let mut entries = create_entries(&zero, events); + // assert!(verify_slice(&entries, &zero)); - // Next, swap two events and ensure verification fails. - let event0 = entries[0].event.clone(); - let event1 = entries[1].event.clone(); - entries[0].event = event1; - entries[1].event = event0; - assert!(!verify_slice(&entries, &zero)); - } + // // Next, swap two events and ensure verification fails. + // let event0 = entries[0].event.clone(); + // let event1 = entries[1].event.clone(); + // entries[0].event = event1; + // entries[1].event = event0; + // assert!(!verify_slice(&entries, &zero)); + //} } #[cfg(all(feature = "unstable", test))] diff --git a/src/logger.rs b/src/logger.rs index b5affd2901..6a90c340c8 100644 --- a/src/logger.rs +++ b/src/logger.rs @@ -7,6 +7,7 @@ use std::sync::mpsc::{Receiver, SyncSender, TryRecvError}; use std::time::{Duration, Instant}; +use std::mem; use hash::Hash; use entry::{create_entry_mut, Entry}; use event::Event; @@ -22,6 +23,7 @@ pub struct Logger { pub sender: SyncSender, pub receiver: Receiver, pub last_id: Hash, + pub events: Vec, pub num_hashes: u64, pub num_ticks: u64, } @@ -32,13 +34,15 @@ impl Logger { receiver, sender, last_id: start_hash, + events: vec![], num_hashes: 0, num_ticks: 0, } } - pub fn log_event(&mut self, event: Event) -> Result { - let entry = create_entry_mut(&mut self.last_id, &mut self.num_hashes, event); + pub fn log_entry(&mut self) -> Result { + let events = mem::replace(&mut self.events, vec![]); + let entry = create_entry_mut(&mut self.last_id, &mut self.num_hashes, events); println!("{}", serde_json::to_string(&entry).unwrap()); Ok(entry) } @@ -51,17 +55,21 @@ impl Logger { loop { if let Some(ms) = ms_per_tick { if epoch.elapsed() > Duration::from_millis((self.num_ticks + 1) * ms) { - self.log_event(Event::Tick)?; + self.log_entry()?; self.num_ticks += 1; } } match self.receiver.try_recv() { Ok(event) => { - let entry = self.log_event(event)?; - self.sender - .send(entry) - .or(Err(ExitReason::SendDisconnected))?; + if let Event::Tick = event { + let entry = self.log_entry()?; + self.sender + .send(entry) + .or(Err(ExitReason::SendDisconnected))?; + } else { + self.events.push(event); + } } Err(TryRecvError::Empty) => return Ok(()), Err(TryRecvError::Disconnected) => return Err(ExitReason::RecvDisconnected), diff --git a/src/mint.rs b/src/mint.rs index 6beeeea986..991a1cb8c1 100644 --- a/src/mint.rs +++ b/src/mint.rs @@ -4,7 +4,7 @@ use event::Event; use transaction::Transaction; use signature::{KeyPair, KeyPairUtil, PublicKey}; use entry::Entry; -use log::create_entries; +use entry::create_entry; use hash::{hash, Hash}; use ring::rand::SystemRandom; use untrusted::Input; @@ -44,11 +44,13 @@ impl Mint { pub fn create_events(&self) -> Vec { let keypair = self.keypair(); let tr = Transaction::new(&keypair, self.pubkey(), self.tokens, self.seed()); - vec![Event::Tick, Event::Transaction(tr)] + vec![Event::Transaction(tr)] } pub fn create_entries(&self) -> Vec { - create_entries(&self.seed(), self.create_events()) + let e0 = create_entry(&self.seed(), 0, vec![]); + let e1 = create_entry(&e0.id, 0, self.create_events()); + vec![e0, e1] } } @@ -60,11 +62,8 @@ mod tests { #[test] fn test_create_events() { let mut events = Mint::new(100).create_events().into_iter(); - assert_eq!(events.next().unwrap(), Event::Tick); if let Event::Transaction(tr) = events.next().unwrap() { assert_eq!(tr.from, tr.to); - } else { - assert!(false); } assert_eq!(events.next(), None); } From b8cd5f04820509bface6f4617df1af702b9fce2f Mon Sep 17 00:00:00 2001 From: Greg Fitzgerald Date: Fri, 9 Mar 2018 16:26:23 -0700 Subject: [PATCH 2/4] Boot Cargo.lock from git Only add Cargo.lock to downstream dependencies. --- .gitignore | 2 +- Cargo.lock | 482 ----------------------------------------------------- 2 files changed, 1 insertion(+), 483 deletions(-) delete mode 100644 Cargo.lock diff --git a/.gitignore b/.gitignore index 0196246bdd..f8d7348a3e 100644 --- a/.gitignore +++ b/.gitignore @@ -1,3 +1,3 @@ - +Cargo.lock /target/ **/*.rs.bk diff --git a/Cargo.lock b/Cargo.lock deleted file mode 100644 index 9de0b7c05f..0000000000 --- a/Cargo.lock +++ /dev/null @@ -1,482 +0,0 @@ -[[package]] -name = "arrayref" -version = "0.3.4" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "arrayvec" -version = "0.4.7" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "nodrop 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "bincode" -version = "1.0.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "byteorder 1.2.1 (registry+https://github.com/rust-lang/crates.io-index)", - "serde 1.0.28 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "bitflags" -version = "1.0.1" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "block-buffer" -version = "0.3.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "arrayref 0.3.4 (registry+https://github.com/rust-lang/crates.io-index)", - "byte-tools 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "byte-tools" -version = "0.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "byteorder" -version = "1.2.1" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "cfg-if" -version = "0.1.2" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "chrono" -version = "0.4.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "num 0.1.42 (registry+https://github.com/rust-lang/crates.io-index)", - "serde 1.0.28 (registry+https://github.com/rust-lang/crates.io-index)", - "time 0.1.39 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "crossbeam-deque" -version = "0.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "crossbeam-epoch 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)", - "crossbeam-utils 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "crossbeam-epoch" -version = "0.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "arrayvec 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)", - "cfg-if 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", - "crossbeam-utils 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)", - "lazy_static 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)", - "memoffset 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)", - "nodrop 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)", - "scopeguard 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "crossbeam-utils" -version = "0.2.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "cfg-if 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "digest" -version = "0.7.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "generic-array 0.9.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "dtoa" -version = "0.4.2" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "either" -version = "1.4.0" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "fake-simd" -version = "0.1.2" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "fuchsia-zircon" -version = "0.3.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "bitflags 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)", - "fuchsia-zircon-sys 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "fuchsia-zircon-sys" -version = "0.3.3" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "gcc" -version = "0.3.54" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "generic-array" -version = "0.8.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "nodrop 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)", - "typenum 1.9.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "generic-array" -version = "0.9.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "serde 1.0.28 (registry+https://github.com/rust-lang/crates.io-index)", - "typenum 1.9.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "itoa" -version = "0.3.4" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "lazy_static" -version = "0.2.11" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "lazy_static" -version = "1.0.0" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "libc" -version = "0.2.39" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "memoffset" -version = "0.2.1" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "nodrop" -version = "0.1.12" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "num" -version = "0.1.42" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "num-integer 0.1.36 (registry+https://github.com/rust-lang/crates.io-index)", - "num-iter 0.1.35 (registry+https://github.com/rust-lang/crates.io-index)", - "num-traits 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "num-integer" -version = "0.1.36" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "num-traits 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "num-iter" -version = "0.1.35" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "num-integer 0.1.36 (registry+https://github.com/rust-lang/crates.io-index)", - "num-traits 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "num-traits" -version = "0.2.1" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "num_cpus" -version = "1.8.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "libc 0.2.39 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "proc-macro2" -version = "0.2.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "unicode-xid 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "quote" -version = "0.4.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "proc-macro2 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "rand" -version = "0.4.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "fuchsia-zircon 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)", - "libc 0.2.39 (registry+https://github.com/rust-lang/crates.io-index)", - "winapi 0.3.4 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "rayon" -version = "0.8.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "rayon-core 1.4.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "rayon" -version = "1.0.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "either 1.4.0 (registry+https://github.com/rust-lang/crates.io-index)", - "rayon-core 1.4.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "rayon-core" -version = "1.4.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "crossbeam-deque 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", - "lazy_static 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)", - "libc 0.2.39 (registry+https://github.com/rust-lang/crates.io-index)", - "num_cpus 1.8.0 (registry+https://github.com/rust-lang/crates.io-index)", - "rand 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "redox_syscall" -version = "0.1.37" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "ring" -version = "0.12.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "gcc 0.3.54 (registry+https://github.com/rust-lang/crates.io-index)", - "lazy_static 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)", - "libc 0.2.39 (registry+https://github.com/rust-lang/crates.io-index)", - "rayon 0.8.2 (registry+https://github.com/rust-lang/crates.io-index)", - "untrusted 0.5.1 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "scopeguard" -version = "0.3.3" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "serde" -version = "1.0.28" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "serde_derive" -version = "1.0.28" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "proc-macro2 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", - "quote 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)", - "serde_derive_internals 0.20.0 (registry+https://github.com/rust-lang/crates.io-index)", - "syn 0.12.13 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "serde_derive_internals" -version = "0.20.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "proc-macro2 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", - "syn 0.12.13 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "serde_json" -version = "1.0.10" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "dtoa 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)", - "itoa 0.3.4 (registry+https://github.com/rust-lang/crates.io-index)", - "num-traits 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)", - "serde 1.0.28 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "sha2" -version = "0.7.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "block-buffer 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)", - "byte-tools 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", - "digest 0.7.2 (registry+https://github.com/rust-lang/crates.io-index)", - "fake-simd 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "sha2-asm" -version = "0.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "gcc 0.3.54 (registry+https://github.com/rust-lang/crates.io-index)", - "generic-array 0.8.3 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "silk" -version = "0.4.0" -dependencies = [ - "bincode 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)", - "chrono 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", - "generic-array 0.9.0 (registry+https://github.com/rust-lang/crates.io-index)", - "rayon 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)", - "ring 0.12.1 (registry+https://github.com/rust-lang/crates.io-index)", - "serde 1.0.28 (registry+https://github.com/rust-lang/crates.io-index)", - "serde_derive 1.0.28 (registry+https://github.com/rust-lang/crates.io-index)", - "serde_json 1.0.10 (registry+https://github.com/rust-lang/crates.io-index)", - "sha2 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)", - "sha2-asm 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)", - "untrusted 0.5.1 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "syn" -version = "0.12.13" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "proc-macro2 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", - "quote 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)", - "unicode-xid 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "time" -version = "0.1.39" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "libc 0.2.39 (registry+https://github.com/rust-lang/crates.io-index)", - "redox_syscall 0.1.37 (registry+https://github.com/rust-lang/crates.io-index)", - "winapi 0.3.4 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "typenum" -version = "1.9.0" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "unicode-xid" -version = "0.1.0" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "untrusted" -version = "0.5.1" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "winapi" -version = "0.3.4" -source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "winapi-i686-pc-windows-gnu 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", - "winapi-x86_64-pc-windows-gnu 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[[package]] -name = "winapi-i686-pc-windows-gnu" -version = "0.4.0" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[[package]] -name = "winapi-x86_64-pc-windows-gnu" -version = "0.4.0" -source = "registry+https://github.com/rust-lang/crates.io-index" - -[metadata] -"checksum arrayref 0.3.4 (registry+https://github.com/rust-lang/crates.io-index)" = "0fd1479b7c29641adbd35ff3b5c293922d696a92f25c8c975da3e0acbc87258f" -"checksum arrayvec 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)" = "a1e964f9e24d588183fcb43503abda40d288c8657dfc27311516ce2f05675aef" -"checksum bincode 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)" = "bda13183df33055cbb84b847becce220d392df502ebe7a4a78d7021771ed94d0" -"checksum bitflags 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)" = "b3c30d3802dfb7281680d6285f2ccdaa8c2d8fee41f93805dba5c4cf50dc23cf" -"checksum block-buffer 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)" = "a076c298b9ecdb530ed9d967e74a6027d6a7478924520acddcddc24c1c8ab3ab" -"checksum byte-tools 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "560c32574a12a89ecd91f5e742165893f86e3ab98d21f8ea548658eb9eef5f40" -"checksum byteorder 1.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "652805b7e73fada9d85e9a6682a4abd490cb52d96aeecc12e33a0de34dfd0d23" -"checksum cfg-if 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)" = "d4c819a1287eb618df47cc647173c5c4c66ba19d888a6e50d605672aed3140de" -"checksum chrono 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "7c20ebe0b2b08b0aeddba49c609fe7957ba2e33449882cb186a180bc60682fa9" -"checksum crossbeam-deque 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "f739f8c5363aca78cfb059edf753d8f0d36908c348f3d8d1503f03d8b75d9cf3" -"checksum crossbeam-epoch 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)" = "59796cc6cbbdc6bb319161349db0c3250ec73ec7fcb763a51065ec4e2e158552" -"checksum crossbeam-utils 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)" = "2760899e32a1d58d5abb31129f8fae5de75220bc2176e77ff7c627ae45c918d9" -"checksum digest 0.7.2 (registry+https://github.com/rust-lang/crates.io-index)" = "00a49051fef47a72c9623101b19bd71924a45cca838826caae3eaa4d00772603" -"checksum dtoa 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)" = "09c3753c3db574d215cba4ea76018483895d7bff25a31b49ba45db21c48e50ab" -"checksum either 1.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "740178ddf48b1a9e878e6d6509a1442a2d42fd2928aae8e7a6f8a36fb01981b3" -"checksum fake-simd 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)" = "e88a8acf291dafb59c2d96e8f59828f3838bb1a70398823ade51a84de6a6deed" -"checksum fuchsia-zircon 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)" = "2e9763c69ebaae630ba35f74888db465e49e259ba1bc0eda7d06f4a067615d82" -"checksum fuchsia-zircon-sys 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)" = "3dcaa9ae7725d12cdb85b3ad99a434db70b468c09ded17e012d86b5c1010f7a7" -"checksum gcc 0.3.54 (registry+https://github.com/rust-lang/crates.io-index)" = "5e33ec290da0d127825013597dbdfc28bee4964690c7ce1166cbc2a7bd08b1bb" -"checksum generic-array 0.8.3 (registry+https://github.com/rust-lang/crates.io-index)" = "fceb69994e330afed50c93524be68c42fa898c2d9fd4ee8da03bd7363acd26f2" -"checksum generic-array 0.9.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ef25c5683767570c2bbd7deba372926a55eaae9982d7726ee2a1050239d45b9d" -"checksum itoa 0.3.4 (registry+https://github.com/rust-lang/crates.io-index)" = "8324a32baf01e2ae060e9de58ed0bc2320c9a2833491ee36cd3b4c414de4db8c" -"checksum lazy_static 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)" = "76f033c7ad61445c5b347c7382dd1237847eb1bce590fe50365dcb33d546be73" -"checksum lazy_static 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)" = "c8f31047daa365f19be14b47c29df4f7c3b581832407daabe6ae77397619237d" -"checksum libc 0.2.39 (registry+https://github.com/rust-lang/crates.io-index)" = "f54263ad99207254cf58b5f701ecb432c717445ea2ee8af387334bdd1a03fdff" -"checksum memoffset 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "0f9dc261e2b62d7a622bf416ea3c5245cdd5d9a7fcc428c0d06804dfce1775b3" -"checksum nodrop 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)" = "9a2228dca57108069a5262f2ed8bd2e82496d2e074a06d1ccc7ce1687b6ae0a2" -"checksum num 0.1.42 (registry+https://github.com/rust-lang/crates.io-index)" = "4703ad64153382334aa8db57c637364c322d3372e097840c72000dabdcf6156e" -"checksum num-integer 0.1.36 (registry+https://github.com/rust-lang/crates.io-index)" = "f8d26da319fb45674985c78f1d1caf99aa4941f785d384a2ae36d0740bc3e2fe" -"checksum num-iter 0.1.35 (registry+https://github.com/rust-lang/crates.io-index)" = "4b226df12c5a59b63569dd57fafb926d91b385dfce33d8074a412411b689d593" -"checksum num-traits 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "0b3c2bd9b9d21e48e956b763c9f37134dc62d9e95da6edb3f672cacb6caf3cd3" -"checksum num_cpus 1.8.0 (registry+https://github.com/rust-lang/crates.io-index)" = "c51a3322e4bca9d212ad9a158a02abc6934d005490c054a2778df73a70aa0a30" -"checksum proc-macro2 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)" = "cd07deb3c6d1d9ff827999c7f9b04cdfd66b1b17ae508e14fe47b620f2282ae0" -"checksum quote 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)" = "1eca14c727ad12702eb4b6bfb5a232287dcf8385cb8ca83a3eeaf6519c44c408" -"checksum rand 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)" = "eba5f8cb59cc50ed56be8880a5c7b496bfd9bd26394e176bc67884094145c2c5" -"checksum rayon 0.8.2 (registry+https://github.com/rust-lang/crates.io-index)" = "b614fe08b6665cb9a231d07ac1364b0ef3cb3698f1239ee0c4c3a88a524f54c8" -"checksum rayon 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)" = "485541959c8ecc49865526fe6c4de9653dd6e60d829d6edf0be228167b60372d" -"checksum rayon-core 1.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "9d24ad214285a7729b174ed6d3bcfcb80177807f959d95fafd5bfc5c4f201ac8" -"checksum redox_syscall 0.1.37 (registry+https://github.com/rust-lang/crates.io-index)" = "0d92eecebad22b767915e4d529f89f28ee96dbbf5a4810d2b844373f136417fd" -"checksum ring 0.12.1 (registry+https://github.com/rust-lang/crates.io-index)" = "6f7d28b30a72c01b458428e0ae988d4149c20d902346902be881e3edc4bb325c" -"checksum scopeguard 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)" = "94258f53601af11e6a49f722422f6e3425c52b06245a5cf9bc09908b174f5e27" -"checksum serde 1.0.28 (registry+https://github.com/rust-lang/crates.io-index)" = "e928fecdb00fe608c96f83a012633383564e730962fc7a0b79225a6acf056798" -"checksum serde_derive 1.0.28 (registry+https://github.com/rust-lang/crates.io-index)" = "95f666a2356d87ce4780ea15b14b13532785579a5cad2dcba5292acc75f6efe2" -"checksum serde_derive_internals 0.20.0 (registry+https://github.com/rust-lang/crates.io-index)" = "1fc848d073be32cd982380c06587ea1d433bc1a4c4a111de07ec2286a3ddade8" -"checksum serde_json 1.0.10 (registry+https://github.com/rust-lang/crates.io-index)" = "57781ed845b8e742fc2bf306aba8e3b408fe8c366b900e3769fbc39f49eb8b39" -"checksum sha2 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)" = "7daca11f2fdb8559c4f6c588386bed5e2ad4b6605c1442935a7f08144a918688" -"checksum sha2-asm 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)" = "3e319010fd740857efd4428b8ee1b74f311aeb0fda1ece174a9bad6741182d26" -"checksum syn 0.12.13 (registry+https://github.com/rust-lang/crates.io-index)" = "517f6da31bc53bf080b9a77b29fbd0ff8da2f5a2ebd24c73c2238274a94ac7cb" -"checksum time 0.1.39 (registry+https://github.com/rust-lang/crates.io-index)" = "a15375f1df02096fb3317256ce2cee6a1f42fc84ea5ad5fc8c421cfe40c73098" -"checksum typenum 1.9.0 (registry+https://github.com/rust-lang/crates.io-index)" = "13a99dc6780ef33c78780b826cf9d2a78840b72cae9474de4bcaf9051e60ebbd" -"checksum unicode-xid 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "fc72304796d0818e357ead4e000d19c9c174ab23dc11093ac919054d20a6a7fc" -"checksum untrusted 0.5.1 (registry+https://github.com/rust-lang/crates.io-index)" = "f392d7819dbe58833e26872f5f6f0d68b7bbbe90fc3667e98731c4a15ad9a7ae" -"checksum winapi 0.3.4 (registry+https://github.com/rust-lang/crates.io-index)" = "04e3bd221fcbe8a271359c04f21a76db7d0c6028862d1bb5512d85e1e2eb5bb3" -"checksum winapi-i686-pc-windows-gnu 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ac3b87c63620426dd9b991e5ce0329eff545bccbbb34f3be09ff6fb6ab51b7b6" -"checksum winapi-x86_64-pc-windows-gnu 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f" From a8b1980de410c1693287b090453a05ed6bd38bfc Mon Sep 17 00:00:00 2001 From: Greg Fitzgerald Date: Fri, 9 Mar 2018 17:02:17 -0700 Subject: [PATCH 3/4] Restore reorder attack test --- src/entry.rs | 24 +++++++++++++++++++++++- src/log.rs | 28 +--------------------------- 2 files changed, 24 insertions(+), 28 deletions(-) diff --git a/src/entry.rs b/src/entry.rs index 14bc6e8c71..36db0d8417 100644 --- a/src/entry.rs +++ b/src/entry.rs @@ -87,9 +87,14 @@ pub fn next_tick(start_hash: &Hash, num_hashes: u64) -> Entry { #[cfg(test)] mod tests { use super::*; + use hash::hash; + use signature::{KeyPair, KeyPairUtil}; + use transaction::Transaction; + use event::Event; + use entry::create_entry; #[test] - fn test_event_verify() { + fn test_entry_verify() { let zero = Hash::default(); let one = hash(&zero); assert!(Entry::new_tick(0, &zero).verify(&zero)); // base case @@ -98,6 +103,23 @@ mod tests { assert!(!next_tick(&zero, 1).verify(&one)); // inductive step, bad } + #[test] + fn test_event_reorder_attack() { + let zero = Hash::default(); + + // First, verify entries + let keypair = KeyPair::new(); + let tr0 = Event::Transaction(Transaction::new(&keypair, keypair.pubkey(), 0, zero)); + let tr1 = Event::Transaction(Transaction::new(&keypair, keypair.pubkey(), 1, zero)); + let mut e0 = create_entry(&zero, 0, vec![tr0.clone(), tr1.clone()]); + assert!(e0.verify(&zero)); + + // Next, swap two events and ensure verification fails. + e0.events[0] = tr1; // <-- attack + e0.events[1] = tr0; + assert!(!e0.verify(&zero)); + } + #[test] fn test_next_tick() { let zero = Hash::default(); diff --git a/src/log.rs b/src/log.rs index 9632714639..058e5eaa25 100644 --- a/src/log.rs +++ b/src/log.rs @@ -14,8 +14,7 @@ /// was generated by the fastest processor at the time the entry was logged. use hash::Hash; -use entry::{create_entry, next_tick, Entry}; -use event::Event; +use entry::{next_tick, Entry}; use rayon::prelude::*; /// Verifies the hashes and counts of a slice of events are all consistent. @@ -25,10 +24,6 @@ pub fn verify_slice(entries: &[Entry], start_hash: &Hash) -> bool { event_pairs.all(|(x0, x1)| x1.verify(&x0.id)) } -pub fn create_entries(start_hash: &Hash, events: Vec) -> Vec { - vec![create_entry(start_hash, 0, events)] -} - /// Create a vector of Ticks of length 'len' from 'start_hash' hash and 'num_hashes'. pub fn next_ticks(start_hash: &Hash, num_hashes: u64, len: usize) -> Vec { let mut id = *start_hash; @@ -59,27 +54,6 @@ mod tests { bad_ticks[1].id = one; assert!(!verify_slice(&bad_ticks, &zero)); // inductive step, bad } - - // TODO: This is no longer relevant. Instead, test for reordered ticks. - //#[test] - //fn test_reorder_attack() { - // let zero = Hash::default(); - - // // First, verify entries - // let keypair = KeyPair::new(); - // let tr0 = Transaction::new(&keypair, keypair.pubkey(), 0, zero); - // let tr1 = Transaction::new(&keypair, keypair.pubkey(), 1, zero); - // let events = vec![Event::Transaction(tr0), Event::Transaction(tr1)]; - // let mut entries = create_entries(&zero, events); - // assert!(verify_slice(&entries, &zero)); - - // // Next, swap two events and ensure verification fails. - // let event0 = entries[0].event.clone(); - // let event1 = entries[1].event.clone(); - // entries[0].event = event1; - // entries[1].event = event0; - // assert!(!verify_slice(&entries, &zero)); - //} } #[cfg(all(feature = "unstable", test))] From 49281b24e53f9c1c1ca9faece045f4100df129f4 Mon Sep 17 00:00:00 2001 From: Greg Fitzgerald Date: Fri, 9 Mar 2018 17:22:14 -0700 Subject: [PATCH 4/4] Move Tick out of Event Every Entry is now a Tick and the entries contain events. --- src/accountant.rs | 7 +++++-- src/bin/historian-demo.rs | 7 ++++--- src/event.rs | 8 -------- src/historian.rs | 18 ++++++++---------- src/logger.rs | 18 ++++++++++++------ 5 files changed, 29 insertions(+), 29 deletions(-) diff --git a/src/accountant.rs b/src/accountant.rs index efb80f3499..3113cf9200 100644 --- a/src/accountant.rs +++ b/src/accountant.rs @@ -9,6 +9,7 @@ use transaction::{Condition, Transaction}; use signature::{KeyPair, PublicKey, Signature}; use mint::Mint; use historian::{reserve_signature, Historian}; +use logger::Signal; use std::sync::mpsc::SendError; use std::collections::{HashMap, HashSet}; use std::result; @@ -96,7 +97,10 @@ impl Accountant { } self.process_verified_transaction(&tr, false)?; - if let Err(SendError(_)) = self.historian.sender.send(Event::Transaction(tr)) { + if let Err(SendError(_)) = self.historian + .sender + .send(Signal::Event(Event::Transaction(tr))) + { return Err(AccountingError::SendError); } @@ -243,7 +247,6 @@ impl Accountant { fn process_verified_event(self: &mut Self, event: &Event, allow_deposits: bool) -> Result<()> { match *event { - Event::Tick => Ok(()), Event::Transaction(ref tr) => self.process_verified_transaction(tr, allow_deposits), Event::Signature { from, tx_sig, .. } => self.process_verified_sig(from, tx_sig), Event::Timestamp { from, dt, .. } => self.process_verified_timestamp(from, dt), diff --git a/src/bin/historian-demo.rs b/src/bin/historian-demo.rs index a421a1348f..1ac5ae2314 100644 --- a/src/bin/historian-demo.rs +++ b/src/bin/historian-demo.rs @@ -4,6 +4,7 @@ use silk::historian::Historian; use silk::hash::Hash; use silk::entry::Entry; use silk::log::verify_slice; +use silk::logger::Signal; use silk::signature::{KeyPair, KeyPairUtil}; use silk::transaction::Transaction; use silk::event::Event; @@ -11,12 +12,12 @@ use std::thread::sleep; use std::time::Duration; use std::sync::mpsc::SendError; -fn create_log(hist: &Historian, seed: &Hash) -> Result<(), SendError> { +fn create_log(hist: &Historian, seed: &Hash) -> Result<(), SendError> { sleep(Duration::from_millis(15)); let keypair = KeyPair::new(); let tr = Transaction::new(&keypair, keypair.pubkey(), 42, *seed); - let event0 = Event::Transaction(tr); - hist.sender.send(event0)?; + let signal0 = Signal::Event(Event::Transaction(tr)); + hist.sender.send(signal0)?; sleep(Duration::from_millis(10)); Ok(()) } diff --git a/src/event.rs b/src/event.rs index 0d6642b3f3..51a71fba90 100644 --- a/src/event.rs +++ b/src/event.rs @@ -5,14 +5,8 @@ use transaction::Transaction; use chrono::prelude::*; use bincode::serialize; -/// When 'event' is Tick, the event represents a simple clock tick, and exists for the -/// sole purpose of improving the performance of event log verification. A tick can -/// be generated in 'num_hashes' hashes and verified in 'num_hashes' hashes. By logging -/// a hash alongside the tick, each tick and be verified in parallel using the 'id' -/// of the preceding tick to seed its hashing. #[derive(Serialize, Deserialize, Debug, PartialEq, Eq, Clone)] pub enum Event { - Tick, Transaction(Transaction), Signature { from: PublicKey, @@ -40,7 +34,6 @@ impl Event { // TODO: Rename this to transaction_signature(). pub fn get_signature(&self) -> Option { match *self { - Event::Tick => None, Event::Transaction(ref tr) => Some(tr.sig), Event::Signature { .. } => None, Event::Timestamp { .. } => None, @@ -49,7 +42,6 @@ impl Event { pub fn verify(&self) -> bool { match *self { - Event::Tick => true, Event::Transaction(ref tr) => tr.verify(), Event::Signature { from, tx_sig, sig } => sig.verify(&from, &tx_sig), Event::Timestamp { from, dt, sig } => sig.verify(&from, &serialize(&dt).unwrap()), diff --git a/src/historian.rs b/src/historian.rs index 6b6e02e934..77e9f35a5b 100644 --- a/src/historian.rs +++ b/src/historian.rs @@ -7,12 +7,11 @@ use std::sync::mpsc::{sync_channel, Receiver, SyncSender}; use std::time::Instant; use hash::{hash, Hash}; use entry::Entry; -use logger::{ExitReason, Logger}; +use logger::{ExitReason, Logger, Signal}; use signature::Signature; -use event::Event; pub struct Historian { - pub sender: SyncSender, + pub sender: SyncSender, pub receiver: Receiver, pub thread_hdl: JoinHandle, pub signatures: HashSet, @@ -38,7 +37,7 @@ impl Historian { fn create_logger( start_hash: Hash, ms_per_tick: Option, - receiver: Receiver, + receiver: Receiver, sender: SyncSender, ) -> JoinHandle { spawn(move || { @@ -69,7 +68,6 @@ pub fn reserve_signature(sigs: &mut HashSet, sig: &Signature) -> bool mod tests { use super::*; use log::*; - use event::*; use std::thread::sleep; use std::time::Duration; @@ -78,11 +76,11 @@ mod tests { let zero = Hash::default(); let hist = Historian::new(&zero, None); - hist.sender.send(Event::Tick).unwrap(); + hist.sender.send(Signal::Tick).unwrap(); sleep(Duration::new(0, 1_000_000)); - hist.sender.send(Event::Tick).unwrap(); + hist.sender.send(Signal::Tick).unwrap(); sleep(Duration::new(0, 1_000_000)); - hist.sender.send(Event::Tick).unwrap(); + hist.sender.send(Signal::Tick).unwrap(); let entry0 = hist.receiver.recv().unwrap(); let entry1 = hist.receiver.recv().unwrap(); @@ -106,7 +104,7 @@ mod tests { let zero = Hash::default(); let hist = Historian::new(&zero, None); drop(hist.receiver); - hist.sender.send(Event::Tick).unwrap(); + hist.sender.send(Signal::Tick).unwrap(); assert_eq!( hist.thread_hdl.join().unwrap(), ExitReason::SendDisconnected @@ -126,7 +124,7 @@ mod tests { let zero = Hash::default(); let hist = Historian::new(&zero, Some(20)); sleep(Duration::from_millis(30)); - hist.sender.send(Event::Tick).unwrap(); + hist.sender.send(Signal::Tick).unwrap(); drop(hist.sender); let entries: Vec = hist.receiver.iter().collect(); diff --git a/src/logger.rs b/src/logger.rs index 6a90c340c8..89f4a8d08e 100644 --- a/src/logger.rs +++ b/src/logger.rs @@ -13,6 +13,11 @@ use entry::{create_entry_mut, Entry}; use event::Event; use serde_json; +pub enum Signal { + Tick, + Event(Event), +} + #[derive(Debug, PartialEq, Eq)] pub enum ExitReason { RecvDisconnected, @@ -21,7 +26,7 @@ pub enum ExitReason { pub struct Logger { pub sender: SyncSender, - pub receiver: Receiver, + pub receiver: Receiver, pub last_id: Hash, pub events: Vec, pub num_hashes: u64, @@ -29,7 +34,7 @@ pub struct Logger { } impl Logger { - pub fn new(receiver: Receiver, sender: SyncSender, start_hash: Hash) -> Self { + pub fn new(receiver: Receiver, sender: SyncSender, start_hash: Hash) -> Self { Logger { receiver, sender, @@ -61,16 +66,17 @@ impl Logger { } match self.receiver.try_recv() { - Ok(event) => { - if let Event::Tick = event { + Ok(signal) => match signal { + Signal::Tick => { let entry = self.log_entry()?; self.sender .send(entry) .or(Err(ExitReason::SendDisconnected))?; - } else { + } + Signal::Event(event) => { self.events.push(event); } - } + }, Err(TryRecvError::Empty) => return Ok(()), Err(TryRecvError::Disconnected) => return Err(ExitReason::RecvDisconnected), };