Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions .changeset/better-masks-tease.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
'@solana/sysvars': patch
---

The `SysvarEpochRewards` encoder/decoder no longer produces malformed data
29 changes: 22 additions & 7 deletions packages/sysvars/src/__tests__/epoch-rewards-test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,14 +4,29 @@ describe('epoch rewards', () => {
it('decode', () => {
// prettier-ignore
const epochRewardsState = new Uint8Array([
0, 45, 49, 1, 0, 0, 0, 0, // distributionCompleteBlockHeight
134, 74, 2, 0, 0, 0, 0, 0, // distributedRewards
0, 132, 215, 23, 0, 0, 0, 0, // totalRewards
// distributionStartingBlockHeight
0xab, 0xa8, 0x87, 0x12, 0x00, 0x00, 0x00, 0x00,
// numPartitions
0x3a, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
// parentBlockhash
0x67, 0x8b, 0xd4, 0xe4, 0xc8, 0x5c, 0x10, 0x87, 0xa8, 0x0a, 0xfb, 0x2f, 0x0d, 0xbb, 0x13, 0x27, 0x16, 0x11, 0x3a, 0xc7, 0xc7, 0xb0, 0xc7, 0xe4, 0x99, 0x51, 0x4d, 0x42, 0xdb, 0x43, 0xd7, 0x1c,
// totalPoints
0x10, 0xbe, 0x90, 0x99, 0x7a, 0x16, 0x9e, 0xa5, 0xc2, 0x2d, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00,
// totalRewards
0x00, 0xb3, 0x04, 0x4e, 0xd0, 0x20, 0x89, 0x00,
// distributedRewards
0x00, 0xb8, 0xea, 0x37, 0xd0, 0x20, 0x89, 0x00,
// active
0x00,
]);
expect(getSysvarEpochRewardsCodec().decode(epochRewardsState)).toMatchObject({
distributedRewards: 150_150n,
distributionCompleteBlockHeight: 20_000_000n,
totalRewards: 400_000_000n,
expect(getSysvarEpochRewardsCodec().decode(epochRewardsState)).toStrictEqual({
active: false,
distributedRewards: 38598150472775680n,
distributionStartingBlockHeight: 310880427n,
numPartitions: 314n,
parentBlockhash: '7yCfKTaamnrmkAfefSgsonQ6rtwCfVaxQJircWb9K4Qj',
totalPoints: 2633948733309470433656336n,
totalRewards: 38598150843577088n,
});
});
// TODO: This account does not seem to exist on-chain yet.
Expand Down
44 changes: 34 additions & 10 deletions packages/sysvars/src/epoch-rewards.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,17 +4,29 @@ import {
type FixedSizeCodec,
type FixedSizeDecoder,
type FixedSizeEncoder,
getBooleanDecoder,
getBooleanEncoder,
getStructDecoder,
getStructEncoder,
getU64Decoder,
getU64Encoder,
getU128Decoder,
getU128Encoder,
} from '@solana/codecs';
import type { GetAccountInfoApi } from '@solana/rpc-api';
import type { Rpc } from '@solana/rpc-spec';
import {
Blockhash,
getBlockhashDecoder,
getBlockhashEncoder,
getDefaultLamportsDecoder,
getDefaultLamportsEncoder,
Lamports,
} from '@solana/rpc-types';

import { fetchEncodedSysvarAccount, SYSVAR_EPOCH_REWARDS_ADDRESS } from './sysvar';

type SysvarEpochRewardsSize = 24;
type SysvarEpochRewardsSize = 81;

/**
* The `EpochRewards` sysvar.
Expand All @@ -30,24 +42,36 @@ type SysvarEpochRewardsSize = 24;
* See https://github.com/anza-xyz/agave/blob/e0203f22dc83cb792fa97f91dbe6e924cbd08af1/docs/src/runtime/sysvars.md?plain=1#L155-L168
*/
export type SysvarEpochRewards = Readonly<{
distributedRewards: bigint;
distributionCompleteBlockHeight: bigint;
totalRewards: bigint;
active: boolean;
distributedRewards: Lamports;
distributionStartingBlockHeight: bigint;
numPartitions: bigint;
parentBlockhash: Blockhash;
totalPoints: bigint;
totalRewards: Lamports;
}>;

export function getSysvarEpochRewardsEncoder(): FixedSizeEncoder<SysvarEpochRewards, SysvarEpochRewardsSize> {
return getStructEncoder([
['distributionCompleteBlockHeight', getU64Encoder()],
['distributedRewards', getU64Encoder()],
['totalRewards', getU64Encoder()],
['distributionStartingBlockHeight', getU64Encoder()],
['numPartitions', getU64Encoder()],
['parentBlockhash', getBlockhashEncoder()],
['totalPoints', getU128Encoder()],
['totalRewards', getDefaultLamportsEncoder()],
['distributedRewards', getDefaultLamportsEncoder()],
['active', getBooleanEncoder()],
]) as FixedSizeEncoder<SysvarEpochRewards, SysvarEpochRewardsSize>;
}

export function getSysvarEpochRewardsDecoder(): FixedSizeDecoder<SysvarEpochRewards, SysvarEpochRewardsSize> {
return getStructDecoder([
['distributionCompleteBlockHeight', getU64Decoder()],
['distributedRewards', getU64Decoder()],
['totalRewards', getU64Decoder()],
['distributionStartingBlockHeight', getU64Decoder()],
['numPartitions', getU64Decoder()],
['parentBlockhash', getBlockhashDecoder()],
['totalPoints', getU128Decoder()],
['totalRewards', getDefaultLamportsDecoder()],
['distributedRewards', getDefaultLamportsDecoder()],
['active', getBooleanDecoder()],
]) as FixedSizeDecoder<SysvarEpochRewards, SysvarEpochRewardsSize>;
}

Expand Down