Skip to content

Commit

Permalink
feat(ir): assign name
Browse files Browse the repository at this point in the history
  • Loading branch information
JuniMay committed Feb 17, 2024
1 parent 18fe887 commit 3c55d3a
Show file tree
Hide file tree
Showing 3 changed files with 35 additions and 19 deletions.
22 changes: 21 additions & 1 deletion src/ir/builder.rs
Original file line number Diff line number Diff line change
Expand Up @@ -87,24 +87,28 @@ pub trait AddBlock {
}

pub trait ConstantBuilder: QueryValueData + AddValue {
/// Build a zero constant.
fn zero(&mut self, ty: Type) -> Result<Value, BuilderErr> {
if !ty.is_zero_initializable() {
return Err(BuilderErr::InvalidType);
}
self.add_value(ValueData::new(ty, ValueKind::Zero))
}

/// Build an undef constant.
fn undef(&mut self, ty: Type) -> Result<Value, BuilderErr> {
self.add_value(ValueData::new(ty, ValueKind::Undef))
}

/// Build a bytes constant.
fn bytes(&mut self, ty: Type, bytes: Vec<u8>) -> Result<Value, BuilderErr> {
if !ty.is_numeric() && !ty.is_ptr() {
return Err(BuilderErr::InvalidType);
}
self.add_value(ValueData::new(ty, ValueKind::Bytes(bytes)))
}

/// Build an array constant.
fn array(&mut self, ty: Type, values: Vec<Value>) -> Result<Value, BuilderErr> {
let (size, elem_type) = ty.as_array().ok_or(BuilderErr::InvalidType)?;

Expand All @@ -124,6 +128,7 @@ pub trait ConstantBuilder: QueryValueData + AddValue {
self.add_value(ValueData::new(ty, ValueKind::Array(values)))
}

/// Build a struct constant.
fn struct_(&mut self, ty: Type, values: Vec<Value>) -> Result<Value, BuilderErr> {
let fields = ty.as_struct().ok_or(BuilderErr::InvalidType)?;

Expand All @@ -145,21 +150,25 @@ pub trait ConstantBuilder: QueryValueData + AddValue {
}

pub trait LocalValueBuilder: QueryDfgData + AddValue + ConstantBuilder {
/// Build a block parameter.
fn block_param(&mut self, ty: Type) -> Result<Value, BuilderErr> {
self.add_value(ValueData::new(ty, ValueKind::BlockParam))
}

/// Build an alloc instruction.
fn alloc(&mut self, ty: Type) -> Result<Value, BuilderErr> {
self.add_value(Alloc::new_value_data(ty))
}

/// Build a load instruction.
fn load(&mut self, ty: Type, ptr: Value) -> Result<Value, BuilderErr> {
if !self.value_type(ptr)?.is_ptr() {
return Err(BuilderErr::InvalidType);
}
self.add_value(Load::new_value_data(ty, ptr))
}

/// Build a store instruction.
fn store(&mut self, val: Value, ptr: Value) -> Result<Value, BuilderErr> {
if !self.value_type(ptr)?.is_ptr() {
return Err(BuilderErr::InvalidType);
Expand All @@ -168,6 +177,7 @@ pub trait LocalValueBuilder: QueryDfgData + AddValue + ConstantBuilder {
self.add_value(Store::new_value_data(val, ptr))
}

/// Build a binary instruction.
fn binary(&mut self, op: BinaryOp, lhs: Value, rhs: Value) -> Result<Value, BuilderErr> {
let lhs_type = self.value_type(lhs)?;
let rhs_type = self.value_type(rhs)?;
Expand All @@ -193,6 +203,7 @@ pub trait LocalValueBuilder: QueryDfgData + AddValue + ConstantBuilder {
self.add_value(Binary::new_value_data(lhs_type, op, lhs, rhs))
}

/// Build a unary instruction.
fn unary(&mut self, op: UnaryOp, val: Value) -> Result<Value, BuilderErr> {
let val_type = self.value_type(val)?;

Expand All @@ -211,6 +222,7 @@ pub trait LocalValueBuilder: QueryDfgData + AddValue + ConstantBuilder {
self.add_value(Unary::new_value_data(val_type, op, val))
}

/// Build a jump instruction.
fn jump(&mut self, dst: Block, args: Vec<Value>) -> Result<Value, BuilderErr> {
let block_data = self.block_data(dst)?;

Expand All @@ -230,6 +242,7 @@ pub trait LocalValueBuilder: QueryDfgData + AddValue + ConstantBuilder {
self.add_value(Jump::new_value_data(dst, args))
}

/// Build a branch instruction.
fn branch(
&mut self,
cond: Value,
Expand Down Expand Up @@ -276,11 +289,13 @@ pub trait LocalValueBuilder: QueryDfgData + AddValue + ConstantBuilder {
))
}

/// Build a return instruction.
fn return_(&mut self, val: Option<Value>) -> Result<Value, BuilderErr> {
// type check of return is not performed here
self.add_value(Return::new_value_data(val))
}

/// Build a call instruction.
fn call(&mut self, ret_ty: Type, callee: Value, args: Vec<Value>) -> Result<Value, BuilderErr> {
let callee_type = self.value_type(callee)?;

Expand All @@ -291,6 +306,7 @@ pub trait LocalValueBuilder: QueryDfgData + AddValue + ConstantBuilder {
self.add_value(Call::new_value_data(ret_ty, callee, args))
}

/// Build a get element pointer instruction.
fn get_elem_ptr(
&mut self,
ptr: Value,
Expand All @@ -306,6 +322,7 @@ pub trait LocalValueBuilder: QueryDfgData + AddValue + ConstantBuilder {
}

pub trait LocalBlockBuilder: QueryDfgData + AddBlock {
/// Build a block.
fn block(&mut self, params: Vec<Value>) -> Result<Block, BuilderErr> {
for param in params.iter() {
if !self.is_value_block_param(*param)? {
Expand All @@ -318,12 +335,14 @@ pub trait LocalBlockBuilder: QueryDfgData + AddBlock {
}

pub trait GlobalValueBuilder: QueryValueData + AddValue + ConstantBuilder {
/// Add a constructed function to the module.
fn add_function(
&mut self,
value_data: ValueData,
function_data: FunctionData,
) -> Result<Function, BuilderErr>;

/// Build a global slot.
fn global_slot(&mut self, init: Value, mutable: bool) -> Result<Value, BuilderErr> {
if !self.is_value_const(init)? {
return Err(BuilderErr::InvalidMutability);
Expand All @@ -336,14 +355,15 @@ pub trait GlobalValueBuilder: QueryValueData + AddValue + ConstantBuilder {
))
}

/// Build a global function.
fn function(
&mut self,
name: String,
ty: Type,
kind: FunctionKind,
) -> Result<Function, BuilderErr> {
let data = FunctionData::new(name, ty.clone(), kind);
self.add_function(ValueData::new(ty, ValueKind::Function), data)
self.add_function(data.new_value_data(), data)
}
}

Expand Down
20 changes: 2 additions & 18 deletions src/ir/entities.rs
Original file line number Diff line number Diff line change
Expand Up @@ -66,26 +66,18 @@ impl FunctionData {
}

/// Create a new `ValueData` struct for the function
pub fn value_data(&self, ty: Type) -> ValueData {
ValueData::new(ty, ValueKind::Function)
pub fn new_value_data(&self) -> ValueData {
ValueData::new(self.ty.clone(), ValueKind::Function)
}

pub fn name(&self) -> &str {
&self.name
}

pub fn name_mut(&mut self) -> &mut String {
&mut self.name
}

pub fn ty(&self) -> &Type {
&self.ty
}

pub fn ty_mut(&mut self) -> &mut Type {
&mut self.ty
}

pub fn kind(&self) -> &FunctionKind {
&self.kind
}
Expand Down Expand Up @@ -225,15 +217,7 @@ impl ValueData {
&self.ty
}

pub fn ty_mut(&mut self) -> &mut Type {
&mut self.ty
}

pub fn kind(&self) -> &ValueKind {
&self.kind
}

pub fn kind_mut(&mut self) -> &mut ValueKind {
&mut self.kind
}
}
12 changes: 12 additions & 0 deletions src/ir/module.rs
Original file line number Diff line number Diff line change
Expand Up @@ -116,6 +116,14 @@ impl DataFlowGraph {
self.block_name_allocator.borrow_mut().get(block)
}

pub fn assign_local_value_name(&self, value: Value, name: String) -> Result<(), NameAllocErr> {
self.value_name_allocator.borrow_mut().assign(value, name)
}

pub fn assign_block_name(&self, block: Block, name: String) -> Result<(), NameAllocErr> {
self.block_name_allocator.borrow_mut().assign(block, name)
}

pub fn block_data(&self, block: Block) -> Option<&BlockData> {
self.blocks.get(&block)
}
Expand Down Expand Up @@ -262,6 +270,10 @@ impl Module {
self.name_allocator.borrow_mut().get(value)
}

pub fn assign_name(&mut self, value: Value, name: String) -> Result<(), NameAllocErr> {
self.name_allocator.borrow_mut().assign(value, name)
}

pub fn add_custom_type(&mut self, name: String, ty: Type) {
self.custom_types.borrow_mut().insert(name.clone(), ty);
self.custom_type_layout.push(name);
Expand Down

0 comments on commit 3c55d3a

Please sign in to comment.