xrpl_std/core/ledger_objects/
mod.rs

1pub mod account;
2pub mod current_escrow;
3pub mod escrow;
4pub mod nft;
5pub mod traits;
6
7pub mod current_ledger_object {
8    use crate::core::error_codes::{
9        match_result_code, match_result_code_with_expected_bytes,
10        match_result_code_with_expected_bytes_optional,
11    };
12    use crate::core::types::account_id::{ACCOUNT_ID_SIZE, AccountID};
13    use crate::core::types::amount::token_amount::TokenAmount;
14    use crate::core::types::blob::Blob;
15    use crate::core::types::hash_256::{HASH256_SIZE, Hash256};
16    use crate::host::{Result, get_current_ledger_obj_field, to_non_optional};
17
18    /// Retrieves an `AccountID` field from the current ledger object.
19    ///
20    /// # Arguments
21    ///
22    /// * `field_code` - The field code identifying which field to retrieve
23    ///
24    /// # Returns
25    ///
26    /// Returns a `Result<AccountID>` where:
27    /// * `Ok(AccountID)` - The account identifier for the specified field
28    /// * `Err(Error)` - If the field cannot be retrieved or has unexpected size
29    #[inline(always)]
30    pub fn get_account_id_field(field_code: i32) -> Result<AccountID> {
31        let mut buffer = [0x00; ACCOUNT_ID_SIZE];
32
33        let result_code =
34            unsafe { get_current_ledger_obj_field(field_code, buffer.as_mut_ptr(), buffer.len()) };
35
36        match_result_code_with_expected_bytes(result_code, buffer.len(), || buffer.into())
37    }
38
39    /// Retrieves a `TokenAmount` field from the current ledger object.
40    ///
41    /// # Arguments
42    ///
43    /// * `field_code` - The field code identifying which field to retrieve
44    ///
45    /// # Returns
46    ///
47    /// Returns a `Result<TokenAmount>` where:
48    /// * `Ok(AccountID)` - The account identifier for the specified field
49    /// * `Err(Error)` - If the field cannot be retrieved or has an unexpected size.
50    #[inline]
51    pub fn get_amount_field(field_code: i32) -> Result<TokenAmount> {
52        const BUFFER_SIZE: usize = 48usize;
53
54        let mut buffer = [0u8; BUFFER_SIZE]; // Enough to hold an Amount
55
56        let result_code =
57            unsafe { get_current_ledger_obj_field(field_code, buffer.as_mut_ptr(), BUFFER_SIZE) };
58
59        match_result_code(result_code, || TokenAmount::from(buffer))
60    }
61
62    /// Retrieves a `u16` field from the current ledger object.
63    ///
64    /// # Arguments
65    ///
66    /// * `field_code` - The field code identifying which field to retrieve
67    ///
68    /// # Returns
69    ///
70    /// Returns a `Result<TokenAmount>` where:
71    /// * `Ok(AccountID)` - The account identifier for the specified field
72    /// * `Err(Error)` - If the field cannot be retrieved or has an unexpected size.
73    #[inline]
74    pub fn get_u16_field(field_code: i32) -> Result<u16> {
75        to_non_optional(get_u16_field_optional(field_code))
76    }
77
78    /// Retrieves an optionally present `u16` field from the current ledger object.
79    ///
80    /// # Arguments
81    ///
82    /// * `field_code` - The field code identifying which field to retrieve
83    ///
84    /// # Returns
85    ///
86    /// Returns a `Result<TokenAmount>` where:
87    /// * `Ok(AccountID)` - The account identifier for the specified field
88    /// * `Err(Error)` - If the field cannot be retrieved or has an unexpected size.
89    #[inline]
90    pub fn get_u16_field_optional(field_code: i32) -> Result<Option<u16>> {
91        let mut value: u16 = 0; // <-- Initialize 8 bytes (only works due to little endian encoding in WASM and WAMR-host
92        let value_ptr: *mut u8 = (&mut value as *mut u16).cast::<u8>();
93
94        let result_code = unsafe { get_current_ledger_obj_field(field_code, value_ptr, 2) };
95
96        match_result_code_with_expected_bytes_optional(result_code, 2, || Some(value))
97    }
98
99    /// Retrieves a `u32` field from the current ledger object.
100    ///
101    /// # Arguments
102    ///
103    /// * `field_code` - The field code identifying which field to retrieve
104    ///
105    /// # Returns
106    ///
107    /// Returns a `Result<TokenAmount>` where:
108    /// * `Ok(AccountID)` - The account identifier for the specified field
109    /// * `Err(Error)` - If the field cannot be retrieved or has an unexpected size.
110    #[inline]
111    pub fn get_u32_field(field_code: i32) -> Result<u32> {
112        to_non_optional(get_u32_field_optional(field_code))
113    }
114
115    /// Retrieves an optionally present `u32` field from the current ledger object.
116    ///
117    /// # Arguments
118    ///
119    /// * `field_code` - The field code identifying which field to retrieve
120    ///
121    /// # Returns
122    ///
123    /// Returns a `Result<TokenAmount>` where:
124    /// * `Ok(AccountID)` - The account identifier for the specified field
125    /// * `Err(Error)` - If the field cannot be retrieved or has an unexpected size.
126    #[inline]
127    pub fn get_u32_field_optional(field_code: i32) -> Result<Option<u32>> {
128        let mut value: u32 = 0; // <-- Initialize 8 bytes (only works due to little endian encoding in WASM and WAMR-host
129        let value_ptr: *mut u8 = (&mut value as *mut u32).cast::<u8>();
130
131        let result_code = unsafe { get_current_ledger_obj_field(field_code, value_ptr, 4) };
132
133        match_result_code_with_expected_bytes_optional(result_code, 4, || Some(value))
134    }
135
136    /// Retrieves a `u64` field from the current ledger object.
137    ///
138    /// # Arguments
139    ///
140    /// * `field_code` - The field code identifying which AccountID field to retrieve
141    ///
142    /// # Returns
143    ///
144    /// Returns a `Result<TokenAmount>` where:
145    /// * `Ok(AccountID)` - The account identifier for the specified field
146    /// * `Err(Error)` - If the field cannot be retrieved or has an unexpected size.
147    #[inline]
148    pub fn get_u64_field(field_code: i32) -> Result<u64> {
149        to_non_optional(get_u64_field_optional(field_code))
150    }
151
152    /// Retrieves an optionally present `u64` field from the current ledger object.
153    ///
154    /// # Arguments
155    ///
156    /// * `field_code` - The field code identifying which field to retrieve
157    ///
158    /// # Returns
159    ///
160    /// Returns a `Result<TokenAmount>` where:
161    /// * `Ok(AccountID)` - The account identifier for the specified field
162    /// * `Err(Error)` - If the field cannot be retrieved or has an unexpected size.
163    #[inline]
164    pub fn get_u64_field_optional(field_code: i32) -> Result<Option<u64>> {
165        let mut value: u64 = 0u64; // <-- Initialize 8 bytes (only works due to little endian encoding in WASM and WAMR-host
166        let value_ptr: *mut u8 = (&mut value as *mut u64).cast::<u8>();
167
168        let result_code = unsafe { get_current_ledger_obj_field(field_code, value_ptr, 8) };
169
170        match_result_code_with_expected_bytes_optional(result_code, 8, || Some(value))
171    }
172
173    /// Retrieves a `Hash256` field from the current ledger object.
174    ///
175    /// # Arguments
176    ///
177    /// * `field_code` - The field code identifying which AccountID field to retrieve
178    ///
179    /// # Returns
180    ///
181    /// Returns a `Result<TokenAmount>` where:
182    /// * `Ok(AccountID)` - The account identifier for the specified field
183    /// * `Err(Error)` - If the field cannot be retrieved or has an unexpected size.
184    #[inline]
185    pub fn get_hash_256_field(field_code: i32) -> Result<Hash256> {
186        to_non_optional(get_hash_256_field_optional(field_code))
187    }
188
189    /// Retrieves an optionally present `Hash256` field from the current ledger object.
190    ///
191    /// # Arguments
192    ///
193    /// * `field_code` - The field code identifying which field to retrieve
194    ///
195    /// # Returns
196    ///
197    /// Returns a `Result<TokenAmount>` where:
198    /// * `Ok(AccountID)` - The account identifier for the specified field
199    /// * `Err(Error)` - If the field cannot be retrieved or has an unexpected size.
200    #[inline]
201    pub fn get_hash_256_field_optional(field_code: i32) -> Result<Option<Hash256>> {
202        let mut buffer = [0u8; HASH256_SIZE]; // Enough to hold 256 bits (32 bytes)
203
204        let result_code =
205            unsafe { get_current_ledger_obj_field(field_code, buffer.as_mut_ptr(), buffer.len()) };
206
207        match_result_code_with_expected_bytes(result_code, HASH256_SIZE, || {
208            Some(Hash256(buffer)) // <-- Move the buffer into a Hash256
209        })
210    }
211
212    /// Retrieves a `Blob` field from the current ledger object.
213    ///
214    /// # Arguments
215    ///
216    /// * `field_code` - The field code identifying which AccountID field to retrieve
217    ///
218    /// # Returns
219    ///
220    /// Returns a `Result<TokenAmount>` where:
221    /// * `Ok(AccountID)` - The account identifier for the specified field
222    /// * `Err(Error)` - If the field cannot be retrieved or has an unexpected size.
223    #[inline]
224    pub fn get_blob_field(field_code: i32) -> Result<Blob> {
225        to_non_optional(get_blob_field_optional(field_code))
226    }
227
228    /// Retrieves an optionally present `Blob` field from the current ledger object.
229    ///
230    /// # Arguments
231    ///
232    /// * `field_code` - The field code identifying which field to retrieve
233    ///
234    /// # Returns
235    ///
236    /// Returns a `Result<TokenAmount>` where:
237    /// * `Ok(AccountID)` - The account identifier for the specified field
238    /// * `Err(Error)` - If the field cannot be retrieved or has an unexpected size.
239    #[inline]
240    pub fn get_blob_field_optional(field_code: i32) -> Result<Option<Blob>> {
241        let mut buffer = [0u8; 1024]; // Enough to hold the largest field, which is a memo.
242
243        let result_code =
244            unsafe { get_current_ledger_obj_field(field_code, buffer.as_mut_ptr(), buffer.len()) };
245
246        match_result_code(result_code, || {
247            Some(Blob {
248                data: buffer,
249                len: result_code as usize,
250            })
251        })
252    }
253}
254
255pub mod ledger_object {
256    use crate::core::error_codes::{
257        match_result_code, match_result_code_with_expected_bytes,
258        match_result_code_with_expected_bytes_optional,
259    };
260    use crate::core::types::account_id::{ACCOUNT_ID_SIZE, AccountID};
261    use crate::core::types::amount::token_amount::TokenAmount;
262    use crate::core::types::blob::Blob;
263    use crate::core::types::hash_256::{HASH256_SIZE, Hash256};
264    use crate::host::{Result, get_ledger_obj_field, to_non_optional};
265
266    /// Retrieves an AccountID field from the current ledger object.
267    ///
268    /// # Arguments
269    ///
270    /// * `field_code` - The field code identifying which AccountID field to retrieve
271    ///
272    /// # Returns
273    ///
274    /// Returns a `Result<AccountID>` where:
275    /// * `Ok(AccountID)` - The account identifier for the specified field
276    /// * `Err(Error)` - If the field cannot be retrieved or has unexpected size
277    #[inline(always)]
278    pub fn get_account_id_field(register_num: i32, field_code: i32) -> Result<AccountID> {
279        let mut buffer = [0x00; ACCOUNT_ID_SIZE];
280
281        let result_code = unsafe {
282            get_ledger_obj_field(register_num, field_code, buffer.as_mut_ptr(), buffer.len())
283        };
284
285        match_result_code_with_expected_bytes(result_code, buffer.len(), || buffer.into())
286    }
287
288    #[inline]
289    pub fn get_amount_field(register_num: i32, field_code: i32) -> Result<TokenAmount> {
290        const BUFFER_SIZE: usize = 48usize;
291
292        let mut buffer = [0u8; BUFFER_SIZE]; // Enough to hold an Amount
293
294        let result_code = unsafe {
295            get_ledger_obj_field(register_num, field_code, buffer.as_mut_ptr(), BUFFER_SIZE)
296        };
297
298        match_result_code(result_code, || TokenAmount::from(buffer))
299    }
300
301    /// Retrieves a `u16` field from the specified ledger object.
302    ///
303    /// # Arguments
304    ///
305    /// * `register_num` - The register number holding the ledger object to look for data in.
306    /// * `field_code` - The field code identifying which field to retrieve
307    ///
308    /// # Returns
309    ///
310    /// Returns a `Result<TokenAmount>` where:
311    /// * `Ok(AccountID)` - The account identifier for the specified field
312    /// * `Err(Error)` - If the field cannot be retrieved or has an unexpected size.
313    #[inline]
314    pub fn get_u16_field(register_num: i32, field_code: i32) -> Result<u16> {
315        to_non_optional(get_u16_field_optional(register_num, field_code))
316    }
317
318    /// Retrieves an optionally present `u16` field from the specified ledger object.
319    ///
320    /// # Arguments
321    ///
322    /// * `register_num` - The register number holding the ledger object to look for data in.
323    /// * `field_code` - The field code identifying which field to retrieve
324    ///
325    /// # Returns
326    ///
327    /// Returns a `Result<TokenAmount>` where:
328    /// * `Ok(AccountID)` - The account identifier for the specified field
329    /// * `Err(Error)` - If the field cannot be retrieved or has an unexpected size.
330    #[inline]
331    pub fn get_u16_field_optional(register_num: i32, field_code: i32) -> Result<Option<u16>> {
332        let mut value: u16 = 0; // <-- Initialize 8 bytes (only works due to little endian encoding in WASM and WAMR-host
333        let value_ptr: *mut u8 = (&mut value as *mut u16).cast::<u8>();
334
335        let result_code = unsafe { get_ledger_obj_field(register_num, field_code, value_ptr, 2) };
336
337        match_result_code_with_expected_bytes_optional(result_code, 2, || Some(value))
338    }
339
340    /// Retrieves a `u32` field from the specified ledger object.
341    ///
342    /// # Arguments
343    ///
344    /// * `register_num` - The register number holding the ledger object to look for data in.
345    /// * `field_code` - The field code identifying which AccountID field to retrieve
346    ///
347    /// # Returns
348    ///
349    /// Returns a `Result<TokenAmount>` where:
350    /// * `Ok(AccountID)` - The account identifier for the specified field
351    /// * `Err(Error)` - If the field cannot be retrieved or has an unexpected size.
352    #[inline]
353    pub fn get_u32_field(register_num: i32, field_code: i32) -> Result<u32> {
354        to_non_optional(get_u32_field_optional(register_num, field_code))
355    }
356
357    /// Retrieves an optionally present `u32` field from the specified ledger object.
358    ///
359    /// # Arguments
360    ///
361    /// * `register_num` - The register number holding the ledger object to look for data in.
362    /// * `field_code` - The field code identifying which field to retrieve
363    ///
364    /// # Returns
365    ///
366    /// Returns a `Result<TokenAmount>` where:
367    /// * `Ok(AccountID)` - The account identifier for the specified field
368    /// * `Err(Error)` - If the field cannot be retrieved or has an unexpected size.
369    #[inline]
370    pub fn get_u32_field_optional(register_num: i32, field_code: i32) -> Result<Option<u32>> {
371        let mut value: u32 = 0; // <-- Initialize 8 bytes (only works due to little endian encoding in WASM and WAMR-host
372        let value_ptr: *mut u8 = (&mut value as *mut u32).cast::<u8>();
373
374        let result_code = unsafe { get_ledger_obj_field(register_num, field_code, value_ptr, 4) };
375
376        match_result_code_with_expected_bytes_optional(result_code, 4, || Some(value))
377    }
378
379    /// Retrieves a `u64` field from the specified ledger object.
380    ///
381    /// # Arguments
382    ///
383    /// * `register_num` - The register number holding the ledger object to look for data in.
384    /// * `field_code` - The field code identifying which AccountID field to retrieve
385    ///
386    /// # Returns
387    ///
388    /// Returns a `Result<TokenAmount>` where:
389    /// * `Ok(AccountID)` - The account identifier for the specified field
390    /// * `Err(Error)` - If the field cannot be retrieved or has an unexpected size.
391    #[inline]
392    pub fn get_u64_field(register_num: i32, field_code: i32) -> Result<u64> {
393        to_non_optional(get_u64_field_optional(register_num, field_code))
394    }
395
396    /// Retrieves an optionally present `u64` field from the specified ledger object.
397    ///
398    /// # Arguments
399    ///
400    /// * `register_num` - The register number holding the ledger object to look for data in.
401    /// * `field_code` - The field code identifying which field to retrieve
402    ///
403    /// # Returns
404    ///
405    /// Returns a `Result<TokenAmount>` where:
406    /// * `Ok(AccountID)` - The account identifier for the specified field
407    /// * `Err(Error)` - If the field cannot be retrieved or has an unexpected size.
408    #[inline]
409    pub fn get_u64_field_optional(register_num: i32, field_code: i32) -> Result<Option<u64>> {
410        let mut value: u64 = 0; // <-- Initialize 8 bytes (only works due to little endian encoding in WASM and WAMR-host
411        let value_ptr: *mut u8 = (&mut value as *mut u64).cast::<u8>();
412
413        let result_code = unsafe { get_ledger_obj_field(register_num, field_code, value_ptr, 8) };
414
415        match_result_code_with_expected_bytes_optional(result_code, 4, || Some(value))
416    }
417
418    #[inline]
419    pub fn get_hash_256_field(register_num: i32, field_code: i32) -> Result<Hash256> {
420        to_non_optional(get_hash_256_field_optional(register_num, field_code))
421    }
422
423    #[inline]
424    pub fn get_hash_256_field_optional(
425        register_num: i32,
426        field_code: i32,
427    ) -> Result<Option<Hash256>> {
428        let mut buffer = [0u8; HASH256_SIZE]; // Enough to hold 256 bits (32 bytes)
429
430        let result_code = unsafe {
431            get_ledger_obj_field(register_num, field_code, buffer.as_mut_ptr(), buffer.len())
432        };
433
434        match_result_code_with_expected_bytes(result_code, HASH256_SIZE, || {
435            Some(Hash256(buffer)) // <-- Move the buffer into an Hash256
436        })
437    }
438
439    #[inline]
440    pub fn get_blob_field(register_num: i32, field_code: i32) -> Result<Blob> {
441        to_non_optional(get_blob_field_optional(register_num, field_code))
442    }
443
444    #[inline]
445    pub fn get_blob_field_optional(register_num: i32, field_code: i32) -> Result<Option<Blob>> {
446        let mut buffer = [0u8; 1024]; // Enough to hold the largest field, which is a memo.
447
448        let result_code = unsafe {
449            get_ledger_obj_field(register_num, field_code, buffer.as_mut_ptr(), buffer.len())
450        };
451
452        match_result_code(result_code, || {
453            Some(Blob {
454                data: buffer,
455                len: result_code as usize,
456            })
457        })
458    }
459}