From 28e4fdc337430a3b6f9c22f60d7d79a7c9e0b365 Mon Sep 17 00:00:00 2001 From: Nikita Orlov Date: Fri, 28 Jun 2024 19:18:51 +0200 Subject: [PATCH] #529 Print output (#530) closes #529 --- src/cmd/cmd.zig | 13 +++++++++++++ src/vm/cairo_run.zig | 12 ++++++++++-- src/vm/config.zig | 2 ++ src/vm/core.zig | 22 +++++++++++----------- 4 files changed, 36 insertions(+), 13 deletions(-) diff --git a/src/cmd/cmd.zig b/src/cmd/cmd.zig index efeb2595..ac696dc0 100644 --- a/src/cmd/cmd.zig +++ b/src/cmd/cmd.zig @@ -79,6 +79,18 @@ pub fn run() !void { .required = false, }; + // Command-line option for enabling trace mode. + const print_output = cli.Option{ + // The full name of the option. + .long_name = "print-output", + // Description of the option's purpose. + .help = "Print output from Output runner", + // Reference to the trace mode configuration. + .value_ref = r.mkRef(&config.print_output), + // Indicates if the option is required. + .required = false, + }; + // Command-line option for specifying the output trace file. const output_trace = cli.Option{ // The full name of the option. @@ -161,6 +173,7 @@ pub fn run() !void { program_option, output_trace, output_memory, + print_output, }, // Action to be executed for the subcommand. .target = .{ .action = .{ .exec = execute } }, diff --git a/src/vm/cairo_run.zig b/src/vm/cairo_run.zig index 1df984be..b5e716cb 100644 --- a/src/vm/cairo_run.zig +++ b/src/vm/cairo_run.zig @@ -70,7 +70,6 @@ pub fn runConfig(allocator: Allocator, config: Config) !void { var entrypoint: []const u8 = "main"; - // TODO: add flag for extensive_hints var runner = try CairoRunner.init( allocator, try parsed_program.value.parseProgramJson(allocator, &entrypoint), @@ -83,7 +82,6 @@ pub fn runConfig(allocator: Allocator, config: Config) !void { const end = try runner.setupExecutionState(config.allow_missing_builtins orelse config.proof_mode); - // TODO: make flag for extensive_hints var hint_processor: HintProcessor = .{}; try runner.runUntilPC(end, &hint_processor); try runner.endRun( @@ -93,6 +91,16 @@ pub fn runConfig(allocator: Allocator, config: Config) !void { &hint_processor, ); + if (config.print_output) { + var buf = try std.ArrayList(u8).initCapacity(allocator, 100); + defer buf.deinit(); + + try buf.appendSlice("Program Output:\n"); + try vm.writeOutput(buf.writer()); + + std.log.debug("{s}", .{buf.items}); + } + // TODO readReturnValues necessary for builtins if (config.output_trace != null or config.output_memory != null) { try runner.relocate(); diff --git a/src/vm/config.zig b/src/vm/config.zig index 2f925f43..2ce794ce 100644 --- a/src/vm/config.zig +++ b/src/vm/config.zig @@ -16,6 +16,8 @@ pub const Config = struct { output_trace: ?[]const u8 = undefined, /// Write memory to binary file output_memory: ?[]const u8 = undefined, + /// Print output from Output runner + print_output: bool = false, allow_missing_builtins: ?bool = null, }; diff --git a/src/vm/core.zig b/src/vm/core.zig index 7f370a02..9e62f792 100644 --- a/src/vm/core.zig +++ b/src/vm/core.zig @@ -23,6 +23,7 @@ const build_options = @import("../build_options.zig"); const RangeCheckBuiltinRunner = @import("builtins/builtin_runner/range_check.zig").RangeCheckBuiltinRunner; const SignatureBuiltinRunner = @import("builtins/builtin_runner/signature.zig").SignatureBuiltinRunner; const BuiltinRunner = @import("builtins/builtin_runner/builtin_runner.zig").BuiltinRunner; +const builtin_runner = @import("builtins/builtin_runner/builtin_runner.zig"); const Felt252 = @import("../math/fields/starknet.zig").Felt252; const HashBuiltinRunner = @import("./builtins/builtin_runner/hash.zig").HashBuiltinRunner; const Instruction = instructions.Instruction; @@ -1357,22 +1358,21 @@ pub const CairoVM = struct { /// /// Returns an error if writing the output fails. pub fn writeOutput(self: *Self, writer: anytype) !void { - var builtin: ?*BuiltinRunner = null; + var builtin: *BuiltinRunner = val: { - // Iterate through the built-in runners to find the output runner. - for (self.builtin_runners.items) |*runner| { - if (runner.* == .Output) { - builtin = runner; - break; + // Iterate through the built-in runners to find the output runner. + for (self.builtin_runners.items) |*runner| { + if (runner.* == .Output) { + break :val runner; + } } - } - - // If no output runner is found, return. - if (builtin == null) return; + // Output runner is not exist, so we just return + return; + }; // Compute effective sizes of memory segments. const segment_used_sizes = try self.segments.computeEffectiveSize(false); - const segment_index = builtin.?.base(); + const segment_index = builtin.base(); // Iterate through the memory segments and write output based on their content. for (0..segment_used_sizes.items[@intCast(segment_index)]) |i| {