1 /* 2 * GPIO driver for the SMSC SCH311x Super-I/O chips 3 * 4 * Copyright (C) 2013 Bruno Randolf <br1@einfach.org> 5 * 6 * SuperIO functions and chip detection: 7 * (c) Copyright 2008 Wim Van Sebroeck <wim@iguana.be>. 8 * 9 * This program is free software; you can redistribute it and/or modify 10 * it under the terms of the GNU General Public License as published by 11 * the Free Software Foundation; either version 2 of the License, or 12 * (at your option) any later version. 13 */ 14 15 #include <linux/module.h> 16 #include <linux/kernel.h> 17 #include <linux/init.h> 18 #include <linux/platform_device.h> 19 #include <linux/gpio.h> 20 #include <linux/bitops.h> 21 #include <linux/io.h> 22 23 #define DRV_NAME "gpio-sch311x" 24 25 #define SCH311X_GPIO_CONF_OUT 0x00 26 #define SCH311X_GPIO_CONF_IN 0x01 27 #define SCH311X_GPIO_CONF_INVERT 0x02 28 #define SCH311X_GPIO_CONF_OPEN_DRAIN 0x80 29 30 #define SIO_CONFIG_KEY_ENTER 0x55 31 #define SIO_CONFIG_KEY_EXIT 0xaa 32 33 #define GP1 0x4b 34 35 static int sch311x_ioports[] = { 0x2e, 0x4e, 0x162e, 0x164e }; 36 37 static struct platform_device *sch311x_gpio_pdev; 38 39 struct sch311x_pdev_data { /* platform device data */ 40 unsigned short runtime_reg; /* runtime register base address */ 41 }; 42 43 struct sch311x_gpio_block { /* one GPIO block runtime data */ 44 struct gpio_chip chip; 45 unsigned short data_reg; /* from definition below */ 46 unsigned short *config_regs; /* pointer to definition below */ 47 unsigned short runtime_reg; /* runtime register */ 48 spinlock_t lock; /* lock for this GPIO block */ 49 }; 50 51 struct sch311x_gpio_priv { /* driver private data */ 52 struct sch311x_gpio_block blocks[6]; 53 }; 54 55 struct sch311x_gpio_block_def { /* register address definitions */ 56 unsigned short data_reg; 57 unsigned short config_regs[8]; 58 unsigned short base; 59 }; 60 61 /* Note: some GPIOs are not available, these are marked with 0x00 */ 62 63 static struct sch311x_gpio_block_def sch311x_gpio_blocks[] = { 64 { 65 .data_reg = 0x4b, /* GP1 */ 66 .config_regs = {0x23, 0x24, 0x25, 0x26, 0x27, 0x29, 0x2a, 0x2b}, 67 .base = 10, 68 }, 69 { 70 .data_reg = 0x4c, /* GP2 */ 71 .config_regs = {0x00, 0x2c, 0x2d, 0x00, 0x00, 0x00, 0x00, 0x32}, 72 .base = 20, 73 }, 74 { 75 .data_reg = 0x4d, /* GP3 */ 76 .config_regs = {0x33, 0x34, 0x35, 0x36, 0x37, 0x00, 0x39, 0x3a}, 77 .base = 30, 78 }, 79 { 80 .data_reg = 0x4e, /* GP4 */ 81 .config_regs = {0x3b, 0x00, 0x3d, 0x00, 0x6e, 0x6f, 0x72, 0x73}, 82 .base = 40, 83 }, 84 { 85 .data_reg = 0x4f, /* GP5 */ 86 .config_regs = {0x3f, 0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46}, 87 .base = 50, 88 }, 89 { 90 .data_reg = 0x50, /* GP6 */ 91 .config_regs = {0x47, 0x48, 0x54, 0x55, 0x56, 0x57, 0x58, 0x59}, 92 .base = 60, 93 }, 94 }; 95 96 static inline struct sch311x_gpio_block * 97 to_sch311x_gpio_block(struct gpio_chip *chip) 98 { 99 return container_of(chip, struct sch311x_gpio_block, chip); 100 } 101 102 103 /* 104 * Super-IO functions 105 */ 106 107 static inline int sch311x_sio_enter(int sio_config_port) 108 { 109 /* Don't step on other drivers' I/O space by accident. */ 110 if (!request_muxed_region(sio_config_port, 2, DRV_NAME)) { 111 pr_err(DRV_NAME "I/O address 0x%04x already in use\n", 112 sio_config_port); 113 return -EBUSY; 114 } 115 116 outb(SIO_CONFIG_KEY_ENTER, sio_config_port); 117 return 0; 118 } 119 120 static inline void sch311x_sio_exit(int sio_config_port) 121 { 122 outb(SIO_CONFIG_KEY_EXIT, sio_config_port); 123 release_region(sio_config_port, 2); 124 } 125 126 static inline int sch311x_sio_inb(int sio_config_port, int reg) 127 { 128 outb(reg, sio_config_port); 129 return inb(sio_config_port + 1); 130 } 131 132 static inline void sch311x_sio_outb(int sio_config_port, int reg, int val) 133 { 134 outb(reg, sio_config_port); 135 outb(val, sio_config_port + 1); 136 } 137 138 139 /* 140 * GPIO functions 141 */ 142 143 static int sch311x_gpio_request(struct gpio_chip *chip, unsigned offset) 144 { 145 struct sch311x_gpio_block *block = to_sch311x_gpio_block(chip); 146 147 if (block->config_regs[offset] == 0) /* GPIO is not available */ 148 return -ENODEV; 149 150 if (!request_region(block->runtime_reg + block->config_regs[offset], 151 1, DRV_NAME)) { 152 dev_err(chip->dev, "Failed to request region 0x%04x.\n", 153 block->runtime_reg + block->config_regs[offset]); 154 return -EBUSY; 155 } 156 return 0; 157 } 158 159 static void sch311x_gpio_free(struct gpio_chip *chip, unsigned offset) 160 { 161 struct sch311x_gpio_block *block = to_sch311x_gpio_block(chip); 162 163 if (block->config_regs[offset] == 0) /* GPIO is not available */ 164 return; 165 166 release_region(block->runtime_reg + block->config_regs[offset], 1); 167 } 168 169 static int sch311x_gpio_get(struct gpio_chip *chip, unsigned offset) 170 { 171 struct sch311x_gpio_block *block = to_sch311x_gpio_block(chip); 172 unsigned char data; 173 174 spin_lock(&block->lock); 175 data = inb(block->runtime_reg + block->data_reg); 176 spin_unlock(&block->lock); 177 178 return !!(data & BIT(offset)); 179 } 180 181 static void __sch311x_gpio_set(struct sch311x_gpio_block *block, 182 unsigned offset, int value) 183 { 184 unsigned char data = inb(block->runtime_reg + block->data_reg); 185 if (value) 186 data |= BIT(offset); 187 else 188 data &= ~BIT(offset); 189 outb(data, block->runtime_reg + block->data_reg); 190 } 191 192 static void sch311x_gpio_set(struct gpio_chip *chip, unsigned offset, 193 int value) 194 { 195 struct sch311x_gpio_block *block = to_sch311x_gpio_block(chip); 196 197 spin_lock(&block->lock); 198 __sch311x_gpio_set(block, offset, value); 199 spin_unlock(&block->lock); 200 } 201 202 static int sch311x_gpio_direction_in(struct gpio_chip *chip, unsigned offset) 203 { 204 struct sch311x_gpio_block *block = to_sch311x_gpio_block(chip); 205 206 spin_lock(&block->lock); 207 outb(SCH311X_GPIO_CONF_IN, block->runtime_reg + 208 block->config_regs[offset]); 209 spin_unlock(&block->lock); 210 211 return 0; 212 } 213 214 static int sch311x_gpio_direction_out(struct gpio_chip *chip, unsigned offset, 215 int value) 216 { 217 struct sch311x_gpio_block *block = to_sch311x_gpio_block(chip); 218 219 spin_lock(&block->lock); 220 221 outb(SCH311X_GPIO_CONF_OUT, block->runtime_reg + 222 block->config_regs[offset]); 223 224 __sch311x_gpio_set(block, offset, value); 225 226 spin_unlock(&block->lock); 227 return 0; 228 } 229 230 static int sch311x_gpio_probe(struct platform_device *pdev) 231 { 232 struct sch311x_pdev_data *pdata = pdev->dev.platform_data; 233 struct sch311x_gpio_priv *priv; 234 struct sch311x_gpio_block *block; 235 int err, i; 236 237 /* we can register all GPIO data registers at once */ 238 if (!request_region(pdata->runtime_reg + GP1, 6, DRV_NAME)) { 239 dev_err(&pdev->dev, "Failed to request region 0x%04x-0x%04x.\n", 240 pdata->runtime_reg + GP1, pdata->runtime_reg + GP1 + 5); 241 return -EBUSY; 242 } 243 244 priv = devm_kzalloc(&pdev->dev, sizeof(*priv), GFP_KERNEL); 245 if (!priv) 246 return -ENOMEM; 247 248 platform_set_drvdata(pdev, priv); 249 250 for (i = 0; i < ARRAY_SIZE(priv->blocks); i++) { 251 block = &priv->blocks[i]; 252 253 spin_lock_init(&block->lock); 254 255 block->chip.label = DRV_NAME; 256 block->chip.owner = THIS_MODULE; 257 block->chip.request = sch311x_gpio_request; 258 block->chip.free = sch311x_gpio_free; 259 block->chip.direction_input = sch311x_gpio_direction_in; 260 block->chip.direction_output = sch311x_gpio_direction_out; 261 block->chip.get = sch311x_gpio_get; 262 block->chip.set = sch311x_gpio_set; 263 block->chip.ngpio = 8; 264 block->chip.dev = &pdev->dev; 265 block->chip.base = sch311x_gpio_blocks[i].base; 266 block->config_regs = sch311x_gpio_blocks[i].config_regs; 267 block->data_reg = sch311x_gpio_blocks[i].data_reg; 268 block->runtime_reg = pdata->runtime_reg; 269 270 err = gpiochip_add(&block->chip); 271 if (err < 0) { 272 dev_err(&pdev->dev, 273 "Could not register gpiochip, %d\n", err); 274 goto exit_err; 275 } 276 dev_info(&pdev->dev, 277 "SMSC SCH311x GPIO block %d registered.\n", i); 278 } 279 280 return 0; 281 282 exit_err: 283 release_region(pdata->runtime_reg + GP1, 6); 284 /* release already registered chips */ 285 for (--i; i >= 0; i--) 286 gpiochip_remove(&priv->blocks[i].chip); 287 return err; 288 } 289 290 static int sch311x_gpio_remove(struct platform_device *pdev) 291 { 292 struct sch311x_pdev_data *pdata = pdev->dev.platform_data; 293 struct sch311x_gpio_priv *priv = platform_get_drvdata(pdev); 294 int err, i; 295 296 release_region(pdata->runtime_reg + GP1, 6); 297 298 for (i = 0; i < ARRAY_SIZE(priv->blocks); i++) { 299 err = gpiochip_remove(&priv->blocks[i].chip); 300 if (err) 301 return err; 302 dev_info(&pdev->dev, 303 "SMSC SCH311x GPIO block %d unregistered.\n", i); 304 } 305 return 0; 306 } 307 308 static struct platform_driver sch311x_gpio_driver = { 309 .driver.name = DRV_NAME, 310 .driver.owner = THIS_MODULE, 311 .probe = sch311x_gpio_probe, 312 .remove = sch311x_gpio_remove, 313 }; 314 315 316 /* 317 * Init & exit routines 318 */ 319 320 static int __init sch311x_detect(int sio_config_port, unsigned short *addr) 321 { 322 int err = 0, reg; 323 unsigned short base_addr; 324 unsigned char dev_id; 325 326 err = sch311x_sio_enter(sio_config_port); 327 if (err) 328 return err; 329 330 /* Check device ID. We currently know about: 331 * SCH3112 (0x7c), SCH3114 (0x7d), and SCH3116 (0x7f). */ 332 reg = sch311x_sio_inb(sio_config_port, 0x20); 333 if (!(reg == 0x7c || reg == 0x7d || reg == 0x7f)) { 334 err = -ENODEV; 335 goto exit; 336 } 337 dev_id = reg == 0x7c ? 2 : reg == 0x7d ? 4 : 6; 338 339 /* Select logical device A (runtime registers) */ 340 sch311x_sio_outb(sio_config_port, 0x07, 0x0a); 341 342 /* Check if Logical Device Register is currently active */ 343 if ((sch311x_sio_inb(sio_config_port, 0x30) & 0x01) == 0) 344 pr_info("Seems that LDN 0x0a is not active...\n"); 345 346 /* Get the base address of the runtime registers */ 347 base_addr = (sch311x_sio_inb(sio_config_port, 0x60) << 8) | 348 sch311x_sio_inb(sio_config_port, 0x61); 349 if (!base_addr) { 350 pr_err("Base address not set\n"); 351 err = -ENODEV; 352 goto exit; 353 } 354 *addr = base_addr; 355 356 pr_info("Found an SMSC SCH311%d chip at 0x%04x\n", dev_id, base_addr); 357 358 exit: 359 sch311x_sio_exit(sio_config_port); 360 return err; 361 } 362 363 static int __init sch311x_gpio_pdev_add(const unsigned short addr) 364 { 365 struct sch311x_pdev_data pdata; 366 int err; 367 368 pdata.runtime_reg = addr; 369 370 sch311x_gpio_pdev = platform_device_alloc(DRV_NAME, -1); 371 if (!sch311x_gpio_pdev) 372 return -ENOMEM; 373 374 err = platform_device_add_data(sch311x_gpio_pdev, 375 &pdata, sizeof(pdata)); 376 if (err) { 377 pr_err(DRV_NAME "Platform data allocation failed\n"); 378 goto err; 379 } 380 381 err = platform_device_add(sch311x_gpio_pdev); 382 if (err) { 383 pr_err(DRV_NAME "Device addition failed\n"); 384 goto err; 385 } 386 return 0; 387 388 err: 389 platform_device_put(sch311x_gpio_pdev); 390 return err; 391 } 392 393 static int __init sch311x_gpio_init(void) 394 { 395 int err, i; 396 unsigned short addr = 0; 397 398 for (i = 0; i < ARRAY_SIZE(sch311x_ioports); i++) 399 if (sch311x_detect(sch311x_ioports[i], &addr) == 0) 400 break; 401 402 if (!addr) 403 return -ENODEV; 404 405 err = platform_driver_register(&sch311x_gpio_driver); 406 if (err) 407 return err; 408 409 err = sch311x_gpio_pdev_add(addr); 410 if (err) 411 goto unreg_platform_driver; 412 413 return 0; 414 415 unreg_platform_driver: 416 platform_driver_unregister(&sch311x_gpio_driver); 417 return err; 418 } 419 420 static void __exit sch311x_gpio_exit(void) 421 { 422 platform_device_unregister(sch311x_gpio_pdev); 423 platform_driver_unregister(&sch311x_gpio_driver); 424 } 425 426 module_init(sch311x_gpio_init); 427 module_exit(sch311x_gpio_exit); 428 429 MODULE_AUTHOR("Bruno Randolf <br1@einfach.org>"); 430 MODULE_DESCRIPTION("SMSC SCH311x GPIO Driver"); 431 MODULE_LICENSE("GPL"); 432 MODULE_ALIAS("platform:gpio-sch311x"); 433