diff --git a/src/frontend/sras.sv b/src/frontend/sras.sv
index 498fddf2a79d9e7326aeb6b6968e37d8d0428637..71208fd8762e8596dcac0cca216abe6d947e5651 100644
--- a/src/frontend/sras.sv
+++ b/src/frontend/sras.sv
@@ -38,48 +38,48 @@ module sras #(
     assign ptr_spec_d = (bad_spec_i) ? ptr_backup_q : (begin_spec_i) ? ptr_spec_q + 1'b1 : ptr_spec_q;
     assign ptr_backup_d = (valid_spec_i) ? ptr_backup_q + 1'b1 : ptr_backup_q;
 
-    always_comb begin
-        stack_d      = stack_q;
-        tos_d        = tos_q;
+    logic [$clog2(SpecDepth)-1:0] previous_tos_addr;
+    logic [$clog2(DEPTH)-1:0] previous_tos, prev_plus_one, pp_plus_one, prev_minus_one;
 
-        if (!bad_spec_i && begin_spec_i) begin
-            stack_d[ptr_spec_d] = stack_q[ptr_spec_q];
-            tos_d[ptr_spec_d] = tos_q[ptr_spec_q];
-        end
+    assign previous_tos_addr = (!bad_spec_i && begin_spec_i) ? ptr_spec_q : ptr_spec_d;
+    assign previous_tos = tos_q[previous_tos_addr];
 
-        data_o = stack_d[ptr_spec_d][tos_d[ptr_spec_d]];
+    assign prev_plus_one = previous_tos + 1'b1;
+    assign pp_plus_one = tos_q[ptr_spec_q] + 1'b1;
+    assign prev_minus_one = previous_tos - 1'b1;
 
-        // leave everything untouched and just push the latest value to the
-        // top of the stack
-        if (pop_i && push_i) begin
-            stack_d[ptr_spec_d][tos_d[ptr_spec_d]].ra = data_i;
-            stack_d[ptr_spec_d][tos_d[ptr_spec_d]].valid = 1'b1;
-        end else begin
-            // push on the stack
-            if (push_i) begin
-                tos_d[ptr_spec_d] = tos_d[ptr_spec_d] + 1'b1;
-                stack_d[ptr_spec_d][tos_d[ptr_spec_d]].ra = data_i;
-                // mark the new return address as valid
-                stack_d[ptr_spec_d][tos_d[ptr_spec_d]].valid = 1'b1;
-
-                if (begin_spec_i) begin
-                    tos_d[ptr_spec_q] = tos_d[ptr_spec_q] + 1'b1;
-                    stack_d[ptr_spec_q][tos_d[ptr_spec_q]] = stack_d[ptr_spec_d][tos_d[ptr_spec_d]];
-                end
-            end
-
-            if (pop_i) begin
-                // we popped the value so invalidate the end of the stack
-                stack_d[ptr_spec_d][tos_d[ptr_spec_d]].ra = '0;
-                stack_d[ptr_spec_d][tos_d[ptr_spec_d]].valid = 1'b0;
-                tos_d[ptr_spec_d] = tos_d[ptr_spec_d] - 1'b1;
-            end
-        end
+    for (genvar i = 0; i < SpecDepth; i++) begin
+        assign tos_d[i] = (flush_i) ? '0 :
+                          (i == ptr_spec_d && push_i && !pop_i) ? prev_plus_one :
+                          (i == ptr_spec_q && push_i && !pop_i) ? pp_plus_one :
+                          (i == ptr_spec_d && !push_i && pop_i) ? prev_minus_one :
+                          (i == ptr_spec_d && !bad_spec_i && begin_spec_i) ? tos_q[ptr_spec_q] :
+                          tos_q[i];
+    end
 
-        if (flush_i) begin
-            stack_d = '0;
-            tos_d   = '0;
-        end
+    assign data_o = stack_q[previous_tos_addr][previous_tos];
+
+    ariane_pkg::ras_t to_push;
+    assign to_push.ra = (push_i) ? data_i : 0;
+    assign to_push.valid = push_i;
+
+    ariane_pkg::ras_t [DEPTH-1:0] new_stack, prev_stack;
+
+    for (genvar i = 0; i < DEPTH; i++) begin
+        assign new_stack[i] = ((i == previous_tos && pop_i) ||
+                               (i == prev_plus_one && push_i)) ? to_push :
+                              (!bad_spec_i && begin_spec_i) ? stack_q[ptr_spec_q][i] :
+                              stack_q[ptr_spec_d][i];
+
+        assign prev_stack[i] = (i == pp_plus_one && push_i) ? to_push :
+                               stack_q[ptr_spec_q][i];
+    end
+
+    for (genvar i = 0; i < SpecDepth; i++) begin
+        assign stack_d[i] = (flush_i) ? '0 :
+                            (i == ptr_spec_d) ? new_stack :
+                            (i == ptr_spec_q) ? prev_stack :
+                            stack_q[i];
     end
 
     always_ff @(posedge clk_i or negedge rst_ni) begin