Require documentation on cretonne public items.
This commit is contained in:
@@ -707,6 +707,11 @@ class InstructionFormat(object):
|
||||
self.members.append(member)
|
||||
yield k
|
||||
|
||||
def __str__(self):
|
||||
args = ', '.join('{}: {}'.format(m, k) if m else str(k)
|
||||
for m, k in zip(self.members, self.kinds))
|
||||
return '{}({})'.format(self.name, args)
|
||||
|
||||
def __getattr__(self, attr):
|
||||
# type: (str) -> FormatField
|
||||
"""
|
||||
|
||||
@@ -19,6 +19,7 @@ def gen_formats(fmt):
|
||||
fmt.line('#[derive(Copy, Clone, PartialEq, Eq, Debug)]')
|
||||
with fmt.indented('pub enum InstructionFormat {', '}'):
|
||||
for f in cretonne.InstructionFormat.all_formats:
|
||||
fmt.doc_comment(str(f))
|
||||
fmt.line(f.name + ',')
|
||||
fmt.line()
|
||||
|
||||
@@ -172,6 +173,7 @@ def gen_opcodes(groups, fmt):
|
||||
fmt.line('#[derive(Copy, Clone, PartialEq, Eq, Debug)]')
|
||||
instrs = []
|
||||
with fmt.indented('pub enum Opcode {', '}'):
|
||||
fmt.doc_comment('An invalid opcode.')
|
||||
fmt.line('NotAnOpcode,')
|
||||
for g in groups:
|
||||
for i in g.instructions:
|
||||
@@ -364,6 +366,7 @@ def gen_format_constructor(iform, fmt):
|
||||
proto = '{}({})'.format(iform.name, ', '.join(args))
|
||||
proto += " -> (Inst, &'f mut DataFlowGraph)"
|
||||
|
||||
fmt.doc_comment(str(iform))
|
||||
fmt.line('#[allow(non_snake_case)]')
|
||||
with fmt.indented('fn {} {{'.format(proto), '}'):
|
||||
# Generate the instruction data.
|
||||
|
||||
@@ -16,10 +16,12 @@ def gen_enum_types(sgrp, fmt):
|
||||
if not isinstance(setting, EnumSetting):
|
||||
continue
|
||||
ty = camel_case(setting.name)
|
||||
fmt.doc_comment('Values for {}.'.format(setting))
|
||||
fmt.line('#[derive(Debug, PartialEq, Eq)]')
|
||||
fmt.line(
|
||||
'pub enum {} {{ {} }}'
|
||||
.format(ty, ", ".join(camel_case(v) for v in setting.values)))
|
||||
with fmt.indented('pub enum {} {{'.format(ty), '}'):
|
||||
for v in setting.values:
|
||||
fmt.doc_comment('`{}`.'.format(v))
|
||||
fmt.line(camel_case(v) + ',')
|
||||
|
||||
|
||||
def gen_getter(setting, sgrp, fmt):
|
||||
@@ -70,7 +72,7 @@ def gen_getters(sgrp, fmt):
|
||||
"""
|
||||
fmt.doc_comment("User-defined settings.")
|
||||
with fmt.indented('impl Flags {', '}'):
|
||||
# Dynamic numbered predicate getter.
|
||||
fmt.doc_comment('Dynamic numbered predicate getter.')
|
||||
with fmt.indented(
|
||||
'pub fn numbered_predicate(&self, p: usize) -> bool {', '}'):
|
||||
fmt.line(
|
||||
@@ -187,6 +189,7 @@ def gen_constructor(sgrp, parent, fmt):
|
||||
if sgrp.parent:
|
||||
p = sgrp.parent
|
||||
args = '{}: &{}::Flags, {}'.format(p.name, p.qual_mod, args)
|
||||
fmt.doc_comment('Create flags {} settings group.'.format(sgrp.name))
|
||||
with fmt.indented(
|
||||
'pub fn new({}) -> Flags {{'.format(args), '}'):
|
||||
fmt.line('let bvec = builder.state_for("{}");'.format(sgrp.name))
|
||||
|
||||
@@ -33,19 +33,12 @@ pub type BasicBlock = (Ebb, Inst);
|
||||
/// A container for the successors and predecessors of some Ebb.
|
||||
#[derive(Debug, Clone, Default)]
|
||||
pub struct CFGNode {
|
||||
/// EBBs that are the targets of branches and jumps in this EBB.
|
||||
pub successors: Vec<Ebb>,
|
||||
/// Basic blocks that can branch or jump to this EBB.
|
||||
pub predecessors: Vec<BasicBlock>,
|
||||
}
|
||||
|
||||
impl CFGNode {
|
||||
pub fn new() -> CFGNode {
|
||||
CFGNode {
|
||||
successors: Vec::new(),
|
||||
predecessors: Vec::new(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// The Control Flow Graph maintains a mapping of ebbs to their predecessors
|
||||
/// and successors where predecessors are basic blocks and successors are
|
||||
/// extended basic blocks.
|
||||
@@ -88,10 +81,12 @@ impl ControlFlowGraph {
|
||||
self.data[to].predecessors.push(from);
|
||||
}
|
||||
|
||||
/// Get the CFG predecessor basic blocks to `ebb`.
|
||||
pub fn get_predecessors(&self, ebb: Ebb) -> &Vec<BasicBlock> {
|
||||
&self.data[ebb].predecessors
|
||||
}
|
||||
|
||||
/// Get the CFG successors to `ebb`.
|
||||
pub fn get_successors(&self, ebb: Ebb) -> &Vec<Ebb> {
|
||||
&self.data[ebb].successors
|
||||
}
|
||||
|
||||
@@ -1,10 +1,11 @@
|
||||
/// ! A Dominator Tree represented as mappings of Ebbs to their immediate dominator.
|
||||
//! A Dominator Tree represented as mappings of Ebbs to their immediate dominator.
|
||||
|
||||
use cfg::*;
|
||||
use ir::Ebb;
|
||||
use ir::entities::NO_INST;
|
||||
use entity_map::EntityMap;
|
||||
|
||||
/// The dominator tree for a single function.
|
||||
pub struct DominatorTree {
|
||||
data: EntityMap<Ebb, Option<BasicBlock>>,
|
||||
}
|
||||
|
||||
@@ -29,15 +29,25 @@ pub trait CondCode: Copy {
|
||||
/// difference.
|
||||
#[derive(Clone, Copy, PartialEq, Eq, Debug)]
|
||||
pub enum IntCC {
|
||||
/// `==`.
|
||||
Equal,
|
||||
/// `!=`.
|
||||
NotEqual,
|
||||
/// Signed `<`.
|
||||
SignedLessThan,
|
||||
/// Signed `>=`.
|
||||
SignedGreaterThanOrEqual,
|
||||
/// Signed `>`.
|
||||
SignedGreaterThan,
|
||||
/// Signed `<=`.
|
||||
SignedLessThanOrEqual,
|
||||
/// Unsigned `<`.
|
||||
UnsignedLessThan,
|
||||
/// Unsigned `>=`.
|
||||
UnsignedGreaterThanOrEqual,
|
||||
/// Unsigned `>`.
|
||||
UnsignedGreaterThan,
|
||||
/// Unsigned `<=`.
|
||||
UnsignedLessThanOrEqual,
|
||||
}
|
||||
|
||||
@@ -131,24 +141,38 @@ impl FromStr for IntCC {
|
||||
/// except the impossible `!UN & !EQ & !LT & !GT` and the always true `UN | EQ | LT | GT`.
|
||||
#[derive(Clone, Copy, PartialEq, Eq, Debug)]
|
||||
pub enum FloatCC {
|
||||
Ordered, // EQ | LT | GT
|
||||
Unordered, // UN
|
||||
/// EQ | LT | GT
|
||||
Ordered,
|
||||
/// UN
|
||||
Unordered,
|
||||
|
||||
Equal, // EQ
|
||||
// The C '!=' operator is the inverse of '==': NotEqual.
|
||||
NotEqual, // UN | LT | GT
|
||||
OrderedNotEqual, // LT | GT
|
||||
UnorderedOrEqual, // UN | EQ
|
||||
/// EQ
|
||||
Equal,
|
||||
/// The C '!=' operator is the inverse of '==': `NotEqual`.
|
||||
/// UN | LT | GT
|
||||
NotEqual,
|
||||
/// LT | GT
|
||||
OrderedNotEqual,
|
||||
/// UN | EQ
|
||||
UnorderedOrEqual,
|
||||
|
||||
LessThan, // LT
|
||||
LessThanOrEqual, // LT | EQ
|
||||
GreaterThan, // GT
|
||||
GreaterThanOrEqual, // GT | EQ
|
||||
/// LT
|
||||
LessThan,
|
||||
/// LT | EQ
|
||||
LessThanOrEqual,
|
||||
/// GT
|
||||
GreaterThan,
|
||||
/// GT | EQ
|
||||
GreaterThanOrEqual,
|
||||
|
||||
UnorderedOrLessThan, // UN | LT
|
||||
UnorderedOrLessThanOrEqual, // UN | LT | EQ
|
||||
UnorderedOrGreaterThan, // UN | GT
|
||||
UnorderedOrGreaterThanOrEqual, // UN | GT | EQ
|
||||
/// UN | LT
|
||||
UnorderedOrLessThan,
|
||||
/// UN | LT | EQ
|
||||
UnorderedOrLessThanOrEqual,
|
||||
/// UN | GT
|
||||
UnorderedOrGreaterThan,
|
||||
/// UN | GT | EQ
|
||||
UnorderedOrGreaterThanOrEqual,
|
||||
}
|
||||
|
||||
impl CondCode for FloatCC {
|
||||
|
||||
@@ -98,16 +98,16 @@ impl Default for Inst {
|
||||
#[derive(Copy, Clone, PartialEq, Eq, Hash, Debug)]
|
||||
pub struct Value(u32);
|
||||
|
||||
// Value references can either reference an instruction directly, or they can refer to the extended
|
||||
// value table.
|
||||
/// Value references can either reference an instruction directly, or they can refer to the
|
||||
/// extended value table.
|
||||
pub enum ExpandedValue {
|
||||
// This is the first value produced by the referenced instruction.
|
||||
/// This is the first value produced by the referenced instruction.
|
||||
Direct(Inst),
|
||||
|
||||
// This value is described in the extended value table.
|
||||
/// This value is described in the extended value table.
|
||||
Table(usize),
|
||||
|
||||
// This is NO_VALUE.
|
||||
/// This is NO_VALUE.
|
||||
None,
|
||||
}
|
||||
|
||||
@@ -135,19 +135,23 @@ impl Value {
|
||||
None
|
||||
}
|
||||
}
|
||||
/// Create a `Direct` value corresponding to the first value produced by `i`.
|
||||
pub fn new_direct(i: Inst) -> Value {
|
||||
let encoding = i.index() * 2;
|
||||
assert!(encoding < u32::MAX as usize);
|
||||
Value(encoding as u32)
|
||||
}
|
||||
|
||||
/// Create a `Table` value referring to entry `i` in the `DataFlowGraph.extended_values` table.
|
||||
/// This constructor should not be used directly. Use the public `DataFlowGraph` methods to
|
||||
/// manipulate values.
|
||||
pub fn new_table(index: usize) -> Value {
|
||||
let encoding = index * 2 + 1;
|
||||
assert!(encoding < u32::MAX as usize);
|
||||
Value(encoding as u32)
|
||||
}
|
||||
|
||||
// Expand the internal representation into something useful.
|
||||
/// Expand the internal representation into something useful.
|
||||
pub fn expand(&self) -> ExpandedValue {
|
||||
use self::ExpandedValue::*;
|
||||
if *self == NO_VALUE {
|
||||
@@ -312,12 +316,19 @@ impl Default for SigRef {
|
||||
pub enum AnyEntity {
|
||||
/// The whole function.
|
||||
Function,
|
||||
/// An extended basic block.
|
||||
Ebb(Ebb),
|
||||
/// An instruction.
|
||||
Inst(Inst),
|
||||
/// An SSA value.
|
||||
Value(Value),
|
||||
/// A stack slot.
|
||||
StackSlot(StackSlot),
|
||||
/// A jump table.
|
||||
JumpTable(JumpTable),
|
||||
/// An external function.
|
||||
FuncRef(FuncRef),
|
||||
/// A function call signature.
|
||||
SigRef(SigRef),
|
||||
}
|
||||
|
||||
|
||||
@@ -14,11 +14,14 @@ use ir::{Type, FunctionName, SigRef};
|
||||
/// details that are needed to call a function correctly.
|
||||
#[derive(Clone, PartialEq, Eq, Debug)]
|
||||
pub struct Signature {
|
||||
/// Types of the arguments passed to the function.
|
||||
pub argument_types: Vec<ArgumentType>,
|
||||
/// Types returned from the function.
|
||||
pub return_types: Vec<ArgumentType>,
|
||||
}
|
||||
|
||||
impl Signature {
|
||||
/// Create a new blank signature.
|
||||
pub fn new() -> Signature {
|
||||
Signature {
|
||||
argument_types: Vec::new(),
|
||||
@@ -59,13 +62,16 @@ impl Display for Signature {
|
||||
/// how the argument is passed.
|
||||
#[derive(Copy, Clone, PartialEq, Eq, Debug)]
|
||||
pub struct ArgumentType {
|
||||
/// Type of the argument value.
|
||||
pub value_type: Type,
|
||||
/// Method for extending argument to a full register.
|
||||
pub extension: ArgumentExtension,
|
||||
/// Place this argument in a register if possible.
|
||||
pub inreg: bool,
|
||||
}
|
||||
|
||||
impl ArgumentType {
|
||||
/// Create an argument type with default flags.
|
||||
pub fn new(vt: Type) -> ArgumentType {
|
||||
ArgumentType {
|
||||
value_type: vt,
|
||||
@@ -109,7 +115,9 @@ pub enum ArgumentExtension {
|
||||
/// Information about a function that can be called directly with a direct `call` instruction.
|
||||
#[derive(Clone, Debug)]
|
||||
pub struct ExtFuncData {
|
||||
/// Name of the external function.
|
||||
pub name: FunctionName,
|
||||
/// Call signature of function.
|
||||
pub signature: SigRef,
|
||||
}
|
||||
|
||||
|
||||
@@ -14,6 +14,7 @@ use std::ascii::AsciiExt;
|
||||
pub struct FunctionName(String);
|
||||
|
||||
impl FunctionName {
|
||||
/// Create new function name equal to `s`.
|
||||
pub fn new<S: Into<String>>(s: S) -> FunctionName {
|
||||
FunctionName(s.into())
|
||||
}
|
||||
|
||||
@@ -17,6 +17,7 @@ use std::str::FromStr;
|
||||
pub struct Imm64(i64);
|
||||
|
||||
impl Imm64 {
|
||||
/// Create a new `Imm64` representing the signed number `x`.
|
||||
pub fn new(x: i64) -> Imm64 {
|
||||
Imm64(x)
|
||||
}
|
||||
@@ -374,6 +375,7 @@ fn parse_float(s: &str, w: u8, t: u8) -> Result<u64, &'static str> {
|
||||
}
|
||||
|
||||
impl Ieee32 {
|
||||
/// Create a new `Ieee32` representing the number `x`.
|
||||
pub fn new(x: f32) -> Ieee32 {
|
||||
Ieee32(x)
|
||||
}
|
||||
@@ -403,6 +405,7 @@ impl FromStr for Ieee32 {
|
||||
}
|
||||
|
||||
impl Ieee64 {
|
||||
/// Create a new `Ieee64` representing the number `x`.
|
||||
pub fn new(x: f64) -> Ieee64 {
|
||||
Ieee64(x)
|
||||
}
|
||||
|
||||
@@ -93,6 +93,7 @@ impl FromStr for Opcode {
|
||||
/// 16 bytes on 64-bit architectures. If more space is needed to represent an instruction, use a
|
||||
/// `Box<AuxData>` to store the additional information out of line.
|
||||
#[derive(Clone, Debug)]
|
||||
#[allow(missing_docs)]
|
||||
pub enum InstructionData {
|
||||
Nullary { opcode: Opcode, ty: Type },
|
||||
Unary {
|
||||
@@ -226,14 +227,17 @@ pub enum InstructionData {
|
||||
pub struct VariableArgs(Vec<Value>);
|
||||
|
||||
impl VariableArgs {
|
||||
/// Create an empty argument list.
|
||||
pub fn new() -> VariableArgs {
|
||||
VariableArgs(Vec::new())
|
||||
}
|
||||
|
||||
/// Add an argument to the end.
|
||||
pub fn push(&mut self, v: Value) {
|
||||
self.0.push(v)
|
||||
}
|
||||
|
||||
/// Check if the list is empty.
|
||||
pub fn is_empty(&self) -> bool {
|
||||
self.0.is_empty()
|
||||
}
|
||||
@@ -276,6 +280,7 @@ impl Default for VariableArgs {
|
||||
/// Payload data for `vconst`.
|
||||
#[derive(Clone, Debug)]
|
||||
pub struct UnaryImmVectorData {
|
||||
/// Raw vector data.
|
||||
pub imm: ImmVector,
|
||||
}
|
||||
|
||||
@@ -292,6 +297,7 @@ impl Display for UnaryImmVectorData {
|
||||
/// Payload data for ternary instructions with multiple results, such as `iadd_carry`.
|
||||
#[derive(Clone, Debug)]
|
||||
pub struct TernaryOverflowData {
|
||||
/// Value arguments.
|
||||
pub args: [Value; 3],
|
||||
}
|
||||
|
||||
@@ -305,7 +311,9 @@ impl Display for TernaryOverflowData {
|
||||
/// in the allowed InstructionData size.
|
||||
#[derive(Clone, Debug)]
|
||||
pub struct JumpData {
|
||||
/// Jump destination EBB.
|
||||
pub destination: Ebb,
|
||||
/// Arguments passed to destination EBB.
|
||||
pub varargs: VariableArgs,
|
||||
}
|
||||
|
||||
@@ -323,8 +331,11 @@ impl Display for JumpData {
|
||||
/// in the allowed InstructionData size.
|
||||
#[derive(Clone, Debug)]
|
||||
pub struct BranchData {
|
||||
/// Value argument controlling the branch.
|
||||
pub arg: Value,
|
||||
/// Branch destination EBB.
|
||||
pub destination: Ebb,
|
||||
/// Arguments passed to destination EBB.
|
||||
pub varargs: VariableArgs,
|
||||
}
|
||||
|
||||
@@ -353,6 +364,8 @@ pub struct CallData {
|
||||
pub struct IndirectCallData {
|
||||
/// Callee function.
|
||||
pub arg: Value,
|
||||
|
||||
/// Signature of the callee function.
|
||||
pub sig_ref: SigRef,
|
||||
|
||||
/// Dynamically sized array containing call argument values.
|
||||
@@ -362,7 +375,7 @@ pub struct IndirectCallData {
|
||||
/// Payload of a return instruction.
|
||||
#[derive(Clone, Debug)]
|
||||
pub struct ReturnData {
|
||||
// Dynamically sized array containing return values.
|
||||
/// Dynamically sized array containing return values.
|
||||
pub varargs: VariableArgs,
|
||||
}
|
||||
|
||||
|
||||
@@ -87,6 +87,7 @@ impl settings::Configurable for Builder {
|
||||
}
|
||||
}
|
||||
|
||||
/// Methods that are specialized to a target ISA.
|
||||
pub trait TargetIsa {
|
||||
/// Get the name of this ISA.
|
||||
fn name(&self) -> &'static str;
|
||||
|
||||
@@ -16,6 +16,7 @@ struct Isa {
|
||||
cpumode: &'static [shared_enc_tables::Level1Entry<u16>],
|
||||
}
|
||||
|
||||
/// Get an ISA builder for creating RISC-V targets.
|
||||
pub fn isa_builder() -> IsaBuilder {
|
||||
IsaBuilder {
|
||||
setup: settings::builder(),
|
||||
|
||||
@@ -1,14 +1,12 @@
|
||||
//! Cretonne code generation library.
|
||||
|
||||
// ====------------------------------------------------------------------------------------==== //
|
||||
//
|
||||
// Cretonne code generation library.
|
||||
//
|
||||
// ====------------------------------------------------------------------------------------==== //
|
||||
#![deny(missing_docs)]
|
||||
|
||||
pub use verifier::verify_function;
|
||||
pub use write::write_function;
|
||||
pub use legalizer::legalize_function;
|
||||
|
||||
/// Version number of the cretonne crate.
|
||||
pub const VERSION: &'static str = env!("CARGO_PKG_VERSION");
|
||||
|
||||
pub mod ir;
|
||||
|
||||
@@ -144,6 +144,7 @@ pub enum Error {
|
||||
BadValue,
|
||||
}
|
||||
|
||||
/// A result returned when changing a setting.
|
||||
pub type Result<T> = result::Result<T, Error>;
|
||||
|
||||
/// Implementation details for generated code.
|
||||
@@ -156,10 +157,15 @@ pub mod detail {
|
||||
|
||||
/// An instruction group template.
|
||||
pub struct Template {
|
||||
/// Name of the instruction group.
|
||||
pub name: &'static str,
|
||||
/// List of setting descriptors.
|
||||
pub descriptors: &'static [Descriptor],
|
||||
/// Union of all enumerators.
|
||||
pub enumerators: &'static [&'static str],
|
||||
/// Hash table of settings.
|
||||
pub hash_table: &'static [u16],
|
||||
/// Default values.
|
||||
pub defaults: &'static [u8],
|
||||
}
|
||||
|
||||
@@ -227,7 +233,10 @@ pub mod detail {
|
||||
#[derive(Clone, Copy)]
|
||||
pub enum Detail {
|
||||
/// A boolean setting only uses one bit, numbered from LSB.
|
||||
Bool { bit: u8 },
|
||||
Bool {
|
||||
/// 0-7.
|
||||
bit: u8,
|
||||
},
|
||||
|
||||
/// A numerical setting uses the whole byte.
|
||||
Num,
|
||||
|
||||
@@ -61,7 +61,9 @@ use std::result;
|
||||
/// A verifier error.
|
||||
#[derive(Debug, PartialEq, Eq)]
|
||||
pub struct Error {
|
||||
/// The entity causing the verifier error.
|
||||
pub location: AnyEntity,
|
||||
/// Error message.
|
||||
pub message: String,
|
||||
}
|
||||
|
||||
@@ -71,6 +73,7 @@ impl Display for Error {
|
||||
}
|
||||
}
|
||||
|
||||
/// Verifier result.
|
||||
pub type Result<T> = result::Result<T, Error>;
|
||||
|
||||
// Create an `Err` variant of `Result<X>` from a location and `format!` args.
|
||||
@@ -90,11 +93,12 @@ macro_rules! err {
|
||||
};
|
||||
}
|
||||
|
||||
/// Verify `func`.
|
||||
pub fn verify_function(func: &Function) -> Result<()> {
|
||||
Verifier::new(func).run()
|
||||
}
|
||||
|
||||
pub struct Verifier<'a> {
|
||||
struct Verifier<'a> {
|
||||
func: &'a Function,
|
||||
}
|
||||
|
||||
@@ -165,7 +169,7 @@ impl<'a> Verifier<'a> {
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use super::*;
|
||||
use super::{Verifier, Error};
|
||||
use ir::Function;
|
||||
use ir::instructions::{InstructionData, Opcode};
|
||||
use ir::types;
|
||||
|
||||
Reference in New Issue
Block a user