LCOV - code coverage report
Current view: top level - flamenco/runtime/sysvar - fd_sysvar_epoch_rewards.c (source / functions) Hit Total Coverage
Test: cov.lcov Lines: 69 75 92.0 %
Date: 2026-11-03 04:25:32 Functions: 7 7 100.0 %

          Line data    Source code
       1             : #include "fd_sysvar_epoch_rewards.h"
       2             : #include "../../events/fd_event_runtime.h"
       3             : #include "fd_sysvar.h"
       4             : #include "../fd_system_ids.h"
       5             : #include "../fd_accdb_svm.h"
       6             : #include "fd_sysvar_rent.h"
       7             : 
       8             : static int
       9         411 : validate( fd_sysvar_epoch_rewards_t const * epoch_rewards ) {
      10         411 :   return epoch_rewards->active!=0 && epoch_rewards->active!=1;
      11             : 
      12         411 : }
      13             : 
      14             : static void
      15             : write_epoch_rewards( fd_bank_t *                 bank,
      16             :                      fd_accdb_t *                accdb,
      17             :                      fd_capture_ctx_t *          capture_ctx,
      18         669 :                      fd_sysvar_epoch_rewards_t * epoch_rewards ) {
      19         669 :   fd_sysvar_account_update( bank, accdb, capture_ctx, &fd_sysvar_epoch_rewards_id, epoch_rewards, FD_SYSVAR_EPOCH_REWARDS_BINCODE_SZ );
      20         669 : }
      21             : 
      22             : /* write_epoch_rewards with the balance set to the rent exempt minimum,
      23             :    burning any surplus.
      24             :    Agave: create_account with RENT_UNADJUSTED_INITIAL_BALANCE followed by
      25             :    adjust_sysvar_balance_for_rent. */
      26             : static void
      27             : write_epoch_rewards_reset_balance( fd_bank_t *                 bank,
      28             :                                    fd_accdb_t *                accdb,
      29             :                                    fd_capture_ctx_t *          capture_ctx,
      30          12 :                                    fd_sysvar_epoch_rewards_t * epoch_rewards ) {
      31          12 :   fd_accdb_svm_update_t update[1];
      32          12 :   fd_acc_t              acc = fd_accdb_svm_open_rw( bank, accdb, update, &fd_sysvar_epoch_rewards_id, 1 );
      33          12 :   fd_memcpy( acc.owner, &fd_sysvar_owner_id, 32UL );
      34          12 :   acc.executable = 0;
      35          12 :   fd_memcpy( acc.data, epoch_rewards, FD_SYSVAR_EPOCH_REWARDS_BINCODE_SZ );
      36          12 :   acc.data_len = FD_SYSVAR_EPOCH_REWARDS_BINCODE_SZ;
      37          12 :   acc.lamports = fd_ulong_max( fd_rent_exempt_minimum_balance( &bank->f.rent, acc.data_len ), FD_SYSVAR_RENT_UNADJUSTED_INITIAL_BALANCE );
      38          12 :   fd_accdb_svm_close_rw( bank, accdb, capture_ctx, &acc, update );
      39          12 : }
      40             : 
      41             : fd_sysvar_epoch_rewards_t *
      42             : fd_sysvar_epoch_rewards_read( fd_accdb_t *                accdb,
      43             :                               fd_accdb_fork_id_t          fork_id,
      44         411 :                               fd_sysvar_epoch_rewards_t * out ) {
      45         411 :   fd_acc_t acc = fd_accdb_read_one( accdb, fork_id, fd_sysvar_epoch_rewards_id.uc );
      46         411 :   if( FD_UNLIKELY( !acc.lamports ) ) {
      47           0 :     fd_accdb_unread_one( accdb, &acc );
      48           0 :     return NULL;
      49           0 :   }
      50         411 :   if( FD_UNLIKELY( acc.data_len!=FD_SYSVAR_EPOCH_REWARDS_BINCODE_SZ ) ) {
      51           0 :     fd_accdb_unread_one( accdb, &acc );
      52           0 :     return NULL;
      53           0 :   }
      54             : 
      55         411 :   fd_memcpy( out, acc.data, FD_SYSVAR_EPOCH_REWARDS_BINCODE_SZ );
      56             : 
      57         411 :   fd_accdb_unread_one( accdb, &acc );
      58         411 :   if( FD_UNLIKELY( validate( out ) ) ) return NULL;
      59         411 :   return out;
      60         411 : }
      61             : 
      62             : void
      63             : fd_sysvar_epoch_rewards_distribute( fd_bank_t *        bank,
      64             :                                     fd_accdb_t *       accdb,
      65             :                                     fd_capture_ctx_t * capture_ctx,
      66             :                                     ulong              distributed,
      67         174 :                                     ulong              debit_block_reward_lamports ) {
      68         174 :   fd_sysvar_epoch_rewards_t epoch_rewards[1];
      69         174 :   FD_TEST( fd_sysvar_epoch_rewards_read( accdb, bank->accdb_fork_id, epoch_rewards ) );
      70         174 :   FD_TEST( epoch_rewards->active );
      71             : 
      72         174 :   ulong new_distributed = fd_ulong_sat_add( epoch_rewards->distributed_rewards, distributed );
      73         174 :   FD_TEST( new_distributed<=epoch_rewards->total_rewards );
      74         174 :   epoch_rewards->distributed_rewards += distributed;
      75             : 
      76         174 :   write_epoch_rewards( bank, accdb, capture_ctx, epoch_rewards );
      77             : 
      78         174 :   if( FD_UNLIKELY( !debit_block_reward_lamports ) ) return;
      79             : 
      80           9 :   fd_accdb_svm_update_t update[1];
      81           9 :   fd_acc_t              acc = fd_accdb_svm_open_rw( bank, accdb, update, &fd_sysvar_epoch_rewards_id, 0 );
      82             :   /* https://github.com/anza-xyz/agave/blob/v4.4.0-alpha.5/runtime/src/bank/partitioned_epoch_rewards/sysvar.rs#L101 */
      83           9 :   FD_TEST( acc.lamports>=debit_block_reward_lamports );
      84           9 :   acc.lamports -= debit_block_reward_lamports;
      85             :   /* https://github.com/anza-xyz/agave/blob/v4.4.0-alpha.5/runtime/src/bank/partitioned_epoch_rewards/sysvar.rs#L102-L105 */
      86           9 :   FD_TEST( acc.lamports>=fd_rent_exempt_minimum_balance( &bank->f.rent, acc.data_len ) );
      87           9 :   fd_accdb_svm_close_rw( bank, accdb, capture_ctx, &acc, update );
      88           9 : }
      89             : 
      90             : void
      91             : fd_sysvar_epoch_rewards_set_inactive( fd_bank_t *        bank,
      92             :                                       fd_accdb_t *       accdb,
      93         165 :                                       fd_capture_ctx_t * capture_ctx ) {
      94         165 :   fd_sysvar_epoch_rewards_t epoch_rewards[1];
      95         165 :   FD_TEST( fd_sysvar_epoch_rewards_read( accdb, bank->accdb_fork_id, epoch_rewards ) );
      96         165 :   FD_TEST( epoch_rewards->total_rewards>=epoch_rewards->distributed_rewards );
      97             : 
      98         165 :   epoch_rewards->active = 0;
      99             : 
     100         165 :   if( FD_FEATURE_ACTIVE_BANK( bank, block_revenue_sharing ) ) {
     101             :     /* Don't inherit the balance to ensure that any remaining lamports
     102             :        get burned: the balance is reset to the rent-exempt minimum and
     103             :        capitalization is updated.
     104             :        https://github.com/anza-xyz/agave/blob/v4.4.0-alpha.5/runtime/src/bank/partitioned_epoch_rewards/sysvar.rs#L120-L135 */
     105          12 :     write_epoch_rewards_reset_balance( bank, accdb, capture_ctx, epoch_rewards );
     106         153 :   } else {
     107         153 :     write_epoch_rewards( bank, accdb, capture_ctx, epoch_rewards );
     108         153 :   }
     109         165 : }
     110             : 
     111             : /* Create EpochRewards sysvar with calculated rewards
     112             : 
     113             :    https://github.com/anza-xyz/agave/blob/cbc8320d35358da14d79ebcada4dfb6756ffac79/runtime/src/bank/partitioned_epoch_rewards/sysvar.rs#L25 */
     114             : void
     115             : fd_sysvar_epoch_rewards_init( fd_bank_t *        bank,
     116             :                               fd_accdb_t *       accdb,
     117             :                               fd_capture_ctx_t * capture_ctx,
     118             :                               ulong              distributed_rewards,
     119             :                               ulong              distribution_starting_block_height,
     120             :                               ulong              num_partitions,
     121             :                               ulong              total_rewards,
     122             :                               uint128            total_points,
     123             :                               fd_hash_t const *  last_blockhash,
     124         342 :                               ulong              block_rewards ) {
     125         342 :   fd_sysvar_epoch_rewards_t epoch_rewards = {
     126         342 :     .distribution_starting_block_height = distribution_starting_block_height,
     127         342 :     .num_partitions                     = num_partitions,
     128         342 :     .total_points                       = { .ud=total_points },
     129         342 :     .total_rewards                      = total_rewards,
     130         342 :     .distributed_rewards                = distributed_rewards,
     131         342 :     .active                             = 1,
     132         342 :     .parent_blockhash                   = *last_blockhash
     133         342 :   };
     134             : 
     135         342 :   FD_TEST( epoch_rewards.total_rewards>=epoch_rewards.distributed_rewards );
     136         342 :   if( FD_UNLIKELY( fd_bank_report_runtime_diffs( bank ) ) ) fd_event_runtime_epoch_rewards( &epoch_rewards );
     137         342 :   write_epoch_rewards( bank, accdb, capture_ctx, &epoch_rewards );
     138             : 
     139             :   /* https://github.com/anza-xyz/agave/blob/v4.4.0-alpha.5/runtime/src/bank/partitioned_epoch_rewards/sysvar.rs#L58-L69 */
     140         342 :   if( block_rewards ) {
     141          12 :     fd_accdb_svm_credit( bank, accdb, capture_ctx, &fd_sysvar_epoch_rewards_id, block_rewards, 0 );
     142          12 :   }
     143         342 : }

Generated by: LCOV version 1.14