2 i2c Support for Atmel's AT91 Two-Wire Interface (TWI)
4 Copyright (C) 2004 Rick Bronson
5 Converted to 2.6 by Andrew Victor <andrew@sanpeople.com>
7 Borrowed heavily from original work by:
8 Copyright (C) 2000 Philip Edelbrock <phil@stimpy.netroedge.com>
10 This program is free software; you can redistribute it and/or modify
11 it under the terms of the GNU General Public License as published by
12 the Free Software Foundation; either version 2 of the License, or
13 (at your option) any later version.
16 #include <linux/module.h>
17 #include <linux/kernel.h>
18 #include <linux/err.h>
19 #include <linux/slab.h>
20 #include <linux/types.h>
21 #include <linux/delay.h>
22 #include <linux/i2c.h>
23 #include <linux/init.h>
24 #include <linux/clk.h>
25 #include <linux/platform_device.h>
28 #include <mach/at91_twi.h>
29 #include <mach/board.h>
32 #define TWI_CLOCK 100000 /* Hz. max 400 Kbits/sec */
35 static struct clk
*twi_clk
;
36 static void __iomem
*twi_base
;
38 #define at91_twi_read(reg) __raw_readl(twi_base + (reg))
39 #define at91_twi_write(reg, val) __raw_writel((val), twi_base + (reg))
43 * Initialize the TWI hardware registers.
45 static void __devinit
at91_twi_hwinit(void)
47 unsigned long cdiv
, ckdiv
;
49 at91_twi_write(AT91_TWI_IDR
, 0xffffffff); /* Disable all interrupts */
50 at91_twi_write(AT91_TWI_CR
, AT91_TWI_SWRST
); /* Reset peripheral */
51 at91_twi_write(AT91_TWI_CR
, AT91_TWI_MSEN
); /* Set Master mode */
53 /* Calcuate clock dividers */
54 cdiv
= (clk_get_rate(twi_clk
) / (2 * TWI_CLOCK
)) - 3;
55 cdiv
= cdiv
+ 1; /* round up */
62 if (cpu_is_at91rm9200()) { /* AT91RM9200 Errata #22 */
64 printk(KERN_ERR
"AT91 I2C: Invalid TWI_CLOCK value!\n");
69 at91_twi_write(AT91_TWI_CWGR
, (ckdiv
<< 16) | (cdiv
<< 8) | cdiv
);
73 * Poll the i2c status register until the specified bit is set.
74 * Returns 0 if timed out (100 msec).
76 static short at91_poll_status(unsigned long bit
)
78 int loop_cntr
= 10000;
82 } while (!(at91_twi_read(AT91_TWI_SR
) & bit
) && (--loop_cntr
> 0));
84 return (loop_cntr
> 0);
87 static int xfer_read(struct i2c_adapter
*adap
, unsigned char *buf
, int length
)
90 at91_twi_write(AT91_TWI_CR
, AT91_TWI_START
);
94 if (!length
) /* need to send Stop before reading last byte */
95 at91_twi_write(AT91_TWI_CR
, AT91_TWI_STOP
);
96 if (!at91_poll_status(AT91_TWI_RXRDY
)) {
97 dev_dbg(&adap
->dev
, "RXRDY timeout\n");
100 *buf
++ = (at91_twi_read(AT91_TWI_RHR
) & 0xff);
106 static int xfer_write(struct i2c_adapter
*adap
, unsigned char *buf
, int length
)
108 /* Load first byte into transmitter */
109 at91_twi_write(AT91_TWI_THR
, *buf
++);
112 at91_twi_write(AT91_TWI_CR
, AT91_TWI_START
);
115 if (!at91_poll_status(AT91_TWI_TXRDY
)) {
116 dev_dbg(&adap
->dev
, "TXRDY timeout\n");
120 length
--; /* byte was transmitted */
122 if (length
> 0) /* more data to send? */
123 at91_twi_write(AT91_TWI_THR
, *buf
++);
127 at91_twi_write(AT91_TWI_CR
, AT91_TWI_STOP
);
133 * Generic i2c master transfer entrypoint.
135 * Note: We do not use Atmel's feature of storing the "internal device address".
136 * Instead the "internal device address" has to be written using a separate
138 * http://lists.arm.linux.org.uk/pipermail/linux-arm-kernel/2004-September/024411.html
140 static int at91_xfer(struct i2c_adapter
*adap
, struct i2c_msg
*pmsg
, int num
)
144 dev_dbg(&adap
->dev
, "at91_xfer: processing %d messages:\n", num
);
146 for (i
= 0; i
< num
; i
++) {
147 dev_dbg(&adap
->dev
, " #%d: %sing %d byte%s %s 0x%02x\n", i
,
148 pmsg
->flags
& I2C_M_RD
? "read" : "writ",
149 pmsg
->len
, pmsg
->len
> 1 ? "s" : "",
150 pmsg
->flags
& I2C_M_RD
? "from" : "to", pmsg
->addr
);
152 at91_twi_write(AT91_TWI_MMR
, (pmsg
->addr
<< 16)
153 | ((pmsg
->flags
& I2C_M_RD
) ? AT91_TWI_MREAD
: 0));
155 if (pmsg
->len
&& pmsg
->buf
) { /* sanity check */
156 if (pmsg
->flags
& I2C_M_RD
)
157 ret
= xfer_read(adap
, pmsg
->buf
, pmsg
->len
);
159 ret
= xfer_write(adap
, pmsg
->buf
, pmsg
->len
);
164 /* Wait until transfer is finished */
165 if (!at91_poll_status(AT91_TWI_TXCOMP
)) {
166 dev_dbg(&adap
->dev
, "TXCOMP timeout\n");
170 dev_dbg(&adap
->dev
, "transfer complete\n");
171 pmsg
++; /* next message */
177 * Return list of supported functionality.
179 static u32
at91_func(struct i2c_adapter
*adapter
)
181 return I2C_FUNC_I2C
| I2C_FUNC_SMBUS_EMUL
;
184 static struct i2c_algorithm at91_algorithm
= {
185 .master_xfer
= at91_xfer
,
186 .functionality
= at91_func
,
190 * Main initialization routine.
192 static int __devinit
at91_i2c_probe(struct platform_device
*pdev
)
194 struct i2c_adapter
*adapter
;
195 struct resource
*res
;
198 res
= platform_get_resource(pdev
, IORESOURCE_MEM
, 0);
202 if (!request_mem_region(res
->start
, resource_size(res
), "at91_i2c"))
205 twi_base
= ioremap(res
->start
, resource_size(res
));
211 twi_clk
= clk_get(NULL
, "twi_clk");
212 if (IS_ERR(twi_clk
)) {
213 dev_err(&pdev
->dev
, "no clock defined\n");
218 adapter
= kzalloc(sizeof(struct i2c_adapter
), GFP_KERNEL
);
219 if (adapter
== NULL
) {
220 dev_err(&pdev
->dev
, "can't allocate inteface!\n");
224 snprintf(adapter
->name
, sizeof(adapter
->name
), "AT91");
225 adapter
->algo
= &at91_algorithm
;
226 adapter
->class = I2C_CLASS_HWMON
;
227 adapter
->dev
.parent
= &pdev
->dev
;
228 /* adapter->id == 0 ... only one TWI controller for now */
230 platform_set_drvdata(pdev
, adapter
);
232 clk_enable(twi_clk
); /* enable peripheral clock */
233 at91_twi_hwinit(); /* initialize TWI controller */
235 rc
= i2c_add_numbered_adapter(adapter
);
237 dev_err(&pdev
->dev
, "Adapter %s registration failed\n",
242 dev_info(&pdev
->dev
, "AT91 i2c bus driver.\n");
246 platform_set_drvdata(pdev
, NULL
);
248 clk_disable(twi_clk
);
254 release_mem_region(res
->start
, resource_size(res
));
259 static int __devexit
at91_i2c_remove(struct platform_device
*pdev
)
261 struct i2c_adapter
*adapter
= platform_get_drvdata(pdev
);
262 struct resource
*res
;
265 rc
= i2c_del_adapter(adapter
);
266 platform_set_drvdata(pdev
, NULL
);
268 res
= platform_get_resource(pdev
, IORESOURCE_MEM
, 0);
270 release_mem_region(res
->start
, resource_size(res
));
272 clk_disable(twi_clk
); /* disable peripheral clock */
280 /* NOTE: could save a few mA by keeping clock off outside of at91_xfer... */
282 static int at91_i2c_suspend(struct platform_device
*pdev
, pm_message_t mesg
)
284 clk_disable(twi_clk
);
288 static int at91_i2c_resume(struct platform_device
*pdev
)
290 return clk_enable(twi_clk
);
294 #define at91_i2c_suspend NULL
295 #define at91_i2c_resume NULL
298 /* work with "modprobe at91_i2c" from hotplugging or coldplugging */
299 MODULE_ALIAS("platform:at91_i2c");
301 static struct platform_driver at91_i2c_driver
= {
302 .probe
= at91_i2c_probe
,
303 .remove
= __devexit_p(at91_i2c_remove
),
304 .suspend
= at91_i2c_suspend
,
305 .resume
= at91_i2c_resume
,
308 .owner
= THIS_MODULE
,
312 static int __init
at91_i2c_init(void)
314 return platform_driver_register(&at91_i2c_driver
);
317 static void __exit
at91_i2c_exit(void)
319 platform_driver_unregister(&at91_i2c_driver
);
322 module_init(at91_i2c_init
);
323 module_exit(at91_i2c_exit
);
325 MODULE_AUTHOR("Rick Bronson");
326 MODULE_DESCRIPTION("I2C (TWI) driver for Atmel AT91");
327 MODULE_LICENSE("GPL");