drivers: dac: esp32: Add support for DAC controller

Initial DAC driver for the ESP32/ESP32-S2 SOCs

Signed-off-by: Marek Matej <marek.matej@espressif.com>
This commit is contained in:
Marek Matej 2022-11-04 19:23:22 +01:00 committed by Fabio Baltieri
parent 5b2d80ca18
commit f86a7d2c25
9 changed files with 209 additions and 0 deletions

View file

@ -11,6 +11,7 @@ supported:
- uart
- nvs
- pwm
- dac
testing:
ignore_tags:
- net

View file

@ -13,4 +13,5 @@ zephyr_library_sources_ifdef(CONFIG_DAC_SHELL dac_shell.c)
zephyr_library_sources_ifdef(CONFIG_DAC_MCP4725 dac_mcp4725.c)
zephyr_library_sources_ifdef(CONFIG_DAC_MCP4728 dac_mcp4728.c)
zephyr_library_sources_ifdef(CONFIG_DAC_GD32 dac_gd32.c)
zephyr_library_sources_ifdef(CONFIG_DAC_ESP32 dac_esp32.c)
zephyr_library_sources_ifdef(CONFIG_USERSPACE dac_handlers.c)

View file

@ -48,4 +48,6 @@ source "drivers/dac/Kconfig.mcp4728"
source "drivers/dac/Kconfig.gd32"
source "drivers/dac/Kconfig.esp32"
endif # DAC

11
drivers/dac/Kconfig.esp32 Normal file
View file

@ -0,0 +1,11 @@
# ESP32 DAC configuration options
# Copyright (c) 2022 Espressif Systems (Shanghai) Co., Ltd.
# SPDX-License-Identifier: Apache-2.0
config DAC_ESP32
bool "ESP32 DAC driver"
default y
depends on DT_HAS_ESPRESSIF_ESP32_DAC_ENABLED
help
Enable the ESP32 DAC driver

99
drivers/dac/dac_esp32.c Normal file
View file

@ -0,0 +1,99 @@
/*
* Copyright (c) 2022 Espressif Systems (Shanghai) Co., Ltd.
*
* SPDX-License-Identifier: Apache-2.0
*/
#define DT_DRV_COMPAT espressif_esp32_dac
#include <soc.h>
#include <zephyr/device.h>
#include <zephyr/drivers/dac.h>
#include <zephyr/drivers/clock_control.h>
#include <hal/rtc_io_types.h>
#include <hal/rtc_io_hal.h>
#include <hal/rtc_io_ll.h>
#include <hal/dac_hal.h>
#include <hal/dac_types.h>
#include "driver/dac_common.h"
#include <zephyr/logging/log.h>
LOG_MODULE_REGISTER(esp32_dac, CONFIG_DAC_LOG_LEVEL);
struct dac_esp32_config {
int irq_source;
const struct device *clock_dev;
clock_control_subsys_t clock_subsys;
};
static int dac_esp32_write_value(const struct device *dev,
uint8_t channel, uint32_t value)
{
ARG_UNUSED(dev);
dac_output_voltage(channel, value);
return 0;
}
static int dac_esp32_channel_setup(const struct device *dev,
const struct dac_channel_cfg *channel_cfg)
{
ARG_UNUSED(dev);
if (channel_cfg->channel_id > DAC_CHANNEL_MAX) {
LOG_ERR("Channel %d is not valid", channel_cfg->channel_id);
return -EINVAL;
}
dac_output_enable(channel_cfg->channel_id);
return 0;
}
static int dac_esp32_init(const struct device *dev)
{
const struct dac_esp32_config *cfg = dev->config;
if (!cfg->clock_dev) {
LOG_ERR("Clock device missing");
return -EINVAL;
}
if (!device_is_ready(cfg->clock_dev)) {
LOG_ERR("Clock device not ready");
return -ENODEV;
}
if (clock_control_on(cfg->clock_dev,
(clock_control_subsys_t *) &cfg->clock_subsys) != 0) {
LOG_ERR("DAC clock setup failed (%d)", -EIO);
return -EIO;
}
return 0;
}
static const struct dac_driver_api dac_esp32_driver_api = {
.channel_setup = dac_esp32_channel_setup,
.write_value = dac_esp32_write_value
};
#define ESP32_DAC_INIT(id) \
\
static const struct dac_esp32_config dac_esp32_config_##id = { \
.irq_source = DT_INST_IRQN(id), \
.clock_dev = DEVICE_DT_GET(DT_INST_CLOCKS_CTLR(id)), \
.clock_subsys = (clock_control_subsys_t) DT_INST_CLOCKS_CELL(id, offset), \
}; \
\
DEVICE_DT_INST_DEFINE(id, \
&dac_esp32_init, \
NULL, \
NULL, \
&dac_esp32_config_##id, \
POST_KERNEL, \
CONFIG_DAC_INIT_PRIORITY, \
&dac_esp32_driver_api);
DT_INST_FOREACH_STATUS_OKAY(ESP32_DAC_INIT);

