LCOV - code coverage report
Current view: top level - choreo/tower - fd_tower_lockos.h (source / functions) Hit Total Coverage
Test: cov.lcov Lines: 0 33 0.0 %
Date: 2026-03-19 18:19:27 Functions: 0 69 0.0 %

          Line data    Source code
       1             : #ifndef HEADER_fd_src_choreo_tower_fd_tower_lockos_h
       2             : #define HEADER_fd_src_choreo_tower_fd_tower_lockos_h
       3             : 
       4             : #include "../fd_choreo_base.h"
       5             : #include "fd_tower_voters.h"
       6             : 
       7             : /* fd_tower_lockos_interval tracks a map of lockout intervals.
       8             : 
       9             :    We need to track a list of lockout intervals per validator per slot.
      10             :    Intervals are inclusive.  Example:
      11             : 
      12             :    After executing slot 33, validator A votes for slot 32, has a tower
      13             : 
      14             :      vote  | confirmation count | lockout interval
      15             :      ----- | -------------------|------------------
      16             :      32    |  1                 | [32, 33]
      17             :      2     |  3                 | [2,  6]
      18             :      1     |  4                 | [1,  9]
      19             : 
      20             :    The lockout interval is the interval of slots that the validator is
      21             :    locked out from voting for if they want to switch off that vote.  For
      22             :    example if validator A wants to switch off fork 1, they have to wait
      23             :    until slot 9.
      24             : 
      25             :    Agave tracks a similar structure.
      26             : 
      27             :    key: for an interval [vote, vote+lockout] for validator A,
      28             :    it is stored like:
      29             :    vote+lockout -> (vote, validator A) -> (2, validator B) -> (any other vote, any other validator)
      30             : 
      31             :    Since a validator can have up to 31 entries in the tower, and we have
      32             :    a max_vote_accounts, we can pool the interval objects to be
      33             :    31*max_vote_accounts entries PER bank / executed slot. We can also
      34             :    string all the intervals of the same bank together as a linkedlist. */
      35             : 
      36             : struct fd_tower_lockos_interval {
      37             :   ulong     key;   /* vote_slot (32 bits) | expiration_slot (32 bits) ie. vote_slot + (1 << confirmation count) */
      38             :   ulong     next;  /* reserved for fd_map_chain and fd_pool */
      39             :   fd_hash_t addr;  /* vote account address */
      40             :   ulong     start; /* start of interval, also vote slot */
      41             : };
      42             : typedef struct fd_tower_lockos_interval fd_tower_lockos_interval_t;
      43             : 
      44             : #define MAP_NAME    fd_tower_lockos_interval_map
      45           0 : #define MAP_ELE_T   fd_tower_lockos_interval_t
      46             : #define MAP_MULTI   1
      47           0 : #define MAP_KEY     key
      48           0 : #define MAP_NEXT    next
      49             : #include "../../util/tmpl/fd_map_chain.c"
      50             : 
      51             : #define POOL_NAME fd_tower_lockos_interval_pool
      52           0 : #define POOL_T    fd_tower_lockos_interval_t
      53           0 : #define POOL_NEXT next
      54             : #include "../../util/tmpl/fd_pool.c"
      55             : 
      56             : struct fd_tower_lockos_slot {
      57             :   ulong   fork_slot;
      58             :   ulong   next;      /* reserved for fd_map_chain and fd_pool */
      59             :   ulong   interval_end;
      60             : };
      61             : typedef struct fd_tower_lockos_slot fd_tower_lockos_slot_t;
      62             : 
      63             : #define MAP_NAME    fd_tower_lockos_slot_map
      64           0 : #define MAP_ELE_T   fd_tower_lockos_slot_t
      65             : #define MAP_MULTI   1
      66           0 : #define MAP_KEY     fork_slot
      67           0 : #define MAP_NEXT    next
      68             : #include "../../util/tmpl/fd_map_chain.c"
      69             : 
      70             : #define POOL_NAME fd_tower_lockos_slot_pool
      71           0 : #define POOL_T    fd_tower_lockos_slot_t
      72           0 : #define POOL_NEXT next
      73             : #include "../../util/tmpl/fd_pool.c"
      74             : 
      75           0 : #define FD_TOWER_LOCKOS_MAX 31UL
      76             : 
      77             : struct __attribute__((aligned(128UL))) fd_tower_lockos {
      78             :   fd_tower_lockos_slot_map_t *     slot_map;
      79             :   fd_tower_lockos_slot_t *         slot_pool;
      80             :   fd_tower_lockos_interval_map_t * interval_map;
      81             :   fd_tower_lockos_interval_t *     interval_pool;
      82             : };
      83             : typedef struct fd_tower_lockos fd_tower_lockos_t;
      84             : 
      85             : FD_PROTOTYPES_BEGIN
      86             : 
      87             : /* fd_tower_lockos_{align,footprint} return the required alignment and
      88             :    footprint of a memory region suitable for use as a tower_lockos. */
      89             : 
      90             : FD_FN_CONST static inline ulong
      91           0 : fd_tower_lockos_align( void ) {
      92           0 :   return 128UL;
      93           0 : }
      94             : 
      95             : FD_FN_CONST static inline ulong
      96             : fd_tower_lockos_footprint( ulong slot_max,
      97           0 :                            ulong vtr_max ) {
      98           0 :   ulong interval_max = fd_ulong_pow2_up( FD_TOWER_LOCKOS_MAX*slot_max*vtr_max );
      99           0 :   return FD_LAYOUT_FINI(
     100           0 :     FD_LAYOUT_APPEND(
     101           0 :     FD_LAYOUT_APPEND(
     102           0 :     FD_LAYOUT_APPEND(
     103           0 :     FD_LAYOUT_APPEND(
     104           0 :     FD_LAYOUT_APPEND(
     105           0 :     FD_LAYOUT_INIT,
     106           0 :       alignof(fd_tower_lockos_t),            sizeof(fd_tower_lockos_t)                               ),
     107           0 :       fd_tower_lockos_slot_pool_align(),     fd_tower_lockos_slot_pool_footprint    ( interval_max ) ),
     108           0 :       fd_tower_lockos_slot_map_align(),      fd_tower_lockos_slot_map_footprint     ( slot_max     ) ),
     109           0 :       fd_tower_lockos_interval_pool_align(), fd_tower_lockos_interval_pool_footprint( interval_max ) ),
     110           0 :       fd_tower_lockos_interval_map_align(),  fd_tower_lockos_interval_map_footprint ( interval_max ) ),
     111           0 :     fd_tower_lockos_align() );
     112           0 : }
     113             : 
     114             : /* fd_tower_lockos_new formats an unused memory region for use as a
     115             :    tower_lockos.  mem is a non-NULL pointer to this region in the local
     116             :    address space with the required footprint and alignment. */
     117             : 
     118             : void *
     119             : fd_tower_lockos_new( void * shmem,
     120             :                      ulong  slot_max,
     121             :                      ulong  vtr_max,
     122             :                      ulong  seed );
     123             : 
     124             : /* fd_tower_lockos_join joins the caller to the tower_lockos. shlockos
     125             :    points to the first byte of the memory region backing the shlockos in
     126             :    the caller's address space.
     127             : 
     128             :    Returns a pointer in the local address space to lockos on success. */
     129             : 
     130             : fd_tower_lockos_t *
     131             : fd_tower_lockos_join( void * shlockos );
     132             : 
     133             : /* fd_tower_lockos_leave leaves a current local join.  Returns a pointer
     134             :    to the underlying shared memory region on success and NULL on failure
     135             :    (logs details).  Reasons for failure include lockos is NULL. */
     136             : 
     137             : void *
     138             : fd_tower_lockos_leave( fd_tower_lockos_t const * lockos );
     139             : 
     140             : /* fd_tower_lockos_delete unformats a memory region used as a lockos.
     141             :    Assumes only the local process is joined to the region.  Returns a
     142             :    pointer to the underlying shared memory region or NULL if used
     143             :    obviously in error (e.g. lockos is obviously not a lockos ...  logs
     144             :    details).  The ownership of the memory region is transferred to the
     145             :    caller. */
     146             : 
     147             : void *
     148             : fd_tower_lockos_delete( void * lockos );
     149             : 
     150             : FD_FN_PURE static inline ulong
     151           0 : fd_tower_lockos_interval_key( ulong fork_slot, ulong end_interval ) {
     152           0 :   return (fork_slot << 32) | end_interval;
     153           0 : }
     154             : 
     155             : void
     156             : fd_tower_lockos_insert( fd_tower_lockos_t * lockos,
     157             :                         ulong               slot,
     158             :                         fd_hash_t const *   vote_acc,
     159             :                         fd_tower_voters_t * voters );
     160             : 
     161             : void
     162             : fd_tower_lockos_remove( fd_tower_lockos_t * lockos,
     163             :                         ulong               slot );
     164             : 
     165             : FD_PROTOTYPES_END
     166             : 
     167             : #endif /* HEADER_fd_src_choreo_tower_fd_tower_lockos_h */

Generated by: LCOV version 1.14