commit 732a4657e2ba4a3bd5b4244e06cfbae9bb2a3e56
Author: Thomas Schöpping <tschoepp@cit-ec.uni-bielefeld.de>
Date:   Mon Feb 25 13:42:39 2019 +0100

    ChibiOS updated to version stable_19.1.x.
    NOTE: ChibiOS 19.1.x seems to contain some issues as of now.

diff --git a/kernel/ChibiOS b/kernel/ChibiOS
index 5b8695c..14eea36 160000
--- a/kernel/ChibiOS
+++ b/kernel/ChibiOS
@@ -1 +1 @@
-Subproject commit 5b8695ccbd8388b7ac880d57fb1fdbc9a0d4c6ca
+Subproject commit 14eea36396e50de3f4f54a53862b130162449821
diff --git a/kernel/patches/I2C-without-DMA.patch b/kernel/patches/I2C-without-DMA.patch
index dfa6be7..d41425c 100644
--- a/kernel/patches/I2C-without-DMA.patch
+++ b/kernel/patches/I2C-without-DMA.patch
@@ -1,853 +1,818 @@
 diff --git a/os/hal/ports/STM32/LLD/I2Cv1/hal_i2c_lld.c b/os/hal/ports/STM32/LLD/I2Cv1/hal_i2c_lld.c
-index 6ade226..96c9da0 100644
 --- a/os/hal/ports/STM32/LLD/I2Cv1/hal_i2c_lld.c
 +++ b/os/hal/ports/STM32/LLD/I2Cv1/hal_i2c_lld.c
 @@ -34,6 +34,7 @@
- /* Driver local definitions.                                                 */
- /*===========================================================================*/
- 
-+#if STM32_I2C_I2C1_USE_DMA
- #define I2C1_RX_DMA_CHANNEL                                                 \
-   STM32_DMA_GETCHANNEL(STM32_I2C_I2C1_RX_DMA_STREAM,                        \
-                        STM32_I2C1_RX_DMA_CHN)
+ /* Driver local definitions.                                                 */
+ /*===========================================================================*/
+ 
++#if STM32_I2C_I2C1_USE_DMA
+ #define I2C1_RX_DMA_CHANNEL                                                 \
+   STM32_DMA_GETCHANNEL(STM32_I2C_I2C1_RX_DMA_STREAM,                        \
+                        STM32_I2C1_RX_DMA_CHN)
 @@ -41,7 +42,9 @@
- #define I2C1_TX_DMA_CHANNEL                                                 \
-   STM32_DMA_GETCHANNEL(STM32_I2C_I2C1_TX_DMA_STREAM,                        \
-                        STM32_I2C1_TX_DMA_CHN)
-+#endif
- 
-+#if STM32_I2C_I2C2_USE_DMA
- #define I2C2_RX_DMA_CHANNEL                                                 \
-   STM32_DMA_GETCHANNEL(STM32_I2C_I2C2_RX_DMA_STREAM,                        \
-                        STM32_I2C2_RX_DMA_CHN)
+ #define I2C1_TX_DMA_CHANNEL                                                 \
+   STM32_DMA_GETCHANNEL(STM32_I2C_I2C1_TX_DMA_STREAM,                        \
+                        STM32_I2C1_TX_DMA_CHN)
++#endif
+ 
++#if STM32_I2C_I2C2_USE_DMA
+ #define I2C2_RX_DMA_CHANNEL                                                 \
+   STM32_DMA_GETCHANNEL(STM32_I2C_I2C2_RX_DMA_STREAM,                        \
+                        STM32_I2C2_RX_DMA_CHN)
 @@ -49,7 +52,9 @@
- #define I2C2_TX_DMA_CHANNEL                                                 \
-   STM32_DMA_GETCHANNEL(STM32_I2C_I2C2_TX_DMA_STREAM,                        \
-                        STM32_I2C2_TX_DMA_CHN)
-+#endif
- 
-+#if STM32_I2C_I2C3_USE_DMA
- #define I2C3_RX_DMA_CHANNEL                                                 \
-   STM32_DMA_GETCHANNEL(STM32_I2C_I2C3_RX_DMA_STREAM,                        \
-                        STM32_I2C3_RX_DMA_CHN)
+ #define I2C2_TX_DMA_CHANNEL                                                 \
+   STM32_DMA_GETCHANNEL(STM32_I2C_I2C2_TX_DMA_STREAM,                        \
+                        STM32_I2C2_TX_DMA_CHN)
++#endif
+ 
++#if STM32_I2C_I2C3_USE_DMA
+ #define I2C3_RX_DMA_CHANNEL                                                 \
+   STM32_DMA_GETCHANNEL(STM32_I2C_I2C3_RX_DMA_STREAM,                        \
+                        STM32_I2C3_RX_DMA_CHN)
 @@ -57,6 +62,7 @@
- #define I2C3_TX_DMA_CHANNEL                                                 \
-   STM32_DMA_GETCHANNEL(STM32_I2C_I2C3_TX_DMA_STREAM,                        \
-                        STM32_I2C3_TX_DMA_CHN)
-+#endif
- 
- /*===========================================================================*/
- /* Driver constants.                                                         */
+ #define I2C3_TX_DMA_CHANNEL                                                 \
+   STM32_DMA_GETCHANNEL(STM32_I2C_I2C3_TX_DMA_STREAM,                        \
+                        STM32_I2C3_TX_DMA_CHN)
++#endif
+ 
+ /*===========================================================================*/
+ /* Driver constants.                                                         */
 @@ -72,6 +78,20 @@
