// Instruction decoder of Nandgame // corresponds to levels // - control selector // - control unit `timescale 1us/1us `include "alu.sv" `include "cond_check.sv" module instruction_decode #( parameter DATA_WIDTH = 16 ) ( input [15:0] instruction, input [(DATA_WIDTH-1):0] A_i, input [(DATA_WIDTH-1):0] D_i, input [(DATA_WIDTH-1):0] pA_i, output [(DATA_WIDTH-1):0] RES, output do_jump, output dst_a, output dst_d, output dst_pa ); wire is_immediate; // bit 15 set = ALU instruction // bit 15 unset = immediate assign is_immediate = !instruction[15]; assign dst_a = is_immediate || instruction[5]; assign dst_d = !is_immediate && instruction[4]; assign dst_pa = !is_immediate && instruction[3]; wire use_pointer_a_for_alu; wire [(DATA_WIDTH-1):0] alu_y; assign use_pointer_a_for_alu = instruction[12]; assign alu_y = use_pointer_a_for_alu ? pA_i : A_i; wire [(DATA_WIDTH-1):0] alu_res; alu #( .DATA_WIDTH(DATA_WIDTH) ) my_alu ( .X(D_i), .Y(alu_y), .u(instruction[10]), .opcode(instruction[9:8]), .zx(instruction[7]), .sw(instruction[6]), .RES(alu_res) ); wire result_jump; cond_check #( .DATA_WIDTH(DATA_WIDTH) ) my_cond ( .X(alu_res), .ltz(instruction[2]), .eqz(instruction[1]), .gtz(instruction[0]), .res(result_jump) ); assign do_jump = is_immediate ? 0 : result_jump; assign RES = is_immediate ? instruction : alu_res; endmodule