mie: ir: implement generation and text output of phi instruction
This commit is contained in:
@@ -14,6 +14,7 @@ struct mie_module;
|
||||
struct mie_data;
|
||||
struct mie_type;
|
||||
struct mie_phi;
|
||||
struct mie_phi_edge;
|
||||
struct mie_ctx;
|
||||
|
||||
struct mie_builder {
|
||||
@@ -111,8 +112,8 @@ extern struct mie_value *mie_builder_getelementptr(
|
||||
extern struct mie_value *mie_builder_setelementptr(
|
||||
struct mie_builder *builder, struct mie_type *container_type,
|
||||
struct mie_value *container, struct mie_value *index);
|
||||
extern struct mie_phi *mie_builder_phi(
|
||||
extern struct mie_value *mie_builder_phi(
|
||||
struct mie_builder *builder, struct mie_type *type,
|
||||
unsigned int nr_edges, const char *name);
|
||||
struct mie_phi_edge *edges, unsigned int nr_edges, const char *name);
|
||||
|
||||
#endif
|
||||
|
||||
@@ -1,9 +1,12 @@
|
||||
#ifndef MIE_PHI_H_
|
||||
#define MIE_PHI_H_
|
||||
|
||||
#include <mie/instr.h>
|
||||
#include <blue/core/queue.h>
|
||||
#include <mie/ir/instr.h>
|
||||
#include <mie/misc.h>
|
||||
|
||||
struct mie_phi_edge {
|
||||
b_queue_entry e_entry;
|
||||
struct mie_block *e_incoming_block;
|
||||
struct mie_value *e_value;
|
||||
};
|
||||
@@ -16,4 +19,7 @@ struct mie_phi {
|
||||
struct mie_phi_edge *p_edges;
|
||||
};
|
||||
|
||||
MIE_API struct mie_phi_edge *mie_phi_edge_create(
|
||||
struct mie_block *incoming_block, struct mie_value *value);
|
||||
|
||||
#endif
|
||||
|
||||
@@ -9,6 +9,7 @@
|
||||
#include <mie/ir/module.h>
|
||||
#include <mie/ir/msg.h>
|
||||
#include <mie/ir/op.h>
|
||||
#include <mie/ir/phi.h>
|
||||
#include <mie/ir/ptr.h>
|
||||
#include <mie/ir/record.h>
|
||||
#include <mie/type.h>
|
||||
@@ -785,9 +786,47 @@ struct mie_value *mie_builder_setelementptr(
|
||||
return NULL;
|
||||
}
|
||||
|
||||
struct mie_phi *mie_builder_phi(
|
||||
struct mie_value *mie_builder_phi(
|
||||
struct mie_builder *builder, struct mie_type *type,
|
||||
unsigned int nr_edges, const char *name)
|
||||
struct mie_phi_edge *edges, unsigned int nr_edges, const char *name)
|
||||
{
|
||||
return NULL;
|
||||
struct mie_block *block = builder->b_current_block;
|
||||
|
||||
if (!block) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (block->b_terminator || !b_queue_empty(&block->b_instr)) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
struct mie_phi *phi = malloc(sizeof *phi);
|
||||
if (!phi) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
memset(phi, 0x0, sizeof *phi);
|
||||
|
||||
mie_instr_init(&phi->p_base, MIE_INSTR_PHI);
|
||||
|
||||
phi->p_type = type;
|
||||
phi->p_nr_edges = nr_edges;
|
||||
phi->p_edges = calloc(nr_edges, sizeof(struct mie_phi_edge));
|
||||
if (!phi->p_edges) {
|
||||
free(phi);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
memcpy(phi->p_edges, edges, nr_edges * sizeof(struct mie_phi_edge));
|
||||
|
||||
if (!mie_block_add_instr(builder->b_current_block, &phi->p_base)) {
|
||||
free(phi);
|
||||
free(phi->p_edges);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
mie_func_generate_value_name(
|
||||
builder->b_current_block->b_parent, MIE_VALUE(phi), name);
|
||||
|
||||
return MIE_VALUE(phi);
|
||||
}
|
||||
|
||||
@@ -14,6 +14,7 @@
|
||||
#include <mie/ir/module.h>
|
||||
#include <mie/ir/msg.h>
|
||||
#include <mie/ir/op.h>
|
||||
#include <mie/ir/phi.h>
|
||||
#include <mie/ir/ptr.h>
|
||||
#include <mie/ir/record.h>
|
||||
#include <mie/ir/value.h>
|
||||
@@ -138,7 +139,7 @@ static b_status write_operand_const(
|
||||
case MIE_TYPE_SELECTOR: {
|
||||
struct mie_selector *v = MIE_SELECTOR(c);
|
||||
|
||||
write_string_f(converter, "\"%s\"", v->sel_value);
|
||||
write_string_f(converter, "@%s", v->sel_value);
|
||||
break;
|
||||
}
|
||||
case MIE_TYPE_CLASS:
|
||||
@@ -648,9 +649,26 @@ static b_status write_instr(
|
||||
case MIE_INSTR_SETELEMENTPTR:
|
||||
write_string(converter, "setelementptr");
|
||||
break;
|
||||
case MIE_INSTR_PHI:
|
||||
write_string(converter, "phi");
|
||||
case MIE_INSTR_PHI: {
|
||||
struct mie_phi *phi = (struct mie_phi *)instr;
|
||||
mie_type_to_string(phi->p_type, type, sizeof type);
|
||||
write_string_f(converter, "phi %s ", type);
|
||||
|
||||
for (size_t i = 0; i < phi->p_nr_edges; i++) {
|
||||
if (i > 0) {
|
||||
write_string(converter, ", ");
|
||||
}
|
||||
|
||||
write_string(converter, "[ ");
|
||||
write_operand(
|
||||
converter,
|
||||
MIE_VALUE(phi->p_edges[i].e_incoming_block), 0);
|
||||
write_string(converter, ", ");
|
||||
write_operand(converter, phi->p_edges[i].e_value, 0);
|
||||
write_string(converter, " ]");
|
||||
}
|
||||
break;
|
||||
}
|
||||
default:
|
||||
write_string_f(converter, "<unknown>");
|
||||
break;
|
||||
|
||||
@@ -2,6 +2,7 @@
|
||||
#include <mie/ir/instr.h>
|
||||
#include <mie/ir/msg.h>
|
||||
#include <mie/ir/op.h>
|
||||
#include <mie/ir/phi.h>
|
||||
#include <mie/ir/ptr.h>
|
||||
|
||||
void mie_instr_init(struct mie_instr *instr, enum mie_instr_type type)
|
||||
@@ -44,6 +45,10 @@ static struct mie_type *get_type(struct mie_value *v, struct mie_ctx *ctx)
|
||||
struct mie_msg *msg = (struct mie_msg *)instr;
|
||||
return msg->msg_ret_type;
|
||||
}
|
||||
case MIE_INSTR_PHI: {
|
||||
struct mie_phi *phi = (struct mie_phi *)instr;
|
||||
return phi->p_type;
|
||||
}
|
||||
default:
|
||||
return NULL;
|
||||
}
|
||||
|
||||
19
mie/ir/phi.c
Normal file
19
mie/ir/phi.c
Normal file
@@ -0,0 +1,19 @@
|
||||
#include <mie/ir/phi.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
struct mie_phi_edge *mie_phi_edge_create(
|
||||
struct mie_block *incoming_block, struct mie_value *value)
|
||||
{
|
||||
struct mie_phi_edge *out = malloc(sizeof *out);
|
||||
if (!out) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
memset(out, 0x0, sizeof *out);
|
||||
|
||||
out->e_incoming_block = incoming_block;
|
||||
out->e_value = value;
|
||||
|
||||
return out;
|
||||
}
|
||||
Reference in New Issue
Block a user