Skip to content

Commit

Permalink
more pblock/call/control-flow plumbing
Browse files Browse the repository at this point in the history
  • Loading branch information
rcgoodfellow committed Sep 23, 2024
1 parent 36234af commit f0d0c24
Show file tree
Hide file tree
Showing 2 changed files with 86 additions and 15 deletions.
43 changes: 34 additions & 9 deletions codegen/htq/src/expression.rs
Original file line number Diff line number Diff line change
Expand Up @@ -561,7 +561,7 @@ fn emit_extern_call(
fn emit_indirect_action_call(
call: &p4::ast::Call,
_hlir: &Hlir,
_ast: &p4::ast::AST,
ast: &p4::ast::AST,
context: &P4Context<'_>,
ra: &mut RegisterAllocator,
_names: &HashMap<String, NameInfo>,
Expand Down Expand Up @@ -603,6 +603,7 @@ fn emit_indirect_action_call(
)?);
block_params.push(block_ra.alloc(&p.name));
}
block_params.push(info.args.clone());

let control_param_values = control_params
.iter()
Expand All @@ -616,21 +617,45 @@ fn emit_indirect_action_call(
.map(Value::reg)
.collect::<Vec<_>>();

let mut block_args = control_param_values.clone();
block_args.push(Value::reg(info.args.clone()));

for (i, a) in info.table.actions.iter().enumerate() {
// make a clean lbock for each action
let mut block_ra = block_ra.clone();
let mut block_param_values = block_param_values.clone();
// pop the args off, we're going to break it up into components
block_param_values.pop();

let action_decl = info.control.get_action(&a.name).ok_or(
CodegenError::ActionNotFound(a.clone(), info.control.clone()),
)?;
let mut control_out_params = Vec::default();
let mut out_params = Vec::default();
let mut stmts = Vec::default();

let mut action_params = Vec::default();

let mut offset = 0;
let key = info.args.clone();
for x in &action_decl.parameters {
if x.direction.is_out() {
out_params.push(ra.get(&x.name).ok_or(
CodegenError::NoRegisterForParameter(
x.name.clone(),
ra.clone(),
),
)?)
out_params.push(block_ra.alloc(&x.name));
}

let action_param_reg = block_ra.alloc(&format!("{}_arg", &x.name));
let sz = type_size(&x.ty, ast);
action_params.push(action_param_reg.clone());
stmts.push(Statement::Load(htq::ast::Load {
target: action_param_reg.clone(),
typ: Type::Bitfield(sz),
source: key.clone(),
offset: Value::number(offset),
}));

block_param_values.push(Value::reg(action_param_reg.clone()));

offset += sz as i128;
}
for x in &info.control.parameters {
if x.ty.is_lookup_result() {
Expand All @@ -646,9 +671,9 @@ fn emit_indirect_action_call(
source: info.variant.clone(),
predicate: Value::number(i as i128),
label: a.name.clone(),
args: control_param_values.clone(),
args: block_args.clone(),
}));
let mut stmts = Vec::default();

stmts.push(Statement::Call(htq::ast::Call {
fname: format!("{}_{}", info.control.name, a.name.clone()),
args: block_param_values.clone(),
Expand Down
58 changes: 52 additions & 6 deletions codegen/htq/src/statement.rs
Original file line number Diff line number Diff line change
Expand Up @@ -95,14 +95,60 @@ fn emit_if_block(
) -> Result<
(Vec<htq::ast::Statement>, Vec<htq::ast::StatementBlock>),
CodegenError,
> {
let (mut statements, mut blocks) = emit_conditional_block(
hlir,
ast,
context,
names,
&iblk.predicate,
&iblk.block,
ra,
afa,
psub,
table_context,
)?;

for elif in &iblk.else_ifs {
let (stmts, blks) = emit_conditional_block(
hlir,
ast,
context,
names,
&elif.predicate,
&elif.block,
ra,
afa,
psub,
table_context,
)?;
statements.extend(stmts);
blocks.extend(blks);
}

Ok((statements, blocks))
}

fn emit_conditional_block(
hlir: &Hlir,
ast: &p4::ast::AST,
context: &P4Context<'_>,
names: &mut HashMap<String, NameInfo>,
predicate: &p4::ast::Expression,
block: &p4::ast::StatementBlock,
ra: &mut RegisterAllocator,
afa: &mut AsyncFlagAllocator,
psub: &mut HashMap<ControlParameter, Vec<Register>>,
table_context: &mut TableContext,
) -> Result<
(Vec<htq::ast::Statement>, Vec<htq::ast::StatementBlock>),
CodegenError,
> {
let mut result = Vec::default();
let mut blocks = Vec::default();

let (source, predicate) =
if let ExpressionKind::Binary(lhs, BinOp::Eq, rhs) =
&iblk.predicate.kind
{
if let ExpressionKind::Binary(lhs, BinOp::Eq, rhs) = &predicate.kind {
let (source_statements, blks, source) =
emit_single_valued_expression(
lhs.as_ref(),
Expand Down Expand Up @@ -135,7 +181,7 @@ fn emit_if_block(
} else {
let (predicate_statements, blks, source) =
emit_single_valued_expression(
iblk.predicate.as_ref(),
predicate,
hlir,
ast,
context,
Expand Down Expand Up @@ -169,7 +215,7 @@ fn emit_if_block(
statements: Vec::default(),
};

for stmt in &iblk.block.statements {
for stmt in &block.statements {
// TODO nested if blocks
let (stmts, blks) = emit_statement(
stmt,
Expand All @@ -195,7 +241,7 @@ fn emit_if_block(
out_params.push(block_ra.get(&x.name).ok_or(
CodegenError::NoRegisterForParameter(
x.name.clone(),
ra.clone(),
block_ra.clone(),
),
)?);
}
Expand Down

0 comments on commit f0d0c24

Please sign in to comment.