Hyperflex® Architecture High-Performance Design Handbook

ID 683353
Date 12/06/2024
Public
Document Table of Contents

8.1. Appendix A: Parameterizable Pipeline Modules

The following examples show parameterizable pipeline modules in Verilog HDL, SystemVerilog, and VHDL. Use these code blocks at top-level I/Os and clock domain boundaries to change the latency of your circuit.

Parameterizable Hyper-Pipelining Verilog HDL Module

(* altera_attribute = "-name AUTO_SHIFT_REGISTER_RECOGNITION off" *) 
module hyperpipe 
#(parameter CYCLES = 1, parameter WIDTH = 1) 
(
    input clk,
    input [WIDTH-1:0] din,
    output [WIDTH-1:0] dout
);

    generate if (CYCLES==0) begin : GEN_COMB_INPUT
        assign dout = din;
    end 
    else begin : GEN_REG_INPUT  
        integer i;
        reg [WIDTH-1:0] R_data [CYCLES-1:0];
        
        always @ (posedge clk) 
        begin   
            R_data[0] <= din;      
            for(i = 1; i < CYCLES; i = i + 1) 
            	R_data[i] <= R_data[i-1];
        end
        assign dout = R_data[CYCLES-1];
    end
    endgenerate  

endmodule

Parameterizable Hyper-Pipelining Verilog HDL Instance

hyperpipe # (
        .CYCLES  ( ),
        .WIDTH   ( )
    ) hp (
        .clk      ( ),
        .din      ( ),
        .dout     ( )
    );

Parameterizable Hyper-Pipelining SystemVerilog Module

(* altera_attribute = "-name AUTO_SHIFT_REGISTER_RECOGNITION off" *) 
module hyperpipe 
    #(parameter int
        CYCLES = 1,
        PACKED_WIDTH = 1,
        UNPACKED_WIDTH = 1
) 
(
    input clk,
    input [PACKED_WIDTH-1:0] din [UNPACKED_WIDTH-1:0],
    output [PACKED_WIDTH-1:0] dout [UNPACKED_WIDTH-1:0]
);

    generate if (CYCLES == 0) begin : GEN_COMB_INPUT
        assign dout = din;
    end
    else begin : GEN_REG_INPUT
        integer i;
        reg [PACKED_WIDTH-1:0] R_data [CYCLES-1:0][UNPACKED_WIDTH-1:0];
          
        always_ff@(posedge clk) 
        begin
            R_data[0] <= din;
            for(i = 1; i < CYCLES; i = i + 1)
                R_data[i] <= R_data[i-1];
        end
        assign dout = R_data[CYCLES-1];
    end
    endgenerate

endmodule : hyperpipe

Parameterizable Hyper-Pipelining SystemVerilog Instance

// Quartus Prime SystemVerilog Template
//
// Hyper-Pipelining Module Instantiation

hyperpipe # (
        .CYCLES         ( ),
        .PACKED_WIDTH   ( ),
        .UNPACKED_WIDTH ( )
    ) hp (
        .clk      ( ),
        .din      ( ),
        .dout     ( )
    );

Parameterizable Hyper-Pipelining VHDL Entity

library IEEE;
use IEEE.std_logic_1164.all;
library altera;
use altera.altera_syn_attributes.all;

entity hyperpipe is
	generic (
 		CYCLES : integer := 1;
 		WIDTH : integer := 1
 	);
 	port (
 		clk : in std_logic;
 		din : in std_logic_vector (WIDTH - 1 downto 0);
 		dout : out std_logic_vector (WIDTH - 1 downto 0)
 	);
end entity;

architecture arch of hyperpipe is
 
	type hyperpipe_t is array(CYCLES-1 downto 0) of
 		std_logic_vector(WIDTH-1 downto 0);
	signal HR : hyperpipe_t;
	
	-- Prevent large hyperpipes from going into memory-based altshift_taps,
	-- since that won't take advantage of Hyper-Registers
 	attribute altera_attribute of HR :
 		signal is "-name AUTO_SHIFT_REGISTER_RECOGNITION off";
 
begin
 	wire : if CYCLES = 0 GENERATE
 		-- The 0 bit is just a pass-thru, when CYCLES is set to 0
 		dout <= din;
 	end generate wire;
 
 	hp : if CYCLES > 0 GENERATE
 		process (clk) begin
 			if (clk'event and clk = '1')then
 				HR <= HR(HR'high-1 downto 0) & din;
 			end if;
 		end process;
 		dout <= HR(HR'high);
 	end generate hp;

end arch;

Parameterizable Hyper-Pipelining VHDL Instance

-- Template Declaration
component hyperpipe
	generic (
		CYCLES : integer;
		WIDTH : integer
 	);
 	port (
 		clk : in std_logic;
 		din : in std_logic_vector(WIDTH - 1 downto 0);
 		dout : out std_logic_vector(WIDTH - 1 downto 0)
 	);
end component;

-- Instantiation Template:
	hp : hyperpipe
 		generic map (
 			CYCLES => ,
 			WIDTH => 
 		)
 		port map (
 			clk => ,
 			din => ,
 			dout =>
 		);