//*************************************************************************
//   > ÎÄ¼þÃû: regfile_display.v
//   > ÃèÊö  £º¼Ä´æÆ÷¶ÑÏÔÊ¾Ä£¿é£¬µ÷ÓÃFPGA°åÉÏµÄIO½Ó¿ÚºÍ´¥ÃþÆÁ
//   > ×÷Õß  : LOONGSON
//   > ÈÕÆÚ  : 2016-04-14
//*************************************************************************
module regfile_display(
    //Ê±ÖÓÓë¸´Î»ÐÅºÅ
    input clk,
    input resetn,    //ºó×º"n"´ú±íµÍµçÆ½ÓÐÐ§

    //²¦Âë¿ª¹Ø£¬ÓÃÓÚ²úÉúÐ´Ê¹ÄÜºÍÑ¡ÔñÊäÈëÊý
    input wen,
    input [1:0] input_sel,

    //ledµÆ£¬ÓÃÓÚÖ¸Ê¾Ð´Ê¹ÄÜÐÅºÅ£¬ºÍÕýÔÚÊäÈëÊ²Ã´Êý¾Ý
    output led_wen,
    output led_waddr,    //Ö¸Ê¾ÊäÈëÐ´µØÖ·
    output led_wdata,    //Ö¸Ê¾ÊäÈëÐ´Êý¾Ý
    output led_raddr1,   //Ö¸Ê¾ÊäÈë¶ÁµØÖ·1
    output led_raddr2,   //Ö¸Ê¾ÊäÈë¶ÁµØÖ·2

    //´¥ÃþÆÁÏà¹Ø½Ó¿Ú£¬²»ÐèÒª¸ü¸Ä
    output lcd_rst,
    output lcd_cs,
    output lcd_rs,
    output lcd_wr,
    output lcd_rd,
    inout[15:0] lcd_data_io,
    output lcd_bl_ctr,
    inout ct_int,
    inout ct_sda,
    output ct_scl,
    output ct_rstn
);
//-----{LEDÏÔÊ¾}begin
    assign led_wen    = wen;
    assign led_raddr1 = (input_sel==2'd0);
    assign led_raddr2 = (input_sel==2'd1);
    assign led_waddr  = (input_sel==2'd2);
    assign led_wdata  = (input_sel==2'd3);
//-----{LEDÏÔÊ¾}end

//-----{µ÷ÓÃ¼Ä´æÆ÷¶ÑÄ£¿é}begin
    //¼Ä´æÆ÷¶Ñ¶àÔö¼ÓÒ»¸ö¶Á¶Ë¿Ú£¬ÓÃÓÚÔÚ´¥ÃþÆÁÉÏÏÔÊ¾32¸ö¼Ä´æÆ÷Öµ
    wire [31:0] test_data;  
    wire [4 :0] test_addr;

    reg  [4 :0] raddr1;
    reg  [4 :0] raddr2;
    reg  [4 :0] waddr;
    reg  [31:0] wdata;
    wire [31:0] rdata1;
    wire [31:0] rdata2;
    regfile rf_module(
        .clk   (clk   ),
        .wen   (wen   ),
        .raddr1(raddr1),
        .raddr2(raddr2),
        .waddr (waddr ),
        .wdata (wdata ),
        .rdata1(rdata1),
        .rdata2(rdata2),
        .test_addr(test_addr),
        .test_data(test_data)
    );
//-----{µ÷ÓÃ¼Ä´æÆ÷¶ÑÄ£¿é}end

//---------------------{µ÷ÓÃ´¥ÃþÆÁÄ£¿é}begin--------------------//
//-----{ÊµÀý»¯´¥ÃþÆÁ}begin
//´ËÐ¡½Ú²»ÐèÒª¸ü¸Ä
    reg         display_valid;
    reg  [39:0] display_name;
    reg  [31:0] display_value;
    wire [5 :0] display_number;
    wire        input_valid;
    wire [31:0] input_value;

    lcd_module lcd_module(
        .clk            (clk           ),   //10Mhz
        .resetn         (resetn        ),

        //µ÷ÓÃ´¥ÃþÆÁµÄ½Ó¿Ú
        .display_valid  (display_valid ),
        .display_name   (display_name  ),
        .display_value  (display_value ),
        .display_number (display_number),
        .input_valid    (input_valid   ),
        .input_value    (input_value   ),

        //lcd´¥ÃþÆÁÏà¹Ø½Ó¿Ú£¬²»ÐèÒª¸ü¸Ä
        .lcd_rst        (lcd_rst       ),
        .lcd_cs         (lcd_cs        ),
        .lcd_rs         (lcd_rs        ),
        .lcd_wr         (lcd_wr        ),
        .lcd_rd         (lcd_rd        ),
        .lcd_data_io    (lcd_data_io   ),
        .lcd_bl_ctr     (lcd_bl_ctr    ),
        .ct_int         (ct_int        ),
        .ct_sda         (ct_sda        ),
        .ct_scl         (ct_scl        ),
        .ct_rstn        (ct_rstn       )
    ); 
//-----{ÊµÀý»¯´¥ÃþÆÁ}end

//-----{´Ó´¥ÃþÆÁ»ñÈ¡ÊäÈë}begin
//¸ù¾ÝÊµ¼ÊÐèÒªÊäÈëµÄÊýÐÞ¸Ä´ËÐ¡½Ú£¬
//½¨Òé¶ÔÃ¿Ò»¸öÊýµÄÊäÈë£¬±àÐ´µ¥¶ÀÒ»¸öalways¿é
    //32¸ö¼Ä´æÆ÷ÏÔÊ¾ÔÚ7~38ºÅµÄÏÔÊ¾¿é£¬¹Ê¶ÁµØÖ·Îª£¨display_number-1£©
    assign test_addr = display_number-5'd7; 
    //µ±input_selÎª2'b00Ê±£¬±íÊ¾ÊäÈëÊýÎª¶ÁµØÖ·1£¬¼´raddr1
    always @(posedge clk)
    begin
        if (!resetn)
        begin
            raddr1 <= 5'd0;
        end
        else if (input_valid &&  input_sel==2'd0)
        begin
            raddr1 <= input_value[4:0];
        end
    end
    
    //µ±input_selÎª2'b01Ê±£¬±íÊ¾ÊäÈëÊýÎª¶ÁµØÖ·2£¬¼´raddr2
    always @(posedge clk)
    begin
        if (!resetn)
        begin
            raddr2 <= 5'd0;
        end
        else if (input_valid && input_sel==2'd1)
        begin
            raddr2 <= input_value[4:0];
        end
    end
    
    //µ±input_selÎª2'b10Ê±£¬±íÊ¾ÊäÈëÊýÎªÐ´µØÖ·£¬¼´waddr
    always @(posedge clk)
    begin
        if (!resetn)
        begin
            waddr  <= 5'd0;
        end
        else if (input_valid && input_sel==2'd2)
        begin
            waddr  <= input_value[4:0];
        end
    end
    
    //µ±input_selÎª2'b11Ê±£¬±íÊ¾ÊäÈëÊýÎªÐ´Êý¾Ý£¬¼´wdata
    always @(posedge clk)
    begin
        if (!resetn)
        begin
            wdata  <= 32'd0;
        end
        else if (input_valid && input_sel==2'd3)
        begin
            wdata  <= input_value;     
        end
    end
//-----{´Ó´¥ÃþÆÁ»ñÈ¡ÊäÈë}end

//-----{Êä³öµ½´¥ÃþÆÁÏÔÊ¾}begin
//¸ù¾ÝÐèÒªÏÔÊ¾µÄÊýÐÞ¸Ä´ËÐ¡½Ú£¬
//´¥ÃþÆÁÉÏ¹²ÓÐ44¿éÏÔÊ¾ÇøÓò£¬¿ÉÏÔÊ¾44×é32Î»Êý¾Ý
//44¿éÏÔÊ¾ÇøÓò´Ó1¿ªÊ¼±àºÅ£¬±àºÅÎª1~44£¬
    always @(posedge clk)
    begin
        if (display_number >6'd6 && display_number <6'd39 )
        begin //¿éºÅ7~38ÏÔÊ¾32¸öÍ¨ÓÃ¼Ä´æÆ÷µÄÖµ
            display_valid <= 1'b1;
            display_name[39:16] <= "REG";
            display_name[15: 8] <= {4'b0011,3'b000,test_addr[4]};
            display_name[7 : 0] <= {4'b0011,test_addr[3:0]}; 
            display_value       <= test_data;
          end
        else
        begin
            case(display_number)
                6'd1 : //ÏÔÊ¾¶Á¶Ë¿Ú1µÄµØÖ·
                begin
                    display_valid <= 1'b1;
                    display_name  <= "RADD1";
                    display_value <= raddr1;
                end
                6'd2 : //ÏÔÊ¾¶Á¶Ë¿Ú1¶Á³öµÄÊý¾Ý
                begin
                    display_valid <= 1'b1;
                    display_name  <= "RDAT1";
                    display_value <= rdata1;
                end
                6'd3 : //ÏÔÊ¾¶Á¶Ë¿Ú2µÄµØÖ·
                begin
                    display_valid <= 1'b1;
                    display_name  <= "RADD2";
                    display_value <= raddr2;
                end
                6'd4 : //ÏÔÊ¾¶Á¶Ë¿Ú2¶Á³öµÄÊý¾Ý
                begin
                    display_valid <= 1'b1;
                    display_name  <= "RDAT2";
                    display_value <= rdata2;
                end
                6'd5 : //ÏÔÊ¾Ð´¶Ë¿ÚµÄµØÖ·
                begin
                    display_valid <= 1'b1;
                    display_name  <= "WADDR";
                    display_value <= waddr;
                end
                6'd6 : //ÏÔÊ¾Ð´¶Ë¿ÚÐ´ÈëµÄÊý¾Ý
                begin
                    display_valid <= 1'b1;
                    display_name  <= "WDATA";
                    display_value <= wdata;
                end
                default :
                begin
                    display_valid <= 1'b0;
                    display_name  <= 40'd0;
                    display_value <= 32'd0;
                end
            endcase
        end
    end
//-----{Êä³öµ½´¥ÃþÆÁÏÔÊ¾}end
//----------------------{µ÷ÓÃ´¥ÃþÆÁÄ£¿é}end---------------------//
endmodule
