Guest User

Untitled

a guest
Jun 5th, 2016
74
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
VeriLog 14.91 KB | None | 0 0
  1. From b171b71ea4d95c9eaa0b531cc8147863e81b20e2 Mon Sep 17 00:00:00 2001
  2. From: "Alex L. White" <space.monkey.delivers@gmail.com>
  3. Date: Thu, 19 May 2016 19:36:06 +0300
  4. Subject: [PATCH] Introducing saturation counter branch predictor
  5.  
  6. ---
  7.  rtl/verilog/mor1kx_branch_prediction.v             | 85 ++++++++++++++++------
  8.  .../mor1kx_branch_predictor_saturation_counter.v   | 84 +++++++++++++++++++++
  9.  rtl/verilog/mor1kx_branch_predictor_simple.v       | 36 +++++++++
  10.  rtl/verilog/mor1kx_cpu_cappuccino.v                | 14 +++-
  11.  rtl/verilog/mor1kx_decode_execute_cappuccino.v     | 10 +++
  12.  5 files changed, 206 insertions(+), 23 deletions(-)
  13.  create mode 100644 rtl/verilog/mor1kx_branch_predictor_saturation_counter.v
  14.  create mode 100644 rtl/verilog/mor1kx_branch_predictor_simple.v
  15.  
  16. diff --git a/rtl/verilog/mor1kx_branch_prediction.v b/rtl/verilog/mor1kx_branch_prediction.v
  17. index a82c1f9..3d56f5e 100644
  18. --- a/rtl/verilog/mor1kx_branch_prediction.v
  19. +++ b/rtl/verilog/mor1kx_branch_prediction.v
  20. @@ -18,35 +18,78 @@
  21.  
  22.  module mor1kx_branch_prediction
  23.    #(
  24. -    parameter OPTION_OPERAND_WIDTH = 32
  25. +    parameter OPTION_OPERAND_WIDTH = 32,
  26. +    parameter FEATURE_BRANCH_PREDICTOR = "NONE"
  27.      )
  28.     (
  29. -    input  clk,
  30. -    input  rst,
  31. +   input clk,
  32. +   input rst,
  33.  
  34. -    // Signals belonging to the stage where the branch is predicted.
  35. -    input  op_bf_i,
  36. -    input  op_bnf_i,
  37. -    input [9:0] immjbr_upper_i,
  38. -    output     predicted_flag_o,
  39. +   // Signals belonging to the stage where the branch is predicted.
  40. +   input op_bf_i,               // from decode stage, brn is bf
  41. +   input op_bnf_i,              // from decode stage, brn is bnf
  42. +   input [9:0] immjbr_upper_i,  // from decode stage, imm
  43. +   output predicted_flag_o,     // to decode-execute stage, flag we predicate to be
  44.  
  45. -    // Signals belonging to the stage where the branch is resolved.
  46. -    input  prev_op_brcond_i,
  47. -    input  prev_predicted_flag_i,
  48. -    input  flag_i,
  49. +   // Signals belonging to the stage where the branch is resolved.
  50. +   input prev_op_brcond_i,      // from decode-execute stage, prev brn was cond
  51. +   input prev_predicted_flag_i, // from decode-execute, prev predicated flag
  52. +   input flag_i,                // from execute-ctrl stage, real flag we got
  53.  
  54. -    // Branch misprediction indicator
  55. -    output     branch_mispredict_o
  56. -    );
  57. +   input padv_decode_i,         // is decode stage stalled
  58. +   input execute_bf_i,          // prev insn was bf
  59. +   input execute_bnf_i,         // prev insn was bnf
  60. +
  61. +   // Branch misprediction indicator
  62. +   output  branch_mispredict_o // to decode-execute stage, was brn mispredicted or not
  63. +   );
  64.  
  65.     // Compare the real flag with the previously predicted flag and signal a
  66.     // misprediction in case of a mismatch.
  67. -   assign branch_mispredict_o = prev_op_brcond_i &
  68. -               (flag_i != prev_predicted_flag_i);
  69. +   assign branch_mispredict_o = prev_op_brcond_i & (flag_i != prev_predicted_flag_i);
  70.  
  71. -   // Static branch prediction - backward branches are predicted as taken,
  72. -   // forward branches as not taken.
  73. -   assign predicted_flag_o = op_bf_i & immjbr_upper_i[9] |
  74. -                op_bnf_i & !immjbr_upper_i[9];
  75. +generate
  76. +if (FEATURE_BRANCH_PREDICTOR=="SAT_COUNTER") begin : branch_predictor_saturation_counter
  77. +   mor1kx_branch_predictor_saturation_counter
  78. +     #(
  79. +       .OPTION_OPERAND_WIDTH(OPTION_OPERAND_WIDTH)
  80. +       )
  81. +      mor1kx_branch_predictor_saturation_counter
  82. +      (
  83. +         // Outputs
  84. +         .predicted_flag_o                 (predicted_flag_o),
  85. +         // Inputs
  86. +         .clk                              (clk),
  87. +         .rst                              (rst),
  88. +         .flag_i                           (flag_i),
  89. +         .execute_op_bf_i                  (execute_op_bf_i),
  90. +         .execute_op_bnf_i                 (execute_op_bnf_i),
  91. +         .op_bf_i                          (op_bf_i),
  92. +         .op_bnf_i                         (op_bnf_i),
  93. +         .prev_op_brcond_i                 (prev_op_brcond_i),
  94. +         .branch_mispredict_i              (branch_mispredict_o));
  95. +      
  96. +end else if (FEATURE_BRANCH_PREDICTOR=="SIMPLE") begin : branch_predictor_simple
  97. +   mor1kx_branch_predictor_simple
  98. +     #(
  99. +       .OPTION_OPERAND_WIDTH(OPTION_OPERAND_WIDTH)
  100. +       )
  101. +      mor1kx_branch_predictor_simple
  102. +      (
  103. +         // Outputs
  104. +         .predicted_flag_o                 (predicted_flag_o),
  105. +         // Inputs
  106. +         .op_bf_i                          (op_bf_i),
  107. +         .op_bnf_i                         (op_bnf_i),
  108. +         .immjbr_upper_i                   (immjbr_upper_i));
  109. +  
  110. +end else if (FEATURE_BRANCH_PREDICTOR!="SIMPLE" &&
  111. +             FEATURE_BRANCH_PREDICTOR!="SAT_COUNTER") begin
  112. +   initial begin
  113. +      $display("Error: FEATURE_PREDICTOR_TYPE, %s, not valid", FEATURE_BRANCH_PREDICTOR);
  114. +      $finish();
  115. +   end
  116. +end
  117. +endgenerate
  118.  
  119.  endmodule
  120. diff --git a/rtl/verilog/mor1kx_branch_predictor_saturation_counter.v b/rtl/verilog/mor1kx_branch_predictor_saturation_counter.v
  121. new file mode 100644
  122. index 0000000..7e93be5
  123. --- /dev/null
  124. +++ b/rtl/verilog/mor1kx_branch_predictor_saturation_counter.v
  125. @@ -0,0 +1,84 @@
  126. +/******************************************************************************
  127. + This Source Code Form is subject to the terms of the
  128. + Open Hardware Description License, v. 1.0. If a copy
  129. + of the OHDL was not distributed with this file, You
  130. + can obtain one at http://juliusbaxter.net/ohdl/ohdl.txt
  131. +
  132. + Description: Branch prediction module
  133. + Generates a predicted flag output and compares that to the real flag
  134. + when it comes back in the following pipeline stage.
  135. + Signals are deliberately not named after the pipeline stage they belong to,
  136. + in order to keep this module generic.
  137. +
  138. + Copyright (C) 2013 Stefan Kristiansson <stefan.kristiansson@saunalahti.fi>
  139. +
  140. + ******************************************************************************/
  141. +
  142. +`include "mor1kx-defines.v"
  143. +
  144. +module mor1kx_branch_predictor_saturation_counter
  145. +  #(
  146. +    parameter OPTION_OPERAND_WIDTH = 32
  147. +    )
  148. +   (
  149. +    input clk,
  150. +    input rst,
  151. +
  152. +    // Signals belonging to the stage where the branch is predicted.
  153. +    output predicted_flag_o,     //result of predictor
  154. +
  155. +    input execute_op_bf_i,       // prev insn was bf
  156. +    input execute_op_bnf_i,      // prev insn was bnf
  157. +    input op_bf_i,               // cur insn is bf
  158. +    input op_bnf_i,              // cur insn is bnf
  159. +    input padv_decode_i,         // pipeline is moved
  160. +    input flag_i,                // prev predicated flag
  161. +
  162. +    // Signals belonging to the stage where the branch is resolved.
  163. +    input prev_op_brcond_i,      // prev op was cond brn
  164. +    input branch_mispredict_i    // prev brn was mispredicted
  165. +    );
  166. +
  167. +   localparam [1:0]
  168. +      STATE_STRONGLY_NOT_TAKEN = 2'b00,
  169. +      STATE_WEAKLY_NOT_TAKEN   = 2'b01,
  170. +      STATE_WEAKLY_TAKEN       = 2'b10,
  171. +      STATE_STRONGLY_TAKEN     = 2'b11;
  172. +
  173. +   reg [1:0] state = STATE_WEAKLY_TAKEN;
  174. +
  175. +   assign predicted_flag_o = (state[1] && op_bf_i) || (!state[1] && op_bnf_i);
  176. +   wire brn_taken = (execute_op_bf_i && flag_i) || (execute_op_bnf_i && !flag_i);
  177. +
  178. +   always @(posedge clk) begin
  179. +      if (rst) begin
  180. +         // set default state to STATE_WEAKLY_TAKEN
  181. +         state <= STATE_WEAKLY_TAKEN;
  182. +      end else begin
  183. +         // if previous insn was cond brn and pipe is not stalled
  184. +         if (prev_op_brcond_i && padv_decode_i) begin
  185. +            // if brn was not taken
  186. +            if (!brn_taken) begin
  187. +               // change fsm state:
  188. +               //   STATE_STRONGLY_TAKEN -> STATE_WEAKLY_TAKEN
  189. +               //   STATE_WEAKLY_TAKEN -> STATE_WEAKLY_NOT_TAKEN
  190. +               //   STATE_WEAKLY_NOT_TAKEN -> STATE_STRONGLY_NOT_TAKEN
  191. +               //   STATE_STRONGLY_NOT_TAKEN -> STATE_STRONGLY_NOT_TAKEN
  192. +               state <= (state == STATE_STRONGLY_TAKEN) ? STATE_WEAKLY_TAKEN :
  193. +                        (state == STATE_WEAKLY_TAKEN)   ? STATE_WEAKLY_NOT_TAKEN
  194. +                                                        : STATE_STRONGLY_NOT_TAKEN;
  195. +            // if brn was taken
  196. +            end else begin
  197. +               // change fsm state:
  198. +               //   STATE_STRONGLY_NOT_TAKEN -> STATE_WEAKLY_NOT_TAKEN
  199. +               //   STATE_WEAKLY_NOT_TAKEN -> STATE_WEAKLY_TAKEN
  200. +               //   STATE_WEAKLY_TAKEN -> STATE_STRONGLY_TAKEN
  201. +               //   STATE_STRONGLY_TAKEN -> STATE_STRONGLY_TAKEN
  202. +               state <= (state == STATE_STRONGLY_NOT_TAKEN) ? STATE_WEAKLY_NOT_TAKEN :
  203. +                        (state == STATE_WEAKLY_NOT_TAKEN)   ? STATE_WEAKLY_TAKEN
  204. +                                                            : STATE_STRONGLY_TAKEN;
  205. +            end
  206. +         end
  207. +      end
  208. +   end
  209. +endmodule
  210. diff --git a/rtl/verilog/mor1kx_branch_predictor_simple.v b/rtl/verilog/mor1kx_branch_predictor_simple.v
  211. new file mode 100644
  212. index 0000000..8ad2f08
  213. --- /dev/null
  214. +++ b/rtl/verilog/mor1kx_branch_predictor_simple.v
  215. @@ -0,0 +1,36 @@
  216. +/******************************************************************************
  217. + This Source Code Form is subject to the terms of the
  218. + Open Hardware Description License, v. 1.0. If a copy
  219. + of the OHDL was not distributed with this file, You
  220. + can obtain one at http://juliusbaxter.net/ohdl/ohdl.txt
  221. +
  222. + Description: Branch prediction module
  223. + Generates a predicted flag output and compares that to the real flag
  224. + when it comes back in the following pipeline stage.
  225. + Signals are deliberately not named after the pipeline stage they belong to,
  226. + in order to keep this module generic.
  227. +
  228. + Copyright (C) 2013 Stefan Kristiansson <stefan.kristiansson@saunalahti.fi>
  229. +
  230. + ******************************************************************************/
  231. +
  232. +`include "mor1kx-defines.v"
  233. +
  234. +module mor1kx_branch_predictor_simple
  235. +  #(
  236. +    parameter OPTION_OPERAND_WIDTH = 32
  237. +    )
  238. +   (
  239. +    // Signals belonging to the stage where the branch is predicted.
  240. +    input op_bf_i,               // branch if flag
  241. +    input op_bnf_i,              // branch if not flag
  242. +    input [9:0] immjbr_upper_i,  // branch offset
  243. +    output predicted_flag_o      //result of predictor
  244. +    );
  245. +  
  246. +   // Static branch prediction - backward branches are predicted as taken,
  247. +   // forward branches as not taken.
  248. +   assign predicted_flag_o = op_bf_i & immjbr_upper_i[9] |
  249. +                             op_bnf_i & !immjbr_upper_i[9];
  250. +
  251. +endmodule
  252. diff --git a/rtl/verilog/mor1kx_cpu_cappuccino.v b/rtl/verilog/mor1kx_cpu_cappuccino.v
  253. index f282374..798fe02 100644
  254. --- a/rtl/verilog/mor1kx_cpu_cappuccino.v
  255. +++ b/rtl/verilog/mor1kx_cpu_cappuccino.v
  256. @@ -96,7 +96,8 @@ module mor1kx_cpu_cappuccino
  257.  
  258.      parameter FEATURE_MULTICORE = "NONE",
  259.  
  260. -    parameter FEATURE_TRACEPORT_EXEC = "NONE"
  261. +    parameter FEATURE_TRACEPORT_EXEC = "NONE",
  262. +    parameter FEATURE_BRANCH_PREDICTOR = "SIMPLE"  // SIMPLE|SAT_COUNTER
  263.      )
  264.     (
  265.      input                clk,
  266. @@ -665,6 +666,8 @@ module mor1kx_cpu_cappuccino
  267.        .execute_op_movhi_o               (execute_op_movhi_o),
  268.        .execute_op_msync_o               (execute_op_msync_o),
  269.        .execute_op_fpu_o                 (execute_op_fpu_o),
  270. +      .execute_op_bf_o                  (execute_op_bf_o),
  271. +      .execute_op_bnf_o                 (execute_op_bnf_o),
  272.        .execute_jal_result_o             (execute_jal_result_o[OPTION_OPERAND_WIDTH-1:0]),
  273.        .execute_opc_insn_o               (execute_opc_insn_o[`OR1K_OPCODE_WIDTH-1:0]),
  274.        .decode_branch_o                  (decode_branch_o),
  275. @@ -745,6 +748,9 @@ module mor1kx_cpu_cappuccino
  276.     /* mor1kx_branch_prediction AUTO_TEMPLATE (
  277.        .op_bf_i             (decode_op_bf_o),
  278.        .op_bnf_i                (decode_op_bnf_o),
  279. +      .execute_bf_i            (execute_op_bf_o),
  280. +      .execute_bnf_i           (execute_op_bnf_o),
  281. +      .padv_decode_i           (padv_decode_o),
  282.        .immjbr_upper_i          (decode_immjbr_upper_o),
  283.        .prev_op_brcond_i            (execute_op_brcond_o),
  284.        .prev_predicted_flag_i       (execute_predicted_flag_o),
  285. @@ -752,7 +758,8 @@ module mor1kx_cpu_cappuccino
  286.      );*/
  287.     mor1kx_branch_prediction
  288.       #(
  289. -       .OPTION_OPERAND_WIDTH(OPTION_OPERAND_WIDTH)
  290. +       .OPTION_OPERAND_WIDTH(OPTION_OPERAND_WIDTH),
  291. +       .FEATURE_BRANCH_PREDICTOR(FEATURE_BRANCH_PREDICTOR)
  292.         )
  293.     mor1kx_branch_prediction
  294.       (/*AUTOINST*/
  295. @@ -764,6 +771,9 @@ module mor1kx_cpu_cappuccino
  296.        .rst                              (rst),
  297.        .op_bf_i                          (decode_op_bf_o),        // Templated
  298.        .op_bnf_i                         (decode_op_bnf_o),       // Templated
  299. +      .execute_bf_i                     (execute_op_bf_o),        // Templated
  300. +      .execute_bnf_i                    (execute_op_bnf_o),        // Templated
  301. +      .padv_decode_i                    (padv_decode_o),        // Templated
  302.        .immjbr_upper_i                   (decode_immjbr_upper_o), // Templated
  303.        .prev_op_brcond_i                 (execute_op_brcond_o),   // Templated
  304.        .prev_predicted_flag_i            (execute_predicted_flag_o), // Templated
  305. diff --git a/rtl/verilog/mor1kx_decode_execute_cappuccino.v b/rtl/verilog/mor1kx_decode_execute_cappuccino.v
  306. index beadc5d..8d48b12 100644
  307. --- a/rtl/verilog/mor1kx_decode_execute_cappuccino.v
  308. +++ b/rtl/verilog/mor1kx_decode_execute_cappuccino.v
  309. @@ -168,6 +168,8 @@ module mor1kx_decode_execute_cappuccino
  310.      output reg                   execute_op_shift_o,
  311.      output reg                   execute_op_ffl1_o,
  312.      output reg                   execute_op_movhi_o,
  313. +    output reg                   execute_op_bf_o,
  314. +    output reg                   execute_op_bnf_o,
  315.      output reg                            execute_op_msync_o,
  316.      output [`OR1K_FPUOP_WIDTH-1:0]        execute_op_fpu_o,
  317.  
  318. @@ -218,6 +220,8 @@ module mor1kx_decode_execute_cappuccino
  319.     // Op control signals to execute stage
  320.     always @(posedge clk `OR_ASYNC_RST)
  321.       if (rst) begin
  322. +   execute_op_bf_o <= 1'b0;
  323. +   execute_op_bnf_o <= 1'b0;
  324.     execute_op_alu_o <= 1'b0;
  325.     execute_op_add_o <= 1'b0;
  326.     execute_op_mul_o <= 1'b0;
  327. @@ -242,6 +246,8 @@ module mor1kx_decode_execute_cappuccino
  328.     execute_op_brcond_o <= 1'b0;
  329.     execute_op_branch_o <= 0;
  330.       end else if (pipeline_flush_i) begin
  331. +   execute_op_bf_o <= 1'b0;
  332. +   execute_op_bnf_o <= 1'b0;
  333.     execute_op_alu_o <= 1'b0;
  334.     execute_op_add_o <= 1'b0;
  335.     execute_op_mul_o <= 1'b0;
  336. @@ -264,6 +270,8 @@ module mor1kx_decode_execute_cappuccino
  337.     execute_op_brcond_o <= 1'b0;
  338.     execute_op_branch_o <= 1'b0;
  339.       end else if (padv_i) begin
  340. +   execute_op_bf_o <= decode_op_bf_i;
  341. +   execute_op_bnf_o <= decode_op_bnf_i;
  342.     execute_op_alu_o <= decode_op_alu_i;
  343.     execute_op_add_o <= decode_op_add_i;
  344.     execute_op_mul_o <= decode_op_mul_i;
  345. @@ -288,6 +296,8 @@ module mor1kx_decode_execute_cappuccino
  346.     execute_op_brcond_o <= decode_op_brcond_i;
  347.     execute_op_branch_o <= decode_op_branch_i;
  348.     if (decode_bubble_o) begin
  349. +      execute_op_bf_o <= 1'b0;
  350. +      execute_op_bnf_o <= 1'b0;
  351.        execute_op_alu_o <= 1'b0;
  352.        execute_op_add_o <= 1'b0;
  353.        execute_op_mul_o <= 1'b0;
  354. --
  355. 2.8.3
Add Comment
Please, Sign In to add comment