11 #include <linux/module.h>
12 #include <linux/kernel.h>
14 #include <linux/i2c.h>
15 #include <linux/slab.h>
31 #define TWI_I2C_MODE_STANDARD 1
32 #define TWI_I2C_MODE_STANDARDSUB 2
33 #define TWI_I2C_MODE_COMBINED 3
34 #define TWI_I2C_MODE_REPEAT 4
36 static void bfin_twi_handle_interrupt(
struct bfin_twi_iface *iface,
37 unsigned short twi_int_status)
39 unsigned short mast_stat = read_MASTER_STAT(iface);
45 write_XMT_DATA8(iface, *(iface->
transPtr++));
52 write_MASTER_CTL(iface,
53 read_MASTER_CTL(iface) |
MDIR);
55 write_MASTER_CTL(iface,
56 read_MASTER_CTL(iface) |
STOP);
60 write_MASTER_CTL(iface,
61 read_MASTER_CTL(iface) |
MDIR);
63 write_MASTER_CTL(iface,
64 read_MASTER_CTL(iface) & ~
MDIR);
70 *(iface->
transPtr) = read_RCV_DATA8(iface);
91 read_RCV_DATA16(iface);
92 write_MASTER_CTL(iface,
93 read_MASTER_CTL(iface) |
STOP);
97 write_MASTER_CTL(iface,
98 read_MASTER_CTL(iface) |
MDIR);
100 write_MASTER_CTL(iface,
101 read_MASTER_CTL(iface) & ~
MDIR);
105 if (twi_int_status &
MERR) {
106 write_INT_MASK(iface, 0);
107 write_MASTER_STAT(iface, 0x3e);
108 write_MASTER_CTL(iface, 0);
113 if (mast_stat &
ANAK)
114 dev_dbg(&iface->
adap.dev,
"Address Not Acknowledged\n");
115 if (mast_stat &
DNAK)
116 dev_dbg(&iface->
adap.dev,
"Data Not Acknowledged\n");
127 if (read_MASTER_STAT(iface) &
SDASEN) {
130 write_MASTER_CTL(iface,
SCLOVR);
132 write_MASTER_CTL(iface, 0);
134 }
while ((read_MASTER_STAT(iface) & SDASEN) && cnt--);
138 write_MASTER_CTL(iface,
SDAOVR);
140 write_MASTER_CTL(iface, 0);
148 (twi_int_status &
MCOMP) && (mast_stat & DNAK))
154 if (twi_int_status &
MCOMP) {
155 if (twi_int_status & (XMTSERV | RCVSERV) &&
156 (read_MASTER_CTL(iface) &
MEN) == 0 &&
160 write_INT_MASK(iface, 0);
161 write_MASTER_CTL(iface, 0);
169 write_MASTER_CTL(iface,
170 read_MASTER_CTL(iface) | (0xff << 6));
175 write_MASTER_CTL(iface,
176 (read_MASTER_CTL(iface) &
181 write_MASTER_CTL(iface,
182 read_MASTER_CTL(iface) & ~
RSTART);
190 write_MASTER_ADDR(iface,
198 write_XMT_DATA8(iface,
205 write_MASTER_CTL(iface,
206 (read_MASTER_CTL(iface) &
211 write_MASTER_CTL(iface,
212 (read_MASTER_CTL(iface) |
218 write_MASTER_CTL(iface,
219 read_MASTER_CTL(iface) & ~
RSTART);
222 write_INT_MASK(iface, 0);
223 write_MASTER_CTL(iface, 0);
234 unsigned short twi_int_status;
238 twi_int_status = read_INT_STAT(iface);
242 write_INT_STAT(iface, twi_int_status);
243 bfin_twi_handle_interrupt(iface, twi_int_status);
246 spin_unlock_irqrestore(&iface->
lock, flags);
260 if (!(read_CONTROL(iface) &
TWI_ENA))
263 if (read_MASTER_STAT(iface) &
BUSBUSY)
272 dev_err(&adap->
dev,
"10 bits addr not supported!\n");
282 init_completion(&(iface->
complete));
284 write_MASTER_ADDR(iface, pmsg->
addr);
289 write_FIFO_CTL(iface, 0x3);
291 write_FIFO_CTL(iface, 0);
300 write_XMT_DATA8(iface, *(iface->
transPtr++));
313 if (pmsg->
len <= 255)
314 write_MASTER_CTL(iface, pmsg->
len << 6);
316 write_MASTER_CTL(iface, 0xff << 6);
321 write_MASTER_CTL(iface, read_MASTER_CTL(iface) |
MEN |
324 ((CONFIG_I2C_BLACKFIN_TWI_CLK_KHZ > 100) ?
FAST : 0));
331 dev_err(&adap->
dev,
"master transfer timeout\n");
346 static int bfin_twi_master_xfer(
struct i2c_adapter *adap,
349 return bfin_twi_do_master_xfer(adap, msgs, num);
356 unsigned short flags,
char read_write,
362 if (!(read_CONTROL(iface) & TWI_ENA))
365 if (read_MASTER_STAT(iface) & BUSBUSY)
443 init_completion(&(iface->
complete));
448 write_FIFO_CTL(iface, 0x3);
450 write_FIFO_CTL(iface, 0);
456 write_MASTER_ADDR(iface, addr);
461 write_XMT_DATA8(iface, iface->
command);
468 write_MASTER_CTL(iface, (iface->
writeNum + 1) << 6);
470 write_MASTER_CTL(iface, 0xff << 6);
474 write_MASTER_CTL(iface, read_MASTER_CTL(iface) |
MEN |
475 ((CONFIG_I2C_BLACKFIN_TWI_CLK_KHZ>100) ?
FAST : 0));
478 write_XMT_DATA8(iface, iface->
command);
483 write_MASTER_CTL(iface, (iface->
writeNum + 1) << 6);
485 write_MASTER_CTL(iface, 0x1 << 6);
487 write_MASTER_CTL(iface, read_MASTER_CTL(iface) |
MEN |
RSTART |
488 ((CONFIG_I2C_BLACKFIN_TWI_CLK_KHZ>100) ?
FAST : 0));
491 write_MASTER_CTL(iface, 0);
498 write_XMT_DATA8(iface,
501 write_MASTER_CTL(iface,
504 write_MASTER_CTL(iface,
510 write_XMT_DATA8(iface, iface->
command);
511 write_MASTER_CTL(iface, 1 << 6);
515 write_MASTER_CTL(iface,
517 else if (iface->
readNum > 255) {
518 write_MASTER_CTL(iface, 0xff << 6);
530 write_MASTER_CTL(iface, read_MASTER_CTL(iface) |
MEN |
532 ((CONFIG_I2C_BLACKFIN_TWI_CLK_KHZ > 100) ?
FAST : 0));
541 dev_err(&adap->
dev,
"smbus transfer timeout\n");
545 rc = (iface->
result >= 0) ? 0 : -1;
558 read_write, command, size, data);
573 .master_xfer = bfin_twi_master_xfer,
575 .functionality = bfin_twi_functionality,
578 static int i2c_bfin_twi_suspend(
struct device *
dev)
593 static int i2c_bfin_twi_resume(
struct device *
dev)
600 dev_err(dev,
"Can't get IRQ %d !\n", iface->
irq);
614 i2c_bfin_twi_suspend, i2c_bfin_twi_resume);
622 unsigned int clkhilow;
626 dev_err(&pdev->
dev,
"Cannot allocate memory\n");
628 goto out_error_nomem;
636 dev_err(&pdev->
dev,
"Cannot get IORESOURCE_MEM\n");
638 goto out_error_get_res;
645 goto out_error_ioremap;
649 if (iface->
irq < 0) {
652 goto out_error_no_irq;
655 p_adap = &iface->
adap;
656 p_adap->
nr = pdev->
id;
658 p_adap->
algo = &bfin_twi_algorithm;
661 p_adap->
dev.parent = &pdev->
dev;
668 dev_err(&pdev->
dev,
"Can't setup pin mux!\n");
669 goto out_error_pin_mux;
673 0, pdev->
name, iface);
677 goto out_error_req_irq;
681 write_CONTROL(iface, ((
get_sclk() / 1000 / 1000 + 5) / 10) & 0x7F);
687 clkhilow = ((10 * 1000 / CONFIG_I2C_BLACKFIN_TWI_CLK_KHZ) + 1) / 2;
690 write_CLKDIV(iface, (clkhilow << 8) | clkhilow);
693 write_CONTROL(iface, read_CONTROL(iface) | TWI_ENA);
698 dev_err(&pdev->
dev,
"Can't add i2c adapter!\n");
699 goto out_error_add_adapter;
702 platform_set_drvdata(pdev, iface);
704 dev_info(&pdev->
dev,
"Blackfin BF5xx on-chip I2C TWI Contoller, "
709 out_error_add_adapter:
727 platform_set_drvdata(pdev,
NULL);
739 .probe = i2c_bfin_twi_probe,
740 .remove = i2c_bfin_twi_remove,
742 .name =
"i2c-bfin-twi",
744 .pm = &i2c_bfin_twi_pm,
748 static int __init i2c_bfin_twi_init(
void)
753 static void __exit i2c_bfin_twi_exit(
void)