use std::collections::{HashMap, VecDeque};
pub struct Regeister {
stack: Vec<String>,
near_stack: Vec<String>,
}
impl Regeister {
pub fn init() -> Self {
Self {
stack: vec!["t6".to_string(),"t5".to_string(),"t4".to_string(),"t3".to_string(),"t2".to_string(),"t1".to_string(),"t0".to_string()],
near_stack: vec![],
}
}
pub fn eat(&mut self) -> String {
let a = self.stack.pop().unwrap();
let b = a.clone();
self.near_stack.push(a);
b
}
pub fn put(&mut self, str: String) {
self.stack.push(str);
}
pub fn near(&mut self) -> String{
self.near_stack.pop().unwrap()
}
pub fn put_near(&mut self, str: String) {
self.near_stack.push(str);
}
}
pub struct VirtualRegeister {
stack: Vec<String>,
near_stack: Vec<String>,
counter: u32,
}
impl VirtualRegeister {
pub fn init() -> Self {
Self {
stack: vec![],
near_stack: vec![],
counter: 0,
}
}
pub fn eat(&mut self) -> String {
self.stack.push(format!("T{}", self.counter));
self.counter += 1;
let a = self.stack.pop().unwrap();
let b = a.clone();
self.near_stack.push(a);
b
}
pub fn near(&mut self) -> String{
self.near_stack.pop().unwrap()
}
pub fn put_near(&mut self, str: String) {
self.near_stack.push(str);
}
}
pub struct ArgTunnel {
args_stack: HashMap<String, Vec<String>>,
args: HashMap<String, VecDeque<String>>,
}
impl ArgTunnel {
pub fn init() -> Self {
Self {
args_stack: HashMap::new(),
args: HashMap::new(),
}
}
pub fn set_arg(&mut self, func_name: &String) -> String {
if !self.args_stack.contains_key(func_name) {
self.args_stack.insert(func_name.to_string(), vec!["a7".to_string(),"a6".to_string(),"a5".to_string(),"a4".to_string(),"a3".to_string(),"a2".to_string(),"a1".to_string(),"a0".to_string()]);
}
let arg = self.args_stack.get_mut(func_name).unwrap().pop().unwrap();
if !self.args.contains_key(func_name) {
self.args.insert(func_name.to_string(), VecDeque::new());
}
self.args.get_mut(func_name).unwrap().push_front(arg.clone());
arg
}
pub fn get_arg(&mut self, func_name: &String) -> String {
let arg = self.args.get_mut(func_name).unwrap().pop_back().unwrap();
arg
}
pub fn is_match(&mut self, func_name: &String) -> bool {
self.args.get(func_name).unwrap().is_empty()
}
}