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

Subversion Repositories i2c

[/] [i2c/] [trunk/] [rtl/] [verilog/] [i2c_master_top.v] - Blame information for rev 13

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

Line No. Rev Author Line
1 10 rherveille
//
2
// WISHBONE revB2 compiant I2C master core
3
//
4
// author: Richard Herveille
5
// rev. 0.1 26-08-2001. Iinitial Verilog release
6
//
7
 
8
`include "timescale.v"
9
`include "i2c_master_defines.v"
10
 
11
module i2c_master_top(
12
        wb_clk_i, wb_rst_i, arst_i, wb_adr_i, wb_dat_i, wb_dat_o,
13
        wb_we_i, wb_stb_i, wb_cyc_i, wb_ack_o, wb_inta_o,
14
        scl_pad_i, scl_pad_o, scl_padoen_o, sda_pad_i, sda_pad_o, sda_padoen_o );
15
 
16 11 rherveille
        // parameters
17
        parameter ARST_LVL = 1'b0; // asynchronous reset level
18
 
19 10 rherveille
        //
20
        // inputs & outputs
21
        //
22
 
23
        // wishbone signals
24
        input        wb_clk_i;     // master clock input
25
        input        wb_rst_i;     // synchronous active high reset
26
        input        arst_i;       // asynchronous reset
27
        input  [2:0] wb_adr_i;     // lower address bits
28
        input  [7:0] wb_dat_i;     // databus input
29
        output [7:0] wb_dat_o;     // databus output
30
        reg [7:0] wb_dat_o;
31
        input        wb_we_i;      // write enable input
32
        input        wb_stb_i;     // stobe/core select signal
33
        input        wb_cyc_i;     // valid bus cycle input
34
        output       wb_ack_o;     // bus cycle acknowledge output
35
        output       wb_inta_o;    // interrupt request signal output
36
        reg wb_inta_o;
37
 
38
        // I2C signals
39
        // i2c clock line
40
        input  scl_pad_i;       // SCL-line input
41
        output scl_pad_o;       // SCL-line output (always 1'b0)
42
        output scl_padoen_o;    // SCL-line output enable (active low)
43
        // i2c data line
44
        input  sda_pad_i;       // SDA-line input
45
        output sda_pad_o;       // SDA-line output (always 1'b0)
46
        output sda_padoen_o;    // SDA-line output enable (active low)
47
 
48
 
49
        //
50
        // variable declarations
51
        //
52
 
53
        // registers
54
        reg  [15:0] prer; // clock prescale register
55
        reg  [ 7:0] ctr;  // control register
56
        reg  [ 7:0] txr;  // transmit register
57
        wire [ 7:0] rxr;  // receive register
58
        reg  [ 7:0] cr;   // command register
59
        wire [ 7:0] sr;   // status register
60
 
61
        // done signal: command completed, clear command register
62
        wire done;
63
 
64
        // core enable signal
65
        wire core_en;
66 13 rherveille
        wire ien;
67 10 rherveille
 
68
        // status register signals
69
        wire irxack;
70
        reg  rxack;       // received aknowledge from slave
71
        reg  tip;         // transfer in progress
72
        reg  irq_flag;    // interrupt pending flag
73
        wire i2c_busy;    // bus busy (start signal detected)
74
 
75
        //
76
        // module body
77
        //
78
 
79
        // generate internal reset
80 11 rherveille
        wire rst_i = arst_i ^ ARST_LVL;
81 10 rherveille
 
82
        // generate acknowledge output signal
83
        assign wb_ack_o = wb_cyc_i && wb_stb_i; // because timing is always honored
84
 
85
        // assign DAT_O
86
        always@(wb_adr_i or prer or ctr or txr or cr or rxr or sr)
87
        begin
88
                case (wb_adr_i) // synopsis full_case parallel_case
89
                        3'b000: wb_dat_o = prer[ 7:0];
90
                        3'b001: wb_dat_o = prer[15:8];
91
                        3'b010: wb_dat_o = ctr;
92
                        3'b011: wb_dat_o = rxr; // write is transmit register (txr)
93
                        3'b100: wb_dat_o = sr;  // write is command register (cr)
94
                        3'b101: wb_dat_o = txr;
95
                        3'b110: wb_dat_o = cr;
96
                endcase
97
        end
98
 
99
 
100
        // generate registers
101
        always@(posedge wb_clk_i or negedge rst_i)
102
                if (!rst_i)
103
                        begin
104
                                prer <= #1 16'h0;
105
                                ctr  <= #1  8'h0;
