github.com/MetalBlockchain/metalgo@v1.11.9/snow/engine/avalanche/state/prefixed_state.go (about)

     1  // Copyright (C) 2019-2024, Ava Labs, Inc. All rights reserved.
     2  // See the file LICENSE for licensing terms.
     3  
     4  package state
     5  
     6  import (
     7  	"github.com/MetalBlockchain/metalgo/cache"
     8  	"github.com/MetalBlockchain/metalgo/ids"
     9  	"github.com/MetalBlockchain/metalgo/snow/choices"
    10  	"github.com/MetalBlockchain/metalgo/snow/engine/avalanche/vertex"
    11  )
    12  
    13  const (
    14  	vtxID uint64 = iota
    15  	vtxStatusID
    16  	edgeID
    17  )
    18  
    19  var uniqueEdgeID = ids.Empty.Prefix(edgeID)
    20  
    21  type prefixedState struct {
    22  	state *state
    23  
    24  	vtx, status cache.Cacher[ids.ID, ids.ID]
    25  	uniqueVtx   cache.Deduplicator[ids.ID, *uniqueVertex]
    26  }
    27  
    28  func newPrefixedState(state *state, idCacheSizes int) *prefixedState {
    29  	return &prefixedState{
    30  		state:     state,
    31  		vtx:       &cache.LRU[ids.ID, ids.ID]{Size: idCacheSizes},
    32  		status:    &cache.LRU[ids.ID, ids.ID]{Size: idCacheSizes},
    33  		uniqueVtx: &cache.EvictableLRU[ids.ID, *uniqueVertex]{Size: idCacheSizes},
    34  	}
    35  }
    36  
    37  func (s *prefixedState) UniqueVertex(vtx *uniqueVertex) *uniqueVertex {
    38  	return s.uniqueVtx.Deduplicate(vtx)
    39  }
    40  
    41  func (s *prefixedState) Vertex(id ids.ID) vertex.StatelessVertex {
    42  	var (
    43  		vID ids.ID
    44  		ok  bool
    45  	)
    46  	if vID, ok = s.vtx.Get(id); !ok {
    47  		vID = id.Prefix(vtxID)
    48  		s.vtx.Put(id, vID)
    49  	}
    50  
    51  	return s.state.Vertex(vID)
    52  }
    53  
    54  func (s *prefixedState) SetVertex(vtx vertex.StatelessVertex) error {
    55  	var (
    56  		rawVertexID = vtx.ID()
    57  		vID         ids.ID
    58  		ok          bool
    59  	)
    60  	if vID, ok = s.vtx.Get(rawVertexID); !ok {
    61  		vID = rawVertexID.Prefix(vtxID)
    62  		s.vtx.Put(rawVertexID, vID)
    63  	}
    64  
    65  	return s.state.SetVertex(vID, vtx)
    66  }
    67  
    68  func (s *prefixedState) Status(id ids.ID) choices.Status {
    69  	var (
    70  		sID ids.ID
    71  		ok  bool
    72  	)
    73  	if sID, ok = s.status.Get(id); !ok {
    74  		sID = id.Prefix(vtxStatusID)
    75  		s.status.Put(id, sID)
    76  	}
    77  
    78  	return s.state.Status(sID)
    79  }
    80  
    81  func (s *prefixedState) SetStatus(id ids.ID, status choices.Status) error {
    82  	var (
    83  		sID ids.ID
    84  		ok  bool
    85  	)
    86  	if sID, ok = s.status.Get(id); !ok {
    87  		sID = id.Prefix(vtxStatusID)
    88  		s.status.Put(id, sID)
    89  	}
    90  
    91  	return s.state.SetStatus(sID, status)
    92  }
    93  
    94  func (s *prefixedState) Edge() []ids.ID {
    95  	return s.state.Edge(uniqueEdgeID)
    96  }
    97  
    98  func (s *prefixedState) SetEdge(frontier []ids.ID) error {
    99  	return s.state.SetEdge(uniqueEdgeID, frontier)
   100  }