OpenCores
URL https://opencores.org/ocsvn/usb_ft232h_avalon-mm_interface/usb_ft232h_avalon-mm_interface/trunk

Subversion Repositories usb_ft232h_avalon-mm_interface

[/] [usb_ft232h_avalon-mm_interface/] [trunk/] [hw/] [usb_ft232h.sv] - Blame information for rev 5

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 2 melman701
/*
2
 *      Если error срабатывает на последнем байте пакета, то он не будет отправлен, пока
3
 * не придет следующий пакет
4
 */
5
 
6
 
7
module usb_ft232h (
8
        //Avalon-MM Slave
9 5 melman701
        clk_i,
10
        reset_i,
11
        address_i,
12
        read_i,
13
        readdata_o,
14
        write_i,
15
        writedata_i,
16 2 melman701
 
17
        //FT232H
18 5 melman701
        usb_clk_i,
19
        usb_data_io,
20
        usb_rxf_n_i,
21
        usb_txe_n_i,
22
        usb_rd_n_o,
23
        usb_wr_n_o,
24
        usb_oe_n_o
25 2 melman701
);
26
 
27 5 melman701
parameter TX_FIFO_DEPTH  = 512;
28
parameter TX_FIFO_WIDTHU = 9;
29
parameter RX_FIFO_DEPTH  = 512;
30
parameter RX_FIFO_WIDTHU = 9;
31 2 melman701
 
32 5 melman701
localparam WRDATA_ADDR    = 4'd0;
33
localparam RDDATA_ADDR    = 4'd1;
34
localparam TXSTATUSL_ADDR = 4'd2;
35
localparam TXSTATUSH_ADDR = 4'd3;
36
localparam RXSTATUSL_ADDR = 4'd4;
37
localparam RXSTATUSH_ADDR = 4'd5;
38 2 melman701
 
39
 
40 5 melman701
input  logic       clk_i;
41
input  logic       reset_i;
42
input  logic [3:0] address_i;
43
input  logic       read_i;
44
output logic [7:0] readdata_o;
45
input  logic       write_i;
46
input  logic [7:0] writedata_i;
47 2 melman701
 
48 5 melman701
input  logic       usb_clk_i;
49
inout  logic [7:0] usb_data_io;
50
input  logic       usb_rxf_n_i;
51
input  logic       usb_txe_n_i;
52
output logic       usb_rd_n_o;
53
output logic       usb_wr_n_o;
54
output logic       usb_oe_n_o;
55 2 melman701
 
56
 
57
 
58 5 melman701
reg                        error;
59
reg                        rxerror;
60
reg   [7:0]                rxerrdata;
61
logic [15:0]               txstatus;
62
logic [15:0]               rxstatus;
63 2 melman701
 
64 5 melman701
reg                        read_pipe;
65
reg                        read_pipe2;
66 2 melman701
 
67 5 melman701
reg                        adr_data;
68
reg                        adr_txsl;
69
reg                        adr_txsh;
70
reg                        adr_rxsl;
71
reg                        adr_rxsh;
72 2 melman701
 
73
 
74 5 melman701
logic [7:0]                txf_wrdata;
75
logic                      txf_wrclk;
76
logic                      txf_wrreq;
77
logic                      txf_wrfull;
78
logic [TX_FIFO_WIDTHU-1:0] txf_wrusedw;
79
logic                      txf_rdclk;
80
logic                      txf_rdreq;
81
logic [7:0]                txf_rddata;
82
logic                      txf_rdempty;
83 2 melman701
 
84 5 melman701
logic [7:0]                rxf_wrdata;
85
logic                      rxf_wrclk;
86
logic                      rxf_wrreq;
87
logic                      rxf_wrfull;
88
logic [RX_FIFO_WIDTHU-1:0] rxf_rdusedw;
89
logic                      rxf_rdclk;
90
logic                      rxf_rdreq;
91
logic [7:0]                rxf_rddata;
92
logic                      rxf_rdempty;
93
logic                      rxf_rdfull;
94 2 melman701
 
95
 
