use crate::asm_generation::FinalizedAsm;
use crate::asm_lang::allocated_ops::{AllocatedOp, AllocatedOpcode};
use crate::asm_lang::*;
use crate::error::*;
pub fn check_invalid_opcodes<'sc>(asm: &FinalizedAsm<'sc>) -> CompileResult<'sc, ()> {
match asm {
FinalizedAsm::ContractAbi { .. } | FinalizedAsm::Library => ok((), vec![], vec![]),
FinalizedAsm::ScriptMain {
program_section, ..
} => check_for_contract_opcodes(&program_section.ops[..]),
FinalizedAsm::PredicateMain {
program_section, ..
} => check_for_contract_opcodes(&program_section.ops[..]),
}
}
fn check_for_contract_opcodes<'sc>(ops: &[AllocatedOp<'sc>]) -> CompileResult<'sc, ()> {
use AllocatedOpcode::*;
let default_span = crate::Span {
span: pest::Span::new("no span found for opcode", 0, 1).unwrap(),
path: None,
};
let mut errors = vec![];
for op in ops {
match op.opcode {
GM(_, VirtualImmediate18 { value: 1 }) | GM(_, VirtualImmediate18 { value: 2 }) => {
errors.push(CompileError::GMFromExternalContract {
span: op
.owning_span
.clone()
.unwrap_or_else(|| default_span.clone()),
});
}
MINT(..) => {
errors.push(CompileError::MintFromExternalContext {
span: op
.owning_span
.clone()
.unwrap_or_else(|| default_span.clone()),
});
}
BURN(..) => {
errors.push(CompileError::BurnFromExternalContext {
span: op
.owning_span
.clone()
.unwrap_or_else(|| default_span.clone()),
});
}
SWW(..) | SRW(..) | SRWQ(..) | SWWQ(..) => {
errors.push(CompileError::ContractStorageFromExternalContext {
span: op
.owning_span
.clone()
.unwrap_or_else(|| default_span.clone()),
});
}
_ => (),
}
}
if errors.is_empty() {
ok((), vec![], errors)
} else {
err(vec![], errors)
}
}