module apb_cfg(
	//global signal
    input  apb_pclk,
	input  apb_prstn,

	//from apb master
	input        apb_psel,
	input        apb_penable,
	input        apb_pwrite,
	input [7:0]  apb_paddr,
	input [31:0] apb_wdata,

	//to apb master 
	output reg [31:0] apb_rdata,
	output            apb_pready,

	//cfg
	//mode ctrl
	output reg        mc_work_en,
	output reg [1:0]  axi_rw_priority,
	//global time
	output reg [7:0]  array_ras_cfg,
	output reg [7:0]  array_rp_cfg,
	output reg [7:0]  array_rc_cfg,
	//wr time
	output reg [7:0]  array_rcd_wr_cfg,
	output reg [7:0]  array_wr_cfg,
	//rd time
	output reg [7:0]  array_rcd_rd_cfg,
	output reg [7:0]  array_rtp_cfg,
	//ref ctrl
	output reg [25:0] array_ref_period0,
    output reg [25:0] array_ref_period1,
	output reg        array_ref_sel
);

wire apb_wr;
wire apb_rd;

assign apb_wr = apb_psel && apb_pwrite;
assign apb_rd = apb_psel && !apb_pwrite && apb_penable;//时序逻辑读

//apb_wr cfg
always @ (posedge apb_pclk or apb_prstn) begin
  if (!apb_prstn) begin
        mc_work_en        <= 1'b0;
		axi_rw_priority   <= 2'b01;
		array_ras_cfg     <= 8'd16;
		array_rp_cfg      <= 8'd6;
		array_rc_cfg      <= 8'd22;
		array_rcd_wr_cfg  <= 8'd7;
		array_wr_cfg      <= 8'd6;
		array_rcd_rd_cfg  <= 8'd7;
		array_rtp_cfg     <= 8'd3;
		array_ref_period0 <= 25'd24_000_000;
		array_ref_period1 <= 25'd24_000_000;
		array_ref_sel     <= 1'b0;
	end
	else begin
    if (apb_wr) begin
      case(apb_paddr)
        8'h00 : begin
           mc_work_en      <= apb_wdata[0];
					 axi_rw_priority <= apb_wdata[2:1];
				end
				8'h04 : begin
           array_ras_cfg <= apb_wdata[7:0];
					 array_rp_cfg  <= apb_wdata[15:8];
					 array_rc_cfg  <= apb_wdata[23:16];
				end
				8'h08 : begin
           array_rcd_wr_cfg <= apb_wdata[7:0];
					 array_wr_cfg     <= apb_wdata[15:8];
				end
				8'h0C : begin
           array_rcd_rd_cfg <= apb_wdata[7:0];
					 array_rtp_cfg    <= apb_wdata[15:8];
				end
				8'h10 : begin
           array_ref_period0 <= 25'd24_000_000;//60_000_000/2.5
				end
				8'h14 : begin
           array_ref_period1 <= 25'd24_000_000;//60_000_000/2.5
				end
				8'h18 : begin
           array_ref_sel <= 1'b0;
				end
				default : ;
	    endcase
		end
	end
end

//apb_rd
always @ (posedge apb_pclk or negedge apb_prstn) begin
  if (!apb_prstn) begin
    apb_rdata <= 32'b0;
	end
	else if (apb_rd) begin
    case (apb_paddr)
      8'h00 : begin
        apb_rdata <= {29'd0,axi_rw_priority,mc_work_en};
			end
			8'h04 : begin
        apb_rdata <= {8'd0,array_rc_cfg,array_rp_cfg,array_ras_cfg};
			end
      8'h08 : begin
        apb_rdata <= {16'd0,array_wr_cfg,array_rcd_wr_cfg};
			end
			8'h0C : begin
        apb_rdata <= {16'd0,array_rtp_cfg,array_rcd_rd_cfg};
			end
			8'h10 : begin
        apb_rdata <= {7'd0,array_ref_period0};
			end
			8'h14 : begin
        apb_rdata <= {7'd0,array_ref_period1};
			end
			8'h18 : begin
        apb_rdata <= {31'd0,array_ref_sel};
			end
			default : begin
        apb_rdata <= 32'b0;
			end
	  endcase
	end
end

assign apb_pready = 1'b1;

endmodule
