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#include <config.h>
26#include <common.h>
27
28#include <tsi108.h>
29
30#if defined(CONFIG_CMD_I2C)
31
32#define I2C_DELAY 100000
33#undef DEBUG_I2C
34
35#ifdef DEBUG_I2C
36#define DPRINT(x) printf (x)
37#else
38#define DPRINT(x)
39#endif
40
41
42
43
44void i2c_init(int speed, int slaveaddr)
45{
46
47
48
49
50
51}
52
53static int i2c_read_byte (
54 uint i2c_chan,
55 uchar chip_addr,
56 uint byte_addr,
57 uchar * buffer
58 )
59{
60 u32 temp;
61 u32 to_count = I2C_DELAY;
62 u32 op_status = TSI108_I2C_TIMEOUT_ERR;
63 u32 chan_offset = TSI108_I2C_OFFSET;
64
65 DPRINT (("I2C read_byte() %d 0x%02x 0x%02x\n",
66 i2c_chan, chip_addr, byte_addr));
67
68 if (0 != i2c_chan)
69 chan_offset = TSI108_I2C_SDRAM_OFFSET;
70
71
72 temp = *(u32 *) (CONFIG_SYS_TSI108_CSR_BASE + chan_offset + I2C_CNTRL2);
73
74 if (0 == (temp & (I2C_CNTRL2_RD_STATUS | I2C_CNTRL2_WR_STATUS |
75 I2C_CNTRL2_START))) {
76
77 temp = (byte_addr << 16) | ((chip_addr & 0x07) << 8) |
78 ((chip_addr >> 3) & 0x0F);
79 *(u32 *) (CONFIG_SYS_TSI108_CSR_BASE + chan_offset + I2C_CNTRL1) =
80 temp;
81
82
83
84
85
86
87 *(u32 *) (CONFIG_SYS_TSI108_CSR_BASE + chan_offset + I2C_CNTRL2) =
88 (I2C_CNTRL2_START);
89
90
91 do {
92
93 temp = *(u32 *) (CONFIG_SYS_TSI108_CSR_BASE + chan_offset + I2C_CNTRL2);
94
95 if (0 == (temp & (I2C_CNTRL2_RD_STATUS | I2C_CNTRL2_START))) {
96 if (0 == (temp &
97 (I2C_CNTRL2_I2C_CFGERR |
98 I2C_CNTRL2_I2C_TO_ERR))
99 ) {
100 op_status = TSI108_I2C_SUCCESS;
101
102 temp = *(u32 *) (CONFIG_SYS_TSI108_CSR_BASE +
103 chan_offset +
104 I2C_RD_DATA);
105
106 *buffer = (u8) (temp & 0xFF);
107 } else {
108
109 op_status = TSI108_I2C_IF_ERROR;
110
111 DPRINT (("I2C HW error reported: 0x%02x\n", temp));
112 }
113
114 break;
115 }
116 } while (to_count--);
117 } else {
118 op_status = TSI108_I2C_IF_BUSY;
119
120 DPRINT (("I2C Transaction start failed: 0x%02x\n", temp));
121 }
122
123 DPRINT (("I2C read_byte() status: 0x%02x\n", op_status));
124 return op_status;
125}
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144int i2c_read (uchar chip_addr, uint byte_addr, int alen,
145 uchar * buffer, int len)
146{
147 u32 op_status = TSI108_I2C_PARAM_ERR;
148 u32 i2c_if = 0;
149
150
151 if (0xD0 == (chip_addr & ~0x07)) {
152 i2c_if = 1;
153 chip_addr &= 0x7F;
154 }
155
156 if (chip_addr <= 0x7F && (byte_addr + len) <= (0x01 << (alen * 8))) {
157 while (len--) {
158 op_status = i2c_read_byte(i2c_if, chip_addr, byte_addr++, buffer++);
159
160 if (TSI108_I2C_SUCCESS != op_status) {
161 DPRINT (("I2C read_byte() failed: 0x%02x (%d left)\n", op_status, len));
162
163 break;
164 }
165 }
166 }
167
168 DPRINT (("I2C read() status: 0x%02x\n", op_status));
169 return op_status;
170}
171
172
173
174static int i2c_write_byte (uchar chip_addr,
175 uint byte_addr,
176 uchar * buffer
177 )
178{
179 u32 temp;
180 u32 to_count = I2C_DELAY;
181 u32 op_status = TSI108_I2C_TIMEOUT_ERR;
182
183
184 temp = *(u32 *) (CONFIG_SYS_TSI108_CSR_BASE + TSI108_I2C_OFFSET + I2C_CNTRL2);
185
186 if (0 == (temp & (I2C_CNTRL2_RD_STATUS | I2C_CNTRL2_WR_STATUS | I2C_CNTRL2_START))) {
187
188 *(u32 *) (CONFIG_SYS_TSI108_CSR_BASE + TSI108_I2C_OFFSET +
189 I2C_TX_DATA) = (u32) * buffer;
190
191
192 temp =
193 I2C_CNTRL1_I2CWRITE | (byte_addr << 16) |
194 ((chip_addr & 0x07) << 8) | ((chip_addr >> 3) & 0x0F);
195 *(u32 *) (CONFIG_SYS_TSI108_CSR_BASE + TSI108_I2C_OFFSET +
196 I2C_CNTRL1) = temp;
197
198
199
200
201
202 *(u32 *) (CONFIG_SYS_TSI108_CSR_BASE + TSI108_I2C_OFFSET +
203 I2C_CNTRL2) = (I2C_CNTRL2_START);
204
205 op_status = TSI108_I2C_TIMEOUT_ERR;
206
207
208 do {
209
210 temp = *(u32 *) (CONFIG_SYS_TSI108_CSR_BASE + TSI108_I2C_OFFSET + I2C_CNTRL2);
211
212 if (0 == (temp & (I2C_CNTRL2_WR_STATUS | I2C_CNTRL2_START))) {
213 if (0 == (temp &
214 (I2C_CNTRL2_I2C_CFGERR |
215 I2C_CNTRL2_I2C_TO_ERR))) {
216 op_status = TSI108_I2C_SUCCESS;
217 } else {
218
219 op_status = TSI108_I2C_IF_ERROR;
220
221 DPRINT (("I2C HW error reported: 0x%02x\n", temp));
222 }
223
224 break;
225 }
226
227 } while (to_count--);
228 } else {
229 op_status = TSI108_I2C_IF_BUSY;
230
231 DPRINT (("I2C Transaction start failed: 0x%02x\n", temp));
232 }
233
234 return op_status;
235}
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250int i2c_write (uchar chip_addr, uint byte_addr, int alen, uchar * buffer,
251 int len)
252{
253 u32 op_status = TSI108_I2C_PARAM_ERR;
254
255
256 if (chip_addr <= 0x7F && (byte_addr + len) <= (0x01 << (alen * 8))) {
257 while (len--) {
258 op_status =
259 i2c_write_byte (chip_addr, byte_addr++, buffer++);
260
261 if (TSI108_I2C_SUCCESS != op_status) {
262 DPRINT (("I2C write_byte() failed: 0x%02x (%d left)\n", op_status, len));
263
264 break;
265 }
266 }
267 }
268
269 return op_status;
270}
271
272
273
274
275
276
277
278int i2c_probe (uchar chip)
279{
280 u32 tmp;
281
282
283
284
285
286
287 return i2c_read (chip, 0, 1, (uchar *)&tmp, 1);
288}
289
290#endif
291