]> git.kernelconcepts.de Git - karo-tx-uboot.git/blob - drivers/i2c/omap24xx_i2c.c
ARMV7: OMAP: I2C driver: Use same timeout value as linux kernel driver
[karo-tx-uboot.git] / drivers / i2c / omap24xx_i2c.c
1 /*
2  * Basic I2C functions
3  *
4  * Copyright (c) 2004 Texas Instruments
5  *
6  * This package is free software;  you can redistribute it and/or
7  * modify it under the terms of the license found in the file
8  * named COPYING that should have accompanied this file.
9  *
10  * THIS PACKAGE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR
11  * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
12  * WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
13  *
14  * Author: Jian Zhang jzhang@ti.com, Texas Instruments
15  *
16  * Copyright (c) 2003 Wolfgang Denk, wd@denx.de
17  * Rewritten to fit into the current U-Boot framework
18  *
19  * Adapted for OMAP2420 I2C, r-woodruff2@ti.com
20  *
21  */
22
23 #include <common.h>
24
25 #include <asm/arch/i2c.h>
26 #include <asm/io.h>
27
28 #include "omap24xx_i2c.h"
29
30 #define I2C_TIMEOUT     1000
31
32 static void wait_for_bb (void);
33 static u16 wait_for_pin (void);
34 static void flush_fifo(void);
35
36 static struct i2c *i2c_base = (struct i2c *)I2C_DEFAULT_BASE;
37
38 static unsigned int bus_initialized[I2C_BUS_MAX];
39 static unsigned int current_bus;
40
41 void i2c_init (int speed, int slaveadd)
42 {
43         DECLARE_GLOBAL_DATA_PTR;
44         int psc, fsscll, fssclh;
45         int hsscll = 0, hssclh = 0;
46         u32 scll, sclh;
47         int timeout = I2C_TIMEOUT;
48
49         /* Only handle standard, fast and high speeds */
50         if ((speed != OMAP_I2C_STANDARD) &&
51             (speed != OMAP_I2C_FAST_MODE) &&
52             (speed != OMAP_I2C_HIGH_SPEED)) {
53                 printf("Error : I2C unsupported speed %d\n", speed);
54                 return;
55         }
56
57         psc = I2C_IP_CLK / I2C_INTERNAL_SAMPLING_CLK;
58         psc -= 1;
59         if (psc < I2C_PSC_MIN) {
60                 printf("Error : I2C unsupported prescalar %d\n", psc);
61                 return;
62         }
63
64         if (speed == OMAP_I2C_HIGH_SPEED) {
65                 /* High speed */
66
67                 /* For first phase of HS mode */
68                 fsscll = fssclh = I2C_INTERNAL_SAMPLING_CLK /
69                         (2 * OMAP_I2C_FAST_MODE);
70
71                 fsscll -= I2C_HIGHSPEED_PHASE_ONE_SCLL_TRIM;
72                 fssclh -= I2C_HIGHSPEED_PHASE_ONE_SCLH_TRIM;
73                 if (((fsscll < 0) || (fssclh < 0)) ||
74                     ((fsscll > 255) || (fssclh > 255))) {
75                         printf("Error : I2C initializing first phase clock\n");
76                         return;
77                 }
78
79                 /* For second phase of HS mode */
80                 hsscll = hssclh = I2C_INTERNAL_SAMPLING_CLK / (2 * speed);
81
82                 hsscll -= I2C_HIGHSPEED_PHASE_TWO_SCLL_TRIM;
83                 hssclh -= I2C_HIGHSPEED_PHASE_TWO_SCLH_TRIM;
84                 if (((fsscll < 0) || (fssclh < 0)) ||
85                     ((fsscll > 255) || (fssclh > 255))) {
86                         printf("Error : I2C initializing second phase clock\n");
87                         return;
88                 }
89
90                 scll = (unsigned int)hsscll << 8 | (unsigned int)fsscll;
91                 sclh = (unsigned int)hssclh << 8 | (unsigned int)fssclh;
92
93         } else {
94                 /* Standard and fast speed */
95                 fsscll = fssclh = I2C_INTERNAL_SAMPLING_CLK / (2 * speed);
96
97                 fsscll -= I2C_FASTSPEED_SCLL_TRIM;
98                 fssclh -= I2C_FASTSPEED_SCLH_TRIM;
99                 if (((fsscll < 0) || (fssclh < 0)) ||
100                     ((fsscll > 255) || (fssclh > 255))) {
101                         printf("Error : I2C initializing clock\n");
102                         return;
103                 }
104
105                 scll = (unsigned int)fsscll;
106                 sclh = (unsigned int)fssclh;
107         }
108
109         if (readw (&i2c_base->con) & I2C_CON_EN) {
110                 writew (0, &i2c_base->con);
111                 udelay (50000);
112         }
113
114         writew(0x2, &i2c_base->sysc); /* for ES2 after soft reset */
115         udelay(1000);
116
117         writew(I2C_CON_EN, &i2c_base->con);
118         while (!(readw(&i2c_base->syss) & I2C_SYSS_RDONE) && timeout--) {
119                 if (timeout <= 0) {
120                         printf("ERROR: Timeout in soft-reset\n");
121                         return;
122                 }
123                 udelay(1000);
124         }
125
126         writew(0, &i2c_base->con);
127         writew(psc, &i2c_base->psc);
128         writew(scll, &i2c_base->scll);
129         writew(sclh, &i2c_base->sclh);
130
131         /* own address */
132         writew (slaveadd, &i2c_base->oa);
133         writew (I2C_CON_EN, &i2c_base->con);
134
135         /* have to enable intrrupts or OMAP i2c module doesn't work */
136         writew (I2C_IE_XRDY_IE | I2C_IE_RRDY_IE | I2C_IE_ARDY_IE |
137                 I2C_IE_NACK_IE | I2C_IE_AL_IE, &i2c_base->ie);
138         udelay (1000);
139         flush_fifo();
140         writew (0xFFFF, &i2c_base->stat);
141         writew (0, &i2c_base->cnt);
142
143         if (gd->flags & GD_FLG_RELOC)
144                 bus_initialized[current_bus] = 1;
145 }
146
147 static int i2c_read_byte (u8 devaddr, u8 regoffset, u8 * value)
148 {
149         int i2c_error = 0;
150         u16 status;
151
152         /* wait until bus not busy */
153         wait_for_bb ();
154
155         /* one byte only */
156         writew (1, &i2c_base->cnt);
157         /* set slave address */
158         writew (devaddr, &i2c_base->sa);
159         /* no stop bit needed here */
160         writew (I2C_CON_EN | I2C_CON_MST | I2C_CON_STT | I2C_CON_TRX, &i2c_base->con);
161
162         status = wait_for_pin ();
163
164         if (status & I2C_STAT_XRDY) {
165                 /* Important: have to use byte access */
166                 writeb (regoffset, &i2c_base->data);
167                 udelay (20000);
168                 if (readw (&i2c_base->stat) & I2C_STAT_NACK) {
169                         i2c_error = 1;
170                 }
171         } else {
172                 i2c_error = 1;
173         }
174
175         if (!i2c_error) {
176                 writew (I2C_CON_EN, &i2c_base->con);
177                 while (readw(&i2c_base->stat) &
178                         (I2C_STAT_XRDY | I2C_STAT_ARDY)) {
179                         udelay (10000);
180                         /* Have to clear pending interrupt to clear I2C_STAT */
181                         writew (0xFFFF, &i2c_base->stat);
182                 }
183
184                 /* set slave address */
185                 writew (devaddr, &i2c_base->sa);
186                 /* read one byte from slave */
187                 writew (1, &i2c_base->cnt);
188                 /* need stop bit here */
189                 writew (I2C_CON_EN | I2C_CON_MST | I2C_CON_STT | I2C_CON_STP,
190                         &i2c_base->con);
191
192                 status = wait_for_pin ();
193                 if (status & I2C_STAT_RRDY) {
194 #if defined(CONFIG_OMAP243X) || defined(CONFIG_OMAP34XX) || \
195     defined(CONFIG_OMAP44XX)
196                         *value = readb (&i2c_base->data);
197 #else
198                         *value = readw (&i2c_base->data);
199 #endif
200                         udelay (20000);
201                 } else {
202                         i2c_error = 1;
203                 }
204
205                 if (!i2c_error) {
206                         writew (I2C_CON_EN, &i2c_base->con);
207                         while (readw (&i2c_base->stat) &
208                                 (I2C_STAT_RRDY | I2C_STAT_ARDY)) {
209                                 udelay (10000);
210                                 writew (0xFFFF, &i2c_base->stat);
211                         }
212                 }
213         }
214         flush_fifo();
215         writew (0xFFFF, &i2c_base->stat);
216         writew (0, &i2c_base->cnt);
217         return i2c_error;
218 }
219
220 static int i2c_write_byte (u8 devaddr, u8 regoffset, u8 value)
221 {
222         int i2c_error = 0;
223         u16 status, stat;
224
225         /* wait until bus not busy */
226         wait_for_bb ();
227
228         /* two bytes */
229         writew (2, &i2c_base->cnt);
230         /* set slave address */
231         writew (devaddr, &i2c_base->sa);
232         /* stop bit needed here */
233         writew (I2C_CON_EN | I2C_CON_MST | I2C_CON_STT | I2C_CON_TRX |
234                 I2C_CON_STP, &i2c_base->con);
235
236         /* wait until state change */
237         status = wait_for_pin ();
238
239         if (status & I2C_STAT_XRDY) {
240 #if defined(CONFIG_OMAP243X) || defined(CONFIG_OMAP34XX) || \
241     defined(CONFIG_OMAP44XX)
242                 /* send out 1 byte */
243                 writeb (regoffset, &i2c_base->data);
244                 writew (I2C_STAT_XRDY, &i2c_base->stat);
245
246                 status = wait_for_pin ();
247                 if ((status & I2C_STAT_XRDY)) {
248                         /* send out next 1 byte */
249                         writeb (value, &i2c_base->data);
250                         writew (I2C_STAT_XRDY, &i2c_base->stat);
251                 } else {
252                         i2c_error = 1;
253                 }
254 #else
255                 /* send out two bytes */
256                 writew ((value << 8) + regoffset, &i2c_base->data);
257 #endif
258                 /* must have enough delay to allow BB bit to go low */
259                 udelay (50000);
260                 if (readw (&i2c_base->stat) & I2C_STAT_NACK) {
261                         i2c_error = 1;
262                 }
263         } else {
264                 i2c_error = 1;
265         }
266
267         if (!i2c_error) {
268                 int eout = 200;
269
270                 writew (I2C_CON_EN, &i2c_base->con);
271                 while ((stat = readw (&i2c_base->stat)) || (readw (&i2c_base->con) & I2C_CON_MST)) {
272                         udelay (1000);
273                         /* have to read to clear intrrupt */
274                         writew (0xFFFF, &i2c_base->stat);
275                         if(--eout == 0) /* better leave with error than hang */
276                                 break;
277                 }
278         }
279         flush_fifo();
280         writew (0xFFFF, &i2c_base->stat);
281         writew (0, &i2c_base->cnt);
282         return i2c_error;
283 }
284
285 static void flush_fifo(void)
286 {       u16 stat;
287
288         /* note: if you try and read data when its not there or ready
289          * you get a bus error
290          */
291         while(1){
292                 stat = readw(&i2c_base->stat);
293                 if(stat == I2C_STAT_RRDY){
294 #if defined(CONFIG_OMAP243X) || defined(CONFIG_OMAP34XX) || \
295     defined(CONFIG_OMAP44XX)
296                         readb(&i2c_base->data);
297 #else
298                         readw(&i2c_base->data);
299 #endif
300                         writew(I2C_STAT_RRDY,&i2c_base->stat);
301                         udelay(1000);
302                 }else
303                         break;
304         }
305 }
306
307 int i2c_probe (uchar chip)
308 {
309         int res = 1; /* default = fail */
310
311         if (chip == readw (&i2c_base->oa)) {
312                 return res;
313         }
314
315         /* wait until bus not busy */
316         wait_for_bb ();
317
318         /* try to read one byte */
319         writew (1, &i2c_base->cnt);
320         /* set slave address */
321         writew (chip, &i2c_base->sa);
322         /* stop bit needed here */
323         writew (I2C_CON_EN | I2C_CON_MST | I2C_CON_STT | I2C_CON_STP, &i2c_base->con);
324         /* enough delay for the NACK bit set */
325         udelay (50000);
326
327         if (!(readw (&i2c_base->stat) & I2C_STAT_NACK)) {
328                 res = 0;      /* success case */
329                 flush_fifo();
330                 writew(0xFFFF, &i2c_base->stat);
331         } else {
332                 writew(0xFFFF, &i2c_base->stat);         /* failue, clear sources*/
333                 writew (readw (&i2c_base->con) | I2C_CON_STP, &i2c_base->con); /* finish up xfer */
334                 udelay(20000);
335                 wait_for_bb ();
336         }
337         flush_fifo();
338         writew (0, &i2c_base->cnt); /* don't allow any more data in...we don't want it.*/
339         writew(0xFFFF, &i2c_base->stat);
340         return res;
341 }
342
343 int i2c_read (uchar chip, uint addr, int alen, uchar * buffer, int len)
344 {
345         int i;
346
347         if (alen > 1) {
348                 printf ("I2C read: addr len %d not supported\n", alen);
349                 return 1;
350         }
351
352         if (addr + len > 256) {
353                 printf ("I2C read: address out of range\n");
354                 return 1;
355         }
356
357         for (i = 0; i < len; i++) {
358                 if (i2c_read_byte (chip, addr + i, &buffer[i])) {
359                         printf ("I2C read: I/O error\n");
360                         i2c_init (CONFIG_SYS_I2C_SPEED, CONFIG_SYS_I2C_SLAVE);
361                         return 1;
362                 }
363         }
364
365         return 0;
366 }
367
368 int i2c_write (uchar chip, uint addr, int alen, uchar * buffer, int len)
369 {
370         int i;
371
372         if (alen > 1) {
373                 printf ("I2C read: addr len %d not supported\n", alen);
374                 return 1;
375         }
376
377         if (addr + len > 256) {
378                 printf ("I2C read: address out of range\n");
379                 return 1;
380         }
381
382         for (i = 0; i < len; i++) {
383                 if (i2c_write_byte (chip, addr + i, buffer[i])) {
384                         printf ("I2C read: I/O error\n");
385                         i2c_init (CONFIG_SYS_I2C_SPEED, CONFIG_SYS_I2C_SLAVE);
386                         return 1;
387                 }
388         }
389
390         return 0;
391 }
392
393 static void wait_for_bb (void)
394 {
395         int timeout = I2C_TIMEOUT;
396         u16 stat;
397
398         writew(0xFFFF, &i2c_base->stat);         /* clear current interruts...*/
399         while ((stat = readw (&i2c_base->stat) & I2C_STAT_BB) && timeout--) {
400                 writew (stat, &i2c_base->stat);
401                 udelay(1000);
402         }
403
404         if (timeout <= 0) {
405                 printf ("timed out in wait_for_bb: I2C_STAT=%x\n",
406                         readw (&i2c_base->stat));
407         }
408         writew(0xFFFF, &i2c_base->stat);         /* clear delayed stuff*/
409 }
410
411 static u16 wait_for_pin (void)
412 {
413         u16 status;
414         int timeout = I2C_TIMEOUT;
415
416         do {
417                 udelay (1000);
418                 status = readw (&i2c_base->stat);
419         } while (  !(status &
420                    (I2C_STAT_ROVR | I2C_STAT_XUDF | I2C_STAT_XRDY |
421                     I2C_STAT_RRDY | I2C_STAT_ARDY | I2C_STAT_NACK |
422                     I2C_STAT_AL)) && timeout--);
423
424         if (timeout <= 0) {
425                 printf ("timed out in wait_for_pin: I2C_STAT=%x\n",
426                         readw (&i2c_base->stat));
427                 writew(0xFFFF, &i2c_base->stat);
428                 status = 0;
429         }
430
431         return status;
432 }
433
434 int i2c_set_bus_num(unsigned int bus)
435 {
436         if ((bus < 0) || (bus >= I2C_BUS_MAX)) {
437                 printf("Bad bus: %d\n", bus);
438                 return -1;
439         }
440
441 #if I2C_BUS_MAX==3
442         if (bus == 2)
443                 i2c_base = (struct i2c *)I2C_BASE3;
444         else
445 #endif
446         if (bus == 1)
447                 i2c_base = (struct i2c *)I2C_BASE2;
448         else
449                 i2c_base = (struct i2c *)I2C_BASE1;
450
451         current_bus = bus;
452
453         if(!bus_initialized[current_bus])
454                 i2c_init(CONFIG_SYS_I2C_SPEED, CONFIG_SYS_I2C_SLAVE);
455
456         return 0;
457 }
458
459 int i2c_get_bus_num(void)
460 {
461         return (int) current_bus;
462 }