sweep most unwraps from ethcore crate, dapps crate (#2762)

* sweep most unwraps from ethcore crate

* purge unwrap from dapps server

* whitespace

[ci:none]
This commit is contained in:
Robert Habermeier 2016-10-20 23:41:15 +02:00 committed by Gav Wood
parent 866ab9c7a3
commit 96f4c10453
31 changed files with 150 additions and 80 deletions

1
Cargo.lock generated
View File

@ -335,6 +335,7 @@ dependencies = [
"jsonrpc-http-server 6.1.1 (git+https://github.com/ethcore/jsonrpc-http-server.git)", "jsonrpc-http-server 6.1.1 (git+https://github.com/ethcore/jsonrpc-http-server.git)",
"linked-hash-map 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)", "linked-hash-map 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)",
"log 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)", "log 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
"mime 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
"mime_guess 1.6.1 (registry+https://github.com/rust-lang/crates.io-index)", "mime_guess 1.6.1 (registry+https://github.com/rust-lang/crates.io-index)",
"parity-dapps 1.4.0 (git+https://github.com/ethcore/parity-ui.git)", "parity-dapps 1.4.0 (git+https://github.com/ethcore/parity-ui.git)",
"parity-dapps-glue 1.4.0", "parity-dapps-glue 1.4.0",

View File

@ -29,6 +29,7 @@ ethcore-util = { path = "../util" }
fetch = { path = "../util/fetch" } fetch = { path = "../util/fetch" }
parity-ui = { path = "./ui" } parity-ui = { path = "./ui" }
parity-dapps-glue = { path = "./js-glue" } parity-dapps-glue = { path = "./js-glue" }
mime = "0.2"
### DEPRECATED ### DEPRECATED
parity-dapps = { git = "https://github.com/ethcore/parity-ui.git", version = "1.4" } parity-dapps = { git = "https://github.com/ethcore/parity-ui.git", version = "1.4" }
parity-dapps-home = { git = "https://github.com/ethcore/parity-ui.git", version = "1.4" } parity-dapps-home = { git = "https://github.com/ethcore/parity-ui.git", version = "1.4" }

View File

@ -27,6 +27,7 @@ use std::default::Default;
pub struct File { pub struct File {
pub path: &'static str, pub path: &'static str,
pub content: &'static [u8], pub content: &'static [u8],
// TODO: use strongly-typed MIME.
pub content_type: &'static str, pub content_type: &'static str,
} }

View File

@ -19,12 +19,16 @@ use serde_json;
use endpoint::Handler; use endpoint::Handler;
use handlers::{ContentHandler, EchoHandler}; use handlers::{ContentHandler, EchoHandler};
pub fn as_json<T : Serialize>(val: &T) -> Box<Handler> { pub fn as_json<T: Serialize>(val: &T) -> Box<Handler> {
Box::new(ContentHandler::ok(serde_json::to_string(val).unwrap(), "application/json".to_owned())) let json = serde_json::to_string(val)
.expect("serialization to string is infallible; qed");
Box::new(ContentHandler::ok(json, mime!(Application/Json)))
} }
pub fn as_json_error<T : Serialize>(val: &T) -> Box<Handler> { pub fn as_json_error<T: Serialize>(val: &T) -> Box<Handler> {
Box::new(ContentHandler::not_found(serde_json::to_string(val).unwrap(), "application/json".to_owned())) let json = serde_json::to_string(val)
.expect("serialization to string is infallible; qed");
Box::new(ContentHandler::not_found(json, mime!(Application/Json)))
} }
pub fn ping_response(local_domain: &str) -> Box<Handler> { pub fn ping_response(local_domain: &str) -> Box<Handler> {

View File

@ -54,8 +54,10 @@ impl ContentCache {
} }
let mut removed = Vec::with_capacity(len - expected_size); let mut removed = Vec::with_capacity(len - expected_size);
while len > expected_size {
let entry = self.cache.pop_front().unwrap(); while self.cache.len() > expected_size {
let entry = self.cache.pop_front().expect("expected_size bounded at 0, len is greater; qed");
match entry.1 { match entry.1 {
ContentStatus::Fetching(ref fetch) => { ContentStatus::Fetching(ref fetch) => {
trace!(target: "dapps", "Aborting {} because of limit.", entry.0); trace!(target: "dapps", "Aborting {} because of limit.", entry.0);
@ -73,7 +75,6 @@ impl ContentCache {
} }
removed.push(entry); removed.push(entry);
len -= 1;
} }
removed removed
} }

View File

@ -156,9 +156,9 @@ impl URLHintContract {
} }
let mut it = vec.into_iter(); let mut it = vec.into_iter();
let account_slash_repo = it.next().unwrap(); let account_slash_repo = it.next().expect("element 0 of 3-len vector known to exist; qed");
let commit = it.next().unwrap(); let commit = it.next().expect("element 1 of 3-len vector known to exist; qed");
let owner = it.next().unwrap(); let owner = it.next().expect("element 2 of 3-len vector known to exist qed");
match (account_slash_repo, commit, owner) { match (account_slash_repo, commit, owner) {
(Token::String(account_slash_repo), Token::FixedBytes(commit), Token::Address(owner)) => { (Token::String(account_slash_repo), Token::FixedBytes(commit), Token::Address(owner)) => {

View File

@ -19,6 +19,7 @@
use std::io::Write; use std::io::Write;
use hyper::{header, server, Decoder, Encoder, Next}; use hyper::{header, server, Decoder, Encoder, Next};
use hyper::net::HttpStream; use hyper::net::HttpStream;
use hyper::mime::Mime;
use hyper::status::StatusCode; use hyper::status::StatusCode;
use util::version; use util::version;
@ -29,22 +30,22 @@ use handlers::add_security_headers;
pub struct ContentHandler { pub struct ContentHandler {
code: StatusCode, code: StatusCode,
content: String, content: String,
mimetype: String, mimetype: Mime,
write_pos: usize, write_pos: usize,
safe_to_embed_at_port: Option<u16>, safe_to_embed_at_port: Option<u16>,
} }
impl ContentHandler { impl ContentHandler {
pub fn ok(content: String, mimetype: String) -> Self { pub fn ok(content: String, mimetype: Mime) -> Self {
Self::new(StatusCode::Ok, content, mimetype) Self::new(StatusCode::Ok, content, mimetype)
} }
pub fn not_found(content: String, mimetype: String) -> Self { pub fn not_found(content: String, mimetype: Mime) -> Self {
Self::new(StatusCode::NotFound, content, mimetype) Self::new(StatusCode::NotFound, content, mimetype)
} }
pub fn html(code: StatusCode, content: String, embeddable_at: Option<u16>) -> Self { pub fn html(code: StatusCode, content: String, embeddable_at: Option<u16>) -> Self {
Self::new_embeddable(code, content, "text/html".into(), embeddable_at) Self::new_embeddable(code, content, mime!(Text/Html), embeddable_at)
} }
pub fn error(code: StatusCode, title: &str, message: &str, details: Option<&str>) -> Self { pub fn error(code: StatusCode, title: &str, message: &str, details: Option<&str>) -> Self {
@ -61,11 +62,11 @@ impl ContentHandler {
), embeddable_at) ), embeddable_at)
} }
pub fn new(code: StatusCode, content: String, mimetype: String) -> Self { pub fn new(code: StatusCode, content: String, mimetype: Mime) -> Self {
Self::new_embeddable(code, content, mimetype, None) Self::new_embeddable(code, content, mimetype, None)
} }
pub fn new_embeddable(code: StatusCode, content: String, mimetype: String, embeddable_at: Option<u16>) -> Self { pub fn new_embeddable(code: StatusCode, content: String, mimetype: Mime, embeddable_at: Option<u16>) -> Self {
ContentHandler { ContentHandler {
code: code, code: code,
content: content, content: content,
@ -87,7 +88,7 @@ impl server::Handler<HttpStream> for ContentHandler {
fn on_response(&mut self, res: &mut server::Response) -> Next { fn on_response(&mut self, res: &mut server::Response) -> Next {
res.set_status(self.code); res.set_status(self.code);
res.headers_mut().set(header::ContentType(self.mimetype.parse().unwrap())); res.headers_mut().set(header::ContentType(self.mimetype.clone()));
add_security_headers(&mut res.headers_mut(), self.safe_to_embed_at_port.clone()); add_security_headers(&mut res.headers_mut(), self.safe_to_embed_at_port.clone());
Next::write() Next::write()
} }

View File

@ -82,7 +82,7 @@ impl server::Handler<HttpStream> for EchoHandler {
// Don't even read the payload if origin is forbidden! // Don't even read the payload if origin is forbidden!
if let Cors::Forbidden = self.cors { if let Cors::Forbidden = self.cors {
self.handler = Some(ContentHandler::ok(String::new(), "text/plain".into())); self.handler = Some(ContentHandler::ok(String::new(), mime!(Text/Plain)));
Next::write() Next::write()
} else { } else {
Next::read() Next::read()
@ -92,7 +92,7 @@ impl server::Handler<HttpStream> for EchoHandler {
fn on_request_readable(&mut self, decoder: &mut Decoder<HttpStream>) -> Next { fn on_request_readable(&mut self, decoder: &mut Decoder<HttpStream>) -> Next {
match decoder.read_to_string(&mut self.content) { match decoder.read_to_string(&mut self.content) {
Ok(0) => { Ok(0) => {
self.handler = Some(ContentHandler::ok(self.content.clone(), "application/json".into())); self.handler = Some(ContentHandler::ok(self.content.clone(), mime!(Application/Json)));
Next::write() Next::write()
}, },
Ok(_) => Next::read(), Ok(_) => Next::read(),
@ -114,11 +114,15 @@ impl server::Handler<HttpStream> for EchoHandler {
])); ]));
headers.set(header::AccessControlAllowOrigin::Value(domain.clone())); headers.set(header::AccessControlAllowOrigin::Value(domain.clone()));
} }
self.handler.as_mut().unwrap().on_response(res) self.handler.as_mut()
.expect("handler always set in on_request, which is before now; qed")
.on_response(res)
} }
fn on_response_writable(&mut self, encoder: &mut Encoder<HttpStream>) -> Next { fn on_response_writable(&mut self, encoder: &mut Encoder<HttpStream>) -> Next {
self.handler.as_mut().unwrap().on_response_writable(encoder) self.handler.as_mut()
.expect("handler always set in on_request, which is before now; qed")
.on_response_writable(encoder)
} }
} }

View File

@ -43,10 +43,8 @@
#![warn(missing_docs)] #![warn(missing_docs)]
#![cfg_attr(feature="nightly", plugin(clippy))] #![cfg_attr(feature="nightly", plugin(clippy))]
#[macro_use]
extern crate log;
extern crate url as url_lib;
extern crate hyper; extern crate hyper;
extern crate url as url_lib;
extern crate unicase; extern crate unicase;
extern crate serde; extern crate serde;
extern crate serde_json; extern crate serde_json;
@ -61,6 +59,13 @@ extern crate ethcore_rpc;
extern crate ethcore_util as util; extern crate ethcore_util as util;
extern crate linked_hash_map; extern crate linked_hash_map;
extern crate fetch; extern crate fetch;
#[macro_use]
extern crate log;
#[macro_use]
extern crate mime;
#[cfg(test)] #[cfg(test)]
extern crate ethcore_devtools as devtools; extern crate ethcore_devtools as devtools;

View File

@ -128,7 +128,12 @@ impl<T: Dapp> server::Handler<HttpStream> for PageHandler<T> {
match self.file { match self.file {
ServedFile::File(ref f) => { ServedFile::File(ref f) => {
res.set_status(StatusCode::Ok); res.set_status(StatusCode::Ok);
res.headers_mut().set(header::ContentType(f.content_type().parse().unwrap()));
match f.content_type().parse() {
Ok(mime) => res.headers_mut().set(header::ContentType(mime)),
Err(()) => debug!(target: "page_handler", "invalid MIME type: {}", f.content_type()),
}
// Security headers: // Security headers:
add_security_headers(&mut res.headers_mut(), self.safe_to_embed_at_port); add_security_headers(&mut res.headers_mut(), self.safe_to_embed_at_port);
Next::write() Next::write()

View File

@ -42,7 +42,7 @@ function FindProxyForURL(url, host) {{
}} }}
"#, "#,
DAPPS_DOMAIN, path.host, path.port); DAPPS_DOMAIN, path.host, path.port);
Box::new(ContentHandler::ok(content, "application/javascript".to_owned())) Box::new(ContentHandler::ok(content, mime!(Application/Javascript)))
} }
} }

View File

@ -81,11 +81,15 @@ impl<A: Authorization + 'static> server::Handler<HttpStream> for Router<A> {
self.handler = match endpoint { self.handler = match endpoint {
// First check special endpoints // First check special endpoints
(ref path, ref endpoint) if self.special.contains_key(endpoint) => { (ref path, ref endpoint) if self.special.contains_key(endpoint) => {
self.special.get(endpoint).unwrap().to_async_handler(path.clone().unwrap_or_default(), control) self.special.get(endpoint)
.expect("special known to contain key; qed")
.to_async_handler(path.clone().unwrap_or_default(), control)
}, },
// Then delegate to dapp // Then delegate to dapp
(Some(ref path), _) if self.endpoints.contains_key(&path.app_id) => { (Some(ref path), _) if self.endpoints.contains_key(&path.app_id) => {
self.endpoints.get(&path.app_id).unwrap().to_async_handler(path.clone(), control) self.endpoints.get(&path.app_id)
.expect("special known to contain key; qed")
.to_async_handler(path.clone(), control)
}, },
// Try to resolve and fetch the dapp // Try to resolve and fetch the dapp
(Some(ref path), _) if self.fetch.contains(&path.app_id) => { (Some(ref path), _) if self.fetch.contains(&path.app_id) => {
@ -108,7 +112,9 @@ impl<A: Authorization + 'static> server::Handler<HttpStream> for Router<A> {
}, },
// RPC by default // RPC by default
_ => { _ => {
self.special.get(&SpecialEndpoint::Rpc).unwrap().to_async_handler(EndpointPath::default(), control) self.special.get(&SpecialEndpoint::Rpc)
.expect("RPC endpoint always stored; qed")
.to_async_handler(EndpointPath::default(), control)
} }
}; };
@ -143,7 +149,9 @@ impl<A: Authorization> Router<A> {
allowed_hosts: Option<Vec<String>>, allowed_hosts: Option<Vec<String>>,
) -> Self { ) -> Self {
let handler = special.get(&SpecialEndpoint::Utils).unwrap().to_handler(EndpointPath::default()); let handler = special.get(&SpecialEndpoint::Utils)
.expect("Utils endpoint always stored; qed")
.to_handler(EndpointPath::default());
Router { Router {
control: Some(control), control: Some(control),
main_page: main_page, main_page: main_page,

View File

@ -176,7 +176,8 @@ impl AccountProvider {
AccountProvider { AccountProvider {
unlocked: Mutex::new(HashMap::new()), unlocked: Mutex::new(HashMap::new()),
address_book: Mutex::new(AddressBook::new(Default::default())), address_book: Mutex::new(AddressBook::new(Default::default())),
sstore: Box::new(EthStore::open(Box::new(NullDir::default())).unwrap()) sstore: Box::new(EthStore::open(Box::new(NullDir::default()))
.expect("NullDir load always succeeds; qed"))
} }
} }
@ -187,7 +188,7 @@ impl AccountProvider {
/// Creates new random account and returns address and public key /// Creates new random account and returns address and public key
pub fn new_account_and_public(&self, password: &str) -> Result<(Address, Public), Error> { pub fn new_account_and_public(&self, password: &str) -> Result<(Address, Public), Error> {
let acc = Random.generate().unwrap(); let acc = Random.generate().expect("secp context has generation capabilities; qed");
let public = acc.public().clone(); let public = acc.public().clone();
let secret = acc.secret().clone(); let secret = acc.secret().clone();
let address = try!(self.sstore.insert_account(secret, password)); let address = try!(self.sstore.insert_account(secret, password));

View File

@ -350,7 +350,7 @@ impl<'x> OpenBlock<'x> {
let t = outcome.trace; let t = outcome.trace;
self.block.traces.as_mut().map(|traces| traces.push(t)); self.block.traces.as_mut().map(|traces| traces.push(t));
self.block.receipts.push(outcome.receipt); self.block.receipts.push(outcome.receipt);
Ok(self.block.receipts.last().unwrap()) Ok(self.block.receipts.last().expect("receipt just pushed; qed"))
} }
Err(x) => Err(From::from(x)) Err(x) => Err(From::from(x))
} }

View File

@ -132,7 +132,8 @@ pub trait BlockProvider {
/// Returns the header of the genesis block. /// Returns the header of the genesis block.
fn genesis_header(&self) -> Header { fn genesis_header(&self) -> Header {
self.block_header(&self.genesis_hash()).unwrap() self.block_header(&self.genesis_hash())
.expect("Genesis header always stored; qed")
} }
/// Returns numbers of blocks containing given bloom. /// Returns numbers of blocks containing given bloom.

View File

@ -55,18 +55,23 @@ impl<T> CacheManager<T> where T: Eq + Hash {
} }
for _ in 0..COLLECTION_QUEUE_SIZE { for _ in 0..COLLECTION_QUEUE_SIZE {
let current_size = notify_unused(self.cache_usage.pop_back().unwrap()); if let Some(back) = self.cache_usage.pop_back() {
let current_size = notify_unused(back);
self.cache_usage.push_front(Default::default()); self.cache_usage.push_front(Default::default());
if current_size < self.max_cache_size { if current_size < self.max_cache_size {
break; break
}
} }
} }
} }
fn rotate_cache_if_needed(&mut self) { fn rotate_cache_if_needed(&mut self) {
if self.cache_usage.len() == 0 { return }
if self.cache_usage[0].len() * self.bytes_per_cache_entry > self.pref_cache_size / COLLECTION_QUEUE_SIZE { if self.cache_usage[0].len() * self.bytes_per_cache_entry > self.pref_cache_size / COLLECTION_QUEUE_SIZE {
let cache = self.cache_usage.pop_back().unwrap(); if let Some(cache) = self.cache_usage.pop_back() {
self.cache_usage.push_front(cache); self.cache_usage.push_front(cache);
} }
} }
}
} }

View File

@ -478,7 +478,11 @@ impl Client {
if number >= self.history { if number >= self.history {
let n = number - self.history; let n = number - self.history;
state.mark_canonical(&mut batch, n, &chain.block_hash(n).unwrap()).expect("DB commit failed"); if let Some(ancient_hash) = chain.block_hash(n) {
state.mark_canonical(&mut batch, n, &ancient_hash).expect("DB commit failed");
} else {
debug!(target: "client", "Missing expected hash for block {}", n);
}
} }
let route = chain.insert_block(&mut batch, block_data, receipts); let route = chain.insert_block(&mut batch, block_data, receipts);

View File

@ -123,10 +123,14 @@ pub trait Engine : Sync + Send {
fn is_builtin(&self, a: &Address) -> bool { self.builtins().contains_key(a) } fn is_builtin(&self, a: &Address) -> bool { self.builtins().contains_key(a) }
/// Determine the code execution cost of the builtin contract with address `a`. /// Determine the code execution cost of the builtin contract with address `a`.
/// Panics if `is_builtin(a)` is not true. /// Panics if `is_builtin(a)` is not true.
fn cost_of_builtin(&self, a: &Address, input: &[u8]) -> U256 { self.builtins().get(a).unwrap().cost(input.len()) } fn cost_of_builtin(&self, a: &Address, input: &[u8]) -> U256 {
self.builtins().get(a).expect("queried cost of nonexistent builtin").cost(input.len())
}
/// Execution the builtin contract `a` on `input` and return `output`. /// Execution the builtin contract `a` on `input` and return `output`.
/// Panics if `is_builtin(a)` is not true. /// Panics if `is_builtin(a)` is not true.
fn execute_builtin(&self, a: &Address, input: &[u8], output: &mut BytesRef) { self.builtins().get(a).unwrap().execute(input, output); } fn execute_builtin(&self, a: &Address, input: &[u8], output: &mut BytesRef) {
self.builtins().get(a).expect("attempted to execute nonexistent builtin").execute(input, output);
}
// TODO: sealing stuff - though might want to leave this for later. // TODO: sealing stuff - though might want to leave this for later.
} }

View File

@ -102,7 +102,7 @@ impl<Cost: CostType> evm::Evm for Interpreter<Cost> {
let mut informant = informant::EvmInformant::new(ext.depth()); let mut informant = informant::EvmInformant::new(ext.depth());
let code = &params.code.as_ref().unwrap(); let code = &params.code.as_ref().expect("exec always called with code; qed");
let valid_jump_destinations = self.cache.jump_destinations(&params.code_hash, code); let valid_jump_destinations = self.cache.jump_destinations(&params.code_hash, code);
let mut gasometer = Gasometer::<Cost>::new(try!(Cost::from_u256(params.gas))); let mut gasometer = Gasometer::<Cost>::new(try!(Cost::from_u256(params.gas)));
@ -318,11 +318,11 @@ impl<Cost: CostType> Interpreter<Cost> {
// Get sender & receive addresses, check if we have balance // Get sender & receive addresses, check if we have balance
let (sender_address, receive_address, has_balance, call_type) = match instruction { let (sender_address, receive_address, has_balance, call_type) = match instruction {
instructions::CALL => { instructions::CALL => {
let has_balance = ext.balance(&params.address) >= value.unwrap(); let has_balance = ext.balance(&params.address) >= value.expect("value set for all but delegate call; qed");
(&params.address, &code_address, has_balance, CallType::Call) (&params.address, &code_address, has_balance, CallType::Call)
}, },
instructions::CALLCODE => { instructions::CALLCODE => {
let has_balance = ext.balance(&params.address) >= value.unwrap(); let has_balance = ext.balance(&params.address) >= value.expect("value set for all but delegate call; qed");
(&params.address, &params.address, has_balance, CallType::CallCode) (&params.address, &params.address, has_balance, CallType::CallCode)
}, },
instructions::DELEGATECALL => (&params.sender, &params.address, true, CallType::DelegateCall), instructions::DELEGATECALL => (&params.sender, &params.address, true, CallType::DelegateCall),

View File

@ -359,7 +359,7 @@ impl evm::Evm for JitEvm {
data.timestamp = ext.env_info().timestamp as i64; data.timestamp = ext.env_info().timestamp as i64;
self.context = Some(unsafe { evmjit::ContextHandle::new(data, schedule, &mut ext_handle) }); self.context = Some(unsafe { evmjit::ContextHandle::new(data, schedule, &mut ext_handle) });
let mut context = self.context.as_mut().unwrap(); let mut context = self.context.as_mut().expect("context handle set on the prior line; qed");
let res = context.exec(); let res = context.exec();
match res { match res {

View File

@ -427,8 +427,16 @@ impl<'a> Executive<'a> {
trace!("exec::finalize: t.gas={}, sstore_refunds={}, suicide_refunds={}, refunds_bound={}, gas_left_prerefund={}, refunded={}, gas_left={}, gas_used={}, refund_value={}, fees_value={}\n", trace!("exec::finalize: t.gas={}, sstore_refunds={}, suicide_refunds={}, refunds_bound={}, gas_left_prerefund={}, refunded={}, gas_left={}, gas_used={}, refund_value={}, fees_value={}\n",
t.gas, sstore_refunds, suicide_refunds, refunds_bound, gas_left_prerefund, refunded, gas_left, gas_used, refund_value, fees_value); t.gas, sstore_refunds, suicide_refunds, refunds_bound, gas_left_prerefund, refunded, gas_left, gas_used, refund_value, fees_value);
trace!("exec::finalize: Refunding refund_value={}, sender={}\n", refund_value, t.sender().unwrap()); let sender = match t.sender() {
self.state.add_balance(&t.sender().unwrap(), &refund_value); Ok(sender) => sender,
Err(e) => {
debug!(target: "executive", "attempted to finalize transaction without sender: {}", e);
return Err(ExecutionError::Internal);
}
};
trace!("exec::finalize: Refunding refund_value={}, sender={}\n", refund_value, sender);
self.state.add_balance(&sender, &refund_value);
trace!("exec::finalize: Compensating author: fees_value={}, author={}\n", fees_value, &self.info.author); trace!("exec::finalize: Compensating author: fees_value={}, author={}\n", fees_value, &self.info.author);
self.state.add_balance(&self.info.author, &fees_value); self.state.add_balance(&self.info.author, &fees_value);

View File

@ -199,8 +199,9 @@ impl Header {
match &mut *hash { match &mut *hash {
&mut Some(ref h) => h.clone(), &mut Some(ref h) => h.clone(),
hash @ &mut None => { hash @ &mut None => {
*hash = Some(self.rlp_sha3(Seal::With)); let h = self.rlp_sha3(Seal::With);
hash.as_ref().unwrap().clone() *hash = Some(h.clone());
h
} }
} }
} }
@ -211,8 +212,9 @@ impl Header {
match &mut *hash { match &mut *hash {
&mut Some(ref h) => h.clone(), &mut Some(ref h) => h.clone(),
hash @ &mut None => { hash @ &mut None => {
*hash = Some(self.rlp_sha3(Seal::Without)); let h = self.rlp_sha3(Seal::Without);
hash.as_ref().unwrap().clone() *hash = Some(h.clone());
h
} }
} }
} }

View File

@ -136,7 +136,7 @@ impl GasPriceCalibrator {
let gas_per_tx: f32 = 21000.0; let gas_per_tx: f32 = 21000.0;
let wei_per_gas: f32 = wei_per_usd * usd_per_tx / gas_per_tx; let wei_per_gas: f32 = wei_per_usd * usd_per_tx / gas_per_tx;
info!(target: "miner", "Updated conversion rate to Ξ1 = {} ({} wei/gas)", Colour::White.bold().paint(format!("US${}", usd_per_eth)), Colour::Yellow.bold().paint(format!("{}", wei_per_gas))); info!(target: "miner", "Updated conversion rate to Ξ1 = {} ({} wei/gas)", Colour::White.bold().paint(format!("US${}", usd_per_eth)), Colour::Yellow.bold().paint(format!("{}", wei_per_gas)));
set_price(U256::from_dec_str(&format!("{:.0}", wei_per_gas)).unwrap()); set_price(U256::from(wei_per_gas as u64));
}) { }) {
self.next_calibration = Instant::now() + self.options.recalibration_period; self.next_calibration = Instant::now() + self.options.recalibration_period;
} else { } else {
@ -747,7 +747,7 @@ impl MinerService for Miner {
let mut transaction_queue = self.transaction_queue.lock(); let mut transaction_queue = self.transaction_queue.lock();
let import = self.add_transactions_to_queue( let import = self.add_transactions_to_queue(
chain, vec![transaction], TransactionOrigin::Local, &mut transaction_queue chain, vec![transaction], TransactionOrigin::Local, &mut transaction_queue
).pop().unwrap(); ).pop().expect("one result returned per added transaction; one added => one result; qed");
match import { match import {
Ok(ref res) => { Ok(ref res) => {
@ -869,7 +869,11 @@ impl MinerService for Miner {
gas_used: receipt.gas_used - prev_gas, gas_used: receipt.gas_used - prev_gas,
contract_address: match tx.action { contract_address: match tx.action {
Action::Call(_) => None, Action::Call(_) => None,
Action::Create => Some(contract_address(&tx.sender().unwrap(), &tx.nonce)), Action::Create => {
let sender = tx.sender()
.expect("transactions in pending block have already been checked for valid sender; qed");
Some(contract_address(&sender, &tx.nonce))
}
}, },
logs: receipt.logs.clone(), logs: receipt.logs.clone(),
} }

View File

@ -52,7 +52,8 @@ impl<F: Fn(PriceInfo) + Sync + Send + 'static> Handler<HttpStream> for SetPriceH
.and_then(|json| json.find_path(&["result", "ethusd"]) .and_then(|json| json.find_path(&["result", "ethusd"])
.and_then(|obj| match *obj { .and_then(|obj| match *obj {
Json::String(ref s) => Some((self.set_price)(PriceInfo { Json::String(ref s) => Some((self.set_price)(PriceInfo {
ethusd: FromStr::from_str(s).unwrap() ethusd: FromStr::from_str(s)
.expect("Etherscan API will always return properly formatted price; qed")
})), })),
_ => None, _ => None,
})); }));
@ -67,7 +68,11 @@ impl PriceInfo {
let client = try!(Client::new().map_err(|_| ())); let client = try!(Client::new().map_err(|_| ()));
thread::spawn(move || { thread::spawn(move || {
let (tx, rx) = mpsc::channel(); let (tx, rx) = mpsc::channel();
let _ = client.request(FromStr::from_str("http://api.etherscan.io/api?module=stats&action=ethprice").unwrap(), SetPriceHandler { let url = FromStr::from_str("http://api.etherscan.io/api?module=stats&action=ethprice")
.expect("string known to be a valid URL; qed");
let _ = client.request(
url,
SetPriceHandler {
set_price: set_price, set_price: set_price,
channel: tx, channel: tx,
}).ok().and_then(|_| rx.recv().ok()); }).ok().and_then(|_| rx.recv().ok());

View File

@ -700,7 +700,7 @@ impl TransactionQueue {
None => vec![], None => vec![],
}; };
for k in nonces_from_sender { for k in nonces_from_sender {
let order = self.current.drop(&sender, &k).unwrap(); let order = self.current.drop(&sender, &k).expect("transaction known to be in self.current; qed");
self.current.insert(sender, k, order.penalize()); self.current.insert(sender, k, order.penalize());
} }
// Same thing for future // Same thing for future
@ -709,7 +709,7 @@ impl TransactionQueue {
None => vec![], None => vec![],
}; };
for k in nonces_from_sender { for k in nonces_from_sender {
let order = self.future.drop(&sender, &k).unwrap(); let order = self.future.drop(&sender, &k).expect("transaction known to be in self.future; qed");
self.future.insert(sender, k, order.penalize()); self.future.insert(sender, k, order.penalize());
} }
} }

View File

@ -150,7 +150,8 @@ impl Spec {
if self.state_root_memo.read().is_none() { if self.state_root_memo.read().is_none() {
*self.state_root_memo.write() = Some(self.genesis_state.root()); *self.state_root_memo.write() = Some(self.genesis_state.root());
} }
self.state_root_memo.read().as_ref().unwrap().clone() self.state_root_memo.read().as_ref().cloned()
.expect("state root memo ensured to be set at this point; qed")
} }
/// Get the known knodes of the network in enode format. /// Get the known knodes of the network in enode format.

View File

@ -520,7 +520,7 @@ impl State {
} }
{ {
let mut trie = factories.trie.from_existing(db.as_hashdb_mut(), root).unwrap(); let mut trie = try!(factories.trie.from_existing(db.as_hashdb_mut(), root));
for (address, ref mut a) in accounts.iter_mut().filter(|&(_, ref a)| a.is_dirty()) { for (address, ref mut a) in accounts.iter_mut().filter(|&(_, ref a)| a.is_dirty()) {
a.state = AccountState::Committed; a.state = AccountState::Committed;
match a.account { match a.account {
@ -691,14 +691,15 @@ impl State {
} }
self.note_cache(a); self.note_cache(a);
match &mut self.cache.borrow_mut().get_mut(a).unwrap().account { // at this point the entry is guaranteed to be in the cache.
RefMut::map(self.cache.borrow_mut(), |c| {
let mut entry = c.get_mut(a).expect("entry known to exist in the cache; qed");
match &mut entry.account {
&mut Some(ref mut acc) => not_default(acc), &mut Some(ref mut acc) => not_default(acc),
slot => *slot = Some(default()), slot => *slot = Some(default()),
} }
// at this point the account is guaranteed to be in the cache.
RefMut::map(self.cache.borrow_mut(), |c| {
let mut entry = c.get_mut(a).unwrap();
// set the dirty flag after changing account data. // set the dirty flag after changing account data.
entry.state = AccountState::Dirty; entry.state = AccountState::Dirty;
match entry.account { match entry.account {

View File

@ -134,10 +134,11 @@ impl StateDB {
let hash_count_entry = db.get(COL_ACCOUNT_BLOOM, ACCOUNT_BLOOM_HASHCOUNT_KEY) let hash_count_entry = db.get(COL_ACCOUNT_BLOOM, ACCOUNT_BLOOM_HASHCOUNT_KEY)
.expect("Low-level database error"); .expect("Low-level database error");
if hash_count_entry.is_none() { let hash_count_bytes = match hash_count_entry {
return Bloom::new(ACCOUNT_BLOOM_SPACE, DEFAULT_ACCOUNT_PRESET); Some(bytes) => bytes,
} None => return Bloom::new(ACCOUNT_BLOOM_SPACE, DEFAULT_ACCOUNT_PRESET),
let hash_count_bytes = hash_count_entry.unwrap(); };
assert_eq!(hash_count_bytes.len(), 1); assert_eq!(hash_count_bytes.len(), 1);
let hash_count = hash_count_bytes[0]; let hash_count = hash_count_bytes[0];

View File

@ -129,7 +129,7 @@ impl<T> TraceDB<T> where T: DatabaseExtras {
pub fn new(config: Config, tracesdb: Arc<Database>, extras: Arc<T>) -> Self { pub fn new(config: Config, tracesdb: Arc<Database>, extras: Arc<T>) -> Self {
let mut batch = DBTransaction::new(&tracesdb); let mut batch = DBTransaction::new(&tracesdb);
batch.put(db::COL_TRACE, b"version", TRACE_DB_VER); batch.put(db::COL_TRACE, b"version", TRACE_DB_VER);
tracesdb.write(batch).unwrap(); tracesdb.write(batch).expect("failed to update version");
TraceDB { TraceDB {
traces: RwLock::new(HashMap::new()), traces: RwLock::new(HashMap::new()),

View File

@ -21,7 +21,7 @@ use std::cell::*;
use rlp::*; use rlp::*;
use util::sha3::Hashable; use util::sha3::Hashable;
use util::{H256, Address, U256, Bytes, HeapSizeOf}; use util::{H256, Address, U256, Bytes, HeapSizeOf};
use ethkey::{Signature, sign, Secret, Public, recover, public_to_address, Error as EthkeyError}; use ethkey::{Signature, Secret, Public, recover, public_to_address, Error as EthkeyError};
use error::*; use error::*;
use evm::Schedule; use evm::Schedule;
use header::BlockNumber; use header::BlockNumber;
@ -143,7 +143,8 @@ impl Transaction {
/// Signs the transaction as coming from `sender`. /// Signs the transaction as coming from `sender`.
pub fn sign(self, secret: &Secret) -> SignedTransaction { pub fn sign(self, secret: &Secret) -> SignedTransaction {
let sig = sign(secret, &self.hash()).unwrap(); let sig = ::ethkey::sign(secret, &self.hash())
.expect("data is valid and context has signing capabilities; qed");
self.with_signature(sig) self.with_signature(sig)
} }

View File

@ -108,7 +108,8 @@ pub fn verify_block_family(header: &Header, bytes: &[u8], engine: &Engine, bc: &
match bc.block_details(&hash) { match bc.block_details(&hash) {
Some(details) => { Some(details) => {
excluded.insert(details.parent.clone()); excluded.insert(details.parent.clone());
let b = bc.block(&hash).unwrap(); let b = bc.block(&hash)
.expect("parent already known to be stored; qed");
excluded.extend(BlockView::new(&b).uncle_hashes()); excluded.extend(BlockView::new(&b).uncle_hashes());
hash = details.parent; hash = details.parent;
} }