Untitled

mail@pastecode.io avatar
unknown
verilog
7 months ago
5.3 kB
8
Indexable
Never
module lab3_3 (
input clk,
input rst,
input en,
output reg [15:0] led
);
// add your design here
wire myclk24, myclk25, myclk26;
reg [15:0] next_led;
reg [15:0] snake1;
reg [15:0] snake2;
reg [15:0] snake3;
reg [4:0] snake1_index;
reg [4:0] snake2_index_left;
reg [4:0] snake2_index_right;
reg [4:0] snake3_index_left;
reg [4:0] snake3_index_middle;
reg [4:0] snake3_index_right;
reg snake1_direction = 1'b1;
reg snake2_direction = 1'b1;
reg snake3_direction = 1'b0;
integer i;

clock_divider #(
    .n(24)
)   c1 (
    .clk(clk),
    .clk_div(myclk24)
);

clock_divider #(
    .n(25)
)   c2 (
    .clk(clk),
    .clk_div(myclk25)
);

clock_divider #(
    .n(26)
)   c3 (
    .clk(clk),
    .clk_div(myclk26)
);

always @(*) begin
    if(rst) begin
        led = 16'b1000110000000111;
    end
    else begin
        led = snake1 | snake2 | snake3;
    end
end

always @(*) begin
    for (i = 0; i < 16; i = i + 1) begin
        if (snake1[i] == 1) snake1_index = i;
        if (snake2[i] == 1) begin
            if (snake2[i+1] == 1) begin
                snake2_index_right = i;
                snake2_index_left = i+1;
            end
        end
        if (snake3[i] == 1) begin
            if(snake3[i+1] == 1 && snake3[i+2] == 1) begin
                snake3_index_right = i;
                snake3_index_middle = i+1;
                snake3_index_left = i+2;
            end
        end
    end
end

always @(posedge myclk24 or posedge rst) begin
    if (rst) begin
        snake1 = 16'b1000000000000000;
        snake1_direction = 1'b1;
    end
    else if (en) begin
        if (snake1_direction == 1'b0) begin
            if (snake1_index == 15) begin
                if (snake2_index_left == snake1_index - 1) begin
                    snake1 = snake1;
                end
                else begin
                    snake1 = snake1 >> 1;
                    snake1_direction = 1'b1;
                end
            end
            else snake1 = snake1 << 1;
        end
        else if (snake1_direction == 1'b1) begin
            if (snake1_index == 15) begin
                if (snake2_index_left == snake1_index - 1) begin
                    snake1 = snake1;
                end
                else begin
                    snake1 = snake1 >> 1;
                end
            end
            else begin
                if (snake2_index_left == snake1_index - 1) begin
                    snake1 = snake1 << 1;
                    snake1_direction = 1'b0;
                end
                else snake1 = snake1 >> 1;
            end
        end
        else snake1 = snake1;
    end
    else begin
        snake1 = snake1;
        snake1_direction = snake1_direction;
    end
end 

always @(posedge myclk25 or posedge rst) begin
    if (rst) begin
        snake2 = 16'b0000110000000000;
        snake2_direction = 1'b1;
    end
    else if (en) begin
        if (snake2_direction == 1'b0) begin
            if (snake1_index == snake2_index_left + 1 && snake3_index_left == snake2_index_right - 1) begin
                snake2 = snake2;
            end
            else if (snake1_index == snake2_index_left + 1 && snake3_index_left != snake2_index_right - 1) begin
                snake2 = snake2 >> 1;
                snake2_direction = 1'b1;
            end
            else snake2 = snake2 << 1;
        end
        else if (snake2_direction == 1'b1) begin
            if (snake1_index == snake2_index_left + 1 && snake3_index_left == snake2_index_right - 1) begin
                snake2 = snake2;
            end
            else if (snake1_index != snake2_index_left + 1 && snake3_index_left == snake2_index_right - 1) begin
                snake2 = snake2 << 1;
                snake2_direction = 1'b0;
            end
            else snake2 = snake2 >> 1;
        end 
        else snake2 = snake2;
    end
    else begin
        snake2 = snake2;
        snake2_direction = snake2_direction;
    end
end

always @(posedge myclk26 or posedge rst) begin
    if (rst) begin
        snake3 = 16'b0000000000000111;
        snake3_direction = 1'b0;
    end
    else if (en) begin
        if (snake3_direction == 1'b0) begin
            if (snake2_index_right == snake3_index_left + 1) begin
                if (snake3_index_right == 0) begin
                    snake3 = snake3;
                end
                else begin
                    snake3 = snake3 >> 1;
                    snake3_direction = 1'b1;
                end
            end
            else snake3 = snake3 << 1;
        end
        else if (snake3_direction == 1'b1) begin
            if (snake3_index_right == 0) begin
                if (snake2_index_right == snake3_index_left + 1) begin
                    snake3 = snake3;
                end
                else begin
                    snake3 = snake3 << 1;
                    snake3_direction = 1'b0;
                end
            end
            else snake3 = snake3 >> 1;
        end
        else snake3 = snake3;
    end
    else begin
        snake3 = snake3;
        snake3_direction = snake3_direction;
    end
end


endmodule

module clock_divider
#(parameter n = 25)
(input clk,
output clk_div);
// add your design here
reg [n-1:0] num;
wire [n-1:0] next_num;
always @(posedge clk) begin
    num <= next_num;
end
assign next_num = num + 1;
assign clk_div = num[n-1];
endmodule