1 /* 2 * Silicon Labs C2 port core Linux support 3 * 4 * Copyright (c) 2007 Rodolfo Giometti <giometti@linux.it> 5 * Copyright (c) 2007 Eurotech S.p.A. <info@eurotech.it> 6 * 7 * This program is free software; you can redistribute it and/or modify it 8 * under the terms of the GNU General Public License version 2 as published by 9 * the Free Software Foundation 10 */ 11 12 #include <linux/module.h> 13 #include <linux/init.h> 14 #include <linux/device.h> 15 #include <linux/errno.h> 16 #include <linux/err.h> 17 #include <linux/kernel.h> 18 #include <linux/kmemcheck.h> 19 #include <linux/ctype.h> 20 #include <linux/delay.h> 21 #include <linux/idr.h> 22 #include <linux/sched.h> 23 #include <linux/slab.h> 24 25 #include <linux/c2port.h> 26 27 #define DRIVER_NAME "c2port" 28 #define DRIVER_VERSION "0.51.0" 29 30 static DEFINE_SPINLOCK(c2port_idr_lock); 31 static DEFINE_IDR(c2port_idr); 32 33 /* 34 * Local variables 35 */ 36 37 static struct class *c2port_class; 38 39 /* 40 * C2 registers & commands defines 41 */ 42 43 /* C2 registers */ 44 #define C2PORT_DEVICEID 0x00 45 #define C2PORT_REVID 0x01 46 #define C2PORT_FPCTL 0x02 47 #define C2PORT_FPDAT 0xB4 48 49 /* C2 interface commands */ 50 #define C2PORT_GET_VERSION 0x01 51 #define C2PORT_DEVICE_ERASE 0x03 52 #define C2PORT_BLOCK_READ 0x06 53 #define C2PORT_BLOCK_WRITE 0x07 54 #define C2PORT_PAGE_ERASE 0x08 55 56 /* C2 status return codes */ 57 #define C2PORT_INVALID_COMMAND 0x00 58 #define C2PORT_COMMAND_FAILED 0x02 59 #define C2PORT_COMMAND_OK 0x0d 60 61 /* 62 * C2 port low level signal managements 63 */ 64 65 static void c2port_reset(struct c2port_device *dev) 66 { 67 struct c2port_ops *ops = dev->ops; 68 69 /* To reset the device we have to keep clock line low for at least 70 * 20us. 71 */ 72 local_irq_disable(); 73 ops->c2ck_set(dev, 0); 74 udelay(25); 75 ops->c2ck_set(dev, 1); 76 local_irq_enable(); 77 78 udelay(1); 79 } 80 81 static void c2port_strobe_ck(struct c2port_device *dev) 82 { 83 struct c2port_ops *ops = dev->ops; 84 85 /* During hi-low-hi transition we disable local IRQs to avoid 86 * interructions since C2 port specification says that it must be 87 * shorter than 5us, otherwise the microcontroller may consider 88 * it as a reset signal! 89 */ 90 local_irq_disable(); 91 ops->c2ck_set(dev, 0); 92 udelay(1); 93 ops->c2ck_set(dev, 1); 94 local_irq_enable(); 95 96 udelay(1); 97 } 98 99 /* 100 * C2 port basic functions 101 */ 102 103 static void c2port_write_ar(struct c2port_device *dev, u8 addr) 104 { 105 struct c2port_ops *ops = dev->ops; 106 int i; 107 108 /* START field */ 109 c2port_strobe_ck(dev); 110 111 /* INS field (11b, LSB first) */ 112 ops->c2d_dir(dev, 0); 113 ops->c2d_set(dev, 1); 114 c2port_strobe_ck(dev); 115 ops->c2d_set(dev, 1); 116 c2port_strobe_ck(dev); 117 118 /* ADDRESS field */ 119 for (i = 0; i < 8; i++) { 120 ops->c2d_set(dev, addr & 0x01); 121 c2port_strobe_ck(dev); 122 123 addr >>= 1; 124 } 125 126 /* STOP field */ 127 ops->c2d_dir(dev, 1); 128 c2port_strobe_ck(dev); 129 } 130 131 static int c2port_read_ar(struct c2port_device *dev, u8 *addr) 132 { 133 struct c2port_ops *ops = dev->ops; 134 int i; 135 136 /* START field */ 137 c2port_strobe_ck(dev); 138 139 /* INS field (10b, LSB first) */ 140 ops->c2d_dir(dev, 0); 141 ops->c2d_set(dev, 0); 142 c2port_strobe_ck(dev); 143 ops->c2d_set(dev, 1); 144 c2port_strobe_ck(dev); 145 146 /* ADDRESS field */ 147 ops->c2d_dir(dev, 1); 148 *addr = 0; 149 for (i = 0; i < 8; i++) { 150 *addr >>= 1; /* shift in 8-bit ADDRESS field LSB first */ 151 152 c2port_strobe_ck(dev); 153 if (ops->c2d_get(dev)) 154 *addr |= 0x80; 155 } 156 157 /* STOP field */ 158 c2port_strobe_ck(dev); 159 160 return 0; 161 } 162 163 static int c2port_write_dr(struct c2port_device *dev, u8 data) 164 { 165 struct c2port_ops *ops = dev->ops; 166 int timeout, i; 167 168 /* START field */ 169 c2port_strobe_ck(dev); 170 171 /* INS field (01b, LSB first) */ 172 ops->c2d_dir(dev, 0); 173 ops->c2d_set(dev, 1); 174 c2port_strobe_ck(dev); 175 ops->c2d_set(dev, 0); 176 c2port_strobe_ck(dev); 177 178 /* LENGTH field (00b, LSB first -> 1 byte) */ 179 ops->c2d_set(dev, 0); 180 c2port_strobe_ck(dev); 181 ops->c2d_set(dev, 0); 182 c2port_strobe_ck(dev); 183 184 /* DATA field */ 185 for (i = 0; i < 8; i++) { 186 ops->c2d_set(dev, data & 0x01); 187 c2port_strobe_ck(dev); 188 189 data >>= 1; 190 } 191 192 /* WAIT field */ 193 ops->c2d_dir(dev, 1); 194 timeout = 20; 195 do { 196 c2port_strobe_ck(dev); 197 if (ops->c2d_get(dev)) 198 break; 199 200 udelay(1); 201 } while (--timeout > 0); 202 if (timeout == 0) 203 return -EIO; 204 205 /* STOP field */ 206 c2port_strobe_ck(dev); 207 208 return 0; 209 } 210 211 static int c2port_read_dr(struct c2port_device *dev, u8 *data) 212 { 213 struct c2port_ops *ops = dev->ops; 214 int timeout, i; 215 216 /* START field */ 217 c2port_strobe_ck(dev); 218 219 /* INS field (00b, LSB first) */ 220 ops->c2d_dir(dev, 0); 221 ops->c2d_set(dev, 0); 222 c2port_strobe_ck(dev); 223 ops->c2d_set(dev, 0); 224 c2port_strobe_ck(dev); 225 226 /* LENGTH field (00b, LSB first -> 1 byte) */ 227 ops->c2d_set(dev, 0); 228 c2port_strobe_ck(dev); 229 ops->c2d_set(dev, 0); 230 c2port_strobe_ck(dev); 231 232 /* WAIT field */ 233 ops->c2d_dir(dev, 1); 234 timeout = 20; 235 do { 236 c2port_strobe_ck(dev); 237 if (ops->c2d_get(dev)) 238 break; 239 240 udelay(1); 241 } while (--timeout > 0); 242 if (timeout == 0) 243 return -EIO; 244 245 /* DATA field */ 246 *data = 0; 247 for (i = 0; i < 8; i++) { 248 *data >>= 1; /* shift in 8-bit DATA field LSB first */ 249 250 c2port_strobe_ck(dev); 251 if (ops->c2d_get(dev)) 252 *data |= 0x80; 253 } 254 255 /* STOP field */ 256 c2port_strobe_ck(dev); 257 258 return 0; 259 } 260 261 static int c2port_poll_in_busy(struct c2port_device *dev) 262 { 263 u8 addr; 264 int ret, timeout = 20; 265 266 do { 267 ret = (c2port_read_ar(dev, &addr)); 268 if (ret < 0) 269 return -EIO; 270 271 if (!(addr & 0x02)) 272 break; 273 274 udelay(1); 275 } while (--timeout > 0); 276 if (timeout == 0) 277 return -EIO; 278 279 return 0; 280 } 281 282 static int c2port_poll_out_ready(struct c2port_device *dev) 283 { 284 u8 addr; 285 int ret, timeout = 10000; /* erase flash needs long time... */ 286 287 do { 288 ret = (c2port_read_ar(dev, &addr)); 289 if (ret < 0) 290 return -EIO; 291 292 if (addr & 0x01) 293 break; 294 295 udelay(1); 296 } while (--timeout > 0); 297 if (timeout == 0) 298 return -EIO; 299 300 return 0; 301 } 302 303 /* 304 * sysfs methods 305 */ 306 307 static ssize_t c2port_show_name(struct device *dev, 308 struct device_attribute *attr, char *buf) 309 { 310 struct c2port_device *c2dev = dev_get_drvdata(dev); 311 312 return sprintf(buf, "%s\n", c2dev->name); 313 } 314 315 static ssize_t c2port_show_flash_blocks_num(struct device *dev, 316 struct device_attribute *attr, char *buf) 317 { 318 struct c2port_device *c2dev = dev_get_drvdata(dev); 319 struct c2port_ops *ops = c2dev->ops; 320 321 return sprintf(buf, "%d\n", ops->blocks_num); 322 } 323 324 static ssize_t c2port_show_flash_block_size(struct device *dev, 325 struct device_attribute *attr, char *buf) 326 { 327 struct c2port_device *c2dev = dev_get_drvdata(dev); 328 struct c2port_ops *ops = c2dev->ops; 329 330 return sprintf(buf, "%d\n", ops->block_size); 331 } 332 333 static ssize_t c2port_show_flash_size(struct device *dev, 334 struct device_attribute *attr, char *buf) 335 { 336 struct c2port_device *c2dev = dev_get_drvdata(dev); 337 struct c2port_ops *ops = c2dev->ops; 338 339 return sprintf(buf, "%d\n", ops->blocks_num * ops->block_size); 340 } 341 342 static ssize_t c2port_show_access(struct device *dev, 343 struct device_attribute *attr, char *buf) 344 { 345 struct c2port_device *c2dev = dev_get_drvdata(dev); 346 347 return sprintf(buf, "%d\n", c2dev->access); 348 } 349 350 static ssize_t c2port_store_access(struct device *dev, 351 struct device_attribute *attr, 352 const char *buf, size_t count) 353 { 354 struct c2port_device *c2dev = dev_get_drvdata(dev); 355 struct c2port_ops *ops = c2dev->ops; 356 int status, ret; 357 358 ret = sscanf(buf, "%d", &status); 359 if (ret != 1) 360 return -EINVAL; 361 362 mutex_lock(&c2dev->mutex); 363 364 c2dev->access = !!status; 365 366 /* If access is "on" clock should be HIGH _before_ setting the line 367 * as output and data line should be set as INPUT anyway */ 368 if (c2dev->access) 369 ops->c2ck_set(c2dev, 1); 370 ops->access(c2dev, c2dev->access); 371 if (c2dev->access) 372 ops->c2d_dir(c2dev, 1); 373 374 mutex_unlock(&c2dev->mutex); 375 376 return count; 377 } 378 379 static ssize_t c2port_store_reset(struct device *dev, 380 struct device_attribute *attr, 381 const char *buf, size_t count) 382 { 383 struct c2port_device *c2dev = dev_get_drvdata(dev); 384 385 /* Check the device access status */ 386 if (!c2dev->access) 387 return -EBUSY; 388 389 mutex_lock(&c2dev->mutex); 390 391 c2port_reset(c2dev); 392 c2dev->flash_access = 0; 393 394 mutex_unlock(&c2dev->mutex); 395 396 return count; 397 } 398 399 static ssize_t __c2port_show_dev_id(struct c2port_device *dev, char *buf) 400 { 401 u8 data; 402 int ret; 403 404 /* Select DEVICEID register for C2 data register accesses */ 405 c2port_write_ar(dev, C2PORT_DEVICEID); 406 407 /* Read and return the device ID register */ 408 ret = c2port_read_dr(dev, &data); 409 if (ret < 0) 410 return ret; 411 412 return sprintf(buf, "%d\n", data); 413 } 414 415 static ssize_t c2port_show_dev_id(struct device *dev, 416 struct device_attribute *attr, char *buf) 417 { 418 struct c2port_device *c2dev = dev_get_drvdata(dev); 419 ssize_t ret; 420 421 /* Check the device access status */ 422 if (!c2dev->access) 423 return -EBUSY; 424 425 mutex_lock(&c2dev->mutex); 426 ret = __c2port_show_dev_id(c2dev, buf); 427 mutex_unlock(&c2dev->mutex); 428 429 if (ret < 0) 430 dev_err(dev, "cannot read from %s\n", c2dev->name); 431 432 return ret; 433 } 434 435 static ssize_t __c2port_show_rev_id(struct c2port_device *dev, char *buf) 436 { 437 u8 data; 438 int ret; 439 440 /* Select REVID register for C2 data register accesses */ 441 c2port_write_ar(dev, C2PORT_REVID); 442 443 /* Read and return the revision ID register */ 444 ret = c2port_read_dr(dev, &data); 445 if (ret < 0) 446 return ret; 447 448 return sprintf(buf, "%d\n", data); 449 } 450 451 static ssize_t c2port_show_rev_id(struct device *dev, 452 struct device_attribute *attr, char *buf) 453 { 454 struct c2port_device *c2dev = dev_get_drvdata(dev); 455 ssize_t ret; 456 457 /* Check the device access status */ 458 if (!c2dev->access) 459 return -EBUSY; 460 461 mutex_lock(&c2dev->mutex); 462 ret = __c2port_show_rev_id(c2dev, buf); 463 mutex_unlock(&c2dev->mutex); 464 465 if (ret < 0) 466 dev_err(c2dev->dev, "cannot read from %s\n", c2dev->name); 467 468 return ret; 469 } 470 471 static ssize_t c2port_show_flash_access(struct device *dev, 472 struct device_attribute *attr, char *buf) 473 { 474 struct c2port_device *c2dev = dev_get_drvdata(dev); 475 476 return sprintf(buf, "%d\n", c2dev->flash_access); 477 } 478 479 static ssize_t __c2port_store_flash_access(struct c2port_device *dev, 480 int status) 481 { 482 int ret; 483 484 /* Check the device access status */ 485 if (!dev->access) 486 return -EBUSY; 487 488 dev->flash_access = !!status; 489 490 /* If flash_access is off we have nothing to do... */ 491 if (dev->flash_access == 0) 492 return 0; 493 494 /* Target the C2 flash programming control register for C2 data 495 * register access */ 496 c2port_write_ar(dev, C2PORT_FPCTL); 497 498 /* Write the first keycode to enable C2 Flash programming */ 499 ret = c2port_write_dr(dev, 0x02); 500 if (ret < 0) 501 return ret; 502 503 /* Write the second keycode to enable C2 Flash programming */ 504 ret = c2port_write_dr(dev, 0x01); 505 if (ret < 0) 506 return ret; 507 508 /* Delay for at least 20ms to ensure the target is ready for 509 * C2 flash programming */ 510 mdelay(25); 511 512 return 0; 513 } 514 515 static ssize_t c2port_store_flash_access(struct device *dev, 516 struct device_attribute *attr, 517 const char *buf, size_t count) 518 { 519 struct c2port_device *c2dev = dev_get_drvdata(dev); 520 int status; 521 ssize_t ret; 522 523 ret = sscanf(buf, "%d", &status); 524 if (ret != 1) 525 return -EINVAL; 526 527 mutex_lock(&c2dev->mutex); 528 ret = __c2port_store_flash_access(c2dev, status); 529 mutex_unlock(&c2dev->mutex); 530 531 if (ret < 0) { 532 dev_err(c2dev->dev, "cannot enable %s flash programming\n", 533 c2dev->name); 534 return ret; 535 } 536 537 return count; 538 } 539 540 static ssize_t __c2port_write_flash_erase(struct c2port_device *dev) 541 { 542 u8 status; 543 int ret; 544 545 /* Target the C2 flash programming data register for C2 data register 546 * access. 547 */ 548 c2port_write_ar(dev, C2PORT_FPDAT); 549 550 /* Send device erase command */ 551 c2port_write_dr(dev, C2PORT_DEVICE_ERASE); 552 553 /* Wait for input acknowledge */ 554 ret = c2port_poll_in_busy(dev); 555 if (ret < 0) 556 return ret; 557 558 /* Should check status before starting FLASH access sequence */ 559 560 /* Wait for status information */ 561 ret = c2port_poll_out_ready(dev); 562 if (ret < 0) 563 return ret; 564 565 /* Read flash programming interface status */ 566 ret = c2port_read_dr(dev, &status); 567 if (ret < 0) 568 return ret; 569 if (status != C2PORT_COMMAND_OK) 570 return -EBUSY; 571 572 /* Send a three-byte arming sequence to enable the device erase. 573 * If the sequence is not received correctly, the command will be 574 * ignored. 575 * Sequence is: 0xde, 0xad, 0xa5. 576 */ 577 c2port_write_dr(dev, 0xde); 578 ret = c2port_poll_in_busy(dev); 579 if (ret < 0) 580 return ret; 581 c2port_write_dr(dev, 0xad); 582 ret = c2port_poll_in_busy(dev); 583 if (ret < 0) 584 return ret; 585 c2port_write_dr(dev, 0xa5); 586 ret = c2port_poll_in_busy(dev); 587 if (ret < 0) 588 return ret; 589 590 ret = c2port_poll_out_ready(dev); 591 if (ret < 0) 592 return ret; 593 594 return 0; 595 } 596 597 static ssize_t c2port_store_flash_erase(struct device *dev, 598 struct device_attribute *attr, 599 const char *buf, size_t count) 600 { 601 struct c2port_device *c2dev = dev_get_drvdata(dev); 602 int ret; 603 604 /* Check the device and flash access status */ 605 if (!c2dev->access || !c2dev->flash_access) 606 return -EBUSY; 607 608 mutex_lock(&c2dev->mutex); 609 ret = __c2port_write_flash_erase(c2dev); 610 mutex_unlock(&c2dev->mutex); 611 612 if (ret < 0) { 613 dev_err(c2dev->dev, "cannot erase %s flash\n", c2dev->name); 614 return ret; 615 } 616 617 return count; 618 } 619 620 static ssize_t __c2port_read_flash_data(struct c2port_device *dev, 621 char *buffer, loff_t offset, size_t count) 622 { 623 struct c2port_ops *ops = dev->ops; 624 u8 status, nread = 128; 625 int i, ret; 626 627 /* Check for flash end */ 628 if (offset >= ops->block_size * ops->blocks_num) 629 return 0; 630 631 if (ops->block_size * ops->blocks_num - offset < nread) 632 nread = ops->block_size * ops->blocks_num - offset; 633 if (count < nread) 634 nread = count; 635 if (nread == 0) 636 return nread; 637 638 /* Target the C2 flash programming data register for C2 data register 639 * access */ 640 c2port_write_ar(dev, C2PORT_FPDAT); 641 642 /* Send flash block read command */ 643 c2port_write_dr(dev, C2PORT_BLOCK_READ); 644 645 /* Wait for input acknowledge */ 646 ret = c2port_poll_in_busy(dev); 647 if (ret < 0) 648 return ret; 649 650 /* Should check status before starting FLASH access sequence */ 651 652 /* Wait for status information */ 653 ret = c2port_poll_out_ready(dev); 654 if (ret < 0) 655 return ret; 656 657 /* Read flash programming interface status */ 658 ret = c2port_read_dr(dev, &status); 659 if (ret < 0) 660 return ret; 661 if (status != C2PORT_COMMAND_OK) 662 return -EBUSY; 663 664 /* Send address high byte */ 665 c2port_write_dr(dev, offset >> 8); 666 ret = c2port_poll_in_busy(dev); 667 if (ret < 0) 668 return ret; 669 670 /* Send address low byte */ 671 c2port_write_dr(dev, offset & 0x00ff); 672 ret = c2port_poll_in_busy(dev); 673 if (ret < 0) 674 return ret; 675 676 /* Send address block size */ 677 c2port_write_dr(dev, nread); 678 ret = c2port_poll_in_busy(dev); 679 if (ret < 0) 680 return ret; 681 682 /* Should check status before reading FLASH block */ 683 684 /* Wait for status information */ 685 ret = c2port_poll_out_ready(dev); 686 if (ret < 0) 687 return ret; 688 689 /* Read flash programming interface status */ 690 ret = c2port_read_dr(dev, &status); 691 if (ret < 0) 692 return ret; 693 if (status != C2PORT_COMMAND_OK) 694 return -EBUSY; 695 696 /* Read flash block */ 697 for (i = 0; i < nread; i++) { 698 ret = c2port_poll_out_ready(dev); 699 if (ret < 0) 700 return ret; 701 702 ret = c2port_read_dr(dev, buffer+i); 703 if (ret < 0) 704 return ret; 705 } 706 707 return nread; 708 } 709 710 static ssize_t c2port_read_flash_data(struct file *filp, struct kobject *kobj, 711 struct bin_attribute *attr, 712 char *buffer, loff_t offset, size_t count) 713 { 714 struct c2port_device *c2dev = 715 dev_get_drvdata(container_of(kobj, 716 struct device, kobj)); 717 ssize_t ret; 718 719 /* Check the device and flash access status */ 720 if (!c2dev->access || !c2dev->flash_access) 721 return -EBUSY; 722 723 mutex_lock(&c2dev->mutex); 724 ret = __c2port_read_flash_data(c2dev, buffer, offset, count); 725 mutex_unlock(&c2dev->mutex); 726 727 if (ret < 0) 728 dev_err(c2dev->dev, "cannot read %s flash\n", c2dev->name); 729 730 return ret; 731 } 732 733 static ssize_t __c2port_write_flash_data(struct c2port_device *dev, 734 char *buffer, loff_t offset, size_t count) 735 { 736 struct c2port_ops *ops = dev->ops; 737 u8 status, nwrite = 128; 738 int i, ret; 739 740 if (nwrite > count) 741 nwrite = count; 742 if (ops->block_size * ops->blocks_num - offset < nwrite) 743 nwrite = ops->block_size * ops->blocks_num - offset; 744 745 /* Check for flash end */ 746 if (offset >= ops->block_size * ops->blocks_num) 747 return -EINVAL; 748 749 /* Target the C2 flash programming data register for C2 data register 750 * access */ 751 c2port_write_ar(dev, C2PORT_FPDAT); 752 753 /* Send flash block write command */ 754 c2port_write_dr(dev, C2PORT_BLOCK_WRITE); 755 756 /* Wait for input acknowledge */ 757 ret = c2port_poll_in_busy(dev); 758 if (ret < 0) 759 return ret; 760 761 /* Should check status before starting FLASH access sequence */ 762 763 /* Wait for status information */ 764 ret = c2port_poll_out_ready(dev); 765 if (ret < 0) 766 return ret; 767 768 /* Read flash programming interface status */ 769 ret = c2port_read_dr(dev, &status); 770 if (ret < 0) 771 return ret; 772 if (status != C2PORT_COMMAND_OK) 773 return -EBUSY; 774 775 /* Send address high byte */ 776 c2port_write_dr(dev, offset >> 8); 777 ret = c2port_poll_in_busy(dev); 778 if (ret < 0) 779 return ret; 780 781 /* Send address low byte */ 782 c2port_write_dr(dev, offset & 0x00ff); 783 ret = c2port_poll_in_busy(dev); 784 if (ret < 0) 785 return ret; 786 787 /* Send address block size */ 788 c2port_write_dr(dev, nwrite); 789 ret = c2port_poll_in_busy(dev); 790 if (ret < 0) 791 return ret; 792 793 /* Should check status before writing FLASH block */ 794 795 /* Wait for status information */ 796 ret = c2port_poll_out_ready(dev); 797 if (ret < 0) 798 return ret; 799 800 /* Read flash programming interface status */ 801 ret = c2port_read_dr(dev, &status); 802 if (ret < 0) 803 return ret; 804 if (status != C2PORT_COMMAND_OK) 805 return -EBUSY; 806 807 /* Write flash block */ 808 for (i = 0; i < nwrite; i++) { 809 ret = c2port_write_dr(dev, *(buffer+i)); 810 if (ret < 0) 811 return ret; 812 813 ret = c2port_poll_in_busy(dev); 814 if (ret < 0) 815 return ret; 816 817 } 818 819 /* Wait for last flash write to complete */ 820 ret = c2port_poll_out_ready(dev); 821 if (ret < 0) 822 return ret; 823 824 return nwrite; 825 } 826 827 static ssize_t c2port_write_flash_data(struct file *filp, struct kobject *kobj, 828 struct bin_attribute *attr, 829 char *buffer, loff_t offset, size_t count) 830 { 831 struct c2port_device *c2dev = 832 dev_get_drvdata(container_of(kobj, 833 struct device, kobj)); 834 int ret; 835 836 /* Check the device access status */ 837 if (!c2dev->access || !c2dev->flash_access) 838 return -EBUSY; 839 840 mutex_lock(&c2dev->mutex); 841 ret = __c2port_write_flash_data(c2dev, buffer, offset, count); 842 mutex_unlock(&c2dev->mutex); 843 844 if (ret < 0) 845 dev_err(c2dev->dev, "cannot write %s flash\n", c2dev->name); 846 847 return ret; 848 } 849 850 /* 851 * Class attributes 852 */ 853 854 static struct device_attribute c2port_attrs[] = { 855 __ATTR(name, 0444, c2port_show_name, NULL), 856 __ATTR(flash_blocks_num, 0444, c2port_show_flash_blocks_num, NULL), 857 __ATTR(flash_block_size, 0444, c2port_show_flash_block_size, NULL), 858 __ATTR(flash_size, 0444, c2port_show_flash_size, NULL), 859 __ATTR(access, 0644, c2port_show_access, c2port_store_access), 860 __ATTR(reset, 0200, NULL, c2port_store_reset), 861 __ATTR(dev_id, 0444, c2port_show_dev_id, NULL), 862 __ATTR(rev_id, 0444, c2port_show_rev_id, NULL), 863 864 __ATTR(flash_access, 0644, c2port_show_flash_access, 865 c2port_store_flash_access), 866 __ATTR(flash_erase, 0200, NULL, c2port_store_flash_erase), 867 __ATTR_NULL, 868 }; 869 870 static struct bin_attribute c2port_bin_attrs = { 871 .attr = { 872 .name = "flash_data", 873 .mode = 0644 874 }, 875 .read = c2port_read_flash_data, 876 .write = c2port_write_flash_data, 877 /* .size is computed at run-time */ 878 }; 879 880 /* 881 * Exported functions 882 */ 883 884 struct c2port_device *c2port_device_register(char *name, 885 struct c2port_ops *ops, void *devdata) 886 { 887 struct c2port_device *c2dev; 888 int id, ret; 889 890 if (unlikely(!ops) || unlikely(!ops->access) || \ 891 unlikely(!ops->c2d_dir) || unlikely(!ops->c2ck_set) || \ 892 unlikely(!ops->c2d_get) || unlikely(!ops->c2d_set)) 893 return ERR_PTR(-EINVAL); 894 895 c2dev = kmalloc(sizeof(struct c2port_device), GFP_KERNEL); 896 kmemcheck_annotate_bitfield(c2dev, flags); 897 if (unlikely(!c2dev)) 898 return ERR_PTR(-ENOMEM); 899 900 ret = idr_pre_get(&c2port_idr, GFP_KERNEL); 901 if (!ret) { 902 ret = -ENOMEM; 903 goto error_idr_get_new; 904 } 905 906 spin_lock_irq(&c2port_idr_lock); 907 ret = idr_get_new(&c2port_idr, c2dev, &id); 908 spin_unlock_irq(&c2port_idr_lock); 909 910 if (ret < 0) 911 goto error_idr_get_new; 912 c2dev->id = id; 913 914 c2dev->dev = device_create(c2port_class, NULL, 0, c2dev, 915 "c2port%d", id); 916 if (unlikely(IS_ERR(c2dev->dev))) { 917 ret = PTR_ERR(c2dev->dev); 918 goto error_device_create; 919 } 920 dev_set_drvdata(c2dev->dev, c2dev); 921 922 strncpy(c2dev->name, name, C2PORT_NAME_LEN); 923 c2dev->ops = ops; 924 mutex_init(&c2dev->mutex); 925 926 /* Create binary file */ 927 c2port_bin_attrs.size = ops->blocks_num * ops->block_size; 928 ret = device_create_bin_file(c2dev->dev, &c2port_bin_attrs); 929 if (unlikely(ret)) 930 goto error_device_create_bin_file; 931 932 /* By default C2 port access is off */ 933 c2dev->access = c2dev->flash_access = 0; 934 ops->access(c2dev, 0); 935 936 dev_info(c2dev->dev, "C2 port %s added\n", name); 937 dev_info(c2dev->dev, "%s flash has %d blocks x %d bytes " 938 "(%d bytes total)\n", 939 name, ops->blocks_num, ops->block_size, 940 ops->blocks_num * ops->block_size); 941 942 return c2dev; 943 944 error_device_create_bin_file: 945 device_destroy(c2port_class, 0); 946 947 error_device_create: 948 spin_lock_irq(&c2port_idr_lock); 949 idr_remove(&c2port_idr, id); 950 spin_unlock_irq(&c2port_idr_lock); 951 952 error_idr_get_new: 953 kfree(c2dev); 954 955 return ERR_PTR(ret); 956 } 957 EXPORT_SYMBOL(c2port_device_register); 958 959 void c2port_device_unregister(struct c2port_device *c2dev) 960 { 961 if (!c2dev) 962 return; 963 964 dev_info(c2dev->dev, "C2 port %s removed\n", c2dev->name); 965 966 device_remove_bin_file(c2dev->dev, &c2port_bin_attrs); 967 spin_lock_irq(&c2port_idr_lock); 968 idr_remove(&c2port_idr, c2dev->id); 969 spin_unlock_irq(&c2port_idr_lock); 970 971 device_destroy(c2port_class, c2dev->id); 972 973 kfree(c2dev); 974 } 975 EXPORT_SYMBOL(c2port_device_unregister); 976 977 /* 978 * Module stuff 979 */ 980 981 static int __init c2port_init(void) 982 { 983 printk(KERN_INFO "Silicon Labs C2 port support v. " DRIVER_VERSION 984 " - (C) 2007 Rodolfo Giometti\n"); 985 986 c2port_class = class_create(THIS_MODULE, "c2port"); 987 if (!c2port_class) { 988 printk(KERN_ERR "c2port: failed to allocate class\n"); 989 return -ENOMEM; 990 } 991 c2port_class->dev_attrs = c2port_attrs; 992 993 return 0; 994 } 995 996 static void __exit c2port_exit(void) 997 { 998 class_destroy(c2port_class); 999 } 1000 1001 module_init(c2port_init); 1002 module_exit(c2port_exit); 1003 1004 MODULE_AUTHOR("Rodolfo Giometti <giometti@linux.it>"); 1005 MODULE_DESCRIPTION("Silicon Labs C2 port support v. " DRIVER_VERSION); 1006 MODULE_LICENSE("GPL"); 1007