Skip to content

Commit 41f26b7

Browse files
committed
address rabbit's feedback
1 parent f5e8762 commit 41f26b7

9 files changed

Lines changed: 61 additions & 91 deletions

File tree

src/args/commit_state.rs

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,6 @@ use crate::args::{ArgsWithBuffer, Boolean};
99
#[repr(C)]
1010
#[derive(Copy, Clone, Pod, Zeroable, Default)]
1111
pub struct CommitBumps {
12-
/// bumps of the PDA accounts to be validated by ix
1312
pub delegation_record: u8,
1413
pub delegation_metadata: u8,
1514
pub validator_fees_vault: u8,
@@ -28,7 +27,7 @@ pub struct CommitFinalizeArgs {
2827
/// whether the account can be undelegated after the commit completes
2928
pub allow_undelegation: Boolean,
3029

31-
/// whether the account can be undelegated after the commit completes
30+
/// whether the data (in the ixdata or in the data account) is diff or full state.
3231
pub data_is_diff: Boolean,
3332

3433
/// bumps of the PDA accounts to be validated by the ix

src/args/types.rs

Lines changed: 16 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ use std::ops::Deref;
33
use bytemuck::{Pod, Zeroable};
44
use pinocchio::program_error::ProgramError;
55

6-
use crate::pod_view::PodView;
6+
use crate::{pod_view::PodView, require_ge};
77

88
///
99
/// Boolean
@@ -31,24 +31,25 @@ impl From<bool> for Boolean {
3131
///
3232
/// ArgsWithBuffer
3333
///
34-
pub struct ArgsWithBuffer<'a, H> {
35-
header: &'a H,
34+
pub struct ArgsWithBuffer<'a, Header> {
35+
header: &'a Header,
3636
pub buffer: &'a [u8],
3737
}
3838

39-
impl<'a, H: PodView> ArgsWithBuffer<'a, H> {
39+
impl<'a, Header: PodView> ArgsWithBuffer<'a, Header> {
4040
pub fn from_bytes(input: &'a [u8]) -> Result<Self, ProgramError> {
41-
let header_size = size_of::<H>();
42-
43-
if input.len() < header_size {
44-
return Err(ProgramError::InvalidInstructionData);
45-
}
46-
47-
let (header_bytes, buffer) = input.split_at(header_size);
48-
49-
let header = H::try_view_from(header_bytes)?;
50-
51-
Ok(Self { header, buffer })
41+
require_ge!(
42+
input.len(),
43+
Header::SPACE,
44+
ProgramError::InvalidInstructionData
45+
);
46+
47+
let (header_bytes, buffer) = input.split_at(Header::SPACE);
48+
49+
Ok(Self {
50+
header: Header::try_view_from(header_bytes)?,
51+
buffer,
52+
})
5253
}
5354
}
5455

src/error.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -154,6 +154,7 @@ impl From<DlpError> for pinocchio::program_error::ProgramError {
154154
}
155155
}
156156

157+
#[cfg(not(feature = "sdk"))]
157158
impl pinocchio::program_error::ToStr for DlpError {
158159
fn to_str<E>(&self) -> &'static str
159160
where

src/instruction_builder/commit_finalize.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -85,7 +85,7 @@ pub fn commit_finalize(
8585
}
8686

8787
///
88-
/// Returns accounts-data-size budget for commit_state instruction.
88+
/// Returns accounts-data-size budget for commit_finalize instruction.
8989
///
9090
/// This value can be used with ComputeBudgetInstruction::SetLoadedAccountsDataSizeLimit
9191
///

src/pod_view.rs

Lines changed: 3 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -137,20 +137,8 @@ impl<T: bytemuck::Pod> PodView for T {
137137
}
138138

139139
#[cfg(feature = "unit_test_config")]
140-
fn try_from_unaligned(unaligned_buffer: &[u8]) -> Result<Self, ProgramError> {
141-
if unaligned_buffer.len() != Self::SPACE {
142-
return Err(ProgramError::InvalidArgument);
143-
}
144-
let mut oversized_memory = vec![0; Self::SPACE + Self::ALIGN - 1];
145-
146-
let aligned_slice = {
147-
let base = oversized_memory.as_mut_ptr() as usize;
148-
let offset = (base + Self::ALIGN - 1) & !(Self::ALIGN - 1) - base;
149-
let aligned = &mut oversized_memory[offset..offset + Self::SPACE];
150-
aligned.copy_from_slice(unaligned_buffer);
151-
aligned
152-
};
153-
154-
Self::try_view_from(aligned_slice).map(|view| *view)
140+
fn try_from_unaligned(possibly_unaligned_buffer: &[u8]) -> Result<Self, ProgramError> {
141+
bytemuck::try_pod_read_unaligned(possibly_unaligned_buffer)
142+
.map_err(|_| ProgramError::InvalidArgument)
155143
}
156144
}

src/processor/fast/commit_finalize.rs

Lines changed: 8 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -8,37 +8,22 @@ use crate::processor::fast::internal::{
88
use crate::processor::fast::NewState;
99
use crate::{require_n_accounts, DiffSet};
1010

11-
/// Commit a new state of a delegated PDA
11+
/// Commit a new state, or a diff, directly to the delegated account. Unlike, CommitState and
12+
/// CommitDiff variants, this instruction does not write to any temporary account first. In other
13+
/// words, this instruction commits and finalizes both.
1214
///
1315
/// Accounts:
1416
///
1517
/// 0: `[signer]` the validator requesting the commit
1618
/// 1: `[]` the delegated account
17-
/// 2: `[writable]` the PDA storing the new state
18-
/// 3: `[writable]` the PDA storing the commit record
19-
/// 4: `[]` the delegation record
20-
/// 5: `[writable]` the delegation metadata
21-
/// 6: `[]` the validator fees vault
22-
/// 7: `[]` the program config account
19+
/// 2: `[]` the delegation record
20+
/// 3: `[writable]` the delegation metadata
21+
/// 4: `[]` the validator fees vault
22+
/// 5: `[]` the program config account
23+
/// 6: `[]` system program
2324
///
2425
/// Instruction Data: CommitFinalizeArgsWithBuffer
2526
///
26-
/// Requirements:
27-
///
28-
/// - delegation record is initialized
29-
/// - delegation metadata is initialized
30-
/// - validator fees vault is initialized
31-
/// - program config is initialized
32-
/// - commit state is uninitialized
33-
/// - commit record is uninitialized
34-
/// - delegated account holds at least the lamports indicated in the delegation record
35-
/// - account was not committed at a later slot
36-
///
37-
/// Steps:
38-
/// 1. Check that the pda is delegated
39-
/// 2. Init a new PDA to store the new state
40-
/// 3. Copy the new state to the new PDA
41-
/// 4. Init a new PDA to store the record of the new state commitment
4227
pub fn process_commit_finalize(
4328
_program_id: &Pubkey,
4429
accounts: &[AccountInfo],

src/processor/fast/internal/commit_finalize_internal.rs

Lines changed: 7 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -9,8 +9,8 @@ use crate::processor::fast::{to_pinocchio_program_error, NewState};
99
use crate::state::{DelegationMetadataFast, DelegationRecord, ProgramConfig};
1010
use crate::{
1111
apply_diff_in_place, pda, require, require_eq, require_eq_keys, require_ge,
12-
require_initialized_pda, require_initialized_pda_unsafe, require_owned_by,
13-
require_program_config, require_program_config_unsafe, require_signer,
12+
require_initialized_pda, require_initialized_pda_fast, require_owned_by,
13+
require_program_config, require_program_config_fast, require_signer,
1414
};
1515

1616
/// Arguments for the commit state internal function
@@ -71,7 +71,7 @@ pub(crate) fn process_commit_finalize_internal(
7171
false
7272
);
7373
} else {
74-
require_initialized_pda_unsafe!(
74+
require_initialized_pda_fast!(
7575
args.delegation_record_account,
7676
&[
7777
pda::DELEGATION_RECORD_TAG,
@@ -80,11 +80,10 @@ pub(crate) fn process_commit_finalize_internal(
8080
&crate::fast::ID,
8181
PDA_MARKER
8282
],
83-
&crate::fast::ID,
8483
false
8584
);
8685

87-
require_initialized_pda_unsafe!(
86+
require_initialized_pda_fast!(
8887
args.delegation_metadata_account,
8988
&[
9089
pda::DELEGATION_METADATA_TAG,
@@ -93,11 +92,10 @@ pub(crate) fn process_commit_finalize_internal(
9392
&crate::fast::ID,
9493
PDA_MARKER
9594
],
96-
&crate::fast::ID,
9795
true
9896
);
9997

100-
require_initialized_pda_unsafe!(
98+
require_initialized_pda_fast!(
10199
args.validator_fees_vault,
102100
&[
103101
pda::VALIDATOR_FEES_VAULT_TAG,
@@ -106,7 +104,6 @@ pub(crate) fn process_commit_finalize_internal(
106104
&crate::fast::ID,
107105
PDA_MARKER
108106
],
109-
&crate::fast::ID,
110107
false
111108
);
112109
}
@@ -125,14 +122,8 @@ pub(crate) fn process_commit_finalize_internal(
125122
);
126123
}
127124

128-
// Load delegation record
129125
let delegation_record_data = args.delegation_record_account.try_borrow_data()?;
130-
let delegation_record = if false {
131-
DelegationRecord::try_from_bytes_with_discriminator(&delegation_record_data)
132-
.map_err(to_pinocchio_program_error)?
133-
} else {
134-
DelegationRecord::try_view_from(&delegation_record_data.as_ref()[8..])?
135-
};
126+
let delegation_record = DelegationRecord::try_view_from(&delegation_record_data.as_ref()[8..])?;
136127

137128
// Check that the authority is allowed to commit
138129
require_eq_keys!(
@@ -168,7 +159,7 @@ pub(crate) fn process_commit_finalize_internal(
168159
false
169160
)
170161
} else {
171-
require_program_config_unsafe!(
162+
require_program_config_fast!(
172163
args.program_config_account,
173164
delegation_record.owner.as_array(),
174165
args.bumps.program_config,

src/processor/fast/utils/requires.rs

Lines changed: 11 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -264,31 +264,28 @@ macro_rules! require_initialized_pda {
264264
}
265265

266266
#[macro_export]
267-
macro_rules! require_initialized_pda_unsafe {
268-
($info:expr, $seeds: expr, $program_id: expr, $is_writable: expr) => {{
267+
macro_rules! require_initialized_pda_fast {
268+
($info:expr, $seeds: expr, $is_writable: expr) => {{
269269
use solana_sha256_hasher::hashv;
270270
let pda = hashv($seeds).to_bytes();
271271
if !pubkey_eq($info.key(), &pda) {
272272
log!(
273-
"require_initialized_pda!({}, {}, {}, {}); pubkey_eq failed",
273+
"require_initialized_pda!({}, {}, {}); pubkey_eq failed",
274274
stringify!($info),
275275
stringify!($seeds),
276-
stringify!($program_id),
277276
stringify!($is_writable)
278277
);
279278
pubkey::log($info.key());
280-
pubkey::log($program_id);
281279
return Err(ProgramError::InvalidSeeds);
282280
}
283281

284-
require_owned_by!($info, $program_id);
282+
require_owned_by!($info, &$crate::fast::ID);
285283

286284
if $is_writable && !$info.is_writable() {
287285
log!(
288-
"require_initialized_pda!({}, {}, {}, {}); is_writable expectation failed",
286+
"require_initialized_pda!({}, {}, {}); is_writable expectation failed",
289287
stringify!($info),
290288
stringify!($seeds),
291-
stringify!($program_id),
292289
stringify!($is_writable)
293290
);
294291
pubkey::log($info.key());
@@ -341,29 +338,26 @@ macro_rules! require_pda {
341338
}
342339

343340
#[macro_export]
344-
macro_rules! require_pda_unsafe {
345-
($info:expr, $seeds: expr, $program_id: expr, $is_writable: expr) => {{
341+
macro_rules! require_pda_fast {
342+
($info:expr, $seeds: expr, $is_writable: expr) => {{
346343
use solana_sha256_hasher::hashv;
347344
let pda = hashv($seeds).to_bytes();
348345
if !pubkey_eq($info.key(), &pda) {
349346
log!(
350-
"require_pda!({}, {}, {}, {}); pubkey_eq failed",
347+
"require_pda!({}, {}, {}); pubkey_eq failed",
351348
stringify!($info),
352349
stringify!($seeds),
353-
stringify!($program_id),
354350
stringify!($is_writable)
355351
);
356352
pubkey::log($info.key());
357-
pubkey::log($program_id);
358353
return Err(ProgramError::InvalidSeeds);
359354
}
360355

361356
if $is_writable && !$info.is_writable() {
362357
log!(
363-
"require_pda!({}, {}, {}, {}); is_writable expectation failed",
358+
"require_pda!({}, {}, {}); is_writable expectation failed",
364359
stringify!($info),
365360
stringify!($seeds),
366-
stringify!($program_id),
367361
stringify!($is_writable)
368362
);
369363
pubkey::log($info.key());
@@ -392,9 +386,9 @@ macro_rules! require_program_config {
392386
}
393387

394388
#[macro_export]
395-
macro_rules! require_program_config_unsafe {
389+
macro_rules! require_program_config_fast {
396390
($program_config: expr, $program: expr, $bump: expr, $is_writable: expr) => {{
397-
$crate::require_pda_unsafe!(
391+
$crate::require_pda_fast!(
398392
$program_config,
399393
&[
400394
pda::PROGRAM_CONFIG_TAG,
@@ -403,7 +397,6 @@ macro_rules! require_program_config_unsafe {
403397
&$crate::fast::ID,
404398
PDA_MARKER
405399
],
406-
&$crate::fast::ID,
407400
$is_writable
408401
);
409402
!pubkey_eq($program_config.owner(), &pinocchio_system::ID)

src/state/delegation_metadata.rs

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,9 @@
11
use std::ptr;
22

3-
use crate::{impl_to_bytes_with_discriminator_borsh, impl_try_from_bytes_with_discriminator_borsh};
3+
use crate::{
4+
impl_to_bytes_with_discriminator_borsh, impl_try_from_bytes_with_discriminator_borsh,
5+
require_ge,
6+
};
47
use borsh::{BorshDeserialize, BorshSerialize};
58
use pinocchio::{
69
account_info::{AccountInfo, RefMut},
@@ -32,6 +35,15 @@ pub struct DelegationMetadataFast<'a> {
3235

3336
impl<'a> DelegationMetadataFast<'a> {
3437
pub fn from_account(account: &'a AccountInfo) -> Result<Self, ProgramError> {
38+
require_ge!(
39+
account.data_len(),
40+
8 // last_update_nonce
41+
+ 1 // is_undelegatable
42+
+ 32 // rent_payer
43+
+ 4, // seeds (at least 4)
44+
ProgramError::InvalidAccountData
45+
);
46+
3547
Ok(Self {
3648
data: account.try_borrow_mut_data()?,
3749
})

0 commit comments

Comments
 (0)