You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@nuttx.apache.org by xi...@apache.org on 2022/09/09 07:30:41 UTC
[incubator-nuttx] branch master updated: Fix some register's values, enable TWAI extended registers and add a missing prototype. Also, replaced critical_sections with spinlocks.
This is an automated email from the ASF dual-hosted git repository.
xiaoxiang pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/incubator-nuttx.git
The following commit(s) were added to refs/heads/master by this push:
new 2892f18f15 Fix some register's values, enable TWAI extended registers and add a missing prototype. Also, replaced critical_sections with spinlocks.
2892f18f15 is described below
commit 2892f18f15a6581066d9564e77f98885ddaed1e8
Author: Victor Benso <vb...@gmail.com>
AuthorDate: Fri Sep 2 18:48:28 2022 -0300
Fix some register's values, enable TWAI extended registers and add a missing prototype.
Also, replaced critical_sections with spinlocks.
---
arch/xtensa/src/esp32/esp32_twai.c | 71 ++++++++++++----------
arch/xtensa/src/esp32/hardware/esp32_twai.h | 22 +++++--
.../xtensa/esp32/esp32-devkitc/src/esp32-devkitc.h | 11 ++++
3 files changed, 65 insertions(+), 39 deletions(-)
diff --git a/arch/xtensa/src/esp32/esp32_twai.c b/arch/xtensa/src/esp32/esp32_twai.c
index ac6c5905db..59ba6f161e 100644
--- a/arch/xtensa/src/esp32/esp32_twai.c
+++ b/arch/xtensa/src/esp32/esp32_twai.c
@@ -37,6 +37,7 @@
#include <nuttx/irq.h>
#include <nuttx/arch.h>
#include <nuttx/can/can.h>
+#include <nuttx/spinlock.h>
#include "xtensa.h"
@@ -124,15 +125,16 @@ struct twai_dev_s
/* Device configuration */
const struct can_bittiming_const *bittiming_const;
- uint8_t port; /* TWAI port number */
- uint8_t periph; /* Peripheral ID */
- uint8_t irq; /* IRQ associated with this TWAI */
- uint8_t cpu; /* CPU ID */
- uint8_t cpuint; /* CPU interrupt assigned to this TWAI */
- uint32_t bitrate; /* Configured bit rate */
- uint32_t samplep; /* Configured sample point */
- uint32_t sjw; /* Synchronization jump width */
- uint32_t base; /* TWAI register base address */
+ uint8_t port; /* TWAI port number */
+ uint8_t periph; /* Peripheral ID */
+ uint8_t irq; /* IRQ associated with this TWAI */
+ uint8_t cpu; /* CPU ID */
+ uint8_t cpuint; /* CPU interrupt assigned to this TWAI */
+ uint32_t bitrate; /* Configured bit rate */
+ uint32_t samplep; /* Configured sample point */
+ uint32_t sjw; /* Synchronization jump width */
+ uint32_t base; /* TWAI register base address */
+ spinlock_t lock; /* Device specific lock */
};
/****************************************************************************
@@ -221,6 +223,7 @@ static struct twai_dev_s g_twai0priv =
.samplep = CONFIG_ESP32_TWAI0_SAMPLEP,
.sjw = CONFIG_ESP32_TWAI0_SJW,
.base = DR_REG_TWAI_BASE,
+ .lock = SP_UNLOCKED,
};
static struct can_dev_s g_twai0dev =
@@ -386,13 +389,15 @@ static void esp32twai_reset(struct can_dev_s *dev)
caninfo("TWAI%" PRIu8 "\n", priv->port);
- flags = enter_critical_section();
+ flags = spin_lock_irqsave(&priv->lock);
/* Disable the TWAI and stop ongoing transmissions */
uint32_t mode_value = TWAI_RESET_MODE_M | TWAI_LISTEN_ONLY_MODE_M;
twai_putreg(TWAI_MODE_REG, mode_value); /* Enter Reset Mode */
+ modifyreg32(TWAI_CLOCK_DIVIDER_REG, 0, TWAI_EXT_MODE_M);
+
twai_putreg(TWAI_INT_ENA_REG, 0); /* Disable interrupts */
twai_getreg(TWAI_STATUS_REG); /* Clear status bits */
@@ -427,8 +432,7 @@ static void esp32twai_reset(struct can_dev_s *dev)
twai_putreg(TWAI_CMD_REG, TWAI_ABORT_TX_M | TWAI_RELEASE_BUF_M |
TWAI_CLR_OVERRUN_M);
-
- leave_critical_section(flags);
+ spin_unlock_irqrestore(&priv->lock, flags);
}
/****************************************************************************
@@ -455,7 +459,7 @@ static int esp32twai_setup(struct can_dev_s *dev)
caninfo("TWAI%" PRIu8 "\n", priv->port);
- flags = enter_critical_section();
+ flags = spin_lock_irqsave(&priv->lock);
twai_putreg(TWAI_INT_ENA_REG, TWAI_DEFAULT_INTERRUPTS);
@@ -465,7 +469,7 @@ static int esp32twai_setup(struct can_dev_s *dev)
{
/* Disable the provided CPU Interrupt to configure it. */
- up_disable_irq(priv->cpuint);
+ up_disable_irq(priv->irq);
}
priv->cpu = up_cpu_index();
@@ -476,7 +480,7 @@ static int esp32twai_setup(struct can_dev_s *dev)
/* Failed to allocate a CPU interrupt of this type. */
ret = priv->cpuint;
- leave_critical_section(flags);
+ spin_unlock_irqrestore(&priv->lock, flags);
return ret;
}
@@ -488,16 +492,16 @@ static int esp32twai_setup(struct can_dev_s *dev)
esp32_teardown_irq(priv->cpu, priv->periph, priv->cpuint);
priv->cpuint = -ENOMEM;
- leave_critical_section(flags);
+ spin_unlock_irqrestore(&priv->lock, flags);
return ret;
}
/* Enable the CPU interrupt that is linked to the TWAI device. */
- up_enable_irq(priv->cpuint);
+ up_enable_irq(priv->irq);
- leave_critical_section(flags);
+ spin_unlock_irqrestore(&priv->lock, flags);
return ret;
}
@@ -529,7 +533,7 @@ static void esp32twai_shutdown(struct can_dev_s *dev)
{
/* Disable cpu interrupt */
- up_disable_irq(priv->cpuint);
+ up_disable_irq(priv->irq);
/* Dissociate the IRQ from the ISR */
@@ -571,7 +575,8 @@ static void esp32twai_rxint(struct can_dev_s *dev, bool enable)
* so we have to protect this code section.
*/
- flags = enter_critical_section();
+ flags = spin_lock_irqsave(&priv->lock);
+
regval = twai_getreg(TWAI_INT_ENA_REG);
if (enable)
{
@@ -583,7 +588,8 @@ static void esp32twai_rxint(struct can_dev_s *dev, bool enable)
}
twai_putreg(TWAI_INT_ENA_REG, regval);
- leave_critical_section(flags);
+ spin_unlock_irqrestore(&priv->lock, flags);
+
return;
}
@@ -621,14 +627,14 @@ static void esp32twai_txint(struct can_dev_s *dev, bool enable)
* have to protect this code section.
*/
- flags = enter_critical_section();
+ flags = spin_lock_irqsave(&priv->lock);
/* Disable all TX interrupts */
regval = twai_getreg(TWAI_INT_ENA_REG);
regval &= ~(TWAI_TX_INT_ENA_M);
twai_putreg(TWAI_INT_ENA_REG, regval);
- leave_critical_section(flags);
+ spin_unlock_irqrestore(&priv->lock, flags);
}
}
@@ -764,7 +770,7 @@ static int esp32twai_send(struct can_dev_s *dev,
frame_info |= (1 << 6);
}
- flags = enter_critical_section();
+ flags = spin_lock_irqsave(&priv->lock);
/* Make sure that TX interrupts are enabled BEFORE sending the
* message.
@@ -826,8 +832,7 @@ static int esp32twai_send(struct can_dev_s *dev,
#else
twai_putreg(TWAI_CMD_REG, TWAI_TX_REQ_M);
#endif
-
- leave_critical_section(flags);
+ spin_unlock_irqrestore(&priv->lock, flags);
return ret;
}
@@ -1170,7 +1175,7 @@ static int twai_baud_rate(struct twai_dev_s *priv, int rate, int clock,
/* Configure bit timing */
- timing0 = (best_brp - 1) / 2;
+ timing0 = (best_brp / 2) - 1;
timing0 |= (sjw - 1) << TWAI_SYNC_JUMP_WIDTH_S;
timing1 = tseg1 - 1;
@@ -1215,11 +1220,13 @@ struct can_dev_s *esp32_twaiinitialize(int port)
caninfo("TWAI%" PRIu8 "\n", port);
- flags = enter_critical_section();
-
#ifdef CONFIG_ESP32_TWAI0
if (port == 0)
{
+ twaidev = &g_twai0dev;
+
+ flags = spin_lock_irqsave(&g_twai0priv.lock);
+
/* Enable power to the TWAI module and
* Enable clocking to the TWAI module
*/
@@ -1235,14 +1242,14 @@ struct can_dev_s *esp32_twaiinitialize(int port)
esp32_configgpio(CONFIG_ESP32_TWAI0_RXPIN, INPUT_FUNCTION_1);
esp32_gpio_matrix_in(CONFIG_ESP32_TWAI0_RXPIN, TWAI_RX_IDX, 0);
- twaidev = &g_twai0dev;
+ spin_unlock_irqrestore(&g_twai0priv.lock, flags);
}
else
#endif
{
canerr("ERROR: Unsupported port: %d\n", port);
- leave_critical_section(flags);
+
return NULL;
}
@@ -1250,8 +1257,6 @@ struct can_dev_s *esp32_twaiinitialize(int port)
esp32twai_reset(twaidev);
- leave_critical_section(flags);
-
return twaidev;
}
#endif
diff --git a/arch/xtensa/src/esp32/hardware/esp32_twai.h b/arch/xtensa/src/esp32/hardware/esp32_twai.h
index c9811826e6..26b96e8e52 100644
--- a/arch/xtensa/src/esp32/hardware/esp32_twai.h
+++ b/arch/xtensa/src/esp32/hardware/esp32_twai.h
@@ -383,7 +383,7 @@
#define TWAI_SYNC_JUMP_WIDTH 0x00000003
#define TWAI_SYNC_JUMP_WIDTH_M (TWAI_SYNC_JUMP_WIDTH_V << TWAI_SYNC_JUMP_WIDTH_S)
#define TWAI_SYNC_JUMP_WIDTH_V 0x00000003
-#define TWAI_SYNC_JUMP_WIDTH_S 14
+#define TWAI_SYNC_JUMP_WIDTH_S 6
/* TWAI_BAUD_PRESC : RO | R/W; bitpos: [13:0]; default: 0;
* Baud Rate Prescaler, determines the frequency dividing ratio.
@@ -833,24 +833,34 @@
#define TWAI_CLOCK_DIVIDER_REG (DR_REG_TWAI_BASE + 0x7c)
-/* TWAI_CLOCK_OFF : RO | R/W; bitpos: [8]; default: 0;
+/* TWAI_CLOCK_OFF : RO | R/W; bitpos: [3]; default: 0;
* This bit can be configured under reset mode. 1: Disable the external
* CLKOUT pin; 0: Enable the external CLKOUT pin
*/
-#define TWAI_CLOCK_OFF (BIT(8))
+#define TWAI_CLOCK_OFF (BIT(3))
#define TWAI_CLOCK_OFF_M (TWAI_CLOCK_OFF_V << TWAI_CLOCK_OFF_S)
#define TWAI_CLOCK_OFF_V 0x00000001
-#define TWAI_CLOCK_OFF_S 8
+#define TWAI_CLOCK_OFF_S 3
+
+/* TWAI_EXT_MODE : RO | R/W; bitpos: [7]; default: 0;
+ * This bit can be configured under reset mode. 1: Extended mode, compatible
+ * with CAN2.0B; 0: Basic mode
+ */
+
+#define TWAI_EXT_MODE (BIT(7))
+#define TWAI_EXT_MODE_M (TWAI_EXT_MODE_V << TWAI_EXT_MODE_S)
+#define TWAI_EXT_MODE_V 0x00000001
+#define TWAI_EXT_MODE_S 7
/* TWAI_CD : R/W; bitpos: [7:0]; default: 0;
* These bits are used to configure frequency dividing coefficients of the
* external CLKOUT pin.
*/
-#define TWAI_CD 0x000000FF
+#define TWAI_CD 0x00000007
#define TWAI_CD_M (TWAI_CD_V << TWAI_CD_S)
-#define TWAI_CD_V 0x000000FF
+#define TWAI_CD_V 0x00000007
#define TWAI_CD_S 0
#endif /* __ARCH_XTENSA_SRC_ESP32_HARDWARE_ESP32_TWAI_H */
diff --git a/boards/xtensa/esp32/esp32-devkitc/src/esp32-devkitc.h b/boards/xtensa/esp32/esp32-devkitc/src/esp32-devkitc.h
index 2640f5a01d..b919197eae 100644
--- a/boards/xtensa/esp32/esp32-devkitc/src/esp32-devkitc.h
+++ b/boards/xtensa/esp32/esp32-devkitc/src/esp32-devkitc.h
@@ -140,5 +140,16 @@ int esp32_pwm_setup(void);
int board_spidev_initialize(int bus);
#endif
+/****************************************************************************
+ * Name: esp32_twai_setup
+ *
+ * Description:
+ * Initialize TWAI and register the TWAI device
+ *
+ ****************************************************************************/
+#ifdef CONFIG_ESP32_TWAI
+int esp32_twai_setup(void);
+#endif
+
#endif /* __ASSEMBLY__ */
#endif /* __BOARDS_XTENSA_ESP32_ESP32_DEVKITC_SRC_ESP32_DEVKITC_H */