Lines Matching +full:conf +full:- +full:rst

1 /*-
2 * SPDX-License-Identifier: BSD-2-Clause
277 {"allwinner,sun4i-a10-pinctrl", (uintptr_t)&a10_gpio_conf},
280 {"allwinner,sun5i-a13-pinctrl", (uintptr_t)&a13_gpio_conf},
283 {"allwinner,sun7i-a20-pinctrl", (uintptr_t)&a20_gpio_conf},
286 {"allwinner,sun6i-a31-pinctrl", (uintptr_t)&a31_gpio_conf},
289 {"allwinner,sun6i-a31s-pinctrl", (uintptr_t)&a31s_gpio_conf},
292 {"allwinner,sun6i-a31-r-pinctrl", (uintptr_t)&a31_r_gpio_conf},
295 {"allwinner,sun6i-a33-pinctrl", (uintptr_t)&a33_gpio_conf},
298 {"allwinner,sun8i-a83t-pinctrl", (uintptr_t)&a83t_gpio_conf},
299 {"allwinner,sun8i-a83t-r-pinctrl", (uintptr_t)&a83t_r_gpio_conf},
302 {"allwinner,sun8i-h3-pinctrl", (uintptr_t)&h3_gpio_conf},
303 {"allwinner,sun50i-h5-pinctrl", (uintptr_t)&h3_gpio_conf},
304 {"allwinner,sun8i-h3-r-pinctrl", (uintptr_t)&h3_r_gpio_conf},
307 {"allwinner,sun50i-a64-pinctrl", (uintptr_t)&a64_gpio_conf},
308 {"allwinner,sun50i-a64-r-pinctrl", (uintptr_t)&a64_r_gpio_conf},
311 {"allwinner,sun20i-d1-pinctrl", (uintptr_t)&d1_gpio_conf},
314 {"allwinner,sun50i-h6-pinctrl", (uintptr_t)&h6_gpio_conf},
315 {"allwinner,sun50i-h6-r-pinctrl", (uintptr_t)&h6_r_gpio_conf},
349 struct aw_gpio_conf *conf; member
359 { -1, 0, 0 }
362 #define AW_GPIO_LOCK(_sc) mtx_lock_spin(&(_sc)->sc_mtx)
363 #define AW_GPIO_UNLOCK(_sc) mtx_unlock_spin(&(_sc)->sc_mtx)
364 #define AW_GPIO_LOCK_ASSERT(_sc) mtx_assert(&(_sc)->sc_mtx, MA_OWNED)
366 #define AW_GPIO_GP_BASE(_sc, _bank) ((_sc)->conf->bank_size * (_bank))
375 (AW_GPIO_GP_BASE(_sc, _bank) + (_sc)->conf->pul_offset + ((_idx) << 2))
407 bus_write_4((_sc)->sc_res[AW_GPIO_MEMRES], _off, _val)
409 bus_read_4((_sc)->sc_res[AW_GPIO_MEMRES], _off)
419 if (pin > sc->conf->padconf->npins) in aw_gpio_get_function()
421 bank = sc->conf->padconf->pins[pin].port; in aw_gpio_get_function()
422 pin = sc->conf->padconf->pins[pin].pin; in aw_gpio_get_function()
436 if (sc->conf->padconf->pins[pin].functions[f] == NULL) in aw_gpio_set_function()
442 bank = sc->conf->padconf->pins[pin].port; in aw_gpio_set_function()
443 pin = sc->conf->padconf->pins[pin].pin; in aw_gpio_set_function()
462 bank = sc->conf->padconf->pins[pin].port; in aw_gpio_get_pud()
463 pin = sc->conf->padconf->pins[pin].pin; in aw_gpio_get_pud()
482 bank = sc->conf->padconf->pins[pin].port; in aw_gpio_set_pud()
483 pin = sc->conf->padconf->pins[pin].pin; in aw_gpio_set_pud()
500 bank = sc->conf->padconf->pins[pin].port; in aw_gpio_get_drv()
501 pin = sc->conf->padconf->pins[pin].pin; in aw_gpio_get_drv()
502 offset = (pin << sc->conf->drv_pin_shift) & 0x1F; in aw_gpio_get_drv()
503 idx = (pin << sc->conf->drv_pin_shift) >> 5; in aw_gpio_get_drv()
521 bank = sc->conf->padconf->pins[pin].port; in aw_gpio_set_drv()
522 pin = sc->conf->padconf->pins[pin].pin; in aw_gpio_set_drv()
523 offset = (pin << sc->conf->drv_pin_shift) & 0x1F; in aw_gpio_set_drv()
524 idx = (pin << sc->conf->drv_pin_shift) >> 5; in aw_gpio_set_drv()
541 if (pin > sc->conf->padconf->npins) in aw_gpio_pin_configure()
568 /* Manage Pull-up/pull-down. */ in aw_gpio_pin_configure()
586 return (sc->sc_busdev); in aw_gpio_get_bus()
596 *maxpin = sc->conf->padconf->npins - 1; in aw_gpio_pin_max()
606 if (pin >= sc->conf->padconf->npins) in aw_gpio_pin_getcaps()
610 if (sc->conf->padconf->pins[pin].eint_func != 0) in aw_gpio_pin_getcaps()
624 if (pin >= sc->conf->padconf->npins) in aw_gpio_pin_getflags()
664 if (pin >= sc->conf->padconf->npins) in aw_gpio_pin_getname()
667 snprintf(name, GPIOMAXNAME - 1, "%s", in aw_gpio_pin_getname()
668 sc->conf->padconf->pins[pin].name); in aw_gpio_pin_getname()
669 name[GPIOMAXNAME - 1] = '\0'; in aw_gpio_pin_getname()
681 if (pin > sc->conf->padconf->npins) in aw_gpio_pin_setflags()
699 if (pin > sc->conf->padconf->npins) in aw_gpio_pin_set_locked()
702 bank = sc->conf->padconf->pins[pin].port; in aw_gpio_pin_set_locked()
703 pin = sc->conf->padconf->pins[pin].pin; in aw_gpio_pin_set_locked()
740 if (pin > sc->conf->padconf->npins) in aw_gpio_pin_get_locked()
744 if (func == sc->conf->padconf->pins[pin].eint_func) { /* "pl_eintX */ in aw_gpio_pin_get_locked()
750 bank = sc->conf->padconf->pins[pin].port; in aw_gpio_pin_get_locked()
751 pin = sc->conf->padconf->pins[pin].pin; in aw_gpio_pin_get_locked()
756 if (func == sc->conf->padconf->pins[pin].eint_func) in aw_gpio_pin_get_locked()
768 (void **)&function) != -1) in aw_gpio_parse_function()
771 (void **)&function) != -1) in aw_gpio_parse_function()
799 if (OF_getencprop(node, "pull", &bias, sizeof(bias)) != -1) in aw_gpio_parse_bias()
801 if (OF_getencprop(node, "allwinner,pull", &bias, sizeof(bias)) != -1) in aw_gpio_parse_bias()
803 if (OF_hasprop(node, "bias-disable")) in aw_gpio_parse_bias()
805 if (OF_hasprop(node, "bias-pull-up")) in aw_gpio_parse_bias()
807 if (OF_hasprop(node, "bias-pull-down")) in aw_gpio_parse_bias()
818 if (OF_getencprop(node, "drive", drive, sizeof(*drive)) != -1) in aw_gpio_parse_drive_strength()
820 if (OF_getencprop(node, "allwinner,drive", drive, sizeof(*drive)) != -1) in aw_gpio_parse_drive_strength()
822 if (OF_getencprop(node, "drive-strength", &drive_str, in aw_gpio_parse_drive_strength()
823 sizeof(drive_str)) != -1) { in aw_gpio_parse_drive_strength()
824 *drive = (drive_str / 10) - 1; in aw_gpio_parse_drive_strength()
853 if (pin > sc->conf->padconf->npins) in aw_gpio_pin_toggle()
856 bank = sc->conf->padconf->pins[pin].port; in aw_gpio_pin_toggle()
857 pin = sc->conf->padconf->pins[pin].pin; in aw_gpio_pin_toggle()
879 if (first_pin > sc->conf->padconf->npins) in aw_gpio_pin_access_32()
886 * (desired); we need to do a read-modify-write on a single register. in aw_gpio_pin_access_32()
888 bank = sc->conf->padconf->pins[first_pin].port; in aw_gpio_pin_access_32()
889 pin = sc->conf->padconf->pins[first_pin].pin; in aw_gpio_pin_access_32()
915 if (first_pin > sc->conf->padconf->npins) in aw_gpio_pin_config_32()
918 if (sc->conf->padconf->pins[first_pin].pin != 0) in aw_gpio_pin_config_32()
946 /* The GPIO pins are mapped as: <gpio-phandle bank pin flags>. */ in aw_gpio_map_gpios()
947 for (i = 0; i < sc->conf->padconf->npins; i++) in aw_gpio_map_gpios()
948 if (sc->conf->padconf->pins[i].port == gpios[0] && in aw_gpio_map_gpios()
949 sc->conf->padconf->pins[i].pin == gpios[1]) { in aw_gpio_map_gpios()
953 *flags = gpios[gcells - 1]; in aw_gpio_map_gpios()
963 for (i = 0; i < sc->conf->padconf->npins; i++) in aw_find_pinnum_by_name()
964 if (!strcmp(pinname, sc->conf->padconf->pins[i].name)) in aw_find_pinnum_by_name()
967 return (-1); in aw_find_pinnum_by_name()
976 if (sc->conf->padconf->pins[pin].functions[i] && in aw_find_pin_func()
977 !strcmp(func, sc->conf->padconf->pins[pin].functions[i])) in aw_find_pin_func()
980 return (-1); in aw_find_pin_func()
1018 if (pin_num == -1) { in aw_fdt_configure_pins()
1023 if (pin_func == -1) { in aw_fdt_configure_pins()
1054 nbanks = strlen(sc->conf->banks); in aw_gpio_enable_bank_supply()
1056 snprintf(bank_reg_name, sizeof(bank_reg_name), "vcc-p%c-supply", in aw_gpio_enable_bank_supply()
1057 sc->conf->banks[i]); in aw_gpio_enable_bank_supply()
1059 if (regulator_get_by_ofw_property(sc->sc_dev, 0, bank_reg_name, &vcc_supply) == 0) { in aw_gpio_enable_bank_supply()
1061 device_printf(sc->sc_dev, in aw_gpio_enable_bank_supply()
1063 sc->conf->banks[i]); in aw_gpio_enable_bank_supply()
1065 device_printf(sc->sc_dev, in aw_gpio_enable_bank_supply()
1067 sc->conf->banks[i]); in aw_gpio_enable_bank_supply()
1080 if (ofw_bus_search_compatible(dev, compat_data)->ocd_data == 0) in aw_gpio_probe()
1095 hwreset_t rst = NULL; in aw_gpio_attach() local
1099 sc->sc_dev = dev; in aw_gpio_attach()
1101 mtx_init(&sc->sc_mtx, "aw gpio", "gpio", MTX_SPIN); in aw_gpio_attach()
1103 if (bus_alloc_resources(dev, aw_gpio_res_spec, sc->sc_res) != 0) { in aw_gpio_attach()
1108 if (bus_setup_intr(dev, sc->sc_res[AW_GPIO_IRQRES], in aw_gpio_attach()
1110 &sc->sc_intrhand)) { in aw_gpio_attach()
1116 gpio = ofw_bus_get_node(sc->sc_dev); in aw_gpio_attach()
1117 if (!OF_hasprop(gpio, "gpio-controller")) in aw_gpio_attach()
1122 sc->conf = (struct aw_gpio_conf *)ofw_bus_search_compatible(dev, in aw_gpio_attach()
1123 compat_data)->ocd_data; in aw_gpio_attach()
1125 if (hwreset_get_by_ofw_idx(dev, 0, 0, &rst) == 0) { in aw_gpio_attach()
1126 error = hwreset_deassert(rst); in aw_gpio_attach()
1128 device_printf(dev, "cannot de-assert reset\n"); in aw_gpio_attach()
1133 TAILQ_INIT(&sc->clk_list); in aw_gpio_attach()
1145 clkp->clk = clk; in aw_gpio_attach()
1146 TAILQ_INSERT_TAIL(&sc->clk_list, clkp, next); in aw_gpio_attach()
1157 sc->sc_busdev = gpiobus_attach_bus(dev); in aw_gpio_attach()
1158 if (sc->sc_busdev == NULL) in aw_gpio_attach()
1174 if (sc->sc_irq_res) in aw_gpio_attach()
1175 bus_release_resource(dev, SYS_RES_IRQ, 0, sc->sc_irq_res); in aw_gpio_attach()
1176 if (sc->sc_mem_res) in aw_gpio_attach()
1177 bus_release_resource(dev, SYS_RES_MEMORY, 0, sc->sc_mem_res); in aw_gpio_attach()
1178 mtx_destroy(&sc->sc_mtx); in aw_gpio_attach()
1181 TAILQ_FOREACH_SAFE(clkp, &sc->clk_list, next, clkp_tmp) { in aw_gpio_attach()
1182 err = clk_disable(clkp->clk); in aw_gpio_attach()
1185 clk_get_name(clkp->clk)); in aw_gpio_attach()
1186 err = clk_release(clkp->clk); in aw_gpio_attach()
1189 clk_get_name(clkp->clk)); in aw_gpio_attach()
1190 TAILQ_REMOVE(&sc->clk_list, clkp, next); in aw_gpio_attach()
1195 if (rst) { in aw_gpio_attach()
1196 hwreset_assert(rst); in aw_gpio_attach()
1197 hwreset_release(rst); in aw_gpio_attach()
1221 for (irq = 0; irq < sc->nirqs; irq++) { in aw_gpio_intr()
1222 if (!sc->gpio_pic_irqsrc[irq].enabled) in aw_gpio_intr()
1225 reg = AW_GPIO_READ(sc, AW_GPIO_GP_INT_STA(sc->gpio_pic_irqsrc[irq].bank)); in aw_gpio_intr()
1226 if (!(reg & (1 << sc->gpio_pic_irqsrc[irq].intnum))) in aw_gpio_intr()
1229 isrc = &sc->gpio_pic_irqsrc[irq].isrc; in aw_gpio_intr()
1230 if (intr_isrc_dispatch(isrc, curthread->td_intr_frame) != 0) { in aw_gpio_intr()
1232 aw_gpio_pic_post_filter(sc->sc_dev, isrc); in aw_gpio_intr()
1233 device_printf(sc->sc_dev, "Stray irq %u disabled\n", irq); in aw_gpio_intr()
1251 name = device_get_nameunit(sc->sc_dev); in aw_gpio_register_isrcs()
1253 for (nirqs = 0, pin = 0; pin < sc->conf->padconf->npins; pin++) { in aw_gpio_register_isrcs()
1254 if (sc->conf->padconf->pins[pin].eint_func == 0) in aw_gpio_register_isrcs()
1260 sc->gpio_pic_irqsrc = malloc(sizeof(*sc->gpio_pic_irqsrc) * nirqs, in aw_gpio_register_isrcs()
1262 for (nirqs = 0, pin = 0; pin < sc->conf->padconf->npins; pin++) { in aw_gpio_register_isrcs()
1263 if (sc->conf->padconf->pins[pin].eint_func == 0) in aw_gpio_register_isrcs()
1266 sc->gpio_pic_irqsrc[nirqs].pin = pin; in aw_gpio_register_isrcs()
1267 sc->gpio_pic_irqsrc[nirqs].bank = sc->conf->padconf->pins[pin].eint_bank; in aw_gpio_register_isrcs()
1268 sc->gpio_pic_irqsrc[nirqs].intnum = sc->conf->padconf->pins[pin].eint_num; in aw_gpio_register_isrcs()
1269 sc->gpio_pic_irqsrc[nirqs].intfunc = sc->conf->padconf->pins[pin].eint_func; in aw_gpio_register_isrcs()
1270 sc->gpio_pic_irqsrc[nirqs].irq = nirqs; in aw_gpio_register_isrcs()
1271 sc->gpio_pic_irqsrc[nirqs].mode = GPIO_INTR_CONFORM; in aw_gpio_register_isrcs()
1273 err = intr_isrc_register(&sc->gpio_pic_irqsrc[nirqs].isrc, in aw_gpio_register_isrcs()
1274 sc->sc_dev, 0, "%s,%s", name, in aw_gpio_register_isrcs()
1275 sc->conf->padconf->pins[pin].functions[sc->conf->padconf->pins[pin].eint_func]); in aw_gpio_register_isrcs()
1277 device_printf(sc->sc_dev, "intr_isrs_register failed for irq %d\n", nirqs); in aw_gpio_register_isrcs()
1283 sc->nirqs = nirqs; in aw_gpio_register_isrcs()
1295 irq = ((struct gpio_irqsrc *)isrc)->irq; in aw_gpio_pic_disable_intr_locked()
1296 reg = AW_GPIO_READ(sc, AW_GPIO_GP_INT_CTL(sc->gpio_pic_irqsrc[irq].bank)); in aw_gpio_pic_disable_intr_locked()
1297 reg &= ~(1 << sc->gpio_pic_irqsrc[irq].intnum); in aw_gpio_pic_disable_intr_locked()
1298 AW_GPIO_WRITE(sc, AW_GPIO_GP_INT_CTL(sc->gpio_pic_irqsrc[irq].bank), reg); in aw_gpio_pic_disable_intr_locked()
1300 sc->gpio_pic_irqsrc[irq].enabled = false; in aw_gpio_pic_disable_intr_locked()
1323 irq = ((struct gpio_irqsrc *)isrc)->irq; in aw_gpio_pic_enable_intr()
1325 reg = AW_GPIO_READ(sc, AW_GPIO_GP_INT_CTL(sc->gpio_pic_irqsrc[irq].bank)); in aw_gpio_pic_enable_intr()
1326 reg |= 1 << sc->gpio_pic_irqsrc[irq].intnum; in aw_gpio_pic_enable_intr()
1327 AW_GPIO_WRITE(sc, AW_GPIO_GP_INT_CTL(sc->gpio_pic_irqsrc[irq].bank), reg); in aw_gpio_pic_enable_intr()
1330 sc->gpio_pic_irqsrc[irq].enabled = true; in aw_gpio_pic_enable_intr()
1340 irq = dag->gpio_pin_num; in aw_gpio_pic_map_gpio()
1342 for (pin = 0; pin < sc->nirqs; pin++) in aw_gpio_pic_map_gpio()
1343 if (sc->gpio_pic_irqsrc[pin].pin == irq) in aw_gpio_pic_map_gpio()
1345 if (pin == sc->nirqs) { in aw_gpio_pic_map_gpio()
1346 device_printf(sc->sc_dev, "Invalid interrupt number %u\n", irq); in aw_gpio_pic_map_gpio()
1350 switch (dag->gpio_intr_mode) { in aw_gpio_pic_map_gpio()
1358 device_printf(sc->sc_dev, "Unsupported interrupt mode 0x%8x\n", in aw_gpio_pic_map_gpio()
1359 dag->gpio_intr_mode); in aw_gpio_pic_map_gpio()
1365 *mode = dag->gpio_intr_mode; in aw_gpio_pic_map_gpio()
1379 switch (data->type) { in aw_gpio_pic_map_intr()
1390 *isrcp = &sc->gpio_pic_irqsrc[irq].isrc; in aw_gpio_pic_map_intr()
1407 switch (data->type) { in aw_gpio_pic_setup_intr()
1419 pinidx = (sc->gpio_pic_irqsrc[irq].intnum % 8) * 4; in aw_gpio_pic_setup_intr()
1441 sc->gpio_pic_irqsrc[irq].oldfunc = aw_gpio_get_function(sc, in aw_gpio_pic_setup_intr()
1442 sc->gpio_pic_irqsrc[irq].pin); in aw_gpio_pic_setup_intr()
1443 aw_gpio_set_function(sc, sc->gpio_pic_irqsrc[irq].pin, in aw_gpio_pic_setup_intr()
1444 sc->gpio_pic_irqsrc[irq].intfunc); in aw_gpio_pic_setup_intr()
1448 AW_GPIO_GP_INT_CFG(sc->gpio_pic_irqsrc[irq].bank, in aw_gpio_pic_setup_intr()
1449 sc->gpio_pic_irqsrc[irq].intnum)); in aw_gpio_pic_setup_intr()
1453 AW_GPIO_GP_INT_CFG(sc->gpio_pic_irqsrc[irq].bank, in aw_gpio_pic_setup_intr()
1454 sc->gpio_pic_irqsrc[irq].intnum), in aw_gpio_pic_setup_intr()
1474 aw_gpio_set_function(sc, gi->pin, gi->oldfunc); in aw_gpio_pic_teardown_intr()
1490 AW_GPIO_WRITE(sc, AW_GPIO_GP_INT_STA(gi->bank), 1 << gi->intnum); in aw_gpio_pic_post_filter()
1503 AW_GPIO_WRITE(sc, AW_GPIO_GP_INT_STA(gi->bank), 1 << gi->intnum); in aw_gpio_pic_post_ithread()