Added error handling to WSPI driver, now LLDs can report error conditions to upper layers.
git-svn-id: svn://svn.code.sf.net/p/chibios/svn/trunk@13061 27425a3e-05d8-49a3-a47f-9c15f0e5edd8
This commit is contained in:
parent
3ea7ec6586
commit
375722180b
|
@ -140,6 +140,10 @@ struct hal_wspi_config {
|
||||||
* @brief Operation complete callback or @p NULL.
|
* @brief Operation complete callback or @p NULL.
|
||||||
*/
|
*/
|
||||||
wspicallback_t end_cb;
|
wspicallback_t end_cb;
|
||||||
|
/**
|
||||||
|
* @brief Operation error callback or @p NULL.
|
||||||
|
*/
|
||||||
|
wspicallback_t error_cb;
|
||||||
/* End of the mandatory fields.*/
|
/* End of the mandatory fields.*/
|
||||||
wspi_lld_config_fields;
|
wspi_lld_config_fields;
|
||||||
};
|
};
|
||||||
|
@ -356,13 +360,13 @@ struct hal_wspi_driver {
|
||||||
*
|
*
|
||||||
* @notapi
|
* @notapi
|
||||||
*/
|
*/
|
||||||
#define _wspi_wakeup_isr(wspip) { \
|
#define _wspi_wakeup_isr(wspip, msg) { \
|
||||||
osalSysLockFromISR(); \
|
osalSysLockFromISR(); \
|
||||||
osalThreadResumeI(&(wspip)->thread, MSG_OK); \
|
osalThreadResumeI(&(wspip)->thread, msg); \
|
||||||
osalSysUnlockFromISR(); \
|
osalSysUnlockFromISR(); \
|
||||||
}
|
}
|
||||||
#else /* !WSPI_USE_WAIT */
|
#else /* !WSPI_USE_WAIT */
|
||||||
#define _wspi_wakeup_isr(wspip)
|
#define _wspi_wakeup_isr(wspip, msg)
|
||||||
#endif /* !WSPI_USE_WAIT */
|
#endif /* !WSPI_USE_WAIT */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -388,7 +392,33 @@ struct hal_wspi_driver {
|
||||||
} \
|
} \
|
||||||
else \
|
else \
|
||||||
(wspip)->state = WSPI_READY; \
|
(wspip)->state = WSPI_READY; \
|
||||||
_wspi_wakeup_isr(wspip); \
|
_wspi_wakeup_isr(wspip, MSG_OK); \
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Common error ISR code.
|
||||||
|
* @details This code handles the portable part of the ISR code:
|
||||||
|
* - Callback invocation.
|
||||||
|
* - Waiting thread wakeup, if any.
|
||||||
|
* - Driver state transitions.
|
||||||
|
* .
|
||||||
|
* @note This macro is meant to be used in the low level drivers
|
||||||
|
* implementation only.
|
||||||
|
*
|
||||||
|
* @param[in] wspip pointer to the @p WSPIDriver object
|
||||||
|
*
|
||||||
|
* @notapi
|
||||||
|
*/
|
||||||
|
#define _wspi_error_code(wspip) { \
|
||||||
|
if ((wspip)->config->error_cb) { \
|
||||||
|
(wspip)->state = WSPI_COMPLETE; \
|
||||||
|
(wspip)->config->error_cb(wspip); \
|
||||||
|
if ((wspip)->state == WSPI_COMPLETE) \
|
||||||
|
(wspip)->state = WSPI_READY; \
|
||||||
|
} \
|
||||||
|
else \
|
||||||
|
(wspip)->state = WSPI_READY; \
|
||||||
|
_wspi_wakeup_isr(wspip, MSG_RESET); \
|
||||||
}
|
}
|
||||||
/** @} */
|
/** @} */
|
||||||
|
|
||||||
|
@ -409,10 +439,10 @@ extern "C" {
|
||||||
void wspiStartReceive(WSPIDriver *wspip, const wspi_command_t *cmdp,
|
void wspiStartReceive(WSPIDriver *wspip, const wspi_command_t *cmdp,
|
||||||
size_t n, uint8_t *rxbuf);
|
size_t n, uint8_t *rxbuf);
|
||||||
#if WSPI_USE_WAIT == TRUE
|
#if WSPI_USE_WAIT == TRUE
|
||||||
void wspiCommand(WSPIDriver *wspip, const wspi_command_t *cmdp);
|
bool wspiCommand(WSPIDriver *wspip, const wspi_command_t *cmdp);
|
||||||
void wspiSend(WSPIDriver *wspip, const wspi_command_t *cmdp,
|
bool wspiSend(WSPIDriver *wspip, const wspi_command_t *cmdp,
|
||||||
size_t n, const uint8_t *txbuf);
|
size_t n, const uint8_t *txbuf);
|
||||||
void wspiReceive(WSPIDriver *wspip, const wspi_command_t *cmdp,
|
bool wspiReceive(WSPIDriver *wspip, const wspi_command_t *cmdp,
|
||||||
size_t n, uint8_t *rxbuf);
|
size_t n, uint8_t *rxbuf);
|
||||||
#endif
|
#endif
|
||||||
#if WSPI_SUPPORTS_MEMMAP == TRUE
|
#if WSPI_SUPPORTS_MEMMAP == TRUE
|
||||||
|
|
|
@ -216,7 +216,8 @@ void wspiStartReceive(WSPIDriver *wspip, const wspi_command_t *cmdp,
|
||||||
*
|
*
|
||||||
* @api
|
* @api
|
||||||
*/
|
*/
|
||||||
void wspiCommand(WSPIDriver *wspip, const wspi_command_t *cmdp) {
|
bool wspiCommand(WSPIDriver *wspip, const wspi_command_t *cmdp) {
|
||||||
|
msg_t msg;
|
||||||
|
|
||||||
osalDbgCheck((wspip != NULL) && (cmdp != NULL));
|
osalDbgCheck((wspip != NULL) && (cmdp != NULL));
|
||||||
osalDbgCheck((cmdp->cfg & WSPI_CFG_DATA_MODE_MASK) == WSPI_CFG_DATA_MODE_NONE);
|
osalDbgCheck((cmdp->cfg & WSPI_CFG_DATA_MODE_MASK) == WSPI_CFG_DATA_MODE_NONE);
|
||||||
|
@ -227,9 +228,11 @@ void wspiCommand(WSPIDriver *wspip, const wspi_command_t *cmdp) {
|
||||||
osalDbgAssert(wspip->config->end_cb == NULL, "has callback");
|
osalDbgAssert(wspip->config->end_cb == NULL, "has callback");
|
||||||
|
|
||||||
wspiStartCommandI(wspip, cmdp);
|
wspiStartCommandI(wspip, cmdp);
|
||||||
(void) osalThreadSuspendS(&wspip->thread);
|
msg = osalThreadSuspendS(&wspip->thread);
|
||||||
|
|
||||||
osalSysUnlock();
|
osalSysUnlock();
|
||||||
|
|
||||||
|
return (bool)(msg != MSG_OK);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -243,11 +246,15 @@ void wspiCommand(WSPIDriver *wspip, const wspi_command_t *cmdp) {
|
||||||
* @param[in] cmdp pointer to the command descriptor
|
* @param[in] cmdp pointer to the command descriptor
|
||||||
* @param[in] n number of bytes to send
|
* @param[in] n number of bytes to send
|
||||||
* @param[in] txbuf the pointer to the transmit buffer
|
* @param[in] txbuf the pointer to the transmit buffer
|
||||||
|
* @return The operation status.
|
||||||
|
* @retval false if the operation succeeded.
|
||||||
|
* @retval true if the operation failed because HW issues.
|
||||||
*
|
*
|
||||||
* @api
|
* @api
|
||||||
*/
|
*/
|
||||||
void wspiSend(WSPIDriver *wspip, const wspi_command_t *cmdp,
|
bool wspiSend(WSPIDriver *wspip, const wspi_command_t *cmdp,
|
||||||
size_t n, const uint8_t *txbuf) {
|
size_t n, const uint8_t *txbuf) {
|
||||||
|
msg_t msg;
|
||||||
|
|
||||||
osalDbgCheck((wspip != NULL) && (cmdp != NULL));
|
osalDbgCheck((wspip != NULL) && (cmdp != NULL));
|
||||||
osalDbgCheck((n > 0U) && (txbuf != NULL));
|
osalDbgCheck((n > 0U) && (txbuf != NULL));
|
||||||
|
@ -259,9 +266,11 @@ void wspiSend(WSPIDriver *wspip, const wspi_command_t *cmdp,
|
||||||
osalDbgAssert(wspip->config->end_cb == NULL, "has callback");
|
osalDbgAssert(wspip->config->end_cb == NULL, "has callback");
|
||||||
|
|
||||||
wspiStartSendI(wspip, cmdp, n, txbuf);
|
wspiStartSendI(wspip, cmdp, n, txbuf);
|
||||||
(void) osalThreadSuspendS(&wspip->thread);
|
msg = osalThreadSuspendS(&wspip->thread);
|
||||||
|
|
||||||
osalSysUnlock();
|
osalSysUnlock();
|
||||||
|
|
||||||
|
return (bool)(msg != MSG_OK);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -275,11 +284,15 @@ void wspiSend(WSPIDriver *wspip, const wspi_command_t *cmdp,
|
||||||
* @param[in] cmdp pointer to the command descriptor
|
* @param[in] cmdp pointer to the command descriptor
|
||||||
* @param[in] n number of bytes to send
|
* @param[in] n number of bytes to send
|
||||||
* @param[out] rxbuf the pointer to the receive buffer
|
* @param[out] rxbuf the pointer to the receive buffer
|
||||||
|
* @return The operation status.
|
||||||
|
* @retval false if the operation succeeded.
|
||||||
|
* @retval true if the operation failed because HW issues.
|
||||||
*
|
*
|
||||||
* @api
|
* @api
|
||||||
*/
|
*/
|
||||||
void wspiReceive(WSPIDriver *wspip, const wspi_command_t *cmdp,
|
bool wspiReceive(WSPIDriver *wspip, const wspi_command_t *cmdp,
|
||||||
size_t n, uint8_t *rxbuf) {
|
size_t n, uint8_t *rxbuf) {
|
||||||
|
msg_t msg;
|
||||||
|
|
||||||
osalDbgCheck((wspip != NULL) && (cmdp != NULL));
|
osalDbgCheck((wspip != NULL) && (cmdp != NULL));
|
||||||
osalDbgCheck((n > 0U) && (rxbuf != NULL));
|
osalDbgCheck((n > 0U) && (rxbuf != NULL));
|
||||||
|
@ -291,9 +304,11 @@ void wspiReceive(WSPIDriver *wspip, const wspi_command_t *cmdp,
|
||||||
osalDbgAssert(wspip->config->end_cb == NULL, "has callback");
|
osalDbgAssert(wspip->config->end_cb == NULL, "has callback");
|
||||||
|
|
||||||
wspiStartReceiveI(wspip, cmdp, n, rxbuf);
|
wspiStartReceiveI(wspip, cmdp, n, rxbuf);
|
||||||
(void) osalThreadSuspendS(&wspip->thread);
|
msg = osalThreadSuspendS(&wspip->thread);
|
||||||
|
|
||||||
osalSysUnlock();
|
osalSysUnlock();
|
||||||
|
|
||||||
|
return (bool)(msg != MSG_OK);
|
||||||
}
|
}
|
||||||
#endif /* WSPI_USE_WAIT == TRUE */
|
#endif /* WSPI_USE_WAIT == TRUE */
|
||||||
|
|
||||||
|
|
|
@ -74,6 +74,8 @@
|
||||||
*****************************************************************************
|
*****************************************************************************
|
||||||
|
|
||||||
*** Next ***
|
*** Next ***
|
||||||
|
- NEW: Added error handling to WSPI driver, now LLDs can report error
|
||||||
|
conditions to upper layers.
|
||||||
- NEW: Added mcuconf.h generator for STM32G4x4.
|
- NEW: Added mcuconf.h generator for STM32G4x4.
|
||||||
- HAL: STM32 DMAv1 driver improvements and generalization, added support
|
- HAL: STM32 DMAv1 driver improvements and generalization, added support
|
||||||
for 8 channels.
|
for 8 channels.
|
||||||
|
|
|
@ -36,6 +36,7 @@
|
||||||
|
|
||||||
const WSPIConfig WSPIcfg1 = {
|
const WSPIConfig WSPIcfg1 = {
|
||||||
.end_cb = NULL,
|
.end_cb = NULL,
|
||||||
|
.error_cb = NULL,
|
||||||
.dcr = STM32_DCR_FSIZE(24U) | /* 16MB device. */
|
.dcr = STM32_DCR_FSIZE(24U) | /* 16MB device. */
|
||||||
STM32_DCR_CSHT(1U) /* NCS 2 cycles delay. */
|
STM32_DCR_CSHT(1U) /* NCS 2 cycles delay. */
|
||||||
};
|
};
|
||||||
|
|
|
@ -36,6 +36,7 @@
|
||||||
|
|
||||||
const WSPIConfig WSPIcfg1 = {
|
const WSPIConfig WSPIcfg1 = {
|
||||||
.end_cb = NULL,
|
.end_cb = NULL,
|
||||||
|
.error_cb = NULL,
|
||||||
.dcr1 = STM32_DCR1_MTYP(1U) | /* Macronix mode. */
|
.dcr1 = STM32_DCR1_MTYP(1U) | /* Macronix mode. */
|
||||||
STM32_DCR1_DEVSIZE(26U) | /* 64MB device. */
|
STM32_DCR1_DEVSIZE(26U) | /* 64MB device. */
|
||||||
STM32_DCR1_CSHT(1U), /* NCS 2 cycles delay. */
|
STM32_DCR1_CSHT(1U), /* NCS 2 cycles delay. */
|
||||||
|
|
Loading…
Reference in New Issue