WIP.
This commit is contained in:
parent
9ef4064853
commit
003650281a
|
@ -19,12 +19,12 @@ pub trait EntityRef: Clone + Copy + PartialEq + Eq + PartialOrd + Ord + Hash {
|
||||||
}
|
}
|
||||||
|
|
||||||
#[macro_export]
|
#[macro_export]
|
||||||
macro_rules! entity {
|
macro_rules! declare_entity {
|
||||||
($name:tt, $prefix:tt) => {
|
($name:tt, $prefix:tt) => {
|
||||||
#[derive(Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash)]
|
#[derive(Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash)]
|
||||||
pub struct $name(u32);
|
pub struct $name(u32);
|
||||||
|
|
||||||
impl crate::entity::EntityRef for $name {
|
impl $crate::entity::EntityRef for $name {
|
||||||
fn new(value: usize) -> Self {
|
fn new(value: usize) -> Self {
|
||||||
use std::convert::TryFrom;
|
use std::convert::TryFrom;
|
||||||
let value = u32::try_from(value).unwrap();
|
let value = u32::try_from(value).unwrap();
|
||||||
|
@ -41,13 +41,13 @@ macro_rules! entity {
|
||||||
|
|
||||||
impl std::convert::From<u32> for $name {
|
impl std::convert::From<u32> for $name {
|
||||||
fn from(val: u32) -> Self {
|
fn from(val: u32) -> Self {
|
||||||
<Self as crate::entity::EntityRef>::new(val as usize)
|
<Self as $crate::entity::EntityRef>::new(val as usize)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl std::default::Default for $name {
|
impl std::default::Default for $name {
|
||||||
fn default() -> Self {
|
fn default() -> Self {
|
||||||
<Self as crate::entity::EntityRef>::invalid()
|
<Self as $crate::entity::EntityRef>::invalid()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1353,6 +1353,9 @@ impl<'a, 'b> FunctionBodyBuilder<'a, 'b> {
|
||||||
let pick = self
|
let pick = self
|
||||||
.body
|
.body
|
||||||
.add_value(ValueDef::PickOutput(value, i, output_ty));
|
.add_value(ValueDef::PickOutput(value, i, output_ty));
|
||||||
|
if let Some(block) = self.cur_block {
|
||||||
|
self.body.blocks[block].insts.push(pick);
|
||||||
|
}
|
||||||
self.op_stack.push((output_ty, pick));
|
self.op_stack.push((output_ty, pick));
|
||||||
log::trace!(" -> pick {}: {:?} ty {:?}", i, pick, output_ty);
|
log::trace!(" -> pick {}: {:?} ty {:?}", i, pick, output_ty);
|
||||||
}
|
}
|
||||||
|
|
18
src/ir.rs
18
src/ir.rs
|
@ -1,6 +1,6 @@
|
||||||
//! Intermediate representation for Wasm.
|
//! Intermediate representation for Wasm.
|
||||||
|
|
||||||
use crate::entity;
|
use crate::declare_entity;
|
||||||
|
|
||||||
#[derive(Clone, Copy, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
|
#[derive(Clone, Copy, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
|
||||||
pub enum Type {
|
pub enum Type {
|
||||||
|
@ -39,14 +39,14 @@ impl std::fmt::Display for Type {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
entity!(Signature, "sig");
|
declare_entity!(Signature, "sig");
|
||||||
entity!(Func, "func");
|
declare_entity!(Func, "func");
|
||||||
entity!(Block, "block");
|
declare_entity!(Block, "block");
|
||||||
entity!(Local, "local");
|
declare_entity!(Local, "local");
|
||||||
entity!(Global, "global");
|
declare_entity!(Global, "global");
|
||||||
entity!(Table, "table");
|
declare_entity!(Table, "table");
|
||||||
entity!(Memory, "memory");
|
declare_entity!(Memory, "memory");
|
||||||
entity!(Value, "v");
|
declare_entity!(Value, "v");
|
||||||
|
|
||||||
mod module;
|
mod module;
|
||||||
pub use module::*;
|
pub use module::*;
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
use super::{Block, FunctionBodyDisplay, Local, Signature, Type, Value, ValueDef};
|
use super::{Block, FunctionBodyDisplay, Local, Module, Signature, Type, Value, ValueDef};
|
||||||
use crate::entity::EntityVec;
|
use crate::entity::EntityVec;
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
@ -48,6 +48,27 @@ pub struct FunctionBody {
|
||||||
}
|
}
|
||||||
|
|
||||||
impl FunctionBody {
|
impl FunctionBody {
|
||||||
|
pub fn new(module: &Module, sig: Signature) -> FunctionBody {
|
||||||
|
let locals = EntityVec::from(module.signature(sig).params.clone());
|
||||||
|
let n_params = locals.len();
|
||||||
|
let rets = module.signature(sig).returns.clone();
|
||||||
|
let mut blocks = EntityVec::default();
|
||||||
|
let entry = blocks.push(BlockDef::default());
|
||||||
|
let mut values = EntityVec::default();
|
||||||
|
for (i, &arg_ty) in locals.values().enumerate() {
|
||||||
|
let value = values.push(ValueDef::BlockParam(entry, i, arg_ty));
|
||||||
|
blocks[entry].params.push((arg_ty, value));
|
||||||
|
}
|
||||||
|
FunctionBody {
|
||||||
|
n_params,
|
||||||
|
rets,
|
||||||
|
locals,
|
||||||
|
entry,
|
||||||
|
blocks,
|
||||||
|
values,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
pub fn add_block(&mut self) -> Block {
|
pub fn add_block(&mut self) -> Block {
|
||||||
let id = self.blocks.push(BlockDef::default());
|
let id = self.blocks.push(BlockDef::default());
|
||||||
log::trace!("add_block: block {}", id);
|
log::trace!("add_block: block {}", id);
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
use super::{Func, FuncDecl, Global, Memory, ModuleDisplay, Signature, Table, Type};
|
use super::{Func, FuncDecl, Global, Memory, ModuleDisplay, Signature, Table, Type};
|
||||||
use crate::entity::EntityVec;
|
use crate::entity::EntityVec;
|
||||||
use crate::frontend;
|
use crate::frontend;
|
||||||
|
use crate::ir::FunctionBody;
|
||||||
use anyhow::Result;
|
use anyhow::Result;
|
||||||
use fxhash::FxHashSet;
|
use fxhash::FxHashSet;
|
||||||
|
|
||||||
|
@ -233,4 +234,8 @@ impl<'a> Module<'a> {
|
||||||
{
|
{
|
||||||
ModuleDisplay(self)
|
ModuleDisplay(self)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn add_func(&mut self, sig: Signature, func: FunctionBody) -> Func {
|
||||||
|
self.funcs.push(FuncDecl::Body(sig, func))
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -6,8 +6,8 @@
|
||||||
pub use wasmparser;
|
pub use wasmparser;
|
||||||
|
|
||||||
mod backend;
|
mod backend;
|
||||||
mod cfg;
|
pub mod cfg;
|
||||||
mod entity;
|
pub mod entity;
|
||||||
mod frontend;
|
mod frontend;
|
||||||
mod ir;
|
mod ir;
|
||||||
mod op_traits;
|
mod op_traits;
|
||||||
|
|
|
@ -36,12 +36,12 @@
|
||||||
//! ensure that (e.g.) block 4 above is visited first when considering
|
//! ensure that (e.g.) block 4 above is visited first when considering
|
||||||
//! successors of block 2.
|
//! successors of block 2.
|
||||||
|
|
||||||
use crate::entity;
|
use crate::declare_entity;
|
||||||
use crate::entity::{EntityRef, EntityVec, PerEntity};
|
use crate::entity::{EntityRef, EntityVec, PerEntity};
|
||||||
use crate::ir::{Block, FunctionBody};
|
use crate::ir::{Block, FunctionBody};
|
||||||
use std::collections::{HashMap, HashSet};
|
use std::collections::{HashMap, HashSet};
|
||||||
|
|
||||||
entity!(RPOIndex, "rpo");
|
declare_entity!(RPOIndex, "rpo");
|
||||||
|
|
||||||
impl RPOIndex {
|
impl RPOIndex {
|
||||||
fn prev(self) -> RPOIndex {
|
fn prev(self) -> RPOIndex {
|
||||||
|
|
Loading…
Reference in a new issue