ProtocolState
Global singleton storing protocol configuration and auto-incrementing counters. Location:lib.rs:472-481
PDA Seeds: ["protocol_state"]
Space: 8 + ProtocolState::INIT_SPACE (8-byte discriminator + 83 bytes)
Fields
Pubkey
required
Protocol admin wallet with permission to modify global settings. Set during
initialize_protocol.u64
required
Auto-incrementing counter for NKA specimen numbers. Starts at 0, incremented by
submit_null_result. Used to derive sequential IDs (NKA-0001, NKA-0002, …).u64
required
Auto-incrementing counter for bounty numbers. Starts at 0, incremented by
create_bounty. Used to derive sequential IDs (NB-0001, NB-0002, …).u16
required
Protocol fee rate in basis points (1/100th of a percent). Default: 250 (2.5%). Used in
approve_bounty_submission to calculate treasury fee.Example: 250 = 2.5%, 100 = 1%, 1000 = 10%Pubkey
required
Treasury wallet address receiving protocol fees. Validated by admin during initialization. Must have an associated USDC token account.
u8
required
PDA bump seed for the ProtocolState account. Stored to avoid recomputation in subsequent instructions.
Code Reference
NullResult
Stores complete scientific metadata for a single Null Knowledge Asset (NKA). Location:lib.rs:483-498
PDA Seeds: ["null_result", researcher.key().as_ref(), &(nka_counter + 1).to_le_bytes()]
Space: 8 + NullResult::INIT_SPACE (8-byte discriminator + 601 bytes)
Fields
Pubkey
required
Wallet address of the researcher who submitted this NKA. Used for
has_one constraint in submit_to_bounty.u64
required
Sequential identifier assigned from
protocol_state.nka_counter. Displayed as NKA-{specimen_number:04} in the frontend.[u8; 128]
required
UTF-8 encoded hypothesis tested in the experiment. Fixed-size buffer, zero-padded. Maximum 128 bytes.Example: “Increasing dopamine levels improves working memory in rats”
[u8; 128]
required
UTF-8 encoded summary of experimental methodology. Fixed-size buffer, zero-padded. Maximum 128 bytes.Example: “Double-blind RCT with 50 subjects, t-test analysis”
[u8; 128]
required
UTF-8 encoded description of what was expected. Fixed-size buffer, zero-padded. Maximum 128 bytes.Example: “Significant improvement in test scores (p < 0.05)”
[u8; 128]
required
UTF-8 encoded description of what actually occurred. Fixed-size buffer, zero-padded. Maximum 128 bytes.Example: “No significant difference observed (p = 0.42)”
u32
required
Statistical p-value stored as fixed-point integer (multiply by 10000). To convert:
p_value / 10000.0.Example: 4200 = 0.42, 500 = 0.05, 8700 = 0.87u32
required
Number of subjects/observations in the experiment. Stored as raw integer.Example:
50, 1000, 250[u8; 32]
required
SHA-256 hash of the underlying dataset file. Provides tamper-proof link between on-chain record and off-chain data. Can be all zeros if no file attached.Computation:
SHA256(raw_data_file_bytes)u8
required
Verification status of the null result:
0= Pending (default)1= Verified (community validated)2= Disputed (challenged by peers)
i64
required
Unix timestamp of submission. Set via
Clock::get()?.unix_timestamp in submit_null_result:62.u8
required
PDA bump seed for this NullResult account.
Code Reference
NullBounty
Bounty posted by a creator seeking a specific null result. Escrows USDC in a PDA-controlled vault. Location:lib.rs:500-515
PDA Seeds: ["null_bounty", creator.key().as_ref(), &(bounty_counter + 1).to_le_bytes()]
Vault Seeds: ["bounty_vault", bounty.key().as_ref()]
Space: 8 + NullBounty::INIT_SPACE (8-byte discriminator + 419 bytes)
Fields
Pubkey
required
Wallet address of the bounty creator. Used for
has_one constraint in approve_bounty_submission and close_bounty.u64
required
Sequential identifier assigned from
protocol_state.bounty_counter. Displayed as NB-{bounty_number:04} in the frontend.[u8; 256]
required
UTF-8 encoded description of the desired null result. Fixed-size buffer, zero-padded. Maximum 256 bytes.Example: “Negative result for CRISPR-based treatment of Huntington’s disease in mouse models”
u64
required
USDC reward in base units (6 decimals). Must be > 0 (validated in
create_bounty:78). Escrowed in vault on creation.Example: 1000000 = 1 USDC, 2500000 = 2.5 USDCPubkey
required
USDC token mint address. Stored to validate transfers in
approve_bounty_submission and close_bounty.Pubkey
required
Address of the PDA token account holding escrowed USDC. Authority is the vault itself.
i64
required
Unix timestamp deadline for bounty submissions. Currently not enforced by program but used for frontend filtering.
u8
required
Bounty lifecycle status:
0= Open (accepting submissions)1= Matched (submission linked, pending approval)2= Fulfilled (submission approved, payout complete)3= Closed (refunded, no longer active)
Pubkey
required
Address of the BountySubmission PDA if status is Matched/Fulfilled. Set to
Pubkey::default() (all zeros) when Open or Closed.i64
required
Unix timestamp of bounty creation. Set via
Clock::get()?.unix_timestamp in create_bounty:94.u8
required
PDA bump seed for the vault token account. Used to derive signer seeds for CPI transfers.
u8
required
PDA bump seed for this NullBounty account.
Code Reference
BountySubmission
Junction account linking a researcher’s NullResult to a specific NullBounty. Location:lib.rs:517-526
PDA Seeds: ["bounty_submission", bounty.key().as_ref(), null_result.key().as_ref()]
Space: 8 + BountySubmission::INIT_SPACE (8-byte discriminator + 106 bytes)
Fields
Pubkey
required
Wallet address of the researcher submitting their NKA. Copied from the linked NullResult account.
Pubkey
required
Address of the NullResult PDA being submitted. Must be owned by the submitting researcher.
Pubkey
required
Address of the NullBounty PDA this submission is for. Must have status Open when created.
u8
required
Submission approval status:
0= Pending (awaiting creator review)1= Approved (accepted, payout executed)2= Rejected (declined by creator - not currently used)
i64
required
Unix timestamp of submission. Set via
Clock::get()?.unix_timestamp in submit_to_bounty:131.u8
required
PDA bump seed for this BountySubmission account.
Code Reference
Account Size Summary
All accounts use Anchor’s
#[derive(InitSpace)] macro to automatically calculate the correct space allocation.