fix verification of testnet block 542 by fixing OP_CHECKSEQENCEVERIFY and OP_CHECKLOCKTIMEVERIFY implementations

This commit is contained in:
debris 2016-12-02 15:07:35 +01:00
parent af095cf505
commit a07741c645
2 changed files with 36 additions and 16 deletions

View File

@ -57,7 +57,7 @@ pub struct VerificationFlags {
/// support CHECKSEQUENCEVERIFY opcode
///
/// See BIP112 for details
pub verify_chechsequenceverify: bool,
pub verify_checksequenceverify: bool,
/// Support segregated witness
pub verify_witness: bool,

View File

@ -454,10 +454,6 @@ pub fn eval_script(
},
Opcode::OP_NOP => break,
Opcode::OP_CHECKLOCKTIMEVERIFY => {
if flags.verify_discourage_upgradable_nops {
return Err(Error::DiscourageUpgradableNops);
}
if flags.verify_clocktimeverify {
// Note that elsewhere numeric opcodes are limited to
// operands in the range -2**31+1 to 2**31-1, however it is
@ -485,22 +481,25 @@ pub fn eval_script(
if !checker.check_lock_time(lock_time) {
return Err(Error::UnsatisfiedLocktime);
}
} else if flags.verify_discourage_upgradable_nops {
return Err(Error::DiscourageUpgradableNops);
}
},
Opcode::OP_CHECKSEQUENCEVERIFY => {
if !flags.verify_chechsequenceverify && flags.verify_discourage_upgradable_nops {
if flags.verify_checksequenceverify {
let sequence = try!(Num::from_slice(try!(stack.last()), flags.verify_minimaldata, 5));
if sequence.is_negative() {
return Err(Error::NegativeLocktime);
}
if (sequence & (SEQUENCE_LOCKTIME_DISABLE_FLAG as i64).into()).is_zero() && !checker.check_sequence(sequence) {
return Err(Error::UnsatisfiedLocktime);
}
} else if flags.verify_discourage_upgradable_nops {
return Err(Error::DiscourageUpgradableNops);
}
let sequence = try!(Num::from_slice(try!(stack.last()), flags.verify_minimaldata, 5));
if sequence.is_negative() {
return Err(Error::NegativeLocktime);
}
if (sequence & (SEQUENCE_LOCKTIME_DISABLE_FLAG as i64).into()).is_zero() && !checker.check_sequence(sequence) {
return Err(Error::UnsatisfiedLocktime);
}
},
Opcode::OP_NOP1 |
Opcode::OP_NOP4 |
@ -1944,5 +1943,26 @@ mod tests {
let result = Ok(true);
basic_test(&script, result, vec![vec![1].into()].into());
}
#[test]
fn test_skipping_sequencetimeverify() {
let script = Builder::default()
.push_opcode(Opcode::OP_1)
.push_opcode(Opcode::OP_NOP1)
.push_opcode(Opcode::OP_CHECKLOCKTIMEVERIFY)
.push_opcode(Opcode::OP_CHECKSEQUENCEVERIFY)
.push_opcode(Opcode::OP_NOP4)
.push_opcode(Opcode::OP_NOP5)
.push_opcode(Opcode::OP_NOP6)
.push_opcode(Opcode::OP_NOP7)
.push_opcode(Opcode::OP_NOP8)
.push_opcode(Opcode::OP_NOP9)
.push_opcode(Opcode::OP_NOP10)
.push_opcode(Opcode::OP_1)
.push_opcode(Opcode::OP_EQUAL)
.into_script();
let result = Ok(true);
basic_test(&script, result, vec![vec![1].into()].into());
}
}