Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: Use stateful instruction in AUTH #22

Merged
merged 36 commits into from
Mar 26, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
36 commits
Select commit Hold shift + click to select a range
dc0277f
added the rest of bls12-381 precompile entrypoints
fgimenez Mar 15, 2024
52d8451
add g1_add test and first failing case
fgimenez Mar 18, 2024
33d2134
initial implementation
fgimenez Mar 18, 2024
18dcbb5
remove impl functions
fgimenez Mar 19, 2024
9cccfe7
use bls12_381 crate, g1add complete
fgimenez Mar 19, 2024
86cd95c
more tests and take into account point of inifinity; more constants
fgimenez Mar 19, 2024
9f36fe0
typo
fgimenez Mar 20, 2024
41074be
add insert_precompiles function
fgimenez Mar 20, 2024
a8e2a48
feat: set authorized context variable in AUTH
fgimenez Mar 21, 2024
97bb353
setup context
fgimenez Mar 22, 2024
95a8bf4
set authority
fgimenez Mar 22, 2024
7f70f29
use revm_precompile::u64_to_address
fgimenez Mar 22, 2024
1fa0aaf
use revm_precompile::u64_to_address
fgimenez Mar 22, 2024
4990005
pass CustomContext to instructions
fgimenez Mar 22, 2024
9ca2468
removed leftovers
fgimenez Mar 22, 2024
77aedcd
properly set contexts for each instruction
fgimenez Mar 22, 2024
56e41a9
add missing lifetime and fix variable name
fgimenez Mar 22, 2024
a7728c5
use macros from revm_interpreter
fgimenez Mar 22, 2024
ab34b06
CustomContext -> Eip3074Context
fgimenez Mar 22, 2024
9278852
add Eip3074Context docs
fgimenez Mar 22, 2024
73fc46a
check authority context variable is set
fgimenez Mar 23, 2024
ce43e11
authority -> authorized
fgimenez Mar 23, 2024
5165e33
generalized instructions context
fgimenez Mar 23, 2024
b85916e
get and set methods for InstructionsContext
fgimenez Mar 23, 2024
4f86b33
refactor and &self for InstructionsContext.reset
fgimenez Mar 23, 2024
1045560
get and set named variables
fgimenez Mar 24, 2024
a7b8e0f
instruction context submodule and test with context writer and reader…
fgimenez Mar 24, 2024
4478554
example of using Inspector to clear instruction context
fgimenez Mar 24, 2024
08f6307
use EndHandle to clear context instructions instead of inspector
fgimenez Mar 25, 2024
860d5d0
InstructionContext handles &'static str keys
fgimenez Mar 25, 2024
29c2f0b
allow clippy
fgimenez Mar 25, 2024
354ff23
InstructionsContext doc
fgimenez Mar 25, 2024
8f397e1
simplify InstructionContext methods
fgimenez Mar 25, 2024
821d4d9
remove inspector
fgimenez Mar 25, 2024
cec20f1
typo
fgimenez Mar 25, 2024
0ad5948
merge handler_registers
fgimenez Mar 25, 2024
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
655 changes: 319 additions & 336 deletions Cargo.lock

Large diffs are not rendered by default.

22 changes: 9 additions & 13 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -50,25 +50,21 @@ alphanet-precompile = { path = "crates/precompile" }
tokio = { version = "1.21", default-features = false }

# reth
reth = { git = "https://github.com/paradigmxyz/reth.git", rev = "82b6504", features = ["optimism"] }
reth-node-api = { git = "https://github.com/paradigmxyz/reth.git", rev = "82b6504" }
reth-node-optimism = { git = "https://github.com/paradigmxyz/reth.git", rev = "82b6504" }
reth-tracing = { git = "https://github.com/paradigmxyz/reth.git", rev = "82b6504" }
reth = { git = "https://github.com/paradigmxyz/reth.git", rev = "1a42b09", features = ["optimism"] }
reth-node-api = { git = "https://github.com/paradigmxyz/reth.git", rev = "1a42b09" }
reth-node-optimism = { git = "https://github.com/paradigmxyz/reth.git", rev = "1a42b09" }
reth-tracing = { git = "https://github.com/paradigmxyz/reth.git", rev = "1a42b09" }

# revm
revm = { version = "7.1.0", features = ["std", "secp256k1"], default-features = false }
revm-inspectors = { git = "https://github.com/paradigmxyz/evm-inspectors", rev = "1f935e7" }
revm-interpreter = { version = "3.3.0", features = ["std"], default-features = false }
revm-precompile = { version = "5.0.0", features = ["std"], default-features = false }
revm-primitives = { version = "3.0.0", features = ["std"], default-features = false }
revm = { version = "7.2.0", features = ["std", "secp256k1"], default-features = false }
revm-inspectors = { git = "https://github.com/paradigmxyz/evm-inspectors", rev = "2b48b65" }
revm-interpreter = { version = "3.4.0", features = ["std"], default-features = false }
revm-precompile = { version = "5.1.0", features = ["std"], default-features = false }
revm-primitives = { version = "3.1.0", features = ["std"], default-features = false }

# misc
clap = "4"
eyre = "0.6.12"
secp256k1 = { version = "0.28.2", default-features = false, features = [
"alloc",
"recovery",
] }
tracing = "0.1.0"

# misc-testing
Expand Down
6 changes: 3 additions & 3 deletions bin/alphanet/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -19,14 +19,14 @@ reth-node-optimism.workspace = true
clap = { workspace = true, features = ["derive"] }

