drivers: pinctrl: Add pinctrl driver for Apollo4
This commit addst pinctrl support for Apollo4 SoCs. Co-authored-by: Mateusz Sierszulski <msierszulski@antmicro.com> Signed-off-by: Maciej Sobkowski <msobkowski@antmicro.com>
This commit is contained in:
parent
0118886624
commit
8a670d0713
|
@ -4,6 +4,7 @@
|
|||
zephyr_library()
|
||||
zephyr_library_sources(common.c)
|
||||
zephyr_library_sources_ifdef(CONFIG_PINCTRL_TELINK_B91 pinctrl_b91.c)
|
||||
zephyr_library_sources_ifdef(CONFIG_PINCTRL_AMBIQ_APOLLO4 pinctrl_ambiq_apollo4.c)
|
||||
zephyr_library_sources_ifdef(CONFIG_PINCTRL_GD32_AF pinctrl_gd32_af.c)
|
||||
zephyr_library_sources_ifdef(CONFIG_PINCTRL_GD32_AFIO pinctrl_gd32_afio.c)
|
||||
zephyr_library_sources_ifdef(CONFIG_PINCTRL_ITE_IT8XXX2 pinctrl_ite_it8xxx2.c)
|
||||
|
|
|
@ -34,6 +34,7 @@ config PINCTRL_DYNAMIC
|
|||
peripheral at early boot stages depending on a certain input.
|
||||
|
||||
source "drivers/pinctrl/Kconfig.b91"
|
||||
source "drivers/pinctrl/Kconfig.ambiq"
|
||||
source "drivers/pinctrl/Kconfig.gd32"
|
||||
source "drivers/pinctrl/Kconfig.it8xxx2"
|
||||
source "drivers/pinctrl/Kconfig.npcx"
|
||||
|
|
12
drivers/pinctrl/Kconfig.ambiq
Normal file
12
drivers/pinctrl/Kconfig.ambiq
Normal file
|
@ -0,0 +1,12 @@
|
|||
# SPDX-License-Identifier: Apache-2.0
|
||||
#
|
||||
# Copyright (c) 2023 Antmicro <www.antmicro.com>
|
||||
|
||||
config PINCTRL_AMBIQ_APOLLO4
|
||||
bool "Ambiq Apollo4 pin controller driver"
|
||||
default y
|
||||
depends on DT_HAS_AMBIQ_APOLLO4_PINCTRL_ENABLED
|
||||
select AMBIQ_HAL
|
||||
select AMBIQ_HAL_USE_GPIO
|
||||
help
|
||||
Ambiq Apollo4 pinctrl driver
|
44
drivers/pinctrl/pinctrl_ambiq_apollo4.c
Normal file
44
drivers/pinctrl/pinctrl_ambiq_apollo4.c
Normal file
|
@ -0,0 +1,44 @@
|
|||
/*
|
||||
* Copyright (c) 2023 Antmicro <www.antmicro.com>
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
#include <zephyr/drivers/pinctrl.h>
|
||||
|
||||
/* ambiq-sdk includes */
|
||||
#include <am_mcu_apollo.h>
|
||||
|
||||
static void pinctrl_configure_pin(const pinctrl_soc_pin_t *pin)
|
||||
{
|
||||
am_hal_gpio_pincfg_t pin_config = {0};
|
||||
|
||||
pin_config.GP.cfg_b.uFuncSel = pin->alt_func;
|
||||
pin_config.GP.cfg_b.eGPInput = pin->input_enable ? AM_HAL_GPIO_PIN_INPUT_ENABLE
|
||||
: AM_HAL_GPIO_PIN_INPUT_NONE;
|
||||
pin_config.GP.cfg_b.eGPOutCfg = pin->push_pull ? AM_HAL_GPIO_PIN_OUTCFG_PUSHPULL
|
||||
: pin->open_drain ? AM_HAL_GPIO_PIN_OUTCFG_OPENDRAIN
|
||||
: pin->tristate ? AM_HAL_GPIO_PIN_OUTCFG_TRISTATE
|
||||
: AM_HAL_GPIO_PIN_OUTCFG_DISABLE;
|
||||
pin_config.GP.cfg_b.eDriveStrength = pin->drive_strength;
|
||||
pin_config.GP.cfg_b.uSlewRate = pin->slew_rate;
|
||||
|
||||
if (pin->bias_pull_up) {
|
||||
pin_config.GP.cfg_b.ePullup = pin->ambiq_pull_up_ohms + AM_HAL_GPIO_PIN_PULLUP_1_5K;
|
||||
} else if (pin->bias_pull_down) {
|
||||
pin_config.GP.cfg_b.ePullup = AM_HAL_GPIO_PIN_PULLDOWN_50K;
|
||||
}
|
||||
|
||||
am_hal_gpio_pinconfig(pin->pin_num, pin_config);
|
||||
}
|
||||
|
||||
int pinctrl_configure_pins(const pinctrl_soc_pin_t *pins, uint8_t pin_cnt, uintptr_t reg)
|
||||
{
|
||||
ARG_UNUSED(reg);
|
||||
|
||||
for (uint8_t i = 0U; i < pin_cnt; i++) {
|
||||
pinctrl_configure_pin(pins++);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
106
dts/bindings/pinctrl/ambiq,apollo4-pinctrl.yaml
Normal file
106
dts/bindings/pinctrl/ambiq,apollo4-pinctrl.yaml
Normal file
|
@ -0,0 +1,106 @@
|
|||
# Copyright (c) 2023 Antmicro <www.antmicro.com>
|
||||
# SPDX-License-Identifier: Apache-2.0
|
||||
|
||||
description: |
|
||||
The Ambiq Apollo4 pin controller is a node responsible for controlling
|
||||
pin function selection and pin properties, such as routing a UART0 TX
|
||||
to pin 60 and enabling the pullup resistor on that pin.
|
||||
|
||||
The node has the 'pinctrl' node label set in your SoC's devicetree,
|
||||
so you can modify it like this:
|
||||
|
||||
&pinctrl {
|
||||
/* your modifications go here */
|
||||
};
|
||||
|
||||
All device pin configurations should be placed in child nodes of the
|
||||
'pinctrl' node, as shown in this example:
|
||||
|
||||
/* You can put this in places like a board-pinctrl.dtsi file in
|
||||
* your board directory, or a devicetree overlay in your application.
|
||||
*/
|
||||
|
||||
/* include pre-defined combinations for the SoC variant used by the board */
|
||||
#include <dt-bindings/pinctrl/ambiq-apollo4-pinctrl.h>
|
||||
|
||||
&pinctrl {
|
||||
uart0_default: uart0_default {
|
||||
group1 {
|
||||
pinmux = <UART0TX_P60>;
|
||||
};
|
||||
group2 {
|
||||
pinmux = <UART0RX_P47>;
|
||||
input-enable;
|
||||
};
|
||||
};
|
||||
};
|
||||
|
||||
The 'uart0_default' child node encodes the pin configurations for a
|
||||
particular state of a device; in this case, the default (that is, active)
|
||||
state.
|
||||
|
||||
As shown, pin configurations are organized in groups within each child node.
|
||||
Each group can specify a list of pin function selections in the 'pinmux'
|
||||
property.
|
||||
|
||||
A group can also specify shared pin properties common to all the specified
|
||||
pins, such as the 'input-enable' property in group 2.
|
||||
|
||||
compatible: "ambiq,apollo4-pinctrl"
|
||||
|
||||
include: base.yaml
|
||||
|
||||
child-binding:
|
||||
description: |
|
||||
Definitions for a pinctrl state.
|
||||
child-binding:
|
||||
|
||||
include:
|
||||
- name: pincfg-node.yaml
|
||||
property-allowlist:
|
||||
- input-enable
|
||||
- drive-push-pull
|
||||
- drive-open-drain
|
||||
- bias-high-impedance
|
||||
- bias-pull-up
|
||||
- bias-pull-down
|
||||
|
||||
properties:
|
||||
pinmux:
|
||||
required: true
|
||||
type: array
|
||||
description: |
|
||||
An array of pins sharing the same group properties. Each
|
||||
element of the array is an integer constructed from the
|
||||
pin number and the alternative function of the pin.
|
||||
drive-strength:
|
||||
type: string
|
||||
enum:
|
||||
- "0.1"
|
||||
- "0.5"
|
||||
- "0.75"
|
||||
- "1.0"
|
||||
default: "0.1"
|
||||
description: |
|
||||
The drive strength of a pin, relative to full-driver strength.
|
||||
The default value is 0.1, which is the reset value.
|
||||
slew-rate:
|
||||
type: string
|
||||
enum:
|
||||
- "slow"
|
||||
- "fast"
|
||||
default: "slow"
|
||||
description: |
|
||||
Select slew rate for a pin. The default is slow, which is the reset value.
|
||||
ambiq,pull-up-ohms:
|
||||
type: int
|
||||
enum:
|
||||
- 1500
|
||||
- 6000
|
||||
- 12000
|
||||
- 24000
|
||||
- 50000
|
||||
- 100000
|
||||
default: 1500
|
||||
description: |
|
||||
The pullup resistor value. The default value is 1500 ohms.
|
1120
include/zephyr/dt-bindings/pinctrl/ambiq-apollo4-pinctrl.h
Normal file
1120
include/zephyr/dt-bindings/pinctrl/ambiq-apollo4-pinctrl.h
Normal file
File diff suppressed because it is too large
Load diff
80
soc/arm/ambiq/apollo4x/pinctrl_soc.h
Normal file
80
soc/arm/ambiq/apollo4x/pinctrl_soc.h
Normal file
|
@ -0,0 +1,80 @@
|
|||
/*
|
||||
* Copyright (c) 2023 Antmicro <www.antmicro.com>
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
#ifndef ZEPHYR_SOC_ARM_AMBIQ_APOLLO4_PINCTRL_SOC_H_
|
||||
#define ZEPHYR_SOC_ARM_AMBIQ_APOLLO4_PINCTRL_SOC_H_
|
||||
|
||||
#include <zephyr/dt-bindings/pinctrl/ambiq-apollo4-pinctrl.h>
|
||||
|
||||
/**
|
||||
* @brief Type to hold a pin's pinctrl configuration.
|
||||
*/
|
||||
struct apollo4_pinctrl_soc_pin {
|
||||
/** Pin number 0..128 */
|
||||
uint32_t pin_num : 7;
|
||||
/** Alternative function (UART, SPI, etc.) */
|
||||
uint32_t alt_func : 4;
|
||||
/** Enable the pin as an input */
|
||||
uint32_t input_enable : 1;
|
||||
/** Drive strength, relative to full-driver strength */
|
||||
uint32_t drive_strength : 2;
|
||||
/** Slew rate, may be either false (slow) or true (fast) */
|
||||
uint32_t slew_rate : 1;
|
||||
/** Drive actively high or low */
|
||||
uint32_t push_pull : 1;
|
||||
/** Drive with open drain */
|
||||
uint32_t open_drain : 1;
|
||||
/** High impedance mode */
|
||||
uint32_t tristate : 1;
|
||||
/** Enable the internal pull up resistor */
|
||||
uint32_t bias_pull_up : 1;
|
||||
/** Enable the internal pull down resistor */
|
||||
uint32_t bias_pull_down : 1;
|
||||
/** pullup resistor value */
|
||||
uint32_t ambiq_pull_up_ohms : 3;
|
||||
};
|
||||
|
||||
typedef struct apollo4_pinctrl_soc_pin pinctrl_soc_pin_t;
|
||||
|
||||
/**
|
||||
* @brief Utility macro to initialize each pin.
|
||||
*
|
||||
* @param node_id Node identifier.
|
||||
* @param prop Property name.
|
||||
* @param idx Property entry index.
|
||||
*/
|
||||
#define Z_PINCTRL_STATE_PIN_INIT(node_id, prop, idx) \
|
||||
{ \
|
||||
APOLLO4_GET_PIN_NUM(DT_PROP_BY_IDX(node_id, prop, idx)), \
|
||||
APOLLO4_GET_PIN_ALT_FUNC(DT_PROP_BY_IDX(node_id, prop, idx)), \
|
||||
DT_PROP(node_id, input_enable), \
|
||||
DT_ENUM_IDX(node_id, drive_strength), \
|
||||
DT_ENUM_IDX(node_id, slew_rate), \
|
||||
DT_PROP(node_id, drive_push_pull), \
|
||||
DT_PROP(node_id, drive_open_drain), \
|
||||
DT_PROP(node_id, bias_high_impedance), \
|
||||
DT_PROP(node_id, bias_pull_up), \
|
||||
DT_PROP(node_id, bias_pull_down), \
|
||||
DT_ENUM_IDX(node_id, ambiq_pull_up_ohms), \
|
||||
},
|
||||
|
||||
/**
|
||||
* @brief Utility macro to initialize state pins contained in a given property.
|
||||
*
|
||||
* @param node_id Node identifier.
|
||||
* @param prop Property name describing state pins.
|
||||
*/
|
||||
#define Z_PINCTRL_STATE_PINS_INIT(node_id, prop) \
|
||||
{DT_FOREACH_CHILD_VARGS(DT_PHANDLE(node_id, prop), \
|
||||
DT_FOREACH_PROP_ELEM, pinmux, \
|
||||
Z_PINCTRL_STATE_PIN_INIT)}
|
||||
|
||||
#define APOLLO4_GET_PIN_NUM(pinctrl) \
|
||||
(((pinctrl) >> APOLLO4_PIN_NUM_POS) & APOLLO4_PIN_NUM_MASK)
|
||||
#define APOLLO4_GET_PIN_ALT_FUNC(pinctrl) \
|
||||
(((pinctrl) >> APOLLO4_ALT_FUNC_POS) & APOLLO4_ALT_FUNC_MASK)
|
||||
|
||||
#endif /* ZEPHYR_SOC_ARM_AMBIQ_APOLLO4_PINCTRL_SOC_H_ */
|
Loading…
Reference in a new issue