Add a PredicateView type to abstract the predicate bit vector a bit.
The encoding tables contain references to numbered ISA predicates. - Give the ISA Flags types a predicate_view() method which returns a PredicateView. - Delete the old predicate_bytes() method which returned a raw &[u8]. - Use a 'static lifetime for the encoding list slice in the Encodings iterator, and a single 'a lifetime for everything else.
This commit is contained in:
@@ -87,15 +87,19 @@ def gen_getters(sgrp, fmt):
|
|||||||
"""
|
"""
|
||||||
fmt.doc_comment("User-defined settings.")
|
fmt.doc_comment("User-defined settings.")
|
||||||
with fmt.indented('impl Flags {', '}'):
|
with fmt.indented('impl Flags {', '}'):
|
||||||
fmt.doc_comment('Returns inner slice of bytes.')
|
fmt.doc_comment('Get a view of the boolean predicates.')
|
||||||
fmt.doc_comment('The byte-sized settings are not included.')
|
with fmt.indented(
|
||||||
with fmt.indented('pub fn predicate_bytes(&self) -> &[u8] {', '}'):
|
'pub fn predicate_view(&self) -> ::settings::PredicateView {',
|
||||||
fmt.line('&self.bytes[{}..]'.format(sgrp.boolean_offset))
|
'}'):
|
||||||
|
fmt.format(
|
||||||
|
'::settings::PredicateView::new(&self.bytes[{}..])',
|
||||||
|
sgrp.boolean_offset)
|
||||||
|
if sgrp.settings:
|
||||||
fmt.doc_comment('Dynamic numbered predicate getter.')
|
fmt.doc_comment('Dynamic numbered predicate getter.')
|
||||||
with fmt.indented(
|
with fmt.indented(
|
||||||
'pub fn numbered_predicate(&self, p: usize) -> bool {', '}'):
|
'fn numbered_predicate(&self, p: usize) -> bool {', '}'):
|
||||||
fmt.line(
|
fmt.line(
|
||||||
'self.bytes[{} + p/8] & (1 << (p%8)) != 0'
|
'self.bytes[{} + p / 8] & (1 << (p % 8)) != 0'
|
||||||
.format(sgrp.boolean_offset))
|
.format(sgrp.boolean_offset))
|
||||||
for setting in sgrp.settings:
|
for setting in sgrp.settings:
|
||||||
gen_getter(setting, sgrp, fmt)
|
gen_getter(setting, sgrp, fmt)
|
||||||
|
|||||||
@@ -61,11 +61,11 @@ impl TargetIsa for Isa {
|
|||||||
enc_tables::INFO.clone()
|
enc_tables::INFO.clone()
|
||||||
}
|
}
|
||||||
|
|
||||||
fn legal_encodings<'a, 'b>(&'a self,
|
fn legal_encodings<'a>(&'a self,
|
||||||
_dfg: &'b ir::DataFlowGraph,
|
_dfg: &'a ir::DataFlowGraph,
|
||||||
inst: &'b ir::InstructionData,
|
inst: &'a ir::InstructionData,
|
||||||
ctrl_typevar: ir::Type)
|
ctrl_typevar: ir::Type)
|
||||||
-> Result<Encodings<'a, 'b>, Legalize> {
|
-> Result<Encodings<'a>, Legalize> {
|
||||||
lookup_enclist(ctrl_typevar,
|
lookup_enclist(ctrl_typevar,
|
||||||
inst.opcode(),
|
inst.opcode(),
|
||||||
self.cpumode,
|
self.cpumode,
|
||||||
@@ -75,7 +75,7 @@ impl TargetIsa for Isa {
|
|||||||
&enc_tables::ENCLISTS[..],
|
&enc_tables::ENCLISTS[..],
|
||||||
inst,
|
inst,
|
||||||
enc_tables::check_instp,
|
enc_tables::check_instp,
|
||||||
self.isa_flags.predicate_bytes()))
|
self.isa_flags.predicate_view()))
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -54,11 +54,11 @@ impl TargetIsa for Isa {
|
|||||||
enc_tables::INFO.clone()
|
enc_tables::INFO.clone()
|
||||||
}
|
}
|
||||||
|
|
||||||
fn legal_encodings<'a, 'b>(&'a self,
|
fn legal_encodings<'a>(&'a self,
|
||||||
_dfg: &'b ir::DataFlowGraph,
|
_dfg: &'a ir::DataFlowGraph,
|
||||||
inst: &'b ir::InstructionData,
|
inst: &'a ir::InstructionData,
|
||||||
ctrl_typevar: ir::Type)
|
ctrl_typevar: ir::Type)
|
||||||
-> Result<Encodings<'a, 'b>, Legalize> {
|
-> Result<Encodings<'a>, Legalize> {
|
||||||
lookup_enclist(ctrl_typevar,
|
lookup_enclist(ctrl_typevar,
|
||||||
inst.opcode(),
|
inst.opcode(),
|
||||||
&enc_tables::LEVEL1_A64[..],
|
&enc_tables::LEVEL1_A64[..],
|
||||||
@@ -68,7 +68,7 @@ impl TargetIsa for Isa {
|
|||||||
&enc_tables::ENCLISTS[..],
|
&enc_tables::ENCLISTS[..],
|
||||||
inst,
|
inst,
|
||||||
enc_tables::check_instp,
|
enc_tables::check_instp,
|
||||||
self.isa_flags.predicate_bytes()))
|
self.isa_flags.predicate_view()))
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -2,9 +2,11 @@
|
|||||||
//!
|
//!
|
||||||
//! This module contains types and functions for working with the encoding tables generated by
|
//! This module contains types and functions for working with the encoding tables generated by
|
||||||
//! `lib/cretonne/meta/gen_encoding.py`.
|
//! `lib/cretonne/meta/gen_encoding.py`.
|
||||||
|
|
||||||
|
use constant_hash::{Table, probe};
|
||||||
use ir::{Type, Opcode, InstructionData};
|
use ir::{Type, Opcode, InstructionData};
|
||||||
use isa::{Encoding, Legalize};
|
use isa::{Encoding, Legalize};
|
||||||
use constant_hash::{Table, probe};
|
use settings::PredicateView;
|
||||||
use std::ops::Range;
|
use std::ops::Range;
|
||||||
|
|
||||||
/// Level 1 hash table entry.
|
/// Level 1 hash table entry.
|
||||||
@@ -127,15 +129,15 @@ const CODE_ALWAYS: EncListEntry = PRED_MASK;
|
|||||||
const CODE_FAIL: EncListEntry = 0xffff;
|
const CODE_FAIL: EncListEntry = 0xffff;
|
||||||
|
|
||||||
/// An iterator over legal encodings for the instruction.
|
/// An iterator over legal encodings for the instruction.
|
||||||
pub struct Encodings<'a, 'b> {
|
pub struct Encodings<'a> {
|
||||||
offset: usize,
|
offset: usize,
|
||||||
enclist: &'b [EncListEntry],
|
enclist: &'static [EncListEntry],
|
||||||
inst: &'b InstructionData,
|
inst: &'a InstructionData,
|
||||||
instp: fn(&InstructionData, EncListEntry) -> bool,
|
instp: fn(&InstructionData, EncListEntry) -> bool,
|
||||||
isa_predicate_bytes: &'a [u8],
|
isa_predicates: PredicateView<'a>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a, 'b> Encodings<'a, 'b> {
|
impl<'a> Encodings<'a> {
|
||||||
/// Creates a new instance of `Encodings`.
|
/// Creates a new instance of `Encodings`.
|
||||||
///
|
///
|
||||||
/// # Parameters
|
/// # Parameters
|
||||||
@@ -151,29 +153,25 @@ impl<'a, 'b> Encodings<'a, 'b> {
|
|||||||
/// encoding lists are laid out such that first call to `next` returns valid entry in the list
|
/// encoding lists are laid out such that first call to `next` returns valid entry in the list
|
||||||
/// or `None`.
|
/// or `None`.
|
||||||
pub fn new(offset: usize,
|
pub fn new(offset: usize,
|
||||||
enclist: &'b [EncListEntry],
|
enclist: &'static [EncListEntry],
|
||||||
inst: &'b InstructionData,
|
inst: &'a InstructionData,
|
||||||
instp: fn(&InstructionData, EncListEntry) -> bool,
|
instp: fn(&InstructionData, EncListEntry) -> bool,
|
||||||
isa_predicate_bytes: &'a [u8])
|
isa_predicates: PredicateView<'a>)
|
||||||
-> Self {
|
-> Self {
|
||||||
Encodings {
|
Encodings {
|
||||||
offset,
|
offset,
|
||||||
enclist,
|
enclist,
|
||||||
inst,
|
inst,
|
||||||
instp,
|
instp,
|
||||||
isa_predicate_bytes,
|
isa_predicates,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a, 'b> Iterator for Encodings<'a, 'b> {
|
impl<'a> Iterator for Encodings<'a> {
|
||||||
type Item = Encoding;
|
type Item = Encoding;
|
||||||
|
|
||||||
fn next(&mut self) -> Option<Encoding> {
|
fn next(&mut self) -> Option<Encoding> {
|
||||||
fn numbered_predicate(bytes: &[u8], p: usize) -> bool {
|
|
||||||
bytes[p / 8] & (1 << (p % 8)) != 0
|
|
||||||
}
|
|
||||||
|
|
||||||
while self.enclist[self.offset] != CODE_FAIL {
|
while self.enclist[self.offset] != CODE_FAIL {
|
||||||
let pred = self.enclist[self.offset];
|
let pred = self.enclist[self.offset];
|
||||||
if pred <= CODE_ALWAYS {
|
if pred <= CODE_ALWAYS {
|
||||||
@@ -189,7 +187,7 @@ impl<'a, 'b> Iterator for Encodings<'a, 'b> {
|
|||||||
} else {
|
} else {
|
||||||
// This is an ISA predicate entry.
|
// This is an ISA predicate entry.
|
||||||
self.offset += 1;
|
self.offset += 1;
|
||||||
if !numbered_predicate(self.isa_predicate_bytes, (pred & PRED_MASK) as usize) {
|
if !self.isa_predicates.test((pred & PRED_MASK) as usize) {
|
||||||
// ISA predicate failed, skip the next N entries.
|
// ISA predicate failed, skip the next N entries.
|
||||||
self.offset += 3 * (pred >> PRED_BITS) as usize;
|
self.offset += 3 * (pred >> PRED_BITS) as usize;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -61,11 +61,11 @@ impl TargetIsa for Isa {
|
|||||||
enc_tables::INFO.clone()
|
enc_tables::INFO.clone()
|
||||||
}
|
}
|
||||||
|
|
||||||
fn legal_encodings<'a, 'b>(&'a self,
|
fn legal_encodings<'a>(&'a self,
|
||||||
_dfg: &'b ir::DataFlowGraph,
|
_dfg: &'a ir::DataFlowGraph,
|
||||||
inst: &'b ir::InstructionData,
|
inst: &'a ir::InstructionData,
|
||||||
ctrl_typevar: ir::Type)
|
ctrl_typevar: ir::Type)
|
||||||
-> Result<Encodings<'a, 'b>, Legalize> {
|
-> Result<Encodings<'a>, Legalize> {
|
||||||
lookup_enclist(ctrl_typevar,
|
lookup_enclist(ctrl_typevar,
|
||||||
inst.opcode(),
|
inst.opcode(),
|
||||||
self.cpumode,
|
self.cpumode,
|
||||||
@@ -75,7 +75,7 @@ impl TargetIsa for Isa {
|
|||||||
&enc_tables::ENCLISTS[..],
|
&enc_tables::ENCLISTS[..],
|
||||||
inst,
|
inst,
|
||||||
enc_tables::check_instp,
|
enc_tables::check_instp,
|
||||||
self.isa_flags.predicate_bytes()))
|
self.isa_flags.predicate_view()))
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -138,11 +138,11 @@ pub trait TargetIsa {
|
|||||||
fn register_info(&self) -> RegInfo;
|
fn register_info(&self) -> RegInfo;
|
||||||
|
|
||||||
/// Returns an iterartor over legal encodings for the instruction.
|
/// Returns an iterartor over legal encodings for the instruction.
|
||||||
fn legal_encodings<'a, 'b>(&'a self,
|
fn legal_encodings<'a>(&'a self,
|
||||||
dfg: &'b ir::DataFlowGraph,
|
dfg: &'a ir::DataFlowGraph,
|
||||||
inst: &'b ir::InstructionData,
|
inst: &'a ir::InstructionData,
|
||||||
ctrl_typevar: ir::Type)
|
ctrl_typevar: ir::Type)
|
||||||
-> Result<Encodings<'a, 'b>, Legalize>;
|
-> Result<Encodings<'a>, Legalize>;
|
||||||
|
|
||||||
/// Encode an instruction after determining it is legal.
|
/// Encode an instruction after determining it is legal.
|
||||||
///
|
///
|
||||||
|
|||||||
@@ -61,11 +61,11 @@ impl TargetIsa for Isa {
|
|||||||
enc_tables::INFO.clone()
|
enc_tables::INFO.clone()
|
||||||
}
|
}
|
||||||
|
|
||||||
fn legal_encodings<'a, 'b>(&'a self,
|
fn legal_encodings<'a>(&'a self,
|
||||||
_dfg: &'b ir::DataFlowGraph,
|
_dfg: &'a ir::DataFlowGraph,
|
||||||
inst: &'b ir::InstructionData,
|
inst: &'a ir::InstructionData,
|
||||||
ctrl_typevar: ir::Type)
|
ctrl_typevar: ir::Type)
|
||||||
-> Result<Encodings<'a, 'b>, Legalize> {
|
-> Result<Encodings<'a>, Legalize> {
|
||||||
lookup_enclist(ctrl_typevar,
|
lookup_enclist(ctrl_typevar,
|
||||||
inst.opcode(),
|
inst.opcode(),
|
||||||
self.cpumode,
|
self.cpumode,
|
||||||
@@ -75,7 +75,7 @@ impl TargetIsa for Isa {
|
|||||||
&enc_tables::ENCLISTS[..],
|
&enc_tables::ENCLISTS[..],
|
||||||
inst,
|
inst,
|
||||||
enc_tables::check_instp,
|
enc_tables::check_instp,
|
||||||
self.isa_flags.predicate_bytes()))
|
self.isa_flags.predicate_view()))
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -162,6 +162,28 @@ pub enum Error {
|
|||||||
/// A result returned when changing a setting.
|
/// A result returned when changing a setting.
|
||||||
pub type Result<T> = result::Result<T, Error>;
|
pub type Result<T> = result::Result<T, Error>;
|
||||||
|
|
||||||
|
/// A reference to just the boolean predicates of a settings object.
|
||||||
|
///
|
||||||
|
/// The settings objects themselves are generated and appear in the `isa/*/settings.rs` modules.
|
||||||
|
/// Each settings object provides a `predicate_view()` method that makes it possible to query
|
||||||
|
/// ISA predicates by number.
|
||||||
|
#[derive(Clone, Copy)]
|
||||||
|
pub struct PredicateView<'a>(&'a [u8]);
|
||||||
|
|
||||||
|
impl<'a> PredicateView<'a> {
|
||||||
|
/// Create a new view of a precomputed predicate vector.
|
||||||
|
///
|
||||||
|
/// See the `predicate_view()` method on the various `Flags` types defined for each ISA.
|
||||||
|
pub fn new(bits: &'a [u8]) -> PredicateView {
|
||||||
|
PredicateView(bits)
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Check a numbered predicate.
|
||||||
|
pub fn test(self, p: usize) -> bool {
|
||||||
|
self.0[p / 8] & (1 << (p % 8)) != 0
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/// Implementation details for generated code.
|
/// Implementation details for generated code.
|
||||||
///
|
///
|
||||||
/// This module holds definitions that need to be public so the can be instantiated by generated
|
/// This module holds definitions that need to be public so the can be instantiated by generated
|
||||||
|
|||||||
Reference in New Issue
Block a user