[target.'cfg(not(windows))'.dependencies]
jemallocator = { version = "0.5", optional = true }
tikv-jemallocator = { version = "0.5", optional = true }

[features]
default = ["jemalloc"]
asm-keccak = []

jemalloc = ["dep:jemallocator"]
jemalloc-prof = ["jemalloc", "jemallocator?/profiling"]
jemalloc = ["dep:tikv-jemallocator"]
jemalloc-prof = ["jemalloc", "tikv-jemallocator?/profiling"]

min-error-logs = ["tracing/release_max_level_error"]
min-warn-logs = ["tracing/release_max_level_warn"]
Expand Down
2 changes: 1 addition & 1 deletion bin/alphanet/src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ use reth_node_optimism::{args::RollupArgs, OptimismEngineTypes, OptimismNode};
// We use jemalloc for performance reasons.
#[cfg(all(feature = "jemalloc", unix))]
#[global_allocator]
static ALLOC: jemallocator::Jemalloc = jemallocator::Jemalloc;
static ALLOC: tikv_jemallocator::Jemalloc = tikv_jemallocator::Jemalloc;

fn main() {
reth::sigsegv_handler::install();
Expand Down
2 changes: 1 addition & 1 deletion crates/instructions/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -12,8 +12,8 @@ categories.workspace = true
[dependencies]
revm.workspace = true
revm-interpreter.workspace = true
revm-precompile.workspace = true
revm-primitives.workspace = true
secp256k1.workspace = true

[dev-dependencies]
secp256k1 = { version = "0.28.2", default-features = false, features = [
Expand Down
110 changes: 110 additions & 0 deletions crates/instructions/src/context.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,110 @@
use std::{cell::RefCell, collections::HashMap, rc::Rc};

#[derive(Clone, Default)]
/// Context variables to be used in instructions. The data set here is expected
/// to live for the duration of a single transaction.
/// Similar to TStore for arbitrary data.
pub struct InstructionsContext {
/// Contains the actual variables. Is meant to be accessed both for reads
/// and writes using interior mutability, so that the Instruction and
/// BoxedInstruction signatures are observed.
inner: Rc<RefCell<HashMap<&'static str, Vec<u8>>>>,
}
Comment on lines +4 to +12
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

the docs here are great


impl InstructionsContext {
/// Sets a value for the given key.
pub fn set(&self, key: &'static str, value: Vec<u8>) {
let _ = self.inner.borrow_mut().insert(key, value);
}

/// Gets the value for the given key, if any.
pub fn get(&self, key: &'static str) -> Option<Vec<u8>> {
self.inner.borrow().get(&key).cloned()
}

/// Empties inner state.
pub fn clear(&self) {
self.inner.borrow_mut().clear();
}
}

#[cfg(test)]
mod tests {
use super::*;
use revm::{Evm, InMemoryDB};
use revm_interpreter::Interpreter;
use revm_primitives::{address, AccountInfo, Bytecode, TransactTo, U256};
use std::sync::Arc;

#[test]
fn test_set_get() {
let ctx = InstructionsContext::default();
let key = "my-key";
let value = vec![0x01, 0x02];

ctx.set(key, value.clone());

let cloned_ctx = ctx.clone();
assert_eq!(cloned_ctx.get(key).unwrap(), value);
}

#[test]
fn test_context_variables_are_available_during_tx() {
let code = Bytecode::new_raw([0xEE, 0xEF, 0x00].into());
let code_hash = code.hash_slow();
let to_addr = address!("ffffffffffffffffffffffffffffffffffffffff");

// initialize the custom context and make sure it's None for a given key
let custom_context = InstructionsContext::default();
let key = "my-key";
assert_eq!(custom_context.get(key), None);

let to_capture_instructions = custom_context.clone();
let to_capture_post_execution = custom_context.clone();
let mut evm = Evm::builder()
.with_db(InMemoryDB::default())
.modify_db(|db| {
db.insert_account_info(to_addr, AccountInfo::new(U256::ZERO, 0, code_hash, code))
})
.modify_tx_env(|tx| tx.transact_to = TransactTo::Call(to_addr))
.append_handler_register_box(Box::new(move |handler| {
let writer_context = to_capture_instructions.clone();
let writer_instruction = Box::new(
move |_interp: &mut Interpreter, _host: &mut Evm<'_, (), InMemoryDB>| {
// write into the context variable.
writer_context.set(key, vec![0x01, 0x02]);
},
);
let reader_context = to_capture_instructions.clone();
let reader_instruction = Box::new(
move |_interp: &mut Interpreter, _host: &mut Evm<'_, (), InMemoryDB>| {
// read from context variable and clear.
assert_eq!(reader_context.get(key).unwrap(), vec![0x01, 0x02]);
},
);

let mut table = handler.take_instruction_table();
table = table.map(|mut table| {
table.insert_boxed(0xEE, writer_instruction);
table.insert_boxed(0xEF, reader_instruction);
table
});
handler.instruction_table = table;

let post_execution_context = to_capture_post_execution.clone();
#[allow(clippy::arc_with_non_send_sync)]
{
handler.post_execution.end = Arc::new(move |_, outcome: _| {
post_execution_context.clear();
outcome
});
Comment on lines +55 to +100
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

love the test

}
}))
.build();

let _result_and_state = evm.transact().unwrap();

// ensure the custom context was cleared
assert_eq!(custom_context.get(key), None);
}
}