blob: 1ed8e8a04b213ce3cb2a4c2d96be5594f5fdd688 [file] [log] [blame]
Taniya Das017c5902021-05-07 10:20:19 +05301/* SPDX-License-Identifier: GPL-2.0-only */
2
3#include <assert.h>
4#include <device/mmio.h>
5#include <gpio.h>
6
7void gpio_configure(gpio_t gpio, uint32_t func, uint32_t pull,
8 uint32_t drive_str, uint32_t enable)
9{
10 struct tlmm_gpio *regs = (void *)(uintptr_t)gpio.addr;
11 uint32_t reg_val;
12
13 /* gpio pull only PULLNONE, PULLUP, KEEPER, PULLDOWN status */
14 assert(pull <= GPIO_PULL_UP);
15
16 reg_val = ((enable & GPIO_BMSK) << GPIO_CFG_OE_SHFT) |
17 ((drive_str & GPIO_CFG_DRV_BMSK) << GPIO_CFG_DRV_SHFT) |
18 ((func & GPIO_CFG_FUNC_BMSK) << GPIO_CFG_FUNC_SHFT) |
19 ((pull & GPIO_CFG_PULL_BMSK) << GPIO_CFG_PULL_SHFT);
20
21 write32(&regs->cfg, reg_val);
22}
23
24void gpio_set(gpio_t gpio, int value)
25{
26 struct tlmm_gpio *regs = (void *)(uintptr_t)gpio.addr;
27
28 write32(&regs->in_out, (!!value) << GPIO_IO_OUT_SHFT);
29}
30
31int gpio_get(gpio_t gpio)
32{
33 struct tlmm_gpio *regs = (void *)(uintptr_t)gpio.addr;
34
35 return ((read32(&regs->in_out) >> GPIO_IO_IN_SHFT) & GPIO_BMSK);
36}
37
38void gpio_input_pulldown(gpio_t gpio)
39{
40 gpio_configure(gpio, GPIO_FUNC_GPIO,
41 GPIO_PULL_DOWN, GPIO_2MA, GPIO_INPUT);
42}
43
44void gpio_input_pullup(gpio_t gpio)
45{
46 gpio_configure(gpio, GPIO_FUNC_GPIO,
47 GPIO_PULL_UP, GPIO_2MA, GPIO_INPUT);
48}
49
50void gpio_input(gpio_t gpio)
51{
52 gpio_configure(gpio, GPIO_FUNC_GPIO,
53 GPIO_NO_PULL, GPIO_2MA, GPIO_INPUT);
54}
55
56void gpio_output(gpio_t gpio, int value)
57{
58 gpio_set(gpio, value);
59 gpio_configure(gpio, GPIO_FUNC_GPIO,
60 GPIO_NO_PULL, GPIO_2MA, GPIO_OUTPUT);
61}
62
63void gpio_input_irq(gpio_t gpio, enum gpio_irq_type type, uint32_t pull)
64{
65 struct tlmm_gpio *regs = (void *)(uintptr_t)gpio.addr;
66
67 gpio_configure(gpio, GPIO_FUNC_GPIO,
68 pull, GPIO_2MA, GPIO_INPUT);
69
70 clrsetbits32(&regs->intr_cfg, GPIO_INTR_DECT_CTL_MASK <<
71 GPIO_INTR_DECT_CTL_SHFT, type << GPIO_INTR_DECT_CTL_SHFT);
72 clrsetbits32(&regs->intr_cfg, GPIO_INTR_STATUS_ENABLE
73 << GPIO_INTR_RAW_STATUS_EN_SHFT, GPIO_INTR_STATUS_ENABLE
74 << GPIO_INTR_RAW_STATUS_EN_SHFT);
75}
76
77int gpio_irq_status(gpio_t gpio)
78{
79 struct tlmm_gpio *regs = (void *)(uintptr_t)gpio.addr;
80
81 if (!(read32(&regs->intr_status) & GPIO_INTR_STATUS_MASK))
82 return GPIO_INTR_STATUS_DISABLE;
83
84 write32(&regs->intr_status, GPIO_INTR_STATUS_DISABLE);
85
86 return GPIO_INTR_STATUS_ENABLE;
87}