96 5 melman701
assign usb_data_io = ( usb_oe_n_o ) ? ( txf_rddata ) : ( {8{1'bZ}} );
97 2 melman701
 
98 5 melman701
assign rxf_wrclk   = ~usb_clk_i;
99
assign txf_rdclk   = usb_clk_i;
100
assign rxf_rdclk   = clk_i;
101
assign txf_wrclk   = ~clk_i;
102 2 melman701
 
103 5 melman701
assign txstatus[15]                  = ~txf_wrfull; //can write
104
assign txstatus[14:TX_FIFO_WIDTHU+1] = 0;
105
assign txstatus[TX_FIFO_WIDTHU]      = txf_wrfull;
106
assign txstatus[TX_FIFO_WIDTHU-1:0]  = ( txf_wrfull ? {TX_FIFO_WIDTHU{1'b0}} : txf_wrusedw );
107 2 melman701
 
108 5 melman701
assign rxstatus[15]                  = ~rxf_rdempty; //can read
109
assign rxstatus[14:RX_FIFO_WIDTHU+1] = 0;
110
assign rxstatus[RX_FIFO_WIDTHU]      = rxf_rdfull;
111
assign rxstatus[RX_FIFO_WIDTHU-1:0]  = ( rxf_rdempty ? {RX_FIFO_WIDTHU{1'b0}} : rxf_rdusedw );
112 2 melman701
 
113
 
114
dcfifo  txfifo (
115 5 melman701
                                .aclr      ( reset_i ),
116
                                .data      ( txf_wrdata ),
117
                                .rdclk     ( txf_rdclk ),
118
                                .rdreq     ( txf_rdreq ),
119
                                .wrclk     ( txf_wrclk ),
120
                                .wrreq     ( txf_wrreq ),
121
                                .q         ( txf_rddata ),
122
                                .rdempty   ( txf_rdempty ),
123
                                .wrfull    ( txf_wrfull ),
124
                                .wrusedw   ( txf_wrusedw ),
125 2 melman701
                                .eccstatus (),
126 5 melman701
                                .rdfull    (),
127
                                .rdusedw   (),
128
                                .wrempty   ());
129 2 melman701
        defparam
130
                txfifo.intended_device_family = "Cyclone IV E",
131 5 melman701
                txfifo.lpm_numwords = TX_FIFO_DEPTH,
132 2 melman701
                txfifo.lpm_showahead = "OFF",
133
                txfifo.lpm_type = "dcfifo",
134
                txfifo.lpm_width = 8,
135 5 melman701
                txfifo.lpm_widthu = TX_FIFO_WIDTHU,
136 2 melman701
                txfifo.overflow_checking = "ON",
137 5 melman701
                txfifo.rdsync_delaypipe = 11,
138
                txfifo.read_aclr_synch = "ON",
139 2 melman701
                txfifo.underflow_checking = "ON",
140
                txfifo.use_eab = "ON",
141 5 melman701
                txfifo.write_aclr_synch = "ON",
142
                txfifo.wrsync_delaypipe = 11;
143
 
144 2 melman701
 
145
dcfifo  rxfifo (
146 5 melman701
                                .aclr      ( reset_i ),
147
                                .data      ( rxf_wrdata ),
148
                                .rdclk     ( rxf_rdclk ),
149
                                .rdreq     ( rxf_rdreq ),
150
                                .wrclk     ( rxf_wrclk ),
151
                                .wrreq     ( rxf_wrreq ),
152
                                .q         ( rxf_rddata ),
153
                                .rdempty   ( rxf_rdempty ),
154
                                .wrfull    ( rxf_wrfull ),
155
                                .wrusedw   (),
156 2 melman701
                                .eccstatus (),
157 5 melman701
                                .rdfull    ( rxf_rdfull ),
158
                                .rdusedw   ( rxf_rdusedw ),
159
                                .wrempty   ());
160 2 melman701
        defparam
161
                rxfifo.intended_device_family = "Cyclone IV E",
162 5 melman701
                rxfifo.lpm_numwords = RX_FIFO_DEPTH,
163 2 melman701
                rxfifo.lpm_showahead = "OFF",
164
                rxfifo.lpm_type = "dcfifo",
165
                rxfifo.lpm_width = 8,
166 5 melman701
                rxfifo.lpm_widthu = RX_FIFO_WIDTHU,
167 2 melman701
                rxfifo.overflow_checking = "ON",
168 5 melman701
                rxfifo.rdsync_delaypipe = 11,
169
                rxfifo.read_aclr_synch = "ON",
170 2 melman701
                rxfifo.underflow_checking = "ON",
171
                rxfifo.use_eab = "ON",
172 5 melman701
                rxfifo.write_aclr_synch = "ON",
173
                rxfifo.wrsync_delaypipe = 11;
174 2 melman701
 
175
 
176 5 melman701
 
177
/* read usb data to rx fifo */
178
always_ff @( negedge rxf_wrclk or posedge reset_i )
179 2 melman701
begin
180 5 melman701
  if( reset_i )
181
    begin
182
           rxf_wrreq <= 1'b0;
183
                rxf_wrdata <= 8'b0;
184
                rxerror <= 1'b0;
185
                rxerrdata <= 8'b0;
186
         end
187
  else
188
    begin
189
           if( ~usb_rd_n_o & rxf_wrfull )
190
                  begin
191
                    rxerror <= 1'b1;
192
                         rxerrdata <= usb_data_io;
193
                  end
194
 
195
           if( ~rxf_wrfull & ((~usb_rd_n_o & ~usb_rxf_n_i) | rxerror) )
196
                  begin
197
                    rxf_wrreq <= 1'b1;
198
                         if( rxerror )
199
                           begin
200
                             rxerror <= 1'b0;
201
                                  rxf_wrdata <= rxerrdata;
202
                                end
203
                         else
204
                           rxf_wrdata <= usb_data_io;
205
                  end
206
                else
207
                  begin
208
                    rxf_wrreq <= 1'b0;
209
                  end
210
         end
211 2 melman701
end
212 5 melman701
always_ff @( posedge usb_clk_i or posedge reset_i )
213 2 melman701
begin
214 5 melman701
  if( reset_i )
215
    begin
216
           usb_oe_n_o <= 1'b1;
217
                usb_rd_n_o <= 1'b1;
218
         end
219
  else
220
    begin
221
           if( ~usb_rxf_n_i & ~rxf_wrfull & ( usb_txe_n_i | ( ~txf_rdreq & ~error )) & ~rxerror )
222
                  begin
223
                    usb_oe_n_o <= 1'b0;
224
                         if( ~usb_oe_n_o )
225
                      usb_rd_n_o <= 1'b0;
226
                  end
227
                else
228
                  begin
229
                    usb_oe_n_o <= 1'b1;
230
                         usb_rd_n_o <= 1'b1;
231
                  end
232
         end
233 2 melman701
end
234
 
235 5 melman701
/*---------------------------------*/
236
 
237
/* write tx fifo data to usb */
238
always_ff @( negedge txf_rdclk or posedge reset_i )
239 2 melman701
begin
240 5 melman701
  if( reset_i )
241
    begin
242
           txf_rdreq <= 1'b0;
243
         end
244
  else
245
    begin
246
           if( ~usb_txe_n_i & ~txf_rdempty & ~error & usb_oe_n_o )
247
                  begin
248
                    txf_rdreq <= 1'b1;
249
                  end
250 2 melman701
                else
251 5 melman701
                  txf_rdreq <= 1'b0;
252
         end
253 2 melman701
end
254 5 melman701
always_ff @( posedge usb_clk_i or posedge reset_i )
255
begin
256
  if( reset_i )
257
    begin
258
                usb_wr_n_o <= 1'b1;
259
                error      <= 1'b0;
260
         end
261
  else
262
    begin
263
           if( usb_txe_n_i & ~usb_wr_n_o )
264
                  begin
265
                    error <= 1'b1;
266
                  end
267
 
268
           if( ~usb_txe_n_i & ( txf_rdreq | error ) & usb_oe_n_o )
269
                  begin
270
                    usb_wr_n_o <= 1'b0;
271
                         if( error )
272
                           error <= 1'b0;
273
                  end
274
                else
275
                  begin
276
                    usb_wr_n_o <= 1'b1;
277
                  end
278
    end
279
end
280
/*-----------------------------*/
281 2 melman701
 
282 5 melman701
 
283
/* avalon data to tx fifo*/
284
always_ff @( negedge txf_wrclk or posedge reset_i )
285 2 melman701
begin
286 5 melman701
  if( reset_i )
287
    begin
288
           txf_wrreq  <= 1'b0;
289
                txf_wrdata <= 8'b0;
290
         end
291
  else
292
    begin
293
           if( write_i & ( address_i == WRDATA_ADDR ) & ~txf_wrfull )
294
                  begin
295
                    txf_wrreq  <= 1'b1;
296
                         txf_wrdata <= writedata_i;
297
                  end
298 2 melman701
                else
299 5 melman701
                  begin
300
                    txf_wrreq  <= 1'b0;
301
                  end
302
         end
303 2 melman701
end
304 5 melman701
/*------------------------------------*/
305 2 melman701
 
306 5 melman701
/* rx fifo data to avalon */
307
always_ff @( posedge clk_i or posedge reset_i )
308 2 melman701
begin
309 5 melman701
  if( reset_i )
310
    begin
311
           adr_data <= 1'b0;
312
                adr_txsl <= 1'b0;
313
                adr_txsh <= 1'b0;
314
                adr_rxsl <= 1'b0;
315
                adr_rxsh <= 1'b0;
316
         end
317
  else
318
    begin
319
           if( read_i )
320
                  begin
321
                    if( address_i == RDDATA_ADDR )
322
                           adr_data <= 1'b1;
323
                         else
324
                           adr_data <= 1'b0;
325
 
326
                         if( address_i == TXSTATUSL_ADDR )
327
                           adr_txsl <= 1'b1;
328
                         else
329
                           adr_txsl <= 1'b0;
330
 
331
                         if( address_i == TXSTATUSH_ADDR )
332
                           adr_txsh <= 1'b1;
333
                         else
334
                           adr_txsh <= 1'b0;
335
 
336
                         if( address_i == RXSTATUSL_ADDR )
337
                           adr_rxsl <= 1'b1;
338
                         else
339
                           adr_rxsl <= 1'b0;
340
 
341
                         if( address_i == RXSTATUSH_ADDR )
342
                           adr_rxsh <= 1'b1;
343
                         else
344
                           adr_rxsh <= 1'b0;
345
                  end
346
         end
347
end
348
 
349
always_ff @( posedge clk_i or posedge reset_i )
350
begin
351
  if( reset_i )
352
    begin
353
           read_pipe <= 1'b0;
354
    end
355
  else
356
    begin
357
           if( read_i )
358
                  read_pipe <= 1'b1;
359 2 melman701
                else
360 5 melman701
                  read_pipe <= 1'b0;
361
         end
362 2 melman701
end
363
 
364 5 melman701
always_ff @( negedge rxf_rdclk or posedge reset_i )
365 2 melman701
begin
366 5 melman701
  if( reset_i )
367
    begin
368
           rxf_rdreq <= 1'b0;
369
         end
370
  else
371
    begin
372
           if( read_pipe & adr_data & ~rxf_rdempty )
373
                  rxf_rdreq <= 1'b1;
374 2 melman701
                else
375 5 melman701
                  rxf_rdreq <= 1'b0;
376
         end
377 2 melman701
end
378
 
379 5 melman701
always_ff @( posedge clk_i or posedge reset_i )
380
begin
381
  if( reset_i )
382
    begin
383
           read_pipe2 <= 1'b0;
384
    end
385
  else
386
    begin
387
           if( read_pipe )
388
                  read_pipe2 <= 1'b1;
389
                else
390
                  read_pipe2 <= 1'b0;
391
         end
392
end
393 2 melman701
 
394 5 melman701
always_ff @( posedge clk_i or posedge reset_i )
395
begin
396
  if( reset_i )
397
    begin
398
           readdata_o <= 8'b0;
399
         end
400
  else
401
    begin
402
           if( read_pipe2 )
403
                  begin
404
                    if( adr_data )
405
                           readdata_o <= rxf_rddata;
406
                         else if( adr_txsl )
407
                           readdata_o <= txstatus[7:0];
408
                         else if( adr_txsh )
409
                           readdata_o <= txstatus[15:8];
410
                         else if( adr_rxsl )
411
                           readdata_o <= rxstatus[7:0];
412
                         else if( adr_rxsh )
413
                           readdata_o <= rxstatus[15:8];
414
                         else
415
                           readdata_o <= 8'b0;
416
                  end
417
         end
418
end
419
/*------------------------------------*/
420 2 melman701
 
421 5 melman701
 
422 2 melman701
endmodule

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.