OpenCores
URL https://opencores.org/ocsvn/wf3d/wf3d/trunk

Subversion Repositories wf3d

[/] [wf3d/] [trunk/] [implement/] [rtl/] [fm_hvc/] [fm_hvc_dma.v] - Blame information for rev 2

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

Line No. Rev Author Line
1 2 specular
//=======================================================================
2
// Project Monophony
3
//   Wire-Frame 3D Graphics Accelerator IP Core
4
//
5
// File:
6
//   fm_hvc_dma.v
7
//
8
// Abstract:
9
//   VGA LCD Controller DMAC
10
//
11
// Author:
12
//   Kenji Ishimaru (kenji.ishimaru@prtissimo.com)
13
//
14
//======================================================================
15
//
16
// Copyright (c) 2015, Kenji Ishimaru
17
// All rights reserved.
18
//
19
// Redistribution and use in source and binary forms, with or without
20
// modification, are permitted provided that the following conditions are met:
21
//
22
//  -Redistributions of source code must retain the above copyright notice,
23
//   this list of conditions and the following disclaimer.
24
//  -Redistributions in binary form must reproduce the above copyright notice,
25
//   this list of conditions and the following disclaimer in the documentation
26
//   and/or other materials provided with the distribution.
27
//
28
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
29
// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
30
// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
31
// PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
32
// CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
33
// EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
34
// PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
35
// OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
36
// WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
37
// OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
38
// EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
39
//
40
// Revision History
41
 
42
module fm_hvc_dma (
43
    clk_core,
44
    rst_x,
45
    i_color_mode,
46
    i_video_start,
47
    i_vsync,
48
    i_hsync,
49
    i_fb0_offset,
50
    i_fb0_ms_offset,
51
    i_fb1_offset,
52
    i_fb1_ms_offset,
53
    i_front_buffer,
54
    i_aa_en,
55
    i_fifo_available,
56
    o_fifo_available_ack,
57
    o_vsync,
58
    o_vsync_edge,
59
    // dram if
60
    o_req,
61
    o_adrs,
62
    o_len,
63
    i_ack
64
);
65
 
66
////////////////////////////
67
// Parameter definition
68
////////////////////////////
69
    parameter P_IDLE   = 3'd0;
70
    parameter P_REQ    = 3'd1;
71
    parameter P_REQ_AA = 3'd2;
72
    parameter P_WAIT_FIFO_AVL = 3'd3;
73
    parameter P_WAIT_AVL_FALL = 3'd4;
74
 
75
    parameter P_BURST_SIZE = 6'd32;
76
    parameter P_BURST_SIZE_H = 6'd16;
77
//////////////////////////////////
78
// I/O port definition
79
//////////////////////////////////
80
    input         clk_core;
81
    input         rst_x;
82
    input [1:0]   i_color_mode;
83
    input         i_video_start;
84
    input         i_vsync;
85
    input         i_hsync;
86
    input  [6:0]  i_fb0_offset;
87
    input  [3:0]  i_fb0_ms_offset;
88
    input  [6:0]  i_fb1_offset;
89
    input  [3:0]  i_fb1_ms_offset;
90
    input         i_front_buffer;
91
    input         i_aa_en;
92
    input         i_fifo_available;
93
    output        o_fifo_available_ack;
94
    output        o_vsync;
95
    output        o_vsync_edge;
96
    // dram if
97
    output        o_req;
98
    output [23:0] o_adrs;
99
    output [5:0]  o_len;  // 32 burst x 10
100
    input         i_ack;
101
 
102
//////////////////////////////////
103
// reg
104
//////////////////////////////////
105
    reg    [2:0]   r_state;
106
    reg            r_req;
107
//    reg    [13:0]  r_cur_adrs_l;
108
    reg    [12:0]  r_cur_adrs_l;
109
 
110
    reg    [3:0]   r_req_cnt;
111
    // syncro register
112
    reg            r_vsync_1z;
113
    reg            r_vsync_2z;
114
    reg            r_vsync_3z;
115
 
116
    reg            r_hsync_1z;
117
    reg            r_hsync_2z;
118
    reg            r_hsync_3z;
119
 
120
    reg            r_fifo_available_1z;
121
    reg            r_fifo_available_2z;
122
    reg            r_fifo_available_3z;
123
    reg            r_fifo_available_ack;
124
//////////////////////////////////
125
// wire
126
//////////////////////////////////
127
    wire           w_set_initial_adrs;
128
    wire           w_v_rise;
129
    wire           w_h_start;
130
    wire           w_adrs_inc;
131
    wire           w_line_end;
132
    wire           w_req_cnt_clear;
133
 
134
    wire    [6:0]  w_fb_offset;
135
    wire    [6:0]  w_fb_ms_offset;
136
    wire    [6:0]  w_offset;
137
         wire           w_hburst;
138
//////////////////////////////////
139
// assign
140
//////////////////////////////////
141
    assign o_req = r_req;
142
    assign w_hburst = (i_color_mode == 2'd3)&(r_req_cnt == 4'd2);
143
    assign o_len = (w_hburst) ? P_BURST_SIZE_H : P_BURST_SIZE;
144
    assign o_fifo_available_ack = r_fifo_available_ack;
145
 
146
    assign w_set_initial_adrs = w_v_rise;
147
    assign w_adrs_inc = (i_aa_en) ? (r_state == P_REQ_AA) & i_ack:
148
                                    (r_state == P_REQ) & i_ack;
149
 
150
    assign w_h_start = i_video_start & r_hsync_2z & !r_hsync_3z;  // rise of hsync
151
    assign w_v_rise = r_vsync_2z & !r_vsync_3z;  // rising edge of vsync
