1/* 2 * Coldfire generic GPIO support 3 * 4 * (C) Copyright 2009, Steven King <sfking@fdwdc.com> 5 * 6 * This program is free software; you can redistribute it and/or modify 7 * it under the terms of the GNU General Public License as published by 8 * the Free Software Foundation; version 2 of the License. 9 * 10 * This program is distributed in the hope that it will be useful, 11 * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 * GNU General Public License for more details. 14*/ 15 16#include <linux/kernel.h> 17#include <linux/init.h> 18 19#include <asm/coldfire.h> 20#include <asm/mcfsim.h> 21#include <asm/mcfgpio.h> 22 23static struct mcf_gpio_chip mcf_gpio_chips[] = { 24 { 25 .gpio_chip = { 26 .label = "NQ", 27 .request = mcf_gpio_request, 28 .free = mcf_gpio_free, 29 .direction_input = mcf_gpio_direction_input, 30 .direction_output = mcf_gpio_direction_output, 31 .get = mcf_gpio_get_value, 32 .set = mcf_gpio_set_value, 33 .base = 1, 34 .ngpio = 7, 35 }, 36 .pddr = MCFEPORT_EPDDR, 37 .podr = MCFEPORT_EPDR, 38 .ppdr = MCFEPORT_EPPDR, 39 }, 40 { 41 .gpio_chip = { 42 .label = "TA", 43 .request = mcf_gpio_request, 44 .free = mcf_gpio_free, 45 .direction_input = mcf_gpio_direction_input, 46 .direction_output = mcf_gpio_direction_output, 47 .get = mcf_gpio_get_value, 48 .set = mcf_gpio_set_value_fast, 49 .base = 8, 50 .ngpio = 4, 51 }, 52 .pddr = MCFGPTA_GPTDDR, 53 .podr = MCFGPTA_GPTPORT, 54 .ppdr = MCFGPTB_GPTPORT, 55 }, 56 { 57 .gpio_chip = { 58 .label = "TB", 59 .request = mcf_gpio_request, 60 .free = mcf_gpio_free, 61 .direction_input = mcf_gpio_direction_input, 62 .direction_output = mcf_gpio_direction_output, 63 .get = mcf_gpio_get_value, 64 .set = mcf_gpio_set_value_fast, 65 .base = 16, 66 .ngpio = 4, 67 }, 68 .pddr = MCFGPTB_GPTDDR, 69 .podr = MCFGPTB_GPTPORT, 70 .ppdr = MCFGPTB_GPTPORT, 71 }, 72 { 73 .gpio_chip = { 74 .label = "QA", 75 .request = mcf_gpio_request, 76 .free = mcf_gpio_free, 77 .direction_input = mcf_gpio_direction_input, 78 .direction_output = mcf_gpio_direction_output, 79 .get = mcf_gpio_get_value, 80 .set = mcf_gpio_set_value_fast, 81 .base = 24, 82 .ngpio = 4, 83 }, 84 .pddr = MCFQADC_DDRQA, 85 .podr = MCFQADC_PORTQA, 86 .ppdr = MCFQADC_PORTQA, 87 }, 88 { 89 .gpio_chip = { 90 .label = "QB", 91 .request = mcf_gpio_request, 92 .free = mcf_gpio_free, 93 .direction_input = mcf_gpio_direction_input, 94 .direction_output = mcf_gpio_direction_output, 95 .get = mcf_gpio_get_value, 96 .set = mcf_gpio_set_value_fast, 97 .base = 32, 98 .ngpio = 4, 99 }, 100 .pddr = MCFQADC_DDRQB, 101 .podr = MCFQADC_PORTQB, 102 .ppdr = MCFQADC_PORTQB, 103 }, 104 { 105 .gpio_chip = { 106 .label = "A", 107 .request = mcf_gpio_request, 108 .free = mcf_gpio_free, 109 .direction_input = mcf_gpio_direction_input, 110 .direction_output = mcf_gpio_direction_output, 111 .get = mcf_gpio_get_value, 112 .set = mcf_gpio_set_value_fast, 113 .base = 40, 114 .ngpio = 8, 115 }, 116 .pddr = MCFGPIO_DDRA, 117 .podr = MCFGPIO_PORTA, 118 .ppdr = MCFGPIO_PORTAP, 119 .setr = MCFGPIO_SETA, 120 .clrr = MCFGPIO_CLRA, 121 }, 122 { 123 .gpio_chip = { 124 .label = "B", 125 .request = mcf_gpio_request, 126 .free = mcf_gpio_free, 127 .direction_input = mcf_gpio_direction_input, 128 .direction_output = mcf_gpio_direction_output, 129 .get = mcf_gpio_get_value, 130 .set = mcf_gpio_set_value_fast, 131 .base = 48, 132 .ngpio = 8, 133 }, 134 .pddr = MCFGPIO_DDRB, 135 .podr = MCFGPIO_PORTB, 136 .ppdr = MCFGPIO_PORTBP, 137 .setr = MCFGPIO_SETB, 138 .clrr = MCFGPIO_CLRB, 139 }, 140 { 141 .gpio_chip = { 142 .label = "C", 143 .request = mcf_gpio_request, 144 .free = mcf_gpio_free, 145 .direction_input = mcf_gpio_direction_input, 146 .direction_output = mcf_gpio_direction_output, 147 .get = mcf_gpio_get_value, 148 .set = mcf_gpio_set_value_fast, 149 .base = 56, 150 .ngpio = 8, 151 }, 152 .pddr = MCFGPIO_DDRC, 153 .podr = MCFGPIO_PORTC, 154 .ppdr = MCFGPIO_PORTCP, 155 .setr = MCFGPIO_SETC, 156 .clrr = MCFGPIO_CLRC, 157 }, 158 { 159 .gpio_chip = { 160 .label = "D", 161 .request = mcf_gpio_request, 162 .free = mcf_gpio_free, 163 .direction_input = mcf_gpio_direction_input, 164 .direction_output = mcf_gpio_direction_output, 165 .get = mcf_gpio_get_value, 166 .set = mcf_gpio_set_value_fast, 167 .base = 64, 168 .ngpio = 8, 169 }, 170 .pddr = MCFGPIO_DDRD, 171 .podr = MCFGPIO_PORTD, 172 .ppdr = MCFGPIO_PORTDP, 173 .setr = MCFGPIO_SETD, 174 .clrr = MCFGPIO_CLRD, 175 }, 176 { 177 .gpio_chip = { 178 .label = "E", 179 .request = mcf_gpio_request, 180 .free = mcf_gpio_free, 181 .direction_input = mcf_gpio_direction_input, 182 .direction_output = mcf_gpio_direction_output, 183 .get = mcf_gpio_get_value, 184 .set = mcf_gpio_set_value_fast, 185 .base = 72, 186 .ngpio = 8, 187 }, 188 .pddr = MCFGPIO_DDRE, 189 .podr = MCFGPIO_PORTE, 190 .ppdr = MCFGPIO_PORTEP, 191 .setr = MCFGPIO_SETE, 192 .clrr = MCFGPIO_CLRE, 193 }, 194 { 195 .gpio_chip = { 196 .label = "F", 197 .request = mcf_gpio_request, 198 .free = mcf_gpio_free, 199 .direction_input = mcf_gpio_direction_input, 200 .direction_output = mcf_gpio_direction_output, 201 .get = mcf_gpio_get_value, 202 .set = mcf_gpio_set_value_fast, 203 .base = 80, 204 .ngpio = 8, 205 }, 206 .pddr = MCFGPIO_DDRF, 207 .podr = MCFGPIO_PORTF, 208 .ppdr = MCFGPIO_PORTFP, 209 .setr = MCFGPIO_SETF, 210 .clrr = MCFGPIO_CLRF, 211 }, 212 { 213 .gpio_chip = { 214 .label = "G", 215 .request = mcf_gpio_request, 216 .free = mcf_gpio_free, 217 .direction_input = mcf_gpio_direction_input, 218 .direction_output = mcf_gpio_direction_output, 219 .get = mcf_gpio_get_value, 220 .set = mcf_gpio_set_value_fast, 221 .base = 88, 222 .ngpio = 8, 223 }, 224 .pddr = MCFGPIO_DDRG, 225 .podr = MCFGPIO_PORTG, 226 .ppdr = MCFGPIO_PORTGP, 227 .setr = MCFGPIO_SETG, 228 .clrr = MCFGPIO_CLRG, 229 }, 230 { 231 .gpio_chip = { 232 .label = "H", 233 .request = mcf_gpio_request, 234 .free = mcf_gpio_free, 235 .direction_input = mcf_gpio_direction_input, 236 .direction_output = mcf_gpio_direction_output, 237 .get = mcf_gpio_get_value, 238 .set = mcf_gpio_set_value_fast, 239 .base = 96, 240 .ngpio = 8, 241 }, 242 .pddr = MCFGPIO_DDRH, 243 .podr = MCFGPIO_PORTH, 244 .ppdr = MCFGPIO_PORTHP, 245 .setr = MCFGPIO_SETH, 246 .clrr = MCFGPIO_CLRH, 247 }, 248 { 249 .gpio_chip = { 250 .label = "J", 251 .request = mcf_gpio_request, 252 .free = mcf_gpio_free, 253 .direction_input = mcf_gpio_direction_input, 254 .direction_output = mcf_gpio_direction_output, 255 .get = mcf_gpio_get_value, 256 .set = mcf_gpio_set_value_fast, 257 .base = 104, 258 .ngpio = 8, 259 }, 260 .pddr = MCFGPIO_DDRJ, 261 .podr = MCFGPIO_PORTJ, 262 .ppdr = MCFGPIO_PORTJP, 263 .setr = MCFGPIO_SETJ, 264 .clrr = MCFGPIO_CLRJ, 265 }, 266 { 267 .gpio_chip = { 268 .label = "DD", 269 .request = mcf_gpio_request, 270 .free = mcf_gpio_free, 271 .direction_input = mcf_gpio_direction_input, 272 .direction_output = mcf_gpio_direction_output, 273 .get = mcf_gpio_get_value, 274 .set = mcf_gpio_set_value_fast, 275 .base = 112, 276 .ngpio = 8, 277 }, 278 .pddr = MCFGPIO_DDRDD, 279 .podr = MCFGPIO_PORTDD, 280 .ppdr = MCFGPIO_PORTDDP, 281 .setr = MCFGPIO_SETDD, 282 .clrr = MCFGPIO_CLRDD, 283 }, 284 { 285 .gpio_chip = { 286 .label = "EH", 287 .request = mcf_gpio_request, 288 .free = mcf_gpio_free, 289 .direction_input = mcf_gpio_direction_input, 290 .direction_output = mcf_gpio_direction_output, 291 .get = mcf_gpio_get_value, 292 .set = mcf_gpio_set_value_fast, 293 .base = 120, 294 .ngpio = 8, 295 }, 296 .pddr = MCFGPIO_DDREH, 297 .podr = MCFGPIO_PORTEH, 298 .ppdr = MCFGPIO_PORTEHP, 299 .setr = MCFGPIO_SETEH, 300 .clrr = MCFGPIO_CLREH, 301 }, 302 { 303 .gpio_chip = { 304 .label = "EL", 305 .request = mcf_gpio_request, 306 .free = mcf_gpio_free, 307 .direction_input = mcf_gpio_direction_input, 308 .direction_output = mcf_gpio_direction_output, 309 .get = mcf_gpio_get_value, 310 .set = mcf_gpio_set_value_fast, 311 .base = 128, 312 .ngpio = 8, 313 }, 314 .pddr = MCFGPIO_DDREL, 315 .podr = MCFGPIO_PORTEL, 316 .ppdr = MCFGPIO_PORTELP, 317 .setr = MCFGPIO_SETEL, 318 .clrr = MCFGPIO_CLREL, 319 }, 320 { 321 .gpio_chip = { 322 .label = "AS", 323 .request = mcf_gpio_request, 324 .free = mcf_gpio_free, 325 .direction_input = mcf_gpio_direction_input, 326 .direction_output = mcf_gpio_direction_output, 327 .get = mcf_gpio_get_value, 328 .set = mcf_gpio_set_value_fast, 329 .base = 136, 330 .ngpio = 6, 331 }, 332 .pddr = MCFGPIO_DDRAS, 333 .podr = MCFGPIO_PORTAS, 334 .ppdr = MCFGPIO_PORTASP, 335 .setr = MCFGPIO_SETAS, 336 .clrr = MCFGPIO_CLRAS, 337 }, 338 { 339 .gpio_chip = { 340 .label = "QS", 341 .request = mcf_gpio_request, 342 .free = mcf_gpio_free, 343 .direction_input = mcf_gpio_direction_input, 344 .direction_output = mcf_gpio_direction_output, 345 .get = mcf_gpio_get_value, 346 .set = mcf_gpio_set_value_fast, 347 .base = 144, 348 .ngpio = 7, 349 }, 350 .pddr = MCFGPIO_DDRQS, 351 .podr = MCFGPIO_PORTQS, 352 .ppdr = MCFGPIO_PORTQSP, 353 .setr = MCFGPIO_SETQS, 354 .clrr = MCFGPIO_CLRQS, 355 }, 356 { 357 .gpio_chip = { 358 .label = "SD", 359 .request = mcf_gpio_request, 360 .free = mcf_gpio_free, 361 .direction_input = mcf_gpio_direction_input, 362 .direction_output = mcf_gpio_direction_output, 363 .get = mcf_gpio_get_value, 364 .set = mcf_gpio_set_value_fast, 365 .base = 152, 366 .ngpio = 6, 367 }, 368 .pddr = MCFGPIO_DDRSD, 369 .podr = MCFGPIO_PORTSD, 370 .ppdr = MCFGPIO_PORTSDP, 371 .setr = MCFGPIO_SETSD, 372 .clrr = MCFGPIO_CLRSD, 373 }, 374 { 375 .gpio_chip = { 376 .label = "TC", 377 .request = mcf_gpio_request, 378 .free = mcf_gpio_free, 379 .direction_input = mcf_gpio_direction_input, 380 .direction_output = mcf_gpio_direction_output, 381 .get = mcf_gpio_get_value, 382 .set = mcf_gpio_set_value_fast, 383 .base = 160, 384 .ngpio = 4, 385 }, 386 .pddr = MCFGPIO_DDRTC, 387 .podr = MCFGPIO_PORTTC, 388 .ppdr = MCFGPIO_PORTTCP, 389 .setr = MCFGPIO_SETTC, 390 .clrr = MCFGPIO_CLRTC, 391 }, 392 { 393 .gpio_chip = { 394 .label = "TD", 395 .request = mcf_gpio_request, 396 .free = mcf_gpio_free, 397 .direction_input = mcf_gpio_direction_input, 398 .direction_output = mcf_gpio_direction_output, 399 .get = mcf_gpio_get_value, 400 .set = mcf_gpio_set_value_fast, 401 .base = 168, 402 .ngpio = 4, 403 }, 404 .pddr = MCFGPIO_DDRTD, 405 .podr = MCFGPIO_PORTTD, 406 .ppdr = MCFGPIO_PORTTDP, 407 .setr = MCFGPIO_SETTD, 408 .clrr = MCFGPIO_CLRTD, 409 }, 410 { 411 .gpio_chip = { 412 .label = "UA", 413 .request = mcf_gpio_request, 414 .free = mcf_gpio_free, 415 .direction_input = mcf_gpio_direction_input, 416 .direction_output = mcf_gpio_direction_output, 417 .get = mcf_gpio_get_value, 418 .set = mcf_gpio_set_value_fast, 419 .base = 176, 420 .ngpio = 4, 421 }, 422 .pddr = MCFGPIO_DDRUA, 423 .podr = MCFGPIO_PORTUA, 424 .ppdr = MCFGPIO_PORTUAP, 425 .setr = MCFGPIO_SETUA, 426 .clrr = MCFGPIO_CLRUA, 427 }, 428}; 429 430static int __init mcf_gpio_init(void) 431{ 432 unsigned i = 0; 433 while (i < ARRAY_SIZE(mcf_gpio_chips)) 434 (void)gpiochip_add((struct gpio_chip *)&mcf_gpio_chips[i++]); 435 return 0; 436} 437 438core_initcall(mcf_gpio_init); 439