Skip to content

Instantly share code, notes, and snippets.

@adria0
Last active October 21, 2020 15:56
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save adria0/829f857351e7a3e758f02ecfba7472ef to your computer and use it in GitHub Desktop.
Save adria0/829f857351e7a3e758f02ecfba7472ef to your computer and use it in GitHub Desktop.
JournalTest1
use std::collections::HashSet;
use std::rc::Rc;
use std::cell::RefCell;
struct AccessList(Rc<AccessListInt>);
struct AccessListInt {
v : RefCell<Option<HashSet<usize>>>,
prev: Option<Rc<AccessListInt>>
}
impl Default for AccessList {
fn default() -> Self {
AccessList( Rc::new (
AccessListInt{
v : RefCell::new(None),
prev: None
}
))
}
}
impl Clone for AccessList {
fn clone(&self) -> Self {
AccessList ( self.0.clone() )
}
}
impl AccessList {
fn clone(&self) -> Self {
AccessList ( Rc::new (
AccessListInt {
v : RefCell::new(None),
prev: Some(self.0.clone())
}
))
}
pub fn insert(&self, n : usize) {
let mut v = self.0.v.borrow_mut();
if v.is_none() {
*v = Some(HashSet::new());
}
if let Some(ref mut v) = *v {
v.insert(n);
}
}
pub fn contains(&self, n : usize) -> bool {
let mut this = self.0.as_ref();
loop {
if let Some(v) = this.v.borrow().as_ref() {
if v.contains(&n) {
return true;
}
}
if let Some(prev) = &this.prev {
this = prev.as_ref();
} else {
return false;
}
}
}
}
fn main() {
let al0 = AccessList::default();
al0.insert(0);
assert_eq!(true,al0.contains(0));
assert_eq!(false,al0.contains(1));
let al1 = al0.clone();
al1.insert(1);
assert_eq!(true,al1.contains(0));
assert_eq!(true,al1.contains(1));
let al3 = al1.clone().clone();
al3.insert(2);
assert_eq!(true,al3.contains(0));
assert_eq!(true,al3.contains(1));
assert_eq!(true,al3.contains(2));
println!("helo");
}
use std::collections::HashSet;
use std::rc::Rc;
use std::cell::RefCell;
struct AccessList(Rc<AccessListInt>);
struct AccessListInt {
v : RefCell<HashSet<usize>>,
prev: Option<Rc<AccessListInt>>
}
impl Default for AccessList {
fn default() -> Self {
AccessList( Rc::new (
AccessListInt{
v : RefCell::new(HashSet::with_capacity(0)),
prev: None
}
))
}
}
impl Clone for AccessList {
fn clone(&self) -> Self {
AccessList ( self.0.clone() )
}
}
impl AccessList {
fn clone(&self) -> Self {
AccessList ( Rc::new (
AccessListInt {
v : RefCell::new(HashSet::with_capacity(0)),
prev: Some(self.0.clone())
}
))
}
pub fn insert(&self, n : usize) {
let mut v = self.0.v.borrow_mut();
v.insert(n);
}
pub fn contains(&self, n : usize) -> bool {
let mut this = self.0.as_ref();
loop {
if this.v.borrow().contains(&n) {
return true;
}
if let Some(prev) = &this.prev {
this = prev.as_ref();
} else {
return false;
}
}
}
}
fn main() {
let al0 = AccessList::default();
al0.insert(0);
assert_eq!(true,al0.contains(0));
assert_eq!(false,al0.contains(1));
let al1 = al0.clone();
al1.insert(1);
assert_eq!(true,al1.contains(0));
assert_eq!(true,al1.contains(1));
let al3 = al1.clone().clone();
al3.insert(2);
assert_eq!(true,al3.contains(0));
assert_eq!(true,al3.contains(1));
assert_eq!(true,al3.contains(2));
println!("success");
}
use std::collections::{HashSet, HashMap};
use std::sync::Arc;
use std::cell::RefCell;
/*
// Implementation of a hasheable borrowed pair
trait KeyPair<A, B> {
fn a(&self) -> &A;
fn b(&self) -> &B;
}
impl<'a, A, B> Borrow<dyn KeyPair<A, B> + 'a> for (A, B)
where
A: Eq + Hash + 'a,
B: Eq + Hash + 'a,
{
fn borrow(&self) -> &(dyn KeyPair<A, B> + 'a) {
self
}
}
impl<A: Hash, B: Hash> Hash for (dyn KeyPair<A, B> + '_) {
fn hash<H: Hasher>(&self, state: &mut H) {
self.a().hash(state);
self.b().hash(state);
}
}
impl<A: Eq, B: Eq> PartialEq for (dyn KeyPair<A, B> + '_) {
fn eq(&self, other: &Self) -> bool {
self.a() == other.a() && self.b() == other.b()
}
}
impl<A: Eq, B: Eq> Eq for (dyn KeyPair<A, B> + '_) {}
impl<A, B> KeyPair<A, B> for (A, B) {
fn a(&self) -> &A {
&self.0
}
fn b(&self) -> &B {
&self.1
}
}
impl<A, B> KeyPair<A, B> for (&A, &B) {
fn a(&self) -> &A {
self.0
}
fn b(&self) -> &B {
self.1
}
}
#[derive(Debug)]
struct Journal {
enabled: bool,
last_id :usize,
addresses: HashMap<Address, usize>,
storage_keys: HashMap<(Address, H256), usize>,
}
#[derive(Debug)]
pub struct AccessList {
id : usize,
journal : Arc<RefCell<Journal>>,
}
impl Clone for AccessList {
fn clone(&self) -> Self {
let mut journal = self.journal.as_ref().borrow_mut();
let id = journal.last_id + 1;
journal.last_id = id;
Self {
id : id,
journal : self.journal.clone()
}
}
}
impl Default for AccessList {
fn default() -> Self {
let journal = Journal {
enabled: false,
last_id : 0,
addresses : HashMap::new(),
storage_keys: HashMap::new()
};
Self {
id : 0,
journal : Arc::new(RefCell::new(journal))
}
}
}
impl AccessList {
/// Returns if the list is enabled
pub fn is_enabled(&self) -> bool {
let journal = self.journal.as_ref().borrow();
journal.enabled
}
/// Enable the access list control
pub fn enable(&mut self) {
let mut journal = self.journal.as_ref().borrow_mut();
journal.enabled = true;
}
/// Checks if contains an storage key
pub fn contains_storage_key(&self, address: &Address, key: &H256) -> bool {
let journal = self.journal.as_ref().borrow();
if journal.enabled {
journal.storage_keys
.contains_key(&(address, key) as &dyn KeyPair<Address, H256>)
} else {
false
}
}
/// Inserts a storage key
pub fn insert_storage_key(&mut self, address: Address, key: H256) {
let mut journal = self.journal.as_ref().borrow_mut();
if journal.enabled {
journal.storage_keys.insert((address, key), self.id);
}
}
/// Checks if contains an address
pub fn contains_address(&self, address: &Address) -> bool {
let journal = self.journal.as_ref().borrow();
if journal.enabled {
journal.addresses.contains_key(&address)
} else {
false
}
}
/// Inserts an address
pub fn insert_address(&mut self, address: Address) {
/* [adria0] eprintln!("insert_address({:?}) [{}]",address,self.addresses.contains(&address)); */
let mut journal = self.journal.as_ref().borrow_mut();
if journal.enabled {
journal.addresses.insert(address, self.id);
}
}
pub fn rollback(&mut self) {
let mut journal = self.journal.as_ref().borrow_mut();
journal.addresses.retain(|_,id| *id != self.id);
journal.storage_keys.retain(|_,id| *id != self.id);
}
pub fn accrue(&mut self, _another: &AccessList) {
}
}
*/
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment