Fix checkpointing when creating contract failed (#9514)
This commit is contained in:
parent
485870296d
commit
631df0fe56
@ -421,16 +421,7 @@ impl<B: Backend> State<B> {
|
|||||||
**prev = checkpoint;
|
**prev = checkpoint;
|
||||||
} else {
|
} else {
|
||||||
for (k, v) in checkpoint.drain() {
|
for (k, v) in checkpoint.drain() {
|
||||||
match prev.entry(k) {
|
prev.entry(k).or_insert(v);
|
||||||
Entry::Occupied(mut e) => {
|
|
||||||
if e.get().is_none() {
|
|
||||||
e.insert(v);
|
|
||||||
}
|
|
||||||
},
|
|
||||||
Entry::Vacant(e) => {
|
|
||||||
e.insert(v);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -2462,6 +2453,25 @@ mod tests {
|
|||||||
assert_eq!(state.storage_at(&a, &k).unwrap(), H256::from(U256::from(1)));
|
assert_eq!(state.storage_at(&a, &k).unwrap(), H256::from(U256::from(1)));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn create_contract_fail() {
|
||||||
|
let mut state = get_temp_state();
|
||||||
|
let orig_root = state.root().clone();
|
||||||
|
let a: Address = 1000.into();
|
||||||
|
|
||||||
|
state.checkpoint(); // c1
|
||||||
|
state.new_contract(&a, U256::zero(), U256::zero()).unwrap();
|
||||||
|
state.add_balance(&a, &U256::from(1), CleanupMode::ForceCreate).unwrap();
|
||||||
|
state.checkpoint(); // c2
|
||||||
|
state.add_balance(&a, &U256::from(1), CleanupMode::ForceCreate).unwrap();
|
||||||
|
state.discard_checkpoint(); // discard c2
|
||||||
|
state.revert_to_checkpoint(); // revert to c1
|
||||||
|
assert_eq!(state.exists(&a).unwrap(), false);
|
||||||
|
|
||||||
|
state.commit().unwrap();
|
||||||
|
assert_eq!(orig_root, state.root().clone());
|
||||||
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn create_empty() {
|
fn create_empty() {
|
||||||
let mut state = get_temp_state();
|
let mut state = get_temp_state();
|
||||||
|
Loading…
Reference in New Issue
Block a user