Avoid further copies of the tries (#393)

* Revert logging change

* Avoid further copies of tries

* Avoid sync on beacon

* Avoid recreating the address for each transaction
This commit is contained in:
petricadaipegsp 2024-12-01 22:24:38 +01:00 committed by GitHub
parent 1b78d758f5
commit e0993a94ea
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
8 changed files with 38 additions and 37 deletions

View File

@ -117,9 +117,6 @@ func (e *DataClockConsensusEngine) prove(
"applied transitions",
zap.Int("successful", len(validTransactions.Requests)),
zap.Int("failed", len(invalidTransactions.Requests)),
zap.Uint64("mint_out_of_order", app.MintOutOfOrder),
zap.Uint64("mint_too_old", app.MintTooOld),
zap.Uint64("mint_tree_verification_failed", app.MintTreeVerificationFailure),
)
outputState, err := app.MaterializeStateFromApplication()
@ -223,7 +220,7 @@ func (e *DataClockConsensusEngine) prove(
}
func (e *DataClockConsensusEngine) GetAheadPeers(frameNumber uint64) []internal.PeerCandidate {
if e.GetFrameProverTrie(0).Contains(e.provingKeyAddress) {
if e.FrameProverTrieContains(0, e.provingKeyAddress) {
return nil
}

View File

@ -59,10 +59,35 @@ func (e *DataClockConsensusEngine) GetFrameProverTrie(i int) *tries.RollingFrece
return newTrie
}
func (e *DataClockConsensusEngine) FrameProverTriesContains(
key []byte,
) bool {
e.frameProverTriesMx.RLock()
defer e.frameProverTriesMx.RUnlock()
for _, trie := range e.frameProverTries {
if trie.Contains(key) {
return true
}
}
return false
}
func (e *DataClockConsensusEngine) FrameProverTrieContains(
i int,
key []byte,
) bool {
e.frameProverTriesMx.RLock()
defer e.frameProverTriesMx.RUnlock()
if i < 0 || i >= len(e.frameProverTries) {
return false
}
return e.frameProverTries[i].Contains(key)
}
func (e *DataClockConsensusEngine) runFramePruning() {
defer e.wg.Done()
// A full prover should _never_ do this
if e.GetFrameProverTrie(0).Contains(e.provingKeyAddress) ||
if e.FrameProverTrieContains(0, e.provingKeyAddress) ||
e.config.Engine.MaxFrames == -1 || e.config.Engine.FullProver {
e.logger.Info("frame pruning not enabled")
return
@ -105,7 +130,7 @@ func (e *DataClockConsensusEngine) runFramePruning() {
func (e *DataClockConsensusEngine) runSync() {
defer e.wg.Done()
// small optimization, beacon should never collect for now:
if e.GetFrameProverTrie(0).Contains(e.provingKeyAddress) {
if e.FrameProverTrieContains(0, e.provingKeyAddress) {
return
}
@ -147,7 +172,7 @@ func (e *DataClockConsensusEngine) runLoop() {
}
if runOnce {
if e.GetFrameProverTrie(0).Contains(e.provingKeyAddress) {
if e.FrameProverTrieContains(0, e.provingKeyAddress) {
dataFrame, err := e.dataTimeReel.Head()
if err != nil {
panic(err)
@ -165,7 +190,7 @@ func (e *DataClockConsensusEngine) runLoop() {
e.validationFilterMx.Lock()
e.validationFilter = make(map[string]struct{}, len(e.validationFilter))
e.validationFilterMx.Unlock()
if e.GetFrameProverTrie(0).Contains(e.provingKeyAddress) {
if e.FrameProverTrieContains(0, e.provingKeyAddress) {
if err = e.publishProof(dataFrame); err != nil {
e.logger.Error("could not publish", zap.Error(err))
e.stateMx.Lock()
@ -191,7 +216,7 @@ func (e *DataClockConsensusEngine) processFrame(
zap.Duration("frame_age", frametime.Since(dataFrame)),
)
var err error
if !e.GetFrameProverTrie(0).Contains(e.provingKeyBytes) {
if !e.FrameProverTrieContains(0, e.provingKeyAddress) {
select {
case e.requestSyncCh <- struct{}{}:
default:

View File

@ -182,8 +182,7 @@ func (e *DataClockConsensusEngine) handleClockFrame(
return errors.Wrap(err, "handle clock frame data")
}
trie := e.GetFrameProverTrie(0)
if !trie.Contains(addr.FillBytes(make([]byte, 32))) {
if !e.FrameProverTrieContains(0, addr.FillBytes(make([]byte, 32))) {
e.logger.Debug(
"prover not in trie at frame, address may be in fork",
zap.Binary("address", address),
@ -370,7 +369,7 @@ func TokenRequestIdentifiers(transition *protobufs.TokenRequest) []string {
func (e *DataClockConsensusEngine) handleTokenRequest(
transition *protobufs.TokenRequest,
) error {
if e.GetFrameProverTrie(0).Contains(e.provingKeyAddress) {
if e.FrameProverTrieContains(0, e.provingKeyAddress) {
identifiers := TokenRequestIdentifiers(transition)
e.stagedTransactionsMx.Lock()

View File

@ -128,7 +128,7 @@ func (e *DataClockConsensusEngine) GetPreMidnightMintStatus(
ctx context.Context,
t *protobufs.PreMidnightMintStatusRequest,
) (*protobufs.PreMidnightMintResponse, error) {
if !e.GetFrameProverTrie(0).Contains(e.provingKeyAddress) {
if !e.FrameProverTrieContains(0, e.provingKeyAddress) {
return nil, errors.Wrap(
errors.New("wrong destination"),
"get pre midnight mint status",
@ -182,7 +182,7 @@ func (e *DataClockConsensusEngine) GetPreMidnightMintStatus(
func (e *DataClockConsensusEngine) handleMint(
t *protobufs.MintCoinRequest,
) ([]byte, error) {
if !e.GetFrameProverTrie(0).Contains(e.provingKeyAddress) {
if !e.FrameProverTrieContains(0, e.provingKeyAddress) {
return nil, errors.Wrap(errors.New("wrong destination"), "handle mint")
}
@ -243,7 +243,7 @@ func (e *DataClockConsensusEngine) handleMint(
t.Proofs[0],
[]byte("pre-dusk"),
) && (!bytes.Equal(t.Proofs[1], make([]byte, 32)) ||
time.Now().Unix() < 1730523600) && e.GetFrameProverTrie(0).Contains(
time.Now().Unix() < 1730523600) && e.FrameProverTrieContains(0,
e.provingKeyAddress,
) {
prevInput := []byte{}

View File

@ -55,13 +55,6 @@ func (e *DataClockConsensusEngine) IsInProverTrie(key []byte) bool {
if err != nil {
return false
}
provingKeyAddress := h.FillBytes(make([]byte, 32))
for _, tries := range e.GetFrameProverTries() {
if tries.Contains(provingKeyAddress) {
return true
}
}
return false
return e.FrameProverTriesContains(provingKeyAddress)
}

View File

@ -5,7 +5,6 @@ import (
"crypto"
"encoding/binary"
"sync"
"sync/atomic"
"github.com/iden3/go-iden3-crypto/poseidon"
"github.com/pkg/errors"
@ -30,10 +29,6 @@ var TOKEN_ADDRESS = []byte{
}
type TokenApplication struct {
MintTreeVerificationFailure uint64
MintOutOfOrder uint64
MintTooOld uint64
Beacon []byte
TokenOutputs *protobufs.TokenOutputs
Tries []*tries.RollingFrecencyCritbitTrie
@ -193,7 +188,6 @@ func (a *TokenApplication) ApplyTransitions(
} else if len(t.Mint.Proofs) >= 3 && currentFrameNumber > PROOF_FRAME_CUTOFF {
frameNumber := binary.BigEndian.Uint64(t.Mint.Proofs[2])
if frameNumber < currentFrameNumber-2 {
atomic.AddUint64(&a.MintTooOld, 1)
fails[i] = transition
continue
}

View File

@ -4,7 +4,6 @@ import (
"bytes"
"encoding/binary"
"math/big"
"sync/atomic"
"github.com/iden3/go-iden3-crypto/poseidon"
pcrypto "github.com/libp2p/go-libp2p/core/crypto"
@ -206,7 +205,6 @@ func (a *TokenApplication) handleMint(
}
if !verified {
atomic.AddUint64(&a.MintTreeVerificationFailure, 1)
a.Logger.Debug(
"tree verification failed",
zap.String("peer_id", base58.Encode([]byte(peerId))),
@ -224,11 +222,6 @@ func (a *TokenApplication) handleMint(
if previousFrame != nil {
previousFrameNumber = previousFrame.FrameNumber
}
if newFrameNumber < currentFrameNumber-2 {
atomic.AddUint64(&a.MintTooOld, 1)
} else {
atomic.AddUint64(&a.MintOutOfOrder, 1)
}
a.Logger.Debug(
"received out of order proofs, ignoring",
zap.Error(err),

View File

@ -473,7 +473,7 @@ func (e *TokenExecutionEngine) ProcessMessage(
switch a.TypeUrl {
case protobufs.TokenRequestType:
if e.clock.IsInProverTrie(e.proverPublicKey) {
if e.clock.FrameProverTriesContains(e.provingKeyAddress) {
payload, err := proto.Marshal(a)
if err != nil {
return nil, errors.Wrap(err, "process message")