diff --git a/Cargo.lock b/Cargo.lock index 94e754997..a19426640 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1250,7 +1250,7 @@ dependencies = [ [[package]] name = "parity-ui-precompiled" version = "1.4.0" -source = "git+https://github.com/ethcore/js-precompiled.git#ce7e830d36483dab10419d9105ac39dc520e7a61" +source = "git+https://github.com/ethcore/js-precompiled.git#5e3b9629692c550811b228d68ca99d1461a4f6cb" dependencies = [ "parity-dapps-glue 1.4.0 (registry+https://github.com/rust-lang/crates.io-index)", ] diff --git a/ethcore/res/authority_round.json b/ethcore/res/authority_round.json new file mode 100644 index 000000000..ad23b461f --- /dev/null +++ b/ethcore/res/authority_round.json @@ -0,0 +1,42 @@ +{ + "name": "TestAuthorityRound", + "engine": { + "AuthorityRound": { + "params": { + "gasLimitBoundDivisor": "0x0400", + "stepDuration": "1", + "authorities" : [ + "0x7d577a597b2742b498cb5cf0c26cdcd726d39e6e", + "0x82a978b3f5962a5b0957d9ee9eef472ee55b42f1" + ] + } + } + }, + "params": { + "accountStartNonce": "0x0", + "maximumExtraDataSize": "0x20", + "minGasLimit": "0x1388", + "networkID" : "0x69" + }, + "genesis": { + "seal": { + "generic": { + "fields": 1, + "rlp": "0x11bbe8db4e347b4e8c937c1c8370e4b5ed33adb3db69cbdb7a38e1e50b1b82fa" + } + }, + "difficulty": "0x20000", + "author": "0x0000000000000000000000000000000000000000", + "timestamp": "0x00", + "parentHash": "0x0000000000000000000000000000000000000000000000000000000000000000", + "extraData": "0x", + "gasLimit": "0x2fefd8" + }, + "accounts": { + "0000000000000000000000000000000000000001": { "balance": "1", "nonce": "1048576", "builtin": { "name": "ecrecover", "pricing": { "linear": { "base": 3000, "word": 0 } } } }, + "0000000000000000000000000000000000000002": { "balance": "1", "nonce": "1048576", "builtin": { "name": "sha256", "pricing": { "linear": { "base": 60, "word": 12 } } } }, + "0000000000000000000000000000000000000003": { "balance": "1", "nonce": "1048576", "builtin": { "name": "ripemd160", "pricing": { "linear": { "base": 600, "word": 120 } } } }, + "0000000000000000000000000000000000000004": { "balance": "1", "nonce": "1048576", "builtin": { "name": "identity", "pricing": { "linear": { "base": 15, "word": 3 } } } }, + "9cce34f7ab185c7aba1b7c8140d620b4bda941d6": { "balance": "1606938044258990275541962092341162602522202993782792835301376", "nonce": "1048576" } + } +} diff --git a/ethcore/res/test_authority.json b/ethcore/res/basic_authority.json similarity index 98% rename from ethcore/res/test_authority.json rename to ethcore/res/basic_authority.json index 1ab482863..51276d487 100644 --- a/ethcore/res/test_authority.json +++ b/ethcore/res/basic_authority.json @@ -1,5 +1,5 @@ { - "name": "TestAuthority", + "name": "TestBasicAuthority", "engine": { "BasicAuthority": { "params": { diff --git a/ethcore/res/ethereum/frontier.json b/ethcore/res/ethereum/frontier.json index be473237c..9bb9c50ff 100644 --- a/ethcore/res/ethereum/frontier.json +++ b/ethcore/res/ethereum/frontier.json @@ -131,10 +131,11 @@ "0x807640a13483f8ac783c557fcdf27be11ea4ac7a" ], "eip150Transition": "0x259518", - "eip155Transition": "0x7fffffffffffffff", - "eip160Transition": "0x7fffffffffffffff", - "eip161abcTransition": "0x7fffffffffffffff", - "eip161dTransition": "0x7fffffffffffffff" + "eip155Transition": 2675000, + "eip160Transition": 2675000, + "eip161abcTransition": 2675000, + "eip161dTransition": 2675000, + "maxCodeSize": 24576 } } }, diff --git a/ethcore/res/ethereum/morden.json b/ethcore/res/ethereum/morden.json index 9d54169c3..6e725e8bf 100644 --- a/ethcore/res/ethereum/morden.json +++ b/ethcore/res/ethereum/morden.json @@ -11,10 +11,10 @@ "registrar": "0x52dff57a8a1532e6afb3dc07e2af58bb9eb05b3d", "homesteadTransition": "0x789b0", "eip150Transition": "0x1b34d8", - "eip155Transition": "0x7fffffffffffffff", - "eip160Transition": "0x7fffffffffffffff", - "eip161abcTransition": "0x7fffffffffffffff", - "eip161dTransition": "0x7fffffffffffffff" + "eip155Transition": 1885000, + "eip160Transition": 1885000, + "eip161abcTransition": 1885000, + "eip161dTransition": 1885000 } } }, diff --git a/ethcore/res/ethereum/tests b/ethcore/res/ethereum/tests index 9028c4801..97066e40c 160000 --- a/ethcore/res/ethereum/tests +++ b/ethcore/res/ethereum/tests @@ -1 +1 @@ -Subproject commit 9028c4801fd39fbb71a9796979182549a24e81c8 +Subproject commit 97066e40ccd061f727deb5cd860e4d9135aa2551 diff --git a/ethcore/src/client/client.rs b/ethcore/src/client/client.rs index 151d7e10e..bf318aeda 100644 --- a/ethcore/src/client/client.rs +++ b/ethcore/src/client/client.rs @@ -554,6 +554,7 @@ impl Client { /// Import transactions from the IO queue pub fn import_queued_transactions(&self, transactions: &[Bytes]) -> usize { + trace!(target: "external_tx", "Importing queued"); let _timer = PerfTimer::new("import_queued_transactions"); self.queue_transactions.fetch_sub(transactions.len(), AtomicOrdering::SeqCst); let txs = transactions.iter().filter_map(|bytes| UntrustedRlp::new(bytes).as_val().ok()).collect(); @@ -561,6 +562,11 @@ impl Client { results.len() } + /// Used by PoA to try sealing on period change. + pub fn update_sealing(&self) { + self.miner.update_sealing(self) + } + /// Attempt to get a copy of a specific block's final state. /// /// This will not fail if given BlockID::Latest. @@ -1193,7 +1199,9 @@ impl BlockChainClient for Client { } fn queue_transactions(&self, transactions: Vec) { - if self.queue_transactions.load(AtomicOrdering::Relaxed) > MAX_TX_QUEUE_SIZE { + let queue_size = self.queue_transactions.load(AtomicOrdering::Relaxed); + trace!(target: "external_tx", "Queue size: {}", queue_size); + if queue_size > MAX_TX_QUEUE_SIZE { debug!("Ignoring {} transactions: queue is full", transactions.len()); } else { let len = transactions.len(); diff --git a/ethcore/src/client/test_client.rs b/ethcore/src/client/test_client.rs index 434edd3e8..84ed25b37 100644 --- a/ethcore/src/client/test_client.rs +++ b/ethcore/src/client/test_client.rs @@ -119,6 +119,16 @@ impl TestBlockChainClient { /// Creates new test client with specified extra data for each block pub fn new_with_extra_data(extra_data: Bytes) -> Self { let spec = Spec::new_test(); + TestBlockChainClient::new_with_spec_and_extra(spec, extra_data) + } + + /// Create test client with custom spec. + pub fn new_with_spec(spec: Spec) -> Self { + TestBlockChainClient::new_with_spec_and_extra(spec, Bytes::new()) + } + + /// Create test client with custom spec and extra data. + pub fn new_with_spec_and_extra(spec: Spec, extra_data: Bytes) -> Self { let mut client = TestBlockChainClient { blocks: RwLock::new(HashMap::new()), numbers: RwLock::new(HashMap::new()), @@ -315,7 +325,7 @@ pub fn get_temp_state_db() -> GuardedTempResult { impl MiningBlockChainClient for TestBlockChainClient { fn latest_schedule(&self) -> Schedule { - Schedule::new_post_eip150(true, true, true) + Schedule::new_post_eip150(24576, true, true, true) } fn prepare_open_block(&self, author: Address, gas_range_target: (U256, U256), extra_data: Bytes) -> OpenBlock { diff --git a/ethcore/src/engines/authority_round.rs b/ethcore/src/engines/authority_round.rs new file mode 100644 index 000000000..9bed99e8b --- /dev/null +++ b/ethcore/src/engines/authority_round.rs @@ -0,0 +1,429 @@ +// Copyright 2015, 2016 Ethcore (UK) Ltd. +// This file is part of Parity. + +// Parity is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. + +// Parity is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. + +// You should have received a copy of the GNU General Public License +// along with Parity. If not, see . + +//! A blockchain engine that supports a non-instant BFT proof-of-authority. + +use std::sync::atomic::{AtomicUsize, AtomicBool, Ordering as AtomicOrdering}; +use std::sync::Weak; +use std::time::{UNIX_EPOCH, Duration}; +use util::*; +use ethkey::{verify_address, Signature}; +use rlp::{UntrustedRlp, View, encode}; +use account_provider::AccountProvider; +use block::*; +use spec::CommonParams; +use engines::Engine; +use header::Header; +use error::{Error, BlockError}; +use evm::Schedule; +use ethjson; +use io::{IoContext, IoHandler, TimerToken, IoService, IoChannel}; +use service::ClientIoMessage; +use transaction::SignedTransaction; +use env_info::EnvInfo; +use builtin::Builtin; + +/// `AuthorityRound` params. +#[derive(Debug, PartialEq)] +pub struct AuthorityRoundParams { + /// Gas limit divisor. + pub gas_limit_bound_divisor: U256, + /// Time to wait before next block or authority switching. + pub step_duration: Duration, + /// Valid authorities. + pub authorities: Vec
, + /// Number of authorities. + pub authority_n: usize, +} + +impl From for AuthorityRoundParams { + fn from(p: ethjson::spec::AuthorityRoundParams) -> Self { + AuthorityRoundParams { + gas_limit_bound_divisor: p.gas_limit_bound_divisor.into(), + step_duration: Duration::from_secs(p.step_duration.into()), + authority_n: p.authorities.len(), + authorities: p.authorities.into_iter().map(Into::into).collect::>(), + } + } +} + +/// Engine using `AuthorityRound` proof-of-work consensus algorithm, suitable for Ethereum +/// mainnet chains in the Olympic, Frontier and Homestead eras. +pub struct AuthorityRound { + params: CommonParams, + our_params: AuthorityRoundParams, + builtins: BTreeMap, + transition_service: IoService, + message_channel: Mutex>>, + step: AtomicUsize, + proposed: AtomicBool, +} + +fn header_step(header: &Header) -> Result { + UntrustedRlp::new(&header.seal()[0]).as_val() +} + +fn header_signature(header: &Header) -> Result { + UntrustedRlp::new(&header.seal()[1]).as_val::().map(Into::into) +} + +trait AsMillis { + fn as_millis(&self) -> u64; +} + +impl AsMillis for Duration { + fn as_millis(&self) -> u64 { + self.as_secs()*1_000 + (self.subsec_nanos()/1_000_000) as u64 + } +} + +impl AuthorityRound { + /// Create a new instance of AuthorityRound engine. + pub fn new(params: CommonParams, our_params: AuthorityRoundParams, builtins: BTreeMap) -> Result, Error> { + let initial_step = (unix_now().as_secs() / our_params.step_duration.as_secs()) as usize; + let engine = Arc::new( + AuthorityRound { + params: params, + our_params: our_params, + builtins: builtins, + transition_service: try!(IoService::::start()), + message_channel: Mutex::new(None), + step: AtomicUsize::new(initial_step), + proposed: AtomicBool::new(false) + }); + let handler = TransitionHandler { engine: Arc::downgrade(&engine) }; + try!(engine.transition_service.register_handler(Arc::new(handler))); + Ok(engine) + } + + fn step(&self) -> usize { + self.step.load(AtomicOrdering::SeqCst) + } + + fn remaining_step_duration(&self) -> Duration { + let now = unix_now(); + let step_end = self.our_params.step_duration * (self.step() as u32 + 1); + if step_end > now { + step_end - now + } else { + Duration::from_secs(0) + } + } + + fn step_proposer(&self, step: usize) -> &Address { + let ref p = self.our_params; + p.authorities.get(step % p.authority_n).expect("There are authority_n authorities; taking number modulo authority_n gives number in authority_n range; qed") + } + + fn is_step_proposer(&self, step: usize, address: &Address) -> bool { + self.step_proposer(step) == address + } +} + +fn unix_now() -> Duration { + UNIX_EPOCH.elapsed().expect("Valid time has to be set in your system.") +} + +struct TransitionHandler { + engine: Weak, +} + +#[derive(Clone)] +struct BlockArrived; + +const ENGINE_TIMEOUT_TOKEN: TimerToken = 23; + +impl IoHandler for TransitionHandler { + fn initialize(&self, io: &IoContext) { + if let Some(engine) = self.engine.upgrade() { + io.register_timer_once(ENGINE_TIMEOUT_TOKEN, engine.remaining_step_duration().as_millis()) + .unwrap_or_else(|e| warn!(target: "poa", "Failed to start consensus step timer: {}.", e)) + } + } + + fn timeout(&self, io: &IoContext, timer: TimerToken) { + if timer == ENGINE_TIMEOUT_TOKEN { + if let Some(engine) = self.engine.upgrade() { + engine.step.fetch_add(1, AtomicOrdering::SeqCst); + engine.proposed.store(false, AtomicOrdering::SeqCst); + if let Some(ref channel) = *engine.message_channel.lock() { + match channel.send(ClientIoMessage::UpdateSealing) { + Ok(_) => trace!(target: "poa", "timeout: UpdateSealing message sent for step {}.", engine.step.load(AtomicOrdering::Relaxed)), + Err(err) => trace!(target: "poa", "timeout: Could not send a sealing message {} for step {}.", err, engine.step.load(AtomicOrdering::Relaxed)), + } + } + io.register_timer_once(ENGINE_TIMEOUT_TOKEN, engine.remaining_step_duration().as_millis()) + .unwrap_or_else(|e| warn!(target: "poa", "Failed to restart consensus step timer: {}.", e)) + } + } + } +} + +impl Engine for AuthorityRound { + fn name(&self) -> &str { "AuthorityRound" } + fn version(&self) -> SemanticVersion { SemanticVersion::new(1, 0, 0) } + /// Two fields - consensus step and the corresponding proposer signature. + fn seal_fields(&self) -> usize { 2 } + + fn params(&self) -> &CommonParams { &self.params } + fn builtins(&self) -> &BTreeMap { &self.builtins } + + /// Additional engine-specific information for the user/developer concerning `header`. + fn extra_info(&self, header: &Header) -> BTreeMap { + map![ + "step".into() => header_step(header).as_ref().map(ToString::to_string).unwrap_or("".into()), + "signature".into() => header_signature(header).as_ref().map(ToString::to_string).unwrap_or("".into()) + ] + } + + fn schedule(&self, _env_info: &EnvInfo) -> Schedule { + Schedule::new_post_eip150(usize::max_value(), true, true, true) + } + + fn populate_from_parent(&self, header: &mut Header, parent: &Header, gas_floor_target: U256, _gas_ceil_target: U256) { + header.set_difficulty(parent.difficulty().clone()); + header.set_gas_limit({ + let gas_limit = parent.gas_limit().clone(); + let bound_divisor = self.our_params.gas_limit_bound_divisor; + if gas_limit < gas_floor_target { + min(gas_floor_target, gas_limit + gas_limit / bound_divisor - 1.into()) + } else { + max(gas_floor_target, gas_limit - gas_limit / bound_divisor + 1.into()) + } + }); + } + + /// Apply the block reward on finalisation of the block. + /// This assumes that all uncles are valid uncles (i.e. of at least one generation before the current). + fn on_close_block(&self, _block: &mut ExecutedBlock) {} + + fn is_sealer(&self, author: &Address) -> Option { + let ref p = self.our_params; + Some(p.authorities.contains(author)) + } + + /// Attempt to seal the block internally. + /// + /// This operation is synchronous and may (quite reasonably) not be available, in which `false` will + /// be returned. + fn generate_seal(&self, block: &ExecutedBlock, accounts: Option<&AccountProvider>) -> Option> { + if self.proposed.load(AtomicOrdering::SeqCst) { return None; } + let header = block.header(); + let step = self.step(); + if self.is_step_proposer(step, header.author()) { + if let Some(ap) = accounts { + // Account should be permanently unlocked, otherwise sealing will fail. + if let Ok(signature) = ap.sign(*header.author(), None, header.bare_hash()) { + trace!(target: "poa", "generate_seal: Issuing a block for step {}.", step); + self.proposed.store(true, AtomicOrdering::SeqCst); + return Some(vec![encode(&step).to_vec(), encode(&(&*signature as &[u8])).to_vec()]); + } else { + warn!(target: "poa", "generate_seal: FAIL: Accounts secret key unavailable."); + } + } else { + warn!(target: "poa", "generate_seal: FAIL: Accounts not provided."); + } + } + None + } + + /// Check the number of seal fields. + fn verify_block_basic(&self, header: &Header, _block: Option<&[u8]>) -> Result<(), Error> { + if header.seal().len() != self.seal_fields() { + trace!(target: "poa", "verify_block_basic: wrong number of seal fields"); + Err(From::from(BlockError::InvalidSealArity( + Mismatch { expected: self.seal_fields(), found: header.seal().len() } + ))) + } else { + Ok(()) + } + } + + /// Check if the signature belongs to the correct proposer. + fn verify_block_unordered(&self, header: &Header, _block: Option<&[u8]>) -> Result<(), Error> { + let header_step = try!(header_step(header)); + // Give one step slack if step is lagging, double vote is still not possible. + if header_step <= self.step() + 1 { + let proposer_signature = try!(header_signature(header)); + let ok_sig = try!(verify_address(self.step_proposer(header_step), &proposer_signature, &header.bare_hash())); + if ok_sig { + Ok(()) + } else { + trace!(target: "poa", "verify_block_unordered: invalid seal signature"); + try!(Err(BlockError::InvalidSeal)) + } + } else { + trace!(target: "poa", "verify_block_unordered: block from the future"); + try!(Err(BlockError::InvalidSeal)) + } + } + + fn verify_block_family(&self, header: &Header, parent: &Header, _block: Option<&[u8]>) -> Result<(), Error> { + // Don't calculate difficulty for genesis blocks. + if header.number() == 0 { + return Err(From::from(BlockError::RidiculousNumber(OutOfBounds { min: Some(1), max: None, found: header.number() }))); + } + + let step = try!(header_step(header)); + // Check if parent is from a previous step. + if step == try!(header_step(parent)) { + trace!(target: "poa", "Multiple blocks proposed for step {}.", step); + try!(Err(BlockError::DoubleVote(header.author().clone()))); + } + + // Check difficulty is correct given the two timestamps. + if header.difficulty() != parent.difficulty() { + return Err(From::from(BlockError::InvalidDifficulty(Mismatch { expected: *parent.difficulty(), found: *header.difficulty() }))) + } + let gas_limit_divisor = self.our_params.gas_limit_bound_divisor; + let min_gas = parent.gas_limit().clone() - parent.gas_limit().clone() / gas_limit_divisor; + let max_gas = parent.gas_limit().clone() + parent.gas_limit().clone() / gas_limit_divisor; + if header.gas_limit() <= &min_gas || header.gas_limit() >= &max_gas { + return Err(From::from(BlockError::InvalidGasLimit(OutOfBounds { min: Some(min_gas), max: Some(max_gas), found: header.gas_limit().clone() }))); + } + Ok(()) + } + + fn verify_transaction_basic(&self, t: &SignedTransaction, _header: &Header) -> Result<(), Error> { + try!(t.check_low_s()); + Ok(()) + } + + fn verify_transaction(&self, t: &SignedTransaction, _header: &Header) -> Result<(), Error> { + t.sender().map(|_|()) // Perform EC recovery and cache sender + } + + fn register_message_channel(&self, message_channel: IoChannel) { + let mut guard = self.message_channel.lock(); + *guard = Some(message_channel); + } +} + +#[cfg(test)] +mod tests { + use util::*; + use env_info::EnvInfo; + use header::Header; + use error::{Error, BlockError}; + use rlp::encode; + use block::*; + use tests::helpers::*; + use account_provider::AccountProvider; + use spec::Spec; + use std::time::UNIX_EPOCH; + + #[test] + fn has_valid_metadata() { + let engine = Spec::new_test_round().engine; + assert!(!engine.name().is_empty()); + assert!(engine.version().major >= 1); + } + + #[test] + fn can_return_schedule() { + let engine = Spec::new_test_round().engine; + let schedule = engine.schedule(&EnvInfo { + number: 10000000, + author: 0.into(), + timestamp: 0, + difficulty: 0.into(), + last_hashes: Arc::new(vec![]), + gas_used: 0.into(), + gas_limit: 0.into(), + }); + + assert!(schedule.stack_limit > 0); + } + + #[test] + fn verification_fails_on_short_seal() { + let engine = Spec::new_test_round().engine; + let header: Header = Header::default(); + + let verify_result = engine.verify_block_basic(&header, None); + + match verify_result { + Err(Error::Block(BlockError::InvalidSealArity(_))) => {}, + Err(_) => { panic!("should be block seal-arity mismatch error (got {:?})", verify_result); }, + _ => { panic!("Should be error, got Ok"); }, + } + } + + #[test] + fn can_do_signature_verification_fail() { + let engine = Spec::new_test_round().engine; + let mut header: Header = Header::default(); + header.set_seal(vec![encode(&H520::default()).to_vec()]); + + let verify_result = engine.verify_block_unordered(&header, None); + assert!(verify_result.is_err()); + } + + #[test] + fn generates_seal_and_does_not_double_propose() { + let tap = AccountProvider::transient_provider(); + let addr1 = tap.insert_account("1".sha3(), "1").unwrap(); + tap.unlock_account_permanently(addr1, "1".into()).unwrap(); + let addr2 = tap.insert_account("2".sha3(), "2").unwrap(); + tap.unlock_account_permanently(addr2, "2".into()).unwrap(); + + let spec = Spec::new_test_round(); + let engine = &*spec.engine; + let genesis_header = spec.genesis_header(); + let mut db1 = get_temp_state_db().take(); + spec.ensure_db_good(&mut db1).unwrap(); + let mut db2 = get_temp_state_db().take(); + spec.ensure_db_good(&mut db2).unwrap(); + let last_hashes = Arc::new(vec![genesis_header.hash()]); + let b1 = OpenBlock::new(engine, Default::default(), false, db1, &genesis_header, last_hashes.clone(), addr1, (3141562.into(), 31415620.into()), vec![]).unwrap(); + let b1 = b1.close_and_lock(); + let b2 = OpenBlock::new(engine, Default::default(), false, db2, &genesis_header, last_hashes, addr2, (3141562.into(), 31415620.into()), vec![]).unwrap(); + let b2 = b2.close_and_lock(); + + if let Some(seal) = engine.generate_seal(b1.block(), Some(&tap)) { + assert!(b1.clone().try_seal(engine, seal).is_ok()); + // Second proposal is forbidden. + assert!(engine.generate_seal(b1.block(), Some(&tap)).is_none()); + } + + if let Some(seal) = engine.generate_seal(b2.block(), Some(&tap)) { + assert!(b2.clone().try_seal(engine, seal).is_ok()); + // Second proposal is forbidden. + assert!(engine.generate_seal(b2.block(), Some(&tap)).is_none()); + } + } + + #[test] + fn proposer_switching() { + let mut header: Header = Header::default(); + let tap = AccountProvider::transient_provider(); + let addr = tap.insert_account("0".sha3(), "0").unwrap(); + + header.set_author(addr); + + let engine = Spec::new_test_round().engine; + + let signature = tap.sign(addr, Some("0".into()), header.bare_hash()).unwrap(); + let mut step = UNIX_EPOCH.elapsed().unwrap().as_secs(); + header.set_seal(vec![encode(&step).to_vec(), encode(&(&*signature as &[u8])).to_vec()]); + let first_ok = engine.verify_block_seal(&header).is_ok(); + step = step + 1; + header.set_seal(vec![encode(&step).to_vec(), encode(&(&*signature as &[u8])).to_vec()]); + let second_ok = engine.verify_block_seal(&header).is_ok(); + + assert!(first_ok ^ second_ok); + } +} diff --git a/ethcore/src/engines/basic_authority.rs b/ethcore/src/engines/basic_authority.rs index 5a55c6210..23a97967c 100644 --- a/ethcore/src/engines/basic_authority.rs +++ b/ethcore/src/engines/basic_authority.rs @@ -181,13 +181,6 @@ impl Engine for BasicAuthority { } } -impl Header { - /// Get the none field of the header. - pub fn signature(&self) -> H520 { - ::rlp::decode(&self.seal()[0]) - } -} - #[cfg(test)] mod tests { use util::*; @@ -201,7 +194,7 @@ mod tests { /// Create a new test chain spec with `BasicAuthority` consensus engine. fn new_test_authority() -> Spec { - let bytes: &[u8] = include_bytes!("../../res/test_authority.json"); + let bytes: &[u8] = include_bytes!("../../res/basic_authority.json"); Spec::load(bytes).expect("invalid chain spec") } diff --git a/ethcore/src/engines/instant_seal.rs b/ethcore/src/engines/instant_seal.rs index 75fae4d81..3dc78d1a2 100644 --- a/ethcore/src/engines/instant_seal.rs +++ b/ethcore/src/engines/instant_seal.rs @@ -55,7 +55,7 @@ impl Engine for InstantSeal { } fn schedule(&self, _env_info: &EnvInfo) -> Schedule { - Schedule::new_post_eip150(false, false, false) + Schedule::new_post_eip150(usize::max_value(), false, false, false) } fn is_sealer(&self, _author: &Address) -> Option { Some(true) } diff --git a/ethcore/src/engines/mod.rs b/ethcore/src/engines/mod.rs index 52812f45e..c70a19de8 100644 --- a/ethcore/src/engines/mod.rs +++ b/ethcore/src/engines/mod.rs @@ -19,10 +19,12 @@ mod null_engine; mod instant_seal; mod basic_authority; +mod authority_round; pub use self::null_engine::NullEngine; pub use self::instant_seal::InstantSeal; pub use self::basic_authority::BasicAuthority; +pub use self::authority_round::AuthorityRound; use util::*; use account_provider::AccountProvider; @@ -32,6 +34,8 @@ use env_info::EnvInfo; use error::Error; use spec::CommonParams; use evm::Schedule; +use io::IoChannel; +use service::ClientIoMessage; use header::Header; use transaction::SignedTransaction; @@ -140,5 +144,7 @@ pub trait Engine : Sync + Send { self.builtins().get(a).expect("attempted to execute nonexistent builtin").execute(input, output); } + /// Add a channel for communication with Client which can be used for sealing. + fn register_message_channel(&self, _message_channel: IoChannel) {} // TODO: sealing stuff - though might want to leave this for later. } diff --git a/ethcore/src/error.rs b/ethcore/src/error.rs index ae68aefa1..261eab268 100644 --- a/ethcore/src/error.rs +++ b/ethcore/src/error.rs @@ -167,6 +167,8 @@ pub enum BlockError { UnknownParent(H256), /// Uncle parent given is unknown. UnknownUncleParent(H256), + /// The same author issued different votes at the same step. + DoubleVote(H160), } impl fmt::Display for BlockError { @@ -200,6 +202,7 @@ impl fmt::Display for BlockError { RidiculousNumber(ref oob) => format!("Implausible block number. {}", oob), UnknownParent(ref hash) => format!("Unknown parent: {}", hash), UnknownUncleParent(ref hash) => format!("Unknown uncle parent: {}", hash), + DoubleVote(ref address) => format!("Author {} issued too many blocks.", address), }; f.write_fmt(format_args!("Block error ({})", msg)) diff --git a/ethcore/src/ethereum/ethash.rs b/ethcore/src/ethereum/ethash.rs index 6436e3531..de2a85942 100644 --- a/ethcore/src/ethereum/ethash.rs +++ b/ethcore/src/ethereum/ethash.rs @@ -73,7 +73,9 @@ pub struct EthashParams { /// Number of first block where ECIP-1010 begins. pub ecip1010_pause_transition: u64, /// Number of first block where ECIP-1010 ends. - pub ecip1010_continue_transition: u64 + pub ecip1010_continue_transition: u64, + /// Maximum amount of code that can be deploying into a contract. + pub max_code_size: u64, } impl From for EthashParams { @@ -87,19 +89,20 @@ impl From for EthashParams { block_reward: p.block_reward.into(), registrar: p.registrar.map_or_else(Address::new, Into::into), homestead_transition: p.homestead_transition.map_or(0, Into::into), - dao_hardfork_transition: p.dao_hardfork_transition.map_or(0x7fffffffffffffff, Into::into), + dao_hardfork_transition: p.dao_hardfork_transition.map_or(u64::max_value(), Into::into), dao_hardfork_beneficiary: p.dao_hardfork_beneficiary.map_or_else(Address::new, Into::into), dao_hardfork_accounts: p.dao_hardfork_accounts.unwrap_or_else(Vec::new).into_iter().map(Into::into).collect(), - difficulty_hardfork_transition: p.difficulty_hardfork_transition.map_or(0x7fffffffffffffff, Into::into), + difficulty_hardfork_transition: p.difficulty_hardfork_transition.map_or(u64::max_value(), Into::into), difficulty_hardfork_bound_divisor: p.difficulty_hardfork_bound_divisor.map_or(p.difficulty_bound_divisor.into(), Into::into), - bomb_defuse_transition: p.bomb_defuse_transition.map_or(0x7fffffffffffffff, Into::into), + bomb_defuse_transition: p.bomb_defuse_transition.map_or(u64::max_value(), Into::into), eip150_transition: p.eip150_transition.map_or(0, Into::into), eip155_transition: p.eip155_transition.map_or(0, Into::into), eip160_transition: p.eip160_transition.map_or(0, Into::into), eip161abc_transition: p.eip161abc_transition.map_or(0, Into::into), - eip161d_transition: p.eip161d_transition.map_or(0x7fffffffffffffff, Into::into), - ecip1010_pause_transition: p.ecip1010_pause_transition.map_or(0x7fffffffffffffff, Into::into), - ecip1010_continue_transition: p.ecip1010_continue_transition.map_or(0x7fffffffffffffff, Into::into), + eip161d_transition: p.eip161d_transition.map_or(u64::max_value(), Into::into), + ecip1010_pause_transition: p.ecip1010_pause_transition.map_or(u64::max_value(), Into::into), + ecip1010_continue_transition: p.ecip1010_continue_transition.map_or(u64::max_value(), Into::into), + max_code_size: p.max_code_size.map_or(u64::max_value(), Into::into), } } } @@ -152,6 +155,7 @@ impl Engine for Ethash { Schedule::new_homestead() } else { Schedule::new_post_eip150( + self.ethash_params.max_code_size as usize, env_info.number >= self.ethash_params.eip160_transition, env_info.number >= self.ethash_params.eip161abc_transition, env_info.number >= self.ethash_params.eip161d_transition diff --git a/ethcore/src/evm/schedule.rs b/ethcore/src/evm/schedule.rs index b68f6acb5..773708956 100644 --- a/ethcore/src/evm/schedule.rs +++ b/ethcore/src/evm/schedule.rs @@ -70,6 +70,8 @@ pub struct Schedule { pub quad_coeff_div: usize, /// Cost for contract length when executing `CREATE` pub create_data_gas: usize, + /// Maximum code size when creating a contract. + pub create_data_limit: usize, /// Transaction cost pub tx_gas: usize, /// `CREATE` transaction cost @@ -111,7 +113,7 @@ impl Schedule { } /// Schedule for the post-EIP-150-era of the Ethereum main net. - pub fn new_post_eip150(fix_exp: bool, no_empty: bool, kill_empty: bool) -> Schedule { + pub fn new_post_eip150(max_code_size: usize, fix_exp: bool, no_empty: bool, kill_empty: bool) -> Schedule { Schedule { exceptional_failed_code_deposit: true, have_delegate_call: true, @@ -139,6 +141,7 @@ impl Schedule { memory_gas: 3, quad_coeff_div: 512, create_data_gas: 200, + create_data_limit: max_code_size, tx_gas: 21000, tx_create_gas: 53000, tx_data_zero_gas: 4, @@ -183,6 +186,7 @@ impl Schedule { memory_gas: 3, quad_coeff_div: 512, create_data_gas: 200, + create_data_limit: usize::max_value(), tx_gas: 21000, tx_create_gas: tcg, tx_data_zero_gas: 4, diff --git a/ethcore/src/externalities.rs b/ethcore/src/externalities.rs index df1b64e67..3704ead67 100644 --- a/ethcore/src/externalities.rs +++ b/ethcore/src/externalities.rs @@ -242,7 +242,7 @@ impl<'a, T, V> Ext for Externalities<'a, T, V> where T: 'a + Tracer, V: 'a + VMT }, OutputPolicy::InitContract(ref mut copy) => { let return_cost = U256::from(data.len()) * U256::from(self.schedule.create_data_gas); - if return_cost > *gas { + if return_cost > *gas || data.len() > self.schedule.create_data_limit { return match self.schedule.exceptional_failed_code_deposit { true => Err(evm::Error::OutOfGas), false => Ok(*gas) diff --git a/ethcore/src/miner/miner.rs b/ethcore/src/miner/miner.rs index f86ecedc4..b770aa40c 100644 --- a/ethcore/src/miner/miner.rs +++ b/ethcore/src/miner/miner.rs @@ -214,7 +214,8 @@ pub struct Miner { sealing_block_last_request: Mutex, // for sealing... options: MinerOptions, - seals_internally: bool, + /// Does the node perform internal (without work) sealing. + pub seals_internally: bool, gas_range_target: RwLock<(U256, U256)>, author: RwLock
, @@ -269,6 +270,11 @@ impl Miner { } } + /// Creates new instance of miner with accounts and with given spec. + pub fn with_spec_and_accounts(spec: &Spec, accounts: Option>) -> Miner { + Miner::new_raw(Default::default(), GasPricer::new_fixed(20_000_000_000u64.into()), spec, accounts) + } + /// Creates new instance of miner without accounts, but with given spec. pub fn with_spec(spec: &Spec) -> Miner { Miner::new_raw(Default::default(), GasPricer::new_fixed(20_000_000_000u64.into()), spec, None) @@ -431,6 +437,7 @@ impl Miner { let last_request = *self.sealing_block_last_request.lock(); let should_disable_sealing = !self.forced_sealing() && !has_local_transactions + && !self.seals_internally && best_block > last_request && best_block - last_request > SEALING_TIMEOUT_IN_BLOCKS; @@ -474,9 +481,10 @@ impl Miner { /// Uses Engine to seal the block internally and then imports it to chain. fn seal_and_import_block_internally(&self, chain: &MiningBlockChainClient, block: ClosedBlock) -> bool { - if !block.transactions().is_empty() { + if !block.transactions().is_empty() || self.forced_sealing() { if let Ok(sealed) = self.seal_block_internally(block) { if chain.import_block(sealed.rlp_bytes()).is_ok() { + trace!(target: "miner", "import_block_internally: imported internally sealed block"); return true } } @@ -775,7 +783,7 @@ impl MinerService for Miner { chain: &MiningBlockChainClient, transactions: Vec ) -> Vec> { - + trace!(target: "external_tx", "Importing external transactions"); let results = { let mut transaction_queue = self.transaction_queue.lock(); self.add_transactions_to_queue( diff --git a/ethcore/src/service.rs b/ethcore/src/service.rs index 00ba981b9..36b5e7157 100644 --- a/ethcore/src/service.rs +++ b/ethcore/src/service.rs @@ -48,6 +48,8 @@ pub enum ClientIoMessage { FeedBlockChunk(H256, Bytes), /// Take a snapshot for the block with given number. TakeSnapshot(u64), + /// Trigger sealing update (useful for internal sealing). + UpdateSealing, } /// Client service setup. Creates and registers client and network services with the IO subsystem. @@ -111,6 +113,8 @@ impl ClientService { }); try!(io_service.register_handler(client_io)); + spec.engine.register_message_channel(io_service.channel()); + let stop_guard = ::devtools::StopGuard::new(); run_ipc(ipc_path, client.clone(), snapshot.clone(), stop_guard.share()); @@ -213,8 +217,11 @@ impl IoHandler for ClientIoHandler { if let Err(e) = res { debug!(target: "snapshot", "Failed to initialize periodic snapshot thread: {:?}", e); } - - } + }, + ClientIoMessage::UpdateSealing => { + trace!(target: "authorityround", "message: UpdateSealing"); + self.client.update_sealing() + }, _ => {} // ignore other messages } } diff --git a/ethcore/src/spec/spec.rs b/ethcore/src/spec/spec.rs index de1b7db42..c8910bbdd 100644 --- a/ethcore/src/spec/spec.rs +++ b/ethcore/src/spec/spec.rs @@ -18,7 +18,7 @@ use util::*; use builtin::Builtin; -use engines::{Engine, NullEngine, InstantSeal, BasicAuthority}; +use engines::{Engine, NullEngine, InstantSeal, BasicAuthority, AuthorityRound}; use pod_state::*; use account_db::*; use header::{BlockNumber, Header}; @@ -150,6 +150,7 @@ impl Spec { ethjson::spec::Engine::InstantSeal => Arc::new(InstantSeal::new(params, builtins)), ethjson::spec::Engine::Ethash(ethash) => Arc::new(ethereum::Ethash::new(params, From::from(ethash.params), builtins)), ethjson::spec::Engine::BasicAuthority(basic_authority) => Arc::new(BasicAuthority::new(params, From::from(basic_authority.params), builtins)), + ethjson::spec::Engine::AuthorityRound(authority_round) => AuthorityRound::new(params, From::from(authority_round.params), builtins).expect("Consensus engine could not be started."), } } @@ -280,6 +281,10 @@ impl Spec { /// Create a new Spec with InstantSeal consensus which does internal sealing (not requiring work). pub fn new_instant() -> Spec { load_bundled!("instant_seal") } + + /// Create a new Spec with AuthorityRound consensus which does internal sealing (not requiring work). + /// Accounts with secrets "1".sha3() and "2".sha3() are the authorities. + pub fn new_test_round() -> Self { load_bundled!("authority_round") } } #[cfg(test)] diff --git a/ethcore/src/tests/helpers.rs b/ethcore/src/tests/helpers.rs index 96d5f8366..adfb4f096 100644 --- a/ethcore/src/tests/helpers.rs +++ b/ethcore/src/tests/helpers.rs @@ -433,18 +433,19 @@ pub fn get_default_ethash_params() -> EthashParams{ block_reward: U256::from(0), registrar: "0000000000000000000000000000000000000001".into(), homestead_transition: 1150000, - dao_hardfork_transition: 0x7fffffffffffffff, + dao_hardfork_transition: u64::max_value(), dao_hardfork_beneficiary: "0000000000000000000000000000000000000001".into(), dao_hardfork_accounts: vec![], - difficulty_hardfork_transition: 0x7fffffffffffffff, + difficulty_hardfork_transition: u64::max_value(), difficulty_hardfork_bound_divisor: U256::from(0), - bomb_defuse_transition: 0x7fffffffffffffff, - eip150_transition: 0x7fffffffffffffff, - eip155_transition: 0x7fffffffffffffff, - eip160_transition: 0x7fffffffffffffff, - eip161abc_transition: 0x7fffffffffffffff, - eip161d_transition: 0x7fffffffffffffff, - ecip1010_pause_transition: 0x7fffffffffffffff, - ecip1010_continue_transition: 0x7fffffffffffffff + bomb_defuse_transition: u64::max_value(), + eip150_transition: u64::max_value(), + eip155_transition: u64::max_value(), + eip160_transition: u64::max_value(), + eip161abc_transition: u64::max_value(), + eip161d_transition: u64::max_value(), + ecip1010_pause_transition: u64::max_value(), + ecip1010_continue_transition: u64::max_value(), + max_code_size: u64::max_value(), } } diff --git a/ethstore/res/wordlist.txt b/ethstore/res/wordlist.txt index f330038cf..caf71f526 100644 --- a/ethstore/res/wordlist.txt +++ b/ethstore/res/wordlist.txt @@ -1,7530 +1,7776 @@ -station -acting -accept -blow -strange -saved -conversation -plane -mama -yesterday -lied -quick -lately -stuck -lovely -security -report -difference -rid -store -bag -bought -ball -single -doubt -listening -major -walking -cops -blue -deep -dangerous -park -sleeping -shh -record -lord -moved -join -key -captain -card -crime -gentlemen -willing -window -return -walked -guilty -likes -fighting -difficult -soul -joke -service -magic -favorite -uncle -promised -public -bother -island -seriously -cell -lead -knowing -broken -advice -somehow -paid -losing -push -helped -killing -usually -earlier -boss -beginning -liked -innocent -doc -rules -summer -cop -learned -thirty -risk -letting -speaking -officer -ridiculous -support -afternoon -born -dreams -apologize -seat -nervous -across -song -charge -patient -boat -brain -hide -detective -general -planning -nine -huge -breakfast -horrible -age -awful -pleasure -driving -hanging -picked -system -sell -quit -apparently -dying -notice -congratulations -chief -faith -gay -month -visit -letter -decide -double -sad -press -forward -fool -showed -smell -seemed -spell -memory -pictures -slow -seconds -hungry -board -position -hearing -kitchen -force -fly -during -space -realized -experience -kick -others -grab -discuss -third -cat -fifty -responsible -miles -fat -reading -idiot -yep -rock -rich -suddenly -agent -bunch -destroy -bucks -track -shoes -scene -peace -arms -demon -low -consider -papers -medical -incredible -witch -drunk -attorney -tells -knock -ways -belle -cash -gives -department -nose -turns -keeps -beer -jealous -drug -sooner -cares -plenty -extra -tea -won -attack -ground -whose -outta -weekend -matters -wrote -type -gosh -opportunity -king -impossible -books -machine -waste -pretend -named -danger -wall -jump -eating -proof -complete -slept -career -arrest -star -breathe -perfectly -warm -pulled -twice -easier -killer -dating -suit -romantic -drugs -comfortable -powers -finds -checked -fit -divorce -begin -ourselves -closer -ruin -although -smile -laugh -fish -treat -fear -otherwise -excited -mail -hiding -cost -green -stole -noticed -fired -excellent -lived -bringing -pop -piper -bottom -note -sudden -church -bathroom -flight -honestly -sing -foot -games -glass -remind -bank -charges -witness -finding -places -tree -dare -hardly -interest -steal -princess -silly -contact -teach -shop -plus -colonel -fresh -trial -invited -roll -radio -art -reach -heh -dirty -choose -emergency -dropped -butt -credit -obvious -cry -locked -loving -positive -nuts -agreed -price -goodbye -condition -guard -grow -cake -mood -total -crap -crying -belong -lay -partner -trick -pressure -ohh -arm -dressed -cup -lies -bus -taste -neck -south -nurse -raise -land -cross -lots -mister -carry -group -whoever -drinking -breaking -file -lock -computer -wine -closed -writing -spot -paying -study -assume -asleep -turning -legal -justice -bedroom -shower -camera -fill -reasons -forty -bigger -nope -keys -breath -doctors -pants -freak -level -movies -gee -action -area -folks -cream -ugh -continue -focus -wild -truly -desk -convince -client -threw -band -hurts -spending -field -allow -grand -answers -shirt -chair -allowed -rough -doin -sees -government -ought -empty -round -lights -insane -hall -hat -bastard -wind -shows -aware -dealing -pack -meaning -flowers -tight -hurting -ship -subject -guest -chicken -pal -match -arrested -sun -confused -surgery -expecting -deacon -unfortunately -goddamn -lab -passed -bottle -beyond -whenever -pool -opinion -naked -held -common -starts -jerk -secrets -falling -played -necessary -barely -dancing -health -tests -copy -video -cousin -planned -dry -ahem -twelve -simply -skin -often -fifteen -spirit -speech -names -issue -orders -nah -final -results -code -believed -complicated -umm -research -nowhere -escape -biggest -restaurant -page -grateful -usual -burn -address -within -someplace -screw -everywhere -train -film -regret -goodness -mistakes -heaven -details -responsibility -suspect -corner -hero -dumb -terrific -mission -further -gas -whoo -hole -memories -truck -following -ended -teeth -ruined -split -bear -airport -bite -smoke -older -liar -horse -showing -van -project -cards -desperate -themselves -search -pathetic -damage -spoke -quickly -scare -beach -brown -afford -vote -settle -gold -mentioned -due -passion -stayed -rule -checking -tie -hired -upon -rush -heads -concern -blew -natural -champagne -connection -tickets -finger -happiness -form -saving -kissing -hated -personally -suggest -prepared -build -leg -onto -leaves -downstairs -ticket -taught -loose -holy -staff -sea -planet -duty -convinced -throwing -defense -kissed -legs -according -loud -practice -bright -babies -army -warning -miracle -carrying -flying -blind -queen -ugly -shopping -hates -monster -sight -vampire -bride -coat -account -states -clearly -celebrate -brilliant -wanting -add -moon -lips -custody -center -screwed -buying -size -toast -thoughts -student -stories -however -professional -stars -reality -birth -attitude -advantage -grandfather -sold -opened -grandma -beg -changes -someday -grade -cheese -roof -pizza -brothers -signed -bird -ahh -marrying -powerful -grown -grandmother -fake -opening -expected -eventually -ideas -exciting -covered -familiar -bomb -television -harmony -color -heavy -schedule -records -dollar -capable -master -numbers -practically -including -correct -clue -forgotten -immediately -appointment -social -nature -ú -deserves -west -teacher -threat -bloody -lonely -ordered -shame -local -jacket -hook -destroyed -scary -loser -investigation -above -invite -shooting -merry -port -precious -lesson -criminal -growing -caused -victim -professor -followed -funeral -dean -considering -burning -couch -strength -harder -loss -view -beauty -sisters -several -pushed -written -shock -pushing -heat -chocolate -greatest -miserable -nightmare -energy -brings -character -became -famous -enemy -crash -chances -sending -recognize -healthy -boring -feed -engaged -percent -headed -lines -treated -purpose -north -knife -rights -drag -fan -badly -speed -hire -curious -paint -pardon -built -behavior -closet -candy -warn -gorgeous -post -milk -survive -forced -daria -victoria -operation -suck -offered -ends -dump -rent -marshall -remembered -lieutenant -trade -thanksgiving -rain -revenge -physical -available -program -prefer -spare -pray -disappeared -aside -statement -sometime -animal -sugar -meat -fantastic -breathing -laughing -itself -tip -stood -market -affair -ours -depends -cook -babe -main -woods -protecting -jury -national -brave -storm -large -prince -interview -roger -football -fingers -murdered -sexy -explanation -process -picking -based -style -stone -pieces -blah -assistant -stronger -block -aah -bullshit -pie -handsome -unbelievable -anytime -nearly -shake -cars -wherever -serve -pulling -points -medicine -facts -waited -lousy -circumstances -stage -disappointed -weak -trusted -license -nothin -community -trey -trash -understanding -slip -cab -sounded -awake -friendship -stomach -weapon -threatened -mystery -official -dick -regular -river -valley -understood -contract -bud -sexual -race -basically -switch -lake -frankly -issues -cheap -lifetime -deny -painting -ear -clock -baldwin -weight -garbage -tear -ears -dig -bullet -selling -setting -indeed -gus -changing -singing -tiny -particular -draw -decent -susan -super -spring -santos -avoid -messed -united -filled -touched -score -disappear -stranger -exact -pills -kicked -harm -recently -snow -fortune -strike -pretending -raised -annie -slayer -monkey -insurance -fancy -sydney -drove -cared -belongs -nights -shape -dogs -lorelai -jackie -base -maggie -lift -lewis -stock -fashion -freedom -timing -johnny -guarantee -chest -bridge -woke -tabitha -source -patients -theory -lisa -camp -original -juice -burned -access -watched -heading -selfish -oil -drinks -wise -failed -period -doll -committed -elevator -freeze -noise -exist -science -pair -edge -wasting -sat -player -ceremony -cartman -pig -uncomfortable -peg -guns -vacation -staring -files -bike -weather -mostly -stress -sucks -permission -arrived -thrown -possibility -faster -example -borrow -release -ate -notes -joy -hoo -library -junior -property -negative -fabulous -event -doors -screaming -vision -member -bone -battle -safety -term -devil -meal -fellow -asshole -apology -anger -honeymoon -wet -bail -parking -fucked -non -hung -protection -manager -fixed -families -dawn -sports -campaign -map -wash -stolen -sensitive -stealing -photo -chose -lets -comfort -worrying -whom -pocket -bleeding -students -shoulder -ignore -fourth -neighborhood -talent -tied -garage -dies -demons -travel -success -dumped -witches -training -rude -crack -model -bothering -radar -grew -willow -remain -soft -meantime -gimme -connected -chase -kinds -cast -cancer -v -sky -likely -fate -buried -hug -driver -concentrate -throat -prom -messages -east -unit -intend -crew -ashamed -somethin -midnight -manage -guilt -weapons -terms -interrupt -guts -tongue -distance -conference -treatment -shoe -basement -sentence -purse -glasses -cabin -universe -towards -repeat -mirror -wound -tall -reaction -odd -engagement -therapy -letters -emotional -runs -magazine -jeez -decisions -soup -thrilled -society -managed -sue -stake -rex -chef -moves -awesome -genius -extremely -entirely -tory -nasty -moments -expensive -counting -shots -kidnapped -square -cleaning -shift -plate -impressed -smells -trapped -male -tour -knocked -charming -attractive -argue -puts -whip -language -heck -embarrassed -settled -package -laid -animals -hitting -disease -bust -stairs -alarm -pure -nail -nerve -incredibly -hill -walks -lane -dirt -bond -stamp -becoming -terribly -friendly -easily -damned -jobs -suffering -disgusting -washington -stopping -deliver -riding -helps -federal -disaster -bars -crossed -rate -create -trap -claim -talks -eggs -effect -chick -turkey -threatening -spoken -snake -introduce -rescue -confession -embarrassing -bags -lover -impression -gate -fantasy -reputation -balls -attacked -among -knowledge -presents -inn -chat -suffer -bryant -argument -talkin -crowd -homework -fought -coincidence -cancel -accepted -rip -pride -solve -hopefully -pounds -pine -mate -illegal -generous -tommy -streets -matt -director -glen -con -separate -outfit -maid -bath -punch -phil -mayor -helen -freaked -begging -recall -enjoying -bug -prepare -parts -wheel -signal -nikki -direction -defend -signs -painful -caroline -yourselves -walls -rat -maris -amount -suspicious -hearts -flat -cooking -button -warned -sixty -pity -parties -crisis -rae -coach -abbott -row -baseball -yelling -leads -awhile -pen -confidence -offering -falls -carter -image -farm -pleased -panic -monday -hers -gettin -smith -role -refuse -determined -jane -grandpa -progress -mexico -testify -passing -military -choices -artist -william -uhh -gym -cruel -wings -traffic -pink -bodies -mental -gentleman -coma -poison -cutting -proteus -guests -expert -bull -benefit -bell -faces -cases -mimi -ghost -led -jumped -toilet -secretary -sneak -q -mix -marty -firm -agreement -privacy -dates -anniversary -smoking -reminds -pot -created -twins -swing -successful -season -scream -considered -solid -options -flash -commitment -senior -ill -crush -ambulance -wallet -discovered -officially -gang -til -rise -reached -eleven -option -laundry -former -assure -stays -skip -hunt -fail -accused -wide -challenge -popular -learning -discussion -clinic -plant -exchange -betrayed -bro -sticking -university -target -members -lower -bored -mansion -soda -silver -sheriff -suite -handled -busted -senator -load -happier -younger -studying -romance -procedure -ocean -section -winter -sec -commit -bones -assignment -suicide -spread -minds -fishing -swim -ending -bat -yell -llanview -league -chasing -seats -proper -holiday -command -believes -humor -hopes -fifth -winning -solution -leader -yellow -sharp -sale -lawyers -giant -nor -material -latest -ash -highly -escaped -audience -winner -parent -burns -tricks -insist -dropping -cheer -medication -higher -flesh -district -wood -routine -cookies -century -shared -sandwich -psycho -handed -false -beating -appear -adult -warrant -spike -garden -awfully -odds -article -treating -thin -suggesting -fever -female -sweat -silent -specific -clever -sweater -request -prize -mall -tries -mile -manning -fully -estate -diamond -union -sharing -assuming -judgment -goodnight -divorced -quality -despite -surely -steps -jet -confess -mountain -math -listened -comin -answered -vulnerable -bless -dreaming -rooms -chip -zero -potential -pissed -kills -grant -wolf -tears -knees -chill -blonde -brains -agency -degree -unusual -joint -rob -packed -dreamed -cure -covering -newspaper -lookin -coast -grave -egg -direct -cheating -breaks -quarter -orange -mixed -locker -gifts -brand -awkward -toy -rare -policy -pilar -joking -competition -classes -assumed -reasonable -dozen -curse -quartermaine -millions -dessert -rolling -detail -alien -served -delicious -closing -vampires -released -ancient -wore -value -tail -site -secure -salad -murderer -hits -toward -spit -screen -pilot -penny -offense -dust -conscience -bread -answering -admitted -lame -invitation -hidden -grief -smiling -path -homer -destiny -del -stands -bowl -pregnancy -prisoner -delivery -guards -desire -virus -shrink -influence -freezing -concert -wreck -partners -chain -birds -walker -wire -technically -presence -blown -anxious -cave -version -mickey -holidays -cleared -wishes -survived -caring -candles -bound -related -charm -apple -yup -pulse -jumping -jokes -frame -boom -vice -performance -occasion -silence -opera -opal -nonsense -frightened -downtown -internet -slipped -holly -duck -dimera -blowing -session -relationships -kidnapping -actual -spin -classic -civil -tool -packing -education -blaming -wrap -obsessed -fruit -torture -personality -location -loan -effort -commander -trees -rocks -owner -fairy -banks -network -per -necessarily -county -contest -chuck -seventy -print -motel -fallen -directly -underwear -grams -exhausted -believing -particularly -freaking -carefully -trace -touching -messing -committee -smooth -recovery -intention -enter -consequences -belt -standard -sacrifice -marina -courage -butter -officers -enjoyed -lack -buck -attracted -appears -bay -yard -returned -remove -nut -carried -testimony -intense -granted -violence -heal -defending -attempt -unfair -relieved -political -loyal -approach -slowly -plays -normally -buzz -alcohol -actor -surprises -psychiatrist -pre -plain -attic -uniform -terrified -sons -pet -cleaned -threaten -teaching -mum -motion -fella -enemies -desert -collection -incident -failure -satisfied -imagination -hooked -headache -forgetting -counselor -acted -opposite -highest -gross -golden -equipment -badge -tennis -visiting -studio -naturally -frozen -commissioner -sakes -labor -glory -appropriate -trunk -armed -twisted -thousands -received -dunno -costume -temporary -sixteen -impressive -zone -kitty -kicking -junk -hon -grabbed -unlike -understands -mercy -describe -priest -clients -cable -owns -affect -witnesses -starving -instincts -happily -discussing -deserved -strangers -leading -intelligence -host -authority -surveillance -cow -commercial -admire -shadow -questioning -fund -dragged -barn -object -deeply -amp -wrapped -wasted -tense -sport -route -reports -plastic -hoped -fellas -election -roommate -pierce -mortal -fascinating -chosen -stops -shown -arranged -abandoned -sides -delivered -china -becomes -arrangements -agenda -hunting -began -theater -series -literally -propose -honesty -basketball -underneath -forces -soldier -services -sauce -review -promises -lecture -eighty -brandy -bills -windows -torn -shocked -relief -horses -golf -explained -counter -design -circle -victims -transfer -response -channel -backup -identity -differently -campus -spy -ninety -interests -guide -elliot -deck -biological -pheebs -minor -ease -creep -waitress -skills -telephone -photos -ripped -raising -scratch -rings -prints -flower -wave -thee -arguing -royal -laws -figures -asks -writer -reception -pin -oops -diner -annoying -agents -taggert -goal -council -mass +abacus +abdomen +abdominal +abide +abiding ability -sergeant -international -gig -blast -basic -wing -tradition -towel -earned -clown -rub -habit -customers -creature -counts -actions -snap -react -prime -paranoid -pace -wha -handling -eaten -dahlia -therapist -comment -charged -tax -sink -reporter -nurses -beats -priority -interrupting -gain -fed -warehouse -virgin -shy -pattern -loyalty -inspector -events -candle -pleasant -media -excuses -duke -castle -threats -permanent -guessing -financial -demand -basket -assault -tend -praying -motive -los -unconscious -trained -museum -alley -tracks -swimming -range -nap -mysterious -unhappy -tone -switched -liberty -bang -award -neighbor -loaded -gut -childhood -causing -swore -sample -piss -hundreds -balance -background -toss -mob -misery -central -boots -thief -squeeze -potter -lobby -hah -geez -exercise -ego -drama -patience -noble -indian -forth -facing -engine -booked -boo -songs -poker -eighteen -cookie -bury -perform -everyday -digging -creepy -compared -wondered -trail -saint -rotten -liver -hmmm -drawn -device -whore -magical -village -march -journey -fits -discussed -zombie -supply -moral -helpful -attached -slut -searching -flew -depressed -aliens -aisle -underground -pro -drew -daughters -cris -amen -vows -proposal -pit -neighbors -darn -clay -cents -arrange -annulment -uses -useless -squad -represent -product -joined -afterwards -adventure -resist -protected -net -fourteen -celebrating -piano -inch -flag -debt -darkness -violent -tag -sand -gum -dammit -strip -hip -celebration -below -reminded -palace -claims -replace -phones -paperwork -mighty -emotions -typical -stubborn -stable -pound -pillow -papa -mature -lap -designed -current -bum -tension -tank -suffered -stroke -steady -provide -overnight -meanwhile -chips -beef -wins -suits -carol -boxes -salt -express -collect -tragedy -therefore -spoil -realm -profile -degrees -wipe -surgeon -stretch -stepped -nephew -neat -limo -fox -confident -anti -victory -perspective -designer -climb -angels -title -suggested -punishment -finest -occurred -hint -furniture -blanket -twist -trigger -surrounded -surface -proceed -lip -jersey -fries -worries -refused -niece -handy -gloves -soap -signature -disappoint -crawl -convicted -zoo -result -pages -lit -flip -counsel -cheers -doubts -crimes -accusing -shaking -remembering -phase -kit -hallway -halfway -bothered -useful -popcorn -makeup -madam -gather -cowboy -concerns -cameras -blackmail -symptoms -rope -ordinary -imagined -concept -cigarette -barb -supportive -memorial -explosion -yay -woo -trauma -ouch -furious -cheat -avoiding -whew -thick -oooh -boarding -approve -urgent -shhh -misunderstanding -minister -drawer -sin -phony -joining -jam -interfere -governor -chapter -catching -bargain -warren -tragic -schools -respond -punish -penthouse -hop -angle -thou -sherry -remains -rach -ohhh -insult -bugs -beside -begged -absolute -strictly -socks -senses -ups -sneaking -yah -worthy -serving -reward -polite -checks -tale -physically -instructions -fooled -blows -tabby -internal -bitter -adorable -tested -suggestion -string -mouse -marks -jewelry -debate -com -alike -pitch -jacks -fax -distracted -shelter -lovers -lessons -hart -goose -foreign -escort -average -twin -testing -damnit -constable -circus -audition -tune -shoulders -mud -mask -helpless -feeding -explains -dated -sucked -robbery -objection -kirk -behave -valuable -shadows -creative -courtroom -confusing -beast -tub -talented -struck -smarter -mistaken -customer -bizarre -scaring -punk -motherfucker -holds -focused -alert -activity -vecchio -sticks -singer -reverend -highway -foolish -compliment -blessed -bastards -attend -scheme -aid -worker -wheelchair -protective -poetry -gentle -script -reverse -picnic -knee -intended -construction -cage -wives -voices -toes -stink -scares -pour -effects -cheated -tower -slide -ruining -recent -jewish -filling -exit -cruise -cottage -corporate -cats -upside -supplies -proves -parked -instance -grounds -diary -complaining -basis -wounded -politics -confessed -wicked -pipe -merely -massage -data -colors -chop -budget -brief -spill -prayer -costs -chicks -betray -begins -arrangement -waiter -sucker -scam -rats -fraud -flu -brush -adopted -tables -sympathy -pill -pee -lean -filthy -cliff -burger -web -seventeen -landed -expression -entrance -employee -drawing -cap -bunny -bracelet -thirteen -scout -principal -pays -fairly -facility -deeper -arrive -unique -tracking -spite -shed -recommend -oughta -nanny -naive -menu -grades -diet -corn -authorities -separated -roses -patch -grey -dime -devastated -description -tap -subtle -include -garrison -citizen -bullets -beans -pile -metal -las -executive -confirm -capital -adults -toe -strings -parade -harbor -bow -borrowed -booth -toys -straighten -steak -status -remote -premonition -poem -planted -honored -youth -specifically -meetings -exam -daily -convenient -traveling -matches -laying -insisted -crystal -apply -units -technology -steel -muscle -dish -aitoro -sis -sales -legend -kindly -grandson -donor -wheels -temper -teenager -strategy -proven -mothers -monitor -iron -houses -eternity -denial -couples -backwards -tent -swell -noon -happiest -gotcha -episode -drives -bacon -thinkin -spirits -potion -holes -fence -dial -affairs -acts -whatsoever -ward -rehearsal -proved -overheard -nuclear -lemme -leather -hostage -hammer -faced -discover -constant -bench -tryin -taxi -shove -sets -moron -limits -impress -gray -entitled -connect -pussy -needle -limit -lad -intelligent -instant -forms -disagree -tiger -stinks -recover -losers -groom -gesture -developed -constantly -blocks -bartender -tunnel -suspects -sealed -removed -paradise -legally -illness -hears -dresses -aye -vehicle -thy -teachers -sheet -receive -psychic -denied -teenage -rabbit -puppy -knocking -judging -bible -behalf -accidentally -waking -ton -superior -slack -seek -rumor -manners -homeless -hollow -hills -desperately -critical -coward -theme -tapes -sheets -referring -personnel -item -gear -majesty -forest -fans -exposed -cried -tons -spells -producer -launch -jay -instinct -extreme -belief -quote -motorcycle -convincing -appeal -advance -greater -fashioned -empire -aids -accomplished -grip -bump -upsetting -soldiers -scheduled -production -needing -invisible -forgiveness -feds -complex -compare -cloud -champion -bothers -blank -treasure -tooth -territory -sacred -inviting -inner -earn -compromise -cocktail -tramp -temperature -signing -messenger -landing -jabot -intimate -dignity -dealt -souls -root -informed -gods -entertainment -dressing -cigarettes -blessing -billion -upper -manner -lightning -leak -fond -alternative -seduce -players -operate -modern -liquor -fingerprints -enchantment -butters -stuffed -filed -emotionally -division -conditions -uhm -transplant -tips -powder -passes -oxygen -nicely -lunatic -hid -drill -designs -complain -announcement -visitors -unfortunate -slap -pumpkin -prayers -plug -organization -opens -oath -mutual -hockey -graduate -confirmed -broad -yacht -spa -remembers -horn -fried -extraordinary -bait -appearance -abuse -sworn -stare -safely -reunion -plot -burst -aha -experiment -experienced -dive -commission -chaos -cells -aboard -returning -lesbian -independent -expose -environment -buddies -trusting -spider -smaller -mountains -booze -tattoo -sweep -sore -scudder -properly -parole -effective -ditch -decides -canceled -bulldog -bra -speaks -rubber -reaching -glow -foundation -wears -thirsty -skull -scotch -ringing -dorm -dining -bend -unexpected -systems -sob -pat -pancakes -harsh -flattered -existence -ahhh -troubles -proposed -fights -favourite -eats -driven -computers -chin -bravo -seal -rage -causes -bubble -border -undercover -spoiled -shine -rug -identify -destroying -deputy -deliberately -conspiracy -clothing -thoughtful -similar -sandwiches -plates -nails -miracles -investment -fridge -drank -contrary -beloved -allergic -washed -stalking -solved -sack -misses -forgiven -earl -cuz -bent -approval -practical -organized -jungle -involve -industry -fuel -dragging -dancer -cotton -cooked -possession -pointing -foul -editor -dull -beneath -ages -peanut -horror -heels -grass -faking -deaf -stunt -portrait -painted -jealousy -hopeless -fears -cuts -conclusion -volunteer -sword -scenario -satellite -necklace -crashed -chapel -accuse -teddy -restraining -naughty -humans -homicide -helicopter -formal -firing -shortly -safer -missy -diamonds -devoted -auction -videotape -tore -stores -reservations -pops -appetite -wounds -vanquish -symbol -prevent -patrol -ironic -flow -fathers -excitement -anyhow -tearing -sends -rape -laughed -function -core -charmed -carpet -bowling -belly -sub -shark -dealer -cooperate -bachelor -accomplish -wakes -struggle -spotted -sorts -reservation -fort -coke -ashes -yards -votes -tastes -supposedly -loft -intentions -integrity -wished -towels -suspected -slightly -qualified -profit -log -investigating -inappropriate -immediate -ginger -companies -backed -sunset -pan -owned -nation -lipstick -lawn -compassion -cafeteria -belonged -affected -scarf -precisely -obsession -management -loses -lighten -infection -granddaughter -explode -chemistry -balcony -storage -spying -publicity -exists -employees -depend -cue -cracked -conscious -aww -ally -ace -accounts -absurd -vicious -tools -strongly -rap -potato -invented -hood -forbid -directions -defendant -bare -announce -screwing -samples -salesman -rounds -robbed -leap -lakeview -insanity -injury -genetic -freaks -fighter -document -burden -swallow -slave -reveal -religious -possibilities -martini -kidnap -gown -entering -chairs -wishing -statue -stalker -setup -serial -sandy -punished -dramatic -dismissed -criminals -carver -blade -seventh -regrets -raped -quarters -produce -pony -lamp -dentist -anyways -anonymous -added -tech -semester -risks -regarding -owes -magazines -machines -lungs -explaining -delicate -tricked -oldest -eager -doomed -coffin -click -cafe -buttons -bureau -adoption -traditional -surrender -stones -stab -sickness -scum -loop -independence -generation -floating -envelope -entered -combination -chamber -casino -worn -vault -sunshine -sorel -pretended -potatoes -plea -photograph -petty -payback -misunderstood -kiddo -healing -fiancée -cascade -capeside -application -stabbed -remarkable -random -guitar -frog -cabinet -brat -wrestling -sixth -scale -privilege -pencil -passionate -nerves -lawsuit -kidney -disturbed -crossing -cozy -avatar -associate -tire -shirts -required -posted -oven -ordering -mill -journal -gallery -delay -clubs -risky -purple -nest -monsters -honorable -grounded -gene -favour -electric -culture -closest -breast -breakdown -attempted -placed -conflict -bald -actress -abandon -wisdom -steam -scar -pole -duh -collar -worthless -warlock -sucking -standards -resources -photographs -introduced -injured -graduation -enormous -disturbing -disturb -distract -deals -conclusions -baker -vodka -situations -require -muffin -mid -measure -dishes -crawling -congress -briefcase -wiped -whistle -sits -roast -rented -pigs -penis -massive -link -flirting -existed -deposit -damaged -bottles -unknown -types -topic -robin -riot -overreacting -minimum -logical -impact -hostile -embarrass -casual -beacon -amusing -altar -values -ultimate -skinny -recognized -maintain -goods -covers -battery -survival -skirt -shave -prisoners -porch -med -ghosts -favors -drops -dizzy -chili -breasts -begun -beaten -advise -transferred -strikes -rehab -raw -photographer -peaceful -leery -kraft -hooker -heavens -fortunately -fooling -expectations -draft -citizens -cigar -active -weakness -ski -ships -ranch -practicing -musical -movement -individual -homes -executed -examine -documents -cranes -column -bribe -beers -task -species -sail -rum -resort -rash -prescription -operating -hush -fuzzy -fragile -forensics -expense -drugged -differences -cows -conduct -comic -bingo -bells -avenue -attacking -assigned -visitor -suitcase -sources -sorta -scan -rod -payment -motor -mini -manticore -inspired -insecure -imagining -hardest -gamble -clerk -yea -wrist -tube -starters -silk -pump -pale -nicer -haul -guardian -flies -dodge -demands -boot -arts -thumb -limited -lighter -elders -connections -shooter -quietly -pulls -lion -idiots -factor -erase -denying -attacks -ankle -amnesia -accepting -ooo -hunter -heartbeat -gal -fry -confront -backing -register -phrase -operations -minus -meets -legitimate -hurricane -fixing -communication -bucket -boats -auto -arrogant -tuna -supper -studies -slightest -sins -sayin -recipe -pier -paternity -mason -lamb -kisses -humiliating -genuine -catholic -snack -rational -pointed -passport -minded -guessed -fiancé -display -dip -advanced -weddings -unh -tumor -teams -reported -marco -humiliated -hee -destruction -copies -closely -bid -banana -august -aspirin -academy -wig -throughout -spray -picks -occur -logic -knight -fields -eyed -equal -drowning -contacts -ritual -perfume -hiring -hating -ham -generally -fusion -error -elected -docks -creatures -visions -thanking -thankful -sock -replaced -reed -nineteen -fork -comedy -analysis -throws -teenagers -studied -stressed -slice -shore -rolls -requires -plead -palm -ladder -kicks -ford -detectives -assured -widow -tissue -tellin -shallow -responsibilities -repay -rejected -permanently -howdy -hack -girlfriends -deadly -comforting -ceiling -bonus -verdict -maintenance -jar -insensitive -heather -factory -aim -triple -spilled -respected -recovered -messy -interrupted -entry -blond -bleed -benefits -wardrobe -takin -significant -objective -murders -foster -doo -ding -chart -backs -airplane -workers -waves -underestimate -ties -soccer -registered -multiple -justify -harmless -frustrated -fold -convention -communicate -bugging -attraction -arson -whack -tits -salary -rumors -residence -obligation -medium -liking -development -develop -dearest -congratulate -alliance -vengeance -severe -rack -puzzle -puerto -guidance -fires -dickie -courtesy -caller -bounce -blamed -wizard -tops -repair -quiz -prep -involves -headquarters -curiosity -codes -circles -bears -barbecue -troops -spinning -scores -pursue -psychotic -groups -cough -claimed -accusations -shares -rushing -resent -laughs -gathered -freshman -envy -drown -chemical -branch -asses -sofa -scientist -poster -models -islands -highness -drain -dock -cha -apologies -welfare -theirs -stat -stall -spots -somewhat -solo -realizes -psych -mmmm -jazz -hawk -fools -finishing -beard -album -wee -understandable -unable -treats -theatre -succeed -stir -relaxed -makin -inches -gratitude -faithful -bin -accent -zip -witter -wandering -shell -regardless -racing -que -locate -inevitable -griffin -deed -crushed -controlling -western -taxes -smelled -sheep -settlement -rocky -robe -retired -poet -opposed -marked -gossip -gambling -determine -cosmetics -cent -accidents -tricky -surprising -stiff -sincere -shield -rushed -rice -resume -reporting -refrigerator -reference -preparing -nightmares -mijo -ignoring -hunch -fog -fireworks -drowned -crown -cooperation -brass -accurate -whispering -sophisticated -religion -luggage -lemon -investigate -hike -explore -emotion -dragon -creek -crashing -contacted -complications -cherry -acid -z -shining -rolled -righteous -reconsider -inspiration -goody -geek -frightening -festival -ethics -creeps -courthouse -camping -assistance -affection -vow -protest -lodge -haircut -forcing -eternal -essay -chairman -baked -apologized -vibe -stud -stargate -sailor -respects -receipt -operator -mami -includes -hats -goat -exclusive -destructive -define -defeat -cheek -adore -adopt -warrior -voted -tracked -signals -shorts -reminding -relative -pond -ninth -floors -dough -creations -continues -cancelled -barrel -tuck -snuck -slight -reporters -rear -pressing -novel -newspapers -magnificent -madame -lick -lazy -goddess -glorious -fiancee -candidate -brick -bits -activities -visitation -teen -scholarship -sane -previous -kingdom -kindness -flames -sunny -shoulda -rescued -mattress -lounge -lobster -lifted -label -importantly -glove -enterprises -disappointment -condo -cemetery -beings -admitting -yelled -waving -spoon -screech -satisfaction -requested -reads -plants -nun -navy -nailed -elephant -described -dedicated -certificate -centuries -annual -worm -tick -resting -primary -polish -monkeys -marvelous -fuss -funds -defensive -compete -chased -bush -balloon -sailing -provided -pockets -filing -depression -conversations -consideration -consciousness -worlds -innocence -indicate -fucker -freaky -forehead -bam -appeared -aggressive -trailer -summers -slam -retirement -quitting -pry -porn -narrow -levels -inform -fee -encourage -dug -delighted -daylight -danced -currently -confidential -chew -aunts -washing -warden -tossed -temple -spectra -permit -mistress -marrow -lined -implying -hatred -grill -formula -efforts -corpse -clues -sober -relatives -promotion -peel -offended -morgue -larger -infected -humanity -eww -electricity -electrical -distraction -chopper -cart -broadcast -wired -violation -suspended -sting -promising -harassment -glue -gathering -deer -cursed -controlled -content -combat -calendar -brutal -bing -assets -warlocks -wagon -unpleasant -tan -robot -proving -priorities -pepper -observation -lease -killers -grows -flame -domestic -divine -disappearance -depressing -thrill -terminal -sitter -ribs -offers -naw -flush -exception -earrings -deadline -corporal -collapsed -update -snapped -smack -offices -melt -madness -figuring -eagle -delusional -coulda -burnt -actors -trips -tender -sperm -specialist -scientific -satan -realise -pork -popped -planes -interrogation -institution -included -gates -esteem -communications -choosing -choir -undo -pres -prayed -plague -manipulate -lifestyle -lance -insulting -honour -detention -delightful -daisy -coffeehouse -chess -betrayal -apologizing -adjust -wrecked -wont -whipped -rides -reminder -psychological -principle -monsieur -injuries -fame -faint -confusion -clouds -bon -bake -sang -nearest -industries -illusion -execution -distress -definition -cutter -creating -correctly -complaint -chickens -blocked -trophy -tortured -structure -rot -risking -pointless -pearl -household -heir -handing -eighth -dumping -cups -alibi +ablaze +able +abnormal +abrasion +abrasive +abreast +abridge +abroad +abruptly absence -vital -towers -thus -struggling -shiny -risked -refer -mummy -mint -keeper -involvement -hose -hobby -fortunate -fitting -curtain -counseling -coats -addition -wit -transport -technical -rode -puppet -prior -opportunities -modeling -memo -liquid -irresponsible -humiliation -hiya -freakin -fez -felony -choke -blackmailing -appreciated -tabloid -suspicion -recovering -rally -psychology -pledge -panicked -nursery -louder -jeans -investigator -identified -homecoming -height -graduated -frustrating -fabric -dot -distant -cock -buys -busting -buff -wax -sleeve -pudding -products -philosophy -japan -irony -hospitals -dope -declare -autopsy -workin -torch -substitute -scandal -prick -limb -leaf -laser -hysterical -growth -goddamnit -fetch -dimension -crowded -cousins -clip -climbing -bonding -bee -approved -yeh -woah -veronica -ultimately -trusts -terror -roller -returns -negotiate -millennium -marsh -majority -lethal -length -iced -fantasies -element -deeds -cigars -bore -babysitter -sponge -sleepy -questioned -peek -outrageous -nigger -medal -insulted -grudge -established -driveway -deserted -definite -capture -beep -wires -weed -suggestions -searched -owed -originally -nickname -lighting -lend -films -drunken -demanding -conviction -characters -bumped -weigh -weasel -valentine -touches -tempted -supreme -shout -rocket -resolve -relate -poisoned -pip -occasionally -meals -maker -invitations -intruder -haunted -fur -footage -depending -bonds -bogus -autograph -apples -affects -tolerate -stepping -spontaneous -southern -sleeps -probation -presentation -performed -identical -herb -fist -cycle -cooler -banner -associates -yankee -streak -spectacular -sector -muscles -lasted -increase -hostages -heroin -havin -hardware -habits -fisher -encouraging -cult -consult -burgers -boyfriends -bailed -baggage -association -wealthy -watches -versus -troubled -torturing -teasing -sweetest -stations -sip -rag -qualities -postpone -pad -overwhelmed -maniac -impulse -hut -follows -duchess -classy -charging -celebrity -amazed -slater -scenes -rising -revealed -representing -policeman -offensive -mug -hypocrite -humiliate -hideous -hairy -finals -experiences -courts -costumes -captured -bolt -bluffing -betting -bein -bedtime -alpha -alcoholic -waters -visual -vegetable -tray -suspicions -sticky -spreading -splendid -smiles -shrimp -shouting -roots -ransom -pressed -nooo -jew -intent -grieving -gladly -fling -eliminate -disorder -cocaine -chancellor -cereal -arrives -aaah -yum -technique -subway -strain -statements -sonofabitch -servant -roads -resident -republican -paralyzed -orb -lotta -locks -guaranteed -dummy -discipline -despise -dental -corporation -cherish -carries -briefing -bluff -batteries -atmosphere -assholes -whatta -tux -sounding -servants -rifle -presume -mamie -handwriting -goals -gin -gale -fainted -elements -dried -cape -allright -allowing -acknowledge -whiskey -whacked -toxic -skating -shepherd -reliable -quicker -penalty -panel -overwhelming -nearby -lining -importance -ike -harassing -global -fatal -endless -elsewhere -dolls -convict -butler -bold -ballet -ñ -whatcha -unlikely -spiritual -shutting -separation -rusty -recording -positively -overcome -mount -method -manual -helmet -goddam -failing -essence -dose -diagnosis -cured -claiming -bully -airline -ahold -yearbook -various -triangle -tempting -shelf -rig -pursuit -prosecution -pouring -possessed -partnership -november -humble -greedy -countries -wonders -tsk -thorough -spine -shotgun -reckless -railroad -psychiatric -meaningless -latte -jammed -ignored -fiance -exposure -exhibit -evidently -duties -contempt -compromised -capacity -cans -weekends -urge -thunder -theft -suing -shipment -scissors -responding -refuses -proposition -porter -noises -matching -marine -located -leon -legacy -ink -hormones -hail -grandchildren -godfather -gently -establish -eastern -darryl -contracts -compound -worldwide -smashed -sexually -sentimental -senor -scored -nicest -marketing -manipulated -jaw -intern -handcuffs -framed -errands -entertaining -discovery -crib -carriage -barge -awards -attending -ambassador -videos -tab -spends -slipping -seated -rubbing -rely -reject -recommendation -reckon -ratings -headaches -float -embrace -corners -whining -turner -sweating -sole -skipped -rolf -restore -receiving -population -pep -olive -mountie -motives -listens -jeep -heroes -controls -cleaner -cheerleader -wooden -unnecessary -stunning -slim -shipping -scent -quest -praise -pose -luxury -loosen -info -hum -hottest -haunt -gracious -git -forgiving -fleet -errand -emperor -cakes -blames -abortion -worship -theories -strict -sketch -shifts -plotting -physician -perimeter -passage -pals -mere -meg -mattered -longest -jews -interference -grease -eyewitness -enthusiasm -encounter -diapers -artists -strongest -shaken -serves -punched -projects -portal -outer -nazi -jewels -concrete -colleagues -catches -carrot -bearing -backyard -academic -winds -whisper -volume -terrorists -sabotage -pope -pea -organs -needy -mock -mentor -measures -listed -lex -cuff -civilization -breeze -articles -yummy -writes -woof -valid -skipper -sands -rarely -rabbi -prank -performing -obnoxious -mates -improve -hereby -gabby -faked -cheeks -cellar -whitelighter -void -trucks -tomato -substance -strangle -sour -skill -senate -purchase -native -muffins -maximum -interfering -hoh -fiction -exotic -demonic -colored -clearing -civilian -buildings -brooks -boutique -winters -trading -terrace -speaker -smoked -skiing -seed -righty -relations -quack -published -preliminary -pact -outstanding -opinions -knot -ketchup -items -examined -disappearing -coin -circuit -assist -administration -violet -uptight -ticking -terrifying -tease -swamp -secretly -rejection -reflection -realizing -rays -partly -mentally -jurisdiction -doubted -deception -crucial -congressman -cheesy -chambers -bitches -arrival -visited -toto -supporting -stalling -shook -scouts -scoop -ribbon -reserve -raid -notion -income -immune -hay -expects -edition -destined -constitution -classroom -boobs -bets -bathing -appreciation -appointed -accomplice -wander -shoved -sewer -seeking -scroll -retire -peach -paintings -nude -lasts -fugitive -freezer -discount -cranky -crank -clowns -clearance -buffalo -bodyguard -anxiety -accountant -whoops -volunteered -terrorist -tales -talents -stinking -snakes -sessions -salmon -resolved -remotely -protocol -nickel -nana -garlic -foreman -decency -cord -beds -beam -areas -altogether -uniforms -tremendous -summit -squash -restaurants -rank -profession -popping -peanuts -outa -observe -myrtle -lung -largest -hangs -feelin -experts -enforcement -encouraged -economy -dudes -donation -disguise -curb -continued -competitive -businessman -bites -balloons -antique -advertising -ads -toothbrush -retreat -represents -realistic -profits -predict -panties -lust -lid -landlord -hourglass -hesitate -focusing -equally -consolation -champ -babbling -aged -tipped -stranded -smartest -rhythm -replacement -repeating -puke -psst -paycheck -overreacted -mechanic -macho -ling -leadership -juvenile -images -grocery -freshen -disposal -cuffs -consent -cartoon -caffeine -broom -biology -arguments -agrees -vanished -unfinished -tobacco -tin -tasty -syndrome -stack -sells -ripping -pinch -missiles -isolated -flattering -expenses -dinners -cos -colleague -ciao -buh -attorneys -woulda -whereabouts -wars -waitin -visits -truce -tripped -tee -tasted -steer -ruling -poisoning -pirate -nursing -manipulative -immature -husbands -heel -granddad -delivering -deaths -condoms -butts -automatically -anchor -addict -trashed -tournament -throne -slick -sausage -raining -prices -pasta -needles -leaning -leaders -judges -ideal -detector -coolest -casting -bean -battles -batch -approximately -appointments -almighty -achieve -vegetables -trapper -swinging -sum -spark -ruled -revolution -principles -perfection -pains -momma -mole -meow -jelly -interviews -initiative -hairs -getaway -employment -den -cracking -counted -compliments -behold -verge -tougher -timer -tapped -taped -surf -superman -stakes -specialty -snooping -shoots -semi -rendezvous -pentagon -passenger -leverage -jeopardize -janitor -grandparents -forbidden -fink -examination -communist -clueless -cities -cattle -bidding -arriving -adding -ungrateful -unacceptable -tutor -soviet -shorter -shaped -serum -scuse -savings -pub -pajamas -mouths -mojo -modest -methods -lure -jackass -irrational -galaxy -doom -depth -cries -classified -bombs -beautifully -arresting -approaching -vessel -variety -traitor -sympathetic -smug -smash -rental -prostitute -premonitions -physics -monk -mild -jumps -inventory -ing -improved -horny -doe -developing -darlin -committing -banging -asap -amendment -worms -violated -vent -traumatic -traced -tow -sweaty -shaft -recommended -rainbow -overboard -literature -insight -healed -haven -grasp -fluid -experiencing -era -crappy -crab -chunk -awww -applied -witnessed -traveled -stain -shack -reacted -pronounce -presented -poured -pervert -occupied -moms -marriages -kings -jabez -invested -handful -gob -gag -flipped -flick -fireplace -expertise -embarrassment -drum -disappears -concussion -bruises -brakes -twisting -tide -swept -summon -splitting -sneaky -sloppy -settling -scientists -reschedule -regard -purposes -notch -mustard -moose -les -improvement -hooray -grabbing -extend -exquisite -disrespect -complaints -armor -amateur -wheat -voting -sustained -stripper -straw -slapped -shipped -shattered -ruthless -refill -recorded -payroll -numb -mourning -marijuana -manly -iris -involving -hunk -graham -fountain -fellows -entertain -earthquake -drift -dreadful -doorstep -confirmation -chops -appreciates -announced -vague -tires -stressful -stem -stashed -stash -sensed -preoccupied -predictable -noticing -madly -halls -gunshot -embassy -dozens -dork -confuse -cleaners -charade -chalk -cappuccino -breed -bouquet -amulet -addiction -warming -villa -unlock -transition -satisfy -sacrificed -relaxing -lone -input -fudge -elaborate -concerning -completed -channels -category -cal -blocking -blend -blankets -addicted -yuck -voters -professionals -positions -mode -jolly -initial -hunger -hamburger -greeting -greet -gravy -gram -finance -dreamt -dice -declared -collecting -caution -bicycle -backpack -agreeing -writers -whale -tribe -taller -supervisor -starling -sacrifices -radiation -queens -poo -phew -outcome -ounce -monty -missile -meter -likewise -irrelevant -gran -felon -feature -favorites -farther -fade -experiments -erased -easiest -disk -disco -convenience -conceived -compassionate -challenged -cane -backstage -agony -adores -veins -tweek -thieves -surgical -sunrise -strangely -recital -proposing -productive -meaningful -marching -kitten -immunity -hassle -goddamned -frighten -directors -dearly -comments -closure -cease -bomber -ambition -wage -unstable -sweetness -stinky -salvage -richer -refusing -raging -pumping -pressuring -pookie -petition -nations -mortals -lowlife -jus -juicy -intimidated -intentionally -inspire -forgave -fart -devotion -despicable -deciding -dash -comfy -breach -bark -alternate -aaaah -twilight -switching -swallowed -stove -slot -screamed -scars -relevant -pounding -poof -pipes -persons -pawn -losses -legit -invest -generations -farewell -experimental -difficulty -curtains -civilized -championship -caviar -carnival -canyon -boost -blues -bliss -token -tends -temporarily -superstition -supernatural -sunk -stream -stocks -spinner -sadness -reduced -recorder -rang -psyched -presidential -owners -objects -motivated -microwave -lands -hallelujah -gap -fraternity -engines -dutch -dryer -cocoa -chewing -brake -bounty -additional -acceptable -unbelievably -survivor -smiled -smelling -sized -simpler -sentenced -respectable -remarks -registration -premises -passengers -organ -occasional -indication -gutter -grabs -goo -fulfill -flashlight -courses -chains -boxing -blooded -blink -blessings -beware -bands -advised -von -uhhh -turf -swings -software -slips -shovel -shocking -resistance -puff -privately -mirrors -lyrics -locking -karma -instrument -historical -heartless -fras -echo -decades -comparison -childish -cardiac -brace -blunt -admission -vanilla -utterly -ticked -tequila -suspension -stunned -sadly -resolution -reserved -purely -opponent -noted -mankind -lowest -kiddin -jerks -hitch -flirt -fare -extension -establishment -equals -dismiss -delayed -decade -christening -casket -broker -breakup -biting -antibiotics -accusation -abducted -witchcraft -traded -titan -thread -spelling -smelly -sharks -runnin -remaining -punching -protein -printed -paramedics -newest -murdering -masks -marathon -laptop -intact -ins -initials -heights -grampa -diaper -democracy -deceased -choking -charms -careless -bushes -buns -bummed -accounting -travels -shred -saves -saddle -rethink -regards -references -razor -precinct -pistol -persuade -patterns -meds -manipulating -llanfair -leash -housing -hearted -guarantees -fucks -folk -flown -feast -extent -educated -disgrace -determination -deposition -coverage -corridor -burial -bronze -bookstore -boil -abilities -werewolf -vitals -veil -trespassing -teaches -sidewalk -sensible -punishing -overtime -optimistic -occasions -obsessing -oak -notify -mornin -jeopardy -injection -hilarious -distinct -directed -desires -dee -dame -curve -confide -cone -challenging -cautious -alter -yada -wilderness -vindictive -vial -venture -tomb -teeny -subjects -stroll -sittin -scrub -rebuild -posters -parallel -ordeal -orbit -nuns -northern -intimacy -inheritance -feather -farmer -fails -exploded -donate -distracting -digger -despair -democratic -defended -crackers -commercials -ammunition -wildwind -virtue -thoroughly -tails -spicy -sketches -sights -sheer -shaving -seize -scarecrow -refreshing -prosecute -possess -platter -napkin -misplaced -merchandise -membership -loony -jinx -herr -heroic -fag -facial -efficient -corps -clan -bummer -boundaries -attract -arrow -ambitious -abbey -waits -virtually -syrup -solitary -shuttle -resignation -resemblance -reacting -pursuing -premature -pod -mortgage -journalist -honors -gravity -genes -flashes -erm -contribution -cheque -charts -cargo -awright -acquainted -wrapping -vest -untie -salute -ruins -resign -realised -priceless -pike -partying -myth -moonlight -lightly -lifting -keen -insisting -glowing -generator -flowing -explosives -employer -cutie -confronted -clause -cinnamon -buts -breakthrough -blouse -ballistic -assassin -antidote -analyze -allowance -adjourned -vet -unto -understatement -tucked -touchy -toll -subconscious -sparky -sequence -screws -sarge -roommates -reaches -programs -pitcher -ping -offend -nerd -knives -kin -jasmine -irresistible -inherited -incapable -hostility -goddammit -fuse -funky -frat -equation -digital -curfew -craft -chow -centered -blackmailed -allows -alleged -wealth -watcher -walkin -turtle -transmission -text -starve -sleigh -sarcastic -recess -rebound -rebel -procedures -pirates -pinned -parlor -outfits -livin -issued -institute -industrial -hoops -heartache -haired -fundraiser -dynamite -doorman -documentary -discreet -d -detect -cracks -cracker -considerate -climbed -chilly -catering -author -apophis -vacuum -urine -tunnels -tanks -strung -stitches -sordid -sark -referred -protector -portion -phoned -pets -paths -moss -mat -lengths -kindergarten -hostess -flaw -flavor -diving -discharge -consumed -confidentiality -cannon -bourbon -blizzard -automatic -amongst -yankees -woody -urban -tactics -straightened -spooky -specials -spaghetti -soil -prettier -powerless -por -poems -playin -playground -paranoia -mutant -mainly -lions -knox -jacqueline -instantly -hopeful -havoc -francis -exaggerating -evaluation -engage -eavesdropping -doughnuts -diversion -delight -deepest -dang -cutest -condom -companion -comb -bela -behaving -avoided -aspen -anyplace -agh -accessory -zap -workout -whereas -translate -titanic -stuffing -stoned -speeding -slime -royalty -polls -plaza -personalities -payments -musician -maze -marital -magician -lurking -lottery -leonardo -journalism -interior -imaginary -hog -hatch -guinea -greetings -fairwinds -ethical -equipped -environmental -elegant -elbow -customs -cuban -credibility -credentials -consistent -collapse -cloth -claws -cinderella -chopped -challenges -bridal -boards -bedside -babysitting -authorized -assumption -ant -alvarez -youngest -witty -vast -unforgivable -underworld -tempt -tabs -succeeded -splash -sophomore -shade -selfless -secrecy -santiago -runway -restless -programming -professionally -okey -nolan -movin -metaphor -messes -meltdown -lecter -jeanne -incoming -hence -glenn -gasoline -gained -funding -episodes -diefenbaker -curl -contain -comedian -collected -coconut -cam -buckle -assembly -ancestors -admired -adjustment -acceptance -weekly -warmth -venice -umbrella -tropical -thumbs -throats -slippery -shitty -seduced -reform -ranger -queer -poll -parenting -onion -noses -mobile -luckiest -hartford -graveyard -gifted -francine -footsteps -dimeras -dale -cynical -corleone -cement -bulls -bloom -assassination -wedded -watson -voyage -volunteers -verbal -unpredictable -tuned -triumph -trevor -stoop -stamps -slides -sinking -rio -rigged -regulations -region -promoted -plumbing -pimp -nell -masters -lingerie -layer -jules -hankey -greed -fluffy -flood -everwood -essential -elope -dresser -departure -dat -dances -custom -creation -coup -chauffeur -bulletin -bugged -brian -bouncing -bimbo -website -veal -tubes -temptation -supported -strangest -slammed -selection -sarcasm -sanity -sandra -rib -primitive -platform -pending -partial -packages -orderly -obsessive -newbie -nevertheless -murderers -motto -meteor -inconvenience -hottie -glimpse -froze -fiber -faggot -execute -etc -ensure -drivers -dispute -damages -crop -courageous -consulate -closes -bosses -bees -amends -wuss -wacky -unemployed -traces -testifying -tendency -syringe -symphony -stew -startled -sorrow -sleazy -shaky -screams -runner -rsquo -riddle -remark -rangers -poop -poke -pickup -nutty -mentioning -mend -menace -inspiring -impulsive -housekeeper -harvest -formed -foam -fingernails -economic -divide -conditioning -chronic -bass -baking -whine -utter -thug -submit -strap -starved -sniffing -sedative -reversed -rated -publishing -programmed -picket -paged -online -nowadays -mines -jumbo -joni -invasion -hound -homosexual -homo -hips -gilbert -forgets -flipping -flea -flatter -enters -dwell -dumpster -ducks -devlin -dent -consultant -clayton -choo -bikini -beale -banking -assignments -apartments -ants +absentee +absently +absinthe +absolute +absolve +abstain +abstract +absurd +accent +acclaim +acclimate +accompany +account +accuracy +accurate +accustom +acetone +achiness +aching +acid +acorn +acquaint +acquire +acre +acrobat +acronym +acting +action +activate +activator +active +activism +activist +activity +actress +acts +acutely +acuteness +aeration +aerobics +aerosol +aerospace +afar +affair +affected affecting -advisor -vile -unreasonable -tossing -thanked -stereo -steals -souvenir -screening -scratched -rep -psychopath -proportion -peyton -outs -operative -obstruction -obey -neutral -maxwell -lump -lockdown -insists -harass -gloat -flights -filth -extended -electronic -edgy -donkey -diseases -didn -curtis -coroner -confessing -cologne -cedar -bruise -betraying -bailing -attempting -appealing -adebisi -wrath -wandered -waist -vain -traps -transportation -trainer -sushi -stepfather -rye -publicly -presidents -poking -obligated -monroe -medina -marshal -lemonade -instructed -hooks -heavenly -hash -halt -grim -engineer -employed -doggie -diplomatic -dilemma -crazed -contagious -coaster -cheering -carved -carpenter -butch -bundle -bubbles -blanks -approached -appearances -wrench -vomit -thingy -stadium -speeches -smashing -savior -rogue -robbing -reflect -raft -qualify -pumped -pillows -piggy -peep -pageant -packs -neo -neglected -montana -marcie -madonna -loneliness -liberal -jaye -intrude -indicates -helluva -hawkeye -gregory -gardener -freely -forresters -fatass -err -eleanor -drooling -continuing -cassandra -betcha -apollo -addressed -acquired -vase -tiffany -supermarket -squat -spitting -spice -spaces -slaves -showers -sanchez -rhyme -relieve -receipts -radical -racket -purchased -preserve -portland -pictured -pause -overdue -officials -nod -motivation -morgendorffer -lacking -kidnapper -introduction -insect -hunters -horns -feminine -eyeballs -dumps -disc -disappointing -difficulties -crock -convertible -context -claw -clamp -canned -cambias -bishop -bathtub -avanya -artery -andre -weep -warmer -vendetta -tenth -suspense -summoned -spiders -sings -reiber -reader -raving -pushy -produced -poverty -postponed -poppy -ohhhh -noooo -mold -mice -laughter -johnnie -incompetent -hugging -horizon -grove -groceries -frequency -fastest -drip -dinosaur -differ -delta -copper -communicating -clare -chi -carrier -brody -beliefs -bats -bases -auntie -adios -wraps -wiser -willingly -weirdest -waltz -voila -timmih -thinner -swelling -swat -steroids -slate -sentinel -sensitivity -scrape -rookie -rehearse -quarterback -prophecy -organic -mercedes -matched -ledge -justified -insults -increased -immortal -heavily -hateful -handles -francie -feared -einstein -doorway -decorations -colour -chatting -buyer -buckaroo -bedrooms -batting -askin -ammo -admiral -wrestle -wolves -velvet -tutoring -subpoena -stein -span -scratching -requests -privileges -pager -mart -manor -madman -knicks -kel -intriguing -idiotic -hotels -grape -granger -goofy -flexible -enlighten -dum -donuts -demonstrate -dairy -corrupt -combined -brunch -bridesmaid -barking -architect -applause +affection +affidavit +affiliate +affirm +affix +afflicted +affluent +afford +affront +aflame +afloat +aflutter +afoot +afraid +afterglow +afterlife +aftermath +aftermost +afternoon +aged +ageless +agency +agenda +agent +aggregate +aghast +agile +agility +aging +agnostic +agonize +agonizing +agony +agreeable +agreeably +agreed +agreeing +agreement +aground +ahead +ahoy +aide +aids +aim +ajar +alabaster +alarm +albatross +album +alfalfa +algebra +algorithm +alias +alibi +alienable +alienate +aliens +alike +alive +alkaline +alkalize +almanac +almighty +almost +aloe +aloft +aloha +alone alongside -ale -acquaintance -yuh -wretched -tango -superficial -sufficient -sued -soak -smoothly -sensing -restraint -quo -posing -pleading -payoff -participate -panda -organize -morals -loans -loaf -lists -laboratory -jumpy -intervention -ignorant -herbal -hangin -germs -generosity -freed -flashing -doughnut -convent -clumsy -chocolates -captive -behaved -babes -apologise -angelus -vanity -trials -stumbled -skate -shampoo -republicans -represented -recognition -preview -poisonous -perjury -parental -onboard -mugged -minding -maestro -linen -learns -knots -jimbo -interviewing -inmates -ingredients -humour -gypsy -grind -greasy -goons -frost -estimate -elementary -drastic -dolly -database -crow -coop -comparing -cocky -clearer -cartoons -bruised -brag -bind -axe -asset -apparent -worthwhile -whoop -warner -volcano -vanquishing -towns -tabloids -survivors -sprung -spotlight -smokes -shops -sentencing -sentences -rivers -revealing -reduce -ram -racist -provoke -preacher -pining -peak -password -overly -oui -ops -mop -mayo -locket -leland -jab -imply -impatient -hovering -hotter -holland -gemini -gaines -fest -endure -dots -doren -dim -diagnosed -debts -cultures -crawled -contained -condemned -cody -chained -brit -breaths -booty -arctic -ambrosia -adds -weirdo -warmed -wand -vienna -utah -troubling -stripped -strapped -spies -soaked -skipping -scrambled -rattle -profound -perez -peoples -musta -moses -mona -mocking -mnh -misunderstand -merit -mayday -loading -linked -limousine -kacl -jody -investors -interviewed -hustle -forensic -foods -espresso -enthusiastic -duct -drawers -devastating -democrats -cosmo -conquer -concentration -comeback -clarify -chores -cheerleaders -cheaper -charter -chantal -callin -butcher -bricks -bozo -blushing -bert -barging -asia -abused -yoga -wrecking -wits -wentworth -waffles -virginity -vibes -uninvited -unfaithful -underwater -tribute -teller -strangled -sissy -scheming -ropes -responded -residents -rescuing -reel -redhead -rave -priests -postcard -peterman -overseas -orientation -onions -ongoing -newly -morphine -lotion -limitations -lilly -lesser -lent -lectures -lads -kidneys -judgement -jog -jingle -jets -itch -intellectual -installed -infant -indefinitely -hazard -grenade -glamorous -genetically -fireman -faculty -engineering -doh -discretion -delusions -declaration -crate -competent -commonwealth -catalog -breaker -blondie -bakery -attempts -asylum -argh -applying -ahhhh -wedge -warriors -wager -unfit -tuxedo -tripping -treatments -torment -superhero -stirring -spinal -sorority -sneakers -server -seminar -scenery -republic -repairs -rabble -pneumonia -perks -peaches -owl -override -ooooh -moo -mija -manslaughter -mailed -lime -lettuce -kinky -intimidate -instructor -guarded -grieve -grad -gorilla -globe -frustration -extensive -exploring -exercises -downs -doorbell -devices -deb -dam -cultural -credits -commerce -chemicals -café -authentic -arraignment -annulled -altered -allergies -wanta -verify -vegetarian -tunes -tourist -tighter -telegram -suitable -stalk -springs -specimen -spared -solving -shoo -satisfying -requesting -publisher -pharmacy - -pens -overprotective -obstacles -notified -negro -nasedo -judged -identification -grandchild -genuinely -founded -flushed -fluids -floss -escaping -dove -ditched -decorated -crunch -criticism -cramp -corny -contribute -connecting -bunk -bombing -bitten -billions -bankrupt -yikes -wrists -winners -ultrasound -ultimatum -thirst -suckers -spelled -sniff -shakes -scope -salsa -retrieve -releasing -reassuring -pumps -properties -predicted -pigeon -neurotic -negotiating -multi -monitors -millionaire -microphone -mechanical -limp -incriminating -hiking -hatchet -gracias -fills -feeds -doubting -dedication -decaf -competing -cellular -carbon -butterfly -bumper -biopsy -whiz -voluntarily -visible -ventilator -unpack -unload -universal -tomatoes -toad -targets -taco -suggests -strawberry -spooked -snitch -showtime -sap -reassure -providing -prey -persuasive -pancake -mystical -mysteries -mixing -mayhem -matrimony -marines -mails -magnet -lighthouse -liability -jock -headline -groovy -gangster -factors -explosive -explanations -dispatch -detailed -curly -cupid -condolences -comrade -bulb -bragging -awaits -assaulted +aloof +alphabet +alright +although +altitude +alto +aluminum +alumni +always +amaretto +amaze +amazingly +amber +ambiance +ambiguity +ambiguous +ambition +ambitious +ambulance ambush -aircraft -adolescent -adjusted -abort -yank -whit -verse -vaguely -undermine -tying -trim -swamped -sunlight -stitch -stabbing -sphere -slippers -slash -sincerely -sigh -setback -secondly -rotting -rev -retail -prospect -proceedings -preparation -precaution -pox -pearls -pcpd -parks -nonetheless -melting -materials -marler -mar -liaison -lair -hots -hooking -headlines -haha -hag -grapes -genie -fury -felicity -fangs -expelled -encouragement -earring -dreidel -draws -dory -donut -dis -dictate -dependent -decorating -cunt -cope -coordinates -cola -cocktails -cocksucker -bumps -blueberry -blackout -believable -backfired -backfire -apron -anticipated +amendable +amendment +amends +amenity +amiable +amicably +amid amigo -adjusting -activated -vous -vouch -voodoo -vitamins -vista -vintage -urn -uncertain -ummm -tourists -tattoos -surrounding -stern -sponsor -slimy -singles -sibling -shhhh -restored -representative -renting -reign -publish -planets -pickle -peculiar -parasite -noo -marries -mailbox -magically -lovebirds -listeners -knocks -intel -informant -hicks -grain -fearless -exits -elf -drazen -distractions -disconnected -dinosaurs -designing -dashwood -crooked -crook -conveniently -contents -colon -barber -argued -ziggy -wink -warped -underestimated -testified -tacky -substantial -steering -staged -stability -shoving -shaved -seizure -reset -repeatedly -radius -pushes -pitching -pairs -painter -opener -notebook -mornings -moody -mash -investigations -invent -indulge -horribly -hallucinating -festive -feathers -eyebrows -expand -enjoys -dictionary -dialogue -desperation -dealers -darkest -daph -critic -cowboys -consulting -canal -boragora -belts -bananas -bagel -authorization -auditions -associated -ape -agitated -adventures -withdraw -wishful -wimp -violin -vehicles -vanish -unbearable -tonic -tackle -suffice -suction -sporting -slaying -safest -rocking -relive -rates -puttin -puppies -prettiest -polo -oval -oatmeal -noisy -newlyweds -nauseous -moi -misguided -mildly -midst -maps -liable -judgmental -introducing -indy -individuals -hunted -hen -givin -frequent -fisherman -fascinated -elephants -dislike -diploma -deluded -decorate -crummy -contractions -carve -careers -bottled -bonded -birdie -bash -whites -unavailable -twenties -trustworthy -translation -traditions -surviving -surgeons -stupidity -snoop -skies -secured -salvation -remorse -preferably -pies -photography -outsider -operational -nuh -northwest -nausea -napkins -mule -mourn -melted -mechanism -mashed -maiden -mafia -inherit -holdings -hel -greatness -golly -girlie -excused -edges -dumbo -drifting -delirious -damaging -cubicle -crawley -compelled -comm -colleges -chooses -checkup -certified -candidates -buffet -boredom -bandages -bah -automobile -athletic -alarms -absorbed -absent -yessir -windshield -whaddya -vitamin -viper -transparent -surprisingly -sunglasses -starring -spears -slit -sided -serenity -schemes -roar -relatively -quarry -prosecutor -prognosis -probe -potentially -poodle -pitiful -persistent -perception -percentage -peas -oww -nosy -neighbourhood -nagging -morons -molecular -meters -masterpiece -martinis -limbo -liars -karate -irritating -inclined -hump -hoynes -holler -hazel -haw -gauge -functions -fiasco -fallout -educational -eatin -dumbass -donated -destination -dense -crimson -continent -concentrating -commanding -colorful -clam -cider -brochure -behaviour -barto -bargaining -awe -artistic +amino +amiss +ammonia +ammonium +amnesty +amniotic +among +amount +amperage +ample +amplifier +amplify +amply +amuck +amulet +amusable +amused +amusement +amuser +amusing +anaconda +anaerobic +anagram +anatomist +anatomy +anchor +anchovy +ancient +android +anemia +anemic +aneurism +anew +angelfish +angelic +anger +angled +angler +angles +angling +angrily +angriness +anguished +angular +animal +animate +animating +animation +animator +anime +animosity +ankle +annex +annotate +announcer +annoying +annually +annuity +anointer +another +answering +antacid +antarctic +anteater +antelope +antennae +anthem +anthill +anthology +antibody +antics +antidote +antihero +antiquely +antiques +antiquity +antirust +antitoxic +antitrust +antiviral +antivirus +antler +antonym +antsy +anvil +anybody +anyhow +anymore +anyone +anyplace +anything +anytime +anyway +anywhere +aorta +apache +apostle +appealing +appear +appease +appeasing +appendage +appendix +appetite +appetizer +applaud +applause +apple +appliance +applicant +applied +apply +appointee +appraisal +appraiser +apprehend +approach +approval +approve +apricot +april +apron +aptitude +aptly +aqua +aqueduct +arbitrary +arbitrate +ardently +area arena -wiggle -welcoming -weighing -villain -vein -vanquished -striking -stains -sooo -snacks -smear -sire -secondary -roughly -rituals -resentment -psychologist -preferred -pint -pension -penguin -passive -panther -overhear -origin -orchestra -negotiations -mounted -morality -leopard -labs -kisser -jackpot -icy -hoot -hippie -handshake -grilled -functioning -formality -elevators -drums -depths -confirms -civilians -bypass -briefly -breeding -boxer -boathouse -binding +arguable +arguably +argue +arise +armadillo +armband +armchair +armed +armful +armhole +arming +armless +armoire +armored +armory +armrest +army +aroma +arose +around +arousal +arrange +array +arrest +arrival +arrive +arrogance +arrogant +arson +art +ascend +ascension +ascent +ascertain +ashamed +ashen +ashes +ashy +aside +askew +asleep +asparagus +aspect +aspirate +aspire +aspirin +astonish +astound +astride +astrology +astronaut +astronomy +astute +atlantic +atlas +atom +atonable +atop +atrium +atrocious +atrophy +attach +attain +attempt +attendant +attendee +attention +attentive +attest +attic +attire +attitude +attractor +attribute +atypical +auction +audacious +audacity +audible +audibly +audience audio -acres -accidental -wacko -ulterior -transferring -tis -thugs -thighs -tangled -stirred -sought -softball -snag -smallest -sling -sleaze -shells -seeds -rumour -ripe -remarried -reluctant -regularly -puddle -promote -precise -popularity -pins -perceptive -oral -miraculous -memorable -maternal -lookout -longing -lockup -locals -lizard -librarian -knights -junkie -inspection -impressions -immoral -hypothetically -guarding -gourmet -fighters -fees -features -faxed -extortion -expressed -essentially -downright -digest -der -crosses -cranberry -covert -costa -chorus -casualties -bygones -buzzing -burying -bugger -bikes -attended -wells -weary -visa -viewing -viewers -uptown -transmitter -trains -tickle -tart -taping -takeout -sweeping -stepmother -stating -stale -señor -settles -seating -seaborn -resigned -rating -pros -porno -plumber -pissing -pilots -pepperoni -ownership -occurs -newborn -nada -merger -mandatory -ludicrous -injected -heating -geeks -forged -faults -expressing -drue -dire -dief -deceiving -centre -celebrities +audition +augmented +august +authentic +author +autism +autistic +autograph +automaker +automated +automatic +autopilot +available +avalanche +avatar +avenge +avenging +avenue +average +aversion +avert +aviation +aviator +avid +avoid +await +awaken +award +aware +awhile +awkward +awning +awoke +awry +axis +babble +babbling +babied +baboon +backache +backboard +backboned +backdrop +backed +backer +backfield +backfire +backhand +backing +backlands +backlash +backless +backlight +backlit +backlog +backpack +backpedal +backrest +backroom +backshift +backside +backslid +backspace +backspin +backstab +backstage +backtalk +backtrack +backup +backward +backwash +backwater +backyard +bacon +bacteria +bacterium +badass +badge +badland +badly +badness +baffle +baffling +bagel +bagful +baggage +bagged +baggie +bagginess +bagging +baggy +bagpipe +baguette +baked +bakery +bakeshop +baking +balance +balancing +balcony +balmy +balsamic +bamboo +banana +banish +banister +banjo +bankable +bankbook +banked +banker +banking +banknote +bankroll +banner +bannister +banshee +banter +barbecue +barbed +barbell +barber +barcode +barge +bargraph +barista +baritone +barley +barmaid +barman +barn +barometer +barrack +barracuda +barrel +barrette +barricade +barrier +barstool +bartender +barterer +bash +basically +basics +basil +basin +basis +basket +batboy +batch +bath +baton +bats +battalion +battered +battering +battery +batting +battle +bauble +bazooka +blabber +bladder +blade +blah +blame +blaming +blanching +blandness +blank +blaspheme +blasphemy +blast +blatancy +blatantly +blazer +blazing +bleach +bleak +bleep +blemish +blend +bless +blighted +blimp +bling +blinked +blinker +blinking +blinks +blip +blissful +blitz +blizzard +bloated +bloating +blob +blog +bloomers +blooming +blooper +blot +blouse +blubber +bluff +bluish +blunderer +blunt +blurb +blurred +blurry +blurt +blush +blustery +boaster +boastful +boasting +boat +bobbed +bobbing +bobble +bobcat +bobsled +bobtail +bodacious +body +bogged +boggle +bogus +boil +bok +bolster +bolt +bonanza +bonded +bonding +bondless +boned +bonehead +boneless +bonelike +boney +bonfire +bonnet +bonsai +bonus +bony +boogeyman +boogieman +book +boondocks +booted +booth +bootie +booting +bootlace +bootleg +boots +boozy +borax +boring +borough +borrower +borrowing +boss +botanical +botanist +botany +botch +both +bottle +bottling +bottom +bounce +bouncing +bouncy +bounding +boundless +bountiful +bovine +boxcar +boxer +boxing +boxlike +boxy +breach +breath +breeches +breeching +breeder +breeding +breeze +breezy +brethren +brewery +brewing +briar +bribe +brick +bride +bridged +brigade +bright +brilliant +brim +bring +brink +brisket +briskly +briskness +bristle +brittle +broadband +broadcast +broaden +broadly +broadness +broadside +broadways +broiler +broiling +broken +broker +bronchial +bronco +bronze +bronzing +brook +broom +brought +browbeat +brownnose +browse +browsing +bruising +brunch +brunette +brunt +brush +brussels +brute +brutishly +bubble +bubbling +bubbly +buccaneer +bucked +bucket +buckle +buckshot +buckskin +bucktooth +buckwheat +buddhism +buddhist +budding +buddy +budget +buffalo +buffed +buffer +buffing +buffoon +buggy +bulb +bulge +bulginess +bulgur +bulk +bulldog +bulldozer +bullfight +bullfrog +bullhorn +bullion +bullish +bullpen +bullring +bullseye +bullwhip +bully +bunch +bundle +bungee +bunion +bunkbed +bunkhouse +bunkmate +bunny +bunt +busboy +bush +busily +busload +bust +busybody +buzz +cabana +cabbage +cabbie +cabdriver +cable +caboose +cache +cackle +cacti +cactus +caddie +caddy +cadet +cadillac +cadmium +cage +cahoots +cake +calamari +calamity +calcium +calculate +calculus +caliber +calibrate +calm +caloric +calorie +calzone +camcorder +cameo +camera +camisole +camper +campfire +camping +campsite +campus +canal +canary +cancel +candied +candle +candy +cane +canine +canister +cannabis +canned +canning +cannon +cannot +canola +canon +canopener +canopy +canteen +canyon +capable +capably +capacity +cape +capillary +capital +capitol +capped +capricorn +capsize +capsule +caption +captivate +captive +captivity +capture +caramel +carat +caravan +carbon +cardboard +carded +cardiac +cardigan +cardinal +cardstock +carefully +caregiver +careless +caress +caretaker +cargo +caring +carless +carload +carmaker +carnage +carnation +carnival +carnivore +carol +carpenter +carpentry +carpool +carport +carried +carrot +carrousel +carry +cartel +cartload +carton +cartoon +cartridge +cartwheel +carve +carving +carwash +cascade +case +cash +casing +casino +casket +cassette +casually +casualty +catacomb +catalog +catalyst +catalyze +catapult +cataract +catatonic +catcall +catchable +catcher +catching +catchy caterer -carrots -calmed -businesses -budge -bridges -applications -ankles -vending -typing -tribbiani -swift -squared -speculation -snowing -shades -sexist -scattered -sanctuary -saints -rewrite -regretted -regain -raises -processing -picky -orphan -nipples -nam +catering +catfight +catfish +cathedral +cathouse +catlike +catnap +catnip +catsup +cattail +cattishly +cattle +catty +catwalk +caucasian +caucus +causal +causation +cause +causing +cauterize +caution +cautious +cavalier +cavalry +caviar +cavity +cedar +celery +celestial +celibacy +celibate +celtic +cement +census +ceramics +ceremony +certainly +certainty +certified +certify +cesarean +cesspool +chafe +chaffing +chain +chair +chalice +challenge +chamber +chamomile +champion +chance +change +channel +chant +chaos +chaperone +chaplain +chapped +chaps +chapter +character +charbroil +charcoal +charger +charging +chariot +charity +charm +charred +charter +charting +chase +chasing +chaste +chastise +chastity +chatroom +chatter +chatting +chatty +cheating +cheddar +cheek +cheer +cheese +cheesy +chef +chemicals +chemist +chemo +cherisher +cherub +chess +chest +chevron +chevy +chewable +chewer +chewing +chewy +chief +chihuahua +childcare +childhood +childish +childless +childlike +chili +chill +chimp +chip +chirping +chirpy +chitchat +chivalry +chive +chloride +chlorine +choice +chokehold +choking +chomp +chooser +choosing +choosy +chop +chosen +chowder +chowtime +chrome +chubby +chuck +chug +chummy +chump +chunk +churn +chute +cider +cilantro +cinch +cinema +cinnamon +circle +circling +circular +circulate +circus +citable +citadel +citation +citizen +citric +citrus +city +civic +civil +clad +claim +clambake +clammy +clamor +clamp +clamshell +clang +clanking +clapped +clapper +clapping +clarify +clarinet +clarity +clash +clasp +class +clatter +clause +clavicle +claw +clay +clean +clear +cleat +cleaver +cleft +clench +clergyman +clerical +clerk +clever +clicker +client +climate +climatic +cling +clinic +clinking +clip +clique +cloak +clobber +clock +clone +cloning +closable +closure +clothes +clothing +cloud +clover +clubbed +clubbing +clubhouse +clump +clumsily +clumsy +clunky +clustered +clutch +clutter +coach +coagulant +coastal +coaster +coasting +coastland +coastline +coat +coauthor +cobalt +cobbler +cobweb +cocoa +coconut +cod +coeditor +coerce +coexist +coffee +cofounder +cognition +cognitive +cogwheel +coherence +coherent +cohesive +coil +coke +cola +cold +coleslaw +coliseum +collage +collapse +collar +collected +collector +collide +collie +collision +colonial +colonist +colonize +colony +colossal +colt +coma +come +comfort +comfy +comic +coming +comma +commence +commend +comment +commerce +commode +commodity +commodore +common +commotion +commute +commuting +compacted +compacter +compactly +compactor +companion +company +compare +compel +compile +comply +component +composed +composer +composite +compost +composure +compound +compress +comprised +computer +computing +comrade +concave +conceal +conceded +concept +concerned +concert +conch +concierge +concise +conclude +concrete +concur +condense +condiment +condition +condone +conducive +conductor +conduit +cone +confess +confetti +confidant +confident +confider +confiding +configure +confined +confining +confirm +conflict +conform +confound +confront +confused +confusing +confusion +congenial +congested +congrats +congress +conical +conjoined +conjure +conjuror +connected +connector +consensus +consent +console +consoling +consonant +constable +constant +constrain +constrict +construct +consult +consumer +consuming +contact +container +contempt +contend +contented +contently +contents +contest +context +contort +contour +contrite +control +contusion +convene +convent +copartner +cope +copied +copier +copilot +coping +copious +copper +copy +coral +cork +cornball +cornbread +corncob +cornea +corned +corner +cornfield +cornflake +cornhusk +cornmeal +cornstalk +corny +coronary +coroner +corporal +corporate +corral +correct +corridor +corrode +corroding +corrosive +corsage +corset +cortex +cosigner +cosmetics +cosmic +cosmos +cosponsor +cost +cottage +cotton +couch +cough +could +countable +countdown +counting +countless +country +county +courier +covenant +cover +coveted +coveting +coyness +cozily +coziness +cozy +crabbing +crabgrass +crablike +crabmeat +cradle +cradling +crafter +craftily +craftsman +craftwork +crafty +cramp +cranberry +crane +cranial +cranium +crank +crate +crave +craving +crawfish +crawlers +crawling +crayfish +crayon +crazed +crazily +craziness +crazy +creamed +creamer +creamlike +crease +creasing +creatable +create +creation +creative +creature +credible +credibly +credit +creed +creme +creole +crepe +crept +crescent +crested +cresting +crestless +crevice +crewless +crewman +crewmate +crib +cricket +cried +crier +crimp +crimson +cringe +cringing +crinkle +crinkly +crisped +crisping +crisply +crispness +crispy +criteria +critter +croak +crock +crook +croon +crop +cross +crouch +crouton +crowbar +crowd +crown +crucial +crudely +crudeness +cruelly +cruelness +cruelty +crumb +crummiest +crummy +crumpet +crumpled +cruncher +crunching +crunchy +crusader +crushable +crushed +crusher +crushing +crust +crux +crying +cryptic +crystal +cubbyhole +cube +cubical +cubicle +cucumber +cuddle +cuddly +cufflink +culinary +culminate +culpable +culprit +cultivate +cultural +culture +cupbearer +cupcake +cupid +cupped +cupping +curable +curator +curdle +cure +curfew +curing +curled +curler +curliness +curling +curly +curry +curse +cursive +cursor +curtain +curtly +curtsy +curvature +curve +curvy +cushy +cusp +cussed +custard +custodian +custody +customary +customer +customize +customs +cut +cycle +cyclic +cycling +cyclist +cylinder +cymbal +cytoplasm +cytoplast +dab +dad +daffodil +dagger +daily +daintily +dainty +dairy +daisy +dallying +dance +dancing +dandelion +dander +dandruff +dandy +danger +dangle +dangling +daredevil +dares +daringly +darkened +darkening +darkish +darkness +darkroom +darling +darn +dart +darwinism +dash +dastardly +data +datebook +dating +daughter +daunting +dawdler +dawn +daybed +daybreak +daycare +daydream +daylight +daylong +dayroom +daytime +dazzler +dazzling +deacon +deafening +deafness +dealer +dealing +dealmaker +dealt +dean +debatable +debate +debating +debit +debrief +debtless +debtor +debug +debunk +decade +decaf +decal +decathlon +decay +deceased +deceit +deceiver +deceiving +december +decency +decent +deception +deceptive +decibel +decidable +decimal +decimeter +decipher +deck +declared +decline +decode +decompose +decorated +decorator +decoy +decrease +decree +dedicate +dedicator +deduce +deduct +deed +deem +deepen +deeply +deepness +deface +defacing +defame +default +defeat +defection +defective +defendant +defender +defense +defensive +deferral +deferred +defiance +defiant +defile +defiling +define +definite +deflate +deflation +deflator +deflected +deflector +defog +deforest +defraud +defrost +deftly +defuse +defy +degraded +degrading +degrease +degree +dehydrate +deity +dejected +delay +delegate +delegator +delete +deletion +delicacy +delicate +delicious +delighted +delirious +delirium +deliverer +delivery +delouse +delta +deluge +delusion +deluxe +demanding +demeaning +demeanor +demise +democracy +democrat +demote +demotion +demystify +denatured +deniable +denial +denim +denote +dense +density +dental +dentist +denture +deny +deodorant +deodorize +departed +departure +depict +deplete +depletion +deplored +deploy +deport +depose +depraved +depravity +deprecate +depress +deprive +depth +deputize +deputy +derail +deranged +derby +derived +desecrate +deserve +deserving +designate +designed +designer +designing +deskbound +desktop +deskwork +desolate +despair +despise +despite +destiny +destitute +destruct +detached +detail +detection +detective +detector +detention +detergent +detest +detonate +detonator +detoxify +detract +deuce +devalue +deviancy +deviant +deviate +deviation +deviator +device +devious +devotedly +devotee +devotion +devourer +devouring +devoutly +dexterity +dexterous +diabetes +diabetic +diabolic +diagnoses +diagnosis +diagram +dial +diameter +diaper +diaphragm +diary +dice +dicing +dictate +dictation +dictator +difficult +diffused +diffuser +diffusion +diffusive +dig +dilation +diligence +diligent +dill +dilute +dime +diminish +dimly +dimmed +dimmer +dimness +dimple +diner +dingbat +dinghy +dinginess +dingo +dingy +dining +dinner +diocese +dioxide +diploma +dipped +dipper +dipping +directed +direction +directive +directly +directory +direness +dirtiness +disabled +disagree +disallow +disarm +disarray +disaster +disband +disbelief +disburse +discard +discern +discharge +disclose +discolor +discount +discourse +discover +discuss +disdain +disengage +disfigure +disgrace +dish +disinfect +disjoin +disk +dislike +disliking +dislocate +dislodge +disloyal +dismantle +dismay +dismiss +dismount +disobey +disorder +disown +disparate +disparity +dispatch +dispense +dispersal +dispersed +disperser +displace +display +displease +disposal +dispose +disprove +dispute +disregard +disrupt +dissuade +distance +distant +distaste +distill +distinct +distort +distract +distress +district +distrust +ditch +ditto +ditzy +dividable +divided +dividend +dividers +dividing +divinely +diving +divinity +divisible +divisibly +division +divisive +divorcee +dizziness +dizzy +doable +docile +dock +doctrine +document +dodge +dodgy +doily +doing +dole +dollar +dollhouse +dollop +dolly +dolphin +domain +domelike +domestic +dominion +dominoes +donated +donation +donator +donor +donut +doodle +doorbell +doorframe +doorknob +doorman +doormat +doornail +doorpost +doorstep +doorstop +doorway +doozy +dork +dormitory +dorsal +dosage +dose +dotted +doubling +douche +dove +down +dowry +doze +drab +dragging +dragonfly +dragonish +dragster +drainable +drainage +drained +drainer +drainpipe +dramatic +dramatize +drank +drapery +drastic +draw +dreaded +dreadful +dreadlock +dreamboat +dreamily +dreamland +dreamless +dreamlike +dreamt +dreamy +drearily +dreary +drench +dress +drew +dribble +dried +drier +drift +driller +drilling +drinkable +drinking +dripping +drippy +drivable +driven +driver +driveway +driving +drizzle +drizzly +drone +drool +droop +drop-down +dropbox +dropkick +droplet +dropout +dropper +drove +drown +drowsily +drudge +drum +dry +dubbed +dubiously +duchess +duckbill +ducking +duckling +ducktail +ducky +duct +dude +duffel +dugout +duh +duke +duller +dullness +duly +dumping +dumpling +dumpster +duo +dupe +duplex +duplicate +duplicity +durable +durably +duration +duress +during +dusk +dust +dutiful +duty +duvet +dwarf +dweeb +dwelled +dweller +dwelling +dwindle +dwindling +dynamic +dynamite +dynasty +dyslexia +dyslexic +each +eagle +earache +eardrum +earflap +earful +earlobe +early +earmark +earmuff +earphone +earpiece +earplugs +earring +earshot +earthen +earthlike +earthling +earthly +earthworm +earthy +earwig +easeful +easel +easiest +easily +easiness +easing +eastbound +eastcoast +easter +eastward +eatable +eaten +eatery +eating +eats +ebay +ebony +ebook +ecard +eccentric +echo +eclair +eclipse +ecologist +ecology +economic +economist +economy +ecosphere +ecosystem +edge +edginess +edging +edgy +edition +editor +educated +education +educator +eel +effective +effects +efficient +effort +eggbeater +egging +eggnog +eggplant +eggshell +egomaniac +egotism +egotistic +either +eject +elaborate +elastic +elated +elbow +eldercare +elderly +eldest +electable +election +elective +elephant +elevate +elevating +elevation +elevator +eleven +elf +eligible +eligibly +eliminate +elite +elitism +elixir +elk +ellipse +elliptic +elm +elongated +elope +eloquence +eloquent +elsewhere +elude +elusive +elves +email +embargo +embark +embassy +embattled +embellish +ember +embezzle +emblaze +emblem +embody +embolism +emboss +embroider +emcee +emerald +emergency +emission +emit +emote +emoticon +emotion +empathic +empathy +emperor +emphases +emphasis +emphasize +emphatic +empirical +employed +employee +employer +emporium +empower +emptier +emptiness +empty +emu +enable +enactment +enamel +enchanted +enchilada +encircle +enclose +enclosure +encode +encore +encounter +encourage +encroach +encrust +encrypt +endanger +endeared +endearing +ended +ending +endless +endnote +endocrine +endorphin +endorse +endowment +endpoint +endurable +endurance +enduring +energetic +energize +energy +enforced +enforcer +engaged +engaging +engine +engorge +engraved +engraver +engraving +engross +engulf +enhance +enigmatic +enjoyable +enjoyably +enjoyer +enjoying +enjoyment +enlarged +enlarging +enlighten +enlisted +enquirer +enrage +enrich +enroll +enslave +ensnare +ensure +entail +entangled +entering +entertain +enticing +entire +entitle +entity +entomb +entourage +entrap +entree +entrench +entrust +entryway +entwine +enunciate +envelope +enviable +enviably +envious +envision +envoy +envy +enzyme +epic +epidemic +epidermal +epidermis +epidural +epilepsy +epileptic +epilogue +epiphany +episode +equal +equate +equation +equator +equinox +equipment +equity +equivocal +eradicate +erasable +erased +eraser +erasure +ergonomic +errand +errant +erratic +error +erupt +escalate +escalator +escapable +escapade +escapist +escargot +eskimo +esophagus +espionage +espresso +esquire +essay +essence +essential +establish +estate +esteemed +estimate +estimator +estranged +estrogen +etching +eternal +eternity +ethanol +ether +ethically +ethics +euphemism +evacuate +evacuee +evade +evaluate +evaluator +evaporate +evasion +evasive +even +everglade +evergreen +everybody +everyday +everyone +evict +evidence +evident +evil +evoke +evolution +evolve +exact +exalted +example +excavate +excavator +exceeding +exception +excess +exchange +excitable +exciting +exclaim +exclude +excluding +exclusion +exclusive +excretion +excretory +excursion +excusable +excusably +excuse +exemplary +exemplify +exemption +exerciser +exert +exes +exfoliate +exhale +exhaust +exhume +exile +existing +exit +exodus +exonerate +exorcism +exorcist +expand +expanse +expansion +expansive +expectant +expedited +expediter +expel +expend +expenses +expensive +expert +expire +expiring +explain +expletive +explicit +explode +exploit +explore +exploring +exponent +exporter +exposable +expose +exposure +express +expulsion +exquisite +extended +extending +extent +extenuate +exterior +external +extinct +extortion +extradite +extras +extrovert +extrude +extruding +exuberant +fable +fabric +fabulous +facebook +facecloth +facedown +faceless +facelift +faceplate +faceted +facial +facility +facing +facsimile +faction +factoid +factor +factsheet +factual +faculty +fade +fading +failing +falcon +fall +false +falsify +fame +familiar +family +famine +famished +fanatic +fancied +fanciness +fancy +fanfare +fang +fanning +fantasize +fantastic +fantasy +fascism +fastball +faster +fasting +fastness +faucet +favorable +favorably +favored +favoring +favorite +fax +feast +federal +fedora +feeble +feed +feel +feisty +feline +felt-tip +feminine +feminism +feminist +feminize +femur +fence +fencing +fender +ferment +fernlike +ferocious +ferocity +ferret +ferris +ferry +fervor +fester +festival +festive +festivity +fetal +fetch +fever +fiber +fiction +fiddle +fiddling +fidelity +fidgeting +fidgety +fifteen +fifth +fiftieth +fifty +figment +figure +figurine +filing +filled +filler +filling +film +filter +filth +filtrate +finale +finalist +finalize +finally +finance +financial +finch +fineness +finer +finicky +finished +finisher +finishing +finite +finless +finlike +fiscally +fit +five +flaccid +flagman +flagpole +flagship +flagstick +flagstone +flail +flakily +flaky +flame +flammable +flanked +flanking +flannels +flap +flaring +flashback +flashbulb +flashcard +flashily +flashing +flashy +flask +flatbed +flatfoot +flatly +flatness +flatten +flattered +flatterer +flattery +flattop +flatware +flatworm +flavored +flavorful +flavoring +flaxseed +fled +fleshed +fleshy +flick +flier +flight +flinch +fling +flint +flip +flirt +float +flock +flogging +flop +floral +florist +floss +flounder +flyable +flyaway +flyer +flying +flyover +flypaper +foam +foe +fog +foil +folic +folk +follicle +follow +fondling +fondly +fondness +fondue +font +food +fool +footage +football +footbath +footboard +footer +footgear +foothill +foothold +footing +footless +footman +footnote +footpad +footpath +footprint +footrest +footsie +footsore +footwear +footwork +fossil +foster +founder +founding +fountain +fox +foyer +fraction +fracture +fragile +fragility +fragment +fragrance +fragrant +frail +frame +framing +frantic +fraternal +frayed +fraying +frays +freckled +freckles +freebase +freebee +freebie +freedom +freefall +freehand +freeing +freeload +freely +freemason +freeness +freestyle +freeware +freeway +freewill +freezable +freezing +freight +french +frenzied +frenzy +frequency +frequent +fresh +fretful +fretted +friction +friday +fridge +fried +friend +frighten +frightful +frigidity +frigidly +frill +fringe +frisbee +frisk +fritter +frivolous +frolic +from +front +frostbite +frosted +frostily +frosting +frostlike +frosty +froth +frown +frozen +fructose +frugality +frugally +fruit +frustrate +frying +gab +gaffe +gag +gainfully +gaining +gains +gala +gallantly +galleria +gallery +galley +gallon +gallows +gallstone +galore +galvanize +gambling +game +gaming +gamma +gander +gangly +gangrene +gangway +gap +garage +garbage +garden +gargle +garland +garlic +garment +garnet +garnish +garter +gas +gatherer +gathering +gating +gauging +gauntlet +gauze +gave +gawk +gazing +gear +gecko +geek +geiger +gem +gender +generic +generous +genetics +genre +gentile +gentleman +gently +gents +geography +geologic +geologist +geology +geometric +geometry +geranium +gerbil +geriatric +germicide +germinate +germless +germproof +gestate +gestation +gesture +getaway +getting +getup +giant +gibberish +giblet +giddily +giddiness +giddy +gift +gigabyte +gigahertz +gigantic +giggle +giggling +giggly +gigolo +gilled +gills +gimmick +girdle +giveaway +given +giver +giving +gizmo +gizzard +glacial +glacier +glade +gladiator +gladly +glamorous +glamour +glance +glancing +glandular +glare +glaring +glass +glaucoma +glazing +gleaming +gleeful +glider +gliding +glimmer +glimpse +glisten +glitch +glitter +glitzy +gloater +gloating +gloomily +gloomy +glorified +glorifier +glorify +glorious +glory +gloss +glove +glowing +glowworm +glucose +glue +gluten +glutinous +glutton +gnarly +gnat +goal +goatskin +goes +goggles +going +goldfish +goldmine +goldsmith +golf +goliath +gonad +gondola +gone +gong +good +gooey +goofball +goofiness +goofy +google +goon +gopher +gore +gorged +gorgeous +gory +gosling +gossip +gothic +gotten +gout +gown +grab +graceful +graceless +gracious +gradation +graded +grader +gradient +grading +gradually +graduate +graffiti +grafted +grafting +grain +granddad +grandkid +grandly +grandma +grandpa +grandson +granite +granny +granola +grant +granular +grape +graph +grapple +grappling +grasp +grass +gratified +gratify +grating +gratitude +gratuity +gravel +graveness +graves +graveyard +gravitate +gravity +gravy +gray +grazing +greasily +greedily +greedless +greedy +green +greeter +greeting +grew +greyhound +grid +grief +grievance +grieving +grievous +grill +grimace +grimacing +grime +griminess +grimy +grinch +grinning +grip +gristle +grit +groggily +groggy +groin +groom +groove +grooving +groovy +grope +ground +grouped +grout +grove +grower +growing +growl +grub +grudge +grudging +grueling +gruffly +grumble +grumbling +grumbly +grumpily +grunge +grunt +guacamole +guidable +guidance +guide +guiding +guileless +guise +gulf +gullible +gully +gulp +gumball +gumdrop +gumminess +gumming +gummy +gurgle +gurgling +guru +gush +gusto +gusty +gutless +guts +gutter +guy +guzzler +gyration +habitable +habitant +habitat +habitual +hacked +hacker +hacking +hacksaw +had +haggler +haiku +half +halogen +halt +halved +halves +hamburger +hamlet +hammock +hamper +hamster +hamstring +handbag +handball +handbook +handbrake +handcart +handclap +handclasp +handcraft +handcuff +handed +handful +handgrip +handgun +handheld +handiness +handiwork +handlebar +handled +handler +handling +handmade +handoff +handpick +handprint +handrail +handsaw +handset +handsfree +handshake +handstand +handwash +handwork +handwoven +handwrite +handyman +hangnail +hangout +hangover +hangup +hankering +hankie +hanky +haphazard +happening +happier +happiest +happily +happiness +happy +harbor +hardcopy +hardcore +hardcover +harddisk +hardened +hardener +hardening +hardhat +hardhead +hardiness +hardly +hardness +hardship +hardware +hardwired +hardwood +hardy +harmful +harmless +harmonica +harmonics +harmonize +harmony +harness +harpist +harsh +harvest +hash +hassle +haste +hastily +hastiness +hasty +hatbox +hatchback +hatchery +hatchet +hatching +hatchling +hate +hatless +hatred +haunt +haven +hazard +hazelnut +hazily +haziness +hazing +hazy +headache +headband +headboard +headcount +headdress +headed +header +headfirst +headgear +heading +headlamp +headless +headlock +headphone +headpiece +headrest +headroom +headscarf +headset +headsman +headstand +headstone +headway +headwear +heap +heat +heave +heavily +heaviness +heaving +hedge +hedging +heftiness +hefty +helium +helmet +helper +helpful +helping +helpless +helpline +hemlock +hemstitch +hence +henchman +henna +herald +herbal +herbicide +herbs +heritage +hermit +heroics +heroism +herring +herself +hertz +hesitancy +hesitant +hesitate +hexagon +hexagram +hubcap +huddle +huddling +huff +hug +hula +hulk +hull +human +humble +humbling +humbly +humid +humiliate +humility +humming +hummus +humongous +humorist +humorless +humorous +humpback +humped +humvee +hunchback +hundredth +hunger +hungrily +hungry +hunk +hunter +hunting +huntress +huntsman +hurdle +hurled +hurler +hurling +hurray +hurricane +hurried +hurry +hurt +husband +hush +husked +huskiness +hut +hybrid +hydrant +hydrated +hydration +hydrogen +hydroxide +hyperlink +hypertext +hyphen +hypnoses +hypnosis +hypnotic +hypnotism +hypnotist +hypnotize +hypocrisy +hypocrite +ibuprofen +ice +iciness +icing +icky +icon +icy +idealism +idealist +idealize +ideally +idealness +identical +identify +identity +ideology +idiocy +idiom +idly +igloo +ignition +ignore +iguana +illicitly +illusion +illusive +image +imaginary +imagines +imaging +imbecile +imitate +imitation +immature +immerse +immersion +imminent +immobile +immodest +immorally +immortal +immovable +immovably +immunity +immunize +impaired +impale +impart +impatient +impeach +impeding +impending +imperfect +imperial +impish +implant +implement +implicate +implicit +implode +implosion +implosive +imply +impolite +important +importer +impose +imposing +impotence +impotency +impotent +impound +imprecise +imprint +imprison +impromptu +improper +improve +improving +improvise +imprudent +impulse +impulsive +impure +impurity +iodine +iodize +ion +ipad +iphone +ipod +irate +irk +iron +irregular +irrigate +irritable +irritably +irritant +irritate +islamic +islamist +isolated +isolating +isolation +isotope +issue +issuing +italicize +italics +item +itinerary +itunes +ivory +ivy +jab +jackal +jacket +jackknife +jackpot +jailbird +jailbreak +jailer +jailhouse +jalapeno +jam +janitor +january +jargon +jarring +jasmine +jaundice +jaunt +java +jawed +jawless +jawline +jaws +jaybird +jaywalker +jazz +jeep +jeeringly +jellied +jelly +jersey +jester +jet +jiffy +jigsaw +jimmy +jingle +jingling +jinx +jitters +jittery +job +jockey +jockstrap +jogger +jogging +john +joining +jokester +jokingly +jolliness +jolly +jolt +jot +jovial +joyfully +joylessly +joyous +joyride +joystick +jubilance +jubilant +judge +judgingly +judicial +judiciary +judo +juggle +juggling +jugular +juice +juiciness +juicy +jujitsu +jukebox +july +jumble +jumbo +jump +junction +juncture +june +junior +juniper +junkie +junkman +junkyard +jurist +juror +jury +justice +justifier +justify +justly +justness +juvenile +kabob +kangaroo +karaoke +karate +karma +kebab +keenly +keenness +keep +keg +kelp +kennel +kept +kerchief +kerosene +kettle +kick +kiln +kilobyte +kilogram +kilometer +kilowatt +kilt +kimono +kindle +kindling +kindly +kindness +kindred +kinetic +kinfolk +king +kinship +kinsman +kinswoman +kissable +kisser +kissing +kitchen +kite +kitten +kitty +kiwi +kleenex +knapsack +knee +knelt +knickers +knoll +koala +kooky +kosher +krypton +kudos +kung +labored +laborer +laboring +laborious +labrador +ladder +ladies +ladle +ladybug +ladylike +lagged +lagging +lagoon +lair +lake +lance +landed +landfall +landfill +landing +landlady +landless +landline +landlord +landmark +landmass +landmine +landowner +landscape +landside +landslide +language +lankiness +lanky +lantern +lapdog +lapel +lapped +lapping +laptop +lard +large +lark +lash +lasso +last +latch +late +lather +latitude +latrine +latter +latticed +launch +launder +laundry +laurel +lavender +lavish +laxative +lazily +laziness +lazy +lecturer +left +legacy +legal +legend +legged +leggings +legible +legibly +legislate +lego +legroom +legume +legwarmer +legwork +lemon +lend +length +lens +lent +leotard +lesser +letdown +lethargic +lethargy +letter +lettuce +level +leverage +levers +levitate +levitator +liability +liable +liberty +librarian +library +licking +licorice +lid +life +lifter +lifting +liftoff +ligament +likely +likeness +likewise +liking +lilac +lilly +lily +limb +limeade +limelight +limes +limit +limping +limpness +line +lingo +linguini +linguist +lining +linked +linoleum +linseed +lint +lion +lip +liquefy +liqueur +liquid +lisp +list +litigate +litigator +litmus +litter +little +livable +lived +lively +liver +livestock +lividly +living +lizard +lubricant +lubricate +lucid +luckily +luckiness +luckless +lucrative +ludicrous +lugged +lukewarm +lullaby +lumber +luminance +luminous +lumpiness +lumping +lumpish +lunacy +lunar +lunchbox +luncheon +lunchroom +lunchtime +lung +lurch +lure +luridness +lurk +lushly +lushness +luster +lustfully +lustily +lustiness +lustrous +lusty +luxurious +luxury +lying +lyrically +lyricism +lyricist +lyrics +macarena +macaroni +macaw +mace +machine +machinist +magazine +magenta +maggot +magical +magician +magma +magnesium +magnetic +magnetism +magnetize +magnifier +magnify +magnitude +magnolia +mahogany +maimed +majestic +majesty +majorette +majority +makeover +maker +makeshift +making +malformed +malt +mama +mammal +mammary +mammogram +manager +managing +manatee +mandarin +mandate +mandatory +mandolin +manger +mangle +mango +mangy +manhandle +manhole +manhood +manhunt +manicotti +manicure +manifesto +manila +mankind +manlike +manliness +manly +manmade +manned +mannish +manor +manpower +mantis +mantra +manual +many +map +marathon +marauding +marbled +marbles +marbling +march +mardi +margarine +margarita +margin +marigold +marina +marine +marital +maritime +marlin +marmalade +maroon +married +marrow +marry +marshland +marshy +marsupial +marvelous +marxism +mascot +masculine +mashed +mashing +massager +masses +massive +mastiff +matador +matchbook +matchbox +matcher +matching +matchless +material +maternal +maternity +math +mating +matriarch +matrimony +matrix +matron +matted +matter +maturely +maturing +maturity +mauve +maverick +maximize +maximum +maybe +mayday +mayflower +moaner +moaning +mobile +mobility +mobilize +mobster +mocha +mocker +mockup +modified +modify +modular +modulator +module +moisten +moistness +moisture +molar +molasses +mold +molecular +molecule +molehill +mollusk +mom +monastery +monday +monetary +monetize +moneybags +moneyless +moneywise +mongoose +mongrel +monitor +monkhood +monogamy +monogram +monologue +monopoly +monorail +monotone +monotype +monoxide +monsieur +monsoon +monstrous +monthly +monument +moocher +moodiness +moody +mooing +moonbeam +mooned +moonlight +moonlike +moonlit +moonrise +moonscape +moonshine +moonstone +moonwalk +mop +morale +morality +morally +morbidity +morbidly +morphine +morphing +morse +mortality +mortally +mortician +mortified +mortify +mortuary +mosaic +mossy +most +mothball +mothproof +motion +motivate +motivator +motive +motocross +motor +motto +mountable +mountain +mounted +mounting +mourner +mournful +mouse +mousiness +moustache +mousy +mouth +movable +move +movie +moving +mower +mowing +much +muck +mud +mug +mulberry +mulch +mule +mulled +mullets +multiple +multiply +multitask +multitude +mumble +mumbling +mumbo +mummified +mummify +mummy +mumps +munchkin +mundane +municipal +muppet mural -misjudged +murkiness +murky +murmuring +muscular +museum +mushily +mushiness +mushroom +mushy +music +musket +muskiness +musky +mustang +mustard +muster +mustiness +musty +mutable +mutate +mutation +mute +mutilated +mutilator +mutiny +mutt +mutual +muzzle +myself +myspace +mystified +mystify +myth +nacho +nag +nail +name +naming +nanny +nanometer +nape +napkin +napped +napping +nappy +narrow +nastily +nastiness +national +native +nativity +natural +nature +naturist +nautical +navigate +navigator +navy +nearby +nearest +nearly +nearness +neatly +neatness +nebula +nebulizer +nectar +negate +negation +negative +neglector +negligee +negligent +negotiate +nemeses +nemesis +neon +nephew +nerd +nervous +nervy +nest +net +neurology +neuron +neurosis +neurotic +neuter +neutron +never +next +nibble +nickname +nicotine +niece +nifty +nimble +nimbly +nineteen +ninetieth +ninja +nintendo +ninth +nuclear +nuclei +nucleus +nugget +nullify +number +numbing +numbly +numbness +numeral +numerate +numerator +numeric +numerous +nuptials +nursery +nursing +nurture +nutcase +nutlike +nutmeg +nutrient +nutshell +nuttiness +nutty +nuzzle +nylon +oaf +oak +oasis +oat +obedience +obedient +obituary +object +obligate +obliged +oblivion +oblivious +oblong +obnoxious +oboe +obscure +obscurity +observant +observer +observing +obsessed +obsession +obsessive +obsolete +obstacle +obstinate +obstruct +obtain +obtrusive +obtuse +obvious +occultist +occupancy +occupant +occupier +occupy +ocean +ocelot +octagon +octane +october +octopus +ogle +oil +oink +ointment +okay +old +olive +olympics +omega +omen +ominous +omission +omit +omnivore +onboard +oncoming +ongoing +onion +online +onlooker +only +onscreen +onset +onshore +onslaught +onstage +onto +onward +onyx +oops +ooze +oozy +opacity +opal +open +operable +operate +operating +operation +operative +operator +opium +opossum +opponent +oppose +opposing +opposite +oppressed +oppressor +opt +opulently +osmosis +other +otter +ouch +ought +ounce +outage +outback +outbid +outboard +outbound +outbreak +outburst +outcast +outclass +outcome +outdated +outdoors +outer +outfield +outfit +outflank +outgoing +outgrow +outhouse +outing +outlast +outlet +outline +outlook +outlying +outmatch +outmost +outnumber +outplayed +outpost +outpour +output +outrage +outrank +outreach +outright +outscore +outsell +outshine +outshoot +outsider +outskirts +outsmart +outsource +outspoken +outtakes +outthink +outward +outweigh +outwit +oval +ovary +oven +overact +overall +overarch +overbid +overbill +overbite +overblown +overboard +overbook +overbuilt +overcast +overcoat +overcome +overcook +overcrowd +overdraft +overdrawn +overdress +overdrive +overdue +overeager +overeater +overexert +overfed +overfeed +overfill +overflow +overfull +overgrown +overhand +overhang +overhaul +overhead +overhear +overheat +overhung +overjoyed +overkill +overlabor +overlaid +overlap +overlay +overload +overlook +overlord +overlying +overnight +overpass +overpay +overplant +overplay +overpower +overprice +overrate +overreach +overreact +override +overripe +overrule +overrun +overshoot +overshot +oversight +oversized +oversleep +oversold +overspend +overstate +overstay +overstep +overstock +overstuff +oversweet +overtake +overthrow +overtime +overtly +overtone +overture +overturn +overuse +overvalue +overview +overwrite +owl +oxford +oxidant +oxidation +oxidize +oxidizing +oxygen +oxymoron +oyster +ozone +paced +pacemaker +pacific +pacifier +pacifism +pacifist +pacify +padded +padding +paddle +paddling +padlock +pagan +pager +paging +pajamas +palace +palatable +palm +palpable +palpitate +paltry +pampered +pamperer +pampers +pamphlet +panama +pancake +pancreas +panda +pandemic +pang +panhandle +panic +panning +panorama +panoramic +panther +pantomime +pantry +pants +pantyhose +paparazzi +papaya +paper +paprika +papyrus +parabola +parachute +parade +paradox +paragraph +parakeet +paralegal +paralyses +paralysis +paralyze +paramedic +parameter +paramount +parasail +parasite +parasitic +parcel +parched +parchment +pardon +parish +parka +parking +parkway +parlor +parmesan +parole +parrot +parsley +parsnip +partake +parted +parting +partition +partly +partner +partridge +party +passable +passably +passage +passcode +passenger +passerby +passing +passion +passive +passivism +passover +passport +password +pasta +pasted +pastel +pastime +pastor +pastrami +pasture +pasty +patchwork +patchy +paternal +paternity +path +patience +patient +patio +patriarch +patriot +patrol +patronage +patronize +pauper +pavement +paver +pavestone +pavilion +paving +pawing +payable +payback +paycheck +payday +payee +payer +paying +payment +payphone +payroll +pebble +pebbly +pecan +pectin +peculiar +peddling +pediatric +pedicure +pedigree +pedometer +pegboard +pelican +pellet +pelt +pelvis +penalize +penalty +pencil +pendant +pending +penholder +penknife +pennant +penniless +penny +penpal +pension +pentagon +pentagram +pep +perceive +percent +perch +percolate +perennial +perfected +perfectly +perfume +periscope +perish +perjurer +perjury +perkiness +perky +perm +peroxide +perpetual +perplexed +persecute +persevere +persuaded +persuader +pesky +peso +pessimism +pessimist +pester +pesticide +petal +petite +petition +petri +petroleum +petted +petticoat +pettiness +petty +petunia +phantom +phobia +phoenix +phonebook +phoney +phonics +phoniness +phony +phosphate +photo +phrase +phrasing +placard +placate +placidly +plank +planner +plant +plasma +plaster +plastic +plated +platform +plating +platinum +platonic +platter +platypus +plausible +plausibly +playable +playback +player +playful +playgroup +playhouse +playing +playlist +playmaker +playmate +playoff +playpen +playroom +playset +plaything +playtime +plaza +pleading +pleat +pledge +plentiful +plenty +plethora +plexiglas +pliable +plod +plop +plot +plow +ploy +pluck +plug +plunder +plunging +plural +plus +plutonium +plywood +poach +pod +poem +poet +pogo +pointed +pointer +pointing +pointless +pointy +poise +poison +poker +poking +polar +police +policy +polio +polish +politely +polka +polo +polyester +polygon +polygraph +polymer +poncho +pond +pony +popcorn +pope +poplar +popper +poppy +popsicle +populace +popular +populate +porcupine +pork +porous +porridge +portable +portal +portfolio +porthole +portion +portly +portside +poser +posh +posing +possible +possibly +possum +postage +postal +postbox +postcard +posted +poster +posting +postnasal +posture +postwar +pouch +pounce +pouncing +pound +pouring +pout +powdered +powdering +powdery +power +powwow +pox +praising +prance +prancing +pranker +prankish +prankster +prayer +praying +preacher +preaching +preachy +preamble +precinct +precise +precision +precook +precut +predator +predefine +predict +preface +prefix +preflight +preformed +pregame +pregnancy +pregnant +preheated +prelaunch +prelaw +prelude +premiere +premises +premium +prenatal +preoccupy +preorder +prepaid +prepay +preplan +preppy +preschool +prescribe +preseason +preset +preshow +president +presoak +press +presume +presuming +preteen +pretended +pretender +pretense +pretext +pretty +pretzel +prevail +prevalent +prevent +preview +previous +prewar +prewashed +prideful +pried +primal +primarily +primary +primate +primer +primp +princess +print +prior +prism +prison +prissy +pristine +privacy +private +privatize +prize +proactive +probable +probably +probation +probe +probing +probiotic +problem +procedure +process +proclaim +procreate +procurer +prodigal +prodigy +produce +product +profane +profanity +professed +professor +profile +profound +profusely +progeny +prognosis +program +progress +projector +prologue +prolonged +promenade +prominent +promoter +promotion +prompter +promptly +prone +prong +pronounce +pronto +proofing +proofread +proofs +propeller +properly +property +proponent +proposal +propose +props +prorate +protector +protegee +proton +prototype +protozoan +protract +protrude +proud +provable +proved +proven +provided +provider +providing +province +proving +provoke +provoking +provolone +prowess +prowler +prowling +proximity +proxy +prozac +prude +prudishly +prune +pruning +pry +psychic +public +publisher +pucker +pueblo +pug +pull +pulmonary +pulp +pulsate +pulse +pulverize +puma +pumice +pummel +punch +punctual +punctuate +punctured +pungent +punisher +punk +pupil +puppet +puppy +purchase +pureblood +purebred +purely +pureness +purgatory +purge +purging +purifier +purify +purist +puritan +purity +purple +purplish +purposely +purr +purse +pursuable +pursuant +pursuit +purveyor +pushcart +pushchair +pusher +pushiness +pushing +pushover +pushpin +pushup +pushy +putdown +putt +puzzle +puzzling +pyramid +pyromania +python +quack +quadrant +quail +quaintly +quake +quaking +qualified +qualifier +qualify +quality +qualm +quantum +quarrel +quarry +quartered +quarterly +quarters +quartet +quench +query +quicken +quickly +quickness +quicksand +quickstep +quiet +quill +quilt +quintet +quintuple +quirk +quit +quiver +quizzical +quotable +quotation +quote +rabid +race +racing +racism +rack +racoon +radar +radial +radiance +radiantly +radiated +radiation +radiator +radio +radish +raffle +raft +rage +ragged +raging +ragweed +raider +railcar +railing +railroad +railway +raisin +rake +raking +rally +ramble +rambling +ramp +ramrod +ranch +rancidity +random +ranged +ranger +ranging +ranked +ranking +ransack +ranting +rants +rare +rarity +rascal +rash +rasping +ravage +raven +ravine +raving +ravioli +ravishing +reabsorb +reach +reacquire +reaction +reactive +reactor +reaffirm +ream +reanalyze +reappear +reapply +reappoint +reapprove +rearrange +rearview +reason +reassign +reassure +reattach +reawake +rebalance +rebate +rebel +rebirth +reboot +reborn +rebound +rebuff +rebuild +rebuilt +reburial +rebuttal +recall +recant +recapture +recast +recede +recent +recess +recharger +recipient +recital +recite +reckless +reclaim +recliner +reclining +recluse +reclusive +recognize +recoil +recollect +recolor +reconcile +reconfirm +reconvene +recopy +record +recount +recoup +recovery +recreate +rectal +rectangle +rectified +rectify +recycled +recycler +recycling +reemerge +reenact +reenter +reentry +reexamine +referable +referee +reference +refill +refinance +refined +refinery +refining +refinish +reflected +reflector +reflex +reflux +refocus +refold +reforest +reformat +reformed +reformer +reformist +refract +refrain +refreeze +refresh +refried +refueling +refund +refurbish +refurnish +refusal +refuse +refusing +refutable +refute +regain +regalia +regally +reggae +regime +region +register +registrar +registry +regress +regretful +regroup +regular +regulate +regulator +rehab +reheat +rehire +rehydrate +reimburse +reissue +reiterate +rejoice +rejoicing +rejoin +rekindle +relapse +relapsing +relatable +related +relation +relative +relax +relay +relearn +release +relenting +reliable +reliably +reliance +reliant +relic +relieve +relieving +relight +relish +relive +reload +relocate +relock +reluctant +rely +remake +remark +remarry +rematch +remedial +remedy +remember +reminder +remindful +remission +remix +remnant +remodeler +remold +remorse +remote +removable +removal +removed +remover +removing +rename +renderer +rendering +rendition +renegade +renewable +renewably +renewal +renewed +renounce +renovate +renovator +rentable +rental +rented +renter +reoccupy +reoccur +reopen +reorder +repackage +repacking +repaint +repair +repave +repaying +repayment +repeal +repeated +repeater +repent +rephrase +replace +replay +replica +reply +reporter +repose +repossess +repost +repressed +reprimand +reprint +reprise +reproach +reprocess +reproduce +reprogram +reps +reptile +reptilian +repugnant +repulsion +repulsive +repurpose +reputable +reputably +request +require +requisite +reroute +rerun +resale +resample +rescuer +reseal +research +reselect +reseller +resemble +resend +resent +reset +reshape +reshoot +reshuffle +residence +residency +resident +residual +residue +resigned +resilient +resistant +resisting +resize +resolute +resolved +resonant +resonate +resort +resource +respect +resubmit +result +resume +resupply +resurface +resurrect +retail +retainer +retaining +retake +retaliate +retention +rethink +retinal +retired +retiree +retiring +retold +retool +retorted +retouch +retrace +retract +retrain +retread +retreat +retrial +retrieval +retriever +retry +return +retying +retype +reunion +reunite +reusable +reuse +reveal +reveler +revenge +revenue +reverb +revered +reverence +reverend +reversal +reverse +reversing +reversion +revert +revisable +revise +revision +revisit +revivable +revival +reviver +reviving +revocable +revoke +revolt +revolver +revolving +reward +rewash +rewind +rewire +reword +rework +rewrap +rewrite +rhyme +ribbon +ribcage +rice +riches +richly +richness +rickety +ricotta +riddance +ridden +ride +riding +rifling +rift +rigging +rigid +rigor +rimless +rimmed +rind +rink +rinse +rinsing +riot +ripcord +ripeness +ripening +ripping +ripple +rippling +riptide +rise +rising +risk +risotto +ritalin +ritzy +rival +riverbank +riverbed +riverboat +riverside +riveter +riveting +roamer +roaming +roast +robbing +robe +robin +robotics +robust +rockband +rocker +rocket +rockfish +rockiness +rocking +rocklike +rockslide +rockstar +rocky +rogue +roman +romp +rope +roping +roster +rosy +rotten +rotting +rotunda +roulette +rounding +roundish +roundness +roundup +roundworm +routine +routing +rover +roving +royal +rubbed +rubber +rubbing +rubble +rubdown +ruby +ruckus +rudder +rug +ruined +rule +rumble +rumbling +rummage +rumor +runaround +rundown +runner +running +runny +runt +runway +rupture +rural +ruse +rush +rust +rut +sabbath +sabotage +sacrament +sacred +sacrifice +sadden +saddlebag +saddled +saddling +sadly +sadness +safari +safeguard +safehouse +safely +safeness +saffron +saga +sage +sagging +saggy +said +saint +sake +salad +salami +salaried +salary +saline +salon +saloon +salsa +salt +salutary +salute +salvage +salvaging +salvation +same +sample +sampling +sanction +sanctity +sanctuary +sandal +sandbag +sandbank +sandbar +sandblast +sandbox +sanded +sandfish +sanding +sandlot +sandpaper +sandpit +sandstone +sandstorm +sandworm +sandy +sanitary +sanitizer +sank +santa +sapling +sappiness +sappy +sarcasm +sarcastic +sardine +sash +sasquatch +sassy +satchel +satiable +satin +satirical +satisfied +satisfy +saturate +saturday +sauciness +saucy +sauna +savage +savanna +saved +savings +savior +savor +saxophone +say +scabbed +scabby +scalded +scalding +scale +scaling +scallion +scallop +scalping +scam +scandal +scanner +scanning +scant +scapegoat +scarce +scarcity +scarecrow +scared +scarf +scarily +scariness +scarring +scary +scavenger +scenic +schedule +schematic +scheme +scheming +schilling +schnapps +scholar +science +scientist +scion +scoff +scolding +scone +scoop +scooter +scope +scorch +scorebook +scorecard +scored +scoreless +scorer +scoring +scorn +scorpion +scotch +scoundrel +scoured +scouring +scouting +scouts +scowling +scrabble +scraggly +scrambled +scrambler +scrap +scratch +scrawny +screen +scribble +scribe +scribing +scrimmage +script +scroll +scrooge +scrounger +scrubbed +scrubber +scruffy +scrunch +scrutiny +scuba +scuff +sculptor +sculpture +scurvy +scuttle +secluded +secluding +seclusion +second +secrecy +secret +sectional +sector +secular +securely +security +sedan +sedate +sedation +sedative +sediment +seduce +seducing +segment +seismic +seizing +seldom +selected +selection +selective +selector +self +seltzer +semantic +semester +semicolon +semifinal +seminar +semisoft +semisweet +senate +senator +send +senior +senorita +sensation +sensitive +sensitize +sensually +sensuous +sepia +september +septic +septum +sequel +sequence +sequester +series +sermon +serotonin +serpent +serrated +serve +service +serving +sesame +sessions +setback +setting +settle +settling +setup +sevenfold +seventeen +seventh +seventy +severity +shabby +shack +shaded +shadily +shadiness +shading +shadow +shady +shaft +shakable +shakily +shakiness +shaking +shaky +shale +shallot +shallow +shame +shampoo +shamrock +shank +shanty +shape +shaping +share +sharpener +sharper +sharpie +sharply +sharpness +shawl +sheath +shed +sheep +sheet +shelf +shell +shelter +shelve +shelving +sherry +shield +shifter +shifting +shiftless +shifty +shimmer +shimmy +shindig +shine +shingle +shininess +shining +shiny +ship +shirt +shivering +shock +shone +shoplift +shopper +shopping +shoptalk +shore +shortage +shortcake +shortcut +shorten +shorter +shorthand +shortlist +shortly +shortness +shorts +shortwave +shorty +shout +shove +showbiz +showcase +showdown +shower +showgirl +showing +showman +shown +showoff +showpiece +showplace +showroom +showy +shrank +shrapnel +shredder +shredding +shrewdly +shriek +shrill +shrimp +shrine +shrink +shrivel +shrouded +shrubbery +shrubs +shrug +shrunk +shucking +shudder +shuffle +shuffling +shun +shush +shut +shy +siamese +siberian +sibling +siding +sierra +siesta +sift +sighing +silenced +silencer +silent +silica +silicon +silk +silliness +silly +silo +silt +silver +similarly +simile +simmering +simple +simplify +simply +sincere +sincerity +singer +singing +single +singular +sinister +sinless +sinner +sinuous +sip +siren +sister +sitcom +sitter +sitting +situated +situation +sixfold +sixteen +sixth +sixties +sixtieth +sixtyfold +sizable +sizably +size +sizing +sizzle +sizzling +skater +skating +skedaddle +skeletal +skeleton +skeptic +sketch +skewed +skewer +skid +skied +skier +skies +skiing +skilled +skillet +skillful +skimmed +skimmer +skimming +skimpily +skincare +skinhead +skinless +skinning +skinny +skintight +skipper +skipping +skirmish +skirt +skittle +skydiver +skylight +skyline +skype +skyrocket +skyward +slab +slacked +slacker +slacking +slackness +slacks +slain +slam +slander +slang +slapping +slapstick +slashed +slashing +slate +slather +slaw +sled +sleek +sleep +sleet +sleeve +slept +sliceable +sliced +slicer +slicing +slick +slider +slideshow +sliding +slighted +slighting +slightly +slimness +slimy +slinging +slingshot +slinky +slip +slit +sliver +slobbery +slogan +sloped +sloping +sloppily +sloppy +slot +slouching +slouchy +sludge +slug +slum +slurp +slush +sly +small +smartly +smartness +smasher +smashing +smashup +smell +smelting +smile +smilingly +smirk +smite +smith +smitten +smock +smog +smoked +smokeless +smokiness +smoking +smoky +smolder +smooth +smother +smudge +smudgy +smuggler +smuggling +smugly +smugness +snack +snagged +snaking +snap +snare +snarl +snazzy +sneak +sneer +sneeze +sneezing +snide +sniff +snippet +snipping +snitch +snooper +snooze +snore +snoring +snorkel +snort +snout +snowbird +snowboard +snowbound +snowcap +snowdrift +snowdrop +snowfall +snowfield +snowflake +snowiness +snowless +snowman +snowplow +snowshoe +snowstorm +snowsuit +snowy +snub +snuff +snuggle +snugly +snugness +speak +spearfish +spearhead +spearman +spearmint +species +specimen +specked +speckled +specks +spectacle +spectator +spectrum +speculate +speech +speed +spellbind +speller +spelling +spendable +spender +spending +spent +spew +sphere +spherical +sphinx +spider +spied +spiffy +spill +spilt +spinach +spinal +spindle +spinner +spinning +spinout +spinster +spiny +spiral +spirited +spiritism +spirits +spiritual +splashed +splashing +splashy +splatter +spleen +splendid +splendor +splice +splicing +splinter +splotchy +splurge +spoilage +spoiled +spoiler +spoiling +spoils +spoken +spokesman +sponge +spongy +sponsor +spoof +spookily +spooky +spool +spoon +spore +sporting +sports +sporty +spotless +spotlight +spotted +spotter +spotting +spotty +spousal +spouse +spout +sprain +sprang +sprawl +spray +spree +sprig +spring +sprinkled +sprinkler +sprint +sprite +sprout +spruce +sprung +spry +spud +spur +sputter +spyglass +squabble +squad +squall +squander +squash +squatted +squatter +squatting +squeak +squealer +squealing +squeamish +squeegee +squeeze +squeezing +squid +squiggle +squiggly +squint +squire +squirt +squishier +squishy +stability +stabilize +stable +stack +stadium +staff +stage +staging +stagnant +stagnate +stainable +stained +staining +stainless +stalemate +staleness +stalling +stallion +stamina +stammer +stamp +stand +stank +staple +stapling +starboard +starch +stardom +stardust +starfish +stargazer +staring +stark +starless +starlet +starlight +starlit +starring +starry +starship +starter +starting +startle +startling +startup +starved +starving +stash +state +static +statistic +statue +stature +status +statute +statutory +staunch +stays +steadfast +steadier +steadily +steadying +steam +steed +steep +steerable +steering +steersman +stegosaur +stellar +stem +stench +stencil +step +stereo +sterile +sterility +sterilize +sterling +sternness +sternum +stew +stick +stiffen +stiffly +stiffness +stifle +stifling +stillness +stilt +stimulant +stimulate +stimuli +stimulus +stinger +stingily +stinging +stingray +stingy +stinking +stinky +stipend +stipulate +stir +stitch +stock +stoic +stoke +stole +stomp +stonewall +stoneware +stonework +stoning +stony +stood +stooge +stool +stoop +stoplight +stoppable +stoppage +stopped +stopper +stopping +stopwatch +storable +storage +storeroom +storewide +storm +stout +stove +stowaway +stowing +straddle +straggler +strained +strainer +straining +strangely +stranger +strangle +strategic +strategy +stratus +straw +stray +streak +stream +street +strength +strenuous +strep +stress +stretch +strewn +stricken +strict +stride +strife +strike +striking +strive +striving +strobe +strode +stroller +strongbox +strongly +strongman +struck +structure +strudel +struggle +strum +strung +strut +stubbed +stubble +stubbly +stubborn +stucco +stuck +student +studied +studio +study +stuffed +stuffing +stuffy +stumble +stumbling +stump +stung +stunned +stunner +stunning +stunt +stupor +sturdily +sturdy +styling +stylishly +stylist +stylized +stylus +suave +subarctic +subatomic +subdivide +subdued +subduing +subfloor +subgroup +subheader +subject +sublease +sublet +sublevel +sublime +submarine +submerge +submersed +submitter +subpanel +subpar +subplot +subprime +subscribe +subscript +subsector +subside +subsiding +subsidize +subsidy +subsoil +subsonic +substance +subsystem +subtext +subtitle +subtly +subtotal +subtract +subtype +suburb +subway +subwoofer +subzero +succulent +such +suction +sudden +sudoku +suds +sufferer +suffering +suffice +suffix +suffocate +suffrage +sugar +suggest +suing +suitable +suitably +suitcase +suitor +sulfate +sulfide +sulfite +sulfur +sulk +sullen +sulphate +sulphuric +sultry +superbowl +superglue +superhero +superior +superjet +superman +supermom +supernova +supervise +supper +supplier +supply +support +supremacy +supreme +surcharge +surely +sureness +surface +surfacing +surfboard +surfer +surgery +surgical +surging +surname +surpass +surplus +surprise +surreal +surrender +surrogate +surround +survey +survival +survive +surviving +survivor +sushi +suspect +suspend +suspense +sustained +sustainer +swab +swaddling +swagger +swampland +swan +swapping +swarm +sway +swear +sweat +sweep +swell +swept +swerve +swifter +swiftly +swiftness +swimmable +swimmer +swimming +swimsuit +swimwear +swinger +swinging +swipe +swirl +switch +swivel +swizzle +swooned +swoop +swoosh +swore +sworn +swung +sycamore +sympathy +symphonic +symphony +symptom +synapse +syndrome +synergy +synopses +synopsis +synthesis +synthetic +syrup +system +t-shirt +tabasco +tabby +tableful +tables +tablet +tableware +tabloid +tackiness +tacking +tackle +tackling +tacky +taco +tactful +tactical +tactics +tactile +tactless +tadpole +taekwondo +tag +tainted +take +taking +talcum +talisman +tall +talon +tamale +tameness +tamer +tamper +tank +tanned +tannery +tanning +tantrum +tapeless +tapered +tapering +tapestry +tapioca +tapping +taps +tarantula +target +tarmac +tarnish +tarot +tartar +tartly +tartness +task +tassel +taste +tastiness +tasting +tasty +tattered +tattle +tattling +tattoo +taunt +tavern +thank +that +thaw +theater +theatrics +thee +theft +theme +theology +theorize +thermal +thermos +thesaurus +these +thesis +thespian +thicken +thicket +thickness +thieving +thievish +thigh +thimble +thing +think +thinly +thinner +thinness +thinning +thirstily +thirsting +thirsty +thirteen +thirty +thong +thorn +those +thousand +thrash +thread +threaten +threefold +thrift +thrill +thrive +thriving +throat +throbbing +throng +throttle +throwaway +throwback +thrower +throwing +thud +thumb +thumping +thursday +thus +thwarting +thyself +tiara +tibia +tidal +tidbit +tidiness +tidings +tidy +tiger +tighten +tightly +tightness +tightrope +tightwad +tigress +tile +tiling +till +tilt +timid +timing +timothy +tinderbox +tinfoil +tingle +tingling +tingly +tinker +tinkling +tinsel +tinsmith +tint +tinwork +tiny +tipoff +tipped +tipper +tipping +tiptoeing +tiptop +tiring +tissue +trace +tracing +track +traction +tractor +trade +trading +tradition +traffic +tragedy +trailing +trailside +train +traitor +trance +tranquil +transfer +transform +translate +transpire +transport +transpose +trapdoor +trapeze +trapezoid +trapped +trapper +trapping +traps +trash +travel +traverse +travesty +tray +treachery +treading +treadmill +treason +treat +treble +tree +trekker +tremble +trembling +tremor +trench +trend +trespass +triage +trial +triangle +tribesman +tribunal +tribune +tributary +tribute +triceps +trickery +trickily +tricking +trickle +trickster +tricky +tricolor +tricycle +trident +tried +trifle +trifocals +trillion +trilogy +trimester +trimmer +trimming +trimness +trinity +trio +tripod +tripping +triumph +trivial +trodden +trolling +trombone +trophy +tropical +tropics +trouble +troubling +trough +trousers +trout +trowel +truce +truck +truffle +trump +trunks +trustable +trustee +trustful +trusting +trustless +truth +try +tubby +tubeless +tubular +tucking +tuesday +tug +tuition +tulip +tumble +tumbling +tummy +turban +turbine +turbofan +turbojet +turbulent +turf +turkey +turmoil +turret +turtle +tusk +tutor +tutu +tux +tweak +tweed +tweet +tweezers +twelve +twentieth +twenty +twerp +twice +twiddle +twiddling +twig +twilight +twine +twins +twirl +twistable +twisted +twister +twisting +twisty +twitch +twitter +tycoon +tying +tyke +udder +ultimate +ultimatum +ultra +umbilical +umbrella +umpire +unabashed +unable +unadorned +unadvised +unafraid +unaired +unaligned +unaltered +unarmored +unashamed +unaudited +unawake +unaware +unbaked +unbalance +unbeaten +unbend +unbent +unbiased +unbitten +unblended +unblessed +unblock +unbolted +unbounded +unboxed +unbraided +unbridle +unbroken +unbuckled +unbundle +unburned +unbutton +uncanny +uncapped +uncaring +uncertain +unchain +unchanged +uncharted +uncheck +uncivil +unclad +unclaimed +unclamped +unclasp +uncle +unclip +uncloak +unclog +unclothed +uncoated +uncoiled +uncolored +uncombed +uncommon +uncooked +uncork +uncorrupt +uncounted +uncouple +uncouth +uncover +uncross +uncrown +uncrushed +uncured +uncurious +uncurled +uncut +undamaged +undated +undaunted +undead +undecided +undefined +underage +underarm +undercoat +undercook +undercut +underdog +underdone +underfed +underfeed +underfoot +undergo +undergrad +underhand +underline +underling +undermine +undermost +underpaid +underpass +underpay +underrate +undertake +undertone +undertook +undertow +underuse +underwear +underwent +underwire +undesired +undiluted +undivided +undocked +undoing +undone +undrafted +undress +undrilled +undusted +undying +unearned +unearth +unease +uneasily +uneasy +uneatable +uneaten +unedited +unelected +unending +unengaged +unenvied +unequal +unethical +uneven +unexpired +unexposed +unfailing +unfair +unfasten +unfazed +unfeeling +unfiled +unfilled +unfitted +unfitting +unfixable +unfixed +unflawed +unfocused +unfold +unfounded +unframed +unfreeze +unfrosted +unfrozen +unfunded +unglazed +ungloved +unglue +ungodly +ungraded +ungreased +unguarded +unguided +unhappily +unhappy +unharmed +unhealthy +unheard +unhearing +unheated +unhelpful +unhidden +unhinge +unhitched +unholy +unhook +unicorn +unicycle +unified +unifier +uniformed +uniformly +unify +unimpeded +uninjured +uninstall +uninsured +uninvited +union +uniquely +unisexual +unison +unissued +unit +universal +universe +unjustly +unkempt +unkind +unknotted +unknowing +unknown +unlaced +unlatch +unlawful +unleaded +unlearned +unleash +unless +unleveled +unlighted +unlikable +unlimited +unlined +unlinked +unlisted +unlit +unlivable +unloaded +unloader +unlocked +unlocking +unlovable +unloved +unlovely +unloving +unluckily +unlucky +unmade +unmanaged +unmanned +unmapped +unmarked +unmasked +unmasking +unmatched +unmindful +unmixable +unmixed +unmolded +unmoral +unmovable +unmoved +unmoving +unnamable +unnamed +unnatural +unneeded +unnerve +unnerving +unnoticed +unopened +unopposed +unpack +unpadded +unpaid +unpainted +unpaired +unpaved +unpeeled +unpicked +unpiloted +unpinned +unplanned +unplanted +unpleased +unpledged +unplowed +unplug +unpopular +unproven +unquote +unranked +unrated +unraveled +unreached +unread +unreal +unreeling +unrefined +unrelated +unrented +unrest +unretired +unrevised +unrigged +unripe +unrivaled +unroasted +unrobed +unroll +unruffled +unruly +unrushed +unsaddle +unsafe +unsaid +unsalted +unsaved +unsavory +unscathed +unscented +unscrew +unsealed +unseated +unsecured +unseeing +unseemly +unseen +unselect +unselfish +unsent +unsettled +unshackle +unshaken +unshaved +unshaven +unsheathe +unshipped +unsightly +unsigned +unskilled +unsliced +unsmooth +unsnap +unsocial +unsoiled +unsold +unsolved +unsorted +unspoiled +unspoken +unstable +unstaffed +unstamped +unsteady +unsterile +unstirred +unstitch +unstopped +unstuck +unstuffed +unstylish +unsubtle +unsubtly +unsuited +unsure +unsworn +untagged +untainted +untaken +untamed +untangled +untapped +untaxed +unthawed +unthread +untidy +untie +until +untimed +untimely +untitled +untoasted +untold +untouched +untracked +untrained +untreated +untried +untrimmed +untrue +untruth +unturned +untwist +untying +unusable +unused +unusual +unvalued +unvaried +unvarying +unveiled +unveiling +unvented +unviable +unvisited +unvocal +unwanted +unwarlike +unwary +unwashed +unwatched +unweave +unwed +unwelcome +unwell +unwieldy +unwilling +unwind +unwired +unwitting +unwomanly +unworldly +unworn +unworried +unworthy +unwound +unwoven +unwrapped +unwritten +unzip +upbeat +upchuck +upcoming +upcountry +update +upfront +upgrade +upheaval +upheld +uphill +uphold +uplifted +uplifting +upload +upon +upper +upright +uprising +upriver +uproar +uproot +upscale +upside +upstage +upstairs +upstart +upstate +upstream +upstroke +upswing +uptake +uptight +uptown +upturned +upward +upwind +uranium +urban +urchin +urethane +urgency +urgent +urging +urologist +urology +usable +usage +useable +used +uselessly +user +usher +usual +utensil +utility +utilize +utmost +utopia +utter +vacancy +vacant +vacate +vacation +vagabond +vagrancy +vagrantly +vaguely +vagueness +valiant +valid +valium +valley +valuables +value +vanilla +vanish +vanity +vanquish +vantage +vaporizer +variable +variably +varied +variety +various +varmint +varnish +varsity +varying +vascular +vaseline +vastly +vastness +veal +vegan +veggie +vehicular +velcro +velocity +velvet +vendetta +vending +vendor +veneering +vengeful +venomous +ventricle +venture +venue +venus +verbalize +verbally +verbose +verdict +verify +verse +version +versus +vertebrae +vertical +vertigo +very +vessel +vest +veteran +veto +vexingly +viability +viable +vibes +vice +vicinity +victory +video +viewable +viewer +viewing +viewless +viewpoint +vigorous +village +villain +vindicate +vineyard +vintage +violate +violation +violator +violet +violin +viper +viral +virtual +virtuous +virus +visa +viscosity +viscous +viselike +visible +visibly +vision +visiting +visitor +visor +vista +vitality +vitalize +vitally +vitamins +vivacious +vividly +vividness +vixen +vocalist +vocalize +vocally +vocation +voice +voicing +void +volatile +volley +voltage +volumes +voter +voting +voucher +vowed +vowel +voyage +wackiness +wad +wafer +waffle +waged +wager +wages +waggle +wagon +wake +waking +walk +walmart +walnut +walrus +waltz +wand +wannabe +wanted +wanting +wasabi +washable +washbasin +washboard +washbowl +washcloth +washday +washed +washer +washhouse +washing +washout +washroom +washstand +washtub +wasp +wasting +watch +water +waviness +waving +wavy +whacking +whacky +wham +wharf +wheat +whenever +whiff +whimsical +whinny +whiny +whisking +whoever +whole +whomever +whoopee +whooping +whoops +why +wick +widely +widen +widget +widow +width +wieldable +wielder +wife +wifi +wikipedia +wildcard +wildcat +wilder +wildfire +wildfowl +wildland +wildlife +wildly +wildness +willed +willfully +willing +willow +willpower +wilt +wimp +wince +wincing +wind +wing +winking +winner +winnings +winter +wipe +wired +wireless +wiring +wiry +wisdom +wise +wish +wisplike +wispy +wistful +wizard +wobble +wobbling +wobbly +wok +wolf +wolverine +womanhood +womankind +womanless +womanlike +womanly +womb +woof +wooing +wool +woozy +word +work +worried +worrier +worrisome +worry +worsening +worshiper +worst +wound +woven +wow +wrangle +wrath +wreath +wreckage +wrecker +wrecking +wrench +wriggle +wriggly +wrinkle +wrinkly +wrist +writing +written +wrongdoer +wronged +wrongful +wrongly +wrongness +wrought +xbox +xerox +yahoo +yam +yanking +yapping +yard +yarn +yeah +yearbook +yearling +yearly +yearning +yeast +yelling +yelp +yen +yesterday +yiddish +yield +yin +yippee +yo-yo +yodel +yoga +yogurt +yonder +yoyo +yummy +zap +zealous +zebra +zen +zeppelin +zero +zestfully +zesty +zigzagged +zipfile +zipping +zippy +zips +zit +zodiac +zombie +zone +zoning +zookeeper +zoologist +zoology +zoom diff --git a/js/package.json b/js/package.json index 8829b6f8b..59b75c591 100644 --- a/js/package.json +++ b/js/package.json @@ -1,6 +1,6 @@ { "name": "parity.js", - "version": "0.2.43", + "version": "0.2.49", "main": "release/index.js", "jsnext:main": "src/index.js", "author": "Parity Team ", diff --git a/js/src/abi/util/pad.js b/js/src/abi/util/pad.js index a7d940431..5a6751a4f 100644 --- a/js/src/abi/util/pad.js +++ b/js/src/abi/util/pad.js @@ -46,7 +46,8 @@ function stringToBytes (input) { if (isArray(input)) { return input; } else if (input.substr(0, 2) === '0x') { - return input.substr(2).toLowerCase().match(/.{1,2}/g).map((value) => parseInt(value, 16)); + const matches = input.substr(2).toLowerCase().match(/.{1,2}/g) || []; + return matches.map((value) => parseInt(value, 16)); } else { return input.split('').map((char) => char.charCodeAt(0)); } diff --git a/js/src/api/contract/contract.js b/js/src/api/contract/contract.js index 8d556a118..06afb0d9d 100644 --- a/js/src/api/contract/contract.js +++ b/js/src/api/contract/contract.js @@ -40,9 +40,12 @@ export default class Contract { this._events.forEach((evt) => { this._instance[evt.name] = evt; + this._instance[evt.signature] = evt; }); + this._functions.forEach((fn) => { this._instance[fn.name] = fn; + this._instance[fn.signature] = fn; }); this._sendSubscriptionChanges(); diff --git a/js/src/api/contract/contract.spec.js b/js/src/api/contract/contract.spec.js index 3d57c2afa..9c08024a9 100644 --- a/js/src/api/contract/contract.spec.js +++ b/js/src/api/contract/contract.spec.js @@ -20,6 +20,7 @@ import sinon from 'sinon'; import { TEST_HTTP_URL, mockHttp } from '../../../test/mockRpc'; import Abi from '../../abi'; +import { sha3 } from '../util/sha3'; import Api from '../api'; import Contract from './contract'; @@ -113,7 +114,13 @@ describe('api/contract/Contract', () => { ]); contract.at('6789'); - expect(Object.keys(contract.instance)).to.deep.equal(['Drained', 'balanceOf', 'address']); + expect(Object.keys(contract.instance)).to.deep.equal([ + 'Drained', + /^(?:0x)(.+)$/.exec(sha3('Drained(uint256)'))[1], + 'balanceOf', + /^(?:0x)(.+)$/.exec(sha3('balanceOf(address)'))[1].substr(0, 8), + 'address' + ]); expect(contract.address).to.equal('6789'); }); }); diff --git a/js/src/api/util/format.js b/js/src/api/util/format.js index 1b68e1138..198e456ee 100644 --- a/js/src/api/util/format.js +++ b/js/src/api/util/format.js @@ -17,3 +17,15 @@ export function bytesToHex (bytes) { return '0x' + bytes.map((b) => ('0' + b.toString(16)).slice(-2)).join(''); } + +export function hex2Ascii (_hex) { + const hex = /^(?:0x)?(.*)$/.exec(_hex.toString())[1]; + + let str = ''; + + for (let i = 0; i < hex.length; i += 2) { + str += String.fromCharCode(parseInt(hex.substr(i, 2), 16)); + } + + return str; +} diff --git a/js/src/api/util/index.js b/js/src/api/util/index.js index fb0f79076..55cf008c5 100644 --- a/js/src/api/util/index.js +++ b/js/src/api/util/index.js @@ -16,7 +16,7 @@ import { isAddress as isAddressValid, toChecksumAddress } from '../../abi/util/address'; import { decodeCallData, decodeMethodInput, methodToAbi } from './decode'; -import { bytesToHex } from './format'; +import { bytesToHex, hex2Ascii } from './format'; import { fromWei, toWei } from './wei'; import { sha3 } from './sha3'; import { isArray, isFunction, isHex, isInstanceOf, isString } from './types'; @@ -30,6 +30,7 @@ export default { isInstanceOf, isString, bytesToHex, + hex2Ascii, createIdentityImg, decodeCallData, decodeMethodInput, diff --git a/js/src/contracts/contracts.js b/js/src/contracts/contracts.js index c9d1c2390..a04321c7b 100644 --- a/js/src/contracts/contracts.js +++ b/js/src/contracts/contracts.js @@ -18,6 +18,7 @@ import DappReg from './dappreg'; import Registry from './registry'; import SignatureReg from './signaturereg'; import TokenReg from './tokenreg'; +import GithubHint from './githubhint'; let instance = null; @@ -30,6 +31,7 @@ export default class Contracts { this._dappreg = new DappReg(api, this._registry); this._signaturereg = new SignatureReg(api, this._registry); this._tokenreg = new TokenReg(api, this._registry); + this._githubhint = new GithubHint(api, this._registry); } get registry () { @@ -48,6 +50,10 @@ export default class Contracts { return this._tokenreg; } + get githubHint () { + return this._githubhint; + } + static create (api) { return new Contracts(api); } diff --git a/js/src/contracts/githubhint.js b/js/src/contracts/githubhint.js new file mode 100644 index 000000000..47d7eca6e --- /dev/null +++ b/js/src/contracts/githubhint.js @@ -0,0 +1,32 @@ +// Copyright 2015, 2016 Ethcore (UK) Ltd. +// This file is part of Parity. + +// Parity is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. + +// Parity is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. + +// You should have received a copy of the GNU General Public License +// along with Parity. If not, see . + +export default class GithubHint { + constructor (api, registry) { + this._api = api; + this._registry = registry; + + this.getInstance(); + } + + getContract () { + return this._registry.getContract('githubhint'); + } + + getInstance () { + return this.getContract().instance; + } +} diff --git a/js/src/contracts/registry.js b/js/src/contracts/registry.js index 9853c0df9..d52b20718 100644 --- a/js/src/contracts/registry.js +++ b/js/src/contracts/registry.js @@ -42,7 +42,7 @@ export default class Registry { }); } - getContractInstance (_name) { + getContract (_name) { const name = _name.toLowerCase(); return new Promise((resolve, reject) => { @@ -54,13 +54,19 @@ export default class Registry { this .lookupAddress(name) .then((address) => { - this._contracts[name] = this._api.newContract(abis[name], address).instance; + this._contracts[name] = this._api.newContract(abis[name], address); resolve(this._contracts[name]); }) .catch(reject); }); } + getContractInstance (_name) { + return this + .getContract(_name) + .then((contract) => contract.instance); + } + lookupAddress (_name) { const name = _name.toLowerCase(); const sha3 = this._api.util.sha3(name); diff --git a/js/src/contracts/tokenreg.js b/js/src/contracts/tokenreg.js index 78bd5e4d9..5e317880b 100644 --- a/js/src/contracts/tokenreg.js +++ b/js/src/contracts/tokenreg.js @@ -22,8 +22,12 @@ export default class TokenReg { this.getInstance(); } + getContract () { + return this._registry.getContract('tokenreg'); + } + getInstance () { - return this._registry.getContractInstance('tokenreg'); + return this.getContract().instance; } tokenCount () { diff --git a/js/src/dapps/basiccoin/Deploy/Event/event.css b/js/src/dapps/basiccoin/Deploy/Event/event.css index 52eada915..40768f6dc 100644 --- a/js/src/dapps/basiccoin/Deploy/Event/event.css +++ b/js/src/dapps/basiccoin/Deploy/Event/event.css @@ -46,11 +46,22 @@ a.link, a.link:hover, a.link:visited { } .address { + max-width: 250px; text-align: left; + + div { + white-space: nowrap; + overflow: hidden; + text-overflow: ellipsis; + } } .description { text-align: left; + + div { + white-space: nowrap; + } } .center { diff --git a/js/src/dapps/basiccoin/Deploy/Event/event.js b/js/src/dapps/basiccoin/Deploy/Event/event.js index 889822208..b32795f7e 100644 --- a/js/src/dapps/basiccoin/Deploy/Event/event.js +++ b/js/src/dapps/basiccoin/Deploy/Event/event.js @@ -58,6 +58,7 @@ export default class Event extends Component {
{ isPending ? '' : coin.tla }
{ isPending ? '' : coin.name }
+
{ this.renderAddress(event.params.coin) }
{ this.renderAddress(event.params.owner) } diff --git a/js/src/dapps/basiccoin/Overview/Owner/owner.css b/js/src/dapps/basiccoin/Overview/Owner/owner.css index 13e89d061..f94945722 100644 --- a/js/src/dapps/basiccoin/Overview/Owner/owner.css +++ b/js/src/dapps/basiccoin/Overview/Owner/owner.css @@ -46,3 +46,9 @@ .icon { margin: 0 0 -4px 1em; } + +.byline { + opacity: 0.75; + font-size: 0.75em; + padding-top: 0.25em; +} diff --git a/js/src/dapps/basiccoin/Overview/Owner/owner.js b/js/src/dapps/basiccoin/Overview/Owner/owner.js index cc3003693..a86a27544 100644 --- a/js/src/dapps/basiccoin/Overview/Owner/owner.js +++ b/js/src/dapps/basiccoin/Overview/Owner/owner.js @@ -68,6 +68,9 @@ export default class Owner extends Component { +
+ { token.address } +
)); } diff --git a/js/src/dapps/tokenreg/Accounts/actions.js b/js/src/dapps/tokenreg/Accounts/actions.js index a310baf7d..5f92280be 100644 --- a/js/src/dapps/tokenreg/Accounts/actions.js +++ b/js/src/dapps/tokenreg/Accounts/actions.js @@ -46,8 +46,6 @@ export const loadAccounts = () => (dispatch) => { address })); - console.log('accounts', accountsList); - dispatch(setAccounts(accountsList)); dispatch(setAccountsInfo(accountsInfo)); dispatch(setSelectedAccount(accountsList[0].address)); diff --git a/js/src/dapps/tokenreg/Actions/Query/query.js b/js/src/dapps/tokenreg/Actions/Query/query.js index 16d13f2f0..5a3c7d5f6 100644 --- a/js/src/dapps/tokenreg/Actions/Query/query.js +++ b/js/src/dapps/tokenreg/Actions/Query/query.js @@ -42,12 +42,9 @@ export default class QueryAction extends Component { onClose: PropTypes.func.isRequired, handleQueryToken: PropTypes.func.isRequired, - handleQueryMetaLookup: PropTypes.func.isRequired, data: PropTypes.object, - notFound: PropTypes.bool, - metaLoading: PropTypes.bool, - metaData: PropTypes.object + notFound: PropTypes.bool } state = initState; @@ -131,11 +128,8 @@ export default class QueryAction extends Component { return ( + tla={ data.tla } + /> ); } diff --git a/js/src/dapps/tokenreg/Actions/actions.js b/js/src/dapps/tokenreg/Actions/actions.js index 1c6703f77..df5b41e6b 100644 --- a/js/src/dapps/tokenreg/Actions/actions.js +++ b/js/src/dapps/tokenreg/Actions/actions.js @@ -16,8 +16,6 @@ import { getTokenTotalSupply } from '../utils'; -const { sha3, bytesToHex } = window.parity.api.util; - export const SET_REGISTER_SENDING = 'SET_REGISTER_SENDING'; export const setRegisterSending = (isSending) => ({ type: SET_REGISTER_SENDING, @@ -41,8 +39,6 @@ export const registerCompleted = () => ({ }); export const registerToken = (tokenData) => (dispatch, getState) => { - console.log('registering token', tokenData); - const state = getState(); const contractInstance = state.status.contract.instance; const fee = state.status.contract.fee; @@ -83,8 +79,6 @@ export const registerToken = (tokenData) => (dispatch, getState) => { }) .then((gasEstimate) => { options.gas = gasEstimate.mul(1.2).toFixed(0); - console.log(`transfer: gas estimated as ${gasEstimate.toFixed(0)} setting to ${options.gas}`); - return contractInstance.register.postTransaction(options, values); }) .then((result) => { @@ -183,34 +177,3 @@ export const queryToken = (key, query) => (dispatch, getState) => { dispatch(setQueryLoading(false)); }); }; - -export const queryTokenMeta = (id, query) => (dispatch, getState) => { - console.log('loading token meta', query); - - const state = getState(); - const contractInstance = state.status.contract.instance; - - const key = sha3(query); - - const startDate = Date.now(); - dispatch(setQueryMetaLoading(true)); - - contractInstance - .meta - .call({}, [ id, key ]) - .then((value) => { - const meta = { - key, query, - value: value.find(v => v !== 0) ? bytesToHex(value) : null - }; - - dispatch(setQueryMeta(meta)); - - setTimeout(() => { - dispatch(setQueryMetaLoading(false)); - }, 500 - (Date.now() - startDate)); - }) - .catch((e) => { - console.error('load meta query error', e); - }); -}; diff --git a/js/src/dapps/tokenreg/Actions/component.js b/js/src/dapps/tokenreg/Actions/component.js index 3e7ef0d64..43acc27ab 100644 --- a/js/src/dapps/tokenreg/Actions/component.js +++ b/js/src/dapps/tokenreg/Actions/component.js @@ -37,7 +37,6 @@ export default class Actions extends Component { handleQueryToken: PropTypes.func.isRequired, handleQueryClose: PropTypes.func.isRequired, - handleQueryMetaLookup: PropTypes.func.isRequired, query: PropTypes.object.isRequired }; @@ -82,7 +81,6 @@ export default class Actions extends Component { show={ this.state.show[ QUERY_ACTION ] } onClose={ this.onQueryClose } handleQueryToken={ this.props.handleQueryToken } - handleQueryMetaLookup={ this.props.handleQueryMetaLookup } { ...this.props.query } /> ); diff --git a/js/src/dapps/tokenreg/Actions/container.js b/js/src/dapps/tokenreg/Actions/container.js index 2c3773122..1d3d8fe31 100644 --- a/js/src/dapps/tokenreg/Actions/container.js +++ b/js/src/dapps/tokenreg/Actions/container.js @@ -19,7 +19,7 @@ import { connect } from 'react-redux'; import Actions from './component'; -import { registerToken, registerReset, queryToken, queryReset, queryTokenMeta } from './actions'; +import { registerToken, registerReset, queryToken, queryReset } from './actions'; class TokensContainer extends Component { @@ -49,9 +49,6 @@ const mapDispatchToProps = (dispatch) => { }, handleQueryClose: () => { dispatch(queryReset()); - }, - handleQueryMetaLookup: (id, query) => { - dispatch(queryTokenMeta(id, query)); } }; }; diff --git a/js/src/dapps/tokenreg/Application/application.css b/js/src/dapps/tokenreg/Application/application.css index 033147ae3..94ca6302e 100644 --- a/js/src/dapps/tokenreg/Application/application.css +++ b/js/src/dapps/tokenreg/Application/application.css @@ -19,6 +19,7 @@ display: flex; flex-direction: column; align-items: center; + padding-bottom: 10em; } .warning { diff --git a/js/src/dapps/tokenreg/Status/actions.js b/js/src/dapps/tokenreg/Status/actions.js index e9e217d6a..b07949a28 100644 --- a/js/src/dapps/tokenreg/Status/actions.js +++ b/js/src/dapps/tokenreg/Status/actions.js @@ -14,11 +14,7 @@ // You should have received a copy of the GNU General Public License // along with Parity. If not, see . -import { - registry as registryAbi, - tokenreg as tokenregAbi, - githubhint as githubhintAbi -} from '../../../contracts/abi'; +import Contracts from '../../../contracts'; import { loadToken, setTokenPending, deleteToken, setTokenData } from '../Tokens/actions'; @@ -34,43 +30,31 @@ export const FIND_CONTRACT = 'FIND_CONTRACT'; export const loadContract = () => (dispatch) => { dispatch(setLoading(true)); - api.parity - .registryAddress() - .then((registryAddress) => { - console.log(`registry found at ${registryAddress}`); - const registry = api.newContract(registryAbi, registryAddress).instance; - - return Promise.all([ - registry.getAddress.call({}, [api.util.sha3('tokenreg'), 'A']), - registry.getAddress.call({}, [api.util.sha3('githubhint'), 'A']) - ]); - }) - .then(([ tokenregAddress, githubhintAddress ]) => { - console.log(`tokenreg was found at ${tokenregAddress}`); - - const tokenregContract = api - .newContract(tokenregAbi, tokenregAddress); - - const githubhintContract = api - .newContract(githubhintAbi, githubhintAddress); + const { tokenReg, githubHint } = new Contracts(api); + return Promise + .all([ + tokenReg.getContract(), + githubHint.getContract() + ]) + .then(([ tokenRegContract, githubHintContract ]) => { dispatch(setContractDetails({ - address: tokenregAddress, - instance: tokenregContract.instance, - raw: tokenregContract + address: tokenRegContract.address, + instance: tokenRegContract.instance, + raw: tokenRegContract })); dispatch(setGithubhintDetails({ - address: githubhintAddress, - instance: githubhintContract.instance, - raw: githubhintContract + address: githubHintContract.address, + instance: githubHintContract.instance, + raw: githubHintContract })); dispatch(loadContractDetails()); dispatch(subscribeEvents()); }) .catch((error) => { - console.error('loadContract error', error); + throw error; }); }; @@ -78,7 +62,7 @@ export const LOAD_CONTRACT_DETAILS = 'LOAD_CONTRACT_DETAILS'; export const loadContractDetails = () => (dispatch, getState) => { const state = getState(); - const instance = state.status.contract.instance; + const { instance } = state.status.contract; Promise .all([ @@ -87,8 +71,6 @@ export const loadContractDetails = () => (dispatch, getState) => { instance.fee.call() ]) .then(([accounts, owner, fee]) => { - console.log(`owner as ${owner}, fee set at ${fee.toFormat()}`); - const isOwner = accounts.filter(a => a === owner).length > 0; dispatch(setContractDetails({ @@ -119,14 +101,14 @@ export const setGithubhintDetails = (details) => ({ export const subscribeEvents = () => (dispatch, getState) => { const state = getState(); - const contract = state.status.contract.raw; + const { raw } = state.status.contract; const previousSubscriptionId = state.status.subscriptionId; if (previousSubscriptionId) { - contract.unsubscribe(previousSubscriptionId); + raw.unsubscribe(previousSubscriptionId); } - contract + raw .subscribe(null, { fromBlock: 'latest', toBlock: 'pending', @@ -187,7 +169,7 @@ export const subscribeEvents = () => (dispatch, getState) => { )); } - console.log('new log event', log); + console.warn('unknown log event', log); }); }) .then((subscriptionId) => { diff --git a/js/src/dapps/tokenreg/Status/reducer.js b/js/src/dapps/tokenreg/Status/reducer.js index 7b018bd85..aee16fbe7 100644 --- a/js/src/dapps/tokenreg/Status/reducer.js +++ b/js/src/dapps/tokenreg/Status/reducer.js @@ -25,17 +25,15 @@ const initialState = { isLoading: true, subscriptionId: null, contract: { - addres: null, + address: null, instance: null, - raw: null, owner: null, isOwner: false, fee: null }, githubhint: { address: null, - instance: null, - raw: null + instance: null } }; diff --git a/js/src/dapps/tokenreg/Tokens/Token/index.js b/js/src/dapps/tokenreg/Tokens/Token/index.js index 4b822b4bd..30ad8896f 100644 --- a/js/src/dapps/tokenreg/Tokens/Token/index.js +++ b/js/src/dapps/tokenreg/Tokens/Token/index.js @@ -14,4 +14,4 @@ // You should have received a copy of the GNU General Public License // along with Parity. If not, see . -export default from './token'; +export default from './tokenContainer'; diff --git a/js/src/dapps/tokenreg/Tokens/Token/token.js b/js/src/dapps/tokenreg/Tokens/Token/token.js index 660b21b97..be14cec84 100644 --- a/js/src/dapps/tokenreg/Tokens/Token/token.js +++ b/js/src/dapps/tokenreg/Tokens/Token/token.js @@ -57,15 +57,28 @@ export default class Token extends Component { isLoading: PropTypes.bool, isPending: PropTypes.bool, isTokenOwner: PropTypes.bool.isRequired, - isContractOwner: PropTypes.bool.isRequired, + isContractOwner: PropTypes.bool, fullWidth: PropTypes.bool }; - state = { - metaKeyIndex: 0 + static defaultProps = { + isContractOwner: false }; + state = { + metaKeyIndex: 0, + showMeta: false + }; + + shouldComponentUpdate (nextProps) { + if (nextProps.isLoading && this.props.isLoading) { + return false; + } + + return true; + } + render () { const { isLoading, fullWidth } = this.props; @@ -237,7 +250,12 @@ export default class Token extends Component { } renderMeta (meta) { - const isMetaLoading = this.props.isMetaLoading; + const { isMetaLoading } = this.props; + const { showMeta } = this.state; + + if (!showMeta) { + return null; + } if (isMetaLoading) { return (
@@ -331,6 +349,7 @@ export default class Token extends Component { const key = metaDataKeys[keyIndex].value; const index = this.props.index; + this.setState({ showMeta: true }); this.props.handleMetaLookup(index, key); } diff --git a/js/src/dapps/tokenreg/Tokens/Token/tokenContainer.js b/js/src/dapps/tokenreg/Tokens/Token/tokenContainer.js new file mode 100644 index 000000000..7351da524 --- /dev/null +++ b/js/src/dapps/tokenreg/Tokens/Token/tokenContainer.js @@ -0,0 +1,73 @@ +// Copyright 2015, 2016 Ethcore (UK) Ltd. +// This file is part of Parity. + +// Parity is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. + +// Parity is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. + +// You should have received a copy of the GNU General Public License +// along with Parity. If not, see . + +import React, { Component, PropTypes } from 'react'; +import { connect } from 'react-redux'; + +import Token from './token'; + +import { queryTokenMeta, unregisterToken, addTokenMeta } from '../actions'; + +class TokenContainer extends Component { + static propTypes = { + handleMetaLookup: PropTypes.func.isRequired, + handleUnregister: PropTypes.func.isRequired, + handleAddMeta: PropTypes.func.isRequired, + + tla: PropTypes.string.isRequired + }; + + render () { + return ( + + ); + } +} + +const mapStateToProps = (_, initProps) => { + const { tla } = initProps; + + return (state) => { + const { isOwner } = state.status.contract; + const { tokens } = state.tokens; + const token = tokens.find((t) => t.tla === tla); + + return { ...token, isContractOwner: isOwner }; + }; +}; + +const mapDispatchToProps = (dispatch) => { + return { + handleMetaLookup: (index, query) => { + dispatch(queryTokenMeta(index, query)); + }, + + handleUnregister: (index) => { + dispatch(unregisterToken(index)); + }, + + handleAddMeta: (index, key, value) => { + dispatch(addTokenMeta(index, key, value)); + } + }; +}; + +export default connect( + mapStateToProps, + mapDispatchToProps +)(TokenContainer); diff --git a/js/src/dapps/tokenreg/Tokens/actions.js b/js/src/dapps/tokenreg/Tokens/actions.js index 7953bb241..d1e13c1dc 100644 --- a/js/src/dapps/tokenreg/Tokens/actions.js +++ b/js/src/dapps/tokenreg/Tokens/actions.js @@ -67,8 +67,6 @@ export const deleteToken = (index) => ({ }); export const loadTokens = () => (dispatch, getState) => { - console.log('loading tokens...'); - const state = getState(); const contractInstance = state.status.contract.instance; @@ -79,7 +77,6 @@ export const loadTokens = () => (dispatch, getState) => { .call() .then((count) => { const tokenCount = parseInt(count); - console.log(`token count: ${tokenCount}`); dispatch(setTokenCount(tokenCount)); for (let i = 0; i < tokenCount; i++) { @@ -94,8 +91,6 @@ export const loadTokens = () => (dispatch, getState) => { }; export const loadToken = (index) => (dispatch, getState) => { - console.log('loading token', index); - const state = getState(); const contractInstance = state.status.contract.instance; @@ -144,7 +139,7 @@ export const loadToken = (index) => (dispatch, getState) => { } data.totalSupply = data.totalSupply.toNumber(); - console.log(`token loaded: #${index}`, data); + dispatch(setTokenData(index, data)); dispatch(setTokenLoading(index, false)); }) @@ -159,8 +154,6 @@ export const loadToken = (index) => (dispatch, getState) => { }; export const queryTokenMeta = (index, query) => (dispatch, getState) => { - console.log('loading token meta', index, query); - const state = getState(); const contractInstance = state.status.contract.instance; @@ -176,7 +169,6 @@ export const queryTokenMeta = (index, query) => (dispatch, getState) => { value: value.find(v => v !== 0) ? bytesToHex(value) : null }; - console.log(`token meta loaded: #${index}`, value); dispatch(setTokenMeta(index, meta)); setTimeout(() => { @@ -189,8 +181,6 @@ export const queryTokenMeta = (index, query) => (dispatch, getState) => { }; export const addTokenMeta = (index, key, value) => (dispatch, getState) => { - console.log('add token meta', index, key, value); - const state = getState(); const contractInstance = state.status.contract.instance; const token = state.tokens.tokens.find(t => t.index === index); @@ -203,8 +193,6 @@ export const addTokenMeta = (index, key, value) => (dispatch, getState) => { .estimateGas(options, values) .then((gasEstimate) => { options.gas = gasEstimate.mul(1.2).toFixed(0); - console.log(`addTokenMeta: gas estimated as ${gasEstimate.toFixed(0)} setting to ${options.gas}`); - return contractInstance.setMeta.postTransaction(options, values); }) .catch((e) => { @@ -213,8 +201,6 @@ export const addTokenMeta = (index, key, value) => (dispatch, getState) => { }; export const addGithubhintURL = (from, key, url) => (dispatch, getState) => { - console.log('add githubhint url', key, url); - const state = getState(); const contractInstance = state.status.githubhint.instance; @@ -227,8 +213,6 @@ export const addGithubhintURL = (from, key, url) => (dispatch, getState) => { .estimateGas(options, values) .then((gasEstimate) => { options.gas = gasEstimate.mul(1.2).toFixed(0); - console.log(`transfer: gas estimated as ${gasEstimate.toFixed(0)} setting to ${options.gas}`); - return contractInstance.hintURL.postTransaction(options, values); }) .catch((e) => { @@ -237,24 +221,20 @@ export const addGithubhintURL = (from, key, url) => (dispatch, getState) => { }; export const unregisterToken = (index) => (dispatch, getState) => { - console.log('unregistering token', index); - - const state = getState(); - const contractInstance = state.status.contract.instance; + const { contract } = getState().status; + const { instance, owner } = contract; const values = [ index ]; const options = { - from: state.accounts.selected.address + from: owner }; - contractInstance + instance .unregister .estimateGas(options, values) .then((gasEstimate) => { options.gas = gasEstimate.mul(1.2).toFixed(0); - console.log(`transfer: gas estimated as ${gasEstimate.toFixed(0)} setting to ${options.gas}`); - - return contractInstance.unregister.postTransaction(options, values); + return instance.unregister.postTransaction(options, values); }) .catch((e) => { console.error(`unregisterToken #${index} error`, e); diff --git a/js/src/dapps/tokenreg/Tokens/container.js b/js/src/dapps/tokenreg/Tokens/container.js index b6171c2cc..33b2de659 100644 --- a/js/src/dapps/tokenreg/Tokens/container.js +++ b/js/src/dapps/tokenreg/Tokens/container.js @@ -19,16 +19,13 @@ import { connect } from 'react-redux'; import Tokens from './tokens'; -import { loadTokens, queryTokenMeta, unregisterToken, addTokenMeta } from './actions'; +import { loadTokens } from './actions'; class TokensContainer extends Component { static propTypes = { - isOwner: PropTypes.bool, isLoading: PropTypes.bool, tokens: PropTypes.array, - tokenCount: PropTypes.number, - onLoadTokens: PropTypes.func, - accounts: PropTypes.array + onLoadTokens: PropTypes.func }; componentDidMount () { @@ -36,7 +33,6 @@ class TokensContainer extends Component { } render () { - console.log(this.props); return ( { - const { list } = state.accounts; - const { isLoading, tokens, tokenCount } = state.tokens; + const { isLoading, tokens } = state.tokens; - const { isOwner } = state.status.contract; + const filteredTokens = tokens + .filter((token) => token && token.tla) + .map((token) => ({ tla: token.tla, owner: token.owner })); - return { isLoading, tokens, tokenCount, isOwner, accounts: list }; + return { isLoading, tokens: filteredTokens }; }; const mapDispatchToProps = (dispatch) => { return { onLoadTokens: () => { dispatch(loadTokens()); - }, - - handleMetaLookup: (index, query) => { - dispatch(queryTokenMeta(index, query)); - }, - - handleUnregister: (index) => { - dispatch(unregisterToken(index)); - }, - - handleAddMeta: (index, key, value) => { - dispatch(addTokenMeta(index, key, value)); } }; }; diff --git a/js/src/dapps/tokenreg/Tokens/tokens.js b/js/src/dapps/tokenreg/Tokens/tokens.js index 43766a8a8..48bc88a74 100644 --- a/js/src/dapps/tokenreg/Tokens/tokens.js +++ b/js/src/dapps/tokenreg/Tokens/tokens.js @@ -23,13 +23,8 @@ import styles from './tokens.css'; export default class Tokens extends Component { static propTypes = { - handleAddMeta: PropTypes.func.isRequired, - handleUnregister: PropTypes.func.isRequired, - handleMetaLookup: PropTypes.func.isRequired, - isOwner: PropTypes.bool.isRequired, isLoading: PropTypes.bool.isRequired, - tokens: PropTypes.array, - accounts: PropTypes.array + tokens: PropTypes.array }; render () { @@ -45,24 +40,12 @@ export default class Tokens extends Component { } renderTokens (tokens) { - const { accounts, isOwner } = this.props; - - return tokens.map((token, index) => { - if (!token || !token.tla) { - return null; - } - - const isTokenOwner = !!accounts.find((account) => account.address === token.owner); - + return tokens.map((token) => { return ( + key={ token.tla } + tla={ token.tla } + /> ); }); } diff --git a/js/src/index.js b/js/src/index.js index c0f4f94ad..fda785842 100644 --- a/js/src/index.js +++ b/js/src/index.js @@ -25,6 +25,7 @@ import ReactDOM from 'react-dom'; import injectTapEventPlugin from 'react-tap-event-plugin'; import { createHashHistory } from 'history'; import { Redirect, Router, Route, useRouterHistory } from 'react-router'; +import qs from 'querystring'; import SecureApi from './secureApi'; import ContractInstances from './contracts'; @@ -45,6 +46,7 @@ import './index.html'; injectTapEventPlugin(); +const AUTH_HASH = '#/auth?'; const parityUrl = process.env.PARITY_URL || ( process.env.NODE_ENV === 'production' @@ -52,7 +54,12 @@ const parityUrl = process.env.PARITY_URL || : '127.0.0.1:8180' ); -const api = new SecureApi(`ws://${parityUrl}`); +let token = null; +if (window.location.hash && window.location.hash.indexOf(AUTH_HASH) === 0) { + token = qs.parse(window.location.hash.substr(AUTH_HASH.length)).token; +} + +const api = new SecureApi(`ws://${parityUrl}`, token); ContractInstances.create(api); const store = initStore(api); @@ -67,6 +74,7 @@ ReactDOM.render( + diff --git a/js/src/modals/AddContract/addContract.js b/js/src/modals/AddContract/addContract.js index 57773d2dc..4c73d3da0 100644 --- a/js/src/modals/AddContract/addContract.js +++ b/js/src/modals/AddContract/addContract.js @@ -227,6 +227,7 @@ export default class AddContract extends Component { onEditAbi = (abiIn) => { const { api } = this.context; const { abi, abiError, abiParsed } = validateAbi(abiIn, api); + this.setState({ abi, abiError, abiParsed }); } diff --git a/js/src/modals/DeployContract/DetailsStep/detailsStep.js b/js/src/modals/DeployContract/DetailsStep/detailsStep.js index 854715396..6e23f79c9 100644 --- a/js/src/modals/DeployContract/DetailsStep/detailsStep.js +++ b/js/src/modals/DeployContract/DetailsStep/detailsStep.js @@ -15,10 +15,10 @@ // along with Parity. If not, see . import React, { Component, PropTypes } from 'react'; -import { MenuItem } from 'material-ui'; -import { AddressSelect, Form, Input, InputAddressSelect, Select } from '../../../ui'; +import { AddressSelect, Form, Input, TypedInput } from '../../../ui'; import { validateAbi } from '../../../util/validation'; +import { parseAbiType } from '../../../util/abi'; import styles from '../deployContract.css'; @@ -103,6 +103,7 @@ export default class DetailsStep extends Component { value={ code } onSubmit={ this.onCodeChange } readOnly={ readOnly } /> + { this.renderConstructorInputs() } ); @@ -117,59 +118,23 @@ export default class DetailsStep extends Component { } return inputs.map((input, index) => { - const onChange = (event, value) => this.onParamChange(index, value); - const onChangeBool = (event, _index, value) => this.onParamChange(index, value === 'true'); - const onSubmit = (value) => this.onParamChange(index, value); - const label = `${input.name}: ${input.type}`; - let inputBox = null; + const onChange = (value) => this.onParamChange(index, value); - switch (input.type) { - case 'address': - inputBox = ( - - ); - break; - - case 'bool': - const boolitems = ['false', 'true'].map((bool) => { - return ( - { bool } - ); - }); - inputBox = ( - - ); - break; - - default: - inputBox = ( - - ); - break; - } + const label = `${input.name ? `${input.name}: ` : ''}${input.type}`; + const value = params[index]; + const error = paramsError[index]; + const param = parseAbiType(input.type); return (
- { inputBox } +
); }); @@ -200,35 +165,14 @@ export default class DetailsStep extends Component { const { abiError, abiParsed } = validateAbi(abi, api); if (!abiError) { - const { inputs } = abiParsed.find((method) => method.type === 'constructor') || { inputs: [] }; + const { inputs } = abiParsed + .find((method) => method.type === 'constructor') || { inputs: [] }; + const params = []; inputs.forEach((input) => { - switch (input.type) { - case 'address': - params.push('0x'); - break; - - case 'bool': - params.push(false); - break; - - case 'bytes': - params.push('0x'); - break; - - case 'uint': - params.push('0'); - break; - - case 'string': - params.push(''); - break; - - default: - params.push('0'); - break; - } + const param = parseAbiType(input.type); + params.push(param.default); }); onParamsChange(params); diff --git a/js/src/modals/DeployContract/deployContract.js b/js/src/modals/DeployContract/deployContract.js index 768723d1f..a99b49412 100644 --- a/js/src/modals/DeployContract/deployContract.js +++ b/js/src/modals/DeployContract/deployContract.js @@ -101,7 +101,8 @@ export default class DeployContract extends Component { steps={ deployError ? null : steps } title={ deployError ? 'deployment failed' : null } waiting={ [1] } - visible> + visible + scroll> { this.renderStep() } ); @@ -118,8 +119,22 @@ export default class DeployContract extends Component { onClick={ this.onClose } /> ); + const closeBtn = ( +
@@ -99,14 +100,14 @@ export default class Queries extends Component { - { this.renderValue(values[fn.name]) } + { this.renderValue(values[fn.name], fn.outputs[0].kind.type) } ); } - renderValue (value) { + renderValue (value, type) { if (typeof value === 'undefined') { return null; } @@ -124,6 +125,16 @@ export default class Queries extends Component { valueToDisplay = value.toString(); } + if (type === 'address') { + return ( + + ); + } + return ( * { @@ -35,10 +38,13 @@ } .name { - text-overflow: ellipsis; - overflow: hidden; white-space: nowrap; - display: lock; + display: block; vertical-align: middle; text-transform: uppercase; + + span { + text-overflow: ellipsis; + overflow: hidden; + } } diff --git a/js/src/views/Signer/components/TransactionFinished/TransactionFinished.css b/js/src/views/Signer/components/TransactionFinished/TransactionFinished.css index ef7c75f08..91749cc61 100644 --- a/js/src/views/Signer/components/TransactionFinished/TransactionFinished.css +++ b/js/src/views/Signer/components/TransactionFinished/TransactionFinished.css @@ -38,7 +38,9 @@ } .transactionDetails { - margin-right: 321px; + padding-right: 321px; + width: 100%; + box-sizing: border-box; } .isConfirmed { diff --git a/js/src/views/Signer/components/TransactionPending/TransactionPending.css b/js/src/views/Signer/components/TransactionPending/TransactionPending.css index 17e85107d..9574826a3 100644 --- a/js/src/views/Signer/components/TransactionPending/TransactionPending.css +++ b/js/src/views/Signer/components/TransactionPending/TransactionPending.css @@ -19,7 +19,9 @@ } .transactionDetails { - margin-right: 321px; + padding-right: 321px; + width: 100%; + box-sizing: border-box; } .mainContainer { diff --git a/js/src/views/Signer/containers/Embedded/embedded.css b/js/src/views/Signer/containers/Embedded/embedded.css index ff6f13a2f..cbe12d6dc 100644 --- a/js/src/views/Signer/containers/Embedded/embedded.css +++ b/js/src/views/Signer/containers/Embedded/embedded.css @@ -15,6 +15,7 @@ /* along with Parity. If not, see . */ .signer { + width: 916px; } .pending { diff --git a/js/webpack.vendor.js b/js/webpack.vendor.js index 74a51dada..222f6ab4e 100644 --- a/js/webpack.vendor.js +++ b/js/webpack.vendor.js @@ -14,6 +14,7 @@ // You should have received a copy of the GNU General Public License // along with Parity. If not, see . +const HappyPack = require('happypack'); const webpack = require('webpack'); const ENV = process.env.NODE_ENV || 'development'; @@ -22,10 +23,26 @@ const DEST = process.env.BUILD_DEST || '.build'; let modules = [ 'babel-polyfill', - 'browserify-aes', 'ethereumjs-tx', 'scryptsy', - 'react', 'react-dom', 'react-redux', 'react-router', - 'redux', 'redux-thunk', 'react-router-redux', - 'lodash', 'material-ui', 'moment', 'blockies' + 'bignumber.js', + 'blockies', + 'brace', + 'browserify-aes', + 'chart.js', + 'ethereumjs-tx', + 'lodash', + 'material-ui', + 'mobx', + 'mobx-react', + 'moment', + 'react', + 'react-dom', + 'react-redux', + 'react-router', + 'react-router-redux', + 'recharts', + 'redux', + 'redux-thunk', + 'scryptsy' ]; if (!isProd) { @@ -44,6 +61,11 @@ module.exports = { { test: /\.json$/, loaders: ['json'] + }, + { + test: /\.js$/, + include: /(ethereumjs-tx)/, + loaders: [ 'happypack/loader?id=js' ] } ] }, @@ -63,6 +85,12 @@ module.exports = { 'process.env': { NODE_ENV: JSON.stringify(ENV) } + }), + + new HappyPack({ + id: 'js', + threads: 4, + loaders: ['babel'] }) ]; diff --git a/json/src/spec/authority_round.rs b/json/src/spec/authority_round.rs new file mode 100644 index 000000000..3d73ef1ef --- /dev/null +++ b/json/src/spec/authority_round.rs @@ -0,0 +1,59 @@ +// Copyright 2015, 2016 Ethcore (UK) Ltd. +// This file is part of Parity. + +// Parity is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. + +// Parity is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. + +// You should have received a copy of the GNU General Public License +// along with Parity. If not, see . + +//! Authority params deserialization. + +use uint::Uint; +use hash::Address; + +/// Authority params deserialization. +#[derive(Debug, PartialEq, Deserialize)] +pub struct AuthorityRoundParams { + /// Gas limit divisor. + #[serde(rename="gasLimitBoundDivisor")] + pub gas_limit_bound_divisor: Uint, + /// Block duration. + #[serde(rename="stepDuration")] + pub step_duration: Uint, + /// Valid authorities + pub authorities: Vec
, +} + +/// Authority engine deserialization. +#[derive(Debug, PartialEq, Deserialize)] +pub struct AuthorityRound { + /// Ethash params. + pub params: AuthorityRoundParams, +} + +#[cfg(test)] +mod tests { + use serde_json; + use spec::authority_round::AuthorityRound; + + #[test] + fn basic_authority_deserialization() { + let s = r#"{ + "params": { + "gasLimitBoundDivisor": "0x0400", + "stepDuration": "0x02", + "authorities" : ["0xc6d9d2cd449a754c494264e1809c50e34d64562b"] + } + }"#; + + let _deserialized: AuthorityRound = serde_json::from_str(s).unwrap(); + } +} diff --git a/json/src/spec/engine.rs b/json/src/spec/engine.rs index 5c8f88758..850eb2502 100644 --- a/json/src/spec/engine.rs +++ b/json/src/spec/engine.rs @@ -18,6 +18,7 @@ use spec::Ethash; use spec::BasicAuthority; +use spec::AuthorityRound; /// Engine deserialization. #[derive(Debug, PartialEq, Deserialize)] @@ -30,6 +31,8 @@ pub enum Engine { Ethash(Ethash), /// BasicAuthority engine. BasicAuthority(BasicAuthority), + /// AuthorityRound engine. + AuthorityRound(AuthorityRound), } #[cfg(test)] diff --git a/json/src/spec/ethash.rs b/json/src/spec/ethash.rs index 10f0c6293..752d6853e 100644 --- a/json/src/spec/ethash.rs +++ b/json/src/spec/ethash.rs @@ -92,6 +92,11 @@ pub struct EthashParams { /// See main EthashParams docs. #[serde(rename="ecip1010ContinueTransition")] pub ecip1010_continue_transition: Option, + + /// See main EthashParams docs. + #[serde(rename="maxCodeSize")] + pub max_code_size: Option, + } /// Ethash engine deserialization. diff --git a/json/src/spec/mod.rs b/json/src/spec/mod.rs index f6c856b13..f9de30170 100644 --- a/json/src/spec/mod.rs +++ b/json/src/spec/mod.rs @@ -26,6 +26,7 @@ pub mod engine; pub mod state; pub mod ethash; pub mod basic_authority; +pub mod authority_round; pub use self::account::Account; pub use self::builtin::{Builtin, Pricing, Linear}; @@ -37,3 +38,4 @@ pub use self::engine::Engine; pub use self::state::State; pub use self::ethash::{Ethash, EthashParams}; pub use self::basic_authority::{BasicAuthority, BasicAuthorityParams}; +pub use self::authority_round::{AuthorityRound, AuthorityRoundParams}; diff --git a/parity/blockchain.rs b/parity/blockchain.rs index 9575b293a..0baeb1354 100644 --- a/parity/blockchain.rs +++ b/parity/blockchain.rs @@ -117,7 +117,7 @@ fn execute_import(cmd: ImportBlockchain) -> Result { let panic_handler = PanicHandler::new_in_arc(); // create dirs used by parity - try!(cmd.dirs.create_dirs()); + try!(cmd.dirs.create_dirs(false, false)); // load spec file let spec = try!(cmd.spec.spec()); @@ -165,6 +165,9 @@ fn execute_import(cmd: ImportBlockchain) -> Result { Arc::new(Miner::with_spec(&spec)), ).map_err(|e| format!("Client service error: {:?}", e))); + // free up the spec in memory. + drop(spec); + panic_handler.forward_from(&service); let client = service.client(); @@ -263,7 +266,7 @@ fn execute_export(cmd: ExportBlockchain) -> Result { let panic_handler = PanicHandler::new_in_arc(); // create dirs used by parity - try!(cmd.dirs.create_dirs()); + try!(cmd.dirs.create_dirs(false, false)); let format = cmd.format.unwrap_or_default(); @@ -312,6 +315,8 @@ fn execute_export(cmd: ExportBlockchain) -> Result { Arc::new(Miner::with_spec(&spec)), ).map_err(|e| format!("Client service error: {:?}", e))); + drop(spec); + panic_handler.forward_from(&service); let client = service.client(); diff --git a/parity/configuration.rs b/parity/configuration.rs index 75d319272..61063aa18 100644 --- a/parity/configuration.rs +++ b/parity/configuration.rs @@ -35,7 +35,7 @@ use params::{ResealPolicy, AccountsConfig, GasPricerConfig, MinerExtras}; use ethcore_logger::Config as LogConfig; use dir::Directories; use dapps::Configuration as DappsConfiguration; -use signer::{Configuration as SignerConfiguration, SignerCommand}; +use signer::{Configuration as SignerConfiguration}; use run::RunCmd; use blockchain::{BlockchainCmd, ImportBlockchain, ExportBlockchain, DataFormat}; use presale::ImportWallet; @@ -49,7 +49,7 @@ pub enum Cmd { Account(AccountCmd), ImportPresaleWallet(ImportWallet), Blockchain(BlockchainCmd), - SignerToken(SignerCommand), + SignerToken(SignerConfiguration), Snapshot(SnapshotCommand), Hash(Option), } @@ -103,9 +103,7 @@ impl Configuration { let cmd = if self.args.flag_version { Cmd::Version } else if self.args.cmd_signer && self.args.cmd_new_token { - Cmd::SignerToken(SignerCommand { - path: dirs.signer - }) + Cmd::SignerToken(signer_conf) } else if self.args.cmd_tools && self.args.cmd_hash { Cmd::Hash(self.args.arg_file) } else if self.args.cmd_account { @@ -690,7 +688,7 @@ mod tests { use ethcore::miner::{MinerOptions, PrioritizationStrategy}; use helpers::{replace_home, default_network_config}; use run::RunCmd; - use signer::{Configuration as SignerConfiguration, SignerCommand}; + use signer::{Configuration as SignerConfiguration}; use blockchain::{BlockchainCmd, ImportBlockchain, ExportBlockchain, DataFormat}; use presale::ImportWallet; use account::{AccountCmd, NewAccount, ImportAccounts}; @@ -827,8 +825,12 @@ mod tests { let args = vec!["parity", "signer", "new-token"]; let conf = parse(&args); let expected = replace_home("$HOME/.parity/signer"); - assert_eq!(conf.into_command().unwrap().cmd, Cmd::SignerToken(SignerCommand { - path: expected, + assert_eq!(conf.into_command().unwrap().cmd, Cmd::SignerToken(SignerConfiguration { + enabled: true, + signer_path: expected, + interface: "127.0.0.1".into(), + port: 8180, + skip_origin_validation: false, })); } diff --git a/parity/dir.rs b/parity/dir.rs index d7638e33b..b9c02efd6 100644 --- a/parity/dir.rs +++ b/parity/dir.rs @@ -44,11 +44,15 @@ impl Default for Directories { } impl Directories { - pub fn create_dirs(&self) -> Result<(), String> { + pub fn create_dirs(&self, dapps_enabled: bool, signer_enabled: bool) -> Result<(), String> { try!(fs::create_dir_all(&self.db).map_err(|e| e.to_string())); try!(fs::create_dir_all(&self.keys).map_err(|e| e.to_string())); - try!(fs::create_dir_all(&self.signer).map_err(|e| e.to_string())); - try!(fs::create_dir_all(&self.dapps).map_err(|e| e.to_string())); + if signer_enabled { + try!(fs::create_dir_all(&self.signer).map_err(|e| e.to_string())); + } + if dapps_enabled { + try!(fs::create_dir_all(&self.dapps).map_err(|e| e.to_string())); + } Ok(()) } diff --git a/parity/run.rs b/parity/run.rs index 56ff92c25..2cc791f8c 100644 --- a/parity/run.rs +++ b/parity/run.rs @@ -93,13 +93,29 @@ pub struct RunCmd { pub check_seal: bool, } +pub fn open_ui(dapps_conf: &dapps::Configuration, signer_conf: &signer::Configuration) -> Result<(), String> { + if !dapps_conf.enabled { + return Err("Cannot use UI command with Dapps turned off.".into()) + } + + if !signer_conf.enabled { + return Err("Cannot use UI command with UI turned off.".into()) + } + + let token = try!(signer::generate_token_and_url(signer_conf)); + // Open a browser + url::open(&token.url); + // Print a message + println!("{}", token.message); + Ok(()) +} + pub fn execute(cmd: RunCmd, logger: Arc) -> Result<(), String> { if cmd.ui && cmd.dapps_conf.enabled { // Check if Parity is already running let addr = format!("{}:{}", cmd.dapps_conf.interface, cmd.dapps_conf.port); if !TcpListener::bind(&addr as &str).is_ok() { - url::open(&format!("http://{}:{}/", cmd.dapps_conf.interface, cmd.dapps_conf.port)); - return Ok(()); + return open_ui(&cmd.dapps_conf, &cmd.signer_conf); } } @@ -110,7 +126,7 @@ pub fn execute(cmd: RunCmd, logger: Arc) -> Result<(), String> { raise_fd_limit(); // create dirs used by parity - try!(cmd.dirs.create_dirs()); + try!(cmd.dirs.create_dirs(cmd.dapps_conf.enabled, cmd.signer_conf.enabled)); // load spec let spec = try!(cmd.spec.spec()); @@ -235,6 +251,9 @@ pub fn execute(cmd: RunCmd, logger: Arc) -> Result<(), String> { miner.clone(), ).map_err(|e| format!("Client service error: {:?}", e))); + // drop the spec to free up genesis state. + drop(spec); + // forward panics from service panic_handler.forward_from(&service); @@ -309,7 +328,7 @@ pub fn execute(cmd: RunCmd, logger: Arc) -> Result<(), String> { }; // start signer server - let signer_server = try!(signer::start(cmd.signer_conf, signer_deps)); + let signer_server = try!(signer::start(cmd.signer_conf.clone(), signer_deps)); let informant = Arc::new(Informant::new( service.client(), @@ -363,10 +382,7 @@ pub fn execute(cmd: RunCmd, logger: Arc) -> Result<(), String> { // start ui if cmd.ui { - if !cmd.dapps_conf.enabled { - return Err("Cannot use UI command with Dapps turned off.".into()) - } - url::open(&format!("http://{}:{}/", cmd.dapps_conf.interface, cmd.dapps_conf.port)); + try!(open_ui(&cmd.dapps_conf, &cmd.signer_conf)); } // Handle exit diff --git a/parity/signer.rs b/parity/signer.rs index a26cc431a..6905fbb3c 100644 --- a/parity/signer.rs +++ b/parity/signer.rs @@ -27,7 +27,7 @@ pub use ethcore_signer::Server as SignerServer; const CODES_FILENAME: &'static str = "authcodes"; -#[derive(Debug, PartialEq)] +#[derive(Debug, PartialEq, Clone)] pub struct Configuration { pub enabled: bool, pub port: u16, @@ -53,6 +53,12 @@ pub struct Dependencies { pub apis: Arc, } +pub struct NewToken { + pub token: String, + pub url: String, + pub message: String, +} + pub fn start(conf: Configuration, deps: Dependencies) -> Result, String> { if !conf.enabled { Ok(None) @@ -68,20 +74,33 @@ fn codes_path(path: String) -> PathBuf { p } -#[derive(Debug, PartialEq)] -pub struct SignerCommand { - pub path: String, +pub fn execute(cmd: Configuration) -> Result { + Ok(try!(generate_token_and_url(&cmd)).message) } -pub fn execute(cmd: SignerCommand) -> Result { - generate_new_token(cmd.path) - .map(|code| format!("This key code will authorise your System Signer UI: {}", Colour::White.bold().paint(code))) - .map_err(|err| format!("Error generating token: {:?}", err)) +pub fn generate_token_and_url(conf: &Configuration) -> Result { + let code = try!(generate_new_token(conf.signer_path.clone()).map_err(|err| format!("Error generating token: {:?}", err))); + let auth_url = format!("http://{}:{}/#/auth?token={}", conf.interface, conf.port, code); + // And print in to the console + Ok(NewToken { + token: code.clone(), + url: auth_url.clone(), + message: format!( + r#" +Open: {} +to authorize your browser. +Or use the generated token: +{}"#, + Colour::White.bold().paint(auth_url), + code + ) + }) } pub fn generate_new_token(path: String) -> io::Result { let path = codes_path(path); let mut codes = try!(signer::AuthCodes::from_file(&path)); + codes.clear_garbage(); let code = try!(codes.generate_new()); try!(codes.to_file(&path)); trace!("New key code created: {}", Colour::White.bold().paint(&code[..])); diff --git a/parity/snapshot.rs b/parity/snapshot.rs index 872e4ba5e..d8323084d 100644 --- a/parity/snapshot.rs +++ b/parity/snapshot.rs @@ -183,7 +183,6 @@ impl SnapshotCommand { Ok((service, panic_handler)) } - /// restore from a snapshot pub fn restore(self) -> Result<(), String> { let file = self.file_path.clone(); diff --git a/signer/src/authcode_store.rs b/signer/src/authcode_store.rs index d8474441c..cbb78db41 100644 --- a/signer/src/authcode_store.rs +++ b/signer/src/authcode_store.rs @@ -16,12 +16,10 @@ use rand::Rng; use rand::os::OsRng; -use std::io; -use std::io::{Read, Write}; -use std::fs; +use std::io::{self, Read, Write}; use std::path::Path; -use std::time; -use util::{H256, Hashable}; +use std::{fs, time, mem}; +use util::{H256, Hashable, Itertools}; /// Providing current time in seconds pub trait TimeProvider { @@ -47,12 +45,35 @@ impl TimeProvider for DefaultTimeProvider { /// No of seconds the hash is valid const TIME_THRESHOLD: u64 = 7; +/// minimal length of hash const TOKEN_LENGTH: usize = 16; +/// special "initial" token used for authorization when there are no tokens yet. const INITIAL_TOKEN: &'static str = "initial"; +/// Separator between fields in serialized tokens file. +const SEPARATOR: &'static str = ";"; +/// Number of seconds to keep unused tokens. +const UNUSED_TOKEN_TIMEOUT: u64 = 3600 * 24; // a day + +struct Code { + code: String, + /// Duration since unix_epoch + created_at: time::Duration, + /// Duration since unix_epoch + last_used_at: Option, +} + +fn decode_time(val: &str) -> Option { + let time = val.parse::().ok(); + time.map(time::Duration::from_secs) +} + +fn encode_time(time: time::Duration) -> String { + format!("{}", time.as_secs()) +} /// Manages authorization codes for `SignerUIs` pub struct AuthCodes { - codes: Vec, + codes: Vec, now: T, } @@ -69,13 +90,32 @@ impl AuthCodes { "".into() } }; + let time_provider = DefaultTimeProvider::default(); + let codes = content.lines() - .filter(|f| f.len() >= TOKEN_LENGTH) - .map(String::from) + .filter_map(|line| { + let mut parts = line.split(SEPARATOR); + let token = parts.next(); + let created = parts.next(); + let used = parts.next(); + + match token { + None => None, + Some(token) if token.len() < TOKEN_LENGTH => None, + Some(token) => { + Some(Code { + code: token.into(), + last_used_at: used.and_then(decode_time), + created_at: created.and_then(decode_time) + .unwrap_or_else(|| time::Duration::from_secs(time_provider.now())), + }) + } + } + }) .collect(); Ok(AuthCodes { codes: codes, - now: DefaultTimeProvider::default(), + now: time_provider, }) } @@ -86,19 +126,30 @@ impl AuthCodes { /// Writes all `AuthCodes` to a disk. pub fn to_file(&self, file: &Path) -> io::Result<()> { let mut file = try!(fs::File::create(file)); - let content = self.codes.join("\n"); + let content = self.codes.iter().map(|code| { + let mut data = vec![code.code.clone(), encode_time(code.created_at.clone())]; + if let Some(used_at) = code.last_used_at.clone() { + data.push(encode_time(used_at)); + } + data.join(SEPARATOR) + }).join("\n"); file.write_all(content.as_bytes()) } /// Creates a new `AuthCodes` store with given `TimeProvider`. pub fn new(codes: Vec, now: T) -> Self { AuthCodes { - codes: codes, + codes: codes.into_iter().map(|code| Code { + code: code, + created_at: time::Duration::from_secs(now.now()), + last_used_at: None, + }).collect(), now: now, } } - /// Checks if given hash is correct identifier of `SignerUI` + /// Checks if given hash is correct authcode of `SignerUI` + /// Updates this hash last used field in case it's valid. #[cfg_attr(feature="dev", allow(wrong_self_convention))] pub fn is_valid(&mut self, hash: &H256, time: u64) -> bool { let now = self.now.now(); @@ -121,8 +172,14 @@ impl AuthCodes { } // look for code - self.codes.iter() - .any(|code| &as_token(code) == hash) + for mut code in &mut self.codes { + if &as_token(&code.code) == hash { + code.last_used_at = Some(time::Duration::from_secs(now)); + return true; + } + } + + false } /// Generates and returns a new code that can be used by `SignerUIs` @@ -135,7 +192,11 @@ impl AuthCodes { .collect::>() .join("-"); trace!(target: "signer", "New authentication token generated."); - self.codes.push(code); + self.codes.push(Code { + code: code, + created_at: time::Duration::from_secs(self.now.now()), + last_used_at: None, + }); Ok(readable_code) } @@ -143,12 +204,31 @@ impl AuthCodes { pub fn is_empty(&self) -> bool { self.codes.is_empty() } -} + /// Removes old tokens that have not been used since creation. + pub fn clear_garbage(&mut self) { + let now = self.now.now(); + let threshold = time::Duration::from_secs(now.saturating_sub(UNUSED_TOKEN_TIMEOUT)); + + let codes = mem::replace(&mut self.codes, Vec::new()); + for code in codes { + // Skip codes that are old and were never used. + if code.last_used_at.is_none() && code.created_at <= threshold { + continue; + } + self.codes.push(code); + } + } +} #[cfg(test)] mod tests { + use devtools; + use std::io::{Read, Write}; + use std::{time, fs}; + use std::cell::Cell; + use util::{H256, Hashable}; use super::*; @@ -217,6 +297,54 @@ mod tests { assert_eq!(res2, false); } + #[test] + fn should_read_old_format_from_file() { + // given + let path = devtools::RandomTempPath::new(); + let code = "23521352asdfasdfadf"; + { + let mut file = fs::File::create(&path).unwrap(); + file.write_all(b"a\n23521352asdfasdfadf\nb\n").unwrap(); + } + + // when + let mut authcodes = AuthCodes::from_file(&path).unwrap(); + let time = time::UNIX_EPOCH.elapsed().unwrap().as_secs(); + + // then + assert!(authcodes.is_valid(&generate_hash(code, time), time), "Code should be read from file"); + } + + #[test] + fn should_remove_old_unused_tokens() { + // given + let path = devtools::RandomTempPath::new(); + let code1 = "11111111asdfasdf111"; + let code2 = "22222222asdfasdf222"; + let code3 = "33333333asdfasdf333"; + + let time = Cell::new(100); + let mut codes = AuthCodes::new(vec![code1.into(), code2.into(), code3.into()], || time.get()); + // `code2` should not be removed (we never remove tokens that were used) + codes.is_valid(&generate_hash(code2, time.get()), time.get()); + + // when + time.set(100 + 10_000_000); + // mark `code1` as used now + codes.is_valid(&generate_hash(code1, time.get()), time.get()); + + let new_code = codes.generate_new().unwrap().replace('-', ""); + codes.clear_garbage(); + codes.to_file(&path).unwrap(); + + // then + let mut content = String::new(); + let mut file = fs::File::open(&path).unwrap(); + file.read_to_string(&mut content).unwrap(); + + assert_eq!(content, format!("{};100;10000100\n{};100;100\n{};10000100", code1, code2, new_code)); + } + } diff --git a/signer/src/ws_server/session.rs b/signer/src/ws_server/session.rs index b99ef48ef..5adc3fa80 100644 --- a/signer/src/ws_server/session.rs +++ b/signer/src/ws_server/session.rs @@ -94,6 +94,9 @@ fn auth_is_valid(codes_path: &Path, protocols: ws::Result>) -> bool { // Check if the code is valid AuthCodes::from_file(codes_path) .map(|mut codes| { + // remove old tokens + codes.clear_garbage(); + let res = codes.is_valid(&auth, time); // make sure to save back authcodes - it might have been modified if let Err(_) = codes.to_file(codes_path) { diff --git a/util/io/src/service.rs b/util/io/src/service.rs index 965a7d08e..5d773f525 100644 --- a/util/io/src/service.rs +++ b/util/io/src/service.rs @@ -56,6 +56,7 @@ pub enum IoMessage where Message: Send + Clone + Sized { handler_id: HandlerId, token: TimerToken, delay: u64, + once: bool, }, RemoveTimer { handler_id: HandlerId, @@ -92,12 +93,24 @@ impl IoContext where Message: Send + Clone + Sync + 'static { } } - /// Register a new IO timer. 'IoHandler::timeout' will be called with the token. + /// Register a new recurring IO timer. 'IoHandler::timeout' will be called with the token. pub fn register_timer(&self, token: TimerToken, ms: u64) -> Result<(), IoError> { try!(self.channel.send_io(IoMessage::AddTimer { token: token, delay: ms, handler_id: self.handler, + once: false, + })); + Ok(()) + } + + /// Register a new IO timer once. 'IoHandler::timeout' will be called with the token. + pub fn register_timer_once(&self, token: TimerToken, ms: u64) -> Result<(), IoError> { + try!(self.channel.send_io(IoMessage::AddTimer { + token: token, + delay: ms, + handler_id: self.handler, + once: true, })); Ok(()) } @@ -163,6 +176,7 @@ impl IoContext where Message: Send + Clone + Sync + 'static { struct UserTimer { delay: u64, timeout: Timeout, + once: bool, } /// Root IO handler. Manages user handlers, messages and IO timers. @@ -235,8 +249,14 @@ impl Handler for IoManager where Message: Send + Clone + Sync let handler_index = token.0 / TOKENS_PER_HANDLER; let token_id = token.0 % TOKENS_PER_HANDLER; if let Some(handler) = self.handlers.read().get(handler_index) { - if let Some(timer) = self.timers.read().get(&token.0) { - event_loop.timeout(token, Duration::from_millis(timer.delay)).expect("Error re-registering user timer"); + let maybe_timer = self.timers.read().get(&token.0).cloned(); + if let Some(timer) = maybe_timer { + if timer.once { + self.timers.write().remove(&token_id); + event_loop.clear_timeout(&timer.timeout); + } else { + event_loop.timeout(token, Duration::from_millis(timer.delay)).expect("Error re-registering user timer"); + } self.worker_channel.push(Work { work_type: WorkType::Timeout, token: token_id, handler: handler.clone(), handler_id: handler_index }); self.work_ready.notify_all(); } @@ -264,10 +284,10 @@ impl Handler for IoManager where Message: Send + Clone + Sync event_loop.clear_timeout(&timer.timeout); } }, - IoMessage::AddTimer { handler_id, token, delay } => { + IoMessage::AddTimer { handler_id, token, delay, once } => { let timer_id = token + handler_id * TOKENS_PER_HANDLER; let timeout = event_loop.timeout(Token(timer_id), Duration::from_millis(delay)).expect("Error registering user timer"); - self.timers.write().insert(timer_id, UserTimer { delay: delay, timeout: timeout }); + self.timers.write().insert(timer_id, UserTimer { delay: delay, timeout: timeout, once: once }); }, IoMessage::RemoveTimer { handler_id, token } => { let timer_id = token + handler_id * TOKENS_PER_HANDLER;