#Bus
- 여러 component들 간에 data를 전송(transfer)할 수 있도록 연결해주는 component
- 새로운 component들을 추가하기 쉬우며, 가격이 저렴
#Features
- 2개의 master와 5개의 slave를 가지고 있다.
- Address의 bandwidth는 8bits
- Data의 bandwidth는 8bits
#Arbitrator State Transition Diagram
module bus(
clk,
reset_n,
M0_req,
M0_address,
M0_wr,
M0_dout,
M0_grant,
M1_req,
M1_address,
M1_wr,
M1_dout,
M1_grant,
M_din,
S0_sel,
S1_sel,
S2_sel,
S3_sel,
S4_sel,
S_address,
S_wr,
S_din,
S0_dout,
S1_dout,
S2_dout,
S3_dout,
S4_dout
);
parameter wordSize = 8;
parameter addrSize = 8;
parameter RAM0_BASE_ADDRESS = 8'h00;
parameter RAM0_ADDRESS_SIZE = 8'h20;
parameter RAM1_BASE_ADDRESS = 8'h20;
parameter RAM1_ADDRESS_SIZE = 8'h20;
parameter RAM2_BASE_ADDRESS = 8'h40;
parameter RAM2_ADDRESS_SIZE = 8'h20;
parameter RAM3_BASE_ADDRESS = 8'h60;
parameter RAM3_ADDRESS_SIZE = 8'h20;
parameter DMAC_BASE_ADDRESS = 8'h80;
parameter DMAC_ADDRESS_SIZE = 8'h10;
input clk;
input reset_n;
//Master interface
input M0_req;
input [addrSize-1:0] M0_address;
input M0_wr;
input [wordSize-1:0] M0_dout;
output M0_grant;
input M1_req;
input [addrSize-1:0] M1_address;
input M1_wr;
input [wordSize-1:0] M1_dout;
output M1_grant;
output [wordSize-1:0] M_din;
//Slave interface
output S0_sel;
output S1_sel;
output S2_sel;
output S3_sel;
output S4_sel;
output [addrSize-1:0] S_address;
output S_wr;
output [wordSize-1:0] S_din;
input [wordSize-1:0] S0_dout;
input [wordSize-1:0] S1_dout;
input [wordSize-1:0] S2_dout;
input [wordSize-1:0] S3_dout;
input [wordSize-1:0] S4_dout;
reg [wordSize-1:0] M_din;
reg S0_sel;
reg S1_sel;
reg S2_sel;
reg S3_sel;
reg S4_sel;
reg [addrSize-1:0] S_address;
reg S_wr;
reg [wordSize-1:0] S_din;
arbitrator U0_arbitrator(.clk(clk), .reset_n(reset_n), .M0_req(M0_req), .M1_req(M1_req), .M0_grant(M0_grant), .M1_grant(M1_grant));
always @(M0_grant, M1_grant, M0_address, M1_address, M0_wr, M1_wr, M0_dout, M1_dout)
begin
if(M0_grant == 1)begin
S_address = M0_address;
S_wr = M0_wr;
S_din = M0_dout;
end
else if(M1_grant == 1)begin
S_address = M1_address;
S_wr = M1_wr;
S_din = M1_dout;
end
else begin
S_address = {addrSize{1'bx}};
S_wr = 1'bx;
S_din = {wordSize{1'bx}};
end
end
always @(S_address)
begin
if((S_address >= RAM0_BASE_ADDRESS) && (S_address < RAM0_BASE_ADDRESS+RAM0_ADDRESS_SIZE))
{S0_sel, S1_sel, S2_sel, S3_sel, S4_sel} = 5'b10000;
else if((S_address >= RAM1_BASE_ADDRESS) && (S_address < RAM1_BASE_ADDRESS+RAM1_ADDRESS_SIZE))
{S0_sel, S1_sel, S2_sel, S3_sel, S4_sel} = 5'b01000;
else if((S_address >= RAM2_BASE_ADDRESS) && (S_address < RAM2_BASE_ADDRESS+RAM2_ADDRESS_SIZE))
{S0_sel, S1_sel, S2_sel, S3_sel, S4_sel} = 5'b00100;
else if((S_address >= RAM3_BASE_ADDRESS) && (S_address < RAM3_BASE_ADDRESS+RAM3_ADDRESS_SIZE))
{S0_sel, S1_sel, S2_sel, S3_sel, S4_sel} = 5'b00010;
else if((S_address >= DMAC_BASE_ADDRESS) && (S_address < DMAC_BASE_ADDRESS+DMAC_ADDRESS_SIZE))
{S0_sel, S1_sel, S2_sel, S3_sel, S4_sel} = 5'b00001;
else
{S0_sel, S1_sel, S2_sel, S3_sel, S4_sel} = 5'b00000;
end
reg prev_S0_sel, prev_S1_sel, prev_S2_sel, prev_S3_sel, prev_S4_sel;
always@(posedge clk or negedge reset_n)
begin
if(reset_n == 0) {prev_S0_sel, prev_S1_sel, prev_S2_sel, prev_S3_sel, prev_S4_sel} = 5'b00000;
else if(reset_n == 1) {prev_S0_sel, prev_S1_sel, prev_S2_sel, prev_S3_sel, prev_S4_sel} = {S0_sel, S1_sel, S2_sel, S3_sel, S4_sel};
else {prev_S0_sel, prev_S1_sel, prev_S2_sel, prev_S3_sel, prev_S4_sel} = 5'bxxxxx;
end
always @(prev_S0_sel, prev_S1_sel, prev_S2_sel, prev_S3_sel, prev_S4_sel, S0_dout, S1_dout, S2_dout, S3_dout, S4_dout)
begin
if({prev_S0_sel, prev_S1_sel, prev_S2_sel, prev_S3_sel, prev_S4_sel} == 5'b00000) M_din = {wordSize{1'b0}};
else if({prev_S0_sel, prev_S1_sel, prev_S2_sel, prev_S3_sel, prev_S4_sel} == 5'b10000) M_din = S0_dout;
else if({prev_S0_sel, prev_S1_sel, prev_S2_sel, prev_S3_sel, prev_S4_sel} == 5'b01000) M_din = S1_dout;
else if({prev_S0_sel, prev_S1_sel, prev_S2_sel, prev_S3_sel, prev_S4_sel} == 5'b00100) M_din = S2_dout;
else if({prev_S0_sel, prev_S1_sel, prev_S2_sel, prev_S3_sel, prev_S4_sel} == 5'b00010) M_din = S3_dout;
else if({prev_S0_sel, prev_S1_sel, prev_S2_sel, prev_S3_sel, prev_S4_sel} == 5'b00001) M_din = S4_dout;
else M_din = {wordSize{1'bx}};
end
endmodule
module arbitrator(clk, reset_n, M0_req, M1_req, M0_grant, M1_grant);
input clk;
input reset_n;
input M0_req;
input M1_req;
output M0_grant;
output M1_grant;
parameter M0_GRANT_STATE = 1'b0;
parameter M1_GRANT_STATE = 1'b1;
reg state;
reg next_state;
reg M0_grant;
reg M1_grant;
always @(posedge clk or negedge reset_n)
begin
if(reset_n == 0) state = M0_GRANT_STATE;
else if(reset_n == 1) state = next_state;
else state = 1'bx;
end
always @(M0_req, M1_req, state)
begin
case(state)
M0_GRANT_STATE:
begin
if((M0_req == 0) && (M1_req == 0)) next_state = M0_GRANT_STATE;
else if((M0_req == 0) && (M1_req == 1)) next_state = M1_GRANT_STATE;
else if((M0_req == 1) && (M1_req == 0)) next_state = M0_GRANT_STATE;
else if((M0_req == 1) && (M1_req == 1)) next_state = M0_GRANT_STATE;
else next_state = 1'bx;
end
M1_GRANT_STATE:
begin
if(M1_req == 0) next_state = M0_GRANT_STATE;
else if(M1_req == 1) next_state = M1_GRANT_STATE;
else next_state = 1'bx;
end
default: next_state = 1'bx;
endcase
end
always @(state)
begin
case(state)
M0_GRANT_STATE: {M0_grant, M1_grant} = 2'b10;
M1_GRANT_STATE: {M0_grant, M1_grant} = 2'b01;
default: {M0_grant, M1_grant} = 2'bxx;
endcase
end
endmodule
'Computer > Computer Structure' 카테고리의 다른 글
DMAC - FIFO (0) | 2013.05.26 |
---|---|
DMAC - Register File (0) | 2013.05.26 |
DMAC - Memory (0) | 2013.05.26 |
Direct Memory Access Control(DMAC) (0) | 2013.05.26 |
I/O Mapped I/O vs Memory Mapped I/O (0) | 2013.05.20 |