ms_dma.v
4.38 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
/************************************************************************\
* *
* Copyright (C) 1994, Silicon Graphics, Inc. *
* *
* These coded instructions, statements, and computer programs contain *
* unpublished proprietary information of Silicon Graphics, Inc., and *
* are protected by Federal copyright law. They may not be disclosed *
* to third parties or copied or duplicated in any form, in whole or *
* in part, without the prior written consent of Silicon Graphics, Inc. *
* *
\************************************************************************/
// $Id: ms_dma.v,v 1.6 2003/01/24 23:07:37 berndt Exp $
// cbus module for memspan dma requests, from jlsmith
// this module takes memspan rdram dma requests (c/z r/w)
// of up to 128 bytes (64 for writes) per request and acts
// as interface between io and memspan; the actual request
// line is wired directly (as are grant, start, done) and are
// not appearing here. this module includes tristate cbus i/f.
//
// a number of ports here are for diag use, as indicated; the
// widths and nature of these functions are still to be worked out.
//mod 11-15-94 read/write delay params updated (read_delay to be verified)
module ms_dma(clock, reset_l,
cbus_read_enable, cbus_write_enable, cbus_select, cbus_command,
read_grant, dma_read, dma_down, dma_address, dma_length,
read_request,
cbus_din, cbus_dout);
`include "ms.vh"
parameter READ_DELAY = 8'd2;
parameter WRITE_DELAY = -8'd2;
input clock; // system clock
input reset_l; // system reset_l
input cbus_read_enable; // enable cbus read mux
input cbus_write_enable; // enable cbus tristate drivers
input [1:0] cbus_select; // cbus data select
input [2:0] cbus_command; // cbus data type
input read_grant; // read response granted
input dma_read; // DMA read/write select
input dma_down; // DMA up/down select
input [DRAM_ADDRESS_SIZE-1:0] dma_address; // DMA slave address
input [DMA_LENGTH_SIZE-1:0] dma_length; // DMA length in words
output read_request; // dma read request cycle
input [31:0] cbus_din; // IO cbus
output [31:0] cbus_dout; // IO cbus
// input/output registers
reg read_request;
reg [2:0] cbus_command_reg;
reg [31:0] cbus_data_reg;
assign cbus_dout = cbus_write_enable ? cbus_data_reg : 32'b0;
always @(posedge clock) begin : cbus_block
reg [31:0] cbus_data_out;
case (cbus_select)
`CBUS_SEL_ADDR : cbus_data_out = dma_address;
`CBUS_SEL_LEN : case ({dma_down, dma_read})
2'b00 : cbus_data_out = {DMA_BLOCK, DMA_MASKED, DMA_UP,
DMA_NSEQ, `CBUS_DEV_SPAN, WRITE_DELAY, DMA_WRITE, dma_length};
2'b01 : cbus_data_out = {DMA_BLOCK, DMA_NON_MASKED, DMA_UP,
DMA_SEQ, `CBUS_DEV_SPAN, READ_DELAY, DMA_READ, dma_length};
2'b10 : cbus_data_out = {DMA_BLOCK, DMA_MASKED, DMA_DOWN,
DMA_NSEQ, `CBUS_DEV_SPAN, WRITE_DELAY, DMA_WRITE, dma_length};
2'b11 : cbus_data_out = {DMA_BLOCK, DMA_NON_MASKED, DMA_DOWN,
DMA_NSEQ, `CBUS_DEV_SPAN, READ_DELAY, DMA_READ, dma_length};
endcase
default : cbus_data_out = 'bx;
endcase
cbus_command_reg <= cbus_command;
cbus_data_reg <= cbus_read_enable ? cbus_din : cbus_data_out;
end
always @(posedge clock) begin
if (reset_l == 1'b0) begin
// resetable registers
read_request <= LOW;
end
else begin : main_block
reg next_read_request;
reg [BUS_ID_SIZE-1:0] next_id;
reg next_select;
reg next_read_command;
next_read_request = read_request;
next_id = cbus_data_reg >> BUS_ID_OFFSET;
next_select = next_id == `CBUS_SPAN;
next_read_command = cbus_command_reg == `CBUS_CMD_READ;
if (next_select) begin
if (next_read_command) begin
next_read_request = HIGH;
end
end
if (read_request && read_grant) begin
next_read_request = LOW;
end
read_request <= next_read_request;
end
end
endmodule