mirror of
https://github.com/pezkuwichain/revive.git
synced 2026-04-26 04:07:57 +00:00
6585973e99
- Update pallet-revive dependency - Implement calls according to pallet-revive call semantics - Switch to the new return data API in pallet revive and get rid of return data buffer - Remove a bunch of resulting dead code
109 lines
3.9 KiB
Rust
109 lines
3.9 KiB
Rust
use inkwell::{
|
|
builder::Builder,
|
|
context::Context,
|
|
module::Module,
|
|
types::{BasicType, StructType},
|
|
values::{BasicValueEnum, PointerValue},
|
|
};
|
|
|
|
/// Creates a module that sets the PolkaVM minimum stack size to [`size`] if linked in.
|
|
pub fn min_stack_size<'context>(
|
|
context: &'context Context,
|
|
module_name: &str,
|
|
size: u32,
|
|
) -> Module<'context> {
|
|
let module = context.create_module(module_name);
|
|
module.set_inline_assembly(&format!(
|
|
".pushsection .polkavm_min_stack_size,\"\",@progbits
|
|
.word {size}
|
|
.popsection"
|
|
));
|
|
module
|
|
}
|
|
|
|
/// Helper for building function calls with stack spilled arguments.
|
|
/// - `pointer`: points to a struct of the packed argument struct type
|
|
/// - `type`: the packed argument struct type
|
|
/// - `arguments`: a correctly ordered list of the struct field values
|
|
pub fn spill<'ctx>(
|
|
builder: &Builder<'ctx>,
|
|
pointer: PointerValue<'ctx>,
|
|
r#type: StructType<'ctx>,
|
|
arguments: &[BasicValueEnum<'ctx>],
|
|
) -> anyhow::Result<()> {
|
|
for index in 0..r#type.get_field_types().len() {
|
|
let field_pointer = builder.build_struct_gep(
|
|
r#type,
|
|
pointer,
|
|
index as u32,
|
|
&format!("spill_parameter_{}", index),
|
|
)?;
|
|
let field_value = arguments
|
|
.get(index)
|
|
.ok_or_else(|| anyhow::anyhow!("invalid index {index} for struct type {}", r#type))?;
|
|
builder.build_store(field_pointer, *field_value)?;
|
|
}
|
|
|
|
Ok(())
|
|
}
|
|
|
|
/// Returns a packed struct argument type for the `instantiate` API.
|
|
pub fn instantiate(context: &Context) -> StructType {
|
|
context.struct_type(
|
|
&[
|
|
// code_hash_ptr: u32,
|
|
context.ptr_type(Default::default()).as_basic_type_enum(),
|
|
// ref_time_limit: u64,
|
|
context.i64_type().as_basic_type_enum(),
|
|
// proof_size_limit: u64,
|
|
context.i64_type().as_basic_type_enum(),
|
|
// deposit_ptr: u32,
|
|
context.ptr_type(Default::default()).as_basic_type_enum(),
|
|
// value_ptr: u32,
|
|
context.ptr_type(Default::default()).as_basic_type_enum(),
|
|
// input_data_ptr: u32,
|
|
context.ptr_type(Default::default()).as_basic_type_enum(),
|
|
// input_data_len: u32,
|
|
context.i32_type().as_basic_type_enum(),
|
|
// address_ptr: u32,
|
|
context.ptr_type(Default::default()).as_basic_type_enum(),
|
|
// output_ptr: u32,
|
|
context.ptr_type(Default::default()).as_basic_type_enum(),
|
|
// output_len_ptr: u32,
|
|
context.ptr_type(Default::default()).as_basic_type_enum(),
|
|
// salt_ptr: u32,
|
|
context.ptr_type(Default::default()).as_basic_type_enum(),
|
|
],
|
|
true,
|
|
)
|
|
}
|
|
|
|
/// Returns a packed struct argument type for the `call` API.
|
|
pub fn call(context: &Context) -> StructType {
|
|
context.struct_type(
|
|
&[
|
|
// flags: u32,
|
|
context.i32_type().as_basic_type_enum(),
|
|
// address_ptr:
|
|
context.ptr_type(Default::default()).as_basic_type_enum(),
|
|
// ref_time_limit: u64,
|
|
context.i64_type().as_basic_type_enum(),
|
|
// proof_size_limit: u64,
|
|
context.i64_type().as_basic_type_enum(),
|
|
// deposit_ptr: u32,
|
|
context.ptr_type(Default::default()).as_basic_type_enum(),
|
|
// value_ptr: u32,
|
|
context.ptr_type(Default::default()).as_basic_type_enum(),
|
|
// input_data_ptr: u32,
|
|
context.ptr_type(Default::default()).as_basic_type_enum(),
|
|
// input_data_len: u32,
|
|
context.i32_type().as_basic_type_enum(),
|
|
// output_ptr: u32,
|
|
context.ptr_type(Default::default()).as_basic_type_enum(),
|
|
// output_len_ptr: u32,
|
|
context.ptr_type(Default::default()).as_basic_type_enum(),
|
|
],
|
|
true,
|
|
)
|
|
}
|