/* * Stack * mainly used for backing up registers in assembly * 32 bits wide, can store an entire register per entry * 128 words long * TODO optional: send interrupt when pop on empty stack */ module Stack ( input clk, input reset, input [31:0] d, output [31:0] q, input push, input pop, input clear, hold ); reg [9:0] ptr = 10'd0; // stack pointer reg [31:0] stack [1023:0]; // stack reg [31:0] ramResult = 32'd0; reg useRamResult = 1'b0; reg [31:0] qreg = 32'd0; assign q = (useRamResult) ? ramResult : qreg; always @(posedge clk) begin if (reset) begin ptr <= 10'd0; useRamResult <= 32'd0; qreg <= 32'd0; end else begin if (push) begin stack[ptr] <= d; ptr <= ptr + 1'b1; $display("%d: push @%d := %d", $time, ptr, d); end if (pop) begin useRamResult <= 1'b0; ramResult <= stack[ptr - 1'b1]; if (clear) begin qreg <= 32'd0; end else if (hold) begin qreg <= qreg; end else begin useRamResult <= 1'b1; ptr <= ptr - 1'b1; //q <= stack[ptr - 1'b1]; // simulation does not like this when ptr = 0 $display("%d: pop @%d := %d", $time, ptr, stack[ptr - 1'b1]); end end end end integer i; initial begin for (i = 0; i < 1024; i = i + 1) begin stack[i] = 32'd0; end end endmodule