neo_solidity/cli/cli_parts/cli_manifest/permissions/
abstract.rs1fn pop_value(stack: &mut Vec<AbstractValue>) -> Result<AbstractValue, ()> {
2 stack.pop().ok_or(())
3}
4
5fn pop_n(stack: &mut Vec<AbstractValue>, n: usize) -> Result<(), ()> {
6 if stack.len() < n {
7 return Err(());
8 }
9 for _ in 0..n {
10 stack.pop();
11 }
12 Ok(())
13}
14
15fn apply_instruction(state: &mut AbstractState, instr: &ir::Instruction) -> Result<(), ()> {
16 use ir::Instruction::*;
17
18 match instr {
19 Drop(_) => {
20 pop_value(&mut state.stack)?;
21 }
22 LoadParameter(_) => state.stack.push(AbstractValue::Unknown),
23 PushLiteral(lit) => state.stack.push(AbstractValue::Literal(lit.clone())),
24 Return | ReturnVoid | ReturnDefault(_) | Abort => {}
25 AbortMsg | Throw => {
26 pop_value(&mut state.stack)?;
27 }
28 BinaryOp(_) => {
29 pop_n(&mut state.stack, 2)?;
30 state.stack.push(AbstractValue::Unknown);
31 }
32 LoadState(_) => state.stack.push(AbstractValue::Unknown),
33 StoreState(_) => {
34 pop_value(&mut state.stack)?;
35 }
36 LoadStorageDynamic => {
37 pop_value(&mut state.stack)?;
38 state.stack.push(AbstractValue::Unknown);
39 }
40 LoadLocal(index) => {
41 let value = state
42 .locals
43 .get(*index)
44 .cloned()
45 .unwrap_or(AbstractValue::Unknown);
46 state.stack.push(value);
47 }
48 StoreLocal(index) => {
49 let value = pop_value(&mut state.stack)?;
50 if let Some(slot) = state.locals.get_mut(*index) {
51 *slot = value;
52 }
53 }
54 LoadMappingElement { key_types, .. } => {
55 pop_n(&mut state.stack, key_types.len())?;
56 state.stack.push(AbstractValue::Unknown);
57 }
58 StoreMappingElement { key_types, .. } => {
59 pop_n(&mut state.stack, key_types.len() + 1)?;
60 }
61 LoadStructField { key_types, .. } => {
62 pop_n(&mut state.stack, key_types.len())?;
63 state.stack.push(AbstractValue::Unknown);
64 }
65 StoreStructField { key_types, .. } => {
66 pop_n(&mut state.stack, key_types.len() + 1)?;
67 }
68 LoadStructArrayElement { key_types, .. } => {
69 pop_n(&mut state.stack, key_types.len() + 1)?;
70 state.stack.push(AbstractValue::Unknown);
71 }
72 StoreStructArrayElement { key_types, .. } => {
73 pop_n(&mut state.stack, key_types.len() + 2)?;
74 }
75 LoadRuntimeValue(_) => state.stack.push(AbstractValue::Unknown),
76 GetSize => {
77 pop_value(&mut state.stack)?;
78 state.stack.push(AbstractValue::Unknown);
79 }
80 CallFunction { arg_count, .. } => {
81 pop_n(&mut state.stack, *arg_count)?;
82 state.stack.push(AbstractValue::Unknown);
85 }
86 CallBuiltin { builtin, arg_count } => {
87 pop_n(&mut state.stack, *arg_count)?;
88 match builtin {
89 ir::BuiltinCall::Syscall(name)
92 if name == "System.Runtime.GetExecutingScriptHash" =>
93 {
94 state.stack.push(AbstractValue::ExecutingScriptHash);
95 }
96 _ => state.stack.push(AbstractValue::Unknown),
97 }
98 }
99 EmitEvent { arg_count, .. } | EmitEventByName { arg_count, .. } => {
100 pop_n(&mut state.stack, arg_count + 1)?;
101 }
102 Convert { .. } => {
103 pop_value(&mut state.stack)?;
104 state.stack.push(AbstractValue::Unknown);
105 }
106 IsType { .. } => {
107 pop_value(&mut state.stack)?;
108 state.stack.push(AbstractValue::Unknown);
109 }
110 NewBuffer => {
111 pop_value(&mut state.stack)?;
112 state.stack.push(AbstractValue::Unknown);
113 }
114 NewArray { .. } => {
115 pop_value(&mut state.stack)?;
116 state.stack.push(AbstractValue::Unknown);
117 }
118 ArrayGet => {
119 pop_n(&mut state.stack, 2)?;
120 state.stack.push(AbstractValue::Unknown);
121 }
122 ArraySet => {
123 pop_n(&mut state.stack, 3)?;
124 }
125 MemCpy => {
126 pop_n(&mut state.stack, 5)?;
128 state.stack.push(AbstractValue::Unknown);
129 }
130 ReverseItems => {
131 pop_value(&mut state.stack)?;
132 }
133 BitwiseNot | LogicalNot => {
134 pop_value(&mut state.stack)?;
135 state.stack.push(AbstractValue::Unknown);
136 }
137 Try { .. } | EndTry { .. } | Jump { .. } | Label(_) => {}
138 JumpIf { .. } => {
139 pop_value(&mut state.stack)?;
140 }
141 Dup => {
142 let value = state.stack.last().cloned().unwrap_or(AbstractValue::Unknown);
143 state.stack.push(value);
144 }
145 Swap => {
146 let len = state.stack.len();
147 if len >= 2 {
148 state.stack.swap(len - 1, len - 2);
149 }
150 }
151 }
152
153 Ok(())
154}