Signable interface.

This commit is contained in:
Jae Kwon 2014-10-07 19:37:20 -07:00
parent 349e3743df
commit 0c206aa748
11 changed files with 85 additions and 81 deletions

View File

@ -1,46 +0,0 @@
package blocks
import (
"fmt"
. "github.com/tendermint/tendermint/config"
)
func GenVoteDocument(voteType byte, height uint32, round uint16, blockHash []byte) []byte {
stepName := ""
switch voteType {
case VoteTypeBare:
stepName = "bare"
case VoteTypePrecommit:
stepName = "precommit"
case VoteTypeCommit:
stepName = "commit"
default:
panic("Unknown vote type")
}
return []byte(fmt.Sprintf(
`!!!!!BEGIN TENDERMINT VOTE!!!!!
Network: %v
Height: %v
Round: %v
Step: %v
BlockHash: %v
!!!!!END TENDERMINT VOTE!!!!!`,
Config.Network, height, round, stepName, blockHash,
))
}
func GenProposalDocument(height uint32, round uint16, blockPartsTotal uint16, blockPartsHash []byte,
polPartsTotal uint16, polPartsHash []byte) []byte {
return []byte(fmt.Sprintf(
`!!!!!BEGIN TENDERMINT PROPOSAL!!!!!
Network: %v
Height: %v
Round: %v
BlockPartsTotal: %v
BlockPartsHash: %X
POLPartsTotal: %v
POLPartsHash: %X
!!!!!END TENDERMINT PROPOSAL!!!!!`,
Config.Network, height, round, blockPartsTotal, blockPartsHash, polPartsTotal, polPartsHash,
))
}

View File

