• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /* SPDX-License-Identifier: GPL-2.0-only */
2 
3 #include <device/mmio.h>
4 #include <gpio.h>
5 #include <assert.h>
6 #include <soc/spi.h>
7 
8 enum {
9 	EN_OFFSET = 0x60,
10 	SEL_OFFSET = 0x80,
11 	EH_RSEL_OFFSET = 0xF0,
12 	GPIO_DRV0_OFFSET = 0xA0,
13 	GPIO_DRV1_OFFSET = 0xB0,
14 };
15 
gpio_set_pull_pupd(gpio_t gpio,enum pull_enable enable,enum pull_select select)16 static void gpio_set_pull_pupd(gpio_t gpio, enum pull_enable enable,
17 			       enum pull_select select)
18 {
19 	void *reg = GPIO_TO_IOCFG_BASE(gpio.base) + gpio.offset;
20 	int bit = gpio.bit;
21 
22 	if (enable == GPIO_PULL_ENABLE) {
23 		if (select == GPIO_PULL_DOWN)
24 			setbits32(reg, 1 << (bit + 2));
25 		else
26 			clrbits32(reg, 1 << (bit + 2));
27 	}
28 
29 	if (enable == GPIO_PULL_ENABLE)
30 		clrsetbits32(reg, 3 << bit, 1 << bit);
31 	else
32 		clrbits32(reg, 3 << bit);
33 }
34 
gpio_set_pull_en_sel(gpio_t gpio,enum pull_enable enable,enum pull_select select)35 static void gpio_set_pull_en_sel(gpio_t gpio, enum pull_enable enable,
36 				 enum pull_select select)
37 {
38 	void *reg = GPIO_TO_IOCFG_BASE(gpio.base) + gpio.offset;
39 	int bit = gpio.bit;
40 
41 	if (enable == GPIO_PULL_ENABLE) {
42 		if (select == GPIO_PULL_DOWN)
43 			clrbits32(reg + SEL_OFFSET, 1 << bit);
44 		else
45 			setbits32(reg + SEL_OFFSET, 1 << bit);
46 	}
47 
48 	if (enable == GPIO_PULL_ENABLE)
49 		setbits32(reg + EN_OFFSET, 1 << bit);
50 	else
51 		clrbits32(reg + EN_OFFSET, 1 << bit);
52 }
53 
gpio_set_pull(gpio_t gpio,enum pull_enable enable,enum pull_select select)54 void gpio_set_pull(gpio_t gpio, enum pull_enable enable,
55 		   enum pull_select select)
56 {
57 	if (gpio.flag)
58 		gpio_set_pull_pupd(gpio, enable, select);
59 	else
60 		gpio_set_pull_en_sel(gpio, enable, select);
61 }
62 
63 enum {
64 	EH_VAL = 0x0,
65 	RSEL_VAL = 0x3,
66 	EH_MASK = 0x7,
67 	RSEL_MASK = 0x3,
68 	SCL0_EH = 19,
69 	SCL0_RSEL = 15,
70 	SDA0_EH = 9,
71 	SDA0_RSEL = 5,
72 	SCL1_EH = 22,
73 	SCL1_RSEL = 17,
74 	SDA1_EH = 12,
75 	SDA1_RSEL = 7,
76 	SCL2_EH = 24,
77 	SCL2_RSEL = 20,
78 	SDA2_EH = 14,
79 	SDA2_RSEL = 10,
80 	SCL3_EH = 12,
81 	SCL3_RSEL = 10,
82 	SDA3_EH = 7,
83 	SDA3_RSEL = 5,
84 	SCL4_EH = 27,
85 	SCL4_RSEL = 22,
86 	SDA4_EH = 17,
87 	SDA4_RSEL = 12,
88 	SCL5_EH = 20,
89 	SCL5_RSEL = 18,
90 	SDA5_EH = 15,
91 	SDA5_RSEL = 13,
92 };
93 
94 #define I2C_EH_RSL_MASK(name) \
95 	(EH_MASK << name##_EH | RSEL_MASK << name##_RSEL)
96 
97 #define I2C_EH_RSL_VAL(name) \
98 	(EH_VAL << name##_EH | RSEL_VAL << name##_RSEL)
99 
gpio_set_i2c_eh_rsel(void)100 void gpio_set_i2c_eh_rsel(void)
101 {
102 	clrsetbits32((void *)IOCFG_RB_BASE + EH_RSEL_OFFSET,
103 		I2C_EH_RSL_MASK(SCL0) | I2C_EH_RSL_MASK(SDA0) |
104 		I2C_EH_RSL_MASK(SCL1) | I2C_EH_RSL_MASK(SDA1),
105 		I2C_EH_RSL_VAL(SCL0) | I2C_EH_RSL_VAL(SDA0) |
106 		I2C_EH_RSL_VAL(SCL1) | I2C_EH_RSL_VAL(SDA1));
107 
108 	clrsetbits32((void *)IOCFG_RM_BASE + EH_RSEL_OFFSET,
109 		I2C_EH_RSL_MASK(SCL2) | I2C_EH_RSL_MASK(SDA2) |
110 		I2C_EH_RSL_MASK(SCL4) | I2C_EH_RSL_MASK(SDA4),
111 		I2C_EH_RSL_VAL(SCL2) | I2C_EH_RSL_VAL(SDA2) |
112 		I2C_EH_RSL_VAL(SCL4) | I2C_EH_RSL_VAL(SDA4));
113 
114 	clrsetbits32((void *)IOCFG_BL_BASE + EH_RSEL_OFFSET,
115 		I2C_EH_RSL_MASK(SCL3) | I2C_EH_RSL_MASK(SDA3),
116 		I2C_EH_RSL_VAL(SCL3) | I2C_EH_RSL_VAL(SDA3));
117 
118 	clrsetbits32((void *)IOCFG_LB_BASE + EH_RSEL_OFFSET,
119 		I2C_EH_RSL_MASK(SCL5) | I2C_EH_RSL_MASK(SDA5),
120 		I2C_EH_RSL_VAL(SCL5) | I2C_EH_RSL_VAL(SDA5));
121 }
122 
gpio_set_spi_driving(unsigned int bus,enum spi_pad_mask pad_select,unsigned int milliamps)123 void gpio_set_spi_driving(unsigned int bus, enum spi_pad_mask pad_select,
124 			  unsigned int milliamps)
125 {
126 	void *reg = NULL;
127 	unsigned int reg_val = milliamps / 2 - 1, offset = 0;
128 
129 	assert(bus < SPI_BUS_NUMBER);
130 	assert(milliamps >= 2 && milliamps <= 16);
131 	assert(pad_select <= SPI_PAD1_MASK);
132 
133 	switch (bus) {
134 	case 0:
135 		reg = (void *)(IOCFG_RB_BASE + GPIO_DRV1_OFFSET);
136 		offset = 0;
137 		break;
138 	case 1:
139 		if (pad_select == SPI_PAD0_MASK) {
140 			reg = (void *)(IOCFG_LM_BASE + GPIO_DRV0_OFFSET);
141 			offset = 0;
142 		} else if (pad_select == SPI_PAD1_MASK) {
143 			clrsetbits32((void *)IOCFG_RM_BASE +
144 					GPIO_DRV0_OFFSET, 0xf | 0xf << 20,
145 					reg_val | reg_val << 20);
146 			clrsetbits32((void *)IOCFG_RM_BASE +
147 					GPIO_DRV1_OFFSET, 0xf << 16,
148 					reg_val << 16);
149 			return;
150 		}
151 		break;
152 	case 2:
153 		clrsetbits32((void *)IOCFG_RM_BASE + GPIO_DRV0_OFFSET,
154 				0xf << 8 | 0xf << 12,
155 				reg_val << 8 | reg_val << 12);
156 		return;
157 	case 3:
158 		reg = (void *)(IOCFG_LM_BASE + GPIO_DRV0_OFFSET);
159 		offset = 16;
160 		break;
161 	case 4:
162 		reg = (void *)(IOCFG_LM_BASE + GPIO_DRV0_OFFSET);
163 		offset = 12;
164 		break;
165 	case 5:
166 		reg = (void *)(IOCFG_LM_BASE + GPIO_DRV0_OFFSET);
167 		offset = 8;
168 		break;
169 	}
170 
171 	clrsetbits32(reg, 0xf << offset, reg_val << offset);
172 }
173