Merge branch 'I2C_SEQUENTIAL_COMMUNICATION_REWORK' of git://github.com/ABOSTM/mbed-os into dev_rollup

pull/11366/head
Martin Kojtal 2019-08-28 18:36:53 +01:00
commit 104f9281c4
6 changed files with 73 additions and 25 deletions

View File

@ -2592,7 +2592,7 @@ HAL_StatusTypeDef HAL_I2C_Master_Sequential_Transmit_IT(I2C_HandleTypeDef *hi2c,
/* Prepare transfer parameters */
hi2c->pBuffPtr = pData;
hi2c->XferCount = Size;
hi2c->XferOptions = (XferOptions & (~I2C_RELOAD_MODE));
hi2c->XferOptions = XferOptions;
hi2c->XferISR = I2C_Master_ISR_IT;
/* If size > MAX_NBYTE_SIZE, use reload mode */
@ -2658,7 +2658,7 @@ HAL_StatusTypeDef HAL_I2C_Master_Sequential_Receive_IT(I2C_HandleTypeDef *hi2c,
/* Prepare transfer parameters */
hi2c->pBuffPtr = pData;
hi2c->XferCount = Size;
hi2c->XferOptions = (XferOptions & (~I2C_RELOAD_MODE));
hi2c->XferOptions = XferOptions;
hi2c->XferISR = I2C_Master_ISR_IT;
/* If hi2c->XferCount > MAX_NBYTE_SIZE, use reload mode */

View File

@ -2592,7 +2592,7 @@ HAL_StatusTypeDef HAL_I2C_Master_Sequential_Transmit_IT(I2C_HandleTypeDef *hi2c,
/* Prepare transfer parameters */
hi2c->pBuffPtr = pData;
hi2c->XferCount = Size;
hi2c->XferOptions = (XferOptions & (~I2C_RELOAD_MODE)); // MBED patch
hi2c->XferOptions = XferOptions;
hi2c->XferISR = I2C_Master_ISR_IT;
/* If size > MAX_NBYTE_SIZE, use reload mode */
@ -2666,7 +2666,7 @@ HAL_StatusTypeDef HAL_I2C_Master_Sequential_Receive_IT(I2C_HandleTypeDef *hi2c,
/* Prepare transfer parameters */
hi2c->pBuffPtr = pData;
hi2c->XferCount = Size;
hi2c->XferOptions = (XferOptions & (~I2C_RELOAD_MODE)); // MBED patch
hi2c->XferOptions = XferOptions;
hi2c->XferISR = I2C_Master_ISR_IT;
/* If hi2c->XferCount > MAX_NBYTE_SIZE, use reload mode */

View File

@ -2598,7 +2598,7 @@ HAL_StatusTypeDef HAL_I2C_Master_Sequential_Transmit_IT(I2C_HandleTypeDef *hi2c,
/* Prepare transfer parameters */
hi2c->pBuffPtr = pData;
hi2c->XferCount = Size;
hi2c->XferOptions = (XferOptions & (~I2C_RELOAD_MODE)); // MBED: changed
hi2c->XferOptions = XferOptions;
hi2c->XferISR = I2C_Master_ISR_IT;
/* If size > MAX_NBYTE_SIZE, use reload mode */
@ -2672,7 +2672,7 @@ HAL_StatusTypeDef HAL_I2C_Master_Sequential_Receive_IT(I2C_HandleTypeDef *hi2c,
/* Prepare transfer parameters */
hi2c->pBuffPtr = pData;
hi2c->XferCount = Size;
hi2c->XferOptions = (XferOptions & (~I2C_RELOAD_MODE)); // MBED: changed
hi2c->XferOptions = XferOptions;
hi2c->XferISR = I2C_Master_ISR_IT;
/* If hi2c->XferCount > MAX_NBYTE_SIZE, use reload mode */

View File

@ -2592,7 +2592,7 @@ HAL_StatusTypeDef HAL_I2C_Master_Sequential_Transmit_IT(I2C_HandleTypeDef *hi2c,
/* Prepare transfer parameters */
hi2c->pBuffPtr = pData;
hi2c->XferCount = Size;
hi2c->XferOptions = (XferOptions & (~I2C_RELOAD_MODE)); // MBED commit 23926a2418
hi2c->XferOptions = XferOptions;
hi2c->XferISR = I2C_Master_ISR_IT;
/* If size > MAX_NBYTE_SIZE, use reload mode */
@ -2666,7 +2666,7 @@ HAL_StatusTypeDef HAL_I2C_Master_Sequential_Receive_IT(I2C_HandleTypeDef *hi2c,
/* Prepare transfer parameters */
hi2c->pBuffPtr = pData;
hi2c->XferCount = Size;
hi2c->XferOptions = (XferOptions & (~I2C_RELOAD_MODE)); // MBED commit 23926a2418
hi2c->XferOptions = XferOptions;
hi2c->XferISR = I2C_Master_ISR_IT;
/* If hi2c->XferCount > MAX_NBYTE_SIZE, use reload mode */

View File

@ -3173,8 +3173,7 @@ HAL_StatusTypeDef HAL_I2C_Master_Seq_Transmit_IT(I2C_HandleTypeDef *hi2c, uint16
/* Prepare transfer parameters */
hi2c->pBuffPtr = pData;
hi2c->XferCount = Size;
// Added for MBED PR #3324
hi2c->XferOptions = (XferOptions & (~I2C_RELOAD_MODE));
hi2c->XferOptions = XferOptions;
hi2c->XferISR = I2C_Master_ISR_IT;
/* If hi2c->XferCount > MAX_NBYTE_SIZE, use reload mode */
@ -3420,8 +3419,7 @@ HAL_StatusTypeDef HAL_I2C_Master_Seq_Receive_IT(I2C_HandleTypeDef *hi2c, uint16_
/* Prepare transfer parameters */
hi2c->pBuffPtr = pData;
hi2c->XferCount = Size;
// Added for MBED PR #3324
hi2c->XferOptions = (XferOptions & (~I2C_RELOAD_MODE));
hi2c->XferOptions = XferOptions;
hi2c->XferISR = I2C_Master_ISR_IT;
/* If hi2c->XferCount > MAX_NBYTE_SIZE, use reload mode */

View File

@ -40,6 +40,7 @@
#include "pinmap.h"
#include "PeripheralPins.h"
#include "i2c_device.h" // family specific defines
#include "mbed_error.h"
#ifndef DEBUG_STDIO
# define DEBUG_STDIO 0
@ -597,8 +598,6 @@ int i2c_stop(i2c_t *obj)
return 0;
}
#endif
// Disable reload mode
handle->Instance->CR2 &= (uint32_t)~I2C_CR2_RELOAD;
// Ensure the transmission is started before sending a stop
if ((handle->Instance->CR2 & (uint32_t)I2C_CR2_RD_WRN) == 0) {
@ -611,7 +610,7 @@ int i2c_stop(i2c_t *obj)
}
// Generate the STOP condition
handle->Instance->CR2 |= I2C_CR2_STOP;
handle->Instance->CR2 = I2C_CR2_STOP;
timeout = FLAG_TIMEOUT;
while (!__HAL_I2C_GET_FLAG(handle, I2C_FLAG_STOPF)) {
@ -664,9 +663,16 @@ int i2c_byte_read(i2c_t *obj, int last)
}
}
/* Enable reload mode as we don't know how many bytes will be sent */
/* and set transfer size to 1 */
tmpreg |= I2C_CR2_RELOAD | (I2C_CR2_NBYTES & (1 << 16));
if (last) {
/* Disable Address Acknowledge */
tmpreg = tmpreg & (~I2C_CR2_RELOAD);
tmpreg |= I2C_CR2_NACK | (I2C_CR2_NBYTES & (1 << 16));
} else {
/* Enable reload mode as we don't know how many bytes will be sent */
/* and set transfer size to 1 */
tmpreg |= I2C_CR2_RELOAD | (I2C_CR2_NBYTES & (1 << 16));
}
/* Set the prepared configuration */
handle->Instance->CR2 = tmpreg;
@ -680,11 +686,6 @@ int i2c_byte_read(i2c_t *obj, int last)
/* Then Get Byte */
data = handle->Instance->RXDR;
if (last) {
/* Disable Address Acknowledge */
handle->Instance->CR2 |= I2C_CR2_NACK;
}
return data;
}
@ -760,7 +761,7 @@ int i2c_read(i2c_t *obj, int address, char *data, int length, int stop)
I2C_HandleTypeDef *handle = &(obj_s->handle);
int count = I2C_ERROR_BUS_BUSY, ret = 0;
uint32_t timeout = 0;
#if defined(I2C_IP_VERSION_V1)
// Trick to remove compiler warning "left and right operands are identical" in some cases
uint32_t op1 = I2C_FIRST_AND_LAST_FRAME;
uint32_t op2 = I2C_LAST_FRAME;
@ -778,6 +779,18 @@ int i2c_read(i2c_t *obj, int address, char *data, int length, int stop)
obj_s->XferOperation = I2C_NEXT_FRAME;
}
}
#elif defined(I2C_IP_VERSION_V2)
if ((obj_s->XferOperation == I2C_FIRST_FRAME) || (obj_s->XferOperation == I2C_FIRST_AND_LAST_FRAME) || (obj_s->XferOperation == I2C_LAST_FRAME)) {
if (stop) {
obj_s->XferOperation = I2C_FIRST_AND_LAST_FRAME;
} else {
obj_s->XferOperation = I2C_FIRST_FRAME;
}
} else {
// should not happend
error("I2C: abnormal case should not happend");
}
#endif
obj_s->event = 0;
@ -818,6 +831,7 @@ int i2c_write(i2c_t *obj, int address, const char *data, int length, int stop)
int count = I2C_ERROR_BUS_BUSY, ret = 0;
uint32_t timeout = 0;
#if defined(I2C_IP_VERSION_V1)
// Trick to remove compiler warning "left and right operands are identical" in some cases
uint32_t op1 = I2C_FIRST_AND_LAST_FRAME;
uint32_t op2 = I2C_LAST_FRAME;
@ -835,6 +849,18 @@ int i2c_write(i2c_t *obj, int address, const char *data, int length, int stop)
obj_s->XferOperation = I2C_NEXT_FRAME;
}
}
#elif defined(I2C_IP_VERSION_V2)
if ((obj_s->XferOperation == I2C_FIRST_FRAME) || (obj_s->XferOperation == I2C_FIRST_AND_LAST_FRAME) || (obj_s->XferOperation == I2C_LAST_FRAME)) {
if (stop) {
obj_s->XferOperation = I2C_FIRST_AND_LAST_FRAME;
} else {
obj_s->XferOperation = I2C_FIRST_FRAME;
}
} else {
// should not happend
error("I2C: abnormal case should not happend");
}
#endif
obj_s->event = 0;
@ -874,11 +900,19 @@ void HAL_I2C_MasterTxCpltCallback(I2C_HandleTypeDef *hi2c)
#if DEVICE_I2C_ASYNCH
/* Handle potential Tx/Rx use case */
if ((obj->tx_buff.length) && (obj->rx_buff.length)) {
#if defined(I2C_IP_VERSION_V1)
if (obj_s->stop) {
obj_s->XferOperation = I2C_LAST_FRAME;
} else {
obj_s->XferOperation = I2C_NEXT_FRAME;
}
#elif defined(I2C_IP_VERSION_V2)
if (obj_s->stop) {
obj_s->XferOperation = I2C_FIRST_AND_LAST_FRAME;
} else {
obj_s->XferOperation = I2C_FIRST_FRAME;
}
#endif
HAL_I2C_Master_Sequential_Receive_IT(hi2c, obj_s->address, (uint8_t *)obj->rx_buff.buffer, obj->rx_buff.length, obj_s->XferOperation);
} else
@ -1143,6 +1177,7 @@ void i2c_transfer_asynch(i2c_t *obj, const void *tx, size_t tx_length, void *rx,
/* Set operation step depending if stop sending required or not */
if ((tx_length && !rx_length) || (!tx_length && rx_length)) {
#if defined(I2C_IP_VERSION_V1)
// Trick to remove compiler warning "left and right operands are identical" in some cases
uint32_t op1 = I2C_FIRST_AND_LAST_FRAME;
uint32_t op2 = I2C_LAST_FRAME;
@ -1160,7 +1195,18 @@ void i2c_transfer_asynch(i2c_t *obj, const void *tx, size_t tx_length, void *rx,
obj_s->XferOperation = I2C_NEXT_FRAME;
}
}
#elif defined(I2C_IP_VERSION_V2)
if ((obj_s->XferOperation == I2C_FIRST_FRAME) || (obj_s->XferOperation == I2C_FIRST_AND_LAST_FRAME) || (obj_s->XferOperation == I2C_LAST_FRAME)) {
if (stop) {
obj_s->XferOperation = I2C_FIRST_AND_LAST_FRAME;
} else {
obj_s->XferOperation = I2C_FIRST_FRAME;
}
} else {
// should not happend
error("I2C: abnormal case should not happend");
}
#endif
if (tx_length > 0) {
HAL_I2C_Master_Sequential_Transmit_IT(handle, address, (uint8_t *)tx, tx_length, obj_s->XferOperation);
}
@ -1169,6 +1215,7 @@ void i2c_transfer_asynch(i2c_t *obj, const void *tx, size_t tx_length, void *rx,
}
} else if (tx_length && rx_length) {
/* Two steps operation, don't modify XferOperation, keep it for next step */
#if defined(I2C_IP_VERSION_V1)
// Trick to remove compiler warning "left and right operands are identical" in some cases
uint32_t op1 = I2C_FIRST_AND_LAST_FRAME;
uint32_t op2 = I2C_LAST_FRAME;
@ -1178,6 +1225,9 @@ void i2c_transfer_asynch(i2c_t *obj, const void *tx, size_t tx_length, void *rx,
(obj_s->XferOperation == I2C_NEXT_FRAME)) {
HAL_I2C_Master_Sequential_Transmit_IT(handle, address, (uint8_t *)tx, tx_length, I2C_NEXT_FRAME);
}
#elif defined(I2C_IP_VERSION_V2)
HAL_I2C_Master_Sequential_Transmit_IT(handle, address, (uint8_t *)tx, tx_length, I2C_FIRST_FRAME);
#endif
}
}