scan registers of instructions leading to verify_attributes interrupt to find the number of registers to save (#2307)
This commit is contained in:
@@ -792,8 +792,8 @@ enum InstructionTemplate {
|
|||||||
#[strum_discriminants(strum(props(Arity = "0", Name = "install_verify_attr")))]
|
#[strum_discriminants(strum(props(Arity = "0", Name = "install_verify_attr")))]
|
||||||
InstallVerifyAttr,
|
InstallVerifyAttr,
|
||||||
// call verify_attrs.
|
// call verify_attrs.
|
||||||
#[strum_discriminants(strum(props(Arity = "0", Name = "verify_attr_interrupt")))]
|
#[strum_discriminants(strum(props(Arity = "1", Name = "verify_attr_interrupt")))]
|
||||||
VerifyAttrInterrupt,
|
VerifyAttrInterrupt(usize),
|
||||||
// procedures
|
// procedures
|
||||||
CallClause(ClauseType, usize, usize, bool, bool), // ClauseType,
|
CallClause(ClauseType, usize, usize, bool, bool), // ClauseType,
|
||||||
// arity,
|
// arity,
|
||||||
@@ -1153,6 +1153,33 @@ fn generate_instruction_preface() -> TokenStream {
|
|||||||
pub type CodeDeque = VecDeque<Instruction>;
|
pub type CodeDeque = VecDeque<Instruction>;
|
||||||
|
|
||||||
impl Instruction {
|
impl Instruction {
|
||||||
|
#[inline]
|
||||||
|
pub fn registers(&self) -> Vec<RegType> {
|
||||||
|
match self {
|
||||||
|
&Instruction::GetConstant(_, _, r) => vec![r],
|
||||||
|
&Instruction::GetList(_, r) => vec![r],
|
||||||
|
&Instruction::GetPartialString(_, _, r, _) => vec![r],
|
||||||
|
&Instruction::GetStructure(_, _, _, r) => vec![r],
|
||||||
|
&Instruction::GetVariable(r, t) => vec![r, temp_v!(t)],
|
||||||
|
&Instruction::GetValue(r, t) => vec![r, temp_v!(t)],
|
||||||
|
&Instruction::UnifyLocalValue(r) => vec![r],
|
||||||
|
&Instruction::UnifyVariable(r) => vec![r],
|
||||||
|
&Instruction::PutConstant(_, _, r) => vec![r],
|
||||||
|
&Instruction::PutList(_, r) => vec![r],
|
||||||
|
&Instruction::PutPartialString(_, _, r, _) => vec![r],
|
||||||
|
&Instruction::PutStructure(_, _, r) => vec![r],
|
||||||
|
&Instruction::PutValue(r, t) => vec![r, temp_v!(t)],
|
||||||
|
&Instruction::PutVariable(r, t) => vec![r, temp_v!(t)],
|
||||||
|
&Instruction::SetLocalValue(r) => vec![r],
|
||||||
|
&Instruction::SetVariable(r) => vec![r],
|
||||||
|
&Instruction::SetValue(r) => vec![r],
|
||||||
|
&Instruction::GetLevel(r) => vec![r],
|
||||||
|
&Instruction::GetPrevLevel(r) => vec![r],
|
||||||
|
&Instruction::GetCutPoint(r) => vec![r],
|
||||||
|
_ => vec![],
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
#[inline]
|
#[inline]
|
||||||
pub fn to_indexing_line_mut(&mut self) -> Option<&mut Vec<IndexingLine>> {
|
pub fn to_indexing_line_mut(&mut self) -> Option<&mut Vec<IndexingLine>> {
|
||||||
match self {
|
match self {
|
||||||
@@ -1243,8 +1270,8 @@ fn generate_instruction_preface() -> TokenStream {
|
|||||||
&Instruction::InstallVerifyAttr => {
|
&Instruction::InstallVerifyAttr => {
|
||||||
functor!(atom!("install_verify_attr"))
|
functor!(atom!("install_verify_attr"))
|
||||||
}
|
}
|
||||||
&Instruction::VerifyAttrInterrupt => {
|
&Instruction::VerifyAttrInterrupt(arity) => {
|
||||||
functor!(atom!("verify_attr_interrupt"))
|
functor!(atom!("verify_attr_interrupt"), [fixnum(arity)])
|
||||||
}
|
}
|
||||||
&Instruction::DynamicElse(birth, death, next_or_fail) => {
|
&Instruction::DynamicElse(birth, death, next_or_fail) => {
|
||||||
match (death, next_or_fail) {
|
match (death, next_or_fail) {
|
||||||
|
|||||||
@@ -557,20 +557,29 @@ impl Machine {
|
|||||||
}
|
}
|
||||||
|
|
||||||
let mut p = self.machine_st.p;
|
let mut p = self.machine_st.p;
|
||||||
|
let mut arity = 0;
|
||||||
|
|
||||||
while self.code[p].is_head_instr() {
|
while self.code[p].is_head_instr() {
|
||||||
|
for r in self.code[p].registers() {
|
||||||
|
if let RegType::Temp(t) = r {
|
||||||
|
arity = std::cmp::max(arity, t);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
p += 1;
|
p += 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
let instr =
|
let instr = std::mem::replace(
|
||||||
std::mem::replace(&mut self.code[p], Instruction::VerifyAttrInterrupt);
|
&mut self.code[p],
|
||||||
|
Instruction::VerifyAttrInterrupt(arity),
|
||||||
|
);
|
||||||
|
|
||||||
self.code[VERIFY_ATTR_INTERRUPT_LOC] = instr;
|
self.code[VERIFY_ATTR_INTERRUPT_LOC] = instr;
|
||||||
self.machine_st.attr_var_init.cp = p;
|
self.machine_st.attr_var_init.cp = p;
|
||||||
}
|
}
|
||||||
&Instruction::VerifyAttrInterrupt => {
|
&Instruction::VerifyAttrInterrupt(arity) => {
|
||||||
let (_, arity) = self.code[VERIFY_ATTR_INTERRUPT_LOC].to_name_and_arity();
|
// let (_, arity) = self.code[VERIFY_ATTR_INTERRUPT_LOC].to_name_and_arity();
|
||||||
let arity = std::cmp::max(arity, self.machine_st.num_of_args);
|
// let arity = std::cmp::max(arity, self.machine_st.num_of_args);
|
||||||
self.run_verify_attr_interrupt(arity);
|
self.run_verify_attr_interrupt(arity);
|
||||||
}
|
}
|
||||||
&Instruction::Add(ref a1, ref a2, t) => {
|
&Instruction::Add(ref a1, ref a2, t) => {
|
||||||
|
|||||||
@@ -391,7 +391,7 @@ impl Machine {
|
|||||||
self.code.extend(vec![
|
self.code.extend(vec![
|
||||||
Instruction::BreakFromDispatchLoop,
|
Instruction::BreakFromDispatchLoop,
|
||||||
Instruction::InstallVerifyAttr,
|
Instruction::InstallVerifyAttr,
|
||||||
Instruction::VerifyAttrInterrupt,
|
Instruction::VerifyAttrInterrupt(0),
|
||||||
Instruction::BreakFromDispatchLoop, // the location of LIB_QUERY_SUCCESS
|
Instruction::BreakFromDispatchLoop, // the location of LIB_QUERY_SUCCESS
|
||||||
Instruction::ExecuteTermGreaterThan,
|
Instruction::ExecuteTermGreaterThan,
|
||||||
Instruction::ExecuteTermLessThan,
|
Instruction::ExecuteTermLessThan,
|
||||||
|
|||||||
@@ -5739,11 +5739,11 @@ impl Machine {
|
|||||||
#[inline(always)]
|
#[inline(always)]
|
||||||
pub(super) fn restore_instr_at_verify_attr_interrupt(&mut self) {
|
pub(super) fn restore_instr_at_verify_attr_interrupt(&mut self) {
|
||||||
match &self.code[VERIFY_ATTR_INTERRUPT_LOC] {
|
match &self.code[VERIFY_ATTR_INTERRUPT_LOC] {
|
||||||
&Instruction::VerifyAttrInterrupt => {}
|
&Instruction::VerifyAttrInterrupt(_) => {}
|
||||||
_ => {
|
_ => {
|
||||||
let instr = mem::replace(
|
let instr = mem::replace(
|
||||||
&mut self.code[VERIFY_ATTR_INTERRUPT_LOC],
|
&mut self.code[VERIFY_ATTR_INTERRUPT_LOC],
|
||||||
Instruction::VerifyAttrInterrupt,
|
Instruction::VerifyAttrInterrupt(0),
|
||||||
);
|
);
|
||||||
|
|
||||||
self.code[self.machine_st.attr_var_init.cp] = instr;
|
self.code[self.machine_st.attr_var_init.cp] = instr;
|
||||||
|
|||||||
Reference in New Issue
Block a user