- #define I2C_EV6_MASTER_REC_MODE_SELECTED                                    \
-   ((uint32_t)(((I2C_SR2_MSL | I2C_SR2_BUSY)<< 16) | I2C_SR1_ADDR))
- 
-+#define I2C_EV7_MASTER_REC_BYTE_RECEIVED                                    \
-+  ((uint32_t)(((I2C_SR2_MSL | I2C_SR2_BUSY)<< 16) | I2C_SR1_RXNE))
-+
-+#define I2C_EV7_MASTER_REC_BYTE_RECEIVED_STOP                               \
-+  ((uint32_t)(I2C_SR1_RXNE))
-+
-+#define I2C_EV7_2_EV7_3_MASTER_REC_BYTE_QUEUED                              \
-+  ((uint32_t)(((I2C_SR2_MSL | I2C_SR2_BUSY)<< 16) |                         \
-+              I2C_SR1_BTF | I2C_SR1_RXNE))
-+
-+#define I2C_EV8_MASTER_BYTE_TRANSMITTING                                    \
-+  ((uint32_t)(((I2C_SR2_MSL | I2C_SR2_BUSY | I2C_SR2_TRA)<< 16) |           \
-+              I2C_SR1_TXE))
-+
- #define I2C_EV8_2_MASTER_BYTE_TRANSMITTED                                   \
-   ((uint32_t)(((I2C_SR2_MSL | I2C_SR2_BUSY | I2C_SR2_TRA) << 16) |          \
-               I2C_SR1_BTF | I2C_SR1_TXE))
+ #define I2C_EV6_MASTER_REC_MODE_SELECTED                                    \
+   ((uint32_t)(((I2C_SR2_MSL | I2C_SR2_BUSY)<< 16) | I2C_SR1_ADDR))
+ 
++#define I2C_EV7_MASTER_REC_BYTE_RECEIVED                                    \
++  ((uint32_t)(((I2C_SR2_MSL | I2C_SR2_BUSY)<< 16) | I2C_SR1_RXNE))
++
++#define I2C_EV7_MASTER_REC_BYTE_RECEIVED_STOP                               \
++  ((uint32_t)(I2C_SR1_RXNE))
++
++#define I2C_EV7_2_EV7_3_MASTER_REC_BYTE_QUEUED                              \
++  ((uint32_t)(((I2C_SR2_MSL | I2C_SR2_BUSY)<< 16) |                         \
++              I2C_SR1_BTF | I2C_SR1_RXNE))
++
++#define I2C_EV8_MASTER_BYTE_TRANSMITTING                                    \
++  ((uint32_t)(((I2C_SR2_MSL | I2C_SR2_BUSY | I2C_SR2_TRA)<< 16) |           \
++              I2C_SR1_TXE))
++
+ #define I2C_EV8_2_MASTER_BYTE_TRANSMITTED                                   \
+   ((uint32_t)(((I2C_SR2_MSL | I2C_SR2_BUSY | I2C_SR2_TRA) << 16) |          \
+               I2C_SR1_BTF | I2C_SR1_TXE))
 @@ -129,8 +149,24 @@ static void i2c_lld_abort_operation(I2CDriver *i2cp) {
-   dp->SR1 = 0;
- 
-   /* Stops the associated DMA streams.*/
--  dmaStreamDisable(i2cp->dmatx);
--  dmaStreamDisable(i2cp->dmarx);
-+#if STM32_I2C_USE_I2C1 && STM32_I2C_I2C1_USE_DMA
-+  if (&I2CD1 == i2cp) {
-+    dmaStreamDisable(i2cp->dmatx);
-+    dmaStreamDisable(i2cp->dmarx);
-+  }
-+#endif
-+#if STM32_I2C_USE_I2C2 && STM32_I2C_I2C2_USE_DMA
-+  if (&I2CD2 == i2cp) {
-+    dmaStreamDisable(i2cp->dmatx);
-+    dmaStreamDisable(i2cp->dmarx);
-+  }
-+#endif
-+#if STM32_I2C_USE_I2C3 && STM32_I2C_I2C3_USE_DMA
-+  if (&I2CD3 == i2cp) {
-+    dmaStreamDisable(i2cp->dmatx);
-+    dmaStreamDisable(i2cp->dmarx);
-+  }
-+#endif
- }
- 
- /**
-@@ -236,13 +272,17 @@ static void i2c_lld_set_opmode(I2CDriver *i2cp) {
- }
- 
- /**
-- * @brief   I2C shared ISR code.
-+ * @brief   I2C shared ISR code for DMA access.
-  *
-  * @param[in] i2cp      pointer to the @p I2CDriver object
-  *
-  * @notapi
-  */
--static void i2c_lld_serve_event_interrupt(I2CDriver *i2cp) {
-+#if (STM32_I2C_USE_I2C1 && STM32_I2C_I2C1_USE_DMA) ||                       \
-+    (STM32_I2C_USE_I2C2 && STM32_I2C_I2C2_USE_DMA) ||                       \
-+    (STM32_I2C_USE_I2C3 && STM32_I2C_I2C3_USE_DMA) ||                       \
-+    defined(__DOXYGEN__)
-+static void i2c_lld_serve_event_interrupt_dma(I2CDriver *i2cp) {
-   I2C_TypeDef *dp = i2cp->i2c;
-   uint32_t regSR2 = dp->SR2;
-   uint32_t event = dp->SR1;
+   dp->SR1 = 0;
+ 
+   /* Stops the associated DMA streams.*/
+-  dmaStreamDisable(i2cp->dmatx);
+-  dmaStreamDisable(i2cp->dmarx);
++#if STM32_I2C_USE_I2C1 && STM32_I2C_I2C1_USE_DMA
++  if (&I2CD1 == i2cp) {
++    dmaStreamDisable(i2cp->dmatx);
++    dmaStreamDisable(i2cp->dmarx);
++  }
++#endif
++#if STM32_I2C_USE_I2C2 && STM32_I2C_I2C2_USE_DMA
++  if (&I2CD2 == i2cp) {
++    dmaStreamDisable(i2cp->dmatx);
++    dmaStreamDisable(i2cp->dmarx);
++  }
++#endif
++#if STM32_I2C_USE_I2C3 && STM32_I2C_I2C3_USE_DMA
++  if (&I2CD3 == i2cp) {
++    dmaStreamDisable(i2cp->dmatx);
++    dmaStreamDisable(i2cp->dmarx);
++  }
++#endif
+ }
+ 
+ /**
+@@ -235,14 +271,18 @@ static void i2c_lld_set_opmode(I2CDriver *i2cp) {
+   dp->CR1 = regCR1;
+ }
+ 
++#if (STM32_I2C_USE_I2C1 && STM32_I2C_I2C1_USE_DMA) ||                       \
++    (STM32_I2C_USE_I2C2 && STM32_I2C_I2C2_USE_DMA) ||                       \
++    (STM32_I2C_USE_I2C3 && STM32_I2C_I2C3_USE_DMA) ||                       \
++    defined(__DOXYGEN__)
+ /**
+- * @brief   I2C shared ISR code.
++ * @brief   I2C shared ISR code for DMA access.
+  *
+  * @param[in] i2cp      pointer to the @p I2CDriver object
+  *
+  * @notapi
+  */
+-static void i2c_lld_serve_event_interrupt(I2CDriver *i2cp) {
++static void i2c_lld_serve_event_interrupt_dma(I2CDriver *i2cp) {
+   I2C_TypeDef *dp = i2cp->i2c;
+   uint32_t regSR2 = dp->SR2;
+   uint32_t event = dp->SR1;
 @@ -252,7 +292,7 @@ static void i2c_lld_serve_event_interrupt(I2CDriver *i2cp) {
-      done by the DMA.*/
-   switch (I2C_EV_MASK & (event | (regSR2 << 16))) {
-   case I2C_EV5_MASTER_MODE_SELECT:
--    if ((i2cp->addr >> 8) > 0) { 
-+    if ((i2cp->addr >> 8) > 0) {
-       /* 10-bit address: 1 1 1 1 0 X X R/W */
-       dp->DR = 0xF0 | (0x6 & (i2cp->addr >> 8)) | (0x1 & i2cp->addr);
-     } else {
-@@ -293,6 +333,140 @@ static void i2c_lld_serve_event_interrupt(I2CDriver *i2cp) {
-   if (event & (I2C_SR1_ADDR | I2C_SR1_ADD10))
-     (void)dp->SR2;
- }
-+#endif /* any I2CDx uses DMA mode */
-+
-+/**
-+ * @brief   I2C shared ISR code for non-DMA access.
-+ *
-+ * @param[in] i2cp      pointer to the @p I2CDriver object
-+ *
-+ * @notapi
-+ */
-+#if (STM32_I2C_USE_I2C1 && !STM32_I2C_I2C1_USE_DMA) ||                      \
-+    (STM32_I2C_USE_I2C2 && !STM32_I2C_I2C2_USE_DMA) ||                      \
-+    (STM32_I2C_USE_I2C3 && !STM32_I2C_I2C3_USE_DMA) ||                      \
-+    defined(__DOXYGEN__)
-+static void i2c_lld_serve_event_interrupt_isr(I2CDriver *i2cp) {
-+  I2C_TypeDef *dp = i2cp->i2c;
-+  uint32_t regSR2 = dp->SR2;
-+  uint32_t event = dp->SR1;
-+
-+  switch (I2C_EV_MASK & (event | (regSR2 << 16))) {
-+  case I2C_EV5_MASTER_MODE_SELECT:
-+    dp->CR2 |= I2C_CR2_ITBUFEN;
-+    dp->DR = i2cp->addr;
-+    break;
-+  case I2C_EV6_MASTER_TRA_MODE_SELECTED:
-+    (void)dp->SR2; // clear ADDR flag
-+    /* EV8_1 */
-+    dp->DR = *(i2cp->txbuf);
-+
-+    ++i2cp->txbuf;
-+    --i2cp->txbytes;
-+
-+    /* if N == 1, skip the I2C_EV8_MASTER_BYTE_TRANSMITTING event
-+     * but enter I2C_EV8_2_MASTER_BYTE_TRANSMITTED next */
-+    if (i2cp->txbytes == 0) {
-+      dp->CR2 &= ~I2C_CR2_ITBUFEN;
-+    }
-+    break;
-+  case I2C_EV6_MASTER_REC_MODE_SELECTED:
-+    switch (i2cp->rxbytes) {
-+    case 1:
-+      dp->CR1 &= ~I2C_CR1_ACK;
-+      (void)dp->SR2; // clear ADDR flag
-+      dp->CR1 |= I2C_CR1_STOP;
-+      break;
-+    case 2:
-+      (void)dp->SR2; // clear ADDR flag
-+      /* EV6_1 */
-+      dp->CR1 |= I2C_CR1_POS;
-+      dp->CR1 &= ~I2C_CR1_ACK;
-+      dp->CR2 &= ~I2C_CR2_ITBUFEN;
-+      break;
-+    case 3: /* N == 3 is a very special case, since EV7 is completely skipped */
-+      (void)dp->SR2; // clear ADDR flag
-+      /* Disable the I2C_EV7_MASTER_REC_BYTE_RECEIVED event
-+       * but enter I2C_EV7_MASTER_REC_BYTE_RECEIVED_STOP next */
-+      dp->CR2 &= ~I2C_CR2_ITBUFEN;
-+      break;
-+    default: /* N > 2 */
-+      (void)dp->SR2; // clear ADDR flag
-+      break;
-+    }
-+    break;
-+  case I2C_EV7_MASTER_REC_BYTE_RECEIVED:
-+    if (i2cp->rxbytes > 3) {
-+      *(i2cp->rxbuf) = dp->DR;
-+      ++i2cp->rxbuf;
-+      --i2cp->rxbytes;
-+    }
-+    if (i2cp->rxbytes == 3) {
-+      /* Disable this event for DataN-2, but force into event
-+       * I2C_EV7_2_EV7_3_MASTER_REC_BYTE_RECEIVED_QUEUED by not reading dp->DR. */
-+      dp->CR2 &= ~I2C_CR2_ITBUFEN;
-+    }
-+    break;
-+  case I2C_EV7_MASTER_REC_BYTE_RECEIVED_STOP:
-+    osalDbgAssert(i2cp->rxbytes == 1, "more than 1 byte to be received");
-+    *(i2cp->rxbuf) = dp->DR;
-+    --i2cp->rxbytes;
-+    dp->CR2 &= ~(I2C_CR2_ITEVTEN | I2C_CR2_ITBUFEN);
-+    _i2c_wakeup_isr(i2cp);
-+    break;
-+  case I2C_EV7_2_EV7_3_MASTER_REC_BYTE_QUEUED:
-+    if (i2cp->rxbytes == 3) {
-+      /* EV7_2 (N > 2) */
-+      dp->CR1 &= ~I2C_CR1_ACK;
-+      *(i2cp->rxbuf) = dp->DR;
-+      ++i2cp->rxbuf;
-+      dp->CR1 |= I2C_CR1_STOP;
-+      *(i2cp->rxbuf) = dp->DR;
-+      ++i2cp->rxbuf;
-+      i2cp->rxbytes -= 2;
-+      /* enable I2C_EV7_MASTER_REC_BYTE_RECEIVED_STOP event */
-+      dp->CR2 |= I2C_CR2_ITBUFEN;
-+    } else {
-+      /* EV7_3 (N == 2) */
-+      dp->CR1 |= I2C_CR1_STOP;
-+      *(i2cp->rxbuf) = dp->DR;
-+      ++i2cp->rxbuf;
-+      *(i2cp->rxbuf) = dp->DR;
-+      i2cp->rxbytes -= 2;
-+
-+      dp->CR1 &= ~I2C_CR1_POS;
-+      dp->CR2 &= ~(I2C_CR2_ITEVTEN | I2C_CR2_ITBUFEN);
-+
-+      _i2c_wakeup_isr(i2cp);
-+    }
-+    break;
-+  case I2C_EV8_MASTER_BYTE_TRANSMITTING:
-+    dp->DR = *(i2cp->txbuf);
-+    ++i2cp->txbuf;
-+    --i2cp->txbytes;
-+
-+    /* if this was the last byte, ensure that this event is not entered again */
-+    if (i2cp->txbytes == 0) {
-+      dp->CR2 &= ~I2C_CR2_ITBUFEN;
-+    }
-+    break;
-+  case I2C_EV8_2_MASTER_BYTE_TRANSMITTED:
-+    if (i2cp->rxbytes > 0) {
-+      /* start "read after write" operation (LSB of address = 1 => read) */
-+      i2cp->addr |= 0x01;
-+      dp->CR1 |= I2C_CR1_START | I2C_CR1_ACK;
-+    } else {
-+      dp->CR1 |= I2C_CR1_STOP;
-+      dp->CR2 &= ~(I2C_CR2_ITEVTEN | I2C_CR2_ITBUFEN);
-+      _i2c_wakeup_isr(i2cp);
-+    }
-+    break;
-+  default:
-+    osalDbgAssert(i2cp->rxbytes != 1, "more than 1 byte to be received");
-+    break;
-+  }
-+}
-+#endif /* any I2CDx uses non-DMA mode */
- 
- /**
-  * @brief   DMA RX end IRQ handler.
-@@ -302,6 +476,10 @@ static void i2c_lld_serve_event_interrupt(I2CDriver *i2cp) {
-  *
-  * @notapi
-  */
-+#if (STM32_I2C_USE_I2C1 && STM32_I2C_I2C1_USE_DMA) ||                      \
-+    (STM32_I2C_USE_I2C2 && STM32_I2C_I2C2_USE_DMA) ||                      \
-+    (STM32_I2C_USE_I2C3 && STM32_I2C_I2C3_USE_DMA) ||                      \
-+    defined(__DOXYGEN__)
- static void i2c_lld_serve_rx_end_irq(I2CDriver *i2cp, uint32_t flags) {
-   I2C_TypeDef *dp = i2cp->i2c;
- 
-@@ -347,6 +525,7 @@ static void i2c_lld_serve_tx_end_irq(I2CDriver *i2cp, uint32_t flags) {
-      of R/W transaction itself.*/
-   dp->CR2 |= I2C_CR2_ITEVTEN;
- }
-+#endif /* any I2CDx uses DMA mode */
- 
- /**
-  * @brief   I2C error handler.
-@@ -359,8 +538,24 @@ static void i2c_lld_serve_tx_end_irq(I2CDriver *i2cp, uint32_t flags) {
- static void i2c_lld_serve_error_interrupt(I2CDriver *i2cp, uint16_t sr) {
- 
-   /* Clears interrupt flags just to be safe.*/
--  dmaStreamDisable(i2cp->dmatx);
--  dmaStreamDisable(i2cp->dmarx);
-+#if STM32_I2C_USE_I2C1 && STM32_I2C_I2C1_USE_DMA
-+  if (&I2CD1 == i2cp) {
-+    dmaStreamDisable(i2cp->dmatx);
-+    dmaStreamDisable(i2cp->dmarx);
-+  }
-+#endif
-+#if STM32_I2C_USE_I2C2 && STM32_I2C_I2C2_USE_DMA
-+  if (&I2CD2 == i2cp) {
-+    dmaStreamDisable(i2cp->dmatx);
-+    dmaStreamDisable(i2cp->dmarx);
-+  }
-+#endif
-+#if STM32_I2C_USE_I2C3 && STM32_I2C_I2C3_USE_DMA
-+  if (&I2CD3 == i2cp) {
-+    dmaStreamDisable(i2cp->dmatx);
-+    dmaStreamDisable(i2cp->dmarx);
-+  }
-+#endif
- 
-   i2cp->errors = I2C_NO_ERROR;
- 
-@@ -407,7 +602,11 @@ OSAL_IRQ_HANDLER(STM32_I2C1_EVENT_HANDLER) {
- 
-   OSAL_IRQ_PROLOGUE();
- 
--  i2c_lld_serve_event_interrupt(&I2CD1);
-+#if STM32_I2C_I2C1_USE_DMA
-+  i2c_lld_serve_event_interrupt_dma(&I2CD1);
-+#else
-+  i2c_lld_serve_event_interrupt_isr(&I2CD1);
-+#endif
- 
-   OSAL_IRQ_EPILOGUE();
- }
-@@ -437,7 +636,11 @@ OSAL_IRQ_HANDLER(STM32_I2C2_EVENT_HANDLER) {
- 
-   OSAL_IRQ_PROLOGUE();
- 
--  i2c_lld_serve_event_interrupt(&I2CD2);
-+#if STM32_I2C_I2C2_USE_DMA
-+  i2c_lld_serve_event_interrupt_dma(&I2CD2);
-+#else
-+  i2c_lld_serve_event_interrupt_isr(&I2CD2);
-+#endif
- 
-   OSAL_IRQ_EPILOGUE();
- }
-@@ -469,7 +672,11 @@ OSAL_IRQ_HANDLER(STM32_I2C3_EVENT_HANDLER) {
- 
-   OSAL_IRQ_PROLOGUE();
- 
--  i2c_lld_serve_event_interrupt(&I2CD3);
-+#if STM32_I2C_I2C3_USE_DMA
-+  i2c_lld_serve_event_interrupt_dma(&I2CD3);
-+#else
-+  i2c_lld_serve_event_interrupt_isr(&I2CD3);
-+#endif
- 
-   OSAL_IRQ_EPILOGUE();
- }
-@@ -506,24 +713,30 @@ void i2c_lld_init(void) {
-   i2cObjectInit(&I2CD1);
-   I2CD1.thread = NULL;
-   I2CD1.i2c    = I2C1;
-+#if STM32_I2C_I2C1_USE_DMA
-   I2CD1.dmarx  = STM32_DMA_STREAM(STM32_I2C_I2C1_RX_DMA_STREAM);
-   I2CD1.dmatx  = STM32_DMA_STREAM(STM32_I2C_I2C1_TX_DMA_STREAM);
-+#endif
- #endif /* STM32_I2C_USE_I2C1 */
- 
- #if STM32_I2C_USE_I2C2
-   i2cObjectInit(&I2CD2);
-   I2CD2.thread = NULL;
-   I2CD2.i2c    = I2C2;
-+#if STM32_I2C_I2C2_USE_DMA
-   I2CD2.dmarx  = STM32_DMA_STREAM(STM32_I2C_I2C2_RX_DMA_STREAM);
-   I2CD2.dmatx  = STM32_DMA_STREAM(STM32_I2C_I2C2_TX_DMA_STREAM);
-+#endif
- #endif /* STM32_I2C_USE_I2C2 */
- 
- #if STM32_I2C_USE_I2C3
-   i2cObjectInit(&I2CD3);
-   I2CD3.thread = NULL;
-   I2CD3.i2c    = I2C3;
-+#if STM32_I2C_I2C3_USE_DMA
-   I2CD3.dmarx  = STM32_DMA_STREAM(STM32_I2C_I2C3_RX_DMA_STREAM);
-   I2CD3.dmatx  = STM32_DMA_STREAM(STM32_I2C_I2C3_TX_DMA_STREAM);
-+#endif
- #endif /* STM32_I2C_USE_I2C3 */
- }
- 
-@@ -540,20 +753,24 @@ void i2c_lld_start(I2CDriver *i2cp) {
-   /* If in stopped state then enables the I2C and DMA clocks.*/
-   if (i2cp->state == I2C_STOP) {
- 
--    i2cp->txdmamode = STM32_DMA_CR_PSIZE_BYTE | STM32_DMA_CR_MSIZE_BYTE |
--                      STM32_DMA_CR_MINC       | STM32_DMA_CR_DMEIE |
--                      STM32_DMA_CR_TEIE       | STM32_DMA_CR_TCIE |
--                      STM32_DMA_CR_DIR_M2P;
--    i2cp->rxdmamode = STM32_DMA_CR_PSIZE_BYTE | STM32_DMA_CR_MSIZE_BYTE |
--                      STM32_DMA_CR_MINC       | STM32_DMA_CR_DMEIE |
--                      STM32_DMA_CR_TEIE       | STM32_DMA_CR_TCIE |
--                      STM32_DMA_CR_DIR_P2M;
--
- #if STM32_I2C_USE_I2C1
-     if (&I2CD1 == i2cp) {
-+#if STM32_I2C_I2C1_USE_DMA
-       bool b;
- 
-+      i2cp->txdmamode = STM32_DMA_CR_PSIZE_BYTE | STM32_DMA_CR_MSIZE_BYTE |
-+                        STM32_DMA_CR_MINC       | STM32_DMA_CR_DMEIE |
-+                        STM32_DMA_CR_TEIE       | STM32_DMA_CR_TCIE |
-+                        STM32_DMA_CR_DIR_M2P;
-+      i2cp->rxdmamode = STM32_DMA_CR_PSIZE_BYTE | STM32_DMA_CR_MSIZE_BYTE |
-+                        STM32_DMA_CR_MINC       | STM32_DMA_CR_DMEIE |
-+                        STM32_DMA_CR_TEIE       | STM32_DMA_CR_TCIE |
-+                        STM32_DMA_CR_DIR_P2M;
-+#endif
-+
-       rccResetI2C1();
-+
-+#if STM32_I2C_I2C1_USE_DMA
-       b = dmaStreamAllocate(i2cp->dmarx,
-                             STM32_I2C_I2C1_IRQ_PRIORITY,
-                             (stm32_dmaisr_t)i2c_lld_serve_rx_end_irq,
-@@ -564,22 +781,52 @@ void i2c_lld_start(I2CDriver *i2cp) {
-                             (stm32_dmaisr_t)i2c_lld_serve_tx_end_irq,
-                             (void *)i2cp);
-       osalDbgAssert(!b, "stream already allocated");
-+#endif
-+
-       rccEnableI2C1(true);
-       nvicEnableVector(I2C1_EV_IRQn, STM32_I2C_I2C1_IRQ_PRIORITY);
-       nvicEnableVector(I2C1_ER_IRQn, STM32_I2C_I2C1_IRQ_PRIORITY);
- 
-+#if STM32_I2C_I2C1_USE_DMA
-       i2cp->rxdmamode |= STM32_DMA_CR_CHSEL(I2C1_RX_DMA_CHANNEL) |
-                        STM32_DMA_CR_PL(STM32_I2C_I2C1_DMA_PRIORITY);
-       i2cp->txdmamode |= STM32_DMA_CR_CHSEL(I2C1_TX_DMA_CHANNEL) |
-                        STM32_DMA_CR_PL(STM32_I2C_I2C1_DMA_PRIORITY);
-+
-+      /* I2C registers pointed by the DMA.*/
-+      dmaStreamSetPeripheral(i2cp->dmarx, &dp->DR);
-+      dmaStreamSetPeripheral(i2cp->dmatx, &dp->DR);
-+#endif
-+
-+      /* Reset i2c peripheral.*/
-+      dp->CR1 = I2C_CR1_SWRST;
-+      dp->CR1 = 0;
-+#if STM32_I2C_I2C1_USE_DMA
-+      dp->CR2 = I2C_CR2_ITERREN | I2C_CR2_DMAEN;
-+#else
-+      dp->CR2 = I2C_CR2_ITERREN;
-+#endif
-     }
- #endif /* STM32_I2C_USE_I2C1 */
- 
- #if STM32_I2C_USE_I2C2
-     if (&I2CD2 == i2cp) {
-+#if STM32_I2C_I2C2_USE_DMA
-       bool b;
- 
-+      i2cp->txdmamode = STM32_DMA_CR_PSIZE_BYTE | STM32_DMA_CR_MSIZE_BYTE |
-+                        STM32_DMA_CR_MINC       | STM32_DMA_CR_DMEIE |
-+                        STM32_DMA_CR_TEIE       | STM32_DMA_CR_TCIE |
-+                        STM32_DMA_CR_DIR_M2P;
-+      i2cp->rxdmamode = STM32_DMA_CR_PSIZE_BYTE | STM32_DMA_CR_MSIZE_BYTE |
-+                        STM32_DMA_CR_MINC       | STM32_DMA_CR_DMEIE |
-+                        STM32_DMA_CR_TEIE       | STM32_DMA_CR_TCIE |
-+                        STM32_DMA_CR_DIR_P2M;
-+#endif
-+
-       rccResetI2C2();
-+
-+#if STM32_I2C_I2C2_USE_DMA
-       b = dmaStreamAllocate(i2cp->dmarx,
-                             STM32_I2C_I2C2_IRQ_PRIORITY,
-                             (stm32_dmaisr_t)i2c_lld_serve_rx_end_irq,
-@@ -590,22 +837,52 @@ void i2c_lld_start(I2CDriver *i2cp) {
-                             (stm32_dmaisr_t)i2c_lld_serve_tx_end_irq,
-                             (void *)i2cp);
-       osalDbgAssert(!b, "stream already allocated");
-+#endif
-+
-       rccEnableI2C2(true);
-       nvicEnableVector(I2C2_EV_IRQn, STM32_I2C_I2C2_IRQ_PRIORITY);
-       nvicEnableVector(I2C2_ER_IRQn, STM32_I2C_I2C2_IRQ_PRIORITY);
- 
-+#if STM32_I2C_I2C2_USE_DMA
-       i2cp->rxdmamode |= STM32_DMA_CR_CHSEL(I2C2_RX_DMA_CHANNEL) |
-                        STM32_DMA_CR_PL(STM32_I2C_I2C2_DMA_PRIORITY);
-       i2cp->txdmamode |= STM32_DMA_CR_CHSEL(I2C2_TX_DMA_CHANNEL) |
-                        STM32_DMA_CR_PL(STM32_I2C_I2C2_DMA_PRIORITY);
-+
-+      /* I2C registers pointed by the DMA.*/
-+      dmaStreamSetPeripheral(i2cp->dmarx, &dp->DR);
-+      dmaStreamSetPeripheral(i2cp->dmatx, &dp->DR);
-+#endif
-+
-+      /* Reset i2c peripheral.*/
-+      dp->CR1 = I2C_CR1_SWRST;
-+      dp->CR1 = 0;
-+#if STM32_I2C_I2C2_USE_DMA
-+      dp->CR2 = I2C_CR2_ITERREN | I2C_CR2_DMAEN;
-+#else
-+      dp->CR2 = I2C_CR2_ITERREN;
-+#endif
-     }
- #endif /* STM32_I2C_USE_I2C2 */
- 
- #if STM32_I2C_USE_I2C3
-     if (&I2CD3 == i2cp) {
-+#if STM32_I2C_I2C3_USE_DMA
-       bool b;
- 
-+      i2cp->txdmamode = STM32_DMA_CR_PSIZE_BYTE | STM32_DMA_CR_MSIZE_BYTE |
-+                        STM32_DMA_CR_MINC       | STM32_DMA_CR_DMEIE |
-+                        STM32_DMA_CR_TEIE       | STM32_DMA_CR_TCIE |
-+                        STM32_DMA_CR_DIR_M2P;
-+      i2cp->rxdmamode = STM32_DMA_CR_PSIZE_BYTE | STM32_DMA_CR_MSIZE_BYTE |
-+                        STM32_DMA_CR_MINC       | STM32_DMA_CR_DMEIE |
-+                        STM32_DMA_CR_TEIE       | STM32_DMA_CR_TCIE |
-+                        STM32_DMA_CR_DIR_P2M;
-+#endif
-+
-       rccResetI2C3();
-+
-+#if STM32_I2C_I2C3_USE_DMA
-       b = dmaStreamAllocate(i2cp->dmarx,
-                             STM32_I2C_I2C3_IRQ_PRIORITY,
-                             (stm32_dmaisr_t)i2c_lld_serve_rx_end_irq,
-@@ -616,27 +893,35 @@ void i2c_lld_start(I2CDriver *i2cp) {
-                             (stm32_dmaisr_t)i2c_lld_serve_tx_end_irq,
-                             (void *)i2cp);
-       osalDbgAssert(!b, "stream already allocated");
-+#endif
-+
-       rccEnableI2C3(true);
-       nvicEnableVector(I2C3_EV_IRQn, STM32_I2C_I2C3_IRQ_PRIORITY);
-       nvicEnableVector(I2C3_ER_IRQn, STM32_I2C_I2C3_IRQ_PRIORITY);
- 
-+#if STM32_I2C_I2C3_USE_DMA
-       i2cp->rxdmamode |= STM32_DMA_CR_CHSEL(I2C3_RX_DMA_CHANNEL) |
-                        STM32_DMA_CR_PL(STM32_I2C_I2C3_DMA_PRIORITY);
-       i2cp->txdmamode |= STM32_DMA_CR_CHSEL(I2C3_TX_DMA_CHANNEL) |
-                        STM32_DMA_CR_PL(STM32_I2C_I2C3_DMA_PRIORITY);
-+
-+      /* I2C registers pointed by the DMA.*/
-+      dmaStreamSetPeripheral(i2cp->dmarx, &dp->DR);
-+      dmaStreamSetPeripheral(i2cp->dmatx, &dp->DR);
-+#endif
-+
-+      /* Reset i2c peripheral.*/
-+      dp->CR1 = I2C_CR1_SWRST;
-+      dp->CR1 = 0;
-+#if STM32_I2C_I2C3_USE_DMA
-+      dp->CR2 = I2C_CR2_ITERREN | I2C_CR2_DMAEN;
-+#else
-+      dp->CR2 = I2C_CR2_ITERREN;
-+#endif
-     }
- #endif /* STM32_I2C_USE_I2C3 */
-   }
- 
--  /* I2C registers pointed by the DMA.*/
--  dmaStreamSetPeripheral(i2cp->dmarx, &dp->DR);
--  dmaStreamSetPeripheral(i2cp->dmatx, &dp->DR);
--
--  /* Reset i2c peripheral.*/
--  dp->CR1 = I2C_CR1_SWRST;
--  dp->CR1 = 0;
--  dp->CR2 = I2C_CR2_ITERREN | I2C_CR2_DMAEN;
--
-   /* Setup I2C parameters.*/
-   i2c_lld_set_clock(i2cp);
-   i2c_lld_set_opmode(i2cp);
-@@ -659,11 +944,13 @@ void i2c_lld_stop(I2CDriver *i2cp) {
- 
-     /* I2C disable.*/
-     i2c_lld_abort_operation(i2cp);
--    dmaStreamRelease(i2cp->dmatx);
--    dmaStreamRelease(i2cp->dmarx);
- 
- #if STM32_I2C_USE_I2C1
-     if (&I2CD1 == i2cp) {
-+#if STM32_I2C_I2C1_USE_DMA
-+      dmaStreamRelease(i2cp->dmatx);
-+      dmaStreamRelease(i2cp->dmarx);
-+ #endif
-       nvicDisableVector(I2C1_EV_IRQn);
-       nvicDisableVector(I2C1_ER_IRQn);
-       rccDisableI2C1();
-@@ -672,6 +959,10 @@ void i2c_lld_stop(I2CDriver *i2cp) {
- 
- #if STM32_I2C_USE_I2C2
-     if (&I2CD2 == i2cp) {
-+#if STM32_I2C_I2C2_USE_DMA
-+      dmaStreamRelease(i2cp->dmatx);
-+      dmaStreamRelease(i2cp->dmarx);
-+ #endif
-       nvicDisableVector(I2C2_EV_IRQn);
-       nvicDisableVector(I2C2_ER_IRQn);
-       rccDisableI2C2();
-@@ -680,6 +971,10 @@ void i2c_lld_stop(I2CDriver *i2cp) {
- 
- #if STM32_I2C_USE_I2C3
-     if (&I2CD3 == i2cp) {
-+#if STM32_I2C_I2C3_USE_DMA
-+      dmaStreamRelease(i2cp->dmatx);
-+      dmaStreamRelease(i2cp->dmarx);
-+ #endif
-       nvicDisableVector(I2C3_EV_IRQn);
-       nvicDisableVector(I2C3_ER_IRQn);
-       rccDisableI2C3();
-@@ -730,10 +1025,43 @@ msg_t i2c_lld_master_receive_timeout(I2CDriver *i2cp, i2caddr_t addr,
-   /* Releases the lock from high level driver.*/
-   osalSysUnlock();
- 
--  /* RX DMA setup.*/
--  dmaStreamSetMode(i2cp->dmarx, i2cp->rxdmamode);
--  dmaStreamSetMemory0(i2cp->dmarx, rxbuf);
--  dmaStreamSetTransactionSize(i2cp->dmarx, rxbytes);
-+  /* RX (DMA) setup.*/
-+#if STM32_I2C_USE_I2C1
-+  if (&I2CD1 == i2cp) {
-+#if STM32_I2C_I2C1_USE_DMA
-+    dmaStreamSetMode(i2cp->dmarx, i2cp->rxdmamode);
-+    dmaStreamSetMemory0(i2cp->dmarx, rxbuf);
-+    dmaStreamSetTransactionSize(i2cp->dmarx, rxbytes);
-+#else
-+    i2cp->rxbuf = rxbuf;
-+    i2cp->rxbytes = rxbytes;
-+#endif
-+  }
-+#endif
-+#if STM32_I2C_USE_I2C2
-+  if (&I2CD2 == i2cp) {
-+#if STM32_I2C_I2C2_USE_DMA
-+    dmaStreamSetMode(i2cp->dmarx, i2cp->rxdmamode);
-+    dmaStreamSetMemory0(i2cp->dmarx, rxbuf);
-+    dmaStreamSetTransactionSize(i2cp->dmarx, rxbytes);
-+#else
-+    i2cp->rxbuf = rxbuf;
-+    i2cp->rxbytes = rxbytes;
-+#endif
-+  }
-+#endif
-+#if STM32_I2C_USE_I2C3
-+  if (&I2CD3 == i2cp) {
-+#if STM32_I2C_I2C3_USE_DMA
-+    dmaStreamSetMode(i2cp->dmarx, i2cp->rxdmamode);
-+    dmaStreamSetMemory0(i2cp->dmarx, rxbuf);
-+    dmaStreamSetTransactionSize(i2cp->dmarx, rxbytes);
-+#else
-+    i2cp->rxbuf = rxbuf;
-+    i2cp->rxbytes = rxbytes;
-+#endif
-+  }
-+#endif
- 
-   /* Calculating the time window for the timeout on the busy bus condition.*/
-   start = osalOsGetSystemTimeX();
-@@ -810,15 +1138,61 @@ msg_t i2c_lld_master_transmit_timeout(I2CDriver *i2cp, i2caddr_t addr,
-   /* Releases the lock from high level driver.*/
-   osalSysUnlock();
- 
--  /* TX DMA setup.*/
--  dmaStreamSetMode(i2cp->dmatx, i2cp->txdmamode);
--  dmaStreamSetMemory0(i2cp->dmatx, txbuf);
--  dmaStreamSetTransactionSize(i2cp->dmatx, txbytes);
--
--  /* RX DMA setup.*/
--  dmaStreamSetMode(i2cp->dmarx, i2cp->rxdmamode);
--  dmaStreamSetMemory0(i2cp->dmarx, rxbuf);
--  dmaStreamSetTransactionSize(i2cp->dmarx, rxbytes);
-+  /* TX (DMA) and RX (DMA) setup */
-+#if STM32_I2C_USE_I2C1
-+  if (&I2CD1 == i2cp) {
-+#if STM32_I2C_I2C1_USE_DMA
-+    dmaStreamSetMode(i2cp->dmatx, i2cp->txdmamode);
-+    dmaStreamSetMemory0(i2cp->dmatx, txbuf);
-+    dmaStreamSetTransactionSize(i2cp->dmatx, txbytes);
-+
-+    dmaStreamSetMode(i2cp->dmarx, i2cp->rxdmamode);
-+    dmaStreamSetMemory0(i2cp->dmarx, rxbuf);
-+    dmaStreamSetTransactionSize(i2cp->dmarx, rxbytes);
-+#else
-+    i2cp->txbuf = txbuf;
-+    i2cp->txbytes = txbytes;
-+    i2cp->rxbuf = rxbuf;
-+    i2cp->rxbytes = rxbytes;
-+#endif
-+  }
-+#endif
-+#if STM32_I2C_USE_I2C2
-+  if (&I2CD2 == i2cp) {
-+#if STM32_I2C_I2C2_USE_DMA
-+    dmaStreamSetMode(i2cp->dmatx, i2cp->txdmamode);
-+    dmaStreamSetMemory0(i2cp->dmatx, txbuf);
-+    dmaStreamSetTransactionSize(i2cp->dmatx, txbytes);
-+
-+    dmaStreamSetMode(i2cp->dmarx, i2cp->rxdmamode);
-+    dmaStreamSetMemory0(i2cp->dmarx, rxbuf);
-+    dmaStreamSetTransactionSize(i2cp->dmarx, rxbytes);
-+#else
-+    i2cp->txbuf = txbuf;
-+    i2cp->txbytes = txbytes;
-+    i2cp->rxbuf = rxbuf;
-+    i2cp->rxbytes = rxbytes;
-+#endif
-+  }
-+#endif
-+#if STM32_I2C_USE_I2C3
-+  if (&I2CD3 == i2cp) {
-+#if STM32_I2C_I2C3_USE_DMA
-+    dmaStreamSetMode(i2cp->dmatx, i2cp->txdmamode);
-+    dmaStreamSetMemory0(i2cp->dmatx, txbuf);
-+    dmaStreamSetTransactionSize(i2cp->dmatx, txbytes);
-+
-+    dmaStreamSetMode(i2cp->dmarx, i2cp->rxdmamode);
-+    dmaStreamSetMemory0(i2cp->dmarx, rxbuf);
-+    dmaStreamSetTransactionSize(i2cp->dmarx, rxbytes);
-+#else
-+    i2cp->txbuf = txbuf;
-+    i2cp->txbytes = txbytes;
-+    i2cp->rxbuf = rxbuf;
-+    i2cp->rxbytes = rxbytes;
-+#endif
-+  }
-+#endif
- 
-   /* Calculating the time window for the timeout on the busy bus condition.*/
-   start = osalOsGetSystemTimeX();
+      done by the DMA.*/
+   switch (I2C_EV_MASK & (event | (regSR2 << 16))) {
+   case I2C_EV5_MASTER_MODE_SELECT:
+-    if ((i2cp->addr >> 8) > 0) { 
++    if ((i2cp->addr >> 8) > 0) {
+       /* 10-bit address: 1 1 1 1 0 X X R/W */
+       dp->DR = 0xF0 | (0x6 & (i2cp->addr >> 8)) | (0x1 & i2cp->addr);
+     } else {
+@@ -293,7 +333,146 @@ static void i2c_lld_serve_event_interrupt(I2CDriver *i2cp) {
+   if (event & (I2C_SR1_ADDR | I2C_SR1_ADD10))
+     (void)dp->SR2;
+ }
++#endif /* any I2CDx uses DMA mode */
++
++#if (STM32_I2C_USE_I2C1 && !STM32_I2C_I2C1_USE_DMA) ||                      \
++    (STM32_I2C_USE_I2C2 && !STM32_I2C_I2C2_USE_DMA) ||                      \
++    (STM32_I2C_USE_I2C3 && !STM32_I2C_I2C3_USE_DMA) ||                      \
++    defined(__DOXYGEN__)
++/**
++ * @brief   I2C shared ISR code for non-DMA access.
++ *
++ * @param[in] i2cp      pointer to the @p I2CDriver object
++ *
++ * @notapi
++ */
++static void i2c_lld_serve_event_interrupt_isr(I2CDriver *i2cp) {
++  I2C_TypeDef *dp = i2cp->i2c;
++  uint32_t regSR2 = dp->SR2;
++  uint32_t event = dp->SR1;
++
++  switch (I2C_EV_MASK & (event | (regSR2 << 16))) {
++  case I2C_EV5_MASTER_MODE_SELECT:
++    dp->CR2 |= I2C_CR2_ITBUFEN;
++    dp->DR = i2cp->addr;
++    break;
++  case I2C_EV6_MASTER_TRA_MODE_SELECTED:
++    (void)dp->SR2; // clear ADDR flag
++    /* EV8_1 */
++    dp->DR = *(i2cp->txbuf);
++
++    ++i2cp->txbuf;
++    --i2cp->txbytes;
++
++    /* if N == 1, skip the I2C_EV8_MASTER_BYTE_TRANSMITTING event
++     * but enter I2C_EV8_2_MASTER_BYTE_TRANSMITTED next */
++    if (i2cp->txbytes == 0) {
++      dp->CR2 &= ~I2C_CR2_ITBUFEN;
++    }
++    break;
++  case I2C_EV6_MASTER_REC_MODE_SELECTED:
++    switch (i2cp->rxbytes) {
++    case 1:
++      dp->CR1 &= ~I2C_CR1_ACK;
++      (void)dp->SR2; // clear ADDR flag
++      dp->CR1 |= I2C_CR1_STOP;
++      break;
++    case 2:
++      (void)dp->SR2; // clear ADDR flag
++      /* EV6_1 */
++      dp->CR1 |= I2C_CR1_POS;
++      dp->CR1 &= ~I2C_CR1_ACK;
++      dp->CR2 &= ~I2C_CR2_ITBUFEN;
++      break;
++    case 3: /* N == 3 is a very special case, since EV7 is completely skipped */
++      (void)dp->SR2; // clear ADDR flag
++      /* Disable the I2C_EV7_MASTER_REC_BYTE_RECEIVED event
++       * but enter I2C_EV7_MASTER_REC_BYTE_RECEIVED_STOP next */
++      dp->CR2 &= ~I2C_CR2_ITBUFEN;
++      break;
++    default: /* N > 2 */
++      (void)dp->SR2; // clear ADDR flag
++      break;
++    }
++    break;
++  case I2C_EV7_MASTER_REC_BYTE_RECEIVED:
++    if (i2cp->rxbytes > 3) {
++      *(i2cp->rxbuf) = dp->DR;
++      ++i2cp->rxbuf;
++      --i2cp->rxbytes;
++    }
++    if (i2cp->rxbytes == 3) {
++      /* Disable this event for DataN-2, but force into event
++       * I2C_EV7_2_EV7_3_MASTER_REC_BYTE_RECEIVED_QUEUED by not reading dp->DR. */
++      dp->CR2 &= ~I2C_CR2_ITBUFEN;
++    }
++    break;
++  case I2C_EV7_MASTER_REC_BYTE_RECEIVED_STOP:
++    osalDbgAssert(i2cp->rxbytes == 1, "more than 1 byte to be received");
++    *(i2cp->rxbuf) = dp->DR;
++    --i2cp->rxbytes;
++    dp->CR2 &= ~(I2C_CR2_ITEVTEN | I2C_CR2_ITBUFEN);
++    _i2c_wakeup_isr(i2cp);
++    break;
++  case I2C_EV7_2_EV7_3_MASTER_REC_BYTE_QUEUED:
++    if (i2cp->rxbytes == 3) {
++      /* EV7_2 (N > 2) */
++      dp->CR1 &= ~I2C_CR1_ACK;
++      *(i2cp->rxbuf) = dp->DR;
++      ++i2cp->rxbuf;
++      dp->CR1 |= I2C_CR1_STOP;
++      *(i2cp->rxbuf) = dp->DR;
++      ++i2cp->rxbuf;
++      i2cp->rxbytes -= 2;
++      /* enable I2C_EV7_MASTER_REC_BYTE_RECEIVED_STOP event */
++      dp->CR2 |= I2C_CR2_ITBUFEN;
++    } else {
++      /* EV7_3 (N == 2) */
++      dp->CR1 |= I2C_CR1_STOP;
++      *(i2cp->rxbuf) = dp->DR;
++      ++i2cp->rxbuf;
++      *(i2cp->rxbuf) = dp->DR;
++      i2cp->rxbytes -= 2;
++
++      dp->CR1 &= ~I2C_CR1_POS;
++      dp->CR2 &= ~(I2C_CR2_ITEVTEN | I2C_CR2_ITBUFEN);
++
++      _i2c_wakeup_isr(i2cp);
++    }
++    break;
++  case I2C_EV8_MASTER_BYTE_TRANSMITTING:
++    dp->DR = *(i2cp->txbuf);
++    ++i2cp->txbuf;
++    --i2cp->txbytes;
++
++    /* if this was the last byte, ensure that this event is not entered again */
++    if (i2cp->txbytes == 0) {
++      dp->CR2 &= ~I2C_CR2_ITBUFEN;
++    }
++    break;
++  case I2C_EV8_2_MASTER_BYTE_TRANSMITTED:
++    if (i2cp->rxbytes > 0) {
++      /* start "read after write" operation (LSB of address = 1 => read) */
++      i2cp->addr |= 0x01;
++      dp->CR1 |= I2C_CR1_START | I2C_CR1_ACK;
++    } else {
++      dp->CR1 |= I2C_CR1_STOP;
++      dp->CR2 &= ~(I2C_CR2_ITEVTEN | I2C_CR2_ITBUFEN);
++      _i2c_wakeup_isr(i2cp);
++    }
++    break;
++  default:
++    osalDbgAssert(i2cp->rxbytes != 1, "more than 1 byte to be received");
++    break;
++  }
++}
++#endif /* any I2CDx uses non-DMA mode */
+ 
++
++#if (STM32_I2C_USE_I2C1 && STM32_I2C_I2C1_USE_DMA) ||                      \
++    (STM32_I2C_USE_I2C2 && STM32_I2C_I2C2_USE_DMA) ||                      \
++    (STM32_I2C_USE_I2C3 && STM32_I2C_I2C3_USE_DMA) ||                      \
++    defined(__DOXYGEN__)
+ /**
+  * @brief   DMA RX end IRQ handler.
+  *
+@@ -347,6 +526,7 @@ static void i2c_lld_serve_tx_end_irq(I2CDriver *i2cp, uint32_t flags) {
+      of R/W transaction itself.*/
+   dp->CR2 |= I2C_CR2_ITEVTEN;
+ }
++#endif /* any I2CDx uses DMA mode */
+ 
+ /**
+  * @brief   I2C error handler.
+@@ -359,8 +539,24 @@ static void i2c_lld_serve_tx_end_irq(I2CDriver *i2cp, uint32_t flags) {
+ static void i2c_lld_serve_error_interrupt(I2CDriver *i2cp, uint16_t sr) {
+ 
+   /* Clears interrupt flags just to be safe.*/
+-  dmaStreamDisable(i2cp->dmatx);
+-  dmaStreamDisable(i2cp->dmarx);
++#if STM32_I2C_USE_I2C1 && STM32_I2C_I2C1_USE_DMA
++  if (&I2CD1 == i2cp) {
++    dmaStreamDisable(i2cp->dmatx);
++    dmaStreamDisable(i2cp->dmarx);
++  }
++#endif
++#if STM32_I2C_USE_I2C2 && STM32_I2C_I2C2_USE_DMA
++  if (&I2CD2 == i2cp) {
++    dmaStreamDisable(i2cp->dmatx);
++    dmaStreamDisable(i2cp->dmarx);
++  }
++#endif
++#if STM32_I2C_USE_I2C3 && STM32_I2C_I2C3_USE_DMA
++  if (&I2CD3 == i2cp) {
++    dmaStreamDisable(i2cp->dmatx);
++    dmaStreamDisable(i2cp->dmarx);
++  }
++#endif
+ 
+   i2cp->errors = I2C_NO_ERROR;
+ 
+@@ -407,7 +603,11 @@ OSAL_IRQ_HANDLER(STM32_I2C1_EVENT_HANDLER) {
+ 
+   OSAL_IRQ_PROLOGUE();
+ 
+-  i2c_lld_serve_event_interrupt(&I2CD1);
++#if STM32_I2C_I2C1_USE_DMA
++  i2c_lld_serve_event_interrupt_dma(&I2CD1);
++#else
++  i2c_lld_serve_event_interrupt_isr(&I2CD1);
++#endif
+ 
+   OSAL_IRQ_EPILOGUE();
+ }
+@@ -437,7 +637,11 @@ OSAL_IRQ_HANDLER(STM32_I2C2_EVENT_HANDLER) {
+ 
+   OSAL_IRQ_PROLOGUE();
+ 
+-  i2c_lld_serve_event_interrupt(&I2CD2);
++#if STM32_I2C_I2C2_USE_DMA
++  i2c_lld_serve_event_interrupt_dma(&I2CD2);
++#else
++  i2c_lld_serve_event_interrupt_isr(&I2CD2);
++#endif
+ 
+   OSAL_IRQ_EPILOGUE();
+ }
+@@ -469,7 +673,11 @@ OSAL_IRQ_HANDLER(STM32_I2C3_EVENT_HANDLER) {
+ 
+   OSAL_IRQ_PROLOGUE();
+ 
+-  i2c_lld_serve_event_interrupt(&I2CD3);
++#if STM32_I2C_I2C3_USE_DMA
++  i2c_lld_serve_event_interrupt_dma(&I2CD3);
++#else
++  i2c_lld_serve_event_interrupt_isr(&I2CD3);
++#endif
+ 
+   OSAL_IRQ_EPILOGUE();
+ }
+@@ -540,19 +748,22 @@ void i2c_lld_start(I2CDriver *i2cp) {
+   /* If in stopped state then enables the I2C and DMA clocks.*/
+   if (i2cp->state == I2C_STOP) {
+ 
+-    i2cp->txdmamode = STM32_DMA_CR_PSIZE_BYTE | STM32_DMA_CR_MSIZE_BYTE |
+-                      STM32_DMA_CR_MINC       | STM32_DMA_CR_DMEIE |
+-                      STM32_DMA_CR_TEIE       | STM32_DMA_CR_TCIE |
+-                      STM32_DMA_CR_DIR_M2P;
+-    i2cp->rxdmamode = STM32_DMA_CR_PSIZE_BYTE | STM32_DMA_CR_MSIZE_BYTE |
+-                      STM32_DMA_CR_MINC       | STM32_DMA_CR_DMEIE |
+-                      STM32_DMA_CR_TEIE       | STM32_DMA_CR_TCIE |
+-                      STM32_DMA_CR_DIR_P2M;
+-
+ #if STM32_I2C_USE_I2C1
+     if (&I2CD1 == i2cp) {
++#if STM32_I2C_I2C1_USE_DMA
++      i2cp->txdmamode = STM32_DMA_CR_PSIZE_BYTE | STM32_DMA_CR_MSIZE_BYTE |
++                        STM32_DMA_CR_MINC       | STM32_DMA_CR_DMEIE |
++                        STM32_DMA_CR_TEIE       | STM32_DMA_CR_TCIE |
++                        STM32_DMA_CR_DIR_M2P;
++      i2cp->rxdmamode = STM32_DMA_CR_PSIZE_BYTE | STM32_DMA_CR_MSIZE_BYTE |
++                        STM32_DMA_CR_MINC       | STM32_DMA_CR_DMEIE |
++                        STM32_DMA_CR_TEIE       | STM32_DMA_CR_TCIE |
++                        STM32_DMA_CR_DIR_P2M;
++#endif
++
+       rccResetI2C1();
+ 
++#if STM32_I2C_I2C1_USE_DMA
+       i2cp->dmarx = dmaStreamAllocI(STM32_I2C_I2C1_RX_DMA_STREAM,
+                                     STM32_I2C_I2C1_IRQ_PRIORITY,
+                                     (stm32_dmaisr_t)i2c_lld_serve_rx_end_irq,
+@@ -563,22 +774,50 @@ void i2c_lld_start(I2CDriver *i2cp) {
+                                     (stm32_dmaisr_t)i2c_lld_serve_tx_end_irq,
+                                     (void *)i2cp);
+       osalDbgAssert(i2cp->dmatx != NULL, "unable to allocate stream");
++#endif
+ 
+       rccEnableI2C1(true);
+       nvicEnableVector(I2C1_EV_IRQn, STM32_I2C_I2C1_IRQ_PRIORITY);
+       nvicEnableVector(I2C1_ER_IRQn, STM32_I2C_I2C1_IRQ_PRIORITY);
+ 
++#if STM32_I2C_I2C1_USE_DMA
+       i2cp->rxdmamode |= STM32_DMA_CR_CHSEL(I2C1_RX_DMA_CHANNEL) |
+                        STM32_DMA_CR_PL(STM32_I2C_I2C1_DMA_PRIORITY);
+       i2cp->txdmamode |= STM32_DMA_CR_CHSEL(I2C1_TX_DMA_CHANNEL) |
+                        STM32_DMA_CR_PL(STM32_I2C_I2C1_DMA_PRIORITY);
++
++      /* I2C registers pointed by the DMA.*/
++      dmaStreamSetPeripheral(i2cp->dmarx, &dp->DR);
++      dmaStreamSetPeripheral(i2cp->dmatx, &dp->DR);
++#endif
++
++      /* Reset i2c peripheral.*/
++      dp->CR1 = I2C_CR1_SWRST;
++      dp->CR1 = 0;
++#if STM32_I2C_I2C1_USE_DMA
++      dp->CR2 = I2C_CR2_ITERREN | I2C_CR2_DMAEN;
++#else
++      dp->CR2 = I2C_CR2_ITERREN;
++#endif
+     }
+ #endif /* STM32_I2C_USE_I2C1 */
+ 
+ #if STM32_I2C_USE_I2C2
+     if (&I2CD2 == i2cp) {
++#if STM32_I2C_I2C2_USE_DMA
++      i2cp->txdmamode = STM32_DMA_CR_PSIZE_BYTE | STM32_DMA_CR_MSIZE_BYTE |
++                        STM32_DMA_CR_MINC       | STM32_DMA_CR_DMEIE |
++                        STM32_DMA_CR_TEIE       | STM32_DMA_CR_TCIE |
++                        STM32_DMA_CR_DIR_M2P;
++      i2cp->rxdmamode = STM32_DMA_CR_PSIZE_BYTE | STM32_DMA_CR_MSIZE_BYTE |
++                        STM32_DMA_CR_MINC       | STM32_DMA_CR_DMEIE |
++                        STM32_DMA_CR_TEIE       | STM32_DMA_CR_TCIE |
++                        STM32_DMA_CR_DIR_P2M;
++#endif
++
+       rccResetI2C2();
+ 
++#if STM32_I2C_I2C2_USE_DMA
+       i2cp->dmarx = dmaStreamAllocI(STM32_I2C_I2C2_RX_DMA_STREAM,
+                                     STM32_I2C_I2C2_IRQ_PRIORITY,
+                                     (stm32_dmaisr_t)i2c_lld_serve_rx_end_irq,
+@@ -589,22 +828,50 @@ void i2c_lld_start(I2CDriver *i2cp) {
+                                     (stm32_dmaisr_t)i2c_lld_serve_tx_end_irq,
+                                     (void *)i2cp);
+       osalDbgAssert(i2cp->dmatx != NULL, "unable to allocate stream");
++#endif
+ 
+       rccEnableI2C2(true);
+       nvicEnableVector(I2C2_EV_IRQn, STM32_I2C_I2C2_IRQ_PRIORITY);
+       nvicEnableVector(I2C2_ER_IRQn, STM32_I2C_I2C2_IRQ_PRIORITY);
+ 
++#if STM32_I2C_I2C2_USE_DMA
+       i2cp->rxdmamode |= STM32_DMA_CR_CHSEL(I2C2_RX_DMA_CHANNEL) |
+                        STM32_DMA_CR_PL(STM32_I2C_I2C2_DMA_PRIORITY);
+       i2cp->txdmamode |= STM32_DMA_CR_CHSEL(I2C2_TX_DMA_CHANNEL) |
+                        STM32_DMA_CR_PL(STM32_I2C_I2C2_DMA_PRIORITY);
++
++      /* I2C registers pointed by the DMA.*/
++      dmaStreamSetPeripheral(i2cp->dmarx, &dp->DR);
++      dmaStreamSetPeripheral(i2cp->dmatx, &dp->DR);
++#endif
++
++      /* Reset i2c peripheral.*/
++      dp->CR1 = I2C_CR1_SWRST;
++      dp->CR1 = 0;
++#if STM32_I2C_I2C2_USE_DMA
++      dp->CR2 = I2C_CR2_ITERREN | I2C_CR2_DMAEN;
++#else
++      dp->CR2 = I2C_CR2_ITERREN;
++#endif
+     }
+ #endif /* STM32_I2C_USE_I2C2 */
+ 
+ #if STM32_I2C_USE_I2C3
+     if (&I2CD3 == i2cp) {
++#if STM32_I2C_I2C3_USE_DMA
++      i2cp->txdmamode = STM32_DMA_CR_PSIZE_BYTE | STM32_DMA_CR_MSIZE_BYTE |
++                        STM32_DMA_CR_MINC       | STM32_DMA_CR_DMEIE |
++                        STM32_DMA_CR_TEIE       | STM32_DMA_CR_TCIE |
++                        STM32_DMA_CR_DIR_M2P;
++      i2cp->rxdmamode = STM32_DMA_CR_PSIZE_BYTE | STM32_DMA_CR_MSIZE_BYTE |
++                        STM32_DMA_CR_MINC       | STM32_DMA_CR_DMEIE |
++                        STM32_DMA_CR_TEIE       | STM32_DMA_CR_TCIE |
++                        STM32_DMA_CR_DIR_P2M;
++#endif
++
+       rccResetI2C3();
+ 
++#if STM32_I2C_I2C3_USE_DMA
+       i2cp->dmarx = dmaStreamAllocI(STM32_I2C_I2C3_RX_DMA_STREAM,
+                                     STM32_I2C_I2C3_IRQ_PRIORITY,
+                                     (stm32_dmaisr_t)i2c_lld_serve_rx_end_irq,
+@@ -615,28 +882,35 @@ void i2c_lld_start(I2CDriver *i2cp) {
+                                     (stm32_dmaisr_t)i2c_lld_serve_tx_end_irq,
+                                     (void *)i2cp);
+       osalDbgAssert(i2cp->dmatx != NULL, "unable to allocate stream");
++#endif
+ 
+       rccEnableI2C3(true);
+       nvicEnableVector(I2C3_EV_IRQn, STM32_I2C_I2C3_IRQ_PRIORITY);
+       nvicEnableVector(I2C3_ER_IRQn, STM32_I2C_I2C3_IRQ_PRIORITY);
+ 
++#if STM32_I2C_I2C3_USE_DMA
+       i2cp->rxdmamode |= STM32_DMA_CR_CHSEL(I2C3_RX_DMA_CHANNEL) |
+                        STM32_DMA_CR_PL(STM32_I2C_I2C3_DMA_PRIORITY);
+       i2cp->txdmamode |= STM32_DMA_CR_CHSEL(I2C3_TX_DMA_CHANNEL) |
+                        STM32_DMA_CR_PL(STM32_I2C_I2C3_DMA_PRIORITY);
++
++      /* I2C registers pointed by the DMA.*/
++      dmaStreamSetPeripheral(i2cp->dmarx, &dp->DR);
++      dmaStreamSetPeripheral(i2cp->dmatx, &dp->DR);
++#endif
++
++      /* Reset i2c peripheral.*/
++      dp->CR1 = I2C_CR1_SWRST;
++      dp->CR1 = 0;
++#if STM32_I2C_I2C3_USE_DMA
++      dp->CR2 = I2C_CR2_ITERREN | I2C_CR2_DMAEN;
++#else
++      dp->CR2 = I2C_CR2_ITERREN;
++#endif
+     }
+ #endif /* STM32_I2C_USE_I2C3 */
+   }
+ 
+-  /* I2C registers pointed by the DMA.*/
+-  dmaStreamSetPeripheral(i2cp->dmarx, &dp->DR);
+-  dmaStreamSetPeripheral(i2cp->dmatx, &dp->DR);
+-
+-  /* Reset i2c peripheral.*/
+-  dp->CR1 = I2C_CR1_SWRST;
+-  dp->CR1 = 0;
+-  dp->CR2 = I2C_CR2_ITERREN | I2C_CR2_DMAEN;
+-
+   /* Setup I2C parameters.*/
+   i2c_lld_set_clock(i2cp);
+   i2c_lld_set_opmode(i2cp);
+@@ -659,13 +933,15 @@ void i2c_lld_stop(I2CDriver *i2cp) {
+ 
+     /* I2C disable.*/
+     i2c_lld_abort_operation(i2cp);
+-    dmaStreamFreeI(i2cp->dmatx);
+-    dmaStreamFreeI(i2cp->dmarx);
+-    i2cp->dmatx = NULL;
+-    i2cp->dmarx = NULL;
+ 
+ #if STM32_I2C_USE_I2C1
+     if (&I2CD1 == i2cp) {
++#if STM32_I2C_I2C1_USE_DMA
++      dmaStreamFreeI(i2cp->dmatx);
++      dmaStreamFreeI(i2cp->dmarx);
++      i2cp->dmatx = NULL;
++      i2cp->dmarx = NULL;
++#endif
+       nvicDisableVector(I2C1_EV_IRQn);
+       nvicDisableVector(I2C1_ER_IRQn);
+       rccDisableI2C1();
+@@ -674,6 +950,12 @@ void i2c_lld_stop(I2CDriver *i2cp) {
+ 
+ #if STM32_I2C_USE_I2C2
+     if (&I2CD2 == i2cp) {
++#if STM32_I2C_I2C2_USE_DMA
++      dmaStreamFreeI(i2cp->dmatx);
++      dmaStreamFreeI(i2cp->dmarx);
++      i2cp->dmatx = NULL;
++      i2cp->dmarx = NULL;
++#endif
+       nvicDisableVector(I2C2_EV_IRQn);
+       nvicDisableVector(I2C2_ER_IRQn);
+       rccDisableI2C2();
+@@ -682,6 +964,12 @@ void i2c_lld_stop(I2CDriver *i2cp) {
+ 
+ #if STM32_I2C_USE_I2C3
+     if (&I2CD3 == i2cp) {
++#if STM32_I2C_I2C3_USE_DMA
++      dmaStreamFreeI(i2cp->dmatx);
++      dmaStreamFreeI(i2cp->dmarx);
++      i2cp->dmatx = NULL;
++      i2cp->dmarx = NULL;
++#endif
+       nvicDisableVector(I2C3_EV_IRQn);
+       nvicDisableVector(I2C3_ER_IRQn);
+       rccDisableI2C3();
+@@ -732,10 +1020,43 @@ msg_t i2c_lld_master_receive_timeout(I2CDriver *i2cp, i2caddr_t addr,
+   /* Releases the lock from high level driver.*/
+   osalSysUnlock();
+ 
+-  /* RX DMA setup.*/
+-  dmaStreamSetMode(i2cp->dmarx, i2cp->rxdmamode);
+-  dmaStreamSetMemory0(i2cp->dmarx, rxbuf);
+-  dmaStreamSetTransactionSize(i2cp->dmarx, rxbytes);
++  /* RX (DMA) setup.*/
++#if STM32_I2C_USE_I2C1
++  if (&I2CD1 == i2cp) {
++#if STM32_I2C_I2C1_USE_DMA
++    dmaStreamSetMode(i2cp->dmarx, i2cp->rxdmamode);
++    dmaStreamSetMemory0(i2cp->dmarx, rxbuf);
++    dmaStreamSetTransactionSize(i2cp->dmarx, rxbytes);
++#else
++    i2cp->rxbuf = rxbuf;
++    i2cp->rxbytes = rxbytes;
++#endif
++  }
++#endif
++#if STM32_I2C_USE_I2C2
++  if (&I2CD2 == i2cp) {
++#if STM32_I2C_I2C2_USE_DMA
++    dmaStreamSetMode(i2cp->dmarx, i2cp->rxdmamode);
++    dmaStreamSetMemory0(i2cp->dmarx, rxbuf);
++    dmaStreamSetTransactionSize(i2cp->dmarx, rxbytes);
++#else
++    i2cp->rxbuf = rxbuf;
++    i2cp->rxbytes = rxbytes;
++#endif
++  }
++#endif
++#if STM32_I2C_USE_I2C3
++  if (&I2CD3 == i2cp) {
++#if STM32_I2C_I2C3_USE_DMA
++    dmaStreamSetMode(i2cp->dmarx, i2cp->rxdmamode);
++    dmaStreamSetMemory0(i2cp->dmarx, rxbuf);
++    dmaStreamSetTransactionSize(i2cp->dmarx, rxbytes);
++#else
++    i2cp->rxbuf = rxbuf;
++    i2cp->rxbytes = rxbytes;
++#endif
++  }
++#endif
+ 
+   /* Calculating the time window for the timeout on the busy bus condition.*/
+   start = osalOsGetSystemTimeX();
+@@ -812,15 +1133,61 @@ msg_t i2c_lld_master_transmit_timeout(I2CDriver *i2cp, i2caddr_t addr,
+   /* Releases the lock from high level driver.*/
+   osalSysUnlock();
+ 
+-  /* TX DMA setup.*/
+-  dmaStreamSetMode(i2cp->dmatx, i2cp->txdmamode);
+-  dmaStreamSetMemory0(i2cp->dmatx, txbuf);
+-  dmaStreamSetTransactionSize(i2cp->dmatx, txbytes);
+-
+-  /* RX DMA setup.*/
+-  dmaStreamSetMode(i2cp->dmarx, i2cp->rxdmamode);
+-  dmaStreamSetMemory0(i2cp->dmarx, rxbuf);
+-  dmaStreamSetTransactionSize(i2cp->dmarx, rxbytes);
++  /* TX (DMA) and RX (DMA) setup.*/
++#if STM32_I2C_USE_I2C1
++  if (&I2CD1 == i2cp) {
++#if STM32_I2C_I2C1_USE_DMA
++    dmaStreamSetMode(i2cp->dmatx, i2cp->txdmamode);
++    dmaStreamSetMemory0(i2cp->dmatx, txbuf);
++    dmaStreamSetTransactionSize(i2cp->dmatx, txbytes);
++
++    dmaStreamSetMode(i2cp->dmarx, i2cp->rxdmamode);
++    dmaStreamSetMemory0(i2cp->dmarx, rxbuf);
++    dmaStreamSetTransactionSize(i2cp->dmarx, rxbytes);
++#else
++    i2cp->txbuf = txbuf;
++    i2cp->txbytes = txbytes;
++    i2cp->rxbuf = rxbuf;
++    i2cp->rxbytes = rxbytes;
++#endif
++  }
++#endif
++#if STM32_I2C_USE_I2C2
++  if (&I2CD2 == i2cp) {
++#if STM32_I2C_I2C2_USE_DMA
++    dmaStreamSetMode(i2cp->dmatx, i2cp->txdmamode);
++    dmaStreamSetMemory0(i2cp->dmatx, txbuf);
++    dmaStreamSetTransactionSize(i2cp->dmatx, txbytes);
++
++    dmaStreamSetMode(i2cp->dmarx, i2cp->rxdmamode);
++    dmaStreamSetMemory0(i2cp->dmarx, rxbuf);
++    dmaStreamSetTransactionSize(i2cp->dmarx, rxbytes);
++#else
++    i2cp->txbuf = txbuf;
++    i2cp->txbytes = txbytes;
++    i2cp->rxbuf = rxbuf;
++    i2cp->rxbytes = rxbytes;
++#endif
++  }
++#endif
++#if STM32_I2C_USE_I2C3
++  if (&I2CD3 == i2cp) {
++#if STM32_I2C_I2C3_USE_DMA
++    dmaStreamSetMode(i2cp->dmatx, i2cp->txdmamode);
++    dmaStreamSetMemory0(i2cp->dmatx, txbuf);
++    dmaStreamSetTransactionSize(i2cp->dmatx, txbytes);
++
++    dmaStreamSetMode(i2cp->dmarx, i2cp->rxdmamode);
++    dmaStreamSetMemory0(i2cp->dmarx, rxbuf);
++    dmaStreamSetTransactionSize(i2cp->dmarx, rxbytes);
++#else
++    i2cp->txbuf = txbuf;
++    i2cp->txbytes = txbytes;
++    i2cp->rxbuf = rxbuf;
++    i2cp->rxbytes = rxbytes;
++#endif
++  }
++#endif
+ 
+   /* Calculating the time window for the timeout on the busy bus condition.*/
+   start = osalOsGetSystemTimeX();
 diff --git a/os/hal/ports/STM32/LLD/I2Cv1/hal_i2c_lld.h b/os/hal/ports/STM32/LLD/I2Cv1/hal_i2c_lld.h
-index 1328d47..68f91e1 100644
 --- a/os/hal/ports/STM32/LLD/I2Cv1/hal_i2c_lld.h
 +++ b/os/hal/ports/STM32/LLD/I2Cv1/hal_i2c_lld.h
-@@ -104,6 +104,33 @@
- #endif
- 
- /**
-+ * @brief   I2C1 DMA enable switch.
-+ * @details If set to @p TRUE the I2C1 driver will use DMA.
-+ * @note    The default is @p TRUE.
-+ */
-+#if !defined(STM32_I2C_I2C1_USE_DMA) || defined(__DOXYGEN__)
-+#define STM32_I2C_I2C1_USE_DMA              TRUE
-+#endif
-+
-+/**
-+ * @brief   I2C2 DMA enable switch.
-+ * @details If set to @p TRUE the I2C2 driver will use DMA.
-+ * @note    The default is @p TRUE.
-+ */
-+#if !defined(STM32_I2C_I2C2_USE_DMA) || defined(__DOXYGEN__)
-+#define STM32_I2C_I2C2_USE_DMA              TRUE
-+#endif
-+
-+/**
-+ * @brief   I2C3 DMA enable switch.
-+ * @details If set to @p TRUE the I2C3 driver will use DMA.
-+ * @note    The default is @p TRUE.
-+ */
-+#if !defined(STM32_I2C_I2C3_USE_DMA) || defined(__DOXYGEN__)
-+#define STM32_I2C_I2C3_USE_DMA              TRUE
-+#endif
-+
-+/**
- * @brief   I2C1 DMA priority (0..3|lowest..highest).
- * @note    The priority level is used for both the TX and RX DMA streams but
- *          because of the streams ordering the RX stream has always priority
+@@ -103,6 +103,33 @@
+ #define STM32_I2C_I2C3_IRQ_PRIORITY         10
+ #endif
+ 
++/**
++ * @brief   I2C1 DMA enable switch.
++ * @details If set to @p TRUE the I2C1 driver will use DMA.
++ * @note    The default is @p TRUE.
++ */
++#if !defined(STM32_I2C_I2C1_USE_DMA) || defined(__DOXYGEN__)
++#define STM32_I2C_I2C1_USE_DMA              TRUE
++#endif
++
++/**
++ * @brief   I2C2 DMA enable switch.
++ * @details If set to @p TRUE the I2C2 driver will use DMA.
++ * @note    The default is @p TRUE.
++ */
++#if !defined(STM32_I2C_I2C2_USE_DMA) || defined(__DOXYGEN__)
++#define STM32_I2C_I2C2_USE_DMA              TRUE
++#endif
++
++/**
++ * @brief   I2C3 DMA enable switch.
++ * @details If set to @p TRUE the I2C3 driver will use DMA.
++ * @note    The default is @p TRUE.
++ */
++#if !defined(STM32_I2C_I2C3_USE_DMA) || defined(__DOXYGEN__)
++#define STM32_I2C_I2C3_USE_DMA              TRUE
++#endif
++
+ /**
+ * @brief   I2C1 DMA priority (0..3|lowest..highest).
+ * @note    The priority level is used for both the TX and RX DMA streams but
 @@ -250,16 +277,19 @@
- #endif
- 
- #if STM32_I2C_USE_I2C1 &&                                                   \
-+    STM32_I2C_I2C1_USE_DMA &&                                               \
-     !STM32_DMA_IS_VALID_PRIORITY(STM32_I2C_I2C1_DMA_PRIORITY)
- #error "Invalid DMA priority assigned to I2C1"
- #endif
- 
- #if STM32_I2C_USE_I2C2 &&                                                   \
-+    STM32_I2C_I2C2_USE_DMA &&                                               \
-     !STM32_DMA_IS_VALID_PRIORITY(STM32_I2C_I2C2_DMA_PRIORITY)
- #error "Invalid DMA priority assigned to I2C2"
- #endif
- 
- #if STM32_I2C_USE_I2C3 &&                                                   \
-+    STM32_I2C_I2C3_USE_DMA &&                                               \
-     !STM32_DMA_IS_VALID_PRIORITY(STM32_I2C_I2C3_DMA_PRIORITY)
- #error "Invalid DMA priority assigned to I2C3"
- #endif
+ #endif
+ 
+ #if STM32_I2C_USE_I2C1 &&                                                   \
++    STM32_I2C_I2C1_USE_DMA &&                                               \
+     !STM32_DMA_IS_VALID_PRIORITY(STM32_I2C_I2C1_DMA_PRIORITY)
+ #error "Invalid DMA priority assigned to I2C1"
+ #endif
+ 
+ #if STM32_I2C_USE_I2C2 &&                                                   \
++    STM32_I2C_I2C2_USE_DMA &&                                               \
+     !STM32_DMA_IS_VALID_PRIORITY(STM32_I2C_I2C2_DMA_PRIORITY)
+ #error "Invalid DMA priority assigned to I2C2"
+ #endif
+ 
+ #if STM32_I2C_USE_I2C3 &&                                                   \
++    STM32_I2C_I2C3_USE_DMA &&                                               \
+     !STM32_DMA_IS_VALID_PRIORITY(STM32_I2C_I2C3_DMA_PRIORITY)
+ #error "Invalid DMA priority assigned to I2C3"
+ #endif
 @@ -316,7 +346,10 @@
- #endif
- #endif /* STM32_ADVANCED_DMA */
- 
--#if !defined(STM32_DMA_REQUIRED)
-+#if ((STM32_I2C_USE_I2C1 && STM32_I2C_I2C1_USE_DMA) ||                       \
-+     (STM32_I2C_USE_I2C2 && STM32_I2C_I2C2_USE_DMA) ||                       \
-+     (STM32_I2C_USE_I2C3 && STM32_I2C_I2C3_USE_DMA)) &&                      \
-+    !defined(STM32_DMA_REQUIRED)
- #define STM32_DMA_REQUIRED
- #endif
- 
+ #endif
+ #endif /* STM32_ADVANCED_DMA */
+ 
+-#if !defined(STM32_DMA_REQUIRED)
++#if ((STM32_I2C_USE_I2C1 && STM32_I2C_I2C1_USE_DMA) ||                       \
++     (STM32_I2C_USE_I2C2 && STM32_I2C_I2C2_USE_DMA) ||                       \
++     (STM32_I2C_USE_I2C3 && STM32_I2C_I2C3_USE_DMA)) &&                      \
++    !defined(STM32_DMA_REQUIRED)
+ #define STM32_DMA_REQUIRED
+ #endif
+ 
 @@ -437,21 +470,52 @@ struct I2CDriver {
-    */
-   i2caddr_t                 addr;
-   /**
--   * @brief RX DMA mode bit mask.
--   */
--  uint32_t                  rxdmamode;
--  /**
--   * @brief TX DMA mode bit mask.
--   */
--  uint32_t                  txdmamode;
--  /**
--   * @brief     Receive DMA channel.
--   */
--  const stm32_dma_stream_t  *dmarx;
--  /**
--   * @brief     Transmit DMA channel.
-+   * @brief   Anonymous union to store transmission related data for either DMA or non-DMA mode.
-    */
--  const stm32_dma_stream_t  *dmatx;
-+  union {
-+    /**
-+     * @brief   Anonymous struct to store data for DMA mode.
-+     */
-+    struct {
-+      /**
-+       * @brief RX DMA mode bit mask.
-+       */
-+      uint32_t                  rxdmamode;
-+      /**
-+       * @brief TX DMA mode bit mask.
-+       */
-+      uint32_t                  txdmamode;
-+      /**
-+       * @brief     Receive DMA channel.
-+       */
-+      const stm32_dma_stream_t  *dmarx;
-+      /**
-+       * @brief     Transmit DMA channel.
-+       */
-+      const stm32_dma_stream_t  *dmatx;
-+    };
-+    /**
-+     * @brief   Anonymous struct to store data for non-DMA mode.
-+     */
-+    struct {
-+      /**
-+       * @brief   Receive buffer.
-+       */
-+      uint8_t                   *rxbuf;
-+      /**
-+       * @brief   Size of the receive buffer.
-+       */
-+      size_t                    rxbytes;
-+      /**
-+       * @brief   Transmit buffer.
-+       */
-+      const uint8_t             *txbuf;
-+      /**
-+       * @brief   Size of the transmit buffer.
-+       */
-+      size_t                    txbytes;
-+    };
-+  };
-   /**
-    * @brief     Pointer to the I2Cx registers block.
-    */
+    */
+   i2caddr_t                 addr;
+   /**
+-   * @brief RX DMA mode bit mask.
+-   */
+-  uint32_t                  rxdmamode;
+-  /**
+-   * @brief TX DMA mode bit mask.
+-   */
+-  uint32_t                  txdmamode;
+-  /**
+-   * @brief     Receive DMA channel.
+-   */
+-  const stm32_dma_stream_t  *dmarx;
+-  /**
+-   * @brief     Transmit DMA channel.
++   * @brief   Anonymous union to store transmission related data for either DMA or non-DMA mode.
+    */
+-  const stm32_dma_stream_t  *dmatx;
++  union {
++    /**
++     * @brief   Anonymous struct to store data for DMA mode.
++     */
++    struct {
++      /**
++       * @brief RX DMA mode bit mask.
++       */
++      uint32_t                  rxdmamode;
++      /**
++       * @brief TX DMA mode bit mask.
++       */
++      uint32_t                  txdmamode;
++      /**
++       * @brief     Receive DMA channel.
++       */
++      const stm32_dma_stream_t  *dmarx;
++      /**
++       * @brief     Transmit DMA channel.
++       */
++      const stm32_dma_stream_t  *dmatx;
++    };
++    /**
++     * @brief   Anonymous struct to store data for non-DMA mode.
++     */
++    struct {
++      /**
++       * @brief   Receive buffer.
++       */
++      uint8_t                   *rxbuf;
++      /**
++       * @brief   Size of the receive buffer.
++       */
++      size_t                    rxbytes;
++      /**
++       * @brief   Transmit buffer.
++       */
++      const uint8_t             *txbuf;
++      /**
++       * @brief   Size of the transmit buffer.
++       */
++      size_t                    txbytes;
++    };
++  };
+   /**
+    * @brief     Pointer to the I2Cx registers block.
+    */
diff --git a/kernel/patches/QEI-driver.patch b/kernel/patches/QEI-driver.patch
index 91fcfe6..8ca8292 100644
--- a/kernel/patches/QEI-driver.patch
+++ b/kernel/patches/QEI-driver.patch
@@ -1,30 +1,28 @@
 diff --git a/os/hal/hal.mk b/os/hal/hal.mk
-index f177a3f..64d96d9 100644
 --- a/os/hal/hal.mk
 +++ b/os/hal/hal.mk
-@@ -41,6 +41,9 @@ endif
- ifneq ($(findstring HAL_USE_ICU TRUE,$(HALCONF)),)
- HALSRC += $(CHIBIOS)/os/hal/src/hal_icu.c
+@@ -54,6 +54,9 @@ endif
+ ifneq ($(findstring HAL_USE_PWM TRUE,$(HALCONF)),)
+ HALSRC += $(CHIBIOS)/os/hal/src/hal_pwm.c
  endif
 +ifneq ($(findstring HAL_USE_QEI TRUE,$(HALCONF)),)
 +HALSRC += $(CHIBIOS)/os/hal/src/hal_qei.c
 +endif
- ifneq ($(findstring HAL_USE_MAC TRUE,$(HALCONF)),)
- HALSRC += $(CHIBIOS)/os/hal/src/hal_mac.c
+ ifneq ($(findstring HAL_USE_RTC TRUE,$(HALCONF)),)
+ HALSRC += $(CHIBIOS)/os/hal/src/hal_rtc.c
  endif
-@@ -94,6 +97,7 @@ HALSRC = $(CHIBIOS)/os/hal/src/hal.c \
-          $(CHIBIOS)/os/hal/src/hal_i2c.c \
-          $(CHIBIOS)/os/hal/src/hal_i2s.c \
-          $(CHIBIOS)/os/hal/src/hal_icu.c \
-+         $(CHIBIOS)/os/hal/src/hal_qei.c \
-          $(CHIBIOS)/os/hal/src/hal_mac.c \
+@@ -104,6 +107,7 @@ HALSRC = $(CHIBIOS)/os/hal/src/hal.c \
           $(CHIBIOS)/os/hal/src/hal_mmc_spi.c \
           $(CHIBIOS)/os/hal/src/hal_pal.c \
+          $(CHIBIOS)/os/hal/src/hal_pwm.c \
++         $(CHIBIOS)/os/hal/src/hal_qei.c \
+          $(CHIBIOS)/os/hal/src/hal_rtc.c \
+          $(CHIBIOS)/os/hal/src/hal_sdc.c \
+          $(CHIBIOS)/os/hal/src/hal_serial.c \
 diff --git a/os/hal/include/hal.h b/os/hal/include/hal.h
-index 79f7c42..8cf221f 100644
 --- a/os/hal/include/hal.h
 +++ b/os/hal/include/hal.h
-@@ -78,6 +78,10 @@
+@@ -74,6 +74,10 @@
  #define HAL_USE_PWM                         FALSE
  #endif
  
@@ -32,26 +30,25 @@ index 79f7c42..8cf221f 100644
 +#define HAL_USE_QEI                         FALSE
 +#endif
 +
- #if !defined(HAL_USE_QSPI)
- #define HAL_USE_QSPI                        FALSE
+ #if !defined(HAL_USE_RTC)
+ #define HAL_USE_RTC                         FALSE
  #endif
-@@ -138,6 +142,7 @@
+@@ -142,6 +146,7 @@
  #include "hal_icu.h"
  #include "hal_mac.h"
  #include "hal_pwm.h"
 +#include "hal_qei.h"
- #include "hal_qspi.h"
  #include "hal_rtc.h"
  #include "hal_serial.h"
+ #include "hal_sdc.h"
 diff --git a/os/hal/include/hal_qei.h b/os/hal/include/hal_qei.h
 new file mode 100644
-index 0000000..8769729
 --- /dev/null
 +++ b/os/hal/include/hal_qei.h
 @@ -0,0 +1,148 @@
 +/*
 +AMiRo-OS is an operating system designed for the Autonomous Mini Robot (AMiRo) platform.
-+Copyright (C) 2016..2018  Thomas Schöpping et al.
++Copyright (C) 2016..2019  Thomas Schöpping et al.
 +
 +This program is free software: you can redistribute it and/or modify
 +it under the terms of the GNU General Public License as published by
@@ -192,13 +189,12 @@ index 0000000..8769729
 +}
 +#endif
 +
-+#endif /* HAL_USE_QEI */
++#endif /* HAL_USE_QEI == TRUE */
 +
 +#endif /* HAL_QEI_H */
 +
 +/** @} */
 diff --git a/os/hal/ports/STM32/LLD/TIMv1/driver.mk b/os/hal/ports/STM32/LLD/TIMv1/driver.mk
-index 032d75a..13e3571 100644
 --- a/os/hal/ports/STM32/LLD/TIMv1/driver.mk
 +++ b/os/hal/ports/STM32/LLD/TIMv1/driver.mk
 @@ -10,10 +10,14 @@ endif
@@ -218,13 +214,12 @@ index 032d75a..13e3571 100644
  PLATFORMINC += $(CHIBIOS)/os/hal/ports/STM32/LLD/TIMv1
 diff --git a/os/hal/ports/STM32/LLD/TIMv1/hal_qei_lld.c b/os/hal/ports/STM32/LLD/TIMv1/hal_qei_lld.c
 new file mode 100644
-index 0000000..cd1ab9b
 --- /dev/null
 +++ b/os/hal/ports/STM32/LLD/TIMv1/hal_qei_lld.c
 @@ -0,0 +1,304 @@
 +/*
 +AMiRo-OS is an operating system designed for the Autonomous Mini Robot (AMiRo) platform.
-+Copyright (C) 2016..2018  Thomas Schöpping et al.
++Copyright (C) 2016..2019  Thomas Schöpping et al.
 +
 +This program is free software: you can redistribute it and/or modify
 +it under the terms of the GNU General Public License as published by
@@ -528,13 +523,12 @@ index 0000000..cd1ab9b
 +/** @} */
 diff --git a/os/hal/ports/STM32/LLD/TIMv1/hal_qei_lld.h b/os/hal/ports/STM32/LLD/TIMv1/hal_qei_lld.h
 new file mode 100644
-index 0000000..ec1cd42
 --- /dev/null
 +++ b/os/hal/ports/STM32/LLD/TIMv1/hal_qei_lld.h
 @@ -0,0 +1,302 @@
 +/*
 +AMiRo-OS is an operating system designed for the Autonomous Mini Robot (AMiRo) platform.
-+Copyright (C) 2016..2018  Thomas Schöpping et al.
++Copyright (C) 2016..2019  Thomas Schöpping et al.
 +
 +This program is free software: you can redistribute it and/or modify
 +it under the terms of the GNU General Public License as published by
@@ -836,13 +830,12 @@ index 0000000..ec1cd42
 +/** @} */
 diff --git a/os/hal/src/hal_qei.c b/os/hal/src/hal_qei.c
 new file mode 100644
-index 0000000..00334bb
 --- /dev/null
 +++ b/os/hal/src/hal_qei.c
 @@ -0,0 +1,152 @@
 +/*
 +AMiRo-OS is an operating system designed for the Autonomous Mini Robot (AMiRo) platform.
-+Copyright (C) 2016..2018  Thomas Schöpping et al.
++Copyright (C) 2016..2019  Thomas Schöpping et al.
 +
 +This program is free software: you can redistribute it and/or modify
 +it under the terms of the GNU General Public License as published by
@@ -989,6 +982,6 @@ index 0000000..00334bb
 +  osalSysUnlock();
 +}
 +
-+#endif /* HAL_USE_QEI */
++#endif /* HAL_USE_QEI == TRUE */
 +
 +/** @} */
diff --git a/kernel/patches/chTimeAddX-overflow-fix.patch b/kernel/patches/chTimeAddX-overflow-fix.patch
index 254723e..8c139d7 100644
--- a/kernel/patches/chTimeAddX-overflow-fix.patch
+++ b/kernel/patches/chTimeAddX-overflow-fix.patch
@@ -1,8 +1,7 @@
 diff --git a/os/rt/include/chtime.h b/os/rt/include/chtime.h
-index c975d10..99ce8d8 100644
 --- a/os/rt/include/chtime.h
 +++ b/os/rt/include/chtime.h
-@@ -472,11 +472,11 @@ static inline time_usecs_t chTimeI2US(sysinterval_t interval) {
+@@ -441,11 +441,11 @@ static inline time_usecs_t chTimeI2US(sysinterval_t interval) {
  static inline systime_t chTimeAddX(systime_t systime,
                                     sysinterval_t interval) {
  
diff --git a/kernel/patches/introduce-thread-hierarchy.patch b/kernel/patches/introduce-thread-hierarchy.patch
index 57ef13b..5632a88 100644
--- a/kernel/patches/introduce-thread-hierarchy.patch
+++ b/kernel/patches/introduce-thread-hierarchy.patch
@@ -1,11 +1,11 @@
 diff --git a/os/rt/include/chschd.h b/os/rt/include/chschd.h
-index 1d11d17..c71d8b4 100644
 --- a/os/rt/include/chschd.h
 +++ b/os/rt/include/chschd.h
-@@ -177,6 +177,23 @@ struct ch_thread {
+@@ -176,6 +176,23 @@ struct ch_thread {
+    * @brief   References to this thread.
     */
    trefs_t               refs;
- #endif
++#endif
 +#if (CH_CFG_USE_THREADHIERARCHY == TRUE) || defined(__DOXYGEN__)
 +  /**
 +   * @brief   Pointer to the parent thread.
@@ -22,35 +22,38 @@ index 1d11d17..c71d8b4 100644
 +   * @brief   NULL if there are no more child threads.
 +   */
 +  thread_t              *sibling;
-+#endif
+ #endif
    /**
     * @brief   Number of ticks remaining to this thread.
-    */
 diff --git a/os/rt/include/chthreads.h b/os/rt/include/chthreads.h
-index 166d566..b767d74 100644
 --- a/os/rt/include/chthreads.h
 +++ b/os/rt/include/chthreads.h
-@@ -79,6 +79,10 @@ typedef struct {
+@@ -79,6 +79,12 @@ typedef struct {
     * @brief   Thread argument.
     */
    void              *arg;
++#if (CH_CFG_USE_THREADHIERARCHY) == TRUE || defined(__DOXYGEN__)
 +  /**
 +   * @brief   Pointer to the parent thread.
 +   */
 +  thread_t          *parent;
++#endif
  } thread_descriptor_t;
  
  /*===========================================================================*/
-@@ -220,7 +224,7 @@ typedef struct {
+@@ -220,7 +226,11 @@ typedef struct {
  #ifdef __cplusplus
  extern "C" {
  #endif
--   thread_t *_thread_init(thread_t *tp, const char *name, tprio_t prio);
++#if CH_CFG_USE_THREADHIERARCHY == TRUE
 +   thread_t *_thread_init(thread_t *tp, thread_t* parent, const char *name, tprio_t prio);
++#else
+    thread_t *_thread_init(thread_t *tp, const char *name, tprio_t prio);
++#endif
  #if CH_DBG_FILL_THREADS == TRUE
    void _thread_memfill(uint8_t *startp, uint8_t *endp, uint8_t v);
  #endif
-@@ -228,8 +232,13 @@ extern "C" {
+@@ -228,8 +238,13 @@ extern "C" {
    thread_t *chThdCreateSuspended(const thread_descriptor_t *tdp);
    thread_t *chThdCreateI(const thread_descriptor_t *tdp);
    thread_t *chThdCreate(const thread_descriptor_t *tdp);
@@ -65,39 +68,49 @@ index 166d566..b767d74 100644
  #if CH_CFG_USE_REGISTRY == TRUE
    thread_t *chThdAddRef(thread_t *tp);
 diff --git a/os/rt/src/chsys.c b/os/rt/src/chsys.c
-index 346a8ba..c789d01 100644
 --- a/os/rt/src/chsys.c
 +++ b/os/rt/src/chsys.c
-@@ -126,13 +126,13 @@ void chSysInit(void) {
+@@ -126,14 +126,26 @@ void chSysInit(void) {
  #if CH_CFG_NO_IDLE_THREAD == FALSE
    /* Now this instructions flow becomes the main thread.*/
  #if CH_CFG_USE_REGISTRY == TRUE
--  currp = _thread_init(&ch.mainthread, (const char *)&ch_debug, NORMALPRIO);
++#if CH_CFG_USE_THREADHIERARCHY == TRUE
 +  currp = _thread_init(&ch.mainthread, NULL, (const char *)&ch_debug, NORMALPRIO);
- #else
--  currp = _thread_init(&ch.mainthread, "main", NORMALPRIO);
++#else
+   currp = _thread_init(&ch.mainthread, (const char *)&ch_debug, NORMALPRIO);
++#endif
++#else
++#if CH_CFG_USE_THREADHIERARCHY == TRUE
 +  currp = _thread_init(&ch.mainthread, NULL, "main", NORMALPRIO);
+ #else
+   currp = _thread_init(&ch.mainthread, "main", NORMALPRIO);
  #endif
++#endif
  #else
    /* Now this instructions flow becomes the idle thread.*/
--  currp = _thread_init(&ch.mainthread, "idle", IDLEPRIO);
++#if CH_CFG_USE_THREADHIERARCHY == TRUE
 +  currp = _thread_init(&ch.mainthread, NULL, "idle", IDLEPRIO);
++#else
+   currp = _thread_init(&ch.mainthread, "idle", IDLEPRIO);
  #endif
++#endif
  
  #if CH_DBG_ENABLE_STACK_CHECK == TRUE
-@@ -172,6 +172,7 @@ void chSysInit(void) {
+   {
+@@ -172,6 +184,9 @@ void chSysInit(void) {
        THD_WORKING_AREA_END(ch_idle_thread_wa),
        IDLEPRIO,
        _idle_thread,
++#if CH_CFG_USE_THREADHIERARCHY == TRUE
 +      NULL,
++#endif
        NULL
      };
  
 diff --git a/os/rt/src/chthreads.c b/os/rt/src/chthreads.c
-index 171c683..6bc0f78 100644
 --- a/os/rt/src/chthreads.c
 +++ b/os/rt/src/chthreads.c
-@@ -70,6 +70,46 @@
+@@ -70,22 +70,67 @@
  /* Module local functions.                                                   */
  /*===========================================================================*/
  
@@ -144,7 +157,10 @@ index 171c683..6bc0f78 100644
  /*===========================================================================*/
  /* Module exported functions.                                                */
  /*===========================================================================*/
-@@ -79,13 +119,14 @@
+ 
++#if CH_CFG_USE_THREADHIERARCHY == TRUE || defined(__DOXYGEN__)
+ /**
+  * @brief   Initializes a thread structure.
   * @note    This is an internal functions, do not use it in application code.
   *
   * @param[in] tp        pointer to the thread
@@ -155,12 +171,14 @@ index 171c683..6bc0f78 100644
   *
   * @notapi
   */
--thread_t *_thread_init(thread_t *tp, const char *name, tprio_t prio) {
 +thread_t *_thread_init(thread_t *tp, thread_t *parent,  const char *name, tprio_t prio) {
++#else
+ thread_t *_thread_init(thread_t *tp, const char *name, tprio_t prio) {
++#endif
  
    tp->prio      = prio;
    tp->state     = CH_STATE_WTSTART;
-@@ -110,6 +151,17 @@ thread_t *_thread_init(thread_t *tp, const char *name, tprio_t prio) {
+@@ -110,6 +155,17 @@ thread_t *_thread_init(thread_t *tp, const char *name, tprio_t prio) {
  #else
    (void)name;
  #endif
@@ -178,16 +196,27 @@ index 171c683..6bc0f78 100644
  #if CH_CFG_USE_WAITEXIT == TRUE
    list_init(&tp->waiting);
  #endif
-@@ -190,7 +242,7 @@ thread_t *chThdCreateSuspendedI(const thread_descriptor_t *tdp) {
+@@ -190,7 +246,11 @@ thread_t *chThdCreateSuspendedI(const thread_descriptor_t *tdp) {
    PORT_SETUP_CONTEXT(tp, tdp->wbase, tp, tdp->funcp, tdp->arg);
  
    /* The driver object is initialized but not started.*/
--  return _thread_init(tp, tdp->name, tdp->prio);
++#if CH_CFG_USE_THREADHIERARCHY == TRUE
 +  return _thread_init(tp, tdp->parent, tdp->name, tdp->prio);
++#else
+   return _thread_init(tp, tdp->name, tdp->prio);
++#endif
+ }
+ 
+ /**
+@@ -300,6 +360,7 @@ thread_t *chThdCreate(const thread_descriptor_t *tdp) {
+   return tp;
  }
  
++#if CH_CFG_USE_THREADHIERARCHY == TRUE || defined(__DOXYGEN__)
  /**
-@@ -315,13 +367,21 @@ thread_t *chThdCreate(const thread_descriptor_t *tdp) {
+  * @brief   Creates a new thread into a static memory area.
+  * @post    The created thread has a reference counter set to one, it is
+@@ -315,13 +376,20 @@ thread_t *chThdCreate(const thread_descriptor_t *tdp) {
   * @param[in] pf        the thread function
   * @param[in] arg       an argument passed to the thread function. It can be
   *                      @p NULL.
@@ -199,7 +228,6 @@ index 171c683..6bc0f78 100644
   *
   * @api
   */
-+#if (CH_CFG_USE_THREADHIERARCHY == TRUE) || defined(__DOXYGEN__)
 +thread_t *chThdCreateStatic(void *wsp, size_t size,
 +                            tprio_t prio, tfunc_t pf, void *arg, thread_t *parent) {
 +#else
@@ -209,20 +237,19 @@ index 171c683..6bc0f78 100644
    thread_t *tp;
  
    chDbgCheck((wsp != NULL) &&
-@@ -358,7 +418,11 @@ thread_t *chThdCreateStatic(void *wsp, size_t size,
+@@ -358,7 +426,11 @@ thread_t *chThdCreateStatic(void *wsp, size_t size,
    /* Setting up the port-dependent part of the working area.*/
    PORT_SETUP_CONTEXT(tp, wsp, tp, pf, arg);
  
--  tp = _thread_init(tp, "noname", prio);
 +#if CH_CFG_USE_THREADHIERARCHY == TRUE
 +  tp = _thread_init(tp, parent, "noname", prio);
 +#else
-+  tp = _thread_init(tp, NULL, "noname", prio);
+   tp = _thread_init(tp, "noname", prio);
 +#endif
  
    /* Starting the thread immediately.*/
    chSchWakeupS(tp, MSG_OK);
-@@ -529,6 +593,30 @@ void chThdExitS(msg_t msg) {
+@@ -529,6 +601,30 @@ void chThdExitS(msg_t msg) {
  #endif
  #endif
  
@@ -253,10 +280,11 @@ index 171c683..6bc0f78 100644
    /* Going into final state.*/
    chSchGoSleepS(CH_STATE_FINAL);
  
-@@ -611,6 +699,43 @@ tprio_t chThdSetPriority(tprio_t newprio) {
+@@ -610,6 +706,43 @@ tprio_t chThdSetPriority(tprio_t newprio) {
+ #else
    oldprio = currp->prio;
    currp->prio = newprio;
- #endif
++#endif
 +#if (CH_CFG_USE_THREADHIERARCHY == TRUE) && (CH_CFG_THREADHIERARCHY_ORDERED == TRUE)
 +  /* Reorder sibling list. */
 +  if (currp->parent != NULL && newprio != oldprio) {
@@ -293,12 +321,10 @@ index 171c683..6bc0f78 100644
 +      }
 +    }
 +  }
-+#endif
+ #endif
    chSchRescheduleS();
    chSysUnlock();
- 
 diff --git a/test/rt/source/test/rt_test_root.c b/test/rt/source/test/rt_test_root.c
-index e03d0f1..150d33d 100644
 --- a/test/rt/source/test/rt_test_root.c
 +++ b/test/rt/source/test/rt_test_root.c
 @@ -106,6 +106,14 @@ void * ROMCONST wa[5] = {test_buffer + (WA_SIZE * 0),
@@ -317,7 +343,6 @@ index e03d0f1..150d33d 100644
   * Sets a termination request in all the test-spawned threads.
   */
 diff --git a/test/rt/source/test/rt_test_root.h b/test/rt/source/test/rt_test_root.h
-index 6da777b..0cd40fc 100644
 --- a/test/rt/source/test/rt_test_root.h
 +++ b/test/rt/source/test/rt_test_root.h
 @@ -88,6 +88,7 @@ extern thread_t *threads[MAX_THREADS];
@@ -329,7 +354,6 @@ index 6da777b..0cd40fc 100644
  void test_wait_threads(void);
  systime_t test_wait_tick(void);
 diff --git a/test/rt/source/test/rt_test_sequence_001.c b/test/rt/source/test/rt_test_sequence_001.c
-index 6f2b96f..f91c23f 100644
 --- a/test/rt/source/test/rt_test_sequence_001.c
 +++ b/test/rt/source/test/rt_test_sequence_001.c
 @@ -193,6 +193,12 @@ static void rt_test_001_003_execute(void) {
@@ -347,7 +371,7 @@ index 6f2b96f..f91c23f 100644
      test_println("");
 @@ -207,7 +213,7 @@ static void rt_test_001_003_execute(void) {
      test_println("");
-     test_print("--- CH_CFG_USE_MUTEXES_RECURS:          ");
+     test_print("--- CH_CFG_USE_MUTEXES_RECURSIVE:       ");
      test_printn(CH_CFG_USE_MUTEXES_RECURSIVE);
 -    test_println("");   
 +    test_println("");
@@ -355,7 +379,6 @@ index 6f2b96f..f91c23f 100644
      test_printn(CH_CFG_USE_CONDVARS);
      test_println("");
 diff --git a/test/rt/source/test/rt_test_sequence_003.c b/test/rt/source/test/rt_test_sequence_003.c
-index 8598b12..f1ece71 100644
 --- a/test/rt/source/test/rt_test_sequence_003.c
 +++ b/test/rt/source/test/rt_test_sequence_003.c
 @@ -46,6 +46,20 @@ static THD_FUNCTION(thread, p) {
@@ -836,18 +859,17 @@ index 8598b12..f1ece71 100644
  /****************************************************************************
   * Exported data.
   ****************************************************************************/
-@@ -339,6 +752,9 @@ const testcase_t * const rt_test_sequence_003_array[] = {
+@@ -338,6 +751,9 @@ const testcase_t * const rt_test_sequence_003_array[] = {
+   &rt_test_003_003,
  #if (CH_CFG_USE_MUTEXES) || defined(__DOXYGEN__)
    &rt_test_003_004,
- #endif
++#endif
 +#if (CH_CFG_USE_THREADHIERARCHY) || defined(__DOXYGEN__)
 +  &rt_test_003_005,
-+#endif
+ #endif
    NULL
  };
- 
 diff --git a/test/rt/source/test/rt_test_sequence_004.c b/test/rt/source/test/rt_test_sequence_004.c
-index 7ad2ab5..4226ffc 100644
 --- a/test/rt/source/test/rt_test_sequence_004.c
 +++ b/test/rt/source/test/rt_test_sequence_004.c
 @@ -83,7 +83,7 @@ static void rt_test_004_001_execute(void) {
@@ -860,7 +882,6 @@ index 7ad2ab5..4226ffc 100644
      msg = chThdSuspendTimeoutS(&tr1, TIME_INFINITE);
      chSysUnlock();
 diff --git a/test/rt/source/test/rt_test_sequence_005.c b/test/rt/source/test/rt_test_sequence_005.c
-index 29cebb9..3cde985 100644
 --- a/test/rt/source/test/rt_test_sequence_005.c
 +++ b/test/rt/source/test/rt_test_sequence_005.c
 @@ -178,11 +178,11 @@ static void rt_test_005_002_execute(void) {
@@ -917,7 +938,6 @@ index 29cebb9..3cde985 100644
    }
  
 diff --git a/test/rt/source/test/rt_test_sequence_006.c b/test/rt/source/test/rt_test_sequence_006.c
-index 3694755..4d50caa 100644
 --- a/test/rt/source/test/rt_test_sequence_006.c
 +++ b/test/rt/source/test/rt_test_sequence_006.c
 @@ -276,11 +276,11 @@ static void rt_test_006_001_execute(void) {
@@ -1038,7 +1058,6 @@ index 3694755..4d50caa 100644
  
    /* [6.9.5] Signaling C1: TA wakes up, unlocks M1 and priority goes to
 diff --git a/test/rt/source/test/rt_test_sequence_007.c b/test/rt/source/test/rt_test_sequence_007.c
-index 62a9df9..6dabea2 100644
 --- a/test/rt/source/test/rt_test_sequence_007.c
 +++ b/test/rt/source/test/rt_test_sequence_007.c
 @@ -79,7 +79,7 @@ static void rt_test_007_001_execute(void) {
@@ -1051,7 +1070,6 @@ index 62a9df9..6dabea2 100644
    }
  
 diff --git a/test/rt/source/test/rt_test_sequence_008.c b/test/rt/source/test/rt_test_sequence_008.c
-index d2bb805..cead16b 100644
 --- a/test/rt/source/test/rt_test_sequence_008.c
 +++ b/test/rt/source/test/rt_test_sequence_008.c
 @@ -226,7 +226,7 @@ static void rt_test_008_003_execute(void) {
@@ -1091,7 +1109,6 @@ index d2bb805..cead16b 100644
    }
  
 diff --git a/test/rt/source/test/rt_test_sequence_010.c b/test/rt/source/test/rt_test_sequence_010.c
-index 1c77343..e21c840 100644
 --- a/test/rt/source/test/rt_test_sequence_010.c
 +++ b/test/rt/source/test/rt_test_sequence_010.c
 @@ -169,7 +169,7 @@ static void rt_test_010_001_execute(void) {
diff --git a/modules/DiWheelDrive_1-1/Makefile b/modules/DiWheelDrive_1-1/Makefile
index daaecbb..a8f03fd 100644
--- a/modules/DiWheelDrive_1-1/Makefile
+++ b/modules/DiWheelDrive_1-1/Makefile
@@ -43,7 +43,7 @@ ifeq ($(USE_CPPOPT),)
   USE_CPPOPT = -fno-rtti -std=c++17
 endif
 
-# Enable this if you want the linker to remove unused code and data
+# Enable this if you want the linker to remove unused code and data.
 ifeq ($(USE_LINK_GC),)
   USE_LINK_GC = yes
 endif
@@ -53,16 +53,11 @@ ifeq ($(USE_LDOPT),)
   USE_LDOPT =
 endif
 
-# Enable this if you want link time optimizations (LTO)
+# Enable this if you want link time optimizations (LTO).
 ifeq ($(USE_LTO),)
   USE_LTO = yes
 endif
 
-# If enabled, this option allows to compile the application in THUMB mode.
-ifeq ($(USE_THUMB),)
-  USE_THUMB = yes
-endif
-
 # Enable this if you want to see the full log while compiling.
 ifeq ($(USE_VERBOSE_COMPILE),)
   USE_VERBOSE_COMPILE = no
@@ -94,7 +89,7 @@ ifeq ($(USE_EXCEPTIONS_STACKSIZE),)
   USE_EXCEPTIONS_STACKSIZE = 0x400
 endif
 
-# Enables the use of FPU on Cortex-M4.
+# Enables the use of FPU.
 # Possible selections are:
 #   no     - no FPU is used (probably equals 'soft')
 #   soft   - does not use the FPU, thus all floating point operations are emulated
@@ -104,32 +99,47 @@ ifeq ($(USE_FPU),)
   USE_FPU = no
 endif
 
+# FPU-related options.
+ifeq ($(USE_FPU_OPT),)
+  USE_FPU_OPT = -mfloat-abi=$(USE_FPU) -mfpu=fpv4-sp-d16
+endif
+
 #                                                                              #
 # Architecture or project specific options                                     #
 ################################################################################
 
 ################################################################################
-# Project, sources and paths                                                   #
+# Project, target, sources and paths                                           #
 #                                                                              #
 
 # Define project name here
 PROJECT := $(patsubst $(abspath $(dir $(abspath $(lastword $(MAKEFILE_LIST))))..)/%,%,$(abspath $(dir $(abspath $(lastword $(MAKEFILE_LIST))))))
 
-# Imported source files and paths
+# Target settings.
+MCU = cortex-m3
+
+# Imported source files and paths.
 include ../../kernel/kernel.mk
-CHIBIOS := $(AMIROOS_KERNEL)
-AMIROOS = ../..
-# Licensing files
+CHIBIOS    := $(AMIROOS_KERNEL)
+CONFDIR    := .
+ifeq ($(BUILDDIR),)
+  BUILDDIR := ./build
+endif
+DEPDIR     := $(dir $(BUILDDIR)).dep
+AMIROOS    := ../..
+# Licensing files.
 include $(CHIBIOS)/os/license/license.mk
-# Startup files
+# Startup files.
 include $(CHIBIOS)/os/common/startup/ARMCMx/compilers/GCC/mk/startup_stm32f1xx.mk
-# HAL-OSAL files
+# HAL-OSAL files (optional).
 include $(CHIBIOS)/os/hal/hal.mk
 include $(CHIBIOS)/os/hal/ports/STM32/STM32F1xx/platform.mk
 include $(CHIBIOS)/os/hal/osal/rt/osal.mk
-# RTOS files
+# RTOS files (optional).
 include $(CHIBIOS)/os/rt/rt.mk
 include $(CHIBIOS)/os/common/ports/ARMCMx/compilers/GCC/mk/port_v7m.mk
+# Auto-build files in ./source recursively.
+include $(CHIBIOS)/tools/mk/autobuild.mk
 # Other files (optional).
 include $(CHIBIOS)/test/lib/test.mk
 include $(CHIBIOS)/test/rt/rt_test.mk
@@ -148,126 +158,58 @@ LDSCRIPT= STM32F103xE.ld
 
 # C sources that can be compiled in ARM or THUMB mode depending on the global
 # setting.
-CSRC = $(LICSRC) \
-       $(STARTUPSRC) \
-       $(KERNSRC) \
-       $(PORTSRC) \
-       $(OSALSRC) \
-       $(HALSRC) \
-       $(PLATFORMSRC) \
-       $(MODULESCSRC) \
+CSRC = $(ALLCSRC) \
        $(TESTSRC) \
-       $(PERIPHERYLLDCSRC) \
-       $(AMIROOSCORECSRC) \
-       $(UNITTESTSCSRC) \
        $(CHIBIOS)/os/various/evtimer.c \
        $(CHIBIOS)/os/various/syscalls.c \
        $(CHIBIOS)/os/hal/lib/streams/chprintf.c \
        board.c \
+       $(PERIPHERYLLDCSRC) \
+       $(UNITTESTSCSRC) \
+       $(AMIROOSCORECSRC) \
+       $(MODULESCSRC) \
        module.c \
        $(APPSCSRC)
 
 # C++ sources that can be compiled in ARM or THUMB mode depending on the global
 # setting.
-CPPSRC = $(AMIROOSCORECPPSRC) \
+CPPSRC = $(ALLCPPSRC) \
          $(CHIBIOS)/os/various/cpp_wrappers/syscalls_cpp.cpp \
+         $(AMIROOSCORECPPSRC) \
          $(APPSCPPSRC)
 
-# C sources to be compiled in ARM mode regardless of the global setting.
-# NOTE: Mixing ARM and THUMB mode enables the -mthumb-interwork compiler
-#       option that results in lower performance and larger code size.
-ACSRC = $(APPSACSRC)
-
-# C++ sources to be compiled in ARM mode regardless of the global setting.
-# NOTE: Mixing ARM and THUMB mode enables the -mthumb-interwork compiler
-#       option that results in lower performance and larger code size.
-ACPPSRC = $(APPSACPPSRC)
-
-# C sources to be compiled in THUMB mode regardless of the global setting.
-# NOTE: Mixing ARM and THUMB mode enables the -mthumb-interwork compiler
-#       option that results in lower performance and larger code size.
-TCSRC = $(APPSTCSRC)
-
-# C sources to be compiled in THUMB mode regardless of the global setting.
-# NOTE: Mixing ARM and THUMB mode enables the -mthumb-interwork compiler
-#       option that results in lower performance and larger code size.
-TCPPSRC = $(APPSTCPPSRC)
-
-# List ASM source files here
-ASMSRC = $(APPSASMSRC)
-ASMXSRC = $(STARTUPASM) \
-          $(PORTASM) \
-          $(OSALASM) \
+# List ASM source files here.
+ASMSRC = $(ALLASMSRC) \
+         $(APPSASMSRC)
+
+# List ASM with preprocessor source files here.
+ASMXSRC = $(ALLXASMSRC) \
           $(APPSASMXSRC)
 
-INCDIR = $(LICINC) \
-         $(STARTUPINC) \
-         $(KERNINC) \
-         $(PORTINC) \
-         $(OSALINC) \
-         $(HALINC) \
-         $(PLATFORMINC) \
-         $(MODULESINC) \
+# Inclusion directories.
+INCDIR = $(CONFDIR) \
+         $(ALLINC) \
          $(TESTINC) \
-         $(BOOTLOADERINC) \
          $(CHIBIOS)/os/hal/lib/streams \
+         $(BOOTLOADERINC) \
          $(PERIPHERYLLDINC) \
          $(AMIROOS) \
-         $(AMIROOSCOREINC) \
          $(UNITTESTSINC) \
+         $(AMIROOSCOREINC) \
+         $(MODULESINC) \
          $(APPSINC)
 
-#                                                                              #
-# Project, sources and paths                                                   #
-################################################################################
+# Define C warning options here.
+CWARN = -Wall -Wextra -Wundef -Wstrict-prototypes
 
-################################################################################
-# Compiler settings                                                            #
-# NOTE: Some can be overridden externally.                                     #
-#                                                                              #
+# Define C++ warning options here.
+CPPWARN = -Wall -Wextra -Wundef
 
-MCU  = cortex-m3
-
-#TRGT = arm-elf-
-TRGT = arm-none-eabi-
-CC   = $(TRGT)gcc
-CPPC = $(TRGT)g++
-# Enable loading with g++ only if you need C++ runtime support.
-# NOTE: You can use C++ even without C++ support if you are careful. C++
-#       runtime support makes code size explode.
-LD   = $(TRGT)gcc
-#LD   = $(TRGT)g++
-CP   = $(TRGT)objcopy
-AS   = $(TRGT)gcc -x assembler-with-cpp
-AR   = $(TRGT)ar
-OD   = $(TRGT)objdump
-SZ   = $(TRGT)size
-HEX  = $(CP) -O ihex
-BIN  = $(CP) -O binary
+# Create an additional .srec image file.
 SREC = $(CP) -O srec --srec-len=248
 
-# ARM-specific options here
-ifeq ($(AOPT),)
-  AOPT =
-endif
-
-# THUMB-specific options here
-ifeq ($(TOPT),)
-  TOPT = -mthumb -DTHUMB
-endif
-
-# Define C warning options here
-ifeq ($(CWARN),)
-  CWARN = -Wall -Wextra -Wundef -Wstrict-prototypes
-endif
-
-# Define C++ warning options here
-ifeq ($(CPPWARN),)
-  CPPWARN = -Wall -Wextra -Wundef
-endif
-
 #                                                                              #
-# Compiler settings                                                            #
+# Project, target, sources and paths                                           #
 ################################################################################
 
 ################################################################################
@@ -290,35 +232,38 @@ ULIBDIR +=
 ULIBS +=
 
 #                                                                              #
-# End of user defines                                                          #
+# End of user section                                                          #
 ################################################################################
 
 ################################################################################
-# Start of targets section                                                     #
+# Common rules                                                                 #
 #                                                                              #
 
-# all and its dependencies
-ifeq ($(BUILDDIR),)
-	BUILDDIR = ./build
-endif
-RULESPATH = $(CHIBIOS)/os/common/startup/ARMCMx/compilers/GCC
+RULESPATH = $(CHIBIOS)/os/common/startup/ARMCMx/compilers/GCC/mk
+include $(RULESPATH)/arm-none-eabi.mk
 include $(RULESPATH)/rules.mk
 
-# flash
-include $(AMIROOS)/bootloader/bootloader.mk
+#                                                                              #
+# Common rules                                                                 #
+################################################################################
+
+################################################################################
+# Custom rules                                                                 #
+#                                                                              #
+
 FLASH_MODULES = $(PROJECT)
 FLASH_FILES = $(BUILDDIR)/$(PROJECT).$(FLASHTOOL_EXT)
 
 flash: $(FLASH_FILES)
 	$(info )
-ifeq ($(FLASHTOOL),SerialBoot)
-	$(info Flashing ($(FLASHTOOL)):)
-	$(FLASHTOOL_CMD) $(FLASHTOOL_ARGS)
-else
-	$(info ERROR: unable to flash the module (SerialBoot unavailable))
-endif
+	ifeq ($(FLASHTOOL),SerialBoot)
+		$(info Flashing ($(FLASHTOOL)):)
+		$(FLASHTOOL_CMD) $(FLASHTOOL_ARGS)
+	else
+		$(info ERROR: unable to flash the module (SerialBoot unavailable))
+	endif
 
 #                                                                              #
-# End of targets section                                                       #
+# Custom rules                                                                 #
 ################################################################################
 
diff --git a/modules/DiWheelDrive_1-1/STM32F103xE.ld b/modules/DiWheelDrive_1-1/STM32F103xE.ld
index 0bf757f..0df70c0 100644
--- a/modules/DiWheelDrive_1-1/STM32F103xE.ld
+++ b/modules/DiWheelDrive_1-1/STM32F103xE.ld
@@ -84,4 +84,4 @@ REGION_ALIAS("BSS_RAM", ram0);
 REGION_ALIAS("HEAP_RAM", ram0);
 
 /* Generic rules inclusion.*/
-INCLUDE ../../kernel/ChibiOS/os/common/startup/ARMCMx/compilers/GCC/ld/rules.ld
+INCLUDE rules.ld
diff --git a/modules/DiWheelDrive_1-1/chconf.h b/modules/DiWheelDrive_1-1/chconf.h
index da19863..b6a67cf 100644
--- a/modules/DiWheelDrive_1-1/chconf.h
+++ b/modules/DiWheelDrive_1-1/chconf.h
@@ -129,6 +129,11 @@
  */
 #define CORTEX_VTOR_INIT                        0x00006000U
 
+/**
+ * @brief   Flag to enable/disable sleep mode when the system is idle.
+ */
+#define CORTEX_ENABLE_WFI_IDLE                  TRUE
+
 /** @} */
 
 /*===========================================================================*/
@@ -138,11 +143,6 @@
  */
 /*===========================================================================*/
 
-/**
- * @brief   Flag to enable/disable sleep mode when the system is idle.
- */
-#define CORTEX_ENABLE_WFI_IDLE                  TRUE
-
 // common definitions in aos_chconf.h
 
 /** @} */
diff --git a/modules/DiWheelDrive_1-1/halconf.h b/modules/DiWheelDrive_1-1/halconf.h
index 94ad299..6bee851 100644
--- a/modules/DiWheelDrive_1-1/halconf.h
+++ b/modules/DiWheelDrive_1-1/halconf.h
@@ -31,7 +31,7 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define HALCONF_H
 
 #define _CHIBIOS_HAL_CONF_
-#define _CHIBIOS_HAL_CONF_VER_6_0_
+#define _CHIBIOS_HAL_CONF_VER_7_0_
 
 #include "mcuconf.h"
 
@@ -71,13 +71,6 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #endif
 
 /**
- * @brief   Enables the EXT subsystem.
- */
-#if !defined(HAL_USE_EXT) || defined(__DOXYGEN__)
-#define HAL_USE_EXT                         FALSE
-#endif
-
-/**
  * @brief   Enables the GPT subsystem.
  */
 #if !defined(HAL_USE_GPT) || defined(__DOXYGEN__)
@@ -134,13 +127,6 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #endif
 
 /**
- * @brief   Enables the QSPI subsystem.
- */
-#if !defined(HAL_USE_QSPI) || defined(__DOXYGEN__)
-#define HAL_USE_QSPI                        FALSE
-#endif
-
-/**
  * @brief   Enables the RTC subsystem.
  */
 #if !defined(HAL_USE_RTC) || defined(__DOXYGEN__)
@@ -169,6 +155,13 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #endif
 
 /**
+ * @brief   Enables the SIO subsystem.
+ */
+#if !defined(HAL_USE_SIO) || defined(__DOXYGEN__)
+#define HAL_USE_SIO                         FALSE
+#endif
+
+/**
  * @brief   Enables the SPI subsystem.
  */
 #if !defined(HAL_USE_SPI) || defined(__DOXYGEN__)
@@ -176,6 +169,13 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #endif
 
 /**
+ * @brief   Enables the TRNG subsystem.
+ */
+#if !defined(HAL_USE_TRNG) || defined(__DOXYGEN__)
+#define HAL_USE_TRNG                        FALSE
+#endif
+
+/**
  * @brief   Enables the UART subsystem.
  */
 #if !defined(HAL_USE_UART) || defined(__DOXYGEN__)
@@ -196,6 +196,13 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define HAL_USE_WDG                         FALSE
 #endif
 
+/**
+ * @brief   Enables the WSPI subsystem.
+ */
+#if !defined(HAL_USE_WSPI) || defined(__DOXYGEN__)
+#define HAL_USE_WSPI                        FALSE
+#endif
+
 /*===========================================================================*/
 /* PAL driver related settings.                                              */
 /*===========================================================================*/
@@ -225,7 +232,7 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  * @note    Disabling this option saves both code and data space.
  */
 #if !defined(ADC_USE_WAIT) || defined(__DOXYGEN__)
-#define ADC_USE_WAIT                        FALSE
+#define ADC_USE_WAIT                        TRUE
 #endif
 
 /**
@@ -233,7 +240,7 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  * @note    Disabling this option saves both code and data space.
  */
 #if !defined(ADC_USE_MUTUAL_EXCLUSION) || defined(__DOXYGEN__)
-#define ADC_USE_MUTUAL_EXCLUSION            FALSE
+#define ADC_USE_MUTUAL_EXCLUSION            TRUE
 #endif
 
 /*===========================================================================*/
@@ -322,7 +329,7 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  * @brief   Enables an event sources for incoming packets.
  */
 #if !defined(MAC_USE_EVENTS) || defined(__DOXYGEN__)
-#define MAC_USE_EVENTS                      FALSE
+#define MAC_USE_EVENTS                      TRUE
 #endif
 
 /*===========================================================================*/
@@ -338,27 +345,7 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  *          use a DMA channel and heavily loads the CPU.
  */
 #if !defined(MMC_NICE_WAITING) || defined(__DOXYGEN__)
-#define MMC_NICE_WAITING                    FALSE
-#endif
-
-/*===========================================================================*/
-/* QSPI driver related settings.                                             */
-/*===========================================================================*/
-
-/**
- * @brief   Enables synchronous APIs.
- * @note    Disabling this option saves both code and data space.
- */
-#if !defined(QSPI_USE_WAIT) || defined(__DOXYGEN__)
-#define QSPI_USE_WAIT                       TRUE
-#endif
-
-/**
- * @brief   Enables the @p qspiAcquireBus() and @p qspiReleaseBus() APIs.
- * @note    Disabling this option saves both code and data space.
- */
-#if !defined(QSPI_USE_MUTUAL_EXCLUSION) || defined(__DOXYGEN__)
-#define QSPI_USE_MUTUAL_EXCLUSION           TRUE
+#define MMC_NICE_WAITING                    TRUE
 #endif
 
 /*===========================================================================*/
@@ -389,7 +376,7 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  *          lower priority, this may slow down the driver a bit however.
  */
 #if !defined(SDC_NICE_WAITING) || defined(__DOXYGEN__)
-#define SDC_NICE_WAITING                    FALSE
+#define SDC_NICE_WAITING                    TRUE
 #endif
 
 /**
@@ -522,6 +509,26 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define USB_USE_WAIT                        FALSE
 #endif
 
+/*===========================================================================*/
+/* WSPI driver related settings.                                             */
+/*===========================================================================*/
+
+/**
+ * @brief   Enables synchronous APIs.
+ * @note    Disabling this option saves both code and data space.
+ */
+#if !defined(WSPI_USE_WAIT) || defined(__DOXYGEN__)
+#define WSPI_USE_WAIT                       TRUE
+#endif
+
+/**
+ * @brief   Enables the @p wspiAcquireBus() and @p wspiReleaseBus() APIs.
+ * @note    Disabling this option saves both code and data space.
+ */
+#if !defined(WSPI_USE_MUTUAL_EXCLUSION) || defined(__DOXYGEN__)
+#define WSPI_USE_MUTUAL_EXCLUSION           TRUE
+#endif
+
 #endif /* HALCONF_H */
 
 /** @} */
diff --git a/modules/DiWheelDrive_1-1/mcuconf.h b/modules/DiWheelDrive_1-1/mcuconf.h
index 27f8026..15fad6c 100644
--- a/modules/DiWheelDrive_1-1/mcuconf.h
+++ b/modules/DiWheelDrive_1-1/mcuconf.h
@@ -19,6 +19,8 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #ifndef MCUCONF_H
 #define MCUCONF_H
 
+#define STM32F103_MCUCONF
+
 /*
  * STM32F103 drivers configuration.
  * The following settings override the default settings present in
@@ -33,8 +35,6 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  * 0...3        Lowest...Highest.
  */
 
-#define STM32F103_MCUCONF
-
 /*
  * HAL driver system settings.
  */
diff --git a/modules/LightRing_1-0/Makefile b/modules/LightRing_1-0/Makefile
index daaecbb..a8f03fd 100644
--- a/modules/LightRing_1-0/Makefile
+++ b/modules/LightRing_1-0/Makefile
@@ -43,7 +43,7 @@ ifeq ($(USE_CPPOPT),)
   USE_CPPOPT = -fno-rtti -std=c++17
 endif
 
-# Enable this if you want the linker to remove unused code and data
+# Enable this if you want the linker to remove unused code and data.
 ifeq ($(USE_LINK_GC),)
   USE_LINK_GC = yes
 endif
@@ -53,16 +53,11 @@ ifeq ($(USE_LDOPT),)
   USE_LDOPT =
 endif
 
-# Enable this if you want link time optimizations (LTO)
+# Enable this if you want link time optimizations (LTO).
 ifeq ($(USE_LTO),)
   USE_LTO = yes
 endif
 
-# If enabled, this option allows to compile the application in THUMB mode.
-ifeq ($(USE_THUMB),)
-  USE_THUMB = yes
-endif
-
 # Enable this if you want to see the full log while compiling.
 ifeq ($(USE_VERBOSE_COMPILE),)
   USE_VERBOSE_COMPILE = no
@@ -94,7 +89,7 @@ ifeq ($(USE_EXCEPTIONS_STACKSIZE),)
   USE_EXCEPTIONS_STACKSIZE = 0x400
 endif
 
-# Enables the use of FPU on Cortex-M4.
+# Enables the use of FPU.
 # Possible selections are:
 #   no     - no FPU is used (probably equals 'soft')
 #   soft   - does not use the FPU, thus all floating point operations are emulated
@@ -104,32 +99,47 @@ ifeq ($(USE_FPU),)
   USE_FPU = no
 endif
 
+# FPU-related options.
+ifeq ($(USE_FPU_OPT),)
+  USE_FPU_OPT = -mfloat-abi=$(USE_FPU) -mfpu=fpv4-sp-d16
+endif
+
 #                                                                              #
 # Architecture or project specific options                                     #
 ################################################################################
 
 ################################################################################
-# Project, sources and paths                                                   #
+# Project, target, sources and paths                                           #
 #                                                                              #
 
 # Define project name here
 PROJECT := $(patsubst $(abspath $(dir $(abspath $(lastword $(MAKEFILE_LIST))))..)/%,%,$(abspath $(dir $(abspath $(lastword $(MAKEFILE_LIST))))))
 
-# Imported source files and paths
+# Target settings.
+MCU = cortex-m3
+
+# Imported source files and paths.
 include ../../kernel/kernel.mk
-CHIBIOS := $(AMIROOS_KERNEL)
-AMIROOS = ../..
-# Licensing files
+CHIBIOS    := $(AMIROOS_KERNEL)
+CONFDIR    := .
+ifeq ($(BUILDDIR),)
+  BUILDDIR := ./build
+endif
+DEPDIR     := $(dir $(BUILDDIR)).dep
+AMIROOS    := ../..
+# Licensing files.
 include $(CHIBIOS)/os/license/license.mk
-# Startup files
+# Startup files.
 include $(CHIBIOS)/os/common/startup/ARMCMx/compilers/GCC/mk/startup_stm32f1xx.mk
-# HAL-OSAL files
+# HAL-OSAL files (optional).
 include $(CHIBIOS)/os/hal/hal.mk
 include $(CHIBIOS)/os/hal/ports/STM32/STM32F1xx/platform.mk
 include $(CHIBIOS)/os/hal/osal/rt/osal.mk
-# RTOS files
+# RTOS files (optional).
 include $(CHIBIOS)/os/rt/rt.mk
 include $(CHIBIOS)/os/common/ports/ARMCMx/compilers/GCC/mk/port_v7m.mk
+# Auto-build files in ./source recursively.
+include $(CHIBIOS)/tools/mk/autobuild.mk
 # Other files (optional).
 include $(CHIBIOS)/test/lib/test.mk
 include $(CHIBIOS)/test/rt/rt_test.mk
@@ -148,126 +158,58 @@ LDSCRIPT= STM32F103xE.ld
 
 # C sources that can be compiled in ARM or THUMB mode depending on the global
 # setting.
-CSRC = $(LICSRC) \
-       $(STARTUPSRC) \
-       $(KERNSRC) \
-       $(PORTSRC) \
-       $(OSALSRC) \
-       $(HALSRC) \
-       $(PLATFORMSRC) \
-       $(MODULESCSRC) \
+CSRC = $(ALLCSRC) \
        $(TESTSRC) \
-       $(PERIPHERYLLDCSRC) \
-       $(AMIROOSCORECSRC) \
-       $(UNITTESTSCSRC) \
        $(CHIBIOS)/os/various/evtimer.c \
        $(CHIBIOS)/os/various/syscalls.c \
        $(CHIBIOS)/os/hal/lib/streams/chprintf.c \
        board.c \
+       $(PERIPHERYLLDCSRC) \
+       $(UNITTESTSCSRC) \
+       $(AMIROOSCORECSRC) \
+       $(MODULESCSRC) \
        module.c \
        $(APPSCSRC)
 
 # C++ sources that can be compiled in ARM or THUMB mode depending on the global
 # setting.
-CPPSRC = $(AMIROOSCORECPPSRC) \
+CPPSRC = $(ALLCPPSRC) \
          $(CHIBIOS)/os/various/cpp_wrappers/syscalls_cpp.cpp \
+         $(AMIROOSCORECPPSRC) \
          $(APPSCPPSRC)
 
-# C sources to be compiled in ARM mode regardless of the global setting.
-# NOTE: Mixing ARM and THUMB mode enables the -mthumb-interwork compiler
-#       option that results in lower performance and larger code size.
-ACSRC = $(APPSACSRC)
-
-# C++ sources to be compiled in ARM mode regardless of the global setting.
-# NOTE: Mixing ARM and THUMB mode enables the -mthumb-interwork compiler
-#       option that results in lower performance and larger code size.
-ACPPSRC = $(APPSACPPSRC)
-
-# C sources to be compiled in THUMB mode regardless of the global setting.
-# NOTE: Mixing ARM and THUMB mode enables the -mthumb-interwork compiler
-#       option that results in lower performance and larger code size.
-TCSRC = $(APPSTCSRC)
-
-# C sources to be compiled in THUMB mode regardless of the global setting.
-# NOTE: Mixing ARM and THUMB mode enables the -mthumb-interwork compiler
-#       option that results in lower performance and larger code size.
-TCPPSRC = $(APPSTCPPSRC)
-
-# List ASM source files here
-ASMSRC = $(APPSASMSRC)
-ASMXSRC = $(STARTUPASM) \
-          $(PORTASM) \
-          $(OSALASM) \
+# List ASM source files here.
+ASMSRC = $(ALLASMSRC) \
+         $(APPSASMSRC)
+
+# List ASM with preprocessor source files here.
+ASMXSRC = $(ALLXASMSRC) \
           $(APPSASMXSRC)
 
-INCDIR = $(LICINC) \
-         $(STARTUPINC) \
-         $(KERNINC) \
-         $(PORTINC) \
-         $(OSALINC) \
-         $(HALINC) \
-         $(PLATFORMINC) \
-         $(MODULESINC) \
+# Inclusion directories.
+INCDIR = $(CONFDIR) \
+         $(ALLINC) \
          $(TESTINC) \
-         $(BOOTLOADERINC) \
          $(CHIBIOS)/os/hal/lib/streams \
+         $(BOOTLOADERINC) \
          $(PERIPHERYLLDINC) \
          $(AMIROOS) \
-         $(AMIROOSCOREINC) \
          $(UNITTESTSINC) \
+         $(AMIROOSCOREINC) \
+         $(MODULESINC) \
          $(APPSINC)
 
-#                                                                              #
-# Project, sources and paths                                                   #
-################################################################################
+# Define C warning options here.
+CWARN = -Wall -Wextra -Wundef -Wstrict-prototypes
 
-################################################################################
-# Compiler settings                                                            #
-# NOTE: Some can be overridden externally.                                     #
-#                                                                              #
+# Define C++ warning options here.
+CPPWARN = -Wall -Wextra -Wundef
 
-MCU  = cortex-m3
-
-#TRGT = arm-elf-
-TRGT = arm-none-eabi-
-CC   = $(TRGT)gcc
-CPPC = $(TRGT)g++
-# Enable loading with g++ only if you need C++ runtime support.
-# NOTE: You can use C++ even without C++ support if you are careful. C++
-#       runtime support makes code size explode.
-LD   = $(TRGT)gcc
-#LD   = $(TRGT)g++
-CP   = $(TRGT)objcopy
-AS   = $(TRGT)gcc -x assembler-with-cpp
-AR   = $(TRGT)ar
-OD   = $(TRGT)objdump
-SZ   = $(TRGT)size
-HEX  = $(CP) -O ihex
-BIN  = $(CP) -O binary
+# Create an additional .srec image file.
 SREC = $(CP) -O srec --srec-len=248
 
-# ARM-specific options here
-ifeq ($(AOPT),)
-  AOPT =
-endif
-
-# THUMB-specific options here
-ifeq ($(TOPT),)
-  TOPT = -mthumb -DTHUMB
-endif
-
-# Define C warning options here
-ifeq ($(CWARN),)
-  CWARN = -Wall -Wextra -Wundef -Wstrict-prototypes
-endif
-
-# Define C++ warning options here
-ifeq ($(CPPWARN),)
-  CPPWARN = -Wall -Wextra -Wundef
-endif
-
 #                                                                              #
-# Compiler settings                                                            #
+# Project, target, sources and paths                                           #
 ################################################################################
 
 ################################################################################
@@ -290,35 +232,38 @@ ULIBDIR +=
 ULIBS +=
 
 #                                                                              #
-# End of user defines                                                          #
+# End of user section                                                          #
 ################################################################################
 
 ################################################################################
-# Start of targets section                                                     #
+# Common rules                                                                 #
 #                                                                              #
 
-# all and its dependencies
-ifeq ($(BUILDDIR),)
-	BUILDDIR = ./build
-endif
-RULESPATH = $(CHIBIOS)/os/common/startup/ARMCMx/compilers/GCC
+RULESPATH = $(CHIBIOS)/os/common/startup/ARMCMx/compilers/GCC/mk
+include $(RULESPATH)/arm-none-eabi.mk
 include $(RULESPATH)/rules.mk
 
-# flash
-include $(AMIROOS)/bootloader/bootloader.mk
+#                                                                              #
+# Common rules                                                                 #
+################################################################################
+
+################################################################################
+# Custom rules                                                                 #
+#                                                                              #
+
 FLASH_MODULES = $(PROJECT)
 FLASH_FILES = $(BUILDDIR)/$(PROJECT).$(FLASHTOOL_EXT)
 
 flash: $(FLASH_FILES)
 	$(info )
-ifeq ($(FLASHTOOL),SerialBoot)
-	$(info Flashing ($(FLASHTOOL)):)
-	$(FLASHTOOL_CMD) $(FLASHTOOL_ARGS)
-else
-	$(info ERROR: unable to flash the module (SerialBoot unavailable))
-endif
+	ifeq ($(FLASHTOOL),SerialBoot)
+		$(info Flashing ($(FLASHTOOL)):)
+		$(FLASHTOOL_CMD) $(FLASHTOOL_ARGS)
+	else
+		$(info ERROR: unable to flash the module (SerialBoot unavailable))
+	endif
 
 #                                                                              #
-# End of targets section                                                       #
+# Custom rules                                                                 #
 ################################################################################
 
diff --git a/modules/LightRing_1-0/chconf.h b/modules/LightRing_1-0/chconf.h
index b726eee..4cff710 100644
--- a/modules/LightRing_1-0/chconf.h
+++ b/modules/LightRing_1-0/chconf.h
@@ -129,6 +129,11 @@
  */
 #define CORTEX_VTOR_INIT                        0x00006000U
 
+/**
+ * @brief   Flag to enable/disable sleep mode when the system is idle.
+ */
+#define CORTEX_ENABLE_WFI_IDLE                  TRUE
+
 /** @} */
 
 /*===========================================================================*/
@@ -138,11 +143,6 @@
  */
 /*===========================================================================*/
 
-/**
- * @brief   Flag to enable/disable sleep mode when the system is idle.
- */
-#define CORTEX_ENABLE_WFI_IDLE                  TRUE
-
 // common definitions in aos_chconf.h
 
 /** @} */
diff --git a/modules/LightRing_1-0/halconf.h b/modules/LightRing_1-0/halconf.h
index e502e0a..d62c369 100644
--- a/modules/LightRing_1-0/halconf.h
+++ b/modules/LightRing_1-0/halconf.h
@@ -31,7 +31,7 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define HALCONF_H
 
 #define _CHIBIOS_HAL_CONF_
-#define _CHIBIOS_HAL_CONF_VER_6_0_
+#define _CHIBIOS_HAL_CONF_VER_7_0_
 
 #include "mcuconf.h"
 
@@ -71,13 +71,6 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #endif
 
 /**
- * @brief   Enables the EXT subsystem.
- */
-#if !defined(HAL_USE_EXT) || defined(__DOXYGEN__)
-#define HAL_USE_EXT                         FALSE
-#endif
-
-/**
  * @brief   Enables the GPT subsystem.
  */
 #if !defined(HAL_USE_GPT) || defined(__DOXYGEN__)
@@ -134,13 +127,6 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #endif
 
 /**
- * @brief   Enables the QSPI subsystem.
- */
-#if !defined(HAL_USE_QSPI) || defined(__DOXYGEN__)
-#define HAL_USE_QSPI                        FALSE
-#endif
-
-/**
  * @brief   Enables the RTC subsystem.
  */
 #if !defined(HAL_USE_RTC) || defined(__DOXYGEN__)
@@ -169,6 +155,13 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #endif
 
 /**
+ * @brief   Enables the SIO subsystem.
+ */
+#if !defined(HAL_USE_SIO) || defined(__DOXYGEN__)
+#define HAL_USE_SIO                         FALSE
+#endif
+
+/**
  * @brief   Enables the SPI subsystem.
  */
 #if !defined(HAL_USE_SPI) || defined(__DOXYGEN__)
@@ -176,6 +169,13 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #endif
 
 /**
+ * @brief   Enables the TRNG subsystem.
+ */
+#if !defined(HAL_USE_TRNG) || defined(__DOXYGEN__)
+#define HAL_USE_TRNG                        FALSE
+#endif
+
+/**
  * @brief   Enables the UART subsystem.
  */
 #if !defined(HAL_USE_UART) || defined(__DOXYGEN__)
@@ -196,6 +196,13 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define HAL_USE_WDG                         FALSE
 #endif
 
+/**
+ * @brief   Enables the WSPI subsystem.
+ */
+#if !defined(HAL_USE_WSPI) || defined(__DOXYGEN__)
+#define HAL_USE_WSPI                        FALSE
+#endif
+
 /*===========================================================================*/
 /* PAL driver related settings.                                              */
 /*===========================================================================*/
@@ -225,7 +232,7 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  * @note    Disabling this option saves both code and data space.
  */
 #if !defined(ADC_USE_WAIT) || defined(__DOXYGEN__)
-#define ADC_USE_WAIT                        FALSE
+#define ADC_USE_WAIT                        TRUE
 #endif
 
 /**
@@ -233,7 +240,7 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  * @note    Disabling this option saves both code and data space.
  */
 #if !defined(ADC_USE_MUTUAL_EXCLUSION) || defined(__DOXYGEN__)
-#define ADC_USE_MUTUAL_EXCLUSION            FALSE
+#define ADC_USE_MUTUAL_EXCLUSION            TRUE
 #endif
 
 /*===========================================================================*/
@@ -322,7 +329,7 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  * @brief   Enables an event sources for incoming packets.
  */
 #if !defined(MAC_USE_EVENTS) || defined(__DOXYGEN__)
-#define MAC_USE_EVENTS                      FALSE
+#define MAC_USE_EVENTS                      TRUE
 #endif
 
 /*===========================================================================*/
@@ -338,27 +345,7 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  *          use a DMA channel and heavily loads the CPU.
  */
 #if !defined(MMC_NICE_WAITING) || defined(__DOXYGEN__)
-#define MMC_NICE_WAITING                    FALSE
-#endif
-
-/*===========================================================================*/
-/* QSPI driver related settings.                                             */
-/*===========================================================================*/
-
-/**
- * @brief   Enables synchronous APIs.
- * @note    Disabling this option saves both code and data space.
- */
-#if !defined(QSPI_USE_WAIT) || defined(__DOXYGEN__)
-#define QSPI_USE_WAIT                       TRUE
-#endif
-
-/**
- * @brief   Enables the @p qspiAcquireBus() and @p qspiReleaseBus() APIs.
- * @note    Disabling this option saves both code and data space.
- */
-#if !defined(QSPI_USE_MUTUAL_EXCLUSION) || defined(__DOXYGEN__)
-#define QSPI_USE_MUTUAL_EXCLUSION           TRUE
+#define MMC_NICE_WAITING                    TRUE
 #endif
 
 /*===========================================================================*/
@@ -389,7 +376,7 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  *          lower priority, this may slow down the driver a bit however.
  */
 #if !defined(SDC_NICE_WAITING) || defined(__DOXYGEN__)
-#define SDC_NICE_WAITING                    FALSE
+#define SDC_NICE_WAITING                    TRUE
 #endif
 
 /**
@@ -522,6 +509,26 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define USB_USE_WAIT                        FALSE
 #endif
 
+/*===========================================================================*/
+/* WSPI driver related settings.                                             */
+/*===========================================================================*/
+
+/**
+ * @brief   Enables synchronous APIs.
+ * @note    Disabling this option saves both code and data space.
+ */
+#if !defined(WSPI_USE_WAIT) || defined(__DOXYGEN__)
+#define WSPI_USE_WAIT                       TRUE
+#endif
+
+/**
+ * @brief   Enables the @p wspiAcquireBus() and @p wspiReleaseBus() APIs.
+ * @note    Disabling this option saves both code and data space.
+ */
+#if !defined(WSPI_USE_MUTUAL_EXCLUSION) || defined(__DOXYGEN__)
+#define WSPI_USE_MUTUAL_EXCLUSION           TRUE
+#endif
+
 #endif /* HALCONF_H */
 
 /** @} */
diff --git a/modules/LightRing_1-0/mcuconf.h b/modules/LightRing_1-0/mcuconf.h
index 28ce35f..33eb4ab 100644
--- a/modules/LightRing_1-0/mcuconf.h
+++ b/modules/LightRing_1-0/mcuconf.h
@@ -19,6 +19,8 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #ifndef MCUCONF_H
 #define MCUCONF_H
 
+#define STM32F103_MCUCONF
+
 /*
  * STM32F103 drivers configuration.
  * The following settings override the default settings present in
@@ -33,8 +35,6 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  * 0...3        Lowest...Highest.
  */
 
-#define STM32F103_MCUCONF
-
 /*
  * HAL driver system settings.
  */
@@ -89,7 +89,7 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 /*
  * GPT driver system settings.
  */
-#define STM32_GPT_USE_TIM1                  TRUE
+#define STM32_GPT_USE_TIM1                  FALSE
 #define STM32_GPT_USE_TIM2                  FALSE
 #define STM32_GPT_USE_TIM3                  FALSE
 #define STM32_GPT_USE_TIM4                  FALSE
diff --git a/modules/NUCLEO-F103RB/Makefile b/modules/NUCLEO-F103RB/Makefile
index f119817..901526b 100644
--- a/modules/NUCLEO-F103RB/Makefile
+++ b/modules/NUCLEO-F103RB/Makefile
@@ -43,7 +43,7 @@ ifeq ($(USE_CPPOPT),)
   USE_CPPOPT = -fno-rtti -std=c++17
 endif
 
-# Enable this if you want the linker to remove unused code and data
+# Enable this if you want the linker to remove unused code and data.
 ifeq ($(USE_LINK_GC),)
   USE_LINK_GC = yes
 endif
@@ -53,16 +53,11 @@ ifeq ($(USE_LDOPT),)
   USE_LDOPT =
 endif
 
-# Enable this if you want link time optimizations (LTO)
+# Enable this if you want link time optimizations (LTO).
 ifeq ($(USE_LTO),)
   USE_LTO = yes
 endif
 
-# If enabled, this option allows to compile the application in THUMB mode.
-ifeq ($(USE_THUMB),)
-  USE_THUMB = yes
-endif
-
 # Enable this if you want to see the full log while compiling.
 ifeq ($(USE_VERBOSE_COMPILE),)
   USE_VERBOSE_COMPILE = no
@@ -94,7 +89,7 @@ ifeq ($(USE_EXCEPTIONS_STACKSIZE),)
   USE_EXCEPTIONS_STACKSIZE = 0x400
 endif
 
-# Enables the use of FPU on Cortex-M4.
+# Enables the use of FPU.
 # Possible selections are:
 #   no     - no FPU is used (probably equals 'soft')
 #   soft   - does not use the FPU, thus all floating point operations are emulated
@@ -104,32 +99,47 @@ ifeq ($(USE_FPU),)
   USE_FPU = no
 endif
 
+# FPU-related options.
+ifeq ($(USE_FPU_OPT),)
+  USE_FPU_OPT = -mfloat-abi=$(USE_FPU) -mfpu=fpv4-sp-d16
+endif
+
 #                                                                              #
 # Architecture or project specific options                                     #
 ################################################################################
 
 ################################################################################
-# Project, sources and paths                                                   #
+# Project, target, sources and paths                                           #
 #                                                                              #
 
 # Define project name here
 PROJECT := $(patsubst $(abspath $(dir $(abspath $(lastword $(MAKEFILE_LIST))))..)/%,%,$(abspath $(dir $(abspath $(lastword $(MAKEFILE_LIST))))))
 
-# Imported source files and paths
+# Target settings.
+MCU = cortex-m3
+
+# Imported source files and paths.
 include ../../kernel/kernel.mk
-CHIBIOS := $(AMIROOS_KERNEL)
-AMIROOS = ../..
-# Licensing files
+CHIBIOS    := $(AMIROOS_KERNEL)
+CONFDIR    := .
+ifeq ($(BUILDDIR),)
+  BUILDDIR := ./build
+endif
+DEPDIR     := $(dir $(BUILDDIR)).dep
+AMIROOS    := ../..
+# Licensing files.
 include $(CHIBIOS)/os/license/license.mk
-# Startup files
+# Startup files.
 include $(CHIBIOS)/os/common/startup/ARMCMx/compilers/GCC/mk/startup_stm32f1xx.mk
-# HAL-OSAL files
+# HAL-OSAL files (optional).
 include $(CHIBIOS)/os/hal/hal.mk
 include $(CHIBIOS)/os/hal/ports/STM32/STM32F1xx/platform.mk
 include $(CHIBIOS)/os/hal/osal/rt/osal.mk
-# RTOS files
+# RTOS files (optional).
 include $(CHIBIOS)/os/rt/rt.mk
 include $(CHIBIOS)/os/common/ports/ARMCMx/compilers/GCC/mk/port_v7m.mk
+# Auto-build files in ./source recursively.
+include $(CHIBIOS)/tools/mk/autobuild.mk
 # Other files (optional).
 include $(CHIBIOS)/test/lib/test.mk
 include $(CHIBIOS)/test/rt/rt_test.mk
@@ -148,126 +158,55 @@ LDSCRIPT= STM32F103xB.ld
 
 # C sources that can be compiled in ARM or THUMB mode depending on the global
 # setting.
-CSRC = $(LICSRC) \
-       $(STARTUPSRC) \
-       $(KERNSRC) \
-       $(PORTSRC) \
-       $(OSALSRC) \
-       $(HALSRC) \
-       $(PLATFORMSRC) \
-       $(MODULESCSRC) \
+CSRC = $(ALLCSRC) \
        $(TESTSRC) \
-       $(PERIPHERYLLDCSRC) \
-       $(AMIROOSCORECSRC) \
-       $(UNITTESTSCSRC) \
        $(CHIBIOS)/os/various/evtimer.c \
        $(CHIBIOS)/os/various/syscalls.c \
        $(CHIBIOS)/os/hal/lib/streams/chprintf.c \
        board.c \
+       $(PERIPHERYLLDCSRC) \
+       $(UNITTESTSCSRC) \
+       $(AMIROOSCORECSRC) \
+       $(MODULESCSRC) \
        module.c \
        $(APPSCSRC)
 
 # C++ sources that can be compiled in ARM or THUMB mode depending on the global
 # setting.
-CPPSRC = $(AMIROOSCORECPPSRC) \
+CPPSRC = $(ALLCPPSRC) \
          $(CHIBIOS)/os/various/cpp_wrappers/syscalls_cpp.cpp \
+         $(AMIROOSCORECPPSRC) \
          $(APPSCPPSRC)
 
-# C sources to be compiled in ARM mode regardless of the global setting.
-# NOTE: Mixing ARM and THUMB mode enables the -mthumb-interwork compiler
-#       option that results in lower performance and larger code size.
-ACSRC = $(APPSACSRC)
-
-# C++ sources to be compiled in ARM mode regardless of the global setting.
-# NOTE: Mixing ARM and THUMB mode enables the -mthumb-interwork compiler
-#       option that results in lower performance and larger code size.
-ACPPSRC = $(APPSACPPSRC)
-
-# C sources to be compiled in THUMB mode regardless of the global setting.
-# NOTE: Mixing ARM and THUMB mode enables the -mthumb-interwork compiler
-#       option that results in lower performance and larger code size.
-TCSRC = $(APPSTCSRC)
-
-# C sources to be compiled in THUMB mode regardless of the global setting.
-# NOTE: Mixing ARM and THUMB mode enables the -mthumb-interwork compiler
-#       option that results in lower performance and larger code size.
-TCPPSRC = $(APPSTCPPSRC)
-
-# List ASM source files here
-ASMSRC = $(APPSASMSRC)
-ASMXSRC = $(STARTUPASM) \
-          $(PORTASM) \
-          $(OSALASM) \
+# List ASM source files here.
+ASMSRC = $(ALLASMSRC) \
+         $(APPSASMSRC)
+
+# List ASM with preprocessor source files here.
+ASMXSRC = $(ALLXASMSRC) \
           $(APPSASMXSRC)
 
-INCDIR = $(LICINC) \
-         $(STARTUPINC) \
-         $(KERNINC) \
-         $(PORTINC) \
-         $(OSALINC) \
-         $(HALINC) \
-         $(PLATFORMINC) \
-         $(MODULESINC) \
+# Inclusion directories.
+INCDIR = $(CONFDIR) \
+         $(ALLINC) \
          $(TESTINC) \
-         $(BOOTLOADERINC) \
          $(CHIBIOS)/os/hal/lib/streams \
+         $(BOOTLOADERINC) \
          $(PERIPHERYLLDINC) \
          $(AMIROOS) \
-         $(AMIROOSCOREINC) \
          $(UNITTESTSINC) \
+         $(AMIROOSCOREINC) \
+         $(MODULESINC) \
          $(APPSINC)
 
-#                                                                              #
-# Project, sources and paths                                                   #
-################################################################################
-
-################################################################################
-# Compiler settings                                                            #
-# NOTE: Some can be overridden externally.                                     #
-#                                                                              #
-
-MCU  = cortex-m3
-
-#TRGT = arm-elf-
-TRGT = arm-none-eabi-
-CC   = $(TRGT)gcc
-CPPC = $(TRGT)g++
-# Enable loading with g++ only if you need C++ runtime support.
-# NOTE: You can use C++ even without C++ support if you are careful. C++
-#       runtime support makes code size explode.
-LD   = $(TRGT)gcc
-#LD   = $(TRGT)g++
-CP   = $(TRGT)objcopy
-AS   = $(TRGT)gcc -x assembler-with-cpp
-AR   = $(TRGT)ar
-OD   = $(TRGT)objdump
-SZ   = $(TRGT)size
-HEX  = $(CP) -O ihex
-BIN  = $(CP) -O binary
-SREC = $(CP) -O srec --srec-len=248
-
-# ARM-specific options here
-ifeq ($(AOPT),)
-  AOPT =
-endif
-
-# THUMB-specific options here
-ifeq ($(TOPT),)
-  TOPT = -mthumb -DTHUMB
-endif
-
-# Define C warning options here
-ifeq ($(CWARN),)
-  CWARN = -Wall -Wextra -Wundef -Wstrict-prototypes
-endif
+# Define C warning options here.
+CWARN = -Wall -Wextra -Wundef -Wstrict-prototypes
 
-# Define C++ warning options here
-ifeq ($(CPPWARN),)
-  CPPWARN = -Wall -Wextra -Wundef
-endif
+# Define C++ warning options here.
+CPPWARN = -Wall -Wextra -Wundef
 
 #                                                                              #
-# Compiler settings                                                            #
+# Project, target, sources and paths                                           #
 ################################################################################
 
 ################################################################################
@@ -290,27 +229,29 @@ ULIBDIR +=
 ULIBS +=
 
 #                                                                              #
-# End of user defines                                                          #
+# End of user section                                                          #
 ################################################################################
 
 ################################################################################
-# Start of targets section                                                     #
+# Common rules                                                                 #
 #                                                                              #
 
-# all and its dependencies
-ifeq ($(BUILDDIR),)
-	BUILDDIR = ./build
-endif
-RULESPATH = $(CHIBIOS)/os/common/startup/ARMCMx/compilers/GCC
+RULESPATH = $(CHIBIOS)/os/common/startup/ARMCMx/compilers/GCC/mk
+include $(RULESPATH)/arm-none-eabi.mk
 include $(RULESPATH)/rules.mk
 
-# flash
-include $(AMIROOS)/bootloader/bootloader.mk
+#                                                                              #
+# Common rules                                                                 #
+################################################################################
+
+################################################################################
+# Custom rules                                                                 #
+#                                                                              #
 
 flash: $(BUILDDIR)/$(PROJECT).elf
 	openocd -f interface/stlink-v2-1.cfg -c "set WORKAREASIZE 0x2000" -f target/stm32f1x.cfg -c "program build/$(PROJECT).elf verify reset exit"
 
 #                                                                              #
-# End of targets section                                                       #
+# Custom rules                                                                 #
 ################################################################################
 
diff --git a/modules/NUCLEO-F103RB/chconf.h b/modules/NUCLEO-F103RB/chconf.h
index 6b7f293..dec49ac 100644
--- a/modules/NUCLEO-F103RB/chconf.h
+++ b/modules/NUCLEO-F103RB/chconf.h
@@ -123,6 +123,11 @@
  */
 /*===========================================================================*/
 
+/**
+ * @brief   Flag to enable/disable sleep mode when the system is idle.
+ */
+#define CORTEX_ENABLE_WFI_IDLE                  TRUE
+
 /** @} */
 
 /*===========================================================================*/
@@ -132,11 +137,6 @@
  */
 /*===========================================================================*/
 
-/**
- * @brief   Flag to enable/disable sleep mode when the system is idle.
- */
-#define CORTEX_ENABLE_WFI_IDLE                  TRUE
-
 // common definitions in aos_chconf.h
 
 /** @} */
diff --git a/modules/NUCLEO-F103RB/halconf.h b/modules/NUCLEO-F103RB/halconf.h
index 07dbcac..d2636a0 100644
--- a/modules/NUCLEO-F103RB/halconf.h
+++ b/modules/NUCLEO-F103RB/halconf.h
@@ -31,7 +31,7 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define HALCONF_H
 
 #define _CHIBIOS_HAL_CONF_
-#define _CHIBIOS_HAL_CONF_VER_6_0_
+#define _CHIBIOS_HAL_CONF_VER_7_0_
 
 #include "mcuconf.h"
 
@@ -71,13 +71,6 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #endif
 
 /**
- * @brief   Enables the EXT subsystem.
- */
-#if !defined(HAL_USE_EXT) || defined(__DOXYGEN__)
-#define HAL_USE_EXT                         FALSE
-#endif
-
-/**
  * @brief   Enables the GPT subsystem.
  */
 #if !defined(HAL_USE_GPT) || defined(__DOXYGEN__)
@@ -134,13 +127,6 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #endif
 
 /**
- * @brief   Enables the QSPI subsystem.
- */
-#if !defined(HAL_USE_QSPI) || defined(__DOXYGEN__)
-#define HAL_USE_QSPI                        FALSE
-#endif
-
-/**
  * @brief   Enables the RTC subsystem.
  */
 #if !defined(HAL_USE_RTC) || defined(__DOXYGEN__)
@@ -169,10 +155,24 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #endif
 
 /**
+ * @brief   Enables the SIO subsystem.
+ */
+#if !defined(HAL_USE_SIO) || defined(__DOXYGEN__)
+#define HAL_USE_SIO                         FALSE
+#endif
+
+/**
  * @brief   Enables the SPI subsystem.
  */
 #if !defined(HAL_USE_SPI) || defined(__DOXYGEN__)
-#define HAL_USE_SPI                         TRUE   
+#define HAL_USE_SPI                         TRUE
+#endif
+
+/**
+ * @brief   Enables the TRNG subsystem.
+ */
+#if !defined(HAL_USE_TRNG) || defined(__DOXYGEN__)
+#define HAL_USE_TRNG                        FALSE
 #endif
 
 /**
@@ -196,6 +196,13 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define HAL_USE_WDG                         FALSE
 #endif
 
+/**
+ * @brief   Enables the WSPI subsystem.
+ */
+#if !defined(HAL_USE_WSPI) || defined(__DOXYGEN__)
+#define HAL_USE_WSPI                        FALSE
+#endif
+
 /*===========================================================================*/
 /* PAL driver related settings.                                              */
 /*===========================================================================*/
@@ -342,26 +349,6 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #endif
 
 /*===========================================================================*/
-/* QSPI driver related settings.                                             */
-/*===========================================================================*/
-
-/**
- * @brief   Enables synchronous APIs.
- * @note    Disabling this option saves both code and data space.
- */
-#if !defined(QSPI_USE_WAIT) || defined(__DOXYGEN__)
-#define QSPI_USE_WAIT                       TRUE
-#endif
-
-/**
- * @brief   Enables the @p qspiAcquireBus() and @p qspiReleaseBus() APIs.
- * @note    Disabling this option saves both code and data space.
- */
-#if !defined(QSPI_USE_MUTUAL_EXCLUSION) || defined(__DOXYGEN__)
-#define QSPI_USE_MUTUAL_EXCLUSION           TRUE
-#endif
-
-/*===========================================================================*/
 /* SDC driver related settings.                                              */
 /*===========================================================================*/
 
@@ -522,6 +509,26 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define USB_USE_WAIT                        FALSE
 #endif
 
+/*===========================================================================*/
+/* WSPI driver related settings.                                             */
+/*===========================================================================*/
+
+/**
+ * @brief   Enables synchronous APIs.
+ * @note    Disabling this option saves both code and data space.
+ */
+#if !defined(WSPI_USE_WAIT) || defined(__DOXYGEN__)
+#define WSPI_USE_WAIT                       TRUE
+#endif
+
+/**
+ * @brief   Enables the @p wspiAcquireBus() and @p wspiReleaseBus() APIs.
+ * @note    Disabling this option saves both code and data space.
+ */
+#if !defined(WSPI_USE_MUTUAL_EXCLUSION) || defined(__DOXYGEN__)
+#define WSPI_USE_MUTUAL_EXCLUSION           TRUE
+#endif
+
 #endif /* HALCONF_H */
 
 /** @} */
diff --git a/modules/NUCLEO-F103RB/mcuconf.h b/modules/NUCLEO-F103RB/mcuconf.h
index 989747e..9de7140 100644
--- a/modules/NUCLEO-F103RB/mcuconf.h
+++ b/modules/NUCLEO-F103RB/mcuconf.h
@@ -110,6 +110,8 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define STM32_I2C_BUSY_TIMEOUT              50
 #define STM32_I2C_I2C1_IRQ_PRIORITY         5
 #define STM32_I2C_I2C2_IRQ_PRIORITY         5
+#define STM32_I2C_I2C1_USE_DMA              TRUE
+#define STM32_I2C_I2C2_USE_DMA              TRUE
 #define STM32_I2C_I2C1_DMA_PRIORITY         3
 #define STM32_I2C_I2C2_DMA_PRIORITY         3
 #define STM32_I2C_DMA_ERROR_HOOK(i2cp)      osalSysHalt("DMA failure")
diff --git a/modules/NUCLEO-F103RB/module.h b/modules/NUCLEO-F103RB/module.h
index 15cb346..76c900f 100644
--- a/modules/NUCLEO-F103RB/module.h
+++ b/modules/NUCLEO-F103RB/module.h
@@ -242,7 +242,7 @@ extern ROMCONST char* moduleShellPrompt;
 /**
  * @brief   HOOK to call process_deca_irq() func when the dw1000 interrupt pin is activated.
  */
-#define MODULE_MAIN_LOOP_IO_EVENT(eventflags) {	                              \
+#define MODULE_MAIN_LOOP_IO_EVENT(eventflags) {                               \
   if (eventflags & MODULE_OS_IOEVENTFLAGS_USERBUTTON) {                       \
     apalControlGpioState_t buttonstate;                                       \
     apalControlGpioGet(&moduleGpioUserButton, &buttonstate);                  \
diff --git a/modules/NUCLEO-L476RG/Makefile b/modules/NUCLEO-L476RG/Makefile
index b9b8b23..d00ea1d 100644
--- a/modules/NUCLEO-L476RG/Makefile
+++ b/modules/NUCLEO-L476RG/Makefile
@@ -43,7 +43,7 @@ ifeq ($(USE_CPPOPT),)
   USE_CPPOPT = -fno-rtti -std=c++17
 endif
 
-# Enable this if you want the linker to remove unused code and data
+# Enable this if you want the linker to remove unused code and data.
 ifeq ($(USE_LINK_GC),)
   USE_LINK_GC = yes
 endif
@@ -53,16 +53,11 @@ ifeq ($(USE_LDOPT),)
   USE_LDOPT =
 endif
 
-# Enable this if you want link time optimizations (LTO)
+# Enable this if you want link time optimizations (LTO).
 ifeq ($(USE_LTO),)
   USE_LTO = yes
 endif
 
-# If enabled, this option allows to compile the application in THUMB mode.
-ifeq ($(USE_THUMB),)
-  USE_THUMB = yes
-endif
-
 # Enable this if you want to see the full log while compiling.
 ifeq ($(USE_VERBOSE_COMPILE),)
   USE_VERBOSE_COMPILE = no
@@ -94,7 +89,7 @@ ifeq ($(USE_EXCEPTIONS_STACKSIZE),)
   USE_EXCEPTIONS_STACKSIZE = 0x400
 endif
 
-# Enables the use of FPU on Cortex-M4.
+# Enables the use of FPU.
 # Possible selections are:
 #   no     - no FPU is used (probably equals 'soft')
 #   soft   - does not use the FPU, thus all floating point operations are emulated
@@ -104,32 +99,47 @@ ifeq ($(USE_FPU),)
   USE_FPU = softfp
 endif
 
+# FPU-related options.
+ifeq ($(USE_FPU_OPT),)
+  USE_FPU_OPT = -mfloat-abi=$(USE_FPU) -mfpu=fpv4-sp-d16
+endif
+
 #                                                                              #
 # Architecture or project specific options                                     #
 ################################################################################
 
 ################################################################################
-# Project, sources and paths                                                   #
+# Project, target, sources and paths                                           #
 #                                                                              #
 
 # Define project name here
 PROJECT := $(patsubst $(abspath $(dir $(abspath $(lastword $(MAKEFILE_LIST))))..)/%,%,$(abspath $(dir $(abspath $(lastword $(MAKEFILE_LIST))))))
 
-# Imported source files and paths
+# Target settings.
+MCU = cortex-m4
+
+# Imported source files and paths.
 include ../../kernel/kernel.mk
-CHIBIOS := $(AMIROOS_KERNEL)
-AMIROOS = ../..
-# Licensing files
+CHIBIOS    := $(AMIROOS_KERNEL)
+CONFDIR    := .
+ifeq ($(BUILDDIR),)
+  BUILDDIR := ./build
+endif
+DEPDIR     := $(dir $(BUILDDIR)).dep
+AMIROOS    := ../..
+# Licensing files.
 include $(CHIBIOS)/os/license/license.mk
-# Startup files
+# Startup files.
 include $(CHIBIOS)/os/common/startup/ARMCMx/compilers/GCC/mk/startup_stm32l4xx.mk
-# HAL-OSAL files
+# HAL-OSAL files (optional).
 include $(CHIBIOS)/os/hal/hal.mk
 include $(CHIBIOS)/os/hal/ports/STM32/STM32L4xx/platform.mk
 include $(CHIBIOS)/os/hal/osal/rt/osal.mk
-# RTOS files
+# RTOS files (optional).
 include $(CHIBIOS)/os/rt/rt.mk
 include $(CHIBIOS)/os/common/ports/ARMCMx/compilers/GCC/mk/port_v7m.mk
+# Auto-build files in ./source recursively.
+include $(CHIBIOS)/tools/mk/autobuild.mk
 # Other files (optional).
 include $(CHIBIOS)/test/lib/test.mk
 include $(CHIBIOS)/test/rt/rt_test.mk
@@ -148,126 +158,55 @@ LDSCRIPT= STM32L476xG.ld
 
 # C sources that can be compiled in ARM or THUMB mode depending on the global
 # setting.
-CSRC = $(LICSRC) \
-       $(STARTUPSRC) \
-       $(KERNSRC) \
-       $(PORTSRC) \
-       $(OSALSRC) \
-       $(HALSRC) \
-       $(PLATFORMSRC) \
-       $(MODULESCSRC) \
+CSRC = $(ALLCSRC) \
        $(TESTSRC) \
-       $(PERIPHERYLLDCSRC) \
-       $(AMIROOSCORECSRC) \
-       $(UNITTESTSCSRC) \
        $(CHIBIOS)/os/various/evtimer.c \
        $(CHIBIOS)/os/various/syscalls.c \
        $(CHIBIOS)/os/hal/lib/streams/chprintf.c \
        board.c \
+       $(PERIPHERYLLDCSRC) \
+       $(UNITTESTSCSRC) \
+       $(AMIROOSCORECSRC) \
+       $(MODULESCSRC) \
        module.c \
        $(APPSCSRC)
 
 # C++ sources that can be compiled in ARM or THUMB mode depending on the global
 # setting.
-CPPSRC = $(AMIROOSCORECPPSRC) \
+CPPSRC = $(ALLCPPSRC) \
          $(CHIBIOS)/os/various/cpp_wrappers/syscalls_cpp.cpp \
+         $(AMIROOSCORECPPSRC) \
          $(APPSCPPSRC)
 
-# C sources to be compiled in ARM mode regardless of the global setting.
-# NOTE: Mixing ARM and THUMB mode enables the -mthumb-interwork compiler
-#       option that results in lower performance and larger code size.
-ACSRC = $(APPSACSRC)
-
-# C++ sources to be compiled in ARM mode regardless of the global setting.
-# NOTE: Mixing ARM and THUMB mode enables the -mthumb-interwork compiler
-#       option that results in lower performance and larger code size.
-ACPPSRC = $(APPSACPPSRC)
-
-# C sources to be compiled in THUMB mode regardless of the global setting.
-# NOTE: Mixing ARM and THUMB mode enables the -mthumb-interwork compiler
-#       option that results in lower performance and larger code size.
-TCSRC = $(APPSTCSRC)
-
-# C sources to be compiled in THUMB mode regardless of the global setting.
-# NOTE: Mixing ARM and THUMB mode enables the -mthumb-interwork compiler
-#       option that results in lower performance and larger code size.
-TCPPSRC = $(APPSTCPPSRC)
-
-# List ASM source files here
-ASMSRC = $(APPSASMSRC)
-ASMXSRC = $(STARTUPASM) \
-          $(PORTASM) \
-          $(OSALASM) \
+# List ASM source files here.
+ASMSRC = $(ALLASMSRC) \
+         $(APPSASMSRC)
+
+# List ASM with preprocessor source files here.
+ASMXSRC = $(ALLXASMSRC) \
           $(APPSASMXSRC)
 
-INCDIR = $(LICINC) \
-         $(STARTUPINC) \
-         $(KERNINC) \
-         $(PORTINC) \
-         $(OSALINC) \
-         $(HALINC) \
-         $(PLATFORMINC) \
-         $(MODULESINC) \
+# Inclusion directories.
+INCDIR = $(CONFDIR) \
+         $(ALLINC) \
          $(TESTINC) \
-         $(BOOTLOADERINC) \
          $(CHIBIOS)/os/hal/lib/streams \
+         $(BOOTLOADERINC) \
          $(PERIPHERYLLDINC) \
          $(AMIROOS) \
-         $(AMIROOSCOREINC) \
          $(UNITTESTSINC) \
+         $(AMIROOSCOREINC) \
+         $(MODULESINC) \
          $(APPSINC)
 
-#                                                                              #
-# Project, sources and paths                                                   #
-################################################################################
-
-################################################################################
-# Compiler settings                                                            #
-# NOTE: Some can be overridden externally.                                     #
-#                                                                              #
-
-MCU  = cortex-m4
-
-#TRGT = arm-elf-
-TRGT = arm-none-eabi-
-CC   = $(TRGT)gcc
-CPPC = $(TRGT)g++
-# Enable loading with g++ only if you need C++ runtime support.
-# NOTE: You can use C++ even without C++ support if you are careful. C++
-#       runtime support makes code size explode.
-LD   = $(TRGT)gcc
-#LD   = $(TRGT)g++
-CP   = $(TRGT)objcopy
-AS   = $(TRGT)gcc -x assembler-with-cpp
-AR   = $(TRGT)ar
-OD   = $(TRGT)objdump
-SZ   = $(TRGT)size
-HEX  = $(CP) -O ihex
-BIN  = $(CP) -O binary
-SREC = $(CP) -O srec --srec-len=248
-
-# ARM-specific options here
-ifeq ($(AOPT),)
-  AOPT =
-endif
-
-# THUMB-specific options here
-ifeq ($(TOPT),)
-  TOPT = -mthumb -DTHUMB
-endif
-
-# Define C warning options here
-ifeq ($(CWARN),)
-  CWARN = -Wall -Wextra -Wundef -Wstrict-prototypes
-endif
+# Define C warning options here.
+CWARN = -Wall -Wextra -Wundef -Wstrict-prototypes
 
-# Define C++ warning options here
-ifeq ($(CPPWARN),)
-  CPPWARN = -Wall -Wextra -Wundef
-endif
+# Define C++ warning options here.
+CPPWARN = -Wall -Wextra -Wundef
 
 #                                                                              #
-# Compiler settings                                                            #
+# Project, target, sources and paths                                           #
 ################################################################################
 
 ################################################################################
@@ -290,27 +229,29 @@ ULIBDIR +=
 ULIBS +=
 
 #                                                                              #
-# End of user defines                                                          #
+# End of user section                                                          #
 ################################################################################
 
 ################################################################################
-# Start of targets section                                                     #
+# Common rules                                                                 #
 #                                                                              #
 
-# all and its dependencies
-ifeq ($(BUILDDIR),)
-	BUILDDIR = ./build
-endif
-RULESPATH = $(CHIBIOS)/os/common/startup/ARMCMx/compilers/GCC
+RULESPATH = $(CHIBIOS)/os/common/startup/ARMCMx/compilers/GCC/mk
+include $(RULESPATH)/arm-none-eabi.mk
 include $(RULESPATH)/rules.mk
 
-# flash
-include $(AMIROOS)/bootloader/bootloader.mk
+#                                                                              #
+# Common rules                                                                 #
+################################################################################
+
+################################################################################
+# Custom rules                                                                 #
+#                                                                              #
 
 flash: $(BUILDDIR)/$(PROJECT).elf
 	openocd -f interface/stlink-v2-1.cfg -c "set WORKAREASIZE 0x2000" -f target/stm32l4x.cfg -c "program build/$(PROJECT).elf verify reset exit"
 
 #                                                                              #
-# End of targets section                                                       #
+# Custom rules                                                                 #
 ################################################################################
 
diff --git a/modules/NUCLEO-L476RG/chconf.h b/modules/NUCLEO-L476RG/chconf.h
index cdaf9b4..71ecd7a 100644
--- a/modules/NUCLEO-L476RG/chconf.h
+++ b/modules/NUCLEO-L476RG/chconf.h
@@ -123,6 +123,11 @@
  */
 /*===========================================================================*/
 
+/**
+ * @brief   Flag to enable/disable sleep mode when the system is idle.
+ */
+#define CORTEX_ENABLE_WFI_IDLE                  TRUE
+
 /** @} */
 
 /*===========================================================================*/
@@ -132,11 +137,6 @@
  */
 /*===========================================================================*/
 
-/**
- * @brief   Flag to enable/disable sleep mode when the system is idle.
- */
-#define CORTEX_ENABLE_WFI_IDLE                  TRUE
-
 // common definitions in aos_chconf.h
 
 /** @} */
diff --git a/modules/NUCLEO-L476RG/halconf.h b/modules/NUCLEO-L476RG/halconf.h
index 0b57bf8..7665d81 100644
--- a/modules/NUCLEO-L476RG/halconf.h
+++ b/modules/NUCLEO-L476RG/halconf.h
@@ -31,7 +31,7 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define HALCONF_H
 
 #define _CHIBIOS_HAL_CONF_
-#define _CHIBIOS_HAL_CONF_VER_6_0_
+#define _CHIBIOS_HAL_CONF_VER_7_0_
 
 #include <alldconf.h>
 #include "mcuconf.h"
@@ -72,13 +72,6 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #endif
 
 /**
- * @brief   Enables the EXT subsystem.
- */
-#if !defined(HAL_USE_EXT) || defined(__DOXYGEN__)
-#define HAL_USE_EXT                         FALSE
-#endif
-
-/**
  * @brief   Enables the GPT subsystem.
  */
 #if !defined(HAL_USE_GPT) || defined(__DOXYGEN__)
@@ -140,13 +133,6 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #endif
 
 /**
- * @brief   Enables the QSPI subsystem.
- */
-#if !defined(HAL_USE_QSPI) || defined(__DOXYGEN__)
-#define HAL_USE_QSPI                        FALSE
-#endif
-
-/**
  * @brief   Enables the RTC subsystem.
  */
 #if !defined(HAL_USE_RTC) || defined(__DOXYGEN__)
@@ -175,6 +161,13 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #endif
 
 /**
+ * @brief   Enables the SIO subsystem.
+ */
+#if !defined(HAL_USE_SIO) || defined(__DOXYGEN__)
+#define HAL_USE_SIO                         FALSE
+#endif
+
+/**
  * @brief   Enables the SPI subsystem.
  */
 #if !defined(HAL_USE_SPI) || defined(__DOXYGEN__)
@@ -182,6 +175,13 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #endif
 
 /**
+ * @brief   Enables the TRNG subsystem.
+ */
+#if !defined(HAL_USE_TRNG) || defined(__DOXYGEN__)
+#define HAL_USE_TRNG                        FALSE
+#endif
+
+/**
  * @brief   Enables the UART subsystem.
  */
 #if !defined(HAL_USE_UART) || defined(__DOXYGEN__)
@@ -202,6 +202,13 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define HAL_USE_WDG                         FALSE
 #endif
 
+/**
+ * @brief   Enables the WSPI subsystem.
+ */
+#if !defined(HAL_USE_WSPI) || defined(__DOXYGEN__)
+#define HAL_USE_WSPI                        FALSE
+#endif
+
 /*===========================================================================*/
 /* PAL driver related settings.                                              */
 /*===========================================================================*/
@@ -348,26 +355,6 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #endif
 
 /*===========================================================================*/
-/* QSPI driver related settings.                                             */
-/*===========================================================================*/
-
-/**
- * @brief   Enables synchronous APIs.
- * @note    Disabling this option saves both code and data space.
- */
-#if !defined(QSPI_USE_WAIT) || defined(__DOXYGEN__)
-#define QSPI_USE_WAIT                       TRUE
-#endif
-
-/**
- * @brief   Enables the @p qspiAcquireBus() and @p qspiReleaseBus() APIs.
- * @note    Disabling this option saves both code and data space.
- */
-#if !defined(QSPI_USE_MUTUAL_EXCLUSION) || defined(__DOXYGEN__)
-#define QSPI_USE_MUTUAL_EXCLUSION           TRUE
-#endif
-
-/*===========================================================================*/
 /* SDC driver related settings.                                              */
 /*===========================================================================*/
 
@@ -528,6 +515,26 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define USB_USE_WAIT                        FALSE
 #endif
 
+/*===========================================================================*/
+/* WSPI driver related settings.                                             */
+/*===========================================================================*/
+
+/**
+ * @brief   Enables synchronous APIs.
+ * @note    Disabling this option saves both code and data space.
+ */
+#if !defined(WSPI_USE_WAIT) || defined(__DOXYGEN__)
+#define WSPI_USE_WAIT                       TRUE
+#endif
+
+/**
+ * @brief   Enables the @p wspiAcquireBus() and @p wspiReleaseBus() APIs.
+ * @note    Disabling this option saves both code and data space.
+ */
+#if !defined(WSPI_USE_MUTUAL_EXCLUSION) || defined(__DOXYGEN__)
+#define WSPI_USE_MUTUAL_EXCLUSION           TRUE
+#endif
+
 #endif /* HALCONF_H */
 
 /** @} */
diff --git a/modules/NUCLEO-L476RG/mcuconf.h b/modules/NUCLEO-L476RG/mcuconf.h
index bc3e350..5671691 100644
--- a/modules/NUCLEO-L476RG/mcuconf.h
+++ b/modules/NUCLEO-L476RG/mcuconf.h
@@ -16,11 +16,8 @@ You should have received a copy of the GNU General Public License
 along with this program.  If not, see <http://www.gnu.org/licenses/>.
 */
 
-#ifndef MCUCONF_H
-#define MCUCONF_H
-
 /*
- * STM32L1xx drivers configuration.
+ * STM32L4xx drivers configuration.
  * The following settings override the default settings present in
  * the various device driver implementation headers.
  * Note that the settings for each driver only have effect if the whole
@@ -33,7 +30,12 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  * 0...3        Lowest...Highest.
  */
 
+#ifndef MCUCONF_H
+#define MCUCONF_H
+
 #define STM32L4xx_MCUCONF
+#define STM32L476_MCUCONF
+#define STM32L486_MCUCONF
 
 /*
  * HAL driver system settings.
@@ -47,10 +49,6 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define STM32_HSE_ENABLED                   FALSE
 #define STM32_LSE_ENABLED                   TRUE
 #define STM32_MSIPLL_ENABLED                TRUE
-#define STM32_ADC_CLOCK_ENABLED             TRUE
-#define STM32_USB_CLOCK_ENABLED             TRUE
-#define STM32_SAI1_CLOCK_ENABLED            TRUE
-#define STM32_SAI2_CLOCK_ENABLED            TRUE
 #define STM32_MSIRANGE                      STM32_MSIRANGE_4M
 #define STM32_MSISRANGE                     STM32_MSISRANGE_4M
 #define STM32_SW                            STM32_SW_PLL
@@ -74,6 +72,10 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define STM32_PLLSAI2N_VALUE                72
 #define STM32_PLLSAI2P_VALUE                7
 #define STM32_PLLSAI2R_VALUE                6
+
+/*
+ * Peripherals clock sources.
+ */
 #define STM32_USART1SEL                     STM32_USART1SEL_SYSCLK
 #define STM32_USART2SEL                     STM32_USART2SEL_SYSCLK
 #define STM32_USART3SEL                     STM32_USART3SEL_SYSCLK
@@ -108,6 +110,10 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define STM32_IRQ_EXTI19_PRIORITY           6
 #define STM32_IRQ_EXTI20_PRIORITY           6
 #define STM32_IRQ_EXTI21_22_PRIORITY        15
+#define STM32_IRQ_TIM1_BRK_TIM15_PRIORITY   7
+#define STM32_IRQ_TIM1_UP_TIM16_PRIORITY    7
+#define STM32_IRQ_TIM1_TRGCO_TIM17_PRIORITY 7
+#define STM32_IRQ_TIM1_CC_PRIORITY          7
 
 /*
  * ADC driver system settings.
@@ -116,7 +122,7 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define STM32_ADC_COMPACT_SAMPLES           FALSE
 #define STM32_ADC_USE_ADC1                  FALSE
 #define STM32_ADC_USE_ADC2                  FALSE
-#define STM32_ADC_USE_ADC3                  TRUE // turned on
+#define STM32_ADC_USE_ADC3                  TRUE
 #define STM32_ADC_ADC1_DMA_STREAM           STM32_DMA_STREAM_ID(1, 1)
 #define STM32_ADC_ADC2_DMA_STREAM           STM32_DMA_STREAM_ID(1, 2)
 #define STM32_ADC_ADC3_DMA_STREAM           STM32_DMA_STREAM_ID(1, 3)
@@ -171,9 +177,6 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define STM32_GPT_TIM6_IRQ_PRIORITY         7
 #define STM32_GPT_TIM7_IRQ_PRIORITY         7
 #define STM32_GPT_TIM8_IRQ_PRIORITY         7
-#define STM32_GPT_TIM15_IRQ_PRIORITY        7
-#define STM32_GPT_TIM16_IRQ_PRIORITY        7
-#define STM32_GPT_TIM17_IRQ_PRIORITY        7
 
 /*
  * I2C driver system settings.
@@ -205,6 +208,7 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define STM32_ICU_USE_TIM4                  FALSE
 #define STM32_ICU_USE_TIM5                  FALSE
 #define STM32_ICU_USE_TIM8                  FALSE
+#define STM32_ICU_USE_TIM15                 FALSE
 #define STM32_ICU_TIM1_IRQ_PRIORITY         7
 #define STM32_ICU_TIM2_IRQ_PRIORITY         7
 #define STM32_ICU_TIM3_IRQ_PRIORITY         7
@@ -222,6 +226,9 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define STM32_PWM_USE_TIM4                  FALSE
 #define STM32_PWM_USE_TIM5                  FALSE
 #define STM32_PWM_USE_TIM8                  FALSE
+#define STM32_PWM_USE_TIM15                 FALSE
+#define STM32_PWM_USE_TIM16                 FALSE
+#define STM32_PWM_USE_TIM17                 FALSE
 #define STM32_PWM_TIM1_IRQ_PRIORITY         7
 #define STM32_PWM_TIM2_IRQ_PRIORITY         7
 #define STM32_PWM_TIM3_IRQ_PRIORITY         7
@@ -230,10 +237,12 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define STM32_PWM_TIM8_IRQ_PRIORITY         7
 
 /*
- * QSPI driver system settings.
+ * RTC driver system settings.
  */
-#define STM32_QSPI_USE_QUADSPI1             FALSE
-#define STM32_QSPI_QUADSPI1_DMA_STREAM      STM32_DMA_STREAM_ID(2, 7)
+#define STM32_RTC_PRESA_VALUE               32
+#define STM32_RTC_PRESS_VALUE               1024
+#define STM32_RTC_CR_INIT                   0
+#define STM32_RTC_TAMPCR_INIT               0
 
 /*
  * SDC driver system settings.
@@ -253,10 +262,14 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define STM32_SERIAL_USE_USART1             FALSE
 #define STM32_SERIAL_USE_USART2             TRUE
 #define STM32_SERIAL_USE_USART3             FALSE
+#define STM32_SERIAL_USE_UART4              FALSE
+#define STM32_SERIAL_USE_UART5              FALSE
 #define STM32_SERIAL_USE_LPUART1            FALSE
 #define STM32_SERIAL_USART1_PRIORITY        12
 #define STM32_SERIAL_USART2_PRIORITY        12
 #define STM32_SERIAL_USART3_PRIORITY        12
+#define STM32_SERIAL_UART4_PRIORITY         12
+#define STM32_SERIAL_UART5_PRIORITY         12
 #define STM32_SERIAL_LPUART1_PRIORITY       12
 
 /*
@@ -286,6 +299,11 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define STM32_ST_USE_TIMER                  2
 
 /*
+ * TRNG driver system settings.
+ */
+#define STM32_TRNG_USE_RNG1                 FALSE
+
+/*
  * UART driver system settings.
  */
 #define STM32_UART_USE_USART1               FALSE
@@ -293,7 +311,6 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define STM32_UART_USE_USART3               FALSE
 #define STM32_UART_USE_UART4                FALSE
 #define STM32_UART_USE_UART5                FALSE
-#define STM32_UART_USE_LPUART1              FALSE
 #define STM32_UART_USART1_RX_DMA_STREAM     STM32_DMA_STREAM_ID(2, 7)
 #define STM32_UART_USART1_TX_DMA_STREAM     STM32_DMA_STREAM_ID(2, 6)
 #define STM32_UART_USART2_RX_DMA_STREAM     STM32_DMA_STREAM_ID(1, 6)
@@ -304,8 +321,6 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define STM32_UART_UART4_TX_DMA_STREAM      STM32_DMA_STREAM_ID(2, 3)
 #define STM32_UART_UART5_RX_DMA_STREAM      STM32_DMA_STREAM_ID(2, 2)
 #define STM32_UART_UART5_TX_DMA_STREAM      STM32_DMA_STREAM_ID(2, 1)
-#define STM32_UART_LPUART1_RX_DMA_STREAM    STM32_DMA_STREAM_ID(2, 7)
-#define STM32_UART_LPUART1_TX_DMA_STREAM    STM32_DMA_STREAM_ID(2, 6)
 #define STM32_UART_USART1_IRQ_PRIORITY      12
 #define STM32_UART_USART2_IRQ_PRIORITY      12
 #define STM32_UART_USART3_IRQ_PRIORITY      12
@@ -316,7 +331,6 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define STM32_UART_USART3_DMA_PRIORITY      0
 #define STM32_UART_UART4_DMA_PRIORITY       0
 #define STM32_UART_UART5_DMA_PRIORITY       0
-#define STM32_UART_LPUART1_DMA_PRIORITY     0
 #define STM32_UART_DMA_ERROR_HOOK(uartp)    osalSysHalt("DMA failure")
 
 /*
@@ -325,9 +339,6 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define STM32_USB_USE_OTG1                  FALSE
 #define STM32_USB_OTG1_IRQ_PRIORITY         14
 #define STM32_USB_OTG1_RX_FIFO_SIZE         512
-#define STM32_USB_OTG_THREAD_PRIO           LOWPRIO
-#define STM32_USB_OTG_THREAD_STACK_SIZE     128
-#define STM32_USB_OTGFIFO_FILL_BASEPRI      0
 
 /*
  * WDG driver system settings.
@@ -335,13 +346,9 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define STM32_WDG_USE_IWDG                  FALSE
 
 /*
- * QEI driver system settings.
+ * WSPI driver system settings.
  */
-#define STM32_QEI_USE_TIM1                  FALSE
-#define STM32_QEI_USE_TIM2                  FALSE
-#define STM32_QEI_USE_TIM3                  FALSE
-#define STM32_QEI_USE_TIM4                  FALSE
-#define STM32_QEI_USE_TIM5                  FALSE
-#define STM32_QEI_USE_TIM8                  FALSE
+#define STM32_WSPI_USE_QUADSPI1             FALSE
+#define STM32_WSPI_QUADSPI1_DMA_STREAM      STM32_DMA_STREAM_ID(2, 7)
 
 #endif /* MCUCONF_H */
diff --git a/modules/PowerManagement_1-1/Makefile b/modules/PowerManagement_1-1/Makefile
index c9164af..aaeeab6 100644
--- a/modules/PowerManagement_1-1/Makefile
+++ b/modules/PowerManagement_1-1/Makefile
@@ -43,7 +43,7 @@ ifeq ($(USE_CPPOPT),)
   USE_CPPOPT = -fno-rtti -std=c++17
 endif
 
-# Enable this if you want the linker to remove unused code and data
+# Enable this if you want the linker to remove unused code and data.
 ifeq ($(USE_LINK_GC),)
   USE_LINK_GC = yes
 endif
@@ -53,16 +53,11 @@ ifeq ($(USE_LDOPT),)
   USE_LDOPT =
 endif
 
-# Enable this if you want link time optimizations (LTO)
+# Enable this if you want link time optimizations (LTO).
 ifeq ($(USE_LTO),)
   USE_LTO = yes
 endif
 
-# If enabled, this option allows to compile the application in THUMB mode.
-ifeq ($(USE_THUMB),)
-  USE_THUMB = yes
-endif
-
 # Enable this if you want to see the full log while compiling.
 ifeq ($(USE_VERBOSE_COMPILE),)
   USE_VERBOSE_COMPILE = no
@@ -94,7 +89,7 @@ ifeq ($(USE_EXCEPTIONS_STACKSIZE),)
   USE_EXCEPTIONS_STACKSIZE = 0x400
 endif
 
-# Enables the use of FPU on Cortex-M4.
+# Enables the use of FPU.
 # Possible selections are:
 #   no     - no FPU is used (probably equals 'soft')
 #   soft   - does not use the FPU, thus all floating point operations are emulated
@@ -104,32 +99,47 @@ ifeq ($(USE_FPU),)
   USE_FPU = softfp
 endif
 
+# FPU-related options.
+ifeq ($(USE_FPU_OPT),)
+  USE_FPU_OPT = -mfloat-abi=$(USE_FPU) -mfpu=fpv4-sp-d16
+endif
+
 #                                                                              #
 # Architecture or project specific options                                     #
 ################################################################################
 
 ################################################################################
-# Project, sources and paths                                                   #
+# Project, target, sources and paths                                           #
 #                                                                              #
 
 # Define project name here
 PROJECT := $(patsubst $(abspath $(dir $(abspath $(lastword $(MAKEFILE_LIST))))..)/%,%,$(abspath $(dir $(abspath $(lastword $(MAKEFILE_LIST))))))
 
-# Imported source files and paths
+# Target settings.
+MCU = cortex-m4
+
+# Imported source files and paths.
 include ../../kernel/kernel.mk
-CHIBIOS := $(AMIROOS_KERNEL)
-AMIROOS = ../..
-# Licensing files
+CHIBIOS    := $(AMIROOS_KERNEL)
+CONFDIR    := .
+ifeq ($(BUILDDIR),)
+  BUILDDIR := ./build
+endif
+DEPDIR     := $(dir $(BUILDDIR)).dep
+AMIROOS    := ../..
+# Licensing files.
 include $(CHIBIOS)/os/license/license.mk
-# Startup files
+# Startup files.
 include $(CHIBIOS)/os/common/startup/ARMCMx/compilers/GCC/mk/startup_stm32f4xx.mk
-# HAL-OSAL files
+# HAL-OSAL files (optional).
 include $(CHIBIOS)/os/hal/hal.mk
 include $(CHIBIOS)/os/hal/ports/STM32/STM32F4xx/platform.mk
 include $(CHIBIOS)/os/hal/osal/rt/osal.mk
-# RTOS files
+# RTOS files (optional).
 include $(CHIBIOS)/os/rt/rt.mk
 include $(CHIBIOS)/os/common/ports/ARMCMx/compilers/GCC/mk/port_v7m.mk
+# Auto-build files in ./source recursively.
+include $(CHIBIOS)/tools/mk/autobuild.mk
 # Other files (optional).
 include $(CHIBIOS)/test/lib/test.mk
 include $(CHIBIOS)/test/rt/rt_test.mk
@@ -148,126 +158,58 @@ LDSCRIPT= STM32F405xG.ld
 
 # C sources that can be compiled in ARM or THUMB mode depending on the global
 # setting.
-CSRC = $(LICSRC) \
-       $(STARTUPSRC) \
-       $(KERNSRC) \
-       $(PORTSRC) \
-       $(OSALSRC) \
-       $(HALSRC) \
-       $(PLATFORMSRC) \
-       $(MODULESCSRC) \
+CSRC = $(ALLCSRC) \
        $(TESTSRC) \
-       $(PERIPHERYLLDCSRC) \
-       $(AMIROOSCORECSRC) \
-       $(UNITTESTSCSRC) \
        $(CHIBIOS)/os/various/evtimer.c \
        $(CHIBIOS)/os/various/syscalls.c \
        $(CHIBIOS)/os/hal/lib/streams/chprintf.c \
        board.c \
+       $(PERIPHERYLLDCSRC) \
+       $(UNITTESTSCSRC) \
+       $(AMIROOSCORECSRC) \
+       $(MODULESCSRC) \
        module.c \
        $(APPSCSRC)
 
 # C++ sources that can be compiled in ARM or THUMB mode depending on the global
 # setting.
-CPPSRC = $(AMIROOSCORECPPSRC) \
+CPPSRC = $(ALLCPPSRC) \
          $(CHIBIOS)/os/various/cpp_wrappers/syscalls_cpp.cpp \
+         $(AMIROOSCORECPPSRC) \
          $(APPSCPPSRC)
 
-# C sources to be compiled in ARM mode regardless of the global setting.
-# NOTE: Mixing ARM and THUMB mode enables the -mthumb-interwork compiler
-#       option that results in lower performance and larger code size.
-ACSRC = $(APPSACSRC)
-
-# C++ sources to be compiled in ARM mode regardless of the global setting.
-# NOTE: Mixing ARM and THUMB mode enables the -mthumb-interwork compiler
-#       option that results in lower performance and larger code size.
-ACPPSRC = $(APPSACPPSRC)
-
-# C sources to be compiled in THUMB mode regardless of the global setting.
-# NOTE: Mixing ARM and THUMB mode enables the -mthumb-interwork compiler
-#       option that results in lower performance and larger code size.
-TCSRC = $(APPSTCSRC)
-
-# C sources to be compiled in THUMB mode regardless of the global setting.
-# NOTE: Mixing ARM and THUMB mode enables the -mthumb-interwork compiler
-#       option that results in lower performance and larger code size.
-TCPPSRC = $(APPSTCPPSRC)
-
-# List ASM source files here
-ASMSRC = $(APPSASMSRC)
-ASMXSRC = $(STARTUPASM) \
-          $(PORTASM) \
-          $(OSALASM) \
+# List ASM source files here.
+ASMSRC = $(ALLASMSRC) \
+         $(APPSASMSRC)
+
+# List ASM with preprocessor source files here.
+ASMXSRC = $(ALLXASMSRC) \
           $(APPSASMXSRC)
 
-INCDIR = $(LICINC) \
-         $(STARTUPINC) \
-         $(KERNINC) \
-         $(PORTINC) \
-         $(OSALINC) \
-         $(HALINC) \
-         $(PLATFORMINC) \
-         $(MODULESINC) \
+# Inclusion directories.
+INCDIR = $(CONFDIR) \
+         $(ALLINC) \
          $(TESTINC) \
-         $(BOOTLOADERINC) \
          $(CHIBIOS)/os/hal/lib/streams \
+         $(BOOTLOADERINC) \
          $(PERIPHERYLLDINC) \
          $(AMIROOS) \
-         $(AMIROOSCOREINC) \
          $(UNITTESTSINC) \
+         $(AMIROOSCOREINC) \
+         $(MODULESINC) \
          $(APPSINC)
 
-#                                                                              #
-# Project, sources and paths                                                   #
-################################################################################
+# Define C warning options here.
+CWARN = -Wall -Wextra -Wundef -Wstrict-prototypes
 
-################################################################################
-# Compiler settings                                                            #
-# NOTE: Some can be overridden externally.                                     #
-#                                                                              #
+# Define C++ warning options here.
+CPPWARN = -Wall -Wextra -Wundef
 
-MCU  = cortex-m4
-
-#TRGT = arm-elf-
-TRGT = arm-none-eabi-
-CC   = $(TRGT)gcc
-CPPC = $(TRGT)g++
-# Enable loading with g++ only if you need C++ runtime support.
-# NOTE: You can use C++ even without C++ support if you are careful. C++
-#       runtime support makes code size explode.
-LD   = $(TRGT)gcc
-#LD   = $(TRGT)g++
-CP   = $(TRGT)objcopy
-AS   = $(TRGT)gcc -x assembler-with-cpp
-AR   = $(TRGT)ar
-OD   = $(TRGT)objdump
-SZ   = $(TRGT)size
-HEX  = $(CP) -O ihex
-BIN  = $(CP) -O binary
+# Create an additional .srec image file.
 SREC = $(CP) -O srec --srec-len=248
 
-# ARM-specific options here
-ifeq ($(AOPT),)
-  AOPT =
-endif
-
-# THUMB-specific options here
-ifeq ($(TOPT),)
-  TOPT = -mthumb -DTHUMB
-endif
-
-# Define C warning options here
-ifeq ($(CWARN),)
-  CWARN = -Wall -Wextra -Wundef -Wstrict-prototypes
-endif
-
-# Define C++ warning options here
-ifeq ($(CPPWARN),)
-  CPPWARN = -Wall -Wextra -Wundef
-endif
-
 #                                                                              #
-# Compiler settings                                                            #
+# Project, target, sources and paths                                           #
 ################################################################################
 
 ################################################################################
@@ -290,35 +232,38 @@ ULIBDIR +=
 ULIBS +=
 
 #                                                                              #
-# End of user defines                                                          #
+# End of user section                                                          #
 ################################################################################
 
 ################################################################################
-# Start of targets section                                                     #
+# Common rules                                                                 #
 #                                                                              #
 
-# all and its dependencies
-ifeq ($(BUILDDIR),)
-	BUILDDIR = ./build
-endif
-RULESPATH = $(CHIBIOS)/os/common/startup/ARMCMx/compilers/GCC
+RULESPATH = $(CHIBIOS)/os/common/startup/ARMCMx/compilers/GCC/mk
+include $(RULESPATH)/arm-none-eabi.mk
 include $(RULESPATH)/rules.mk
 
-# flash
-include $(AMIROOS)/bootloader/bootloader.mk
+#                                                                              #
+# Common rules                                                                 #
+################################################################################
+
+################################################################################
+# Custom rules                                                                 #
+#                                                                              #
+
 FLASH_MODULES = $(PROJECT)
 FLASH_FILES = $(BUILDDIR)/$(PROJECT).$(FLASHTOOL_EXT)
 
 flash: $(FLASH_FILES)
 	$(info )
-ifeq ($(FLASHTOOL),SerialBoot)
-	$(info Flashing ($(FLASHTOOL)):)
-	$(FLASHTOOL_CMD) $(FLASHTOOL_ARGS)
-else
-	$(info ERROR: unable to flash the module (SerialBoot unavailable))
-endif
+	ifeq ($(FLASHTOOL),SerialBoot)
+		$(info Flashing ($(FLASHTOOL)):)
+		$(FLASHTOOL_CMD) $(FLASHTOOL_ARGS)
+	else
+		$(info ERROR: unable to flash the module (SerialBoot unavailable))
+	endif
 
 #                                                                              #
-# End of targets section                                                       #
+# Custom rules                                                                 #
 ################################################################################
 
diff --git a/modules/PowerManagement_1-1/chconf.h b/modules/PowerManagement_1-1/chconf.h
index 377acdb..1eae532 100644
--- a/modules/PowerManagement_1-1/chconf.h
+++ b/modules/PowerManagement_1-1/chconf.h
@@ -129,6 +129,11 @@
  */
 #define CORTEX_VTOR_INIT                        0x00008000U
 
+/**
+ * @brief   Flag to enable/disable sleep mode when the system is idle.
+ */
+#define CORTEX_ENABLE_WFI_IDLE                  TRUE
+
 /** @} */
 
 /*===========================================================================*/
@@ -138,11 +143,6 @@
  */
 /*===========================================================================*/
 
-/**
- * @brief   Flag to enable/disable sleep mode when the system is idle.
- */
-#define CORTEX_ENABLE_WFI_IDLE                  TRUE
-
 // common definitions in aos_chconf.h
 
 /** @} */
diff --git a/modules/PowerManagement_1-1/halconf.h b/modules/PowerManagement_1-1/halconf.h
index 391f838..cc61d2e 100644
--- a/modules/PowerManagement_1-1/halconf.h
+++ b/modules/PowerManagement_1-1/halconf.h
@@ -31,7 +31,7 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define HALCONF_H
 
 #define _CHIBIOS_HAL_CONF_
-#define _CHIBIOS_HAL_CONF_VER_6_0_
+#define _CHIBIOS_HAL_CONF_VER_7_0_
 
 #include "mcuconf.h"
 
@@ -71,13 +71,6 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #endif
 
 /**
- * @brief   Enables the EXT subsystem.
- */
-#if !defined(HAL_USE_EXT) || defined(__DOXYGEN__)
-#define HAL_USE_EXT                         FALSE
-#endif
-
-/**
  * @brief   Enables the GPT subsystem.
  */
 #if !defined(HAL_USE_GPT) || defined(__DOXYGEN__)
@@ -134,13 +127,6 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #endif
 
 /**
- * @brief   Enables the QSPI subsystem.
- */
-#if !defined(HAL_USE_QSPI) || defined(__DOXYGEN__)
-#define HAL_USE_QSPI                        FALSE
-#endif
-
-/**
  * @brief   Enables the RTC subsystem.
  */
 #if !defined(HAL_USE_RTC) || defined(__DOXYGEN__)
@@ -169,6 +155,13 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #endif
 
 /**
+ * @brief   Enables the SIO subsystem.
+ */
+#if !defined(HAL_USE_SIO) || defined(__DOXYGEN__)
+#define HAL_USE_SIO                         FALSE
+#endif
+
+/**
  * @brief   Enables the SPI subsystem.
  */
 #if !defined(HAL_USE_SPI) || defined(__DOXYGEN__)
@@ -176,6 +169,13 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #endif
 
 /**
+ * @brief   Enables the TRNG subsystem.
+ */
+#if !defined(HAL_USE_TRNG) || defined(__DOXYGEN__)
+#define HAL_USE_TRNG                        FALSE
+#endif
+
+/**
  * @brief   Enables the UART subsystem.
  */
 #if !defined(HAL_USE_UART) || defined(__DOXYGEN__)
@@ -196,6 +196,13 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define HAL_USE_WDG                         FALSE
 #endif
 
+/**
+ * @brief   Enables the WSPI subsystem.
+ */
+#if !defined(HAL_USE_WSPI) || defined(__DOXYGEN__)
+#define HAL_USE_WSPI                        FALSE
+#endif
+
 /*===========================================================================*/
 /* PAL driver related settings.                                              */
 /*===========================================================================*/
@@ -322,7 +329,7 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  * @brief   Enables an event sources for incoming packets.
  */
 #if !defined(MAC_USE_EVENTS) || defined(__DOXYGEN__)
-#define MAC_USE_EVENTS                      FALSE
+#define MAC_USE_EVENTS                      TRUE
 #endif
 
 /*===========================================================================*/
@@ -338,27 +345,7 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  *          use a DMA channel and heavily loads the CPU.
  */
 #if !defined(MMC_NICE_WAITING) || defined(__DOXYGEN__)
-#define MMC_NICE_WAITING                    FALSE
-#endif
-
-/*===========================================================================*/
-/* QSPI driver related settings.                                             */
-/*===========================================================================*/
-
-/**
- * @brief   Enables synchronous APIs.
- * @note    Disabling this option saves both code and data space.
- */
-#if !defined(QSPI_USE_WAIT) || defined(__DOXYGEN__)
-#define QSPI_USE_WAIT                       TRUE
-#endif
-
-/**
- * @brief   Enables the @p qspiAcquireBus() and @p qspiReleaseBus() APIs.
- * @note    Disabling this option saves both code and data space.
- */
-#if !defined(QSPI_USE_MUTUAL_EXCLUSION) || defined(__DOXYGEN__)
-#define QSPI_USE_MUTUAL_EXCLUSION           TRUE
+#define MMC_NICE_WAITING                    TRUE
 #endif
 
 /*===========================================================================*/
@@ -389,7 +376,7 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  *          lower priority, this may slow down the driver a bit however.
  */
 #if !defined(SDC_NICE_WAITING) || defined(__DOXYGEN__)
-#define SDC_NICE_WAITING                    FALSE
+#define SDC_NICE_WAITING                    TRUE
 #endif
 
 /**
@@ -522,6 +509,26 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define USB_USE_WAIT                        FALSE
 #endif
 
+/*===========================================================================*/
+/* WSPI driver related settings.                                             */
+/*===========================================================================*/
+
+/**
+ * @brief   Enables synchronous APIs.
+ * @note    Disabling this option saves both code and data space.
+ */
+#if !defined(WSPI_USE_WAIT) || defined(__DOXYGEN__)
+#define WSPI_USE_WAIT                       TRUE
+#endif
+
+/**
+ * @brief   Enables the @p wspiAcquireBus() and @p wspiReleaseBus() APIs.
+ * @note    Disabling this option saves both code and data space.
+ */
+#if !defined(WSPI_USE_MUTUAL_EXCLUSION) || defined(__DOXYGEN__)
+#define WSPI_USE_MUTUAL_EXCLUSION           TRUE
+#endif
+
 #endif /* HALCONF_H */
 
 /** @} */
diff --git a/modules/PowerManagement_1-1/mcuconf.h b/modules/PowerManagement_1-1/mcuconf.h
index e1abd26..9714490 100644
--- a/modules/PowerManagement_1-1/mcuconf.h
+++ b/modules/PowerManagement_1-1/mcuconf.h
@@ -74,7 +74,7 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define STM32_BKPRAM_ENABLE                 FALSE
 
 /*
- * EXT driver system settings.
+ * IRQ system settings.
  */
 #define STM32_IRQ_EXTI0_PRIORITY            6
 #define STM32_IRQ_EXTI1_PRIORITY            6
@@ -247,8 +247,8 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  */
 #define STM32_SDC_SDIO_DMA_PRIORITY         3
 #define STM32_SDC_SDIO_IRQ_PRIORITY         9
-#define STM32_SDC_WRITE_TIMEOUT_MS          250
-#define STM32_SDC_READ_TIMEOUT_MS           25
+#define STM32_SDC_WRITE_TIMEOUT_MS          1000
+#define STM32_SDC_READ_TIMEOUT_MS           1000
 #define STM32_SDC_CLOCK_ACTIVATION_DELAY    10
 #define STM32_SDC_SDIO_UNALIGNED_SUPPORT    TRUE
 #define STM32_SDC_SDIO_DMA_STREAM           STM32_DMA_STREAM_ID(2, 3)
@@ -348,14 +348,4 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  */
 #define STM32_WDG_USE_IWDG                  FALSE
 
-/*
- * QEI driver system settings.
- */
-#define STM32_QEI_USE_TIM1                  FALSE
-#define STM32_QEI_USE_TIM2                  FALSE
-#define STM32_QEI_USE_TIM3                  FALSE
-#define STM32_QEI_USE_TIM4                  FALSE
-#define STM32_QEI_USE_TIM5                  FALSE
-#define STM32_QEI_USE_TIM8                  FALSE
-
 #endif /* MCUCONF_H */
diff --git a/modules/STM32F407G-DISC1/Makefile b/modules/STM32F407G-DISC1/Makefile
index 6debb2f..7f8b6a6 100644
--- a/modules/STM32F407G-DISC1/Makefile
+++ b/modules/STM32F407G-DISC1/Makefile
@@ -43,7 +43,7 @@ ifeq ($(USE_CPPOPT),)
   USE_CPPOPT = -fno-rtti -std=c++17
 endif
 
-# Enable this if you want the linker to remove unused code and data
+# Enable this if you want the linker to remove unused code and data.
 ifeq ($(USE_LINK_GC),)
   USE_LINK_GC = yes
 endif
@@ -53,16 +53,11 @@ ifeq ($(USE_LDOPT),)
   USE_LDOPT =
 endif
 
-# Enable this if you want link time optimizations (LTO)
+# Enable this if you want link time optimizations (LTO).
 ifeq ($(USE_LTO),)
   USE_LTO = yes
 endif
 
-# If enabled, this option allows to compile the application in THUMB mode.
-ifeq ($(USE_THUMB),)
-  USE_THUMB = yes
-endif
-
 # Enable this if you want to see the full log while compiling.
 ifeq ($(USE_VERBOSE_COMPILE),)
   USE_VERBOSE_COMPILE = no
@@ -94,7 +89,7 @@ ifeq ($(USE_EXCEPTIONS_STACKSIZE),)
   USE_EXCEPTIONS_STACKSIZE = 0x400
 endif
 
-# Enables the use of FPU on Cortex-M4.
+# Enables the use of FPU.
 # Possible selections are:
 #   no     - no FPU is used (probably equals 'soft')
 #   soft   - does not use the FPU, thus all floating point operations are emulated
@@ -104,32 +99,47 @@ ifeq ($(USE_FPU),)
   USE_FPU = softfp
 endif
 
+# FPU-related options.
+ifeq ($(USE_FPU_OPT),)
+  USE_FPU_OPT = -mfloat-abi=$(USE_FPU) -mfpu=fpv4-sp-d16
+endif
+
 #                                                                              #
 # Architecture or project specific options                                     #
 ################################################################################
 
 ################################################################################
-# Project, sources and paths                                                   #
+# Project, target, sources and paths                                           #
 #                                                                              #
 
 # Define project name here
 PROJECT := $(patsubst $(abspath $(dir $(abspath $(lastword $(MAKEFILE_LIST))))..)/%,%,$(abspath $(dir $(abspath $(lastword $(MAKEFILE_LIST))))))
 
-# Imported source files and paths
+# Target settings.
+MCU = cortex-m4
+
+# Imported source files and paths.
 include ../../kernel/kernel.mk
-CHIBIOS := $(AMIROOS_KERNEL)
-AMIROOS = ../..
-# Licensing files
+CHIBIOS    := $(AMIROOS_KERNEL)
+CONFDIR    := .
+ifeq ($(BUILDDIR),)
+  BUILDDIR := ./build
+endif
+DEPDIR     := $(dir $(BUILDDIR)).dep
+AMIROOS    := ../..
+# Licensing files.
 include $(CHIBIOS)/os/license/license.mk
-# Startup files
+# Startup files.
 include $(CHIBIOS)/os/common/startup/ARMCMx/compilers/GCC/mk/startup_stm32f4xx.mk
-# HAL-OSAL files
+# HAL-OSAL files (optional).
 include $(CHIBIOS)/os/hal/hal.mk
 include $(CHIBIOS)/os/hal/ports/STM32/STM32F4xx/platform.mk
 include $(CHIBIOS)/os/hal/osal/rt/osal.mk
-# RTOS files
+# RTOS files (optional).
 include $(CHIBIOS)/os/rt/rt.mk
 include $(CHIBIOS)/os/common/ports/ARMCMx/compilers/GCC/mk/port_v7m.mk
+# Auto-build files in ./source recursively.
+include $(CHIBIOS)/tools/mk/autobuild.mk
 # Other files (optional).
 include $(CHIBIOS)/test/lib/test.mk
 include $(CHIBIOS)/test/rt/rt_test.mk
@@ -148,126 +158,55 @@ LDSCRIPT= STM32F407xG.ld
 
 # C sources that can be compiled in ARM or THUMB mode depending on the global
 # setting.
-CSRC = $(LICSRC) \
-       $(STARTUPSRC) \
-       $(KERNSRC) \
-       $(PORTSRC) \
-       $(OSALSRC) \
-       $(HALSRC) \
-       $(PLATFORMSRC) \
-       $(MODULESCSRC) \
+CSRC = $(ALLCSRC) \
        $(TESTSRC) \
-       $(PERIPHERYLLDCSRC) \
-       $(AMIROOSCORECSRC) \
-       $(UNITTESTSCSRC) \
        $(CHIBIOS)/os/various/evtimer.c \
        $(CHIBIOS)/os/various/syscalls.c \
        $(CHIBIOS)/os/hal/lib/streams/chprintf.c \
        board.c \
+       $(PERIPHERYLLDCSRC) \
+       $(UNITTESTSCSRC) \
+       $(AMIROOSCORECSRC) \
+       $(MODULESCSRC) \
        module.c \
        $(APPSCSRC)
 
 # C++ sources that can be compiled in ARM or THUMB mode depending on the global
 # setting.
-CPPSRC = $(AMIROOSCORECPPSRC) \
+CPPSRC = $(ALLCPPSRC) \
          $(CHIBIOS)/os/various/cpp_wrappers/syscalls_cpp.cpp \
+         $(AMIROOSCORECPPSRC) \
          $(APPSCPPSRC)
 
-# C sources to be compiled in ARM mode regardless of the global setting.
-# NOTE: Mixing ARM and THUMB mode enables the -mthumb-interwork compiler
-#       option that results in lower performance and larger code size.
-ACSRC = $(APPSACSRC)
-
-# C++ sources to be compiled in ARM mode regardless of the global setting.
-# NOTE: Mixing ARM and THUMB mode enables the -mthumb-interwork compiler
-#       option that results in lower performance and larger code size.
-ACPPSRC = $(APPSACPPSRC)
-
-# C sources to be compiled in THUMB mode regardless of the global setting.
-# NOTE: Mixing ARM and THUMB mode enables the -mthumb-interwork compiler
-#       option that results in lower performance and larger code size.
-TCSRC = $(APPSTCSRC)
-
-# C sources to be compiled in THUMB mode regardless of the global setting.
-# NOTE: Mixing ARM and THUMB mode enables the -mthumb-interwork compiler
-#       option that results in lower performance and larger code size.
-TCPPSRC = $(APPSTCPPSRC)
-
-# List ASM source files here
-ASMSRC = $(APPSASMSRC)
-ASMXSRC = $(STARTUPASM) \
-          $(PORTASM) \
-          $(OSALASM) \
+# List ASM source files here.
+ASMSRC = $(ALLASMSRC) \
+         $(APPSASMSRC)
+
+# List ASM with preprocessor source files here.
+ASMXSRC = $(ALLXASMSRC) \
           $(APPSASMXSRC)
 
-INCDIR = $(LICINC) \
-         $(STARTUPINC) \
-         $(KERNINC) \
-         $(PORTINC) \
-         $(OSALINC) \
-         $(HALINC) \
-         $(PLATFORMINC) \
-         $(MODULESINC) \
+# Inclusion directories.
+INCDIR = $(CONFDIR) \
+         $(ALLINC) \
          $(TESTINC) \
-         $(BOOTLOADERINC) \
          $(CHIBIOS)/os/hal/lib/streams \
+         $(BOOTLOADERINC) \
          $(PERIPHERYLLDINC) \
          $(AMIROOS) \
-         $(AMIROOSCOREINC) \
          $(UNITTESTSINC) \
+         $(AMIROOSCOREINC) \
+         $(MODULESINC) \
          $(APPSINC)
 
-#                                                                              #
-# Project, sources and paths                                                   #
-################################################################################
-
-################################################################################
-# Compiler settings                                                            #
-# NOTE: Some can be overridden externally.                                     #
-#                                                                              #
-
-MCU  = cortex-m4
-
-#TRGT = arm-elf-
-TRGT = arm-none-eabi-
-CC   = $(TRGT)gcc
-CPPC = $(TRGT)g++
-# Enable loading with g++ only if you need C++ runtime support.
-# NOTE: You can use C++ even without C++ support if you are careful. C++
-#       runtime support makes code size explode.
-LD   = $(TRGT)gcc
-#LD   = $(TRGT)g++
-CP   = $(TRGT)objcopy
-AS   = $(TRGT)gcc -x assembler-with-cpp
-AR   = $(TRGT)ar
-OD   = $(TRGT)objdump
-SZ   = $(TRGT)size
-HEX  = $(CP) -O ihex
-BIN  = $(CP) -O binary
-SREC = $(CP) -O srec --srec-len=248
-
-# ARM-specific options here
-ifeq ($(AOPT),)
-  AOPT =
-endif
-
-# THUMB-specific options here
-ifeq ($(TOPT),)
-  TOPT = -mthumb -DTHUMB
-endif
-
-# Define C warning options here
-ifeq ($(CWARN),)
-  CWARN = -Wall -Wextra -Wundef -Wstrict-prototypes
-endif
+# Define C warning options here.
+CWARN = -Wall -Wextra -Wundef -Wstrict-prototypes
 
-# Define C++ warning options here
-ifeq ($(CPPWARN),)
-  CPPWARN = -Wall -Wextra -Wundef
-endif
+# Define C++ warning options here.
+CPPWARN = -Wall -Wextra -Wundef
 
 #                                                                              #
-# Compiler settings                                                            #
+# Project, target, sources and paths                                           #
 ################################################################################
 
 ################################################################################
@@ -290,27 +229,29 @@ ULIBDIR +=
 ULIBS +=
 
 #                                                                              #
-# End of user defines                                                          #
+# End of user section                                                          #
 ################################################################################
 
 ################################################################################
-# Start of targets section                                                     #
+# Common rules                                                                 #
 #                                                                              #
 
-# all and its dependencies
-ifeq ($(BUILDDIR),)
-	BUILDDIR = ./build
-endif
-RULESPATH = $(CHIBIOS)/os/common/startup/ARMCMx/compilers/GCC
+RULESPATH = $(CHIBIOS)/os/common/startup/ARMCMx/compilers/GCC/mk
+include $(RULESPATH)/arm-none-eabi.mk
 include $(RULESPATH)/rules.mk
 
-# flash
-include $(AMIROOS)/bootloader/bootloader.mk
+#                                                                              #
+# Common rules                                                                 #
+################################################################################
+
+################################################################################
+# Custom rules                                                                 #
+#                                                                              #
 
 flash: $(BUILDDIR)/$(PROJECT).elf
 	openocd -f interface/stlink-v2-1.cfg -c "set WORKAREASIZE 0x2000" -f target/stm32f4x.cfg -c "program build/$(PROJECT).elf verify reset exit"
 
 #                                                                              #
-# End of targets section                                                       #
+# Custom rules                                                                 #
 ################################################################################
 
diff --git a/modules/STM32F407G-DISC1/chconf.h b/modules/STM32F407G-DISC1/chconf.h
index 37bce4a..1dfce21 100644
--- a/modules/STM32F407G-DISC1/chconf.h
+++ b/modules/STM32F407G-DISC1/chconf.h
@@ -123,6 +123,11 @@
  */
 /*===========================================================================*/
 
+/**
+ * @brief   Flag to enable/disable sleep mode when the system is idle.
+ */
+#define CORTEX_ENABLE_WFI_IDLE                  TRUE
+
 /** @} */
 
 /*===========================================================================*/
@@ -132,11 +137,6 @@
  */
 /*===========================================================================*/
 
-/**
- * @brief   Flag to enable/disable sleep mode when the system is idle.
- */
-#define CORTEX_ENABLE_WFI_IDLE                  TRUE
-
 // common definitions in aos_chconf.h
 
 /** @} */
diff --git a/modules/STM32F407G-DISC1/halconf.h b/modules/STM32F407G-DISC1/halconf.h
index 9683b0e..c87a173 100644
--- a/modules/STM32F407G-DISC1/halconf.h
+++ b/modules/STM32F407G-DISC1/halconf.h
@@ -31,7 +31,7 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define HALCONF_H
 
 #define _CHIBIOS_HAL_CONF_
-#define _CHIBIOS_HAL_CONF_VER_6_0_
+#define _CHIBIOS_HAL_CONF_VER_7_0_
 
 #include "mcuconf.h"
 
@@ -71,13 +71,6 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #endif
 
 /**
- * @brief   Enables the EXT subsystem.
- */
-#if !defined(HAL_USE_EXT) || defined(__DOXYGEN__)
-#define HAL_USE_EXT                         FALSE
-#endif
-
-/**
  * @brief   Enables the GPT subsystem.
  */
 #if !defined(HAL_USE_GPT) || defined(__DOXYGEN__)
@@ -134,13 +127,6 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #endif
 
 /**
- * @brief   Enables the QSPI subsystem.
- */
-#if !defined(HAL_USE_QSPI) || defined(__DOXYGEN__)
-#define HAL_USE_QSPI                        FALSE
-#endif
-
-/**
  * @brief   Enables the RTC subsystem.
  */
 #if !defined(HAL_USE_RTC) || defined(__DOXYGEN__)
@@ -169,6 +155,13 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #endif
 
 /**
+ * @brief   Enables the SIO subsystem.
+ */
+#if !defined(HAL_USE_SIO) || defined(__DOXYGEN__)
+#define HAL_USE_SIO                         FALSE
+#endif
+
+/**
  * @brief   Enables the SPI subsystem.
  */
 #if !defined(HAL_USE_SPI) || defined(__DOXYGEN__)
@@ -176,6 +169,13 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #endif
 
 /**
+ * @brief   Enables the TRNG subsystem.
+ */
+#if !defined(HAL_USE_TRNG) || defined(__DOXYGEN__)
+#define HAL_USE_TRNG                        FALSE
+#endif
+
+/**
  * @brief   Enables the UART subsystem.
  */
 #if !defined(HAL_USE_UART) || defined(__DOXYGEN__)
@@ -196,6 +196,13 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define HAL_USE_WDG                         FALSE
 #endif
 
+/**
+ * @brief   Enables the WSPI subsystem.
+ */
+#if !defined(HAL_USE_WSPI) || defined(__DOXYGEN__)
+#define HAL_USE_WSPI                        FALSE
+#endif
+
 /*===========================================================================*/
 /* PAL driver related settings.                                              */
 /*===========================================================================*/
@@ -342,26 +349,6 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #endif
 
 /*===========================================================================*/
-/* QSPI driver related settings.                                             */
-/*===========================================================================*/
-
-/**
- * @brief   Enables synchronous APIs.
- * @note    Disabling this option saves both code and data space.
- */
-#if !defined(QSPI_USE_WAIT) || defined(__DOXYGEN__)
-#define QSPI_USE_WAIT                       TRUE
-#endif
-
-/**
- * @brief   Enables the @p qspiAcquireBus() and @p qspiReleaseBus() APIs.
- * @note    Disabling this option saves both code and data space.
- */
-#if !defined(QSPI_USE_MUTUAL_EXCLUSION) || defined(__DOXYGEN__)
-#define QSPI_USE_MUTUAL_EXCLUSION           TRUE
-#endif
-
-/*===========================================================================*/
 /* SDC driver related settings.                                              */
 /*===========================================================================*/
 
@@ -522,6 +509,26 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define USB_USE_WAIT                        FALSE
 #endif
 
+/*===========================================================================*/
+/* WSPI driver related settings.                                             */
+/*===========================================================================*/
+
+/**
+ * @brief   Enables synchronous APIs.
+ * @note    Disabling this option saves both code and data space.
+ */
+#if !defined(WSPI_USE_WAIT) || defined(__DOXYGEN__)
+#define WSPI_USE_WAIT                       TRUE
+#endif
+
+/**
+ * @brief   Enables the @p wspiAcquireBus() and @p wspiReleaseBus() APIs.
+ * @note    Disabling this option saves both code and data space.
+ */
+#if !defined(WSPI_USE_MUTUAL_EXCLUSION) || defined(__DOXYGEN__)
+#define WSPI_USE_MUTUAL_EXCLUSION           TRUE
+#endif
+
 #endif /* HALCONF_H */
 
 /** @} */
diff --git a/modules/STM32F407G-DISC1/mcuconf.h b/modules/STM32F407G-DISC1/mcuconf.h
index 578792f..0d03cf3 100644
--- a/modules/STM32F407G-DISC1/mcuconf.h
+++ b/modules/STM32F407G-DISC1/mcuconf.h
@@ -341,14 +341,4 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  */
 #define STM32_WDG_USE_IWDG                  FALSE
 
-/*
- * QEI driver system settings.
- */
-#define STM32_QEI_USE_TIM1                  FALSE
-#define STM32_QEI_USE_TIM2                  FALSE
-#define STM32_QEI_USE_TIM3                  FALSE
-#define STM32_QEI_USE_TIM4                  FALSE
-#define STM32_QEI_USE_TIM5                  FALSE
-#define STM32_QEI_USE_TIM8                  FALSE
-
 #endif /* MCUCONF_H */
diff --git a/modules/aos_chconf.h b/modules/aos_chconf.h
index 166c681..055f2d4 100644
--- a/modules/aos_chconf.h
+++ b/modules/aos_chconf.h
@@ -30,7 +30,7 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define AOS_CHCONF_H
 
 #define _CHIBIOS_RT_CONF_
-#define _CHIBIOS_RT_CONF_VER_5_1_
+#define _CHIBIOS_RT_CONF_VER_6_0_
 
 /*===========================================================================*/
 /**
@@ -97,7 +97,9 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  * @note    The round robin preemption is not supported in tickless mode and
  *          must be set to zero in that case.
  */
+#if !defined(CH_CFG_TIME_QUANTUM)
 #define CH_CFG_TIME_QUANTUM                 0
+#endif
 
 /**
  * @brief   Managed RAM size.
@@ -110,7 +112,9 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  *          provide the @p __heap_base__ and @p __heap_end__ symbols.
  * @note    Requires @p CH_CFG_USE_MEMCORE.
  */
+#if !defined(CH_CFG_MEMCORE_SIZE)
 #define CH_CFG_MEMCORE_SIZE                 0
+#endif
 
 /**
  * @brief   Idle thread automatic spawn suppression.
@@ -119,7 +123,9 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  *          function becomes the idle thread and must implement an
  *          infinite loop.
  */
+#if !defined(CH_CFG_NO_IDLE_THREAD)
 #define CH_CFG_NO_IDLE_THREAD               FALSE
+#endif
 
 /** @} */
 
@@ -138,7 +144,9 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  * @note    This is not related to the compiler optimization options.
  * @note    The default is @p TRUE.
  */
+#if !defined(CH_CFG_OPTIMIZE_SPEED)
 #define CH_CFG_OPTIMIZE_SPEED               TRUE
+#endif
 
 /** @} */
 
@@ -156,7 +164,9 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  *
  * @note    The default is @p TRUE.
  */
+#if !defined(CH_CFG_USE_TM)
 #define CH_CFG_USE_TM                       TRUE
+#endif
 
 /**
  * @brief   Threads registry APIs.
@@ -164,7 +174,9 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  *
  * @note    The default is @p TRUE.
  */
+#if !defined(CH_CFG_USE_REGISTRY)
 #define CH_CFG_USE_REGISTRY                 FALSE
+#endif
 
 /**
  * @brief   Thread hierarchy APIs.
@@ -172,14 +184,18 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  *
  * @note    The default is @p FALSE.
  */
+#if !defined(CH_CFG_USE_THREADHIERARCHY)
 #define CH_CFG_USE_THREADHIERARCHY          TRUE
+#endif
 
 /**
  * @brief   Enable ordering of child lists.
  * @details Children will be ordered by their priority (descending).
  *          If sibliblings have identical priority, they are ordered by age (descending).
  */
+#if !defined(CH_CFG_THREADHIERARCHY_ORDERED)
 #define CH_CFG_THREADHIERARCHY_ORDERED      TRUE
+#endif
 
 /**
  * @brief   Threads synchronization APIs.
@@ -188,7 +204,9 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  *
  * @note    The default is @p TRUE.
  */
+#if !defined(CH_CFG_USE_WAITEXIT)
 #define CH_CFG_USE_WAITEXIT                 TRUE
+#endif
 
 /**
  * @brief   Semaphores APIs.
@@ -196,7 +214,9 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  *
  * @note    The default is @p TRUE.
  */
+#if !defined(CH_CFG_USE_SEMAPHORES)
 #define CH_CFG_USE_SEMAPHORES               TRUE
+#endif
 
 /**
  * @brief   Semaphores queuing mode.
@@ -207,7 +227,9 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  *          requirements.
  * @note    Requires @p CH_CFG_USE_SEMAPHORES.
  */
+#if !defined(CH_CFG_USE_SEMAPHORES_PRIORITY)
 #define CH_CFG_USE_SEMAPHORES_PRIORITY      FALSE
+#endif
 
 /**
  * @brief   Mutexes APIs.
@@ -215,7 +237,9 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  *
  * @note    The default is @p TRUE.
  */
+#if !defined(CH_CFG_USE_MUTEXES)
 #define CH_CFG_USE_MUTEXES                  TRUE
+#endif
 
 /**
  * @brief   Enables recursive behavior on mutexes.
@@ -225,7 +249,9 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  * @note    The default is @p FALSE.
  * @note    Requires @p CH_CFG_USE_MUTEXES.
  */
+#if !defined(CH_CFG_USE_MUTEXES_RECURSIVE)
 #define CH_CFG_USE_MUTEXES_RECURSIVE        FALSE
+#endif
 
 /**
  * @brief   Conditional Variables APIs.
@@ -235,7 +261,9 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  * @note    The default is @p TRUE.
  * @note    Requires @p CH_CFG_USE_MUTEXES.
  */
+#if !defined(CH_CFG_USE_CONDVARS)
 #define CH_CFG_USE_CONDVARS                 TRUE
+#endif
 
 /**
  * @brief   Conditional Variables APIs with timeout.
@@ -245,7 +273,9 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  * @note    The default is @p TRUE.
  * @note    Requires @p CH_CFG_USE_CONDVARS.
  */
+#if !defined(CH_CFG_USE_CONDVARS_TIMEOUT)
 #define CH_CFG_USE_CONDVARS_TIMEOUT         TRUE
+#endif
 
 /**
  * @brief   Events Flags APIs.
@@ -253,7 +283,9 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  *
  * @note    The default is @p TRUE.
  */
+#if !defined(CH_CFG_USE_EVENTS)
 #define CH_CFG_USE_EVENTS                   TRUE
+#endif
 
 /**
  * @brief   Events Flags APIs with timeout.
@@ -263,7 +295,9 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  * @note    The default is @p TRUE.
  * @note    Requires @p CH_CFG_USE_EVENTS.
  */
+#if !defined(CH_CFG_USE_EVENTS_TIMEOUT)
 #define CH_CFG_USE_EVENTS_TIMEOUT           TRUE
+#endif
 
 /**
  * @brief   Synchronous Messages APIs.
@@ -272,7 +306,9 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  *
  * @note    The default is @p TRUE.
  */
+#if !defined(CH_CFG_USE_MESSAGES)
 #define CH_CFG_USE_MESSAGES                 FALSE
+#endif
 
 /**
  * @brief   Synchronous Messages queuing mode.
@@ -283,7 +319,9 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  *          requirements.
  * @note    Requires @p CH_CFG_USE_MESSAGES.
  */
+#if !defined(CH_CFG_USE_MESSAGES_PRIORITY)
 #define CH_CFG_USE_MESSAGES_PRIORITY        FALSE
+#endif
 
 /**
  * @brief   Mailboxes APIs.
@@ -293,7 +331,9 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  * @note    The default is @p TRUE.
  * @note    Requires @p CH_CFG_USE_SEMAPHORES.
  */
+#if !defined(CH_CFG_USE_MAILBOXES)
 #define CH_CFG_USE_MAILBOXES                FALSE
+#endif
 
 /**
  * @brief   Core Memory Manager APIs.
@@ -302,7 +342,9 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  *
  * @note    The default is @p TRUE.
  */
+#if !defined(CH_CFG_USE_MEMCORE)
 #define CH_CFG_USE_MEMCORE                  FALSE
+#endif
 
 /**
  * @brief   Heap Allocator APIs.
@@ -314,7 +356,9 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  *          @p CH_CFG_USE_SEMAPHORES.
  * @note    Mutexes are recommended.
  */
+#if !defined(CH_CFG_USE_HEAP)
 #define CH_CFG_USE_HEAP                     FALSE
+#endif
 
 /**
  * @brief   Memory Pools Allocator APIs.
@@ -323,16 +367,31 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  *
  * @note    The default is @p TRUE.
  */
+#if !defined(CH_CFG_USE_MEMPOOLS)
 #define CH_CFG_USE_MEMPOOLS                 FALSE
+#endif
 
 /**
- * @brief  Objects FIFOs APIs.
+ * @brief   Objects FIFOs APIs.
  * @details If enabled then the objects FIFOs APIs are included
  *          in the kernel.
  *
  * @note    The default is @p TRUE.
  */
+#if !defined(CH_CFG_USE_OBJ_FIFOS)
 #define CH_CFG_USE_OBJ_FIFOS                FALSE
+#endif
+
+/**
+ * @brief   Pipes APIs.
+ * @details If enabled then the pipes APIs are included
+ *          in the kernel.
+ *
+ * @note    The default is @p TRUE.
+ */
+#if !defined(CH_CFG_USE_PIPES)
+#define CH_CFG_USE_PIPES                    FALSE
+#endif
 
 /**
  * @brief   Dynamic Threads APIs.
@@ -343,7 +402,9 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  * @note    Requires @p CH_CFG_USE_WAITEXIT.
  * @note    Requires @p CH_CFG_USE_HEAP and/or @p CH_CFG_USE_MEMPOOLS.
  */
+#if !defined(CH_CFG_USE_DYNAMIC)
 #define CH_CFG_USE_DYNAMIC                  FALSE
+#endif
 
 /** @} */
 
@@ -409,6 +470,13 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #define CH_CFG_FACTORY_OBJ_FIFOS            TRUE
 #endif
 
+/**
+ * @brief   Enables factory for Pipes.
+ */
+#if !defined(CH_CFG_FACTORY_PIPES) || defined(__DOXYGEN__)
+#define CH_CFG_FACTORY_PIPES                TRUE
+#endif
+
 /** @} */
 
 /*===========================================================================*/
@@ -423,11 +491,13 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  *
  * @note    The default is @p FALSE.
  */
+#if !defined(CH_DBG_STATISTICS)
 #if ((CH_CFG_USE_TM == TRUE) && (AMIROOS_CFG_DBG == true)) || defined(__DOXYGEN__)
   #define CH_DBG_STATISTICS                 TRUE
 #else
   #define CH_DBG_STATISTICS                 FALSE
 #endif
+#endif
 
 /**
  * @brief   Debug option, system state check.
@@ -436,11 +506,13 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  *
  * @note    The default is @p FALSE.
  */
+#if !defined(CH_DBG_SYSTEM_STATE_CHECK)
 #if (AMIROOS_CFG_DBG == true) || defined(__DOXYGEN__)
   #define CH_DBG_SYSTEM_STATE_CHECK         TRUE
 #else
   #define CH_DBG_SYSTEM_STATE_CHECK         FALSE
 #endif
+#endif
 
 /**
  * @brief   Debug option, parameters checks.
@@ -449,11 +521,13 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  *
  * @note    The default is @p FALSE.
  */
+#if !defined(CH_DBG_ENABLE_CHECKS)
 #if (AMIROOS_CFG_DBG == true) || defined(__DOXYGEN__)
   #define CH_DBG_ENABLE_CHECKS              TRUE
 #else
   #define CH_DBG_ENABLE_CHECKS              FALSE
 #endif
+#endif
 
 /**
  * @brief   Debug option, consistency checks.
@@ -463,11 +537,13 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  *
  * @note    The default is @p FALSE.
  */
+#if !defined(CH_DBG_ENABLE_ASSERTS)
 #if (AMIROOS_CFG_DBG == true) || defined(__DOXYGEN__)
   #define CH_DBG_ENABLE_ASSERTS             TRUE
 #else
   #define CH_DBG_ENABLE_ASSERTS             FALSE
 #endif
+#endif
 
 /**
  * @brief   Debug option, trace buffer.
@@ -475,14 +551,18 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  *
  * @note    The default is @p CH_DBG_TRACE_MASK_DISABLED.
  */
+#if !defined(CH_DBG_TRACE_MASK)
 #define CH_DBG_TRACE_MASK                   CH_DBG_TRACE_MASK_DISABLED
+#endif
 
 /**
  * @brief   Trace buffer entries.
  * @note    The trace buffer is only allocated if @p CH_DBG_TRACE_MASK is
  *          different from @p CH_DBG_TRACE_MASK_DISABLED.
  */
+#if !defined(CH_DBG_TRACE_BUFFER_SIZE)
 #define CH_DBG_TRACE_BUFFER_SIZE            128
+#endif
 
 /**
  * @brief   Debug option, stack checks.
@@ -494,11 +574,13 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  * @note    The default failure mode is to halt the system with the global
  *          @p panic_msg variable set to @p NULL.
  */
+#if !defined(CH_DBG_ENABLE_STACK_CHECK)
 #if (AMIROOS_CFG_DBG == true) || defined(__DOXYGEN__)
   #define CH_DBG_ENABLE_STACK_CHECK         TRUE
 #else
   #define CH_DBG_ENABLE_STACK_CHECK         FALSE
 #endif
+#endif
 
 /**
  * @brief   Debug option, stacks initialization.
@@ -508,11 +590,13 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  *
  * @note    The default is @p FALSE.
  */
+#if !defined(CH_DBG_FILL_THREADS)
 #if (AMIROOS_CFG_PROFILE == true) || defined(__DOXYGEN__)
   #define CH_DBG_FILL_THREADS               TRUE
 #else
   #define CH_DBG_FILL_THREADS               FALSE
 #endif
+#endif
 
 /**
  * @brief   Debug option, threads profiling.
@@ -523,11 +607,13 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
  * @note    This debug option is not currently compatible with the
  *          tickless mode.
  */
+#if !defined(CH_DBG_THREADS_PROFILING)
 #if ((CH_CFG_ST_TIMEDELTA == 0) && (AMIROOS_CFG_PROFILE == true)) || defined(__DOXYGEN__)
   #define CH_DBG_THREADS_PROFILING          TRUE
 #else
   #define CH_DBG_THREADS_PROFILING          FALSE
 #endif
+#endif
 
 /** @} */
 
@@ -661,12 +747,15 @@ along with this program.  If not, see <http://www.gnu.org/licenses/>.
 
 /*===========================================================================*/
 /**
- * @name Port specific settings
+ * @name Port-specific settings (override port settings defaulted in chcore.h).
+ * @{
  */
 /*===========================================================================*/
 
 // These settings are specific to each module.
 
+/** @} */
+
 /*===========================================================================*/
 /**
  * @name other
