Files
base/drivers/include/sdrv_gpio.h
2025-11-07 09:57:14 +08:00

499 lines
17 KiB
C

/**
* @file sdrv_gpio.h
* @brief SemiDrive GPIO driver header file.
*
* @copyright Copyright (c) 2022 Semidrive Semiconductor.
* All rights reserved.
*/
#ifndef SDRV_GPIO_H_
#define SDRV_GPIO_H_
#include <sdrv_common.h>
#include <sdrv_pinctrl.h>
#include <types.h>
/**
* @brief GPIO status error code.
*/
enum sdrv_gpio_error {
SDRV_GPIO_BAD_PIN = SDRV_ERROR_STATUS(SDRV_STATUS_GROUP_GPIO,
1), /* GPIO Pin Index Wrong. */
SDRV_GPIO_CTRL_NULL = SDRV_ERROR_STATUS(SDRV_STATUS_GROUP_GPIO,
2), /* GPIO Controller is NULL. */
SDRV_GPIO_IRQ_ATTACH_FAIL = SDRV_ERROR_STATUS(
SDRV_STATUS_GROUP_GPIO, 3), /* GPIO Attach Irq failed. */
};
/**
* @brief Definition for gpio direction.
*/
typedef enum gpio_direction {
GPIO_DIR_OUT, /**< gpio output */
GPIO_DIR_IN, /**< gpio input */
} gpio_direction_e;
/**
* @brief Definition for gpio interrupt type.
*/
typedef enum gpio_interrupt {
GPIO_INTR_DISABLE, /* INPUT. Interrupt disable. */
GPIO_INTR_HIGH_LEVEL, /* INPUT. Interrupt on high level. */
GPIO_INTR_LOW_LEVEL, /* INPUT. Interrupt on low level. */
GPIO_INTR_RISING_EDGE, /* INPUT. Interrupt on rising edge. */
GPIO_INTR_FALLING_EDGE, /* INPUT. Interrupt on falling edge. */
GPIO_INTR_BOTH_EDGE, /* INPUT. Interrupt on both edges. */
} gpio_interrupt_e;
/**
* @brief Definition for gpio interrupt share with core bit mask.
*
*/
typedef enum gpio_interrupt_share {
GPIO_INTR_SF = 0x1, /**< Default GPIO interrupt send to SF */
GPIO_INTR_SP0 = 0x2, /**< GPIO interrupt share with SP0 */
GPIO_INTR_SP1 = 0x4, /**< GPIO interrupt share with SP1 */
GPIO_INTR_SX0 = 0x8, /**< GPIO interrupt share with SX0 */
GPIO_INTR_SX1 = 0x10, /**< GPIO interrupt share with SX1 */
} gpio_interrupt_share_e;
/**
* @brief GPIO Controller Instance.
*
*/
typedef struct sdrv_gpio {
paddr_t base;
uint32_t pin_start;
uint32_t pin_num;
} sdrv_gpio_t;
/**
* @brief Function prototype for gpio interrupt callback.
*
* @param [in] irq irq number occured.
* @param [in] pin pin index defined in pinctrl.h.
* @param [in] arg user register callback param.
*/
typedef void (*sdrv_gpio_interrupt_handler_t)(uint32_t irq, uint32_t pin,
void *arg);
/**
* @brief Config gpio direction.
*
* This function config gpio as input or output.
*
* @param [in] pin_index defined pin macro in pinctrl.h.
* @param [in] dir direction defined as gpio_direction_e.
* @return SDRV_STATUS_OK or error code.
*/
status_t sdrv_gpio_set_pin_direction(uint32_t pin_index, gpio_direction_e dir);
/**
* @brief Config gpio output level.
*
* This function config gpio output high or low level.
*
* @param [in] pin_index defined pin macro in pinctrl.h.
* @param [in] level true represents high, false represents low.
* @return SDRV_STATUS_OK or error code.
*/
status_t sdrv_gpio_set_pin_output_level(uint32_t pin_index, bool level);
/**
* @brief Get gpio output level.
*
* This function read gpio output data register for specific pin.
*
* @param [in] pin_index defined pin macro in pinctrl.h.
* @return true represents high configed, false represents low configed.
*/
bool sdrv_gpio_get_pin_output_level(uint32_t pin_index);
/**
* @brief Toggle specific pin output level.
*
* This function toggle output level for specific pin, for example, if pin
* output high at first, after call this function, it will output low.
*
* @param [in] pin_index defined pin macro in pinctrl.h.
* @return SDRV_STATUS_OK or error code.
*/
status_t sdrv_gpio_toggle_pin_output_level(uint32_t pin_index);
/**
* @brief Get specific pin input level.
*
* This function read pin input level.
*
* @param [in] pin_index defined pin macro in pinctrl.h.
* @return true represents high level, false represents low level.
*/
bool sdrv_gpio_read_pin_input_level(uint32_t pin_index);
/**
* @brief Config interrupt type for specific pin.
*
* This function config pin as interrupt type, after configuration, you also
* need call sdrv_gpio_pin_interrupt_enable for starting receive interrupt.
*
* @param [in] pin_index defined pin macro in pinctrl.h.
* @param [in] intr interrupt type defined in gpio_interrupt_e.
* @return SDRV_STATUS_OK or error code.
*/
status_t sdrv_gpio_set_pin_interrupt(uint32_t pin_index, gpio_interrupt_e intr);
/**
* @brief Enable interrupt for specific pin.
*
* This function config pin interrupt enable register and unmask pin interrupt
* status.
*
* @param [in] pin_index defined pin macro in pinctrl.h.
* @return SDRV_STATUS_OK or error code.
*/
status_t sdrv_gpio_pin_interrupt_enable(uint32_t pin_index);
/**
* @brief Disable interrupt for specific pin.
*
* This function config pin interrupt disable register and mask pin interrupt
* status.
*
* @param [in] pin_index defined pin macro in pinctrl.h.
* @return SDRV_STATUS_OK or error code.
*/
status_t sdrv_gpio_pin_interrupt_disable(uint32_t pin_index);
/**
* @brief Get specific pin interrupt status.
*
* This function read pin interrupt status register.
*
* @param [in] pin_index defined pin macro in pinctrl.h.
* @return true represents interrupt status is set, false represents no
*/
bool sdrv_gpio_pin_interrupt_status(uint32_t pin_index);
/**
* @brief Clear specific pin interrupt status.
*
* This function clear pin interrupt status. Only edge interrupt type need clear
* status, level type should inactive source level.
*
* @param [in] pin_index defined pin macro in pinctrl.h.
* @return SDRV_STATUS_OK or error code.
*/
status_t sdrv_gpio_clear_pin_interrupt_status(uint32_t pin_index);
/**
* @brief Config asynchronous interrupt type for specific pin.
*
* This function config pin as interrupt type using asynchronous way. Compare to
* normal interrupt way, asynchronous interrupt can also receive interrupt
* without clock, so it can be work in lowpower mode.
*
* @param [in] pin_index defined pin macro in pinctrl.h.
* @param [in] intr interrupt type defined in gpio_interrupt_e.
* @return SDRV_STATUS_OK or error code.
*/
status_t sdrv_gpio_set_pin_async_interrupt(uint32_t pin_index,
gpio_interrupt_e intr);
/**
* @brief Enable asynchronous interrupt for specific pin.
*
* This function config pin interrupt enable register and unmask pin interrupt
* status.
*
* @param [in] pin_index defined pin macro in pinctrl.h.
* @return SDRV_STATUS_OK or error code.
*/
status_t sdrv_gpio_pin_async_interrupt_enable(uint32_t pin_index);
/**
* @brief Disable asynchronous interrupt for specific pin.
*
* This function config pin interrupt disable register and mask pin interrupt
* status.
*
* @param [in] pin_index defined pin macro in pinctrl.h.
* @return SDRV_STATUS_OK or error code.
*/
status_t sdrv_gpio_pin_async_interrupt_disable(uint32_t pin_index);
/**
* @brief Get specific pin asynchronous interrupt status.
*
* This function read pin asynchronous interrupt status register.
*
* @param [in] pin_index defined pin macro in pinctrl.h.
* @return true represents interrupt status is set, false represents no
* interrupt status.
*/
bool sdrv_gpio_pin_async_interrupt_status(uint32_t pin_index);
/**
* @brief Clear specific pin asynchronous interrupt status.
*
* This function clear pin asynchronous interrupt status. Only edge interrupt
* type need clear status, level type should inactive source level.
*
* @param [in] pin_index defined pin macro in pinctrl.h.
* @return SDRV_STATUS_OK or error code.
*/
status_t sdrv_gpio_clear_pin_async_interrupt_status(uint32_t pin_index);
/**
* @brief Register interrupt callback function for specific pin.
*
* This function register pin interrupt callback. It according to pin index
* getting irq number, and use irq_attach/irq_enable to enable it. Each 32 pin
* share one interrupt number.
*
* @param [in] pin_index defined pin macro in pinctrl.h.
* @param [in] handler callback function handler.
* @param [in] arg callback function param.
* @return SDRV_STATUS_OK or error code.
*/
status_t sdrv_gpio_register_interrupt_handler(
uint32_t pin_index, sdrv_gpio_interrupt_handler_t handler, void *arg);
/**
* @brief Unregister interrupt callback function for specific pin.
*
* This function unregister pin interrupt callback. If it is last pin for its
* group interrupt number, irq_disable/irq_detach will be called.
*
* @param [in] pin_index defined pin macro in pinctrl.h.
* @return SDRV_STATUS_OK or error code.
*/
status_t sdrv_gpio_unregister_interrupt_handler(uint32_t pin_index);
/**
* @brief Set gpio interrupt share with other core.
*
* This function set gpio interrupt with core sp or sx. Pin interrupt default
* send to sf only, if you want use other core handler this interrupt, you must
* share interrupt with core.
*
* @param [in] pin_index defined pin macro in pinctrl.h.
* @param [in] mask OR'ed value defined in gpio_interrupt_share_e.
* @return SDRV_STATUS_OK or error code.
*/
status_t sdrv_gpio_interrupt_share_with(uint32_t pin_index, uint32_t mask);
/**
* @brief Cancel gpio interrupt share with other core.
*
* This function cancel gpio interrupt with core sp or sx.
*
* @param [in] pin_index defined pin macro in pinctrl.h.
* @param [in] mask OR'ed value defined in gpio_interrupt_share_e.
* @return SDRV_STATUS_OK or error code.
*/
status_t sdrv_gpio_cancel_interrupt_share_with(uint32_t pin_index,
uint32_t mask);
/**
* @brief Config gpio direction.
*
* This function config gpio as input or output.
*
* @param [in] gpio_ctrl gpio instance.
* @param [in] pin_index defined pin macro in pinctrl.h.
* @param [in] dir direction defined as gpio_direction_e.
* @return SDRV_STATUS_OK or error code.
*/
status_t sdrv_gpio_ctrl_set_pin_direction(sdrv_gpio_t *gpio_ctrl,
uint32_t pin_index,
gpio_direction_e dir);
/**
* @brief Config gpio output level.
*
* This function config gpio output high or low level.
*
* @param [in] gpio_ctrl gpio instance.
* @param [in] pin_index defined pin macro in pinctrl.h.
* @param [in] level true represents high, false represents low.
* @return SDRV_STATUS_OK or error code.
*/
status_t sdrv_gpio_ctrl_set_pin_output_level(sdrv_gpio_t *gpio_ctrl,
uint32_t pin_index, bool level);
/**
* @brief Toggle specific pin output level.
*
* This function toggle output level for specific pin, for example, if pin
* output high at first, after call this function, it will output low.
*
* @param [in] gpio_ctrl gpio instance.
* @param [in] pin_index defined pin macro in pinctrl.h.
* @return SDRV_STATUS_OK or error code.
*/
status_t sdrv_gpio_ctrl_toggle_pin_output_level(sdrv_gpio_t *gpio_ctrl,
uint32_t pin_index);
/**
* @brief Get specific pin input level.
*
* This function read pin input level.
*
* @param [in] gpio_ctrl gpio instance.
* @param [in] pin_index defined pin macro in pinctrl.h.
* @return true represents high level, false represents low level.
*/
bool sdrv_gpio_ctrl_read_pin_input_level(sdrv_gpio_t *gpio_ctrl,
uint32_t pin_index);
/**
* @brief Get gpio output level.
*
* This function read gpio output data register for specific pin.
*
* @param [in] gpio_ctrl gpio instance.
* @param [in] pin_index defined pin macro in pinctrl.h.
* @return true represents high configed, false represents low configed.
*/
bool sdrv_gpio_ctrl_get_pin_output_level(sdrv_gpio_t *gpio_ctrl,
uint32_t pin_index);
/**
* @brief Config interrupt type for specific pin.
*
* This function config pin as interrupt type, after configuration, you also
* need call sdrv_gpio_pin_interrupt_enable for starting receive interrupt.
*
* @param [in] gpio_ctrl gpio instance.
* @param [in] pin_index defined pin macro in pinctrl.h.
* @param [in] intr interrupt type defined in gpio_interrupt_e.
* @return SDRV_STATUS_OK or error code.
*/
status_t sdrv_gpio_ctrl_set_pin_interrupt(sdrv_gpio_t *gpio_ctrl,
uint32_t pin_index,
gpio_interrupt_e intr);
/**
* @brief Enable interrupt for specific pin.
*
* This function config pin interrupt enable register and unmask pin interrupt
* status.
*
* @param [in] gpio_ctrl gpio instance.
* @param [in] pin_index defined pin macro in pinctrl.h.
* @return SDRV_STATUS_OK or error code.
*/
status_t sdrv_gpio_ctrl_pin_interrupt_enable(sdrv_gpio_t *gpio_ctrl,
uint32_t pin_index);
/**
* @brief Disable interrupt for specific pin.
*
* This function config pin interrupt disable register and mask pin interrupt
* status.
*
* @param [in] gpio_ctrl gpio instance.
* @param [in] pin_index defined pin macro in pinctrl.h.
* @return SDRV_STATUS_OK or error code.
*/
status_t sdrv_gpio_ctrl_pin_interrupt_disable(sdrv_gpio_t *gpio_ctrl,
uint32_t pin_index);
/**
* @brief Get specific pin interrupt status.
*
* This function read pin interrupt status register.
*
* @param [in] gpio_ctrl gpio instance.
* @param [in] pin_index defined pin macro in pinctrl.h.
* @return true represents interrupt status is set, false represents no
*/
bool sdrv_gpio_ctrl_pin_interrupt_status(sdrv_gpio_t *gpio_ctrl,
uint32_t pin_index);
/**
* @brief Clear specific pin interrupt status.
*
* This function clear pin interrupt status. Only edge interrupt type need clear
* status, level type should inactive source level.
*
* @param [in] gpio_ctrl gpio instance.
* @param [in] pin_index defined pin macro in pinctrl.h.
* @return SDRV_STATUS_OK or error code.
*/
status_t sdrv_gpio_ctrl_clear_pin_interrupt_status(sdrv_gpio_t *gpio_ctrl,
uint32_t pin_index);
/**
* @brief Config asynchronous interrupt type for specific pin.
*
* This function config pin as interrupt type using asynchronous way. Compare to
* normal interrupt way, asynchronous interrupt can also receive interrupt
* without clock, so it can be work in lowpower mode.
*
* @param [in] gpio_ctrl gpio instance.
* @param [in] pin_index defined pin macro in pinctrl.h.
* @param [in] intr interrupt type defined in gpio_interrupt_e.
* @return SDRV_STATUS_OK or error code.
*/
status_t sdrv_gpio_ctrl_set_pin_async_interrupt(sdrv_gpio_t *gpio_ctrl,
uint32_t pin_index,
gpio_interrupt_e intr);
/**
* @brief Enable asynchronous interrupt for specific pin.
*
* This function config pin interrupt enable register and unmask pin interrupt
* status.
*
* @param [in] gpio_ctrl gpio instance.
* @param [in] pin_index defined pin macro in pinctrl.h.
* @return SDRV_STATUS_OK or error code.
*/
status_t sdrv_gpio_ctrl_pin_async_interrupt_enable(sdrv_gpio_t *gpio_ctrl,
uint32_t pin_index);
/**
* @brief Disable asynchronous interrupt for specific pin.
*
* This function config pin interrupt disable register and mask pin interrupt
* status.
*
* @param [in] gpio_ctrl gpio instance.
* @param [in] pin_index defined pin macro in pinctrl.h.
* @return SDRV_STATUS_OK or error code.
*/
status_t sdrv_gpio_ctrl_pin_async_interrupt_disable(sdrv_gpio_t *gpio_ctrl,
uint32_t pin_index);
/**
* @brief Get specific pin asynchronous interrupt status.
*
* This function read pin asynchronous interrupt status register.
*
* @param [in] gpio_ctrl gpio instance.
* @param [in] pin_index defined pin macro in pinctrl.h.
* @return true represents interrupt status is set, false represents no
* interrupt status.
*/
bool sdrv_gpio_ctrl_pin_async_interrupt_status(sdrv_gpio_t *gpio_ctrl,
uint32_t pin_index);
/**
* @brief Clear specific pin asynchronous interrupt status.
*
* This function clear pin asynchronous interrupt status. Only edge interrupt
* type need clear status, level type should inactive source level.
*
* @param [in] gpio_ctrl gpio instance.
* @param [in] pin_index defined pin macro in pinctrl.h.
* @return SDRV_STATUS_OK or error code.
*/
status_t sdrv_gpio_ctrl_clear_pin_async_interrupt_status(sdrv_gpio_t *gpio_ctrl,
uint32_t pin_index);
#endif /* SDRV_GPIO_H_ */