lpc_gpio.c revision 278782
1/*- 2 * Copyright (c) 2011 Jakub Wojciech Klama <jceel@FreeBSD.org> 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions 7 * are met: 8 * 1. Redistributions of source code must retain the above copyright 9 * notice, this list of conditions and the following disclaimer. 10 * 2. Redistributions in binary form must reproduce the above copyright 11 * notice, this list of conditions and the following disclaimer in the 12 * documentation and/or other materials provided with the distribution. 13 * 14 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 15 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 16 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 17 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 18 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 19 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 20 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 21 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 22 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 23 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 24 * SUCH DAMAGE. 25 * 26 */ 27 28/* 29 * GPIO on LPC32x0 consist of 4 ports: 30 * - Port0 with 8 input/output pins 31 * - Port1 with 24 input/output pins 32 * - Port2 with 13 input/output pins 33 * - Port3 with: 34 * - 26 input pins (GPI_00..GPI_09 + GPI_15..GPI_23 + GPI_25 + GPI_27..GPI_28) 35 * - 24 output pins (GPO_00..GPO_23) 36 * - 6 input/output pins (GPIO_00..GPIO_05) 37 * 38 * Pins are mapped to logical pin number as follows: 39 * [0..9] -> GPI_00..GPI_09 (port 3) 40 * [10..18] -> GPI_15..GPI_23 (port 3) 41 * [19] -> GPI_25 (port 3) 42 * [20..21] -> GPI_27..GPI_28 (port 3) 43 * [22..45] -> GPO_00..GPO_23 (port 3) 44 * [46..51] -> GPIO_00..GPIO_05 (port 3) 45 * [52..64] -> P2.0..P2.12 (port 2) 46 * [65..88] -> P1.0..P1.23 (port 1) 47 * [89..96] -> P0.0..P0.7 (port 0) 48 * 49 */ 50 51 52#include <sys/cdefs.h> 53__FBSDID("$FreeBSD: stable/10/sys/arm/lpc/lpc_gpio.c 278782 2015-02-14 20:37:33Z loos $"); 54 55#include <sys/param.h> 56#include <sys/systm.h> 57#include <sys/bio.h> 58#include <sys/bus.h> 59#include <sys/conf.h> 60#include <sys/endian.h> 61#include <sys/kernel.h> 62#include <sys/kthread.h> 63#include <sys/lock.h> 64#include <sys/malloc.h> 65#include <sys/module.h> 66#include <sys/mutex.h> 67#include <sys/queue.h> 68#include <sys/resource.h> 69#include <sys/rman.h> 70#include <sys/time.h> 71#include <sys/timetc.h> 72#include <sys/watchdog.h> 73#include <sys/gpio.h> 74 75#include <machine/bus.h> 76#include <machine/cpu.h> 77#include <machine/cpufunc.h> 78#include <machine/resource.h> 79#include <machine/intr.h> 80#include <machine/fdt.h> 81 82#include <dev/ofw/ofw_bus.h> 83#include <dev/ofw/ofw_bus_subr.h> 84 85#include <arm/lpc/lpcreg.h> 86#include <arm/lpc/lpcvar.h> 87 88#include "gpio_if.h" 89 90struct lpc_gpio_softc 91{ 92 device_t lg_dev; 93 struct resource * lg_res; 94 bus_space_tag_t lg_bst; 95 bus_space_handle_t lg_bsh; 96}; 97 98struct lpc_gpio_pinmap 99{ 100 int lp_start_idx; 101 int lp_pin_count; 102 int lp_port; 103 int lp_start_bit; 104 int lp_flags; 105}; 106 107static const struct lpc_gpio_pinmap lpc_gpio_pins[] = { 108 { 0, 10, 3, 0, GPIO_PIN_INPUT }, 109 { 10, 9, 3, 15, GPIO_PIN_INPUT }, 110 { 19, 1, 3, 25, GPIO_PIN_INPUT }, 111 { 20, 2, 3, 27, GPIO_PIN_INPUT }, 112 { 22, 24, 3, 0, GPIO_PIN_OUTPUT }, 113 /* 114 * -1 below is to mark special case for Port3 GPIO pins, as they 115 * have other bits in Port 3 registers as inputs and as outputs 116 */ 117 { 46, 6, 3, -1, GPIO_PIN_INPUT | GPIO_PIN_OUTPUT }, 118 { 52, 13, 2, 0, GPIO_PIN_INPUT | GPIO_PIN_OUTPUT }, 119 { 65, 24, 1, 0, GPIO_PIN_INPUT | GPIO_PIN_OUTPUT }, 120 { 89, 8, 0, 0, GPIO_PIN_INPUT | GPIO_PIN_OUTPUT }, 121 { -1, -1, -1, -1, -1 }, 122}; 123 124#define LPC_GPIO_NPINS \ 125 (LPC_GPIO_P0_COUNT + LPC_GPIO_P1_COUNT + \ 126 LPC_GPIO_P2_COUNT + LPC_GPIO_P3_COUNT) 127 128#define LPC_GPIO_PIN_IDX(_map, _idx) \ 129 (_idx - _map->lp_start_idx) 130 131#define LPC_GPIO_PIN_BIT(_map, _idx) \ 132 (_map->lp_start_bit + LPC_GPIO_PIN_IDX(_map, _idx)) 133 134static int lpc_gpio_probe(device_t); 135static int lpc_gpio_attach(device_t); 136static int lpc_gpio_detach(device_t); 137 138static int lpc_gpio_pin_max(device_t, int *); 139static int lpc_gpio_pin_getcaps(device_t, uint32_t, uint32_t *); 140static int lpc_gpio_pin_getflags(device_t, uint32_t, uint32_t *); 141static int lpc_gpio_pin_setflags(device_t, uint32_t, uint32_t); 142static int lpc_gpio_pin_getname(device_t, uint32_t, char *); 143static int lpc_gpio_pin_get(device_t, uint32_t, uint32_t *); 144static int lpc_gpio_pin_set(device_t, uint32_t, uint32_t); 145static int lpc_gpio_pin_toggle(device_t, uint32_t); 146 147static const struct lpc_gpio_pinmap *lpc_gpio_get_pinmap(int); 148 149static struct lpc_gpio_softc *lpc_gpio_sc = NULL; 150 151#define lpc_gpio_read_4(_sc, _reg) \ 152 bus_space_read_4(_sc->lg_bst, _sc->lg_bsh, _reg) 153#define lpc_gpio_write_4(_sc, _reg, _val) \ 154 bus_space_write_4(_sc->lg_bst, _sc->lg_bsh, _reg, _val) 155#define lpc_gpio_get_4(_sc, _test, _reg1, _reg2) \ 156 lpc_gpio_read_4(_sc, ((_test) ? _reg1 : _reg2)) 157#define lpc_gpio_set_4(_sc, _test, _reg1, _reg2, _val) \ 158 lpc_gpio_write_4(_sc, ((_test) ? _reg1 : _reg2), _val) 159 160static int 161lpc_gpio_probe(device_t dev) 162{ 163 164 if (!ofw_bus_status_okay(dev)) 165 return (ENXIO); 166 167 if (!ofw_bus_is_compatible(dev, "lpc,gpio")) 168 return (ENXIO); 169 170 device_set_desc(dev, "LPC32x0 GPIO"); 171 return (BUS_PROBE_DEFAULT); 172} 173 174static int 175lpc_gpio_attach(device_t dev) 176{ 177 struct lpc_gpio_softc *sc = device_get_softc(dev); 178 int rid; 179 180 sc->lg_dev = dev; 181 182 rid = 0; 183 sc->lg_res = bus_alloc_resource_any(dev, SYS_RES_MEMORY, &rid, 184 RF_ACTIVE); 185 if (!sc->lg_res) { 186 device_printf(dev, "cannot allocate memory window\n"); 187 return (ENXIO); 188 } 189 190 sc->lg_bst = rman_get_bustag(sc->lg_res); 191 sc->lg_bsh = rman_get_bushandle(sc->lg_res); 192 193 lpc_gpio_sc = sc; 194 195 device_add_child(dev, "gpioc", -1); 196 device_add_child(dev, "gpiobus", -1); 197 198 return (bus_generic_attach(dev)); 199} 200 201static int 202lpc_gpio_detach(device_t dev) 203{ 204 return (EBUSY); 205} 206 207static int 208lpc_gpio_pin_max(device_t dev, int *npins) 209{ 210 *npins = LPC_GPIO_NPINS - 1; 211 return (0); 212} 213 214static int 215lpc_gpio_pin_getcaps(device_t dev, uint32_t pin, uint32_t *caps) 216{ 217 const struct lpc_gpio_pinmap *map; 218 219 if (pin > LPC_GPIO_NPINS) 220 return (ENODEV); 221 222 map = lpc_gpio_get_pinmap(pin); 223 224 *caps = map->lp_flags; 225 return (0); 226} 227 228static int 229lpc_gpio_pin_getflags(device_t dev, uint32_t pin, uint32_t *flags) 230{ 231 struct lpc_gpio_softc *sc = device_get_softc(dev); 232 const struct lpc_gpio_pinmap *map; 233 uint32_t state; 234 int dir; 235 236 if (pin > LPC_GPIO_NPINS) 237 return (ENODEV); 238 239 map = lpc_gpio_get_pinmap(pin); 240 241 /* Check whether it's bidirectional pin */ 242 if ((map->lp_flags & (GPIO_PIN_INPUT | GPIO_PIN_OUTPUT)) != 243 (GPIO_PIN_INPUT | GPIO_PIN_OUTPUT)) { 244 *flags = map->lp_flags; 245 return (0); 246 } 247 248 switch (map->lp_port) { 249 case 0: 250 state = lpc_gpio_read_4(sc, LPC_GPIO_P0_DIR_STATE); 251 dir = (state & (1 << LPC_GPIO_PIN_BIT(map, pin))); 252 break; 253 case 1: 254 state = lpc_gpio_read_4(sc, LPC_GPIO_P1_DIR_STATE); 255 dir = (state & (1 << LPC_GPIO_PIN_BIT(map, pin))); 256 break; 257 case 2: 258 state = lpc_gpio_read_4(sc, LPC_GPIO_P2_DIR_STATE); 259 dir = (state & (1 << LPC_GPIO_PIN_BIT(map, pin))); 260 break; 261 case 3: 262 state = lpc_gpio_read_4(sc, LPC_GPIO_P2_DIR_STATE); 263 dir = (state & (1 << (25 + LPC_GPIO_PIN_IDX(map, pin)))); 264 break; 265 default: 266 panic("unknown GPIO port"); 267 } 268 269 *flags = dir ? GPIO_PIN_OUTPUT : GPIO_PIN_INPUT; 270 271 return (0); 272} 273 274static int 275lpc_gpio_pin_setflags(device_t dev, uint32_t pin, uint32_t flags) 276{ 277 struct lpc_gpio_softc *sc = device_get_softc(dev); 278 const struct lpc_gpio_pinmap *map; 279 uint32_t dir, state; 280 281 if (pin > LPC_GPIO_NPINS) 282 return (ENODEV); 283 284 map = lpc_gpio_get_pinmap(pin); 285 286 /* Check whether it's bidirectional pin */ 287 if ((map->lp_flags & (GPIO_PIN_INPUT | GPIO_PIN_OUTPUT)) != 288 (GPIO_PIN_INPUT | GPIO_PIN_OUTPUT)) 289 return (ENOTSUP); 290 291 if (flags & GPIO_PIN_INPUT) 292 dir = 0; 293 294 if (flags & GPIO_PIN_OUTPUT) 295 dir = 1; 296 297 switch (map->lp_port) { 298 case 0: 299 state = (1 << LPC_GPIO_PIN_IDX(map, pin)); 300 lpc_gpio_set_4(sc, dir, LPC_GPIO_P0_DIR_SET, 301 LPC_GPIO_P0_DIR_CLR, state); 302 break; 303 case 1: 304 state = (1 << LPC_GPIO_PIN_IDX(map, pin)); 305 lpc_gpio_set_4(sc, dir, LPC_GPIO_P1_DIR_SET, 306 LPC_GPIO_P0_DIR_CLR, state); 307 break; 308 case 2: 309 state = (1 << LPC_GPIO_PIN_IDX(map, pin)); 310 lpc_gpio_set_4(sc, dir, LPC_GPIO_P2_DIR_SET, 311 LPC_GPIO_P0_DIR_CLR, state); 312 break; 313 case 3: 314 state = (1 << (25 + (pin - map->lp_start_idx))); 315 lpc_gpio_set_4(sc, dir, LPC_GPIO_P2_DIR_SET, 316 LPC_GPIO_P0_DIR_CLR, state); 317 break; 318 } 319 320 return (0); 321} 322 323static int 324lpc_gpio_pin_getname(device_t dev, uint32_t pin, char *name) 325{ 326 const struct lpc_gpio_pinmap *map; 327 int idx; 328 329 map = lpc_gpio_get_pinmap(pin); 330 idx = LPC_GPIO_PIN_IDX(map, pin); 331 332 switch (map->lp_port) { 333 case 0: 334 case 1: 335 case 2: 336 snprintf(name, GPIOMAXNAME - 1, "P%d.%d", map->lp_port, 337 map->lp_start_bit + LPC_GPIO_PIN_IDX(map, pin)); 338 break; 339 case 3: 340 if (map->lp_start_bit == -1) { 341 snprintf(name, GPIOMAXNAME - 1, "GPIO_%02d", idx); 342 break; 343 } 344 345 snprintf(name, GPIOMAXNAME - 1, "GP%c_%02d", 346 (map->lp_flags & GPIO_PIN_INPUT) ? 'I' : 'O', 347 map->lp_start_bit + idx); 348 break; 349 } 350 351 return (0); 352} 353 354static int 355lpc_gpio_pin_get(device_t dev, uint32_t pin, uint32_t *value) 356{ 357 struct lpc_gpio_softc *sc = device_get_softc(dev); 358 const struct lpc_gpio_pinmap *map; 359 uint32_t state, flags; 360 int dir; 361 362 map = lpc_gpio_get_pinmap(pin); 363 364 if (lpc_gpio_pin_getflags(dev, pin, &flags)) 365 return (ENXIO); 366 367 if (flags & GPIO_PIN_OUTPUT) 368 dir = 1; 369 370 if (flags & GPIO_PIN_INPUT) 371 dir = 0; 372 373 switch (map->lp_port) { 374 case 0: 375 state = lpc_gpio_get_4(sc, dir, LPC_GPIO_P0_OUTP_STATE, 376 LPC_GPIO_P0_INP_STATE); 377 *value = !!(state & (1 << LPC_GPIO_PIN_BIT(map, pin))); 378 case 1: 379 state = lpc_gpio_get_4(sc, dir, LPC_GPIO_P1_OUTP_STATE, 380 LPC_GPIO_P1_INP_STATE); 381 *value = !!(state & (1 << LPC_GPIO_PIN_BIT(map, pin))); 382 case 2: 383 state = lpc_gpio_read_4(sc, LPC_GPIO_P2_INP_STATE); 384 *value = !!(state & (1 << LPC_GPIO_PIN_BIT(map, pin))); 385 case 3: 386 state = lpc_gpio_get_4(sc, dir, LPC_GPIO_P3_OUTP_STATE, 387 LPC_GPIO_P3_INP_STATE); 388 if (map->lp_start_bit == -1) { 389 if (dir) 390 *value = !!(state & (1 << (25 + 391 LPC_GPIO_PIN_IDX(map, pin)))); 392 else 393 *value = !!(state & (1 << (10 + 394 LPC_GPIO_PIN_IDX(map, pin)))); 395 } 396 397 *value = !!(state & (1 << LPC_GPIO_PIN_BIT(map, pin))); 398 } 399 400 return (0); 401} 402 403static int 404lpc_gpio_pin_set(device_t dev, uint32_t pin, uint32_t value) 405{ 406 struct lpc_gpio_softc *sc = device_get_softc(dev); 407 const struct lpc_gpio_pinmap *map; 408 uint32_t state, flags; 409 410 map = lpc_gpio_get_pinmap(pin); 411 412 if (lpc_gpio_pin_getflags(dev, pin, &flags)) 413 return (ENXIO); 414 415 if ((flags & GPIO_PIN_OUTPUT) == 0) 416 return (EINVAL); 417 418 state = (1 << LPC_GPIO_PIN_BIT(map, pin)); 419 420 switch (map->lp_port) { 421 case 0: 422 lpc_gpio_set_4(sc, value, LPC_GPIO_P0_OUTP_SET, 423 LPC_GPIO_P0_OUTP_CLR, state); 424 break; 425 case 1: 426 lpc_gpio_set_4(sc, value, LPC_GPIO_P1_OUTP_SET, 427 LPC_GPIO_P1_OUTP_CLR, state); 428 break; 429 case 2: 430 lpc_gpio_set_4(sc, value, LPC_GPIO_P2_OUTP_SET, 431 LPC_GPIO_P2_OUTP_CLR, state); 432 break; 433 case 3: 434 if (map->lp_start_bit == -1) 435 state = (1 << (25 + LPC_GPIO_PIN_IDX(map, pin))); 436 437 lpc_gpio_set_4(sc, value, LPC_GPIO_P3_OUTP_SET, 438 LPC_GPIO_P3_OUTP_CLR, state); 439 break; 440 } 441 442 return (0); 443} 444 445static int 446lpc_gpio_pin_toggle(device_t dev, uint32_t pin) 447{ 448 const struct lpc_gpio_pinmap *map; 449 uint32_t flags; 450 451 map = lpc_gpio_get_pinmap(pin); 452 453 if (lpc_gpio_pin_getflags(dev, pin, &flags)) 454 return (ENXIO); 455 456 if ((flags & GPIO_PIN_OUTPUT) == 0) 457 return (EINVAL); 458 459 panic("not implemented yet"); 460 461 return (0); 462 463} 464 465static const struct lpc_gpio_pinmap * 466lpc_gpio_get_pinmap(int pin) 467{ 468 const struct lpc_gpio_pinmap *map; 469 470 for (map = &lpc_gpio_pins[0]; map->lp_start_idx != -1; map++) { 471 if (pin >= map->lp_start_idx && 472 pin < map->lp_start_idx + map->lp_pin_count) 473 return map; 474 } 475 476 panic("pin number %d out of range", pin); 477} 478 479int 480lpc_gpio_set_flags(device_t dev, int pin, int flags) 481{ 482 if (lpc_gpio_sc == NULL) 483 return (ENXIO); 484 485 return lpc_gpio_pin_setflags(lpc_gpio_sc->lg_dev, pin, flags); 486} 487 488int 489lpc_gpio_set_state(device_t dev, int pin, int state) 490{ 491 if (lpc_gpio_sc == NULL) 492 return (ENXIO); 493 494 return lpc_gpio_pin_set(lpc_gpio_sc->lg_dev, pin, state); 495} 496 497int 498lpc_gpio_get_state(device_t dev, int pin, int *state) 499{ 500 if (lpc_gpio_sc == NULL) 501 return (ENXIO); 502 503 return lpc_gpio_pin_get(lpc_gpio_sc->lg_dev, pin, state); 504} 505 506void 507platform_gpio_init() 508{ 509 bus_space_tag_t bst; 510 bus_space_handle_t bsh; 511 512 bst = fdtbus_bs_tag; 513 514 /* Preset SPI devices CS pins to one */ 515 bus_space_map(bst, LPC_GPIO_PHYS_BASE, LPC_GPIO_SIZE, 0, &bsh); 516 bus_space_write_4(bst, bsh, LPC_GPIO_P3_OUTP_SET, 517 1 << (SSD1289_CS_PIN - LPC_GPIO_GPO_00(0)) | 518 1 << (SSD1289_DC_PIN - LPC_GPIO_GPO_00(0)) | 519 1 << (ADS7846_CS_PIN - LPC_GPIO_GPO_00(0))); 520 bus_space_unmap(bst, bsh, LPC_GPIO_SIZE); 521} 522 523static device_method_t lpc_gpio_methods[] = { 524 /* Device interface */ 525 DEVMETHOD(device_probe, lpc_gpio_probe), 526 DEVMETHOD(device_attach, lpc_gpio_attach), 527 DEVMETHOD(device_detach, lpc_gpio_detach), 528 529 /* GPIO interface */ 530 DEVMETHOD(gpio_pin_max, lpc_gpio_pin_max), 531 DEVMETHOD(gpio_pin_getcaps, lpc_gpio_pin_getcaps), 532 DEVMETHOD(gpio_pin_getflags, lpc_gpio_pin_getflags), 533 DEVMETHOD(gpio_pin_setflags, lpc_gpio_pin_setflags), 534 DEVMETHOD(gpio_pin_getname, lpc_gpio_pin_getname), 535 DEVMETHOD(gpio_pin_set, lpc_gpio_pin_set), 536 DEVMETHOD(gpio_pin_get, lpc_gpio_pin_get), 537 DEVMETHOD(gpio_pin_toggle, lpc_gpio_pin_toggle), 538 539 { 0, 0 } 540}; 541 542static devclass_t lpc_gpio_devclass; 543 544static driver_t lpc_gpio_driver = { 545 "lpcgpio", 546 lpc_gpio_methods, 547 sizeof(struct lpc_gpio_softc), 548}; 549 550extern devclass_t gpiobus_devclass, gpioc_devclass; 551extern driver_t gpiobus_driver, gpioc_driver; 552 553DRIVER_MODULE(lpcgpio, simplebus, lpc_gpio_driver, lpc_gpio_devclass, 0, 0); 554DRIVER_MODULE(gpiobus, lpcgpio, gpiobus_driver, gpiobus_devclass, 0, 0); 555DRIVER_MODULE(gpioc, lpcgpio, gpioc_driver, gpioc_devclass, 0, 0); 556MODULE_VERSION(lpcgpio, 1); 557