commit inicial do projeto
This commit is contained in:
72
internal/consensus/finality.go
Normal file
72
internal/consensus/finality.go
Normal file
@ -0,0 +1,72 @@
|
||||
package consensus
|
||||
|
||||
import (
|
||||
"crypto/ecdsa"
|
||||
"crypto/rand"
|
||||
"crypto/sha256"
|
||||
"encoding/hex"
|
||||
"errors"
|
||||
"fmt"
|
||||
"math/big"
|
||||
"time"
|
||||
|
||||
"dejo_node/internal/transactions"
|
||||
)
|
||||
|
||||
// Finalizer encapsula a lógica de selar e assinar blocos.
|
||||
type Finalizer struct {
|
||||
PrivateKey *ecdsa.PrivateKey
|
||||
NodeID string // opcional: ID do produtor do bloco
|
||||
}
|
||||
|
||||
// Finalize executa a finalização de um bloco:
|
||||
// - Adiciona timestamp
|
||||
// - Gera hash final
|
||||
// - Retorna assinatura
|
||||
func (f *Finalizer) Finalize(block *transactions.Block) (string, error) {
|
||||
if block == nil {
|
||||
return "", errors.New("bloco nulo")
|
||||
}
|
||||
|
||||
block.Timestamp = time.Now().Unix()
|
||||
|
||||
// Geração do hash usando campos existentes do bloco
|
||||
hashInput := []byte(
|
||||
fmt.Sprintf("%d|%s|%d|%s",
|
||||
block.Index,
|
||||
block.PrevHash,
|
||||
block.Timestamp,
|
||||
f.NodeID,
|
||||
),
|
||||
)
|
||||
hash := sha256.Sum256(hashInput)
|
||||
block.Hash = hex.EncodeToString(hash[:])
|
||||
|
||||
r, s, err := ecdsa.Sign(rand.Reader, f.PrivateKey, hash[:])
|
||||
if err != nil {
|
||||
return "", err
|
||||
}
|
||||
|
||||
sig := append(r.Bytes(), s.Bytes()...)
|
||||
signature := hex.EncodeToString(sig)
|
||||
|
||||
return signature, nil
|
||||
}
|
||||
|
||||
// VerifySignature verifica se a assinatura é válida com a chave pública fornecida.
|
||||
func VerifySignature(block *transactions.Block, signature string, pubKey *ecdsa.PublicKey) bool {
|
||||
hash, err := hex.DecodeString(block.Hash)
|
||||
if err != nil {
|
||||
return false
|
||||
}
|
||||
|
||||
sig, err := hex.DecodeString(signature)
|
||||
if err != nil || len(sig) < 64 {
|
||||
return false
|
||||
}
|
||||
|
||||
r := big.NewInt(0).SetBytes(sig[:len(sig)/2])
|
||||
s := big.NewInt(0).SetBytes(sig[len(sig)/2:])
|
||||
|
||||
return ecdsa.Verify(pubKey, hash, r, s)
|
||||
}
|
||||
Reference in New Issue
Block a user