mirror of https://github.com/ARMmbed/mbed-os.git
Fix I2C driver for RZ/A1H
Previously, when "length = 0" as failsafe, "return 0" is executed. But we changed so that only START bit and STOP bit are executed same as other devices.pull/3551/head
parent
3a326c0b94
commit
0236d95fed
|
|
@ -416,9 +416,6 @@ int i2c_read(i2c_t *obj, int address, char *data, int length, int stop) {
|
||||||
int value;
|
int value;
|
||||||
volatile uint32_t work_reg = 0;
|
volatile uint32_t work_reg = 0;
|
||||||
|
|
||||||
if(length <= 0) {
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
i2c_set_MR3_ACK(obj);
|
i2c_set_MR3_ACK(obj);
|
||||||
/* There is a STOP condition for last processing */
|
/* There is a STOP condition for last processing */
|
||||||
if (obj->i2c.last_stop_flag != 0) {
|
if (obj->i2c.last_stop_flag != 0) {
|
||||||
|
|
@ -448,76 +445,90 @@ int i2c_read(i2c_t *obj, int address, char *data, int length, int stop) {
|
||||||
obj->i2c.last_stop_flag = 1;
|
obj->i2c.last_stop_flag = 1;
|
||||||
return I2C_ERROR_NO_SLAVE;
|
return I2C_ERROR_NO_SLAVE;
|
||||||
}
|
}
|
||||||
/* Read in all except last byte */
|
if (length != 0) {
|
||||||
if (length > 2) {
|
/* Read in all except last byte */
|
||||||
/* dummy read */
|
if (length > 2) {
|
||||||
value = REG(DRR.UINT32);
|
/* dummy read */
|
||||||
for (count = 0; count < (length - 1); count++) {
|
value = REG(DRR.UINT32);
|
||||||
|
for (count = 0; count < (length - 1); count++) {
|
||||||
|
/* wait for it to arrive */
|
||||||
|
status = i2c_wait_RDRF(obj);
|
||||||
|
if (status != 0) {
|
||||||
|
i2c_set_err_noslave(obj);
|
||||||
|
return I2C_ERROR_NO_SLAVE;
|
||||||
|
}
|
||||||
|
/* Recieve the data */
|
||||||
|
if (count == (length - 2)) {
|
||||||
|
value = i2c_do_read(obj, 1);
|
||||||
|
} else if ((length >= 3) && (count == (length - 3))) {
|
||||||
|
value = i2c_do_read(obj, 2);
|
||||||
|
} else {
|
||||||
|
value = i2c_do_read(obj, 0);
|
||||||
|
}
|
||||||
|
data[count] = (char)value;
|
||||||
|
}
|
||||||
|
} else if (length == 2) {
|
||||||
|
/* Set MR3 WAIT bit is 1 */
|
||||||
|
REG(MR3.UINT32) |= MR3_WAIT;
|
||||||
|
/* dummy read */
|
||||||
|
value = REG(DRR.UINT32);
|
||||||
/* wait for it to arrive */
|
/* wait for it to arrive */
|
||||||
status = i2c_wait_RDRF(obj);
|
status = i2c_wait_RDRF(obj);
|
||||||
if (status != 0) {
|
if (status != 0) {
|
||||||
i2c_set_err_noslave(obj);
|
i2c_set_err_noslave(obj);
|
||||||
return I2C_ERROR_NO_SLAVE;
|
return I2C_ERROR_NO_SLAVE;
|
||||||
}
|
}
|
||||||
/* Recieve the data */
|
i2c_set_MR3_NACK(obj);
|
||||||
if (count == (length - 2)) {
|
data[count] = (char)REG(DRR.UINT32);
|
||||||
value = i2c_do_read(obj, 1);
|
count++;
|
||||||
} else if ((length >= 3) && (count == (length - 3))) {
|
} else {
|
||||||
value = i2c_do_read(obj, 2);
|
/* length == 1 */
|
||||||
} else {
|
/* Set MR3 WAIT bit is 1 */;
|
||||||
value = i2c_do_read(obj, 0);
|
REG(MR3.UINT32) |= MR3_WAIT;
|
||||||
}
|
i2c_set_MR3_NACK(obj);
|
||||||
data[count] = (char)value;
|
/* dummy read */
|
||||||
|
value = REG(DRR.UINT32);
|
||||||
}
|
}
|
||||||
} else if (length == 2) {
|
|
||||||
/* Set MR3 WAIT bit is 1 */
|
|
||||||
REG(MR3.UINT32) |= MR3_WAIT;
|
|
||||||
/* dummy read */
|
|
||||||
value = REG(DRR.UINT32);
|
|
||||||
/* wait for it to arrive */
|
/* wait for it to arrive */
|
||||||
status = i2c_wait_RDRF(obj);
|
status = i2c_wait_RDRF(obj);
|
||||||
if (status != 0) {
|
if (status != 0) {
|
||||||
i2c_set_err_noslave(obj);
|
i2c_set_err_noslave(obj);
|
||||||
return I2C_ERROR_NO_SLAVE;
|
return I2C_ERROR_NO_SLAVE;
|
||||||
}
|
}
|
||||||
i2c_set_MR3_NACK(obj);
|
|
||||||
data[count] = (char)REG(DRR.UINT32);
|
|
||||||
count++;
|
|
||||||
} else {
|
|
||||||
/* length == 1 */
|
|
||||||
/* Set MR3 WAIT bit is 1 */;
|
|
||||||
REG(MR3.UINT32) |= MR3_WAIT;
|
|
||||||
i2c_set_MR3_NACK(obj);
|
|
||||||
/* dummy read */
|
|
||||||
value = REG(DRR.UINT32);
|
|
||||||
}
|
|
||||||
/* wait for it to arrive */
|
|
||||||
status = i2c_wait_RDRF(obj);
|
|
||||||
if (status != 0) {
|
|
||||||
i2c_set_err_noslave(obj);
|
|
||||||
return I2C_ERROR_NO_SLAVE;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* If not repeated start, send stop. */
|
/* If not repeated start, send stop. */
|
||||||
if (stop) {
|
if (stop) {
|
||||||
(void)i2c_set_STOP(obj);
|
(void)i2c_set_STOP(obj);
|
||||||
/* RIICnDRR read */
|
/* RIICnDRR read */
|
||||||
value = (REG(DRR.UINT32) & 0xFF);
|
value = (REG(DRR.UINT32) & 0xFF);
|
||||||
data[count] = (char)value;
|
data[count] = (char)value;
|
||||||
/* RIICnMR3.WAIT = 0 */
|
/* RIICnMR3.WAIT = 0 */
|
||||||
REG(MR3.UINT32) &= ~MR3_WAIT;
|
REG(MR3.UINT32) &= ~MR3_WAIT;
|
||||||
(void)i2c_wait_STOP(obj);
|
(void)i2c_wait_STOP(obj);
|
||||||
i2c_set_SR2_NACKF_STOP(obj);
|
i2c_set_SR2_NACKF_STOP(obj);
|
||||||
|
} else {
|
||||||
|
(void)i2c_restart(obj);
|
||||||
|
/* RIICnDRR read */
|
||||||
|
value = (REG(DRR.UINT32) & 0xFF);
|
||||||
|
data[count] = (char)value;
|
||||||
|
/* RIICnMR3.WAIT = 0 */
|
||||||
|
REG(MR3.UINT32) &= ~MR3_WAIT;
|
||||||
|
(void)i2c_wait_START(obj);
|
||||||
|
/* SR2.START = 0 */
|
||||||
|
REG(SR2.UINT32) &= ~SR2_START;
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
(void)i2c_restart(obj);
|
/* If not repeated start, send stop. */
|
||||||
/* RIICnDRR read */
|
if (stop) {
|
||||||
value = (REG(DRR.UINT32) & 0xFF);
|
(void)i2c_set_STOP(obj);
|
||||||
data[count] = (char)value;
|
(void)i2c_wait_STOP(obj);
|
||||||
/* RIICnMR3.WAIT = 0 */
|
i2c_set_SR2_NACKF_STOP(obj);
|
||||||
REG(MR3.UINT32) &= ~MR3_WAIT;
|
} else {
|
||||||
(void)i2c_wait_START(obj);
|
(void)i2c_restart(obj);
|
||||||
/* SR2.START = 0 */
|
(void)i2c_wait_START(obj);
|
||||||
REG(SR2.UINT32) &= ~SR2_START;
|
/* SR2.START = 0 */
|
||||||
|
REG(SR2.UINT32) &= ~SR2_START;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return length;
|
return length;
|
||||||
|
|
@ -527,10 +538,6 @@ int i2c_write(i2c_t *obj, int address, const char *data, int length, int stop) {
|
||||||
int cnt;
|
int cnt;
|
||||||
int status;
|
int status;
|
||||||
|
|
||||||
if(length <= 0) {
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* There is a STOP condition for last processing */
|
/* There is a STOP condition for last processing */
|
||||||
if (obj->i2c.last_stop_flag != 0) {
|
if (obj->i2c.last_stop_flag != 0) {
|
||||||
status = i2c_start(obj);
|
status = i2c_start(obj);
|
||||||
|
|
|
||||||
|
|
@ -418,9 +418,6 @@ int i2c_read(i2c_t *obj, int address, char *data, int length, int stop) {
|
||||||
int value;
|
int value;
|
||||||
volatile uint32_t work_reg = 0;
|
volatile uint32_t work_reg = 0;
|
||||||
|
|
||||||
if(length <= 0) {
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
i2c_set_MR3_ACK(obj);
|
i2c_set_MR3_ACK(obj);
|
||||||
/* There is a STOP condition for last processing */
|
/* There is a STOP condition for last processing */
|
||||||
if (obj->last_stop_flag != 0) {
|
if (obj->last_stop_flag != 0) {
|
||||||
|
|
@ -450,76 +447,90 @@ int i2c_read(i2c_t *obj, int address, char *data, int length, int stop) {
|
||||||
obj->last_stop_flag = 1;
|
obj->last_stop_flag = 1;
|
||||||
return I2C_ERROR_NO_SLAVE;
|
return I2C_ERROR_NO_SLAVE;
|
||||||
}
|
}
|
||||||
/* Read in all except last byte */
|
if (length != 0) {
|
||||||
if (length > 2) {
|
/* Read in all except last byte */
|
||||||
/* dummy read */
|
if (length > 2) {
|
||||||
value = REG(DRR.UINT32);
|
/* dummy read */
|
||||||
for (count = 0; count < (length - 1); count++) {
|
value = REG(DRR.UINT32);
|
||||||
|
for (count = 0; count < (length - 1); count++) {
|
||||||
|
/* wait for it to arrive */
|
||||||
|
status = i2c_wait_RDRF(obj);
|
||||||
|
if (status != 0) {
|
||||||
|
i2c_set_err_noslave(obj);
|
||||||
|
return I2C_ERROR_NO_SLAVE;
|
||||||
|
}
|
||||||
|
/* Recieve the data */
|
||||||
|
if (count == (length - 2)) {
|
||||||
|
value = i2c_do_read(obj, 1);
|
||||||
|
} else if ((length >= 3) && (count == (length - 3))) {
|
||||||
|
value = i2c_do_read(obj, 2);
|
||||||
|
} else {
|
||||||
|
value = i2c_do_read(obj, 0);
|
||||||
|
}
|
||||||
|
data[count] = (char)value;
|
||||||
|
}
|
||||||
|
} else if (length == 2) {
|
||||||
|
/* Set MR3 WAIT bit is 1 */
|
||||||
|
REG(MR3.UINT32) |= MR3_WAIT;
|
||||||
|
/* dummy read */
|
||||||
|
value = REG(DRR.UINT32);
|
||||||
/* wait for it to arrive */
|
/* wait for it to arrive */
|
||||||
status = i2c_wait_RDRF(obj);
|
status = i2c_wait_RDRF(obj);
|
||||||
if (status != 0) {
|
if (status != 0) {
|
||||||
i2c_set_err_noslave(obj);
|
i2c_set_err_noslave(obj);
|
||||||
return I2C_ERROR_NO_SLAVE;
|
return I2C_ERROR_NO_SLAVE;
|
||||||
}
|
}
|
||||||
/* Recieve the data */
|
i2c_set_MR3_NACK(obj);
|
||||||
if (count == (length - 2)) {
|
data[count] = (char)REG(DRR.UINT32);
|
||||||
value = i2c_do_read(obj, 1);
|
count++;
|
||||||
} else if ((length >= 3) && (count == (length - 3))) {
|
} else {
|
||||||
value = i2c_do_read(obj, 2);
|
/* length == 1 */
|
||||||
} else {
|
/* Set MR3 WAIT bit is 1 */;
|
||||||
value = i2c_do_read(obj, 0);
|
REG(MR3.UINT32) |= MR3_WAIT;
|
||||||
}
|
i2c_set_MR3_NACK(obj);
|
||||||
data[count] = (char)value;
|
/* dummy read */
|
||||||
|
value = REG(DRR.UINT32);
|
||||||
}
|
}
|
||||||
} else if (length == 2) {
|
|
||||||
/* Set MR3 WATI bit is 1 */
|
|
||||||
REG(MR3.UINT32) |= MR3_WAIT;
|
|
||||||
/* dummy read */
|
|
||||||
value = REG(DRR.UINT32);
|
|
||||||
/* wait for it to arrive */
|
/* wait for it to arrive */
|
||||||
status = i2c_wait_RDRF(obj);
|
status = i2c_wait_RDRF(obj);
|
||||||
if (status != 0) {
|
if (status != 0) {
|
||||||
i2c_set_err_noslave(obj);
|
i2c_set_err_noslave(obj);
|
||||||
return I2C_ERROR_NO_SLAVE;
|
return I2C_ERROR_NO_SLAVE;
|
||||||
}
|
}
|
||||||
i2c_set_MR3_NACK(obj);
|
|
||||||
data[count] = (char)REG(DRR.UINT32);
|
|
||||||
count++;
|
|
||||||
} else {
|
|
||||||
/* length == 1 */
|
|
||||||
/* Set MR3 WATI bit is 1 */;
|
|
||||||
REG(MR3.UINT32) |= MR3_WAIT;
|
|
||||||
i2c_set_MR3_NACK(obj);
|
|
||||||
/* dummy read */
|
|
||||||
value = REG(DRR.UINT32);
|
|
||||||
}
|
|
||||||
/* wait for it to arrive */
|
|
||||||
status = i2c_wait_RDRF(obj);
|
|
||||||
if (status != 0) {
|
|
||||||
i2c_set_err_noslave(obj);
|
|
||||||
return I2C_ERROR_NO_SLAVE;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* If not repeated start, send stop. */
|
/* If not repeated start, send stop. */
|
||||||
if (stop) {
|
if (stop) {
|
||||||
(void)i2c_set_STOP(obj);
|
(void)i2c_set_STOP(obj);
|
||||||
/* RIICnDRR read */
|
/* RIICnDRR read */
|
||||||
value = (REG(DRR.UINT32) & 0xFF);
|
value = (REG(DRR.UINT32) & 0xFF);
|
||||||
data[count] = (char)value;
|
data[count] = (char)value;
|
||||||
/* RIICnMR3.WAIT = 0 */
|
/* RIICnMR3.WAIT = 0 */
|
||||||
REG(MR3.UINT32) &= ~MR3_WAIT;
|
REG(MR3.UINT32) &= ~MR3_WAIT;
|
||||||
(void)i2c_wait_STOP(obj);
|
(void)i2c_wait_STOP(obj);
|
||||||
i2c_set_SR2_NACKF_STOP(obj);
|
i2c_set_SR2_NACKF_STOP(obj);
|
||||||
|
} else {
|
||||||
|
(void)i2c_restart(obj);
|
||||||
|
/* RIICnDRR read */
|
||||||
|
value = (REG(DRR.UINT32) & 0xFF);
|
||||||
|
data[count] = (char)value;
|
||||||
|
/* RIICnMR3.WAIT = 0 */
|
||||||
|
REG(MR3.UINT32) &= ~MR3_WAIT;
|
||||||
|
(void)i2c_wait_START(obj);
|
||||||
|
/* SR2.START = 0 */
|
||||||
|
REG(SR2.UINT32) &= ~SR2_START;
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
(void)i2c_restart(obj);
|
/* If not repeated start, send stop. */
|
||||||
/* RIICnDRR read */
|
if (stop) {
|
||||||
value = (REG(DRR.UINT32) & 0xFF);
|
(void)i2c_set_STOP(obj);
|
||||||
data[count] = (char)value;
|
(void)i2c_wait_STOP(obj);
|
||||||
/* RIICnMR3.WAIT = 0 */
|
i2c_set_SR2_NACKF_STOP(obj);
|
||||||
REG(MR3.UINT32) &= ~MR3_WAIT;
|
} else {
|
||||||
(void)i2c_wait_START(obj);
|
(void)i2c_restart(obj);
|
||||||
/* SR2.START = 0 */
|
(void)i2c_wait_START(obj);
|
||||||
REG(SR2.UINT32) &= ~SR2_START;
|
/* SR2.START = 0 */
|
||||||
|
REG(SR2.UINT32) &= ~SR2_START;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return length;
|
return length;
|
||||||
|
|
@ -529,10 +540,6 @@ int i2c_write(i2c_t *obj, int address, const char *data, int length, int stop) {
|
||||||
int cnt;
|
int cnt;
|
||||||
int status;
|
int status;
|
||||||
|
|
||||||
if(length <= 0) {
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* There is a STOP condition for last processing */
|
/* There is a STOP condition for last processing */
|
||||||
if (obj->last_stop_flag != 0) {
|
if (obj->last_stop_flag != 0) {
|
||||||
status = i2c_start(obj);
|
status = i2c_start(obj);
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue