diff options
Diffstat (limited to 'drivers/i2c/busses/i2c-bfin-twi.c')
-rw-r--r-- | drivers/i2c/busses/i2c-bfin-twi.c | 47 |
1 files changed, 27 insertions, 20 deletions
diff --git a/drivers/i2c/busses/i2c-bfin-twi.c b/drivers/i2c/busses/i2c-bfin-twi.c index 05080c449c6b..13ea1c29873d 100644 --- a/drivers/i2c/busses/i2c-bfin-twi.c +++ b/drivers/i2c/busses/i2c-bfin-twi.c | |||
@@ -39,33 +39,40 @@ static void bfin_twi_handle_interrupt(struct bfin_twi_iface *iface, | |||
39 | unsigned short mast_stat = read_MASTER_STAT(iface); | 39 | unsigned short mast_stat = read_MASTER_STAT(iface); |
40 | 40 | ||
41 | if (twi_int_status & XMTSERV) { | 41 | if (twi_int_status & XMTSERV) { |
42 | if (iface->writeNum <= 0) { | ||
43 | /* start receive immediately after complete sending in | ||
44 | * combine mode. | ||
45 | */ | ||
46 | if (iface->cur_mode == TWI_I2C_MODE_COMBINED) | ||
47 | write_MASTER_CTL(iface, | ||
48 | read_MASTER_CTL(iface) | MDIR); | ||
49 | else if (iface->manual_stop) | ||
50 | write_MASTER_CTL(iface, | ||
51 | read_MASTER_CTL(iface) | STOP); | ||
52 | else if (iface->cur_mode == TWI_I2C_MODE_REPEAT && | ||
53 | iface->cur_msg + 1 < iface->msg_num) { | ||
54 | if (iface->pmsg[iface->cur_msg + 1].flags & | ||
55 | I2C_M_RD) | ||
56 | write_MASTER_CTL(iface, | ||
57 | read_MASTER_CTL(iface) | | ||
58 | MDIR); | ||
59 | else | ||
60 | write_MASTER_CTL(iface, | ||
61 | read_MASTER_CTL(iface) & | ||
62 | ~MDIR); | ||
63 | } | ||
64 | } | ||
42 | /* Transmit next data */ | 65 | /* Transmit next data */ |
43 | if (iface->writeNum > 0) { | 66 | while (iface->writeNum > 0 && |
67 | (read_FIFO_STAT(iface) & XMTSTAT) != XMT_FULL) { | ||
44 | SSYNC(); | 68 | SSYNC(); |
45 | write_XMT_DATA8(iface, *(iface->transPtr++)); | 69 | write_XMT_DATA8(iface, *(iface->transPtr++)); |
46 | iface->writeNum--; | 70 | iface->writeNum--; |
47 | } | 71 | } |
48 | /* start receive immediately after complete sending in | ||
49 | * combine mode. | ||
50 | */ | ||
51 | else if (iface->cur_mode == TWI_I2C_MODE_COMBINED) | ||
52 | write_MASTER_CTL(iface, | ||
53 | read_MASTER_CTL(iface) | MDIR); | ||
54 | else if (iface->manual_stop) | ||
55 | write_MASTER_CTL(iface, | ||
56 | read_MASTER_CTL(iface) | STOP); | ||
57 | else if (iface->cur_mode == TWI_I2C_MODE_REPEAT && | ||
58 | iface->cur_msg + 1 < iface->msg_num) { | ||
59 | if (iface->pmsg[iface->cur_msg + 1].flags & I2C_M_RD) | ||
60 | write_MASTER_CTL(iface, | ||
61 | read_MASTER_CTL(iface) | MDIR); | ||
62 | else | ||
63 | write_MASTER_CTL(iface, | ||
64 | read_MASTER_CTL(iface) & ~MDIR); | ||
65 | } | ||
66 | } | 72 | } |
67 | if (twi_int_status & RCVSERV) { | 73 | if (twi_int_status & RCVSERV) { |
68 | if (iface->readNum > 0) { | 74 | while (iface->readNum > 0 && |
75 | (read_FIFO_STAT(iface) & RCVSTAT)) { | ||
69 | /* Receive next data */ | 76 | /* Receive next data */ |
70 | *(iface->transPtr) = read_RCV_DATA8(iface); | 77 | *(iface->transPtr) = read_RCV_DATA8(iface); |
71 | if (iface->cur_mode == TWI_I2C_MODE_COMBINED) { | 78 | if (iface->cur_mode == TWI_I2C_MODE_COMBINED) { |