static int rk30_gpio_pin_set(device_t dev, uint32_t pin, unsigned int value) { struct rk30_gpio_softc *sc = device_get_softc(dev); uint32_t bank, offset, data; int i; for (i = 0; i < sc->sc_gpio_npins; i++) { if (sc->sc_gpio_pins[i].gp_pin == pin) break; } if (i >= sc->sc_gpio_npins) return (EINVAL); bank = pin / 32; pin = pin % 32; offset = 1 << pin; RK30_GPIO_LOCK(sc); data = RK30_GPIO_READ(sc, RK30_GPIO_SWPORT_DDR); data |= offset; RK30_GPIO_WRITE(sc, RK30_GPIO_SWPORT_DDR, data); data = RK30_GPIO_READ(sc, RK30_GPIO_SWPORT_DR); if (value) data |= offset; else data &= ~offset; RK30_GPIO_WRITE(sc, RK30_GPIO_SWPORT_DR, data); RK30_GPIO_UNLOCK(sc); return (0); }
static int rk30_gpio_pin_get(device_t dev, uint32_t pin, unsigned int *val) { struct rk30_gpio_softc *sc = device_get_softc(dev); uint32_t bank, offset, reg_data; int i; for (i = 0; i < sc->sc_gpio_npins; i++) { if (sc->sc_gpio_pins[i].gp_pin == pin) break; } if (i >= sc->sc_gpio_npins) return (EINVAL); bank = pin / 32; pin = pin % 32; offset = 1 << pin; RK30_GPIO_LOCK(sc); reg_data = RK30_GPIO_READ(sc, RK30_GPIO_EXT_PORT); RK30_GPIO_UNLOCK(sc); *val = (reg_data & offset) ? 1 : 0; return (0); }
static int rk30_gpio_pin_toggle(device_t dev, uint32_t pin) { int i; struct rk30_gpio_softc *sc; uint32_t data; sc = device_get_softc(dev); for (i = 0; i < sc->sc_gpio_npins; i++) { if (sc->sc_gpio_pins[i].gp_pin == pin) break; } if (i >= sc->sc_gpio_npins) return (EINVAL); RK30_GPIO_LOCK(sc); data = RK30_GPIO_READ(sc, RK30_GPIO_SWPORT_DR); if (data & (1U << pin)) data &= ~(1U << pin); else data |= (1U << pin); RK30_GPIO_WRITE(sc, RK30_GPIO_SWPORT_DR, data); RK30_GPIO_UNLOCK(sc); return (0); }
static uint32_t rk30_gpio_get_function(struct rk30_gpio_softc *sc, uint32_t pin) { if (RK30_GPIO_READ(sc, RK30_GPIO_SWPORT_DDR) & (1U << pin)) return (GPIO_PIN_OUTPUT); else return (GPIO_PIN_INPUT); }
static uint32_t rk30_gpio_get_function(struct rk30_gpio_softc *sc, uint32_t pin) { uint32_t bank, func, offset; bank = pin / 32; pin = pin % 32; offset = 1 << pin; func = RK30_GPIO_READ(sc, RK30_GPIO_SWPORT_DDR); func &= offset; return (func); }
static void rk30_gpio_set_function(struct rk30_gpio_softc *sc, uint32_t pin, uint32_t func) { uint32_t data; /* Must be called with lock held. */ RK30_GPIO_LOCK_ASSERT(sc); data = RK30_GPIO_READ(sc, RK30_GPIO_SWPORT_DDR); if (func == GPIO_PIN_OUTPUT) data |= (1U << pin); else data &= ~(1U << pin); RK30_GPIO_WRITE(sc, RK30_GPIO_SWPORT_DDR, data); }
static void rk30_gpio_set_function(struct rk30_gpio_softc *sc, uint32_t pin, uint32_t f) { uint32_t bank, data, offset; /* Must be called with lock held. */ RK30_GPIO_LOCK_ASSERT(sc); bank = pin / 32; pin = pin % 32; offset = 1 << pin; data = RK30_GPIO_READ(sc, RK30_GPIO_SWPORT_DDR); if (f) data |= offset; else data &= ~offset; RK30_GPIO_WRITE(sc, RK30_GPIO_SWPORT_DDR, data); }
static int rk30_gpio_pin_get(device_t dev, uint32_t pin, unsigned int *val) { int i; struct rk30_gpio_softc *sc; uint32_t data; sc = device_get_softc(dev); for (i = 0; i < sc->sc_gpio_npins; i++) { if (sc->sc_gpio_pins[i].gp_pin == pin) break; } if (i >= sc->sc_gpio_npins) return (EINVAL); RK30_GPIO_LOCK(sc); data = RK30_GPIO_READ(sc, RK30_GPIO_EXT_PORT); RK30_GPIO_UNLOCK(sc); *val = (data & (1U << pin)) ? 1 : 0; return (0); }