chipsalliance / yosys-f4pga-plugins

Plugins for Yosys developed as part of the F4PGA project.
https://f4pga.org
Apache License 2.0
83 stars 46 forks source link

duplicated ranges #521

Closed wsipak closed 10 months ago

wsipak commented 1 year ago
  1. This refactors add_multirange_attribute function.
    • The purpose of the function is to put data about multiranges in node->multirange_dimensions vector, and as it doesn't do anything related to node->attributes, the name could be considered misleading. I'm renaming it to set_multirange_dimensions and will be happy to consider other options, too.
    • There was a node duplicated and then both nodes were simplified. Now it's duplicated after simplification.
    • Ideally, the function should be called only once for each node. The function will now use both packed_ranges and unpacked_ranges in a single call, so that it's easier to forbid multiple calls of the function later on.
  2. The process_net function has a bug which causes ranges to be duplicated. With the current solution, the same range is added to a node here: https://github.com/chipsalliance/yosys-f4pga-plugins/blob/main/systemverilog-plugin/UhdmAst.cc#L501 and here: https://github.com/chipsalliance/yosys-f4pga-plugins/blob/main/systemverilog-plugin/UhdmAst.cc#L542 The solution is that during the part when process_* functions are executed, we should store information about the ranges in attributes, and later on in the simplification process replace the attributes with children nodes.

Input:

typedef logic [3:0][7:0] my_struct_packed_t;
module single_range_dot_access (
    input  my_struct_packed_t x,
    output my_struct_packed_t y
);
   assign y[2][1] = x[0][0];
endmodule : single_range_dot_access

Result without the changes:

    module single_range_dot_access(x, y);
      (* wiretype = "\my_struct_packed_t" *)
      input [1023:0] x;
      (* wiretype = "\my_struct_packed_t" *)
      output [1023:0] y;
      assign y[319:288] = x[31:0];
      /** AST_TYPEDEF **/
    endmodule

Result with the changes and Surelog 654c4fe230 and 7689edf1:

module single_range_dot_access(x, y);
  (* wiretype = "\my_struct_packed_t" *)
  input [31:0] x;
  (* wiretype = "\my_struct_packed_t" *)
  output [31:0] y;
  assign y[9:9] = x[0:0];
  /** AST_TYPEDEF **/
endmodule

The size of the input/output wires is fixed. With the current Surelog (bf13c83) it doesn't appear to break anything, and also fixes one FV test.

CI with the changes: https://github.com/antmicro/yosys-systemverilog/actions/runs/5309555386 https://github.com/antmicro/yosys-systemverilog/actions/runs/5290316276