@ -5,6 +5,14 @@ import (
"io"
)
type Signable interface {
GenDocument() []byte
GetSignature() Signature
SetSignature(Signature)
}
//-----------------------------------------------------------------------------
type Signature struct {
SignerId uint64
Bytes []byte

View File

@ -20,8 +20,6 @@ Validation Txs:
type Tx interface {
Type() byte
GetSequence() uint64
GetSignature() *Signature
//IsValidation() bool
Binary
}
@ -99,20 +97,20 @@ func ReadBaseTx(r io.Reader, n *int64, err *error) BaseTx {
}
}
func (tx *BaseTx) GetSequence() uint64 {
return tx.Sequence
}
func (tx *BaseTx) GetSignature() *Signature {
return &tx.Signature
}
func (tx *BaseTx) WriteTo(w io.Writer) (n int64, err error) {
func (tx BaseTx) WriteTo(w io.Writer) (n int64, err error) {
WriteUVarInt(w, tx.Sequence, &n, &err)
WriteBinary(w, tx.Signature, &n, &err)
return
}
func (tx *BaseTx) GetSignature() Signature {
return tx.Signature
}
func (tx *BaseTx) SetSignature(sig Signature) {
tx.Signature = sig
}
//-----------------------------------------------------------------------------
type SendTx struct {
@ -128,7 +126,7 @@ func (tx *SendTx) Type() byte {
func (tx *SendTx) WriteTo(w io.Writer) (n int64, err error) {
WriteByte(w, tx.Type(), &n, &err)
WriteBinary(w, &tx.BaseTx, &n, &err)
WriteBinary(w, tx.BaseTx, &n, &err)
WriteUInt64(w, tx.Fee, &n, &err)
WriteUInt64(w, tx.To, &n, &err)
WriteUInt64(w, tx.Amount, &n, &err)
@ -150,7 +148,7 @@ func (tx *NameTx) Type() byte {
func (tx *NameTx) WriteTo(w io.Writer) (n int64, err error) {
WriteByte(w, tx.Type(), &n, &err)
WriteBinary(w, &tx.BaseTx, &n, &err)
WriteBinary(w, tx.BaseTx, &n, &err)
WriteUInt64(w, tx.Fee, &n, &err)
WriteString(w, tx.Name, &n, &err)
WriteByteSlice(w, tx.PubKey, &n, &err)
@ -172,7 +170,7 @@ func (tx *BondTx) Type() byte {
func (tx *BondTx) WriteTo(w io.Writer) (n int64, err error) {
WriteByte(w, tx.Type(), &n, &err)
WriteBinary(w, &tx.BaseTx, &n, &err)
WriteBinary(w, tx.BaseTx, &n, &err)
WriteUInt64(w, tx.Fee, &n, &err)
WriteUInt64(w, tx.UnbondTo, &n, &err)
WriteUInt64(w, tx.Amount, &n, &err)
@ -193,7 +191,7 @@ func (tx *UnbondTx) Type() byte {
func (tx *UnbondTx) WriteTo(w io.Writer) (n int64, err error) {
WriteByte(w, tx.Type(), &n, &err)
WriteBinary(w, &tx.BaseTx, &n, &err)
WriteBinary(w, tx.BaseTx, &n, &err)
WriteUInt64(w, tx.Fee, &n, &err)
WriteUInt64(w, tx.Amount, &n, &err)
return
@ -213,7 +211,7 @@ func (tx *TimeoutTx) Type() byte {
func (tx *TimeoutTx) WriteTo(w io.Writer) (n int64, err error) {
WriteByte(w, tx.Type(), &n, &err)
WriteBinary(w, &tx.BaseTx, &n, &err)
WriteBinary(w, tx.BaseTx, &n, &err)
WriteUInt64(w, tx.AccountId, &n, &err)
WriteUInt64(w, tx.Penalty, &n, &err)
return
@ -233,8 +231,16 @@ func (tx *DupeoutTx) Type() byte {
func (tx *DupeoutTx) WriteTo(w io.Writer) (n int64, err error) {
WriteByte(w, tx.Type(), &n, &err)
WriteBinary(w, &tx.BaseTx, &n, &err)
WriteBinary(w, tx.BaseTx, &n, &err)
WriteBinary(w, &tx.VoteA, &n, &err)
WriteBinary(w, &tx.VoteB, &n, &err)
return
}
func (tx *DupeoutTx) GenDocument() []byte {
oldSig := tx.Signature
tx.Signature = Signature{}
doc := BinaryBytes(tx)
tx.Signature = oldSig
return doc
}

View File

@ -50,5 +50,17 @@ func (v *Vote) WriteTo(w io.Writer) (n int64, err error) {
}
func (v *Vote) GenDocument() []byte {
return GenVoteDocument(v.Type, v.Height, v.Round, v.BlockHash)
oldSig := v.Signature
v.Signature = Signature{}
doc := BinaryBytes(v)
v.Signature = oldSig
return doc
}
func (v *Vote) GetSignature() Signature {
return v.Signature
}
func (v *Vote) SetSignature(sig Signature) {
v.Signature = sig
}

View File

@ -45,7 +45,8 @@ func (pol *POL) WriteTo(w io.Writer) (n int64, err error) {
func (pol *POL) Verify(vset *ValidatorSet) error {
talliedVotingPower := uint64(0)
voteDoc := GenVoteDocument(VoteTypeBare, pol.Height, pol.Round, pol.BlockHash)
voteDoc := (&Vote{Height: pol.Height, Round: pol.Round,
Type: VoteTypeBare, BlockHash: pol.BlockHash}).GenDocument()
seenValidators := map[uint64]struct{}{}
for _, sig := range pol.Votes {
@ -78,7 +79,9 @@ func (pol *POL) Verify(vset *ValidatorSet) error {
if validator == nil {
return Errorf("Invalid validator for commit %v for POL %v", sig, pol)
}
commitDoc := GenVoteDocument(VoteTypeCommit, pol.Height, round, pol.BlockHash) // TODO cache
commitDoc := (&Vote{Height: pol.Height, Round: round,
Type: VoteTypeCommit, BlockHash: pol.BlockHash}).GenDocument() // TODO cache
if !validator.Verify(commitDoc, sig) {
return Errorf("Invalid signature for commit %v for POL %v", sig, pol)
}

View File

@ -16,14 +16,11 @@ type PrivValidator struct {
// Double signing results in an error.
func (pv *PrivValidator) SignProposal(proposal *Proposal) {
//TODO: prevent double signing.
doc := GenProposalDocument(proposal.Height, proposal.Round, proposal.BlockPartsTotal,
proposal.BlockPartsHash, proposal.POLPartsTotal, proposal.POLPartsHash)
proposal.Signature = pv.Sign([]byte(doc))
pv.SignSignable(proposal)
}
// Double signing results in an error.
func (pv *PrivValidator) SignVote(vote *Vote) {
//TODO: prevent double signing.
doc := GenVoteDocument(vote.Type, vote.Height, vote.Round, vote.BlockHash)
vote.Signature = pv.Sign([]byte(doc))
pv.SignSignable(vote)
}

View File

@ -59,6 +59,17 @@ func (p *Proposal) WriteTo(w io.Writer) (n int64, err error) {
}
func (p *Proposal) GenDocument() []byte {
return GenProposalDocument(p.Height, p.Round, p.BlockPartsTotal, p.BlockPartsHash,
p.POLPartsTotal, p.POLPartsHash)
oldSig := p.Signature
p.Signature = Signature{}
doc := BinaryBytes(p)
p.Signature = oldSig
return doc
}
func (p *Proposal) GetSignature() Signature {
return p.Signature
}
func (p *Proposal) SetSignature(sig Signature) {
p.Signature = sig
}

View File

@ -79,18 +79,18 @@ func (cs *ConsensusState) GetRoundState() *RoundState {
func (cs *ConsensusState) updateToState(state *State) {
// Sanity check state.
stateHeight := state.Height()
stateHeight := state.Height
if stateHeight > 0 && stateHeight != cs.Height+1 {
Panicf("updateToState() expected state height of %v but found %v", cs.Height+1, stateHeight)
}
// Reset fields based on state.
height := state.Height()
validators := state.Validators()
height := state.Height
validators := state.Validators
cs.Height = height
cs.Round = 0
cs.Step = RoundStepStart
cs.StartTime = state.CommitTime().Add(newBlockWaitDuration)
cs.StartTime = state.CommitTime.Add(newBlockWaitDuration)
cs.Validators = validators
cs.Proposer = validators.GetProposer()
cs.Proposal = nil

View File

@ -33,7 +33,7 @@ func (account Account) WriteTo(w io.Writer) (n int64, err error) {
func (account Account) Verify(msg []byte, sig Signature) bool {
if sig.SignerId != account.Id {
panic("Account.Id doesn't match sig.SignerId")
panic("account.id doesn't match sig.signerid")
}
v1 := &crypto.Verify{
Message: msg,
@ -44,6 +44,12 @@ func (account Account) Verify(msg []byte, sig Signature) bool {
return ok
}
func (account Account) VerifySignable(o Signable) bool {
msg := o.GenDocument()
sig := o.GetSignature()
return account.Verify(msg, sig)
}
//-----------------------------------------------------------------------------
type AccountBalance struct {
@ -90,8 +96,15 @@ func GenPrivAccount() *PrivAccount {
func (pa *PrivAccount) Sign(msg []byte) Signature {
signature := crypto.SignMessage(msg, pa.PrivKey, pa.PubKey)
return Signature{
sig := Signature{
SignerId: pa.Id,
Bytes: signature,
}
return sig
}
func (pa *PrivAccount) SignSignable(o Signable) {
msg := o.GenDocument()
sig := pa.Sign(msg)
o.SetSignature(sig)
}

View File

@ -10,6 +10,6 @@ func init() {
logging.SetFormatter(logging.MustStringFormatter("[%{level:.1s}] %{message}"))
}
func SetStatesLogger(l *logging.Logger) {
func SetStateLogger(l *logging.Logger) {
log = l
}

View File

@ -147,7 +147,7 @@ func (s *State) ExecTx(tx Tx) error {
}
// NOTE: If an error occurs during block execution, state will be left
// at an invalid state. Copy the state before calling Commit!
// at an invalid state. Copy the state before calling AppendBlock!
func (s *State) AppendBlock(b *Block) error {
// Basic block validation.
err := b.ValidateBasic(s.Height, s.BlockHash)