1 /* 2 * GPIO driver for Fintek Super-I/O F71869, F71869A, F71882, F71889 and F81866 3 * 4 * Copyright (C) 2010-2013 LaCie 5 * 6 * Author: Simon Guinot <simon.guinot@sequanux.org> 7 * 8 * This program is free software; you can redistribute it and/or modify 9 * it under the terms of the GNU General Public License as published by 10 * the Free Software Foundation; either version 2 of the License, or 11 * (at your option) any later version. 12 */ 13 14 #include <linux/module.h> 15 #include <linux/init.h> 16 #include <linux/platform_device.h> 17 #include <linux/io.h> 18 #include <linux/gpio/driver.h> 19 #include <linux/bitops.h> 20 21 #define DRVNAME "gpio-f7188x" 22 23 /* 24 * Super-I/O registers 25 */ 26 #define SIO_LDSEL 0x07 /* Logical device select */ 27 #define SIO_DEVID 0x20 /* Device ID (2 bytes) */ 28 #define SIO_DEVREV 0x22 /* Device revision */ 29 #define SIO_MANID 0x23 /* Fintek ID (2 bytes) */ 30 31 #define SIO_LD_GPIO 0x06 /* GPIO logical device */ 32 #define SIO_UNLOCK_KEY 0x87 /* Key to enable Super-I/O */ 33 #define SIO_LOCK_KEY 0xAA /* Key to disable Super-I/O */ 34 35 #define SIO_FINTEK_ID 0x1934 /* Manufacturer ID */ 36 #define SIO_F71869_ID 0x0814 /* F71869 chipset ID */ 37 #define SIO_F71869A_ID 0x1007 /* F71869A chipset ID */ 38 #define SIO_F71882_ID 0x0541 /* F71882 chipset ID */ 39 #define SIO_F71889_ID 0x0909 /* F71889 chipset ID */ 40 #define SIO_F81866_ID 0x1010 /* F81866 chipset ID */ 41 42 enum chips { f71869, f71869a, f71882fg, f71889f, f81866 }; 43 44 static const char * const f7188x_names[] = { 45 "f71869", 46 "f71869a", 47 "f71882fg", 48 "f71889f", 49 "f81866", 50 }; 51 52 struct f7188x_sio { 53 int addr; 54 enum chips type; 55 }; 56 57 struct f7188x_gpio_bank { 58 struct gpio_chip chip; 59 unsigned int regbase; 60 struct f7188x_gpio_data *data; 61 }; 62 63 struct f7188x_gpio_data { 64 struct f7188x_sio *sio; 65 int nr_bank; 66 struct f7188x_gpio_bank *bank; 67 }; 68 69 /* 70 * Super-I/O functions. 71 */ 72 73 static inline int superio_inb(int base, int reg) 74 { 75 outb(reg, base); 76 return inb(base + 1); 77 } 78 79 static int superio_inw(int base, int reg) 80 { 81 int val; 82 83 outb(reg++, base); 84 val = inb(base + 1) << 8; 85 outb(reg, base); 86 val |= inb(base + 1); 87 88 return val; 89 } 90 91 static inline void superio_outb(int base, int reg, int val) 92 { 93 outb(reg, base); 94 outb(val, base + 1); 95 } 96 97 static inline int superio_enter(int base) 98 { 99 /* Don't step on other drivers' I/O space by accident. */ 100 if (!request_muxed_region(base, 2, DRVNAME)) { 101 pr_err(DRVNAME "I/O address 0x%04x already in use\n", base); 102 return -EBUSY; 103 } 104 105 /* According to the datasheet the key must be send twice. */ 106 outb(SIO_UNLOCK_KEY, base); 107 outb(SIO_UNLOCK_KEY, base); 108 109 return 0; 110 } 111 112 static inline void superio_select(int base, int ld) 113 { 114 outb(SIO_LDSEL, base); 115 outb(ld, base + 1); 116 } 117 118 static inline void superio_exit(int base) 119 { 120 outb(SIO_LOCK_KEY, base); 121 release_region(base, 2); 122 } 123 124 /* 125 * GPIO chip. 126 */ 127 128 static int f7188x_gpio_get_direction(struct gpio_chip *chip, unsigned offset); 129 static int f7188x_gpio_direction_in(struct gpio_chip *chip, unsigned offset); 130 static int f7188x_gpio_get(struct gpio_chip *chip, unsigned offset); 131 static int f7188x_gpio_direction_out(struct gpio_chip *chip, 132 unsigned offset, int value); 133 static void f7188x_gpio_set(struct gpio_chip *chip, unsigned offset, int value); 134 static int f7188x_gpio_set_single_ended(struct gpio_chip *gc, 135 unsigned offset, 136 enum single_ended_mode mode); 137 138 #define F7188X_GPIO_BANK(_base, _ngpio, _regbase) \ 139 { \ 140 .chip = { \ 141 .label = DRVNAME, \ 142 .owner = THIS_MODULE, \ 143 .get_direction = f7188x_gpio_get_direction, \ 144 .direction_input = f7188x_gpio_direction_in, \ 145 .get = f7188x_gpio_get, \ 146 .direction_output = f7188x_gpio_direction_out, \ 147 .set = f7188x_gpio_set, \ 148 .set_single_ended = f7188x_gpio_set_single_ended, \ 149 .base = _base, \ 150 .ngpio = _ngpio, \ 151 .can_sleep = true, \ 152 }, \ 153 .regbase = _regbase, \ 154 } 155 156 #define gpio_dir(base) (base + 0) 157 #define gpio_data_out(base) (base + 1) 158 #define gpio_data_in(base) (base + 2) 159 /* Output mode register (0:open drain 1:push-pull). */ 160 #define gpio_out_mode(base) (base + 3) 161 162 static struct f7188x_gpio_bank f71869_gpio_bank[] = { 163 F7188X_GPIO_BANK(0, 6, 0xF0), 164 F7188X_GPIO_BANK(10, 8, 0xE0), 165 F7188X_GPIO_BANK(20, 8, 0xD0), 166 F7188X_GPIO_BANK(30, 8, 0xC0), 167 F7188X_GPIO_BANK(40, 8, 0xB0), 168 F7188X_GPIO_BANK(50, 5, 0xA0), 169 F7188X_GPIO_BANK(60, 6, 0x90), 170 }; 171 172 static struct f7188x_gpio_bank f71869a_gpio_bank[] = { 173 F7188X_GPIO_BANK(0, 6, 0xF0), 174 F7188X_GPIO_BANK(10, 8, 0xE0), 175 F7188X_GPIO_BANK(20, 8, 0xD0), 176 F7188X_GPIO_BANK(30, 8, 0xC0), 177 F7188X_GPIO_BANK(40, 8, 0xB0), 178 F7188X_GPIO_BANK(50, 5, 0xA0), 179 F7188X_GPIO_BANK(60, 8, 0x90), 180 F7188X_GPIO_BANK(70, 8, 0x80), 181 }; 182 183 static struct f7188x_gpio_bank f71882_gpio_bank[] = { 184 F7188X_GPIO_BANK(0, 8, 0xF0), 185 F7188X_GPIO_BANK(10, 8, 0xE0), 186 F7188X_GPIO_BANK(20, 8, 0xD0), 187 F7188X_GPIO_BANK(30, 4, 0xC0), 188 F7188X_GPIO_BANK(40, 4, 0xB0), 189 }; 190 191 static struct f7188x_gpio_bank f71889_gpio_bank[] = { 192 F7188X_GPIO_BANK(0, 7, 0xF0), 193 F7188X_GPIO_BANK(10, 7, 0xE0), 194 F7188X_GPIO_BANK(20, 8, 0xD0), 195 F7188X_GPIO_BANK(30, 8, 0xC0), 196 F7188X_GPIO_BANK(40, 8, 0xB0), 197 F7188X_GPIO_BANK(50, 5, 0xA0), 198 F7188X_GPIO_BANK(60, 8, 0x90), 199 F7188X_GPIO_BANK(70, 8, 0x80), 200 }; 201 202 static struct f7188x_gpio_bank f81866_gpio_bank[] = { 203 F7188X_GPIO_BANK(0, 8, 0xF0), 204 F7188X_GPIO_BANK(10, 8, 0xE0), 205 F7188X_GPIO_BANK(20, 8, 0xD0), 206 F7188X_GPIO_BANK(30, 8, 0xC0), 207 F7188X_GPIO_BANK(40, 8, 0xB0), 208 F7188X_GPIO_BANK(50, 8, 0xA0), 209 F7188X_GPIO_BANK(60, 8, 0x90), 210 F7188X_GPIO_BANK(70, 8, 0x80), 211 F7188X_GPIO_BANK(80, 8, 0x88), 212 }; 213 214 static int f7188x_gpio_get_direction(struct gpio_chip *chip, unsigned offset) 215 { 216 int err; 217 struct f7188x_gpio_bank *bank = gpiochip_get_data(chip); 218 struct f7188x_sio *sio = bank->data->sio; 219 u8 dir; 220 221 err = superio_enter(sio->addr); 222 if (err) 223 return err; 224 superio_select(sio->addr, SIO_LD_GPIO); 225 226 dir = superio_inb(sio->addr, gpio_dir(bank->regbase)); 227 228 superio_exit(sio->addr); 229 230 return !(dir & 1 << offset); 231 } 232 233 static int f7188x_gpio_direction_in(struct gpio_chip *chip, unsigned offset) 234 { 235 int err; 236 struct f7188x_gpio_bank *bank = gpiochip_get_data(chip); 237 struct f7188x_sio *sio = bank->data->sio; 238 u8 dir; 239 240 err = superio_enter(sio->addr); 241 if (err) 242 return err; 243 superio_select(sio->addr, SIO_LD_GPIO); 244 245 dir = superio_inb(sio->addr, gpio_dir(bank->regbase)); 246 dir &= ~BIT(offset); 247 superio_outb(sio->addr, gpio_dir(bank->regbase), dir); 248 249 superio_exit(sio->addr); 250 251 return 0; 252 } 253 254 static int f7188x_gpio_get(struct gpio_chip *chip, unsigned offset) 255 { 256 int err; 257 struct f7188x_gpio_bank *bank = gpiochip_get_data(chip); 258 struct f7188x_sio *sio = bank->data->sio; 259 u8 dir, data; 260 261 err = superio_enter(sio->addr); 262 if (err) 263 return err; 264 superio_select(sio->addr, SIO_LD_GPIO); 265 266 dir = superio_inb(sio->addr, gpio_dir(bank->regbase)); 267 dir = !!(dir & BIT(offset)); 268 if (dir) 269 data = superio_inb(sio->addr, gpio_data_out(bank->regbase)); 270 else 271 data = superio_inb(sio->addr, gpio_data_in(bank->regbase)); 272 273 superio_exit(sio->addr); 274 275 return !!(data & BIT(offset)); 276 } 277 278 static int f7188x_gpio_direction_out(struct gpio_chip *chip, 279 unsigned offset, int value) 280 { 281 int err; 282 struct f7188x_gpio_bank *bank = gpiochip_get_data(chip); 283 struct f7188x_sio *sio = bank->data->sio; 284 u8 dir, data_out; 285 286 err = superio_enter(sio->addr); 287 if (err) 288 return err; 289 superio_select(sio->addr, SIO_LD_GPIO); 290 291 data_out = superio_inb(sio->addr, gpio_data_out(bank->regbase)); 292 if (value) 293 data_out |= BIT(offset); 294 else 295 data_out &= ~BIT(offset); 296 superio_outb(sio->addr, gpio_data_out(bank->regbase), data_out); 297 298 dir = superio_inb(sio->addr, gpio_dir(bank->regbase)); 299 dir |= BIT(offset); 300 superio_outb(sio->addr, gpio_dir(bank->regbase), dir); 301 302 superio_exit(sio->addr); 303 304 return 0; 305 } 306 307 static void f7188x_gpio_set(struct gpio_chip *chip, unsigned offset, int value) 308 { 309 int err; 310 struct f7188x_gpio_bank *bank = gpiochip_get_data(chip); 311 struct f7188x_sio *sio = bank->data->sio; 312 u8 data_out; 313 314 err = superio_enter(sio->addr); 315 if (err) 316 return; 317 superio_select(sio->addr, SIO_LD_GPIO); 318 319 data_out = superio_inb(sio->addr, gpio_data_out(bank->regbase)); 320 if (value) 321 data_out |= BIT(offset); 322 else 323 data_out &= ~BIT(offset); 324 superio_outb(sio->addr, gpio_data_out(bank->regbase), data_out); 325 326 superio_exit(sio->addr); 327 } 328 329 static int f7188x_gpio_set_single_ended(struct gpio_chip *chip, 330 unsigned offset, 331 enum single_ended_mode mode) 332 { 333 int err; 334 struct f7188x_gpio_bank *bank = gpiochip_get_data(chip); 335 struct f7188x_sio *sio = bank->data->sio; 336 u8 data; 337 338 if (mode != LINE_MODE_OPEN_DRAIN && 339 mode != LINE_MODE_PUSH_PULL) 340 return -ENOTSUPP; 341 342 err = superio_enter(sio->addr); 343 if (err) 344 return err; 345 superio_select(sio->addr, SIO_LD_GPIO); 346 347 data = superio_inb(sio->addr, gpio_out_mode(bank->regbase)); 348 if (mode == LINE_MODE_OPEN_DRAIN) 349 data &= ~BIT(offset); 350 else 351 data |= BIT(offset); 352 superio_outb(sio->addr, gpio_out_mode(bank->regbase), data); 353 354 superio_exit(sio->addr); 355 return 0; 356 } 357 358 /* 359 * Platform device and driver. 360 */ 361 362 static int f7188x_gpio_probe(struct platform_device *pdev) 363 { 364 int err; 365 int i; 366 struct f7188x_sio *sio = dev_get_platdata(&pdev->dev); 367 struct f7188x_gpio_data *data; 368 369 data = devm_kzalloc(&pdev->dev, sizeof(*data), GFP_KERNEL); 370 if (!data) 371 return -ENOMEM; 372 373 switch (sio->type) { 374 case f71869: 375 data->nr_bank = ARRAY_SIZE(f71869_gpio_bank); 376 data->bank = f71869_gpio_bank; 377 break; 378 case f71869a: 379 data->nr_bank = ARRAY_SIZE(f71869a_gpio_bank); 380 data->bank = f71869a_gpio_bank; 381 break; 382 case f71882fg: 383 data->nr_bank = ARRAY_SIZE(f71882_gpio_bank); 384 data->bank = f71882_gpio_bank; 385 break; 386 case f71889f: 387 data->nr_bank = ARRAY_SIZE(f71889_gpio_bank); 388 data->bank = f71889_gpio_bank; 389 break; 390 case f81866: 391 data->nr_bank = ARRAY_SIZE(f81866_gpio_bank); 392 data->bank = f81866_gpio_bank; 393 break; 394 default: 395 return -ENODEV; 396 } 397 data->sio = sio; 398 399 platform_set_drvdata(pdev, data); 400 401 /* For each GPIO bank, register a GPIO chip. */ 402 for (i = 0; i < data->nr_bank; i++) { 403 struct f7188x_gpio_bank *bank = &data->bank[i]; 404 405 bank->chip.parent = &pdev->dev; 406 bank->data = data; 407 408 err = devm_gpiochip_add_data(&pdev->dev, &bank->chip, bank); 409 if (err) { 410 dev_err(&pdev->dev, 411 "Failed to register gpiochip %d: %d\n", 412 i, err); 413 return err; 414 } 415 } 416 417 return 0; 418 } 419 420 static int __init f7188x_find(int addr, struct f7188x_sio *sio) 421 { 422 int err; 423 u16 devid; 424 425 err = superio_enter(addr); 426 if (err) 427 return err; 428 429 err = -ENODEV; 430 devid = superio_inw(addr, SIO_MANID); 431 if (devid != SIO_FINTEK_ID) { 432 pr_debug(DRVNAME ": Not a Fintek device at 0x%08x\n", addr); 433 goto err; 434 } 435 436 devid = superio_inw(addr, SIO_DEVID); 437 switch (devid) { 438 case SIO_F71869_ID: 439 sio->type = f71869; 440 break; 441 case SIO_F71869A_ID: 442 sio->type = f71869a; 443 break; 444 case SIO_F71882_ID: 445 sio->type = f71882fg; 446 break; 447 case SIO_F71889_ID: 448 sio->type = f71889f; 449 break; 450 case SIO_F81866_ID: 451 sio->type = f81866; 452 break; 453 default: 454 pr_info(DRVNAME ": Unsupported Fintek device 0x%04x\n", devid); 455 goto err; 456 } 457 sio->addr = addr; 458 err = 0; 459 460 pr_info(DRVNAME ": Found %s at %#x, revision %d\n", 461 f7188x_names[sio->type], 462 (unsigned int) addr, 463 (int) superio_inb(addr, SIO_DEVREV)); 464 465 err: 466 superio_exit(addr); 467 return err; 468 } 469 470 static struct platform_device *f7188x_gpio_pdev; 471 472 static int __init 473 f7188x_gpio_device_add(const struct f7188x_sio *sio) 474 { 475 int err; 476 477 f7188x_gpio_pdev = platform_device_alloc(DRVNAME, -1); 478 if (!f7188x_gpio_pdev) 479 return -ENOMEM; 480 481 err = platform_device_add_data(f7188x_gpio_pdev, 482 sio, sizeof(*sio)); 483 if (err) { 484 pr_err(DRVNAME "Platform data allocation failed\n"); 485 goto err; 486 } 487 488 err = platform_device_add(f7188x_gpio_pdev); 489 if (err) { 490 pr_err(DRVNAME "Device addition failed\n"); 491 goto err; 492 } 493 494 return 0; 495 496 err: 497 platform_device_put(f7188x_gpio_pdev); 498 499 return err; 500 } 501 502 /* 503 * Try to match a supported Fintek device by reading the (hard-wired) 504 * configuration I/O ports. If available, then register both the platform 505 * device and driver to support the GPIOs. 506 */ 507 508 static struct platform_driver f7188x_gpio_driver = { 509 .driver = { 510 .name = DRVNAME, 511 }, 512 .probe = f7188x_gpio_probe, 513 }; 514 515 static int __init f7188x_gpio_init(void) 516 { 517 int err; 518 struct f7188x_sio sio; 519 520 if (f7188x_find(0x2e, &sio) && 521 f7188x_find(0x4e, &sio)) 522 return -ENODEV; 523 524 err = platform_driver_register(&f7188x_gpio_driver); 525 if (!err) { 526 err = f7188x_gpio_device_add(&sio); 527 if (err) 528 platform_driver_unregister(&f7188x_gpio_driver); 529 } 530 531 return err; 532 } 533 subsys_initcall(f7188x_gpio_init); 534 535 static void __exit f7188x_gpio_exit(void) 536 { 537 platform_device_unregister(f7188x_gpio_pdev); 538 platform_driver_unregister(&f7188x_gpio_driver); 539 } 540 module_exit(f7188x_gpio_exit); 541 542 MODULE_DESCRIPTION("GPIO driver for Super-I/O chips F71869, F71869A, F71882FG, F71889F and F81866"); 543 MODULE_AUTHOR("Simon Guinot <simon.guinot@sequanux.org>"); 544 MODULE_LICENSE("GPL"); 545