drivers: i2s: i2s_litex: Calculate offsets from DT
To support both 8-bit and 32-bit Control/Status register variants, register offsets need to be calculated from device tree. Updated register data in device tree to the 32-bit CSR variant. Renamed defines to be similar to other LiteX drivers. Changed frequencies in clock-outputs nodes, so i2s/litex sample works. Signed-off-by: Michal Sieron <msieron@internships.antmicro.com>
This commit is contained in:
parent
17a2c6d647
commit
dc98691c97
3 changed files with 64 additions and 51 deletions
|
@ -27,9 +27,9 @@ LOG_MODULE_REGISTER(i2s_litex);
|
|||
*/
|
||||
static void i2s_enable(uintptr_t reg)
|
||||
{
|
||||
uint8_t reg_data = litex_read8(reg + I2S_CONTROL_REG_OFFSET);
|
||||
uint8_t reg_data = litex_read8(reg + I2S_CONTROL_OFFSET);
|
||||
|
||||
litex_write8(reg_data | I2S_ENABLE, reg + I2S_CONTROL_REG_OFFSET);
|
||||
litex_write8(reg_data | I2S_ENABLE, reg + I2S_CONTROL_OFFSET);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -39,9 +39,9 @@ static void i2s_enable(uintptr_t reg)
|
|||
*/
|
||||
static void i2s_disable(uintptr_t reg)
|
||||
{
|
||||
uint8_t reg_data = litex_read8(reg + I2S_CONTROL_REG_OFFSET);
|
||||
uint8_t reg_data = litex_read8(reg + I2S_CONTROL_OFFSET);
|
||||
|
||||
litex_write8(reg_data & ~(I2S_ENABLE), reg + I2S_CONTROL_REG_OFFSET);
|
||||
litex_write8(reg_data & ~(I2S_ENABLE), reg + I2S_CONTROL_OFFSET);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -51,9 +51,9 @@ static void i2s_disable(uintptr_t reg)
|
|||
*/
|
||||
static void i2s_reset_fifo(uintptr_t reg)
|
||||
{
|
||||
uint8_t reg_data = litex_read8(reg + I2S_CONTROL_REG_OFFSET);
|
||||
uint8_t reg_data = litex_read8(reg + I2S_CONTROL_OFFSET);
|
||||
|
||||
litex_write8(reg_data | I2S_FIFO_RESET, reg + I2S_CONTROL_REG_OFFSET);
|
||||
litex_write8(reg_data | I2S_FIFO_RESET, reg + I2S_CONTROL_OFFSET);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -66,7 +66,7 @@ static void i2s_reset_fifo(uintptr_t reg)
|
|||
*/
|
||||
static i2s_fmt_t i2s_get_foramt(uintptr_t reg)
|
||||
{
|
||||
uint8_t reg_data = litex_read32(reg + I2S_CONFIG_REG_OFFSET);
|
||||
uint8_t reg_data = litex_read32(reg + I2S_CONFIG_OFFSET);
|
||||
|
||||
reg_data &= I2S_CONF_FORMAT_MASK;
|
||||
if (reg_data == LITEX_I2S_STANDARD) {
|
||||
|
@ -86,7 +86,7 @@ static i2s_fmt_t i2s_get_foramt(uintptr_t reg)
|
|||
*/
|
||||
static uint32_t i2s_get_sample_width(uintptr_t reg)
|
||||
{
|
||||
uint32_t reg_data = litex_read32(reg + I2S_CONFIG_REG_OFFSET);
|
||||
uint32_t reg_data = litex_read32(reg + I2S_CONFIG_OFFSET);
|
||||
|
||||
reg_data &= I2S_CONF_SAMPLE_WIDTH_MASK;
|
||||
return reg_data >> I2S_CONF_SAMPLE_WIDTH_OFFSET;
|
||||
|
@ -101,7 +101,7 @@ static uint32_t i2s_get_sample_width(uintptr_t reg)
|
|||
*/
|
||||
static uint32_t i2s_get_audio_freq(uintptr_t reg)
|
||||
{
|
||||
uint32_t reg_data = litex_read32(reg + I2S_CONFIG_REG_OFFSET);
|
||||
uint32_t reg_data = litex_read32(reg + I2S_CONFIG_OFFSET);
|
||||
|
||||
reg_data &= I2S_CONF_LRCK_MASK;
|
||||
return reg_data >> I2S_CONF_LRCK_FREQ_OFFSET;
|
||||
|
@ -117,9 +117,9 @@ static void i2s_irq_enable(uintptr_t reg, int irq_type)
|
|||
{
|
||||
__ASSERT_NO_MSG(irq_type == I2S_EV_READY || irq_type == I2S_EV_ERROR);
|
||||
|
||||
uint8_t reg_data = litex_read8(reg + I2S_EV_ENABLE_REG_OFFSET);
|
||||
uint8_t reg_data = litex_read8(reg + I2S_EV_ENABLE_OFFSET);
|
||||
|
||||
litex_write8(reg_data | irq_type, reg + I2S_EV_ENABLE_REG_OFFSET);
|
||||
litex_write8(reg_data | irq_type, reg + I2S_EV_ENABLE_OFFSET);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -132,9 +132,9 @@ static void i2s_irq_disable(uintptr_t reg, int irq_type)
|
|||
{
|
||||
__ASSERT_NO_MSG(irq_type == I2S_EV_READY || irq_type == I2S_EV_ERROR);
|
||||
|
||||
uint8_t reg_data = litex_read8(reg + I2S_EV_ENABLE_REG_OFFSET);
|
||||
uint8_t reg_data = litex_read8(reg + I2S_EV_ENABLE_OFFSET);
|
||||
|
||||
litex_write8(reg_data & ~(irq_type), reg + I2S_EV_ENABLE_REG_OFFSET);
|
||||
litex_write8(reg_data & ~(irq_type), reg + I2S_EV_ENABLE_OFFSET);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -144,9 +144,9 @@ static void i2s_irq_disable(uintptr_t reg, int irq_type)
|
|||
*/
|
||||
static void i2s_clear_pending_irq(uintptr_t reg)
|
||||
{
|
||||
uint8_t reg_data = litex_read8(reg + I2S_EV_PENDING_REG_OFFSET);
|
||||
uint8_t reg_data = litex_read8(reg + I2S_EV_PENDING_OFFSET);
|
||||
|
||||
litex_write8(reg_data, reg + I2S_EV_PENDING_REG_OFFSET);
|
||||
litex_write8(reg_data, reg + I2S_EV_PENDING_OFFSET);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -323,18 +323,16 @@ static int i2s_litex_configure(const struct device *dev, enum i2s_dir dir,
|
|||
struct i2s_litex_data *const dev_data = dev->data;
|
||||
const struct i2s_litex_cfg *const cfg = dev->config;
|
||||
struct stream *stream;
|
||||
int channels_concatenated;
|
||||
int channels_concatenated = litex_read8(cfg->base + I2S_STATUS_OFFSET);
|
||||
int dev_audio_freq = i2s_get_audio_freq(cfg->base);
|
||||
int channel_div;
|
||||
|
||||
if (dir == I2S_DIR_RX) {
|
||||
stream = &dev_data->rx;
|
||||
channels_concatenated = litex_read8(I2S_RX_STATUS_REG) &
|
||||
I2S_RX_STAT_CHANNEL_CONCATENATED_MASK;
|
||||
channels_concatenated &= I2S_RX_STAT_CHANNEL_CONCATENATED_MASK;
|
||||
} else if (dir == I2S_DIR_TX) {
|
||||
stream = &dev_data->tx;
|
||||
channels_concatenated = litex_read8(I2S_TX_STATUS_REG) &
|
||||
I2S_TX_STAT_CHANNEL_CONCATENATED_MASK;
|
||||
channels_concatenated &= I2S_TX_STAT_CHANNEL_CONCATENATED_MASK;
|
||||
} else if (dir == I2S_DIR_BOTH) {
|
||||
return -ENOSYS;
|
||||
} else {
|
||||
|
@ -612,7 +610,7 @@ static const struct i2s_driver_api i2s_litex_driver_api = {
|
|||
static void i2s_litex_irq_config_func_##dir(const struct device *dev); \
|
||||
\
|
||||
static struct i2s_litex_cfg i2s_litex_cfg_##dir = { \
|
||||
.base = DT_REG_ADDR_BY_NAME(DT_NODELABEL(i2s_##dir), control), \
|
||||
.base = DT_REG_ADDR(DT_NODELABEL(i2s_##dir)), \
|
||||
.fifo_base = \
|
||||
DT_REG_ADDR_BY_NAME(DT_NODELABEL(i2s_##dir), fifo), \
|
||||
.fifo_depth = DT_PROP(DT_NODELABEL(i2s_##dir), fifo_depth), \
|
||||
|
|
|
@ -11,14 +11,6 @@
|
|||
#include <zephyr/drivers/i2s.h>
|
||||
#include <zephyr/devicetree.h>
|
||||
|
||||
/* i2s register offsets*/
|
||||
#define I2S_EV_STATUS_REG_OFFSET 0x0
|
||||
#define I2S_EV_PENDING_REG_OFFSET 0x4
|
||||
#define I2S_EV_ENABLE_REG_OFFSET 0x8
|
||||
#define I2S_CONTROL_REG_OFFSET 0xc
|
||||
#define I2S_STATUS_REG_OFFSET 0x10
|
||||
#define I2S_CONFIG_REG_OFFSET 0x20
|
||||
|
||||
/* i2s configuration mask*/
|
||||
#define I2S_CONF_FORMAT_OFFSET 0
|
||||
#define I2S_CONF_SAMPLE_WIDTH_OFFSET 2
|
||||
|
@ -36,14 +28,6 @@
|
|||
#define I2S_EV_READY (1 << 0)
|
||||
#define I2S_EV_ERROR (1 << 1)
|
||||
/* i2s rx*/
|
||||
#define I2S_RX_BASE_ADDR DT_REG_ADDR_BY_NAME(DT_NODELABEL(i2s_rx), control)
|
||||
#define I2S_RX_EV_STATUS_REG (I2S_RX_BASE_ADDR + I2S_EV_STATUS_REG_OFFSET)
|
||||
#define I2S_RX_EV_PENDING_REG (I2S_RX_BASE_ADDR + I2S_EV_PENDING_REG_OFFSET)
|
||||
#define I2S_RX_EV_ENABLE_REG (I2S_RX_BASE_ADDR + I2S_EV_ENABLE_REG_OFFSET)
|
||||
#define I2S_RX_CONTROL_REG (I2S_RX_BASE_ADDR + I2S_CONTROL_REG_OFFSET)
|
||||
#define I2S_RX_STATUS_REG (I2S_RX_BASE_ADDR + I2S_STATUS_REG_OFFSET)
|
||||
#define I2S_RX_CONFIG_REG (I2S_RX_BASE_ADDR + I2S_CONFIG_REG_OFFSET)
|
||||
|
||||
#define I2S_RX_STAT_CHANNEL_CONCATENATED_OFFSET 31
|
||||
#define I2S_RX_STAT_CHANNEL_CONCATENATED_MASK \
|
||||
(0x1 << I2S_RX_STAT_CHANNEL_CONCATENATED_OFFSET)
|
||||
|
@ -52,14 +36,6 @@
|
|||
#define I2S_RX_FIFO_DEPTH DT_PROP(DT_NODELABEL(i2s_rx), fifo_depth)
|
||||
|
||||
/* i2s tx*/
|
||||
#define I2S_TX_BASE_ADDR DT_REG_ADDR_BY_NAME(DT_NODELABEL(i2s_tx), control)
|
||||
#define I2S_TX_EV_STATUS_REG (I2S_RX_BASE_ADDR + I2S_EV_STATUS_REG_OFFSET)
|
||||
#define I2S_TX_EV_PENDING_REG (I2S_TX_BASE_ADDR + I2S_EV_PENDING_REG_OFFSET)
|
||||
#define I2S_TX_EV_ENABLE_REG (I2S_TX_BASE_ADDR + I2S_EV_ENABLE_REG_OFFSET)
|
||||
#define I2S_TX_CONTROL_REG (I2S_TX_BASE_ADDR + I2S_CONTROL_REG_OFFSET)
|
||||
#define I2S_TX_STATUS_REG (I2S_TX_BASE_ADDR + I2S_STATUS_REG_OFFSET)
|
||||
#define I2S_TX_CONFIG_REG (I2S_TX_BASE_ADDR + I2S_CONFIG_REG_OFFSET)
|
||||
|
||||
#define I2S_TX_STAT_CHANNEL_CONCATENATED_OFFSET 24
|
||||
#define I2S_TX_STAT_CHANNEL_CONCATENATED_MASK \
|
||||
(0x1 << I2S_TX_STAT_CHANNEL_CONCATENATED_OFFSET)
|
||||
|
@ -67,6 +43,21 @@
|
|||
#define I2S_TX_FIFO_ADDR DT_REG_ADDR_BY_NAME(DT_NODELABEL(i2s_tx), fifo)
|
||||
#define I2S_TX_FIFO_DEPTH DT_PROP(DT_NODELABEL(i2s_tx), fifo_depth)
|
||||
|
||||
/* i2s register offsets (they are the same for all i2s nodes, both rx and tx) */
|
||||
#define I2S_BASE_ADDR DT_REG_ADDR(DT_NODELABEL(i2s_rx))
|
||||
#define I2S_EV_STATUS_OFFSET (DT_REG_ADDR_BY_NAME(DT_NODELABEL(i2s_rx), ev_status) \
|
||||
- I2S_BASE_ADDR)
|
||||
#define I2S_EV_PENDING_OFFSET (DT_REG_ADDR_BY_NAME(DT_NODELABEL(i2s_rx), ev_pending) \
|
||||
- I2S_BASE_ADDR)
|
||||
#define I2S_EV_ENABLE_OFFSET (DT_REG_ADDR_BY_NAME(DT_NODELABEL(i2s_rx), ev_enable) \
|
||||
- I2S_BASE_ADDR)
|
||||
#define I2S_CONTROL_OFFSET (DT_REG_ADDR_BY_NAME(DT_NODELABEL(i2s_rx), rx_ctl) \
|
||||
- I2S_BASE_ADDR)
|
||||
#define I2S_STATUS_OFFSET (DT_REG_ADDR_BY_NAME(DT_NODELABEL(i2s_rx), rx_stat) \
|
||||
- I2S_BASE_ADDR)
|
||||
#define I2S_CONFIG_OFFSET (DT_REG_ADDR_BY_NAME(DT_NODELABEL(i2s_rx), rx_conf) \
|
||||
- I2S_BASE_ADDR)
|
||||
|
||||
enum litex_i2s_fmt {
|
||||
LITEX_I2S_STANDARD = 1,
|
||||
LITEX_I2S_LEFT_JUSTIFIED = 2,
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue