#include "../cmd.h" #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include enum { OPT_GENERIC, OPT_NO_ABBREV, OPT_PASS_OFFSET = 100, }; static int builder_test( const b_command *cmd, const b_arglist *args, const b_array *_) { struct mie_ctx *ctx = mie_ctx_create(); mie_builtin_dialect_create(ctx); mie_meta_dialect_create(ctx); mie_select_dialect_create(ctx); mie_ptr_dialect_create(ctx); mie_arith_dialect_create(ctx); mie_func_dialect_create(ctx); mie_cf_dialect_create(ctx); mie_scf_dialect_create(ctx); mie_index_dialect_create(ctx); mie_builtin_passes_register(ctx); struct mie_op *module = mie_ctx_create_op(ctx, "builtin", "module"); struct mie_builder *builder = mie_builder_create(ctx, module); const struct mie_type *i32 = mie_ctx_get_int_type(ctx, 32); const struct mie_type *i64 = mie_ctx_get_int_type(ctx, 64); struct mie_func_parameter params[] = { {.param_name = "p1", .param_type = i32}, {.param_name = "p2", .param_type = i64}, }; size_t nr_params = sizeof params / sizeof params[0]; const struct mie_type *ret_type = mie_ctx_get_int_type(ctx, 64); struct mie_op *func = mie_func_func_put( MIE_EMITTER(builder), "test_func", params, nr_params, &ret_type, 1); mie_builder_step_into_op(builder, func); struct mie_region *r_true, *r_false; struct mie_op *if_op = mie_scf_if_put( MIE_EMITTER(builder), params[0].param_reg, i32, &r_true, &r_false, NULL); struct mie_register *tmp = NULL; mie_builder_step_into_region(builder, r_true); tmp = mie_arith_constant_i_put(MIE_EMITTER(builder), 10, NULL); mie_scf_yield_put(MIE_EMITTER(builder), tmp); mie_builder_step_out(builder); mie_builder_step_into_region(builder, r_false); tmp = mie_arith_constant_i_put(MIE_EMITTER(builder), 20, NULL); mie_scf_yield_put(MIE_EMITTER(builder), tmp); mie_builder_step_out(builder); struct mie_register *v1 = mie_arith_constant_i_put(MIE_EMITTER(builder), 1024, NULL); struct mie_register *v2 = mie_arith_constant_i_put(MIE_EMITTER(builder), 2048, NULL); struct mie_register *add = mie_arith_addi_put(MIE_EMITTER(builder), v1, v2, NULL); struct mie_register *add2 = mie_arith_addi_put( MIE_EMITTER(builder), add, &if_op->op_result.items[0], NULL); mie_builder_step_out(builder); struct mie_pass_manager *pm = mie_pass_manager_create(ctx); struct mie_pass_manager *module_pm = mie_pass_manager_nest(pm); mie_pass_manager_filter_op(module_pm, "builtin", "module"); struct mie_pass_manager *func_pm = mie_pass_manager_nest(pm); mie_pass_manager_filter_op(module_pm, "func", "func"); b_arglist_iterator it; b_arglist_foreach(&it, args) { if (it.opt_id < OPT_PASS_OFFSET) { continue; } const b_command_option *opt = b_command_get_option(cmd, it.opt_id); if (!opt) { continue; } const char *pass_name = b_command_option_get_long_name(opt); struct mie_pass *pass = NULL; enum mie_status status = mie_ctx_get_pass(ctx, pass_name, NULL, &pass); if (status != MIE_SUCCESS) { printf("cannot load pass %s\n", pass_name); return -1; } mie_pass_manager_add_pass(func_pm, pass); } mie_pass_manager_run(pm, module); enum mie_print_flags flags = 0; if (b_arglist_get_count(args, OPT_GENERIC, B_COMMAND_INVALID_ID) > 0) { flags |= MIE_PRINT_F_GENERIC; } if (b_arglist_get_count(args, OPT_NO_ABBREV, B_COMMAND_INVALID_ID) == 0) { flags |= MIE_PRINT_F_ABBREVIATED; } struct mie_printer printer; mie_printer_init(&printer, ctx, b_stdout, flags); mie_printer_print_op(&printer, module); printf("\n"); return 0; } B_COMMAND(CMD_INTERNAL_BUILDER_TEST, CMD_INTERNAL) { B_COMMAND_NAME("builder-test"); B_COMMAND_DESC("mie_builder test"); B_COMMAND_FUNCTION(builder_test); B_COMMAND_OPTION(OPT_GENERIC) { B_OPTION_LONG_NAME("generic"); B_OPTION_SHORT_NAME('g'); B_OPTION_DESC("print operations in generic format."); } B_COMMAND_OPTION(OPT_NO_ABBREV) { B_OPTION_LONG_NAME("no-abbrev"); B_OPTION_SHORT_NAME('n'); B_OPTION_DESC( "don't use abbreviations for builtin types and ops."); } B_COMMAND_HELP_OPTION(); struct mie_ctx *ctx = mie_ctx_create(); mie_builtin_passes_register(ctx); size_t i = 0; b_btree_node *node = b_btree_first(&ctx->ctx_passes.map_entries); while (node) { mie_id *id = b_unbox(mie_id, node, e_node); struct mie_pass_definition *pass = b_unbox(struct mie_pass_definition, id, p_id); B_COMMAND_OPTION_GEN(OPT_PASS_OFFSET + i) { B_OPTION_LONG_NAME(pass->p_name); B_OPTION_DESC(pass->p_description); } node = b_btree_next(node); i++; } }