blob: b477b796f5e9c6a288eb986a5e1ac88f78f8660e [file] [log] [blame]
Pankaj Guptab4806422020-12-09 14:02:39 +05301/*
2 * Copyright 2021 NXP
3 *
4 * SPDX-License-Identifier: BSD-3-Clause
5 *
6 */
7
8#include <common/debug.h>
9#include <lib/mmio.h>
10#include <nxp_gpio.h>
11
12static gpio_init_info_t *gpio_init_info;
13
14void gpio_init(gpio_init_info_t *gpio_init_data)
15{
16 gpio_init_info = gpio_init_data;
17}
18
19/* This function set GPIO pin for raising POVDD. */
20int set_gpio_bit(uint32_t *gpio_base_addr,
21 uint32_t bit_num)
22{
23 uint32_t val = 0U;
24 uint32_t *gpdir = NULL;
25 uint32_t *gpdat = NULL;
26
27 if (gpio_init_info == NULL) {
28 ERROR("GPIO is not initialized.\n");
29 return GPIO_FAILURE;
30 }
Antonin Godard3fc37572024-05-10 09:05:16 -070031 /* Divide by 4 since we're operating on 32-bit pointer addresses. */
32 gpdir = gpio_base_addr + (GPDIR_REG_OFFSET >> 2);
Pankaj Guptab4806422020-12-09 14:02:39 +053033 gpdat = gpio_base_addr + (GPDAT_REG_OFFSET >> 2);
34
35 /*
36 * Set the corresponding bit in direction register
37 * to configure the GPIO as output.
38 */
39 val = gpio_read32(gpdir);
40 val = val | bit_num;
41 gpio_write32(gpdir, val);
42
43 /* Set the corresponding bit in GPIO data register */
44 val = gpio_read32(gpdat);
45 val = val | bit_num;
46 gpio_write32(gpdat, val);
47
48 val = gpio_read32(gpdat);
49
50 if ((val & bit_num) == 0U) {
51 return GPIO_FAILURE;
52 }
53
54 return GPIO_SUCCESS;
55}
56
57/* This function reset GPIO pin set for raising POVDD. */
58int clr_gpio_bit(uint32_t *gpio_base_addr, uint32_t bit_num)
59{
60 uint32_t val = 0U;
61 uint32_t *gpdir = NULL;
62 uint32_t *gpdat = NULL;
63
64
65 if (gpio_init_info == NULL) {
66 ERROR("GPIO is not initialized.\n");
67 return GPIO_FAILURE;
68 }
69
Antonin Godard3fc37572024-05-10 09:05:16 -070070 /* Divide by 4 since we're operating on 32-bit pointer addresses. */
71 gpdir = gpio_base_addr + (GPDIR_REG_OFFSET >> 2);
72 gpdat = gpio_base_addr + (GPDAT_REG_OFFSET >> 2);
Pankaj Guptab4806422020-12-09 14:02:39 +053073
74 /*
75 * Reset the corresponding bit in direction and data register
76 * to configure the GPIO as input.
77 */
78 val = gpio_read32(gpdat);
79 val = val & ~(bit_num);
80 gpio_write32(gpdat, val);
81
82 val = gpio_read32(gpdat);
83
84 val = gpio_read32(gpdir);
85 val = val & ~(bit_num);
86 gpio_write32(gpdir, val);
87
88 val = gpio_read32(gpdat);
89
90 if ((val & bit_num) != 0U) {
91 return GPIO_FAILURE;
92 }
93
94 return GPIO_SUCCESS;
95}
96
97uint32_t *select_gpio_n_bitnum(uint32_t povdd_gpio, uint32_t *bit_num)
98{
99 uint32_t *ret_gpio;
100 uint32_t povdd_gpio_val = 0U;
101 uint32_t gpio_num = 0U;
102
103 if (gpio_init_info == NULL) {
104 ERROR("GPIO is not initialized.\n");
105 }
106 /*
107 * Subtract 1 from fuse_hdr povdd_gpio value as
108 * for 0x1 value, bit 0 is to be set
109 * for 0x20 value i.e 32, bit 31 i.e. 0x1f is to be set.
110 * 0x1f - 0x00 : GPIO_1
111 * 0x3f - 0x20 : GPIO_2
112 * 0x5f - 0x40 : GPIO_3
113 * 0x7f - 0x60 : GPIO_4
114 */
115 povdd_gpio_val = (povdd_gpio - 1U) & GPIO_SEL_MASK;
116
117 /* Right shift by 5 to divide by 32 */
118 gpio_num = povdd_gpio_val >> GPIO_ID_BASE_ADDR_SHIFT;
119 *bit_num = 1U << (GPIO_BITS_PER_BASE_REG
120 - (povdd_gpio_val & GPIO_BIT_MASK)
121 - 1U);
122
123 switch (gpio_num) {
124 case GPIO_0:
125 ret_gpio = (uint32_t *) gpio_init_info->gpio1_base_addr;
126 break;
127 case GPIO_1:
128 ret_gpio = (uint32_t *) gpio_init_info->gpio2_base_addr;
129 break;
130 case GPIO_2:
131 ret_gpio = (uint32_t *) gpio_init_info->gpio3_base_addr;
132 break;
133 case GPIO_3:
134 ret_gpio = (uint32_t *) gpio_init_info->gpio4_base_addr;
135 break;
136 default:
137 ret_gpio = NULL;
138 }
139
140 if (ret_gpio == NULL) {
141 INFO("GPIO_NUM = %d doesn't exist.\n", gpio_num);
142 }
143
144 return ret_gpio;
145}