View file

@ -0,0 +1,53 @@
# Copyright (c) 2022 Espressif Systems (Shanghai) Co., Ltd.
# SPDX-License-Identifier: Apache-2.0
description: |
Espressif Digital to Analog converter (DAC) control node
is part of the RTC low-power domain and belongs to the SENSE
peripherals set. RTC peripherals has GPIOs controlled by the
RTCIO mux, which is separated from the main IO mux.
Two GPIO pads can only be connected to the DAC peripheral.
ESP32 pads
- GPIO25 as DAC channel 1
- GPIO26 as DAC channel 2
ESP32-S2 pads
- GPIO17 as DAC channel 1
- GPIO18 as DAC channel 2
To enable the DAC peripheral it must be enabled in the board
dts, or in subsequent overlay file.
&dac {
status = "okay";
};
To specify the DAC channel to use, dts overlay must include
properties 'dac-channel-id', which uses zero based channel index.
Variable 'dac-resolution' must be also specified, although ESP32
only supported resolution is 8bits.
/ {
zephyr,user {
dac = <&dac>;
dac-channel-id = <0>;
dac-resolution = <8>;
};
};
NOTE: The DAC peripheral outputs are fixed to gpio pads, therefore
it does not need to be controlled by the pinctrl node.
compatible: "espressif,esp32-dac"
include: [dac-controller.yaml]
properties:
"#io-channel-cells":
const: 1
io-channel-cells:
- output

View file

@ -354,6 +354,16 @@
interrupt-parent = <&intc>;
status = "disabled";
};
dac: dac@3ff48800 {
compatible = "espressif,esp32-dac";
reg = <0x3ff48800 0x100>;
interrupts = <RTC_CORE_INTR_SOURCE>;
interrupt-parent = <&intc>;
clocks = <&rtc ESP32_SARADC_MODULE>;
#io-channel-cells = <1>;
status = "disabled";
};
};
};

View file

@ -254,6 +254,16 @@
clocks = <&rtc ESP32_TIMG1_MODULE>;
status = "disabled";
};
dac: dac@3f408800 {
compatible = "espressif,esp32-dac";
reg = <0x3f408800 0x100>;
interrupts = <RTC_CORE_INTR_SOURCE>;
interrupt-parent = <&intc>;
clocks = <&rtc ESP32_PERIPH_SARADC_MODULE>;
#io-channel-cells = <1>;
status = "disabled";
};
};
};

View file

@ -419,4 +419,26 @@
#define ESP_SIG_IN_FUNC228 228
#define ESP_SIG_GPIO_OUT 256
/* RTC-IO MUX */
#define ESP_ADC1_CH0 0
#define ESP_ADC1_CH1 1
#define ESP_ADC1_CH2 2
#define ESP_ADC1_CH3 3
#define ESP_ADC1_CH6 4
#define ESP_ADC1_CH7 5
#define ESP_ADC2_CH8 6
#define ESP_ADC2_CH9 7
#define ESP_DAC1_OUT 6
#define ESP_DAC2_OUT 7
#define ESP_ADC1_CH5 8
#define ESP_ADC1_CH4 9
#define ESP_ADC2_CH0 10
#define ESP_ADC2_CH1 11
#define ESP_ADC2_CH2 12
#define ESP_ADC2_CH3 13
#define ESP_ADC2_CH4 14
#define ESP_ADC2_CH5 15
#define ESP_ADC2_CH6 16
#define ESP_ADC2_CH7 17
#endif /* ZEPHYR_INCLUDE_DT_BINDINGS_PINCTRL_ESP32_GPIO_SIGMAP_H_ */