4
\$\begingroup\$

There are both a simple byte endian (little and big) order swapper and its testbench. A data stream inputs to the module and is converted to the other endianness by computational logic.

byte_order_swap.v

`timescale 1ns / 1ps
module byte_order_swap #
(
 parameter integer DATA_WIDTH = 32
)
(
 input wire [DATA_WIDTH - 1 : 0] data_i,
 input wire [DATA_WIDTH - 1 : 0] data_o
);
 localparam integer DATA_BYTE_NUMBER = DATA_WIDTH / 8;
 localparam integer DEC_DATA_WIDTH = DATA_WIDTH - 1;
 generate
 genvar i;
 if (0 == (DATA_WIDTH % 4)) begin
 for(i = 0; i < DATA_BYTE_NUMBER; i = i + 1) begin
 assign data_o[(i * 8) +: 8] = data_i[(DEC_DATA_WIDTH - i * 8) -: 8];
 end
 end
 else begin
 assign data_o = {DATA_WIDTH{1'h0}};
 end
 endgenerate
endmodule

byte_order_swap_tb.v

`timescale 1ns / 1ps
module byte_order_swap_tb;
 localparam integer DATA_WIDTH = 32;
 localparam integer CLOCK_PERIOD = 100;
 localparam integer ITERATION_NUMBER = 1000;
 localparam [DATA_WIDTH - 1 : 0] COUNTER_START_VALUE = 32'hAABB1122;
 
 wire [DATA_WIDTH - 1 : 0] counter_swap_value;
 
 reg clk;
 reg [DATA_WIDTH - 1 : 0] counter_dir_value;
 byte_order_swap #
 (
 .DATA_WIDTH (DATA_WIDTH)
 )
 byte_order_swap_dut
 (
 .data_i (counter_dir_value),
 .data_o (counter_swap_value)
 );
 
 initial begin
 clk = 1'h0;
 
 forever begin
 #( CLOCK_PERIOD / 2 ) clk = !clk;
 end 
 end
 
 initial begin
 counter_dir_value <= COUNTER_START_VALUE;
 
 repeat(ITERATION_NUMBER) begin
 @(posedge clk);
 counter_dir_value <= counter_dir_value + 1'h1;
 end
 end
 
 task check_swap;
 begin
 repeat(ITERATION_NUMBER) begin
 @(posedge clk);
 $display("A direction value: %h -> the swap value: %h",counter_dir_value, counter_swap_value, $time);
 end
 end
 endtask
 
 initial begin
 
 check_swap;
 
 $stop();
 end
endmodule
asked Mar 4, 2021 at 12:50
\$\endgroup\$
0

1 Answer 1

1
\$\begingroup\$

The code makes good use of parameters. However, I see a potential problem.

 if (0 == (DATA_WIDTH % 4)) begin

That code seems to imply that any multiple of 4 is supported. But, if I try DATA_WIDTH = 20, then I see z values in the output. Perhaps you should restrict values to be a multiple of 8 instead:

 if (0 == (DATA_WIDTH % 8)) begin

Conventionally, the word "check" means that you will compare an actual value to an expected value and report an error if the two do not match. The check_swap task simply displays the values. If that is all you are looking to do, then I suggest renaming the task as display_swap or monitor_swap.

However, you could add code to the testbench to do a comparison. If your tool suite supports SystemVerilog features, then the following additions/modifications would provide automatic checking:

wire [DATA_WIDTH - 1 : 0] data_o;
generate
 if (0 == (DATA_WIDTH % 8)) begin
 assign data_o = {<< 8{counter_dir_value}};
 end else begin
 assign data_o = '0;
 end
endgenerate
task check_swap;
 repeat(ITERATION_NUMBER) begin
 @(posedge clk);
 $display("A direction value: %h -> the swap value: %h", counter_dir_value, counter_swap_value, $time);
 if (data_o !== counter_swap_value) begin
 $display("ERROR: data miscompare", $time);
 end
 end
endtask

To create the expected data (data_o), I copied the generate code from the design and made some simplifications. The {<< 8{counter_dir_value}} syntax is another way to perform the byte swap. Refer to IEEE Std 1800-2017, section 11.4.14 Streaming operators (pack/unpack). The '0 syntax is a simplified way of assigning all bits to 0, equivalent to what you have already. If you plan to synthesize the design, and your tool chain supports this syntax, you could even use this code in your design module.

A minor note: with that type of task body, the begin/end keywords are now optional.

answered Mar 4, 2021 at 22:18
\$\endgroup\$
1
  • 1
    \$\begingroup\$ Thank you for the reply. Your criticism and rectification of my code are very important for me. Sorry for the late answer. \$\endgroup\$ Commented Mar 18, 2021 at 7:15

Your Answer

Draft saved
Draft discarded

Sign up or log in

Sign up using Google
Sign up using Email and Password

Post as a guest

Required, but never shown

Post as a guest

Required, but never shown

By clicking "Post Your Answer", you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.