diff options
Diffstat (limited to 'drivers/cdrom/cdrom.c')
-rw-r--r-- | drivers/cdrom/cdrom.c | 328 |
1 files changed, 202 insertions, 126 deletions
diff --git a/drivers/cdrom/cdrom.c b/drivers/cdrom/cdrom.c index 12f5baea439b..ac3829030ac5 100644 --- a/drivers/cdrom/cdrom.c +++ b/drivers/cdrom/cdrom.c | |||
@@ -360,10 +360,9 @@ static int cdrom_mrw_exit(struct cdrom_device_info *cdi); | |||
360 | 360 | ||
361 | static int cdrom_get_disc_info(struct cdrom_device_info *cdi, disc_information *di); | 361 | static int cdrom_get_disc_info(struct cdrom_device_info *cdi, disc_information *di); |
362 | 362 | ||
363 | #ifdef CONFIG_SYSCTL | ||
364 | static void cdrom_sysctl_register(void); | 363 | static void cdrom_sysctl_register(void); |
365 | #endif /* CONFIG_SYSCTL */ | 364 | |
366 | static struct cdrom_device_info *topCdromPtr; | 365 | static LIST_HEAD(cdrom_list); |
367 | 366 | ||
368 | static int cdrom_dummy_generic_packet(struct cdrom_device_info *cdi, | 367 | static int cdrom_dummy_generic_packet(struct cdrom_device_info *cdi, |
369 | struct packet_command *cgc) | 368 | struct packet_command *cgc) |
@@ -394,13 +393,11 @@ int register_cdrom(struct cdrom_device_info *cdi) | |||
394 | cdinfo(CD_OPEN, "entering register_cdrom\n"); | 393 | cdinfo(CD_OPEN, "entering register_cdrom\n"); |
395 | 394 | ||
396 | if (cdo->open == NULL || cdo->release == NULL) | 395 | if (cdo->open == NULL || cdo->release == NULL) |
397 | return -2; | 396 | return -EINVAL; |
398 | if (!banner_printed) { | 397 | if (!banner_printed) { |
399 | printk(KERN_INFO "Uniform CD-ROM driver " REVISION "\n"); | 398 | printk(KERN_INFO "Uniform CD-ROM driver " REVISION "\n"); |
400 | banner_printed = 1; | 399 | banner_printed = 1; |
401 | #ifdef CONFIG_SYSCTL | ||
402 | cdrom_sysctl_register(); | 400 | cdrom_sysctl_register(); |
403 | #endif /* CONFIG_SYSCTL */ | ||
404 | } | 401 | } |
405 | 402 | ||
406 | ENSURE(drive_status, CDC_DRIVE_STATUS ); | 403 | ENSURE(drive_status, CDC_DRIVE_STATUS ); |
@@ -439,35 +436,18 @@ int register_cdrom(struct cdrom_device_info *cdi) | |||
439 | 436 | ||
440 | cdinfo(CD_REG_UNREG, "drive \"/dev/%s\" registered\n", cdi->name); | 437 | cdinfo(CD_REG_UNREG, "drive \"/dev/%s\" registered\n", cdi->name); |
441 | mutex_lock(&cdrom_mutex); | 438 | mutex_lock(&cdrom_mutex); |
442 | cdi->next = topCdromPtr; | 439 | list_add(&cdi->list, &cdrom_list); |
443 | topCdromPtr = cdi; | ||
444 | mutex_unlock(&cdrom_mutex); | 440 | mutex_unlock(&cdrom_mutex); |
445 | return 0; | 441 | return 0; |
446 | } | 442 | } |
447 | #undef ENSURE | 443 | #undef ENSURE |
448 | 444 | ||
449 | int unregister_cdrom(struct cdrom_device_info *unreg) | 445 | void unregister_cdrom(struct cdrom_device_info *cdi) |
450 | { | 446 | { |
451 | struct cdrom_device_info *cdi, *prev; | ||
452 | cdinfo(CD_OPEN, "entering unregister_cdrom\n"); | 447 | cdinfo(CD_OPEN, "entering unregister_cdrom\n"); |
453 | 448 | ||
454 | prev = NULL; | ||
455 | mutex_lock(&cdrom_mutex); | 449 | mutex_lock(&cdrom_mutex); |
456 | cdi = topCdromPtr; | 450 | list_del(&cdi->list); |
457 | while (cdi && cdi != unreg) { | ||
458 | prev = cdi; | ||
459 | cdi = cdi->next; | ||
460 | } | ||
461 | |||
462 | if (cdi == NULL) { | ||
463 | mutex_unlock(&cdrom_mutex); | ||
464 | return -2; | ||
465 | } | ||
466 | if (prev) | ||
467 | prev->next = cdi->next; | ||
468 | else | ||
469 | topCdromPtr = cdi->next; | ||
470 | |||
471 | mutex_unlock(&cdrom_mutex); | 451 | mutex_unlock(&cdrom_mutex); |
472 | 452 | ||
473 | if (cdi->exit) | 453 | if (cdi->exit) |
@@ -475,34 +455,43 @@ int unregister_cdrom(struct cdrom_device_info *unreg) | |||
475 | 455 | ||
476 | cdi->ops->n_minors--; | 456 | cdi->ops->n_minors--; |
477 | cdinfo(CD_REG_UNREG, "drive \"/dev/%s\" unregistered\n", cdi->name); | 457 | cdinfo(CD_REG_UNREG, "drive \"/dev/%s\" unregistered\n", cdi->name); |
478 | return 0; | ||
479 | } | 458 | } |
480 | 459 | ||
481 | int cdrom_get_media_event(struct cdrom_device_info *cdi, | 460 | int cdrom_get_media_event(struct cdrom_device_info *cdi, |
482 | struct media_event_desc *med) | 461 | struct media_event_desc *med) |
483 | { | 462 | { |
484 | struct packet_command cgc; | 463 | struct packet_command cgc; |
485 | unsigned char buffer[8]; | 464 | unsigned char *buffer; |
486 | struct event_header *eh = (struct event_header *) buffer; | 465 | struct event_header *eh; |
466 | int ret = 1; | ||
487 | 467 | ||
488 | init_cdrom_command(&cgc, buffer, sizeof(buffer), CGC_DATA_READ); | 468 | buffer = kmalloc(8, GFP_KERNEL); |
469 | if (!buffer) | ||
470 | return -ENOMEM; | ||
471 | |||
472 | eh = (struct event_header *)buffer; | ||
473 | |||
474 | init_cdrom_command(&cgc, buffer, 8, CGC_DATA_READ); | ||
489 | cgc.cmd[0] = GPCMD_GET_EVENT_STATUS_NOTIFICATION; | 475 | cgc.cmd[0] = GPCMD_GET_EVENT_STATUS_NOTIFICATION; |
490 | cgc.cmd[1] = 1; /* IMMED */ | 476 | cgc.cmd[1] = 1; /* IMMED */ |
491 | cgc.cmd[4] = 1 << 4; /* media event */ | 477 | cgc.cmd[4] = 1 << 4; /* media event */ |
492 | cgc.cmd[8] = sizeof(buffer); | 478 | cgc.cmd[8] = 8; |
493 | cgc.quiet = 1; | 479 | cgc.quiet = 1; |
494 | 480 | ||
495 | if (cdi->ops->generic_packet(cdi, &cgc)) | 481 | if (cdi->ops->generic_packet(cdi, &cgc)) |
496 | return 1; | 482 | goto err; |
497 | 483 | ||
498 | if (be16_to_cpu(eh->data_len) < sizeof(*med)) | 484 | if (be16_to_cpu(eh->data_len) < sizeof(*med)) |
499 | return 1; | 485 | goto err; |
500 | 486 | ||
501 | if (eh->nea || eh->notification_class != 0x4) | 487 | if (eh->nea || eh->notification_class != 0x4) |
502 | return 1; | 488 | goto err; |
503 | 489 | ||
504 | memcpy(med, &buffer[sizeof(*eh)], sizeof(*med)); | 490 | memcpy(med, buffer + sizeof(*eh), sizeof(*med)); |
505 | return 0; | 491 | ret = 0; |
492 | err: | ||
493 | kfree(buffer); | ||
494 | return ret; | ||
506 | } | 495 | } |
507 | 496 | ||
508 | /* | 497 | /* |
@@ -512,68 +501,82 @@ int cdrom_get_media_event(struct cdrom_device_info *cdi, | |||
512 | static int cdrom_mrw_probe_pc(struct cdrom_device_info *cdi) | 501 | static int cdrom_mrw_probe_pc(struct cdrom_device_info *cdi) |
513 | { | 502 | { |
514 | struct packet_command cgc; | 503 | struct packet_command cgc; |
515 | char buffer[16]; | 504 | char *buffer; |
505 | int ret = 1; | ||
516 | 506 | ||
517 | init_cdrom_command(&cgc, buffer, sizeof(buffer), CGC_DATA_READ); | 507 | buffer = kmalloc(16, GFP_KERNEL); |
508 | if (!buffer) | ||
509 | return -ENOMEM; | ||
510 | |||
511 | init_cdrom_command(&cgc, buffer, 16, CGC_DATA_READ); | ||
518 | 512 | ||
519 | cgc.timeout = HZ; | 513 | cgc.timeout = HZ; |
520 | cgc.quiet = 1; | 514 | cgc.quiet = 1; |
521 | 515 | ||
522 | if (!cdrom_mode_sense(cdi, &cgc, MRW_MODE_PC, 0)) { | 516 | if (!cdrom_mode_sense(cdi, &cgc, MRW_MODE_PC, 0)) { |
523 | cdi->mrw_mode_page = MRW_MODE_PC; | 517 | cdi->mrw_mode_page = MRW_MODE_PC; |
524 | return 0; | 518 | ret = 0; |
525 | } else if (!cdrom_mode_sense(cdi, &cgc, MRW_MODE_PC_PRE1, 0)) { | 519 | } else if (!cdrom_mode_sense(cdi, &cgc, MRW_MODE_PC_PRE1, 0)) { |
526 | cdi->mrw_mode_page = MRW_MODE_PC_PRE1; | 520 | cdi->mrw_mode_page = MRW_MODE_PC_PRE1; |
527 | return 0; | 521 | ret = 0; |
528 | } | 522 | } |
529 | 523 | kfree(buffer); | |
530 | return 1; | 524 | return ret; |
531 | } | 525 | } |
532 | 526 | ||
533 | static int cdrom_is_mrw(struct cdrom_device_info *cdi, int *write) | 527 | static int cdrom_is_mrw(struct cdrom_device_info *cdi, int *write) |
534 | { | 528 | { |
535 | struct packet_command cgc; | 529 | struct packet_command cgc; |
536 | struct mrw_feature_desc *mfd; | 530 | struct mrw_feature_desc *mfd; |
537 | unsigned char buffer[16]; | 531 | unsigned char *buffer; |
538 | int ret; | 532 | int ret; |
539 | 533 | ||
540 | *write = 0; | 534 | *write = 0; |
535 | buffer = kmalloc(16, GFP_KERNEL); | ||
536 | if (!buffer) | ||
537 | return -ENOMEM; | ||
541 | 538 | ||
542 | init_cdrom_command(&cgc, buffer, sizeof(buffer), CGC_DATA_READ); | 539 | init_cdrom_command(&cgc, buffer, 16, CGC_DATA_READ); |
543 | 540 | ||
544 | cgc.cmd[0] = GPCMD_GET_CONFIGURATION; | 541 | cgc.cmd[0] = GPCMD_GET_CONFIGURATION; |
545 | cgc.cmd[3] = CDF_MRW; | 542 | cgc.cmd[3] = CDF_MRW; |
546 | cgc.cmd[8] = sizeof(buffer); | 543 | cgc.cmd[8] = 16; |
547 | cgc.quiet = 1; | 544 | cgc.quiet = 1; |
548 | 545 | ||
549 | if ((ret = cdi->ops->generic_packet(cdi, &cgc))) | 546 | if ((ret = cdi->ops->generic_packet(cdi, &cgc))) |
550 | return ret; | 547 | goto err; |
551 | 548 | ||
552 | mfd = (struct mrw_feature_desc *)&buffer[sizeof(struct feature_header)]; | 549 | mfd = (struct mrw_feature_desc *)&buffer[sizeof(struct feature_header)]; |
553 | if (be16_to_cpu(mfd->feature_code) != CDF_MRW) | 550 | if (be16_to_cpu(mfd->feature_code) != CDF_MRW) { |
554 | return 1; | 551 | ret = 1; |
552 | goto err; | ||
553 | } | ||
555 | *write = mfd->write; | 554 | *write = mfd->write; |
556 | 555 | ||
557 | if ((ret = cdrom_mrw_probe_pc(cdi))) { | 556 | if ((ret = cdrom_mrw_probe_pc(cdi))) { |
558 | *write = 0; | 557 | *write = 0; |
559 | return ret; | ||
560 | } | 558 | } |
561 | 559 | err: | |
562 | return 0; | 560 | kfree(buffer); |
561 | return ret; | ||
563 | } | 562 | } |
564 | 563 | ||
565 | static int cdrom_mrw_bgformat(struct cdrom_device_info *cdi, int cont) | 564 | static int cdrom_mrw_bgformat(struct cdrom_device_info *cdi, int cont) |
566 | { | 565 | { |
567 | struct packet_command cgc; | 566 | struct packet_command cgc; |
568 | unsigned char buffer[12]; | 567 | unsigned char *buffer; |
569 | int ret; | 568 | int ret; |
570 | 569 | ||
571 | printk(KERN_INFO "cdrom: %sstarting format\n", cont ? "Re" : ""); | 570 | printk(KERN_INFO "cdrom: %sstarting format\n", cont ? "Re" : ""); |
572 | 571 | ||
572 | buffer = kmalloc(12, GFP_KERNEL); | ||
573 | if (!buffer) | ||
574 | return -ENOMEM; | ||
575 | |||
573 | /* | 576 | /* |
574 | * FmtData bit set (bit 4), format type is 1 | 577 | * FmtData bit set (bit 4), format type is 1 |
575 | */ | 578 | */ |
576 | init_cdrom_command(&cgc, buffer, sizeof(buffer), CGC_DATA_WRITE); | 579 | init_cdrom_command(&cgc, buffer, 12, CGC_DATA_WRITE); |
577 | cgc.cmd[0] = GPCMD_FORMAT_UNIT; | 580 | cgc.cmd[0] = GPCMD_FORMAT_UNIT; |
578 | cgc.cmd[1] = (1 << 4) | 1; | 581 | cgc.cmd[1] = (1 << 4) | 1; |
579 | 582 | ||
@@ -600,6 +603,7 @@ static int cdrom_mrw_bgformat(struct cdrom_device_info *cdi, int cont) | |||
600 | if (ret) | 603 | if (ret) |
601 | printk(KERN_INFO "cdrom: bgformat failed\n"); | 604 | printk(KERN_INFO "cdrom: bgformat failed\n"); |
602 | 605 | ||
606 | kfree(buffer); | ||
603 | return ret; | 607 | return ret; |
604 | } | 608 | } |
605 | 609 | ||
@@ -659,16 +663,17 @@ static int cdrom_mrw_set_lba_space(struct cdrom_device_info *cdi, int space) | |||
659 | { | 663 | { |
660 | struct packet_command cgc; | 664 | struct packet_command cgc; |
661 | struct mode_page_header *mph; | 665 | struct mode_page_header *mph; |
662 | char buffer[16]; | 666 | char *buffer; |
663 | int ret, offset, size; | 667 | int ret, offset, size; |
664 | 668 | ||
665 | init_cdrom_command(&cgc, buffer, sizeof(buffer), CGC_DATA_READ); | 669 | buffer = kmalloc(16, GFP_KERNEL); |
670 | if (!buffer) | ||
671 | return -ENOMEM; | ||
666 | 672 | ||
667 | cgc.buffer = buffer; | 673 | init_cdrom_command(&cgc, buffer, 16, CGC_DATA_READ); |
668 | cgc.buflen = sizeof(buffer); | ||
669 | 674 | ||
670 | if ((ret = cdrom_mode_sense(cdi, &cgc, cdi->mrw_mode_page, 0))) | 675 | if ((ret = cdrom_mode_sense(cdi, &cgc, cdi->mrw_mode_page, 0))) |
671 | return ret; | 676 | goto err; |
672 | 677 | ||
673 | mph = (struct mode_page_header *) buffer; | 678 | mph = (struct mode_page_header *) buffer; |
674 | offset = be16_to_cpu(mph->desc_length); | 679 | offset = be16_to_cpu(mph->desc_length); |
@@ -678,55 +683,70 @@ static int cdrom_mrw_set_lba_space(struct cdrom_device_info *cdi, int space) | |||
678 | cgc.buflen = size; | 683 | cgc.buflen = size; |
679 | 684 | ||
680 | if ((ret = cdrom_mode_select(cdi, &cgc))) | 685 | if ((ret = cdrom_mode_select(cdi, &cgc))) |
681 | return ret; | 686 | goto err; |
682 | 687 | ||
683 | printk(KERN_INFO "cdrom: %s: mrw address space %s selected\n", cdi->name, mrw_address_space[space]); | 688 | printk(KERN_INFO "cdrom: %s: mrw address space %s selected\n", cdi->name, mrw_address_space[space]); |
684 | return 0; | 689 | ret = 0; |
690 | err: | ||
691 | kfree(buffer); | ||
692 | return ret; | ||
685 | } | 693 | } |
686 | 694 | ||
687 | static int cdrom_get_random_writable(struct cdrom_device_info *cdi, | 695 | static int cdrom_get_random_writable(struct cdrom_device_info *cdi, |
688 | struct rwrt_feature_desc *rfd) | 696 | struct rwrt_feature_desc *rfd) |
689 | { | 697 | { |
690 | struct packet_command cgc; | 698 | struct packet_command cgc; |
691 | char buffer[24]; | 699 | char *buffer; |
692 | int ret; | 700 | int ret; |
693 | 701 | ||
694 | init_cdrom_command(&cgc, buffer, sizeof(buffer), CGC_DATA_READ); | 702 | buffer = kmalloc(24, GFP_KERNEL); |
703 | if (!buffer) | ||
704 | return -ENOMEM; | ||
705 | |||
706 | init_cdrom_command(&cgc, buffer, 24, CGC_DATA_READ); | ||
695 | 707 | ||
696 | cgc.cmd[0] = GPCMD_GET_CONFIGURATION; /* often 0x46 */ | 708 | cgc.cmd[0] = GPCMD_GET_CONFIGURATION; /* often 0x46 */ |
697 | cgc.cmd[3] = CDF_RWRT; /* often 0x0020 */ | 709 | cgc.cmd[3] = CDF_RWRT; /* often 0x0020 */ |
698 | cgc.cmd[8] = sizeof(buffer); /* often 0x18 */ | 710 | cgc.cmd[8] = 24; /* often 0x18 */ |
699 | cgc.quiet = 1; | 711 | cgc.quiet = 1; |
700 | 712 | ||
701 | if ((ret = cdi->ops->generic_packet(cdi, &cgc))) | 713 | if ((ret = cdi->ops->generic_packet(cdi, &cgc))) |
702 | return ret; | 714 | goto err; |
703 | 715 | ||
704 | memcpy(rfd, &buffer[sizeof(struct feature_header)], sizeof (*rfd)); | 716 | memcpy(rfd, &buffer[sizeof(struct feature_header)], sizeof (*rfd)); |
705 | return 0; | 717 | ret = 0; |
718 | err: | ||
719 | kfree(buffer); | ||
720 | return ret; | ||
706 | } | 721 | } |
707 | 722 | ||
708 | static int cdrom_has_defect_mgt(struct cdrom_device_info *cdi) | 723 | static int cdrom_has_defect_mgt(struct cdrom_device_info *cdi) |
709 | { | 724 | { |
710 | struct packet_command cgc; | 725 | struct packet_command cgc; |
711 | char buffer[16]; | 726 | char *buffer; |
712 | __be16 *feature_code; | 727 | __be16 *feature_code; |
713 | int ret; | 728 | int ret; |
714 | 729 | ||
715 | init_cdrom_command(&cgc, buffer, sizeof(buffer), CGC_DATA_READ); | 730 | buffer = kmalloc(16, GFP_KERNEL); |
731 | if (!buffer) | ||
732 | return -ENOMEM; | ||
733 | |||
734 | init_cdrom_command(&cgc, buffer, 16, CGC_DATA_READ); | ||
716 | 735 | ||
717 | cgc.cmd[0] = GPCMD_GET_CONFIGURATION; | 736 | cgc.cmd[0] = GPCMD_GET_CONFIGURATION; |
718 | cgc.cmd[3] = CDF_HWDM; | 737 | cgc.cmd[3] = CDF_HWDM; |
719 | cgc.cmd[8] = sizeof(buffer); | 738 | cgc.cmd[8] = 16; |
720 | cgc.quiet = 1; | 739 | cgc.quiet = 1; |
721 | 740 | ||
722 | if ((ret = cdi->ops->generic_packet(cdi, &cgc))) | 741 | if ((ret = cdi->ops->generic_packet(cdi, &cgc))) |
723 | return ret; | 742 | goto err; |
724 | 743 | ||
725 | feature_code = (__be16 *) &buffer[sizeof(struct feature_header)]; | 744 | feature_code = (__be16 *) &buffer[sizeof(struct feature_header)]; |
726 | if (be16_to_cpu(*feature_code) == CDF_HWDM) | 745 | if (be16_to_cpu(*feature_code) == CDF_HWDM) |
727 | return 0; | 746 | ret = 0; |
728 | 747 | err: | |
729 | return 1; | 748 | kfree(buffer); |
749 | return ret; | ||
730 | } | 750 | } |
731 | 751 | ||
732 | 752 | ||
@@ -817,10 +837,14 @@ static int cdrom_mrw_open_write(struct cdrom_device_info *cdi) | |||
817 | static int mo_open_write(struct cdrom_device_info *cdi) | 837 | static int mo_open_write(struct cdrom_device_info *cdi) |
818 | { | 838 | { |
819 | struct packet_command cgc; | 839 | struct packet_command cgc; |
820 | char buffer[255]; | 840 | char *buffer; |
821 | int ret; | 841 | int ret; |
822 | 842 | ||
823 | init_cdrom_command(&cgc, &buffer, 4, CGC_DATA_READ); | 843 | buffer = kmalloc(255, GFP_KERNEL); |
844 | if (!buffer) | ||
845 | return -ENOMEM; | ||
846 | |||
847 | init_cdrom_command(&cgc, buffer, 4, CGC_DATA_READ); | ||
824 | cgc.quiet = 1; | 848 | cgc.quiet = 1; |
825 | 849 | ||
826 | /* | 850 | /* |
@@ -837,10 +861,15 @@ static int mo_open_write(struct cdrom_device_info *cdi) | |||
837 | } | 861 | } |
838 | 862 | ||
839 | /* drive gave us no info, let the user go ahead */ | 863 | /* drive gave us no info, let the user go ahead */ |
840 | if (ret) | 864 | if (ret) { |
841 | return 0; | 865 | ret = 0; |
866 | goto err; | ||
867 | } | ||
842 | 868 | ||
843 | return buffer[3] & 0x80; | 869 | ret = buffer[3] & 0x80; |
870 | err: | ||
871 | kfree(buffer); | ||
872 | return ret; | ||
844 | } | 873 | } |
845 | 874 | ||
846 | static int cdrom_ram_open_write(struct cdrom_device_info *cdi) | 875 | static int cdrom_ram_open_write(struct cdrom_device_info *cdi) |
@@ -863,15 +892,19 @@ static int cdrom_ram_open_write(struct cdrom_device_info *cdi) | |||
863 | static void cdrom_mmc3_profile(struct cdrom_device_info *cdi) | 892 | static void cdrom_mmc3_profile(struct cdrom_device_info *cdi) |
864 | { | 893 | { |
865 | struct packet_command cgc; | 894 | struct packet_command cgc; |
866 | char buffer[32]; | 895 | char *buffer; |
867 | int ret, mmc3_profile; | 896 | int ret, mmc3_profile; |
868 | 897 | ||
869 | init_cdrom_command(&cgc, buffer, sizeof(buffer), CGC_DATA_READ); | 898 | buffer = kmalloc(32, GFP_KERNEL); |
899 | if (!buffer) | ||
900 | return; | ||
901 | |||
902 | init_cdrom_command(&cgc, buffer, 32, CGC_DATA_READ); | ||
870 | 903 | ||
871 | cgc.cmd[0] = GPCMD_GET_CONFIGURATION; | 904 | cgc.cmd[0] = GPCMD_GET_CONFIGURATION; |
872 | cgc.cmd[1] = 0; | 905 | cgc.cmd[1] = 0; |
873 | cgc.cmd[2] = cgc.cmd[3] = 0; /* Starting Feature Number */ | 906 | cgc.cmd[2] = cgc.cmd[3] = 0; /* Starting Feature Number */ |
874 | cgc.cmd[8] = sizeof(buffer); /* Allocation Length */ | 907 | cgc.cmd[8] = 32; /* Allocation Length */ |
875 | cgc.quiet = 1; | 908 | cgc.quiet = 1; |
876 | 909 | ||
877 | if ((ret = cdi->ops->generic_packet(cdi, &cgc))) | 910 | if ((ret = cdi->ops->generic_packet(cdi, &cgc))) |
@@ -880,6 +913,7 @@ static void cdrom_mmc3_profile(struct cdrom_device_info *cdi) | |||
880 | mmc3_profile = (buffer[6] << 8) | buffer[7]; | 913 | mmc3_profile = (buffer[6] << 8) | buffer[7]; |
881 | 914 | ||
882 | cdi->mmc3_profile = mmc3_profile; | 915 | cdi->mmc3_profile = mmc3_profile; |
916 | kfree(buffer); | ||
883 | } | 917 | } |
884 | 918 | ||
885 | static int cdrom_is_dvd_rw(struct cdrom_device_info *cdi) | 919 | static int cdrom_is_dvd_rw(struct cdrom_device_info *cdi) |
@@ -1594,12 +1628,15 @@ static void setup_send_key(struct packet_command *cgc, unsigned agid, unsigned t | |||
1594 | static int dvd_do_auth(struct cdrom_device_info *cdi, dvd_authinfo *ai) | 1628 | static int dvd_do_auth(struct cdrom_device_info *cdi, dvd_authinfo *ai) |
1595 | { | 1629 | { |
1596 | int ret; | 1630 | int ret; |
1597 | u_char buf[20]; | 1631 | u_char *buf; |
1598 | struct packet_command cgc; | 1632 | struct packet_command cgc; |
1599 | struct cdrom_device_ops *cdo = cdi->ops; | 1633 | struct cdrom_device_ops *cdo = cdi->ops; |
1600 | rpc_state_t rpc_state; | 1634 | rpc_state_t *rpc_state; |
1635 | |||
1636 | buf = kzalloc(20, GFP_KERNEL); | ||
1637 | if (!buf) | ||
1638 | return -ENOMEM; | ||
1601 | 1639 | ||
1602 | memset(buf, 0, sizeof(buf)); | ||
1603 | init_cdrom_command(&cgc, buf, 0, CGC_DATA_READ); | 1640 | init_cdrom_command(&cgc, buf, 0, CGC_DATA_READ); |
1604 | 1641 | ||
1605 | switch (ai->type) { | 1642 | switch (ai->type) { |
@@ -1610,7 +1647,7 @@ static int dvd_do_auth(struct cdrom_device_info *cdi, dvd_authinfo *ai) | |||
1610 | setup_report_key(&cgc, ai->lsa.agid, 0); | 1647 | setup_report_key(&cgc, ai->lsa.agid, 0); |
1611 | 1648 | ||
1612 | if ((ret = cdo->generic_packet(cdi, &cgc))) | 1649 | if ((ret = cdo->generic_packet(cdi, &cgc))) |
1613 | return ret; | 1650 | goto err; |
1614 | 1651 | ||
1615 | ai->lsa.agid = buf[7] >> 6; | 1652 | ai->lsa.agid = buf[7] >> 6; |
1616 | /* Returning data, let host change state */ | 1653 | /* Returning data, let host change state */ |
@@ -1621,7 +1658,7 @@ static int dvd_do_auth(struct cdrom_device_info *cdi, dvd_authinfo *ai) | |||
1621 | setup_report_key(&cgc, ai->lsk.agid, 2); | 1658 | setup_report_key(&cgc, ai->lsk.agid, 2); |
1622 | 1659 | ||
1623 | if ((ret = cdo->generic_packet(cdi, &cgc))) | 1660 | if ((ret = cdo->generic_packet(cdi, &cgc))) |
1624 | return ret; | 1661 | goto err; |
1625 | 1662 | ||
1626 | copy_key(ai->lsk.key, &buf[4]); | 1663 | copy_key(ai->lsk.key, &buf[4]); |
1627 | /* Returning data, let host change state */ | 1664 | /* Returning data, let host change state */ |
@@ -1632,7 +1669,7 @@ static int dvd_do_auth(struct cdrom_device_info *cdi, dvd_authinfo *ai) | |||
1632 | setup_report_key(&cgc, ai->lsc.agid, 1); | 1669 | setup_report_key(&cgc, ai->lsc.agid, 1); |
1633 | 1670 | ||
1634 | if ((ret = cdo->generic_packet(cdi, &cgc))) | 1671 | if ((ret = cdo->generic_packet(cdi, &cgc))) |
1635 | return ret; | 1672 | goto err; |
1636 | 1673 | ||
1637 | copy_chal(ai->lsc.chal, &buf[4]); | 1674 | copy_chal(ai->lsc.chal, &buf[4]); |
1638 | /* Returning data, let host change state */ | 1675 | /* Returning data, let host change state */ |
@@ -1649,7 +1686,7 @@ static int dvd_do_auth(struct cdrom_device_info *cdi, dvd_authinfo *ai) | |||
1649 | cgc.cmd[2] = ai->lstk.lba >> 24; | 1686 | cgc.cmd[2] = ai->lstk.lba >> 24; |
1650 | 1687 | ||
1651 | if ((ret = cdo->generic_packet(cdi, &cgc))) | 1688 | if ((ret = cdo->generic_packet(cdi, &cgc))) |
1652 | return ret; | 1689 | goto err; |
1653 | 1690 | ||
1654 | ai->lstk.cpm = (buf[4] >> 7) & 1; | 1691 | ai->lstk.cpm = (buf[4] >> 7) & 1; |
1655 | ai->lstk.cp_sec = (buf[4] >> 6) & 1; | 1692 | ai->lstk.cp_sec = (buf[4] >> 6) & 1; |
@@ -1663,7 +1700,7 @@ static int dvd_do_auth(struct cdrom_device_info *cdi, dvd_authinfo *ai) | |||
1663 | setup_report_key(&cgc, ai->lsasf.agid, 5); | 1700 | setup_report_key(&cgc, ai->lsasf.agid, 5); |
1664 | 1701 | ||
1665 | if ((ret = cdo->generic_packet(cdi, &cgc))) | 1702 | if ((ret = cdo->generic_packet(cdi, &cgc))) |
1666 | return ret; | 1703 | goto err; |
1667 | 1704 | ||
1668 | ai->lsasf.asf = buf[7] & 1; | 1705 | ai->lsasf.asf = buf[7] & 1; |
1669 | break; | 1706 | break; |
@@ -1676,7 +1713,7 @@ static int dvd_do_auth(struct cdrom_device_info *cdi, dvd_authinfo *ai) | |||
1676 | copy_chal(&buf[4], ai->hsc.chal); | 1713 | copy_chal(&buf[4], ai->hsc.chal); |
1677 | 1714 | ||
1678 | if ((ret = cdo->generic_packet(cdi, &cgc))) | 1715 | if ((ret = cdo->generic_packet(cdi, &cgc))) |
1679 | return ret; | 1716 | goto err; |
1680 | 1717 | ||
1681 | ai->type = DVD_LU_SEND_KEY1; | 1718 | ai->type = DVD_LU_SEND_KEY1; |
1682 | break; | 1719 | break; |
@@ -1689,7 +1726,7 @@ static int dvd_do_auth(struct cdrom_device_info *cdi, dvd_authinfo *ai) | |||
1689 | 1726 | ||
1690 | if ((ret = cdo->generic_packet(cdi, &cgc))) { | 1727 | if ((ret = cdo->generic_packet(cdi, &cgc))) { |
1691 | ai->type = DVD_AUTH_FAILURE; | 1728 | ai->type = DVD_AUTH_FAILURE; |
1692 | return ret; | 1729 | goto err; |
1693 | } | 1730 | } |
1694 | ai->type = DVD_AUTH_ESTABLISHED; | 1731 | ai->type = DVD_AUTH_ESTABLISHED; |
1695 | break; | 1732 | break; |
@@ -1700,24 +1737,23 @@ static int dvd_do_auth(struct cdrom_device_info *cdi, dvd_authinfo *ai) | |||
1700 | cdinfo(CD_DVD, "entering DVD_INVALIDATE_AGID\n"); | 1737 | cdinfo(CD_DVD, "entering DVD_INVALIDATE_AGID\n"); |
1701 | setup_report_key(&cgc, ai->lsa.agid, 0x3f); | 1738 | setup_report_key(&cgc, ai->lsa.agid, 0x3f); |
1702 | if ((ret = cdo->generic_packet(cdi, &cgc))) | 1739 | if ((ret = cdo->generic_packet(cdi, &cgc))) |
1703 | return ret; | 1740 | goto err; |
1704 | break; | 1741 | break; |
1705 | 1742 | ||
1706 | /* Get region settings */ | 1743 | /* Get region settings */ |
1707 | case DVD_LU_SEND_RPC_STATE: | 1744 | case DVD_LU_SEND_RPC_STATE: |
1708 | cdinfo(CD_DVD, "entering DVD_LU_SEND_RPC_STATE\n"); | 1745 | cdinfo(CD_DVD, "entering DVD_LU_SEND_RPC_STATE\n"); |
1709 | setup_report_key(&cgc, 0, 8); | 1746 | setup_report_key(&cgc, 0, 8); |
1710 | memset(&rpc_state, 0, sizeof(rpc_state_t)); | ||
1711 | cgc.buffer = (char *) &rpc_state; | ||
1712 | 1747 | ||
1713 | if ((ret = cdo->generic_packet(cdi, &cgc))) | 1748 | if ((ret = cdo->generic_packet(cdi, &cgc))) |
1714 | return ret; | 1749 | goto err; |
1715 | 1750 | ||
1716 | ai->lrpcs.type = rpc_state.type_code; | 1751 | rpc_state = (rpc_state_t *)buf; |
1717 | ai->lrpcs.vra = rpc_state.vra; | 1752 | ai->lrpcs.type = rpc_state->type_code; |
1718 | ai->lrpcs.ucca = rpc_state.ucca; | 1753 | ai->lrpcs.vra = rpc_state->vra; |
1719 | ai->lrpcs.region_mask = rpc_state.region_mask; | 1754 | ai->lrpcs.ucca = rpc_state->ucca; |
1720 | ai->lrpcs.rpc_scheme = rpc_state.rpc_scheme; | 1755 | ai->lrpcs.region_mask = rpc_state->region_mask; |
1756 | ai->lrpcs.rpc_scheme = rpc_state->rpc_scheme; | ||
1721 | break; | 1757 | break; |
1722 | 1758 | ||
1723 | /* Set region settings */ | 1759 | /* Set region settings */ |
@@ -1728,20 +1764,23 @@ static int dvd_do_auth(struct cdrom_device_info *cdi, dvd_authinfo *ai) | |||
1728 | buf[4] = ai->hrpcs.pdrc; | 1764 | buf[4] = ai->hrpcs.pdrc; |
1729 | 1765 | ||
1730 | if ((ret = cdo->generic_packet(cdi, &cgc))) | 1766 | if ((ret = cdo->generic_packet(cdi, &cgc))) |
1731 | return ret; | 1767 | goto err; |
1732 | break; | 1768 | break; |
1733 | 1769 | ||
1734 | default: | 1770 | default: |
1735 | cdinfo(CD_WARNING, "Invalid DVD key ioctl (%d)\n", ai->type); | 1771 | cdinfo(CD_WARNING, "Invalid DVD key ioctl (%d)\n", ai->type); |
1736 | return -ENOTTY; | 1772 | ret = -ENOTTY; |
1773 | goto err; | ||
1737 | } | 1774 | } |
1738 | 1775 | ret = 0; | |
1739 | return 0; | 1776 | err: |
1777 | kfree(buf); | ||
1778 | return ret; | ||
1740 | } | 1779 | } |
1741 | 1780 | ||
1742 | static int dvd_read_physical(struct cdrom_device_info *cdi, dvd_struct *s) | 1781 | static int dvd_read_physical(struct cdrom_device_info *cdi, dvd_struct *s) |
1743 | { | 1782 | { |
1744 | unsigned char buf[21], *base; | 1783 | unsigned char *buf, *base; |
1745 | struct dvd_layer *layer; | 1784 | struct dvd_layer *layer; |
1746 | struct packet_command cgc; | 1785 | struct packet_command cgc; |
1747 | struct cdrom_device_ops *cdo = cdi->ops; | 1786 | struct cdrom_device_ops *cdo = cdi->ops; |
@@ -1750,7 +1789,11 @@ static int dvd_read_physical(struct cdrom_device_info *cdi, dvd_struct *s) | |||
1750 | if (layer_num >= DVD_LAYERS) | 1789 | if (layer_num >= DVD_LAYERS) |
1751 | return -EINVAL; | 1790 | return -EINVAL; |
1752 | 1791 | ||
1753 | init_cdrom_command(&cgc, buf, sizeof(buf), CGC_DATA_READ); | 1792 | buf = kmalloc(21, GFP_KERNEL); |
1793 | if (!buf) | ||
1794 | return -ENOMEM; | ||
1795 | |||
1796 | init_cdrom_command(&cgc, buf, 21, CGC_DATA_READ); | ||
1754 | cgc.cmd[0] = GPCMD_READ_DVD_STRUCTURE; | 1797 | cgc.cmd[0] = GPCMD_READ_DVD_STRUCTURE; |
1755 | cgc.cmd[6] = layer_num; | 1798 | cgc.cmd[6] = layer_num; |
1756 | cgc.cmd[7] = s->type; | 1799 | cgc.cmd[7] = s->type; |
@@ -1762,7 +1805,7 @@ static int dvd_read_physical(struct cdrom_device_info *cdi, dvd_struct *s) | |||
1762 | cgc.quiet = 1; | 1805 | cgc.quiet = 1; |
1763 | 1806 | ||
1764 | if ((ret = cdo->generic_packet(cdi, &cgc))) | 1807 | if ((ret = cdo->generic_packet(cdi, &cgc))) |
1765 | return ret; | 1808 | goto err; |
1766 | 1809 | ||
1767 | base = &buf[4]; | 1810 | base = &buf[4]; |
1768 | layer = &s->physical.layer[layer_num]; | 1811 | layer = &s->physical.layer[layer_num]; |
@@ -1786,17 +1829,24 @@ static int dvd_read_physical(struct cdrom_device_info *cdi, dvd_struct *s) | |||
1786 | layer->end_sector_l0 = base[13] << 16 | base[14] << 8 | base[15]; | 1829 | layer->end_sector_l0 = base[13] << 16 | base[14] << 8 | base[15]; |
1787 | layer->bca = base[16] >> 7; | 1830 | layer->bca = base[16] >> 7; |
1788 | 1831 | ||
1789 | return 0; | 1832 | ret = 0; |
1833 | err: | ||
1834 | kfree(buf); | ||
1835 | return ret; | ||
1790 | } | 1836 | } |
1791 | 1837 | ||
1792 | static int dvd_read_copyright(struct cdrom_device_info *cdi, dvd_struct *s) | 1838 | static int dvd_read_copyright(struct cdrom_device_info *cdi, dvd_struct *s) |
1793 | { | 1839 | { |
1794 | int ret; | 1840 | int ret; |
1795 | u_char buf[8]; | 1841 | u_char *buf; |
1796 | struct packet_command cgc; | 1842 | struct packet_command cgc; |
1797 | struct cdrom_device_ops *cdo = cdi->ops; | 1843 | struct cdrom_device_ops *cdo = cdi->ops; |
1798 | 1844 | ||
1799 | init_cdrom_command(&cgc, buf, sizeof(buf), CGC_DATA_READ); | 1845 | buf = kmalloc(8, GFP_KERNEL); |
1846 | if (!buf) | ||
1847 | return -ENOMEM; | ||
1848 | |||
1849 | init_cdrom_command(&cgc, buf, 8, CGC_DATA_READ); | ||
1800 | cgc.cmd[0] = GPCMD_READ_DVD_STRUCTURE; | 1850 | cgc.cmd[0] = GPCMD_READ_DVD_STRUCTURE; |
1801 | cgc.cmd[6] = s->copyright.layer_num; | 1851 | cgc.cmd[6] = s->copyright.layer_num; |
1802 | cgc.cmd[7] = s->type; | 1852 | cgc.cmd[7] = s->type; |
@@ -1804,12 +1854,15 @@ static int dvd_read_copyright(struct cdrom_device_info *cdi, dvd_struct *s) | |||
1804 | cgc.cmd[9] = cgc.buflen & 0xff; | 1854 | cgc.cmd[9] = cgc.buflen & 0xff; |
1805 | 1855 | ||
1806 | if ((ret = cdo->generic_packet(cdi, &cgc))) | 1856 | if ((ret = cdo->generic_packet(cdi, &cgc))) |
1807 | return ret; | 1857 | goto err; |
1808 | 1858 | ||
1809 | s->copyright.cpst = buf[4]; | 1859 | s->copyright.cpst = buf[4]; |
1810 | s->copyright.rmi = buf[5]; | 1860 | s->copyright.rmi = buf[5]; |
1811 | 1861 | ||
1812 | return 0; | 1862 | ret = 0; |
1863 | err: | ||
1864 | kfree(buf); | ||
1865 | return ret; | ||
1813 | } | 1866 | } |
1814 | 1867 | ||
1815 | static int dvd_read_disckey(struct cdrom_device_info *cdi, dvd_struct *s) | 1868 | static int dvd_read_disckey(struct cdrom_device_info *cdi, dvd_struct *s) |
@@ -1841,26 +1894,33 @@ static int dvd_read_disckey(struct cdrom_device_info *cdi, dvd_struct *s) | |||
1841 | static int dvd_read_bca(struct cdrom_device_info *cdi, dvd_struct *s) | 1894 | static int dvd_read_bca(struct cdrom_device_info *cdi, dvd_struct *s) |
1842 | { | 1895 | { |
1843 | int ret; | 1896 | int ret; |
1844 | u_char buf[4 + 188]; | 1897 | u_char *buf; |
1845 | struct packet_command cgc; | 1898 | struct packet_command cgc; |
1846 | struct cdrom_device_ops *cdo = cdi->ops; | 1899 | struct cdrom_device_ops *cdo = cdi->ops; |
1847 | 1900 | ||
1848 | init_cdrom_command(&cgc, buf, sizeof(buf), CGC_DATA_READ); | 1901 | buf = kmalloc(4 + 188, GFP_KERNEL); |
1902 | if (!buf) | ||
1903 | return -ENOMEM; | ||
1904 | |||
1905 | init_cdrom_command(&cgc, buf, 4 + 188, CGC_DATA_READ); | ||
1849 | cgc.cmd[0] = GPCMD_READ_DVD_STRUCTURE; | 1906 | cgc.cmd[0] = GPCMD_READ_DVD_STRUCTURE; |
1850 | cgc.cmd[7] = s->type; | 1907 | cgc.cmd[7] = s->type; |
1851 | cgc.cmd[9] = cgc.buflen & 0xff; | 1908 | cgc.cmd[9] = cgc.buflen & 0xff; |
1852 | 1909 | ||
1853 | if ((ret = cdo->generic_packet(cdi, &cgc))) | 1910 | if ((ret = cdo->generic_packet(cdi, &cgc))) |
1854 | return ret; | 1911 | goto err; |
1855 | 1912 | ||
1856 | s->bca.len = buf[0] << 8 | buf[1]; | 1913 | s->bca.len = buf[0] << 8 | buf[1]; |
1857 | if (s->bca.len < 12 || s->bca.len > 188) { | 1914 | if (s->bca.len < 12 || s->bca.len > 188) { |
1858 | cdinfo(CD_WARNING, "Received invalid BCA length (%d)\n", s->bca.len); | 1915 | cdinfo(CD_WARNING, "Received invalid BCA length (%d)\n", s->bca.len); |
1859 | return -EIO; | 1916 | ret = -EIO; |
1917 | goto err; | ||
1860 | } | 1918 | } |
1861 | memcpy(s->bca.value, &buf[4], s->bca.len); | 1919 | memcpy(s->bca.value, &buf[4], s->bca.len); |
1862 | 1920 | ret = 0; | |
1863 | return 0; | 1921 | err: |
1922 | kfree(buf); | ||
1923 | return ret; | ||
1864 | } | 1924 | } |
1865 | 1925 | ||
1866 | static int dvd_read_manufact(struct cdrom_device_info *cdi, dvd_struct *s) | 1926 | static int dvd_read_manufact(struct cdrom_device_info *cdi, dvd_struct *s) |
@@ -1960,9 +2020,13 @@ static int cdrom_read_subchannel(struct cdrom_device_info *cdi, | |||
1960 | { | 2020 | { |
1961 | struct cdrom_device_ops *cdo = cdi->ops; | 2021 | struct cdrom_device_ops *cdo = cdi->ops; |
1962 | struct packet_command cgc; | 2022 | struct packet_command cgc; |
1963 | char buffer[32]; | 2023 | char *buffer; |
1964 | int ret; | 2024 | int ret; |
1965 | 2025 | ||
2026 | buffer = kmalloc(32, GFP_KERNEL); | ||
2027 | if (!buffer) | ||
2028 | return -ENOMEM; | ||
2029 | |||
1966 | init_cdrom_command(&cgc, buffer, 16, CGC_DATA_READ); | 2030 | init_cdrom_command(&cgc, buffer, 16, CGC_DATA_READ); |
1967 | cgc.cmd[0] = GPCMD_READ_SUBCHANNEL; | 2031 | cgc.cmd[0] = GPCMD_READ_SUBCHANNEL; |
1968 | cgc.cmd[1] = 2; /* MSF addressing */ | 2032 | cgc.cmd[1] = 2; /* MSF addressing */ |
@@ -1971,7 +2035,7 @@ static int cdrom_read_subchannel(struct cdrom_device_info *cdi, | |||
1971 | cgc.cmd[8] = 16; | 2035 | cgc.cmd[8] = 16; |
1972 | 2036 | ||
1973 | if ((ret = cdo->generic_packet(cdi, &cgc))) | 2037 | if ((ret = cdo->generic_packet(cdi, &cgc))) |
1974 | return ret; | 2038 | goto err; |
1975 | 2039 | ||
1976 | subchnl->cdsc_audiostatus = cgc.buffer[1]; | 2040 | subchnl->cdsc_audiostatus = cgc.buffer[1]; |
1977 | subchnl->cdsc_format = CDROM_MSF; | 2041 | subchnl->cdsc_format = CDROM_MSF; |
@@ -1986,7 +2050,10 @@ static int cdrom_read_subchannel(struct cdrom_device_info *cdi, | |||
1986 | subchnl->cdsc_absaddr.msf.second = cgc.buffer[10]; | 2050 | subchnl->cdsc_absaddr.msf.second = cgc.buffer[10]; |
1987 | subchnl->cdsc_absaddr.msf.frame = cgc.buffer[11]; | 2051 | subchnl->cdsc_absaddr.msf.frame = cgc.buffer[11]; |
1988 | 2052 | ||
1989 | return 0; | 2053 | ret = 0; |
2054 | err: | ||
2055 | kfree(buffer); | ||
2056 | return ret; | ||
1990 | } | 2057 | } |
1991 | 2058 | ||
1992 | /* | 2059 | /* |
@@ -3309,7 +3376,7 @@ static int cdrom_print_info(const char *header, int val, char *info, | |||
3309 | 3376 | ||
3310 | *pos += ret; | 3377 | *pos += ret; |
3311 | 3378 | ||
3312 | for (cdi = topCdromPtr; cdi; cdi = cdi->next) { | 3379 | list_for_each_entry(cdi, &cdrom_list, list) { |
3313 | switch (option) { | 3380 | switch (option) { |
3314 | case CTL_NAME: | 3381 | case CTL_NAME: |
3315 | ret = scnprintf(info + *pos, max_size - *pos, | 3382 | ret = scnprintf(info + *pos, max_size - *pos, |
@@ -3430,7 +3497,8 @@ static void cdrom_update_settings(void) | |||
3430 | { | 3497 | { |
3431 | struct cdrom_device_info *cdi; | 3498 | struct cdrom_device_info *cdi; |
3432 | 3499 | ||
3433 | for (cdi = topCdromPtr; cdi != NULL; cdi = cdi->next) { | 3500 | mutex_lock(&cdrom_mutex); |
3501 | list_for_each_entry(cdi, &cdrom_list, list) { | ||
3434 | if (autoclose && CDROM_CAN(CDC_CLOSE_TRAY)) | 3502 | if (autoclose && CDROM_CAN(CDC_CLOSE_TRAY)) |
3435 | cdi->options |= CDO_AUTO_CLOSE; | 3503 | cdi->options |= CDO_AUTO_CLOSE; |
3436 | else if (!autoclose) | 3504 | else if (!autoclose) |
@@ -3448,6 +3516,7 @@ static void cdrom_update_settings(void) | |||
3448 | else | 3516 | else |
3449 | cdi->options &= ~CDO_CHECK_TYPE; | 3517 | cdi->options &= ~CDO_CHECK_TYPE; |
3450 | } | 3518 | } |
3519 | mutex_unlock(&cdrom_mutex); | ||
3451 | } | 3520 | } |
3452 | 3521 | ||
3453 | static int cdrom_sysctl_handler(ctl_table *ctl, int write, struct file * filp, | 3522 | static int cdrom_sysctl_handler(ctl_table *ctl, int write, struct file * filp, |
@@ -3571,22 +3640,29 @@ static void cdrom_sysctl_unregister(void) | |||
3571 | unregister_sysctl_table(cdrom_sysctl_header); | 3640 | unregister_sysctl_table(cdrom_sysctl_header); |
3572 | } | 3641 | } |
3573 | 3642 | ||
3643 | #else /* CONFIG_SYSCTL */ | ||
3644 | |||
3645 | static void cdrom_sysctl_register(void) | ||
3646 | { | ||
3647 | } | ||
3648 | |||
3649 | static void cdrom_sysctl_unregister(void) | ||
3650 | { | ||
3651 | } | ||
3652 | |||
3574 | #endif /* CONFIG_SYSCTL */ | 3653 | #endif /* CONFIG_SYSCTL */ |
3575 | 3654 | ||
3576 | static int __init cdrom_init(void) | 3655 | static int __init cdrom_init(void) |
3577 | { | 3656 | { |
3578 | #ifdef CONFIG_SYSCTL | ||
3579 | cdrom_sysctl_register(); | 3657 | cdrom_sysctl_register(); |
3580 | #endif | 3658 | |
3581 | return 0; | 3659 | return 0; |
3582 | } | 3660 | } |
3583 | 3661 | ||
3584 | static void __exit cdrom_exit(void) | 3662 | static void __exit cdrom_exit(void) |
3585 | { | 3663 | { |
3586 | printk(KERN_INFO "Uniform CD-ROM driver unloaded\n"); | 3664 | printk(KERN_INFO "Uniform CD-ROM driver unloaded\n"); |
3587 | #ifdef CONFIG_SYSCTL | ||
3588 | cdrom_sysctl_unregister(); | 3665 | cdrom_sysctl_unregister(); |
3589 | #endif | ||
3590 | } | 3666 | } |
3591 | 3667 | ||
3592 | module_init(cdrom_init); | 3668 | module_init(cdrom_init); |