1#![no_std]
51#![deny(unsafe_op_in_unsafe_fn)]
52
53#[cfg(test)]
54extern crate std;
55
56pub mod abi;
57pub mod account;
58pub mod accounts;
59pub mod check;
60#[cfg(feature = "collections")]
61pub mod collections;
62pub mod cpi;
63pub mod dispatch;
64pub mod event;
65pub mod field_map;
66pub mod invariant;
67pub mod math;
68pub mod segment_map;
69pub mod state;
70pub mod sysvar;
71pub mod time;
72
73#[cfg(feature = "diff")]
78pub mod diff;
79#[cfg(feature = "frame")]
80pub mod frame;
81#[cfg(feature = "migrate")]
82pub mod migrate;
83#[cfg(feature = "policy")]
84pub mod policy;
85#[cfg(feature = "receipt")]
86pub mod receipt;
87#[cfg(feature = "virtual-state")]
88pub mod virtual_state;
89
90pub use field_map::*;
91
92#[doc(hidden)]
98pub use hopper_runtime as __runtime;
99
100#[doc(hidden)]
109pub const fn __sha256_const(data: &[u8]) -> [u8; 32] {
110 #[cfg(feature = "sha2-layout-id")]
111 {
112 sha2_const_stable::Sha256::new().update(data).finalize()
113 }
114 #[cfg(not(feature = "sha2-layout-id"))]
115 {
116 __fnv_expand_const(data)
117 }
118}
119
120#[doc(hidden)]
126#[cfg(not(feature = "sha2-layout-id"))]
127pub const fn __fnv_expand_const(data: &[u8]) -> [u8; 32] {
128 const FNV_OFFSET: u64 = 0xcbf2_9ce4_8422_2325;
129 const FNV_PRIME: u64 = 0x0000_0100_0000_01b3;
130 let mut out = [0u8; 32];
131 let mut block: u8 = 0;
132 while block < 4 {
133 let mut h: u64 = FNV_OFFSET ^ (block as u64).wrapping_mul(0x9E37_79B9_7F4A_7C15);
134 let mut i = 0;
135 while i < data.len() {
136 h ^= data[i] as u64;
137 h = h.wrapping_mul(FNV_PRIME);
138 i += 1;
139 }
140 let le = h.to_le_bytes();
141 let base = (block as usize) * 8;
142 out[base] = le[0];
143 out[base + 1] = le[1];
144 out[base + 2] = le[2];
145 out[base + 3] = le[3];
146 out[base + 4] = le[4];
147 out[base + 5] = le[5];
148 out[base + 6] = le[6];
149 out[base + 7] = le[7];
150 block += 1;
151 }
152 out
153}
154
155#[doc(hidden)]
157pub const fn __str_eq(a: &str, b: &str) -> bool {
158 let a = a.as_bytes();
159 let b = b.as_bytes();
160 if a.len() != b.len() {
161 return false;
162 }
163 let mut i = 0;
164 while i < a.len() {
165 if a[i] != b[i] {
166 return false;
167 }
168 i += 1;
169 }
170 true
171}
172
173#[doc(hidden)]
175pub const fn const_str_eq(a: &str, b: &str) -> bool {
176 __str_eq(a, b)
177}
178
179#[cfg(feature = "anchor-compat")]
194pub const fn anchor_discriminator(instruction_name: &str) -> [u8; 8] {
195 let hash = sha2_const_stable::Sha256::new()
196 .update(b"global:")
197 .update(instruction_name.as_bytes())
198 .finalize();
199 [
200 hash[0], hash[1], hash[2], hash[3], hash[4], hash[5], hash[6], hash[7],
201 ]
202}
203
204#[cfg(feature = "anchor-compat")]
209pub const fn anchor_account_discriminator(type_name: &str) -> [u8; 8] {
210 let hash = sha2_const_stable::Sha256::new()
211 .update(b"account:")
212 .update(type_name.as_bytes())
213 .finalize();
214 [
215 hash[0], hash[1], hash[2], hash[3], hash[4], hash[5], hash[6], hash[7],
216 ]
217}
218
219pub mod prelude_core {
232 pub use crate::abi::{
234 Authority, LayoutFingerprint, Mint, Program, Token, TokenAccount, TypedAddress,
235 UntypedAddress,
236 };
237
238 pub use crate::account::{
240 cast_unchecked, cast_unchecked_mut, pod_from_bytes, pod_from_bytes_mut, pod_read,
241 pod_write, read_layout_id, write_header, zero_init, AccountHeader, AccountReader,
242 FixedLayout, Pod, ReallocGuard, VerifiedAccount, VerifiedAccountMut, CLOSE_SENTINEL,
243 HEADER_LEN,
244 };
245
246 pub use crate::accounts::{
248 hopper_entry, AccountMetaProvider, HopperAccount, HopperAccounts, HopperCtx, HopperIx,
249 ProgramAccount, ProgramRef, SegmentedAccount, SignerAccount, UncheckedAccount,
250 ValidateAccount,
251 };
252
253 pub use crate::check::fast::{
255 check_account_fast, check_authority_fast, check_executable_fast, check_signer_fast,
256 check_writable_fast, HEADER_EXECUTABLE, HEADER_SIGNER, HEADER_SIGNER_WRITABLE,
257 HEADER_WRITABLE,
258 };
259 pub use crate::check::modifier::{
260 Account, AccountMut, FromAccount, HasView, HopperLayout, Mut, Signer,
261 };
262 pub use crate::check::{
263 check_account, check_discriminator, check_executable, check_has_one, check_keys_eq,
264 check_owner, check_owner_multi, check_program, check_rent_exempt, check_signer, check_size,
265 check_writable, find_and_verify_pda, is_zero_address, keys_eq_fast, rent_exempt_min,
266 verify_pda, verify_pda_cached,
267 };
268
269 pub use crate::dispatch::{
271 dispatch_instruction, dispatch_instruction_8, dispatch_instruction_u16, EVENT_CPI_PREFIX,
272 };
273 #[cfg(feature = "cpi")]
274 pub use crate::event::emit_event_cpi;
275 pub use crate::event::{emit_event, emit_event_tagged, emit_slices};
276
277 pub use crate::field_map::{FieldInfo, FieldMap};
279 pub use crate::segment_map::{assert_segment_field_alignment, SegmentMap, StaticSegment};
280 pub use hopper_runtime::segment_borrow::{AccessKind, SegmentBorrow, SegmentBorrowRegistry};
281 pub use hopper_runtime::Segment;
282
283 pub use crate::cpi::{HopperCpi, HopperCpiBuf};
285
286 pub use crate::invariant::{check_invariant, check_invariant_fn, InvariantSet};
288 pub use crate::math::{
289 bps_of, bps_of_ceil, checked_add, checked_div, checked_div_ceil, checked_mul,
290 checked_mul_div, checked_mul_div_ceil, checked_pow, checked_sub, div_ceil, scale_amount,
291 scale_amount_ceil, scale_bps, scale_fraction, to_u64,
292 };
293 pub use crate::state::check_state_transition;
294 pub use crate::sysvar::{CachedClock, CachedRent, SysvarContext};
295 pub use crate::time::{check_cooldown_elapsed, check_deadline_not_passed, check_staleness};
296
297 pub use crate::account::segment_role::{
299 SegmentRole, SEG_ROLE_AUDIT, SEG_ROLE_CACHE, SEG_ROLE_CORE, SEG_ROLE_EXTENSION,
300 SEG_ROLE_INDEX, SEG_ROLE_JOURNAL, SEG_ROLE_SHARD,
301 };
302 pub use crate::account::{
303 segment_id, SegmentEntry, SegmentId, SegmentRegistry, SegmentRegistryMut,
304 };
305
306 #[cfg(feature = "anchor-compat")]
308 pub use crate::{anchor_account_discriminator, anchor_discriminator};
309
310 #[cfg(feature = "collections")]
312 pub use crate::collections::journal::{Journal, JournalReader};
313 #[cfg(feature = "collections")]
314 pub use crate::collections::slab::Slab;
315 #[cfg(feature = "collections")]
316 pub use crate::collections::{BitSet, FixedVec, PackedMap, RingBuffer, SlotMap, SortedVec};
317}
318
319pub mod prelude_advanced {
328 pub use crate::check::guards::{
330 check_lamport_conservation, check_writable_coherence, require_all_unique,
331 require_authority, require_owned_writable, require_payer, require_unique_signers,
332 require_unique_writable, snapshot_lamports,
333 };
334 pub use crate::check::trust::{
335 load_foreign_with_profile, TrustFlags, TrustLevel, TrustProfile,
336 };
337 pub use crate::check::{
338 check_no_subsequent_invocation, detect_flash_loan_bracket, require_top_level,
339 };
340
341 #[cfg(feature = "diff")]
342 pub use crate::diff::{StateDiff, StateSnapshot};
343
344 #[cfg(feature = "explain")]
345 pub use crate::accounts::{AccountExplain, ContextExplain, ExplainAccount};
346
347 #[cfg(feature = "migrate")]
348 pub use crate::accounts::MigratingAccount;
349
350 #[cfg(feature = "frame")]
351 pub use crate::frame::args::{InstructionArgs, ValidateArgs};
352 #[cfg(feature = "frame")]
353 pub use crate::frame::phase::{ExecutionContext, PhasedFrame, ResolvedFrame, ValidatedFrame};
354 #[cfg(feature = "frame")]
355 pub use crate::frame::{Frame, FrameAccount, FrameAccountMut};
356
357 #[cfg(feature = "graph")]
358 pub use crate::check::graph::{
359 require_all_unique_accounts, require_data_min, require_keys_equal, require_lamports_gte,
360 require_owned_at, require_signer_at, require_unique, require_unique_signer_accounts,
361 require_unique_writable_accounts, require_writable_at, AccountConstraint,
362 PostMutationValidator, TransactionConstraint, TransitionRulePack, Validatable,
363 ValidationBundle, ValidationContext, ValidationGraph, ValidationGroup,
364 };
365
366 #[cfg(feature = "migrate")]
367 pub use crate::migrate::{migrate_append, MigrationKind};
368
369 #[cfg(feature = "policy")]
370 pub use crate::policy::{
371 Capability, CapabilitySet, InstructionPolicy, PolicyPackDescriptor, PolicyRequirement,
372 RequirementSet, ACCOUNT_CLOSE_CAPS, ACCOUNT_CLOSE_POLICY, ACCOUNT_INIT_CAPS,
373 ACCOUNT_INIT_POLICY, AUTHORITY_CHANGE_CAPS, AUTHORITY_CHANGE_POLICY, EXTERNAL_CALL_CAPS,
374 EXTERNAL_CALL_POLICY, JOURNAL_TOUCH_CAPS, JOURNAL_TOUCH_POLICY, MIGRATION_SENSITIVE_CAPS,
375 MIGRATION_SENSITIVE_POLICY, NAMED_POLICY_PACKS, READ_ONLY_AUDIT_CAPS,
376 READ_ONLY_AUDIT_POLICY, SHARD_MUTATION_CAPS, SHARD_MUTATION_POLICY, TREASURY_WRITE_CAPS,
377 TREASURY_WRITE_POLICY,
378 };
379
380 #[cfg(feature = "receipt")]
381 pub use crate::receipt::{
382 CompatImpact, DecodedReceipt, FailureStage, Phase, ReceiptExplain, StateReceipt,
383 FAILED_INVARIANT_NONE, RECEIPT_SIZE, RECEIPT_SIZE_LEGACY,
384 };
385
386 #[cfg(feature = "virtual-state")]
387 pub use crate::virtual_state::{ShardedAccess, VirtualSlot, VirtualState};
388}
389
390pub mod prelude {
398 pub use crate::abi::*;
399 pub use crate::abi::{
400 Authority, Mint, Program, Token, TokenAccount, TypedAddress, UntypedAddress,
401 };
402 pub use crate::abi::{FingerprintTransition, LayoutFingerprint};
403 pub use crate::account::segment_role::{
404 SegmentRole, SEG_ROLE_AUDIT, SEG_ROLE_CACHE, SEG_ROLE_CORE, SEG_ROLE_EXTENSION,
405 SEG_ROLE_INDEX, SEG_ROLE_JOURNAL, SEG_ROLE_SHARD,
406 };
407 pub use crate::account::{
408 cast_unchecked, cast_unchecked_mut, pod_from_bytes, pod_from_bytes_mut, pod_read,
409 pod_write, read_layout_id, write_header, zero_init, AccountHeader, AccountReader,
410 FixedLayout, Pod, ReallocGuard, VerifiedAccount, VerifiedAccountMut, CLOSE_SENTINEL,
411 HEADER_LEN,
412 };
413 pub use crate::account::{
414 segment_id, SegmentEntry, SegmentId, SegmentRegistry, SegmentRegistryMut,
415 };
416 #[cfg(feature = "migrate")]
417 pub use crate::accounts::MigratingAccount;
418 pub use crate::accounts::{
419 hopper_entry, AccountMetaProvider, HopperAccount, HopperAccounts, HopperCtx, HopperIx,
420 ProgramAccount, ProgramRef, SegmentedAccount, SignerAccount, UncheckedAccount,
421 ValidateAccount,
422 };
423 #[cfg(feature = "explain")]
424 pub use crate::accounts::{AccountExplain, ContextExplain, ExplainAccount};
425 #[cfg(feature = "anchor-compat")]
426 pub use crate::anchor_account_discriminator;
427 #[cfg(feature = "anchor-compat")]
428 pub use crate::anchor_discriminator;
429 pub use crate::check::fast::{
430 check_account_fast, check_authority_fast, check_executable_fast, check_signer_fast,
431 check_writable_fast, HEADER_EXECUTABLE, HEADER_SIGNER, HEADER_SIGNER_WRITABLE,
432 HEADER_WRITABLE,
433 };
434 #[cfg(feature = "graph")]
435 pub use crate::check::graph::{
436 require_all_unique_accounts, require_data_min, require_keys_equal, require_lamports_gte,
437 require_owned_at, require_signer_at, require_unique, require_unique_signer_accounts,
438 require_unique_writable_accounts, require_writable_at, AccountConstraint,
439 PostMutationValidator, TransactionConstraint, TransitionRulePack, Validatable,
440 ValidationBundle, ValidationContext, ValidationGraph, ValidationGroup,
441 };
442 pub use crate::check::guards::{
443 check_lamport_conservation, check_writable_coherence, require_all_unique,
444 require_authority, require_owned_writable, require_payer, require_unique_signers,
445 require_unique_writable, snapshot_lamports,
446 };
447 pub use crate::check::modifier::{
448 Account, AccountMut, FromAccount, HasView, HopperLayout, Mut, Signer,
449 };
450 pub use crate::check::trust::{
451 load_foreign_with_profile, TrustFlags, TrustLevel, TrustProfile,
452 };
453 pub use crate::check::{
454 check_account, check_discriminator, check_has_one, check_keys_eq,
455 check_no_subsequent_invocation, check_owner, check_owner_multi, check_rent_exempt,
456 check_signer, check_size, check_writable, detect_flash_loan_bracket, find_and_verify_pda,
457 is_zero_address, keys_eq_fast, rent_exempt_min, require_top_level, verify_pda,
458 verify_pda_cached,
459 };
460 #[cfg(feature = "collections")]
461 pub use crate::collections::journal::{Journal, JournalReader};
462 #[cfg(feature = "collections")]
463 pub use crate::collections::slab::Slab;
464 #[cfg(feature = "collections")]
465 pub use crate::collections::{BitSet, FixedVec, PackedMap, RingBuffer, SlotMap, SortedVec};
466 pub use crate::cpi::{HopperCpi, HopperCpiBuf};
467 #[cfg(feature = "diff")]
468 pub use crate::diff::{StateDiff, StateSnapshot};
469 pub use crate::dispatch::{
470 dispatch_instruction, dispatch_instruction_8, dispatch_instruction_u16, EVENT_CPI_PREFIX,
471 };
472 #[cfg(feature = "cpi")]
473 pub use crate::event::emit_event_cpi;
474 pub use crate::event::{emit_event, emit_event_tagged, emit_slices};
475 pub use crate::field_map::{FieldInfo, FieldMap};
476 #[cfg(feature = "frame")]
477 pub use crate::frame::args::{InstructionArgs, ValidateArgs};
478 #[cfg(feature = "frame")]
479 pub use crate::frame::phase::{ExecutionContext, PhasedFrame, ResolvedFrame, ValidatedFrame};
480 #[cfg(feature = "frame")]
481 pub use crate::frame::{Frame, FrameAccount, FrameAccountMut};
482 pub use crate::invariant::{check_invariant, check_invariant_fn, InvariantSet};
483 pub use crate::math::{
484 bps_of, bps_of_ceil, checked_add, checked_div, checked_div_ceil, checked_mul,
485 checked_mul_div, checked_mul_div_ceil, checked_pow, checked_sub, div_ceil, scale_amount,
486 scale_amount_ceil, scale_bps, scale_fraction, to_u64,
487 };
488 #[cfg(feature = "migrate")]
489 pub use crate::migrate::{migrate_append, MigrationKind};
490 #[cfg(feature = "policy")]
491 pub use crate::policy::{
492 Capability,
493 CapabilitySet,
494 InstructionPolicy,
495 PolicyPackDescriptor,
496 PolicyRequirement,
497 RequirementSet,
498 ACCOUNT_CLOSE_CAPS,
499 ACCOUNT_CLOSE_POLICY,
500 ACCOUNT_INIT_CAPS,
501 ACCOUNT_INIT_POLICY,
502 AUTHORITY_CHANGE_CAPS,
503 AUTHORITY_CHANGE_POLICY,
504 EXTERNAL_CALL_CAPS,
505 EXTERNAL_CALL_POLICY,
506 JOURNAL_TOUCH_CAPS,
507 JOURNAL_TOUCH_POLICY,
508 MIGRATION_SENSITIVE_CAPS,
509 MIGRATION_SENSITIVE_POLICY,
510 NAMED_POLICY_PACKS,
511 READ_ONLY_AUDIT_CAPS,
512 READ_ONLY_AUDIT_POLICY,
513 SHARD_MUTATION_CAPS,
514 SHARD_MUTATION_POLICY,
515 TREASURY_WRITE_CAPS,
516 TREASURY_WRITE_POLICY,
518 };
519 #[cfg(feature = "receipt")]
520 pub use crate::receipt::{
521 CompatImpact, DecodedReceipt, FailureStage, Phase, ReceiptExplain, StateReceipt,
522 FAILED_INVARIANT_NONE, RECEIPT_SIZE, RECEIPT_SIZE_LEGACY,
523 };
524 pub use crate::segment_map::{assert_segment_field_alignment, SegmentMap, StaticSegment};
525 pub use crate::state::check_state_transition;
526 pub use crate::sysvar::{CachedClock, CachedRent, SysvarContext};
527 pub use crate::time::{check_cooldown_elapsed, check_deadline_not_passed, check_staleness};
528 #[cfg(feature = "virtual-state")]
529 pub use crate::virtual_state::{ShardedAccess, VirtualSlot, VirtualState};
530 pub use hopper_runtime::segment_borrow::{AccessKind, SegmentBorrow, SegmentBorrowRegistry};
531}