152
    assign w_line_end = (i_color_mode == 2'd3) ? (r_req_cnt == 4'd3)  :// 80 times:
153
                                       (i_color_mode == 2'd2) ? (r_req_cnt == 4'd5)  :// 160 times
154
                                                 (r_req_cnt == 4'd10); // 320 times
155
 
156
    assign w_req_cnt_clear = (w_line_end & !r_fifo_available_2z &
157
                             (r_state == P_WAIT_AVL_FALL)) |
158
                                                                          (w_line_end & (r_state == P_WAIT_FIFO_AVL) & (i_color_mode == 'd3));
159
 
160
//   assign o_adrs = {w_offset, r_cur_adrs_l,4'b0};  // w_offset[21:18]
161
   assign o_adrs = {w_offset,r_cur_adrs_l,4'b0};  // w_offset[23:17]
162
 
163
    assign w_fb_offset = (i_front_buffer) ? i_fb1_offset : i_fb0_offset;
164
    assign w_fb_ms_offset = (i_front_buffer) ? i_fb1_ms_offset : i_fb0_ms_offset;
165
    assign w_offset = (r_state == P_REQ_AA) ? w_fb_ms_offset : w_fb_offset;
166
 
167
    assign o_vsync = r_vsync_2z;
168
    assign o_vsync_edge = !r_vsync_2z & r_vsync_3z;  // falling edge
169
 
170
//////////////////////////////////
171
// always
172
//////////////////////////////////
173
    // request state
174
    always @(posedge clk_core or negedge rst_x) begin
175
        if (~rst_x) begin
176
            r_state <= P_IDLE;
177
            r_req <= 1'b0;
178
            r_fifo_available_ack <= 1'b0;
179
        end else begin
180
            case (r_state)
181
                P_IDLE: begin
182
                    if (w_h_start) begin
183
                        r_req <= 1'b1;
184
                        r_state <= P_REQ;
185
                    end
186
                end
187
                P_REQ: begin
188
                    if (i_ack) begin
189
                        if (i_aa_en) begin
190
                            r_req <= 1'b1;
191
                            r_state <= P_REQ_AA;
192
                        end else begin
193
                            r_req <= 1'b0;
194
                            r_state <= P_WAIT_FIFO_AVL;
195
                        end
196
                    end
197
                end
198
                P_REQ_AA: begin
199
                    if (i_ack) begin
200
                        r_req <= 1'b0;
201
                        r_state <= P_WAIT_FIFO_AVL;
202
                    end
203
                end
204
                P_WAIT_FIFO_AVL: begin
205
                   if (r_req_cnt < 4'd4) begin
206
                                                          if (w_line_end) begin
207
                           r_state <= P_IDLE;
208
                                                          end else begin
209
                           r_req <= 1'b1;
210
                           r_state <= P_REQ;
211
                       end
212
                                                 end else begin
213
                       if (r_fifo_available_2z) begin
214
                           r_fifo_available_ack <= 1'b1;
215
                           r_state <= P_WAIT_AVL_FALL;
216
                       end
217
                   end
218
                end
219
                P_WAIT_AVL_FALL: begin
220
                    if (!r_fifo_available_2z) begin
221
                       r_fifo_available_ack <= 1'b0;
222
                        if (w_line_end) begin
223
                            r_state <= P_IDLE;
224
                        end else begin
225
                            r_req <= 1'b1;
226
                            r_state <= P_REQ;
227
                        end
228
                    end
229
                end
230
            endcase
231
        end
232
    end
233
 
234
    // current address
235
    always @(posedge clk_core or negedge rst_x) begin
236
        if (~rst_x) begin
237
            r_cur_adrs_l <= 13'h0; // for simulation
238
        end else begin
239
            if (w_set_initial_adrs) begin
240
                r_cur_adrs_l <= 13'h0;
241
            end else if (w_adrs_inc) begin
242
              if (w_hburst)
243
                r_cur_adrs_l <= r_cur_adrs_l + 1'b1;  // same as + 16
244
                                  else
245
                r_cur_adrs_l <= r_cur_adrs_l + 2'b10;  // same as + 32
246
            end
247
        end
248
    end
249
 
250
    always @(posedge clk_core or negedge rst_x) begin
251
        if (~rst_x) begin
252
            r_req_cnt <= 4'd0;
253
        end else begin
254
           if (w_req_cnt_clear) r_req_cnt <= 4'd0;
255
           else if (w_adrs_inc) r_req_cnt <= r_req_cnt + 1'b1;
256
        end
257
    end
258
 
259
    // syncro register
260
    always @(posedge clk_core or negedge rst_x) begin
261
        if (~rst_x) begin
262
            r_vsync_1z <= 1'b1;
263
            r_vsync_2z <= 1'b1;
264
            r_vsync_3z <= 1'b1;
265
            r_hsync_1z <= 1'b1;
266
            r_hsync_2z <= 1'b1;
267
            r_hsync_3z <= 1'b1;
268
            r_fifo_available_1z <= 1'b0;
269
            r_fifo_available_2z <= 1'b0;
270
        end else begin
271
            r_vsync_1z <= i_vsync;
272
            r_vsync_2z <= r_vsync_1z;
273
            r_vsync_3z <= r_vsync_2z;
274
            r_hsync_1z <= i_hsync;
275
            r_hsync_2z <= r_hsync_1z;
276
            r_hsync_3z <= r_hsync_2z;
277
            r_fifo_available_1z <= i_fifo_available;
278
            r_fifo_available_2z <= r_fifo_available_1z;
279
        end
280
    end
281
 
282
 
283
 
284
endmodule

powered by: WebSVN 2.1.0

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