106
                                txr  <= #1  8'h0;
107
                                cr   <= #1  8'h0;
108
                        end
109
                else if (wb_rst_i)
110
                        begin
111
                                prer <= #1 16'h0;
112
                                ctr  <= #1  8'h0;
113
                                txr  <= #1  8'h0;
114
                                cr   <= #1  8'h0;
115
                        end
116
                else
117
                        if (wb_cyc_i && wb_stb_i && wb_we_i)
118
                                begin
119
                                        if (!wb_adr_i[2])
120
                                                case (wb_adr_i[1:0]) // synopsis full_case parallel_case
121
                                                        2'b00 : prer [ 7:0] <= #1 wb_dat_i;
122
                                                        2'b01 : prer [15:8] <= #1 wb_dat_i;
123
                                                        2'b10 : ctr         <= #1 wb_dat_i;
124
                                                        2'b11 : txr         <= #1 wb_dat_i;
125
                                                endcase
126
                                        else
127
                                                if (core_en && (wb_adr_i[1:0] == 2'b00) ) // only take new commands when i2c core enabled, pending commands are finished
128
                                                        cr <= #1 wb_dat_i;
129
                                end
130
                        else
131
                                begin
132
                                        if (done)
133
                                                cr[7:4] <= #1 4'h0; // clear command bits when done
134
 
135
                                        cr[2:1] <= #1 2'b00;  // reserved bits
136
                                        cr[0]   <= #1 cr[0] && irq_flag; // clear when irq_flag cleared
137
                                end
138
 
139
 
140
        // decode command register
141
        wire sta  = cr[7];
142
        wire sto  = cr[6];
143
        wire rd   = cr[5];
144
        wire wr   = cr[4];
145
        wire ack  = cr[3];
146
        wire iack = cr[0];
147
 
148
        // decode control register
149
        assign core_en = ctr[7];
150 13 rherveille
        assign ien = ctr[6];
151 10 rherveille
 
152
        // hookup byte controller block
153
        i2c_master_byte_ctrl byte_controller (
154
                .clk(wb_clk_i),
155
                .rst(wb_rst_i),
156
                .nReset(rst_i),
157
                .ena(core_en),
158
                .clk_cnt(prer),
159
                .start(sta),
160
                .stop(sto),
161
                .read(rd),
162
                .write(wr),
163
                .ack_in(ack),
164
                .din(txr),
165
                .cmd_ack(done),
166
                .ack_out(irxack),
167
                .dout(rxr),
168
                .i2c_busy(i2c_busy),
169
                .scl_i(scl_pad_i),
170
                .scl_o(scl_pad_o),
171
                .scl_oen(scl_padoen_o),
172
                .sda_i(sda_pad_i),
173
                .sda_o(sda_pad_o),
174
                .sda_oen(sda_padoen_o)
175
        );
176
 
177
 
178
        // status register block + interrupt request signal
179
        always@(posedge wb_clk_i or negedge rst_i)
180
                if (!rst_i)
181
                        begin
182
                                rxack    <= #1 1'b0;
183
                                tip      <= #1 1'b0;
184
                                irq_flag <= #1 1'b0;
185
                        end
186
                else if (wb_rst_i)
187
                        begin
188
                                rxack    <= #1 1'b0;
189
                                tip      <= #1 1'b0;
190
                                irq_flag <= #1 1'b0;
191
                        end
192
                else
193
                        begin
194
                                rxack    <= #1 irxack;
195
                                tip      <= #1 (rd || wr);
196
                                irq_flag <= #1 (done || irq_flag) && !iack; // interrupt request flag is always generated
197
                        end
198
 
199
                // generate interrupt request signals
200
                always@(posedge wb_clk_i or negedge rst_i)
201
                        if (!rst_i)
202
                                wb_inta_o <= #1 1'b0;
203
                        else if (wb_rst_i)
204
                                wb_inta_o <= #1 1'b0;
205
                        else
206 13 rherveille
                                wb_inta_o <= #1 irq_flag && ien; // interrupt signal is only generated when IEN (interrupt enable bit is set)
207 10 rherveille
 
208
                // assign status register bits
209
                assign sr[7]   = rxack;
210
                assign sr[6]   = i2c_busy;
211
                assign sr[5:2] = 4'h0; // reserved
212
                assign sr[1]   = tip;
213
                assign sr[0]   = irq_flag;
214
 
215
endmodule
216
 
217
 
218
 
219
 
220
 
221
 
222
 
223
 
224 11 rherveille
 

powered by: WebSVN 2.1.0

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