diff options
Diffstat (limited to 'drivers/char/tpm/tpm.c')
| -rw-r--r-- | drivers/char/tpm/tpm.c | 128 |
1 files changed, 95 insertions, 33 deletions
diff --git a/drivers/char/tpm/tpm.c b/drivers/char/tpm/tpm.c index e1fc193d9396..ae766d868454 100644 --- a/drivers/char/tpm/tpm.c +++ b/drivers/char/tpm/tpm.c | |||
| @@ -580,91 +580,133 @@ void tpm_continue_selftest(struct tpm_chip *chip) | |||
| 580 | } | 580 | } |
| 581 | EXPORT_SYMBOL_GPL(tpm_continue_selftest); | 581 | EXPORT_SYMBOL_GPL(tpm_continue_selftest); |
| 582 | 582 | ||
| 583 | #define TPM_INTERNAL_RESULT_SIZE 200 | ||
| 584 | |||
| 583 | ssize_t tpm_show_enabled(struct device * dev, struct device_attribute * attr, | 585 | ssize_t tpm_show_enabled(struct device * dev, struct device_attribute * attr, |
| 584 | char *buf) | 586 | char *buf) |
| 585 | { | 587 | { |
| 586 | u8 data[max_t(int, ARRAY_SIZE(tpm_cap), 35)]; | 588 | u8 *data; |
| 587 | ssize_t rc; | 589 | ssize_t rc; |
| 588 | 590 | ||
| 589 | struct tpm_chip *chip = dev_get_drvdata(dev); | 591 | struct tpm_chip *chip = dev_get_drvdata(dev); |
| 590 | if (chip == NULL) | 592 | if (chip == NULL) |
| 591 | return -ENODEV; | 593 | return -ENODEV; |
| 592 | 594 | ||
| 595 | data = kzalloc(TPM_INTERNAL_RESULT_SIZE, GFP_KERNEL); | ||
| 596 | if (!data) | ||
| 597 | return -ENOMEM; | ||
| 598 | |||
| 593 | memcpy(data, tpm_cap, sizeof(tpm_cap)); | 599 | memcpy(data, tpm_cap, sizeof(tpm_cap)); |
| 594 | data[TPM_CAP_IDX] = TPM_CAP_FLAG; | 600 | data[TPM_CAP_IDX] = TPM_CAP_FLAG; |
| 595 | data[TPM_CAP_SUBCAP_IDX] = TPM_CAP_FLAG_PERM; | 601 | data[TPM_CAP_SUBCAP_IDX] = TPM_CAP_FLAG_PERM; |
| 596 | 602 | ||
| 597 | rc = transmit_cmd(chip, data, sizeof(data), | 603 | rc = transmit_cmd(chip, data, TPM_INTERNAL_RESULT_SIZE, |
| 598 | "attemtping to determine the permanent state"); | 604 | "attemtping to determine the permanent enabled state"); |
| 599 | if (rc) | 605 | if (rc) { |
| 606 | kfree(data); | ||
| 600 | return 0; | 607 | return 0; |
| 601 | return sprintf(buf, "%d\n", !data[TPM_GET_CAP_PERM_DISABLE_IDX]); | 608 | } |
| 609 | |||
| 610 | rc = sprintf(buf, "%d\n", !data[TPM_GET_CAP_PERM_DISABLE_IDX]); | ||
| 611 | |||
| 612 | kfree(data); | ||
| 613 | return rc; | ||
| 602 | } | 614 | } |
| 603 | EXPORT_SYMBOL_GPL(tpm_show_enabled); | 615 | EXPORT_SYMBOL_GPL(tpm_show_enabled); |
| 604 | 616 | ||
| 605 | ssize_t tpm_show_active(struct device * dev, struct device_attribute * attr, | 617 | ssize_t tpm_show_active(struct device * dev, struct device_attribute * attr, |
| 606 | char *buf) | 618 | char *buf) |
| 607 | { | 619 | { |
| 608 | u8 data[max_t(int, ARRAY_SIZE(tpm_cap), 35)]; | 620 | u8 *data; |
| 609 | ssize_t rc; | 621 | ssize_t rc; |
| 610 | 622 | ||
| 611 | struct tpm_chip *chip = dev_get_drvdata(dev); | 623 | struct tpm_chip *chip = dev_get_drvdata(dev); |
| 612 | if (chip == NULL) | 624 | if (chip == NULL) |
| 613 | return -ENODEV; | 625 | return -ENODEV; |
| 614 | 626 | ||
| 627 | data = kzalloc(TPM_INTERNAL_RESULT_SIZE, GFP_KERNEL); | ||
| 628 | if (!data) | ||
| 629 | return -ENOMEM; | ||
| 630 | |||
| 615 | memcpy(data, tpm_cap, sizeof(tpm_cap)); | 631 | memcpy(data, tpm_cap, sizeof(tpm_cap)); |
| 616 | data[TPM_CAP_IDX] = TPM_CAP_FLAG; | 632 | data[TPM_CAP_IDX] = TPM_CAP_FLAG; |
| 617 | data[TPM_CAP_SUBCAP_IDX] = TPM_CAP_FLAG_PERM; | 633 | data[TPM_CAP_SUBCAP_IDX] = TPM_CAP_FLAG_PERM; |
| 618 | 634 | ||
| 619 | rc = transmit_cmd(chip, data, sizeof(data), | 635 | rc = transmit_cmd(chip, data, TPM_INTERNAL_RESULT_SIZE, |
| 620 | "attemtping to determine the permanent state"); | 636 | "attemtping to determine the permanent active state"); |
| 621 | if (rc) | 637 | if (rc) { |
| 638 | kfree(data); | ||
| 622 | return 0; | 639 | return 0; |
| 623 | return sprintf(buf, "%d\n", !data[TPM_GET_CAP_PERM_INACTIVE_IDX]); | 640 | } |
| 641 | |||
| 642 | rc = sprintf(buf, "%d\n", !data[TPM_GET_CAP_PERM_INACTIVE_IDX]); | ||
| 643 | |||
| 644 | kfree(data); | ||
| 645 | return rc; | ||
| 624 | } | 646 | } |
| 625 | EXPORT_SYMBOL_GPL(tpm_show_active); | 647 | EXPORT_SYMBOL_GPL(tpm_show_active); |
| 626 | 648 | ||
| 627 | ssize_t tpm_show_owned(struct device * dev, struct device_attribute * attr, | 649 | ssize_t tpm_show_owned(struct device * dev, struct device_attribute * attr, |
| 628 | char *buf) | 650 | char *buf) |
| 629 | { | 651 | { |
| 630 | u8 data[sizeof(tpm_cap)]; | 652 | u8 *data; |
| 631 | ssize_t rc; | 653 | ssize_t rc; |
| 632 | 654 | ||
| 633 | struct tpm_chip *chip = dev_get_drvdata(dev); | 655 | struct tpm_chip *chip = dev_get_drvdata(dev); |
| 634 | if (chip == NULL) | 656 | if (chip == NULL) |
| 635 | return -ENODEV; | 657 | return -ENODEV; |
| 636 | 658 | ||
| 659 | data = kzalloc(TPM_INTERNAL_RESULT_SIZE, GFP_KERNEL); | ||
| 660 | if (!data) | ||
| 661 | return -ENOMEM; | ||
| 662 | |||
| 637 | memcpy(data, tpm_cap, sizeof(tpm_cap)); | 663 | memcpy(data, tpm_cap, sizeof(tpm_cap)); |
| 638 | data[TPM_CAP_IDX] = TPM_CAP_PROP; | 664 | data[TPM_CAP_IDX] = TPM_CAP_PROP; |
| 639 | data[TPM_CAP_SUBCAP_IDX] = TPM_CAP_PROP_OWNER; | 665 | data[TPM_CAP_SUBCAP_IDX] = TPM_CAP_PROP_OWNER; |
| 640 | 666 | ||
| 641 | rc = transmit_cmd(chip, data, sizeof(data), | 667 | rc = transmit_cmd(chip, data, TPM_INTERNAL_RESULT_SIZE, |
| 642 | "attempting to determine the owner state"); | 668 | "attempting to determine the owner state"); |
| 643 | if (rc) | 669 | if (rc) { |
| 670 | kfree(data); | ||
| 644 | return 0; | 671 | return 0; |
| 645 | return sprintf(buf, "%d\n", data[TPM_GET_CAP_RET_BOOL_1_IDX]); | 672 | } |
| 673 | |||
| 674 | rc = sprintf(buf, "%d\n", data[TPM_GET_CAP_RET_BOOL_1_IDX]); | ||
| 675 | |||
| 676 | kfree(data); | ||
| 677 | return rc; | ||
| 646 | } | 678 | } |
| 647 | EXPORT_SYMBOL_GPL(tpm_show_owned); | 679 | EXPORT_SYMBOL_GPL(tpm_show_owned); |
| 648 | 680 | ||
| 649 | ssize_t tpm_show_temp_deactivated(struct device * dev, | 681 | ssize_t tpm_show_temp_deactivated(struct device * dev, |
| 650 | struct device_attribute * attr, char *buf) | 682 | struct device_attribute * attr, char *buf) |
| 651 | { | 683 | { |
| 652 | u8 data[sizeof(tpm_cap)]; | 684 | u8 *data; |
| 653 | ssize_t rc; | 685 | ssize_t rc; |
| 654 | 686 | ||
| 655 | struct tpm_chip *chip = dev_get_drvdata(dev); | 687 | struct tpm_chip *chip = dev_get_drvdata(dev); |
| 656 | if (chip == NULL) | 688 | if (chip == NULL) |
| 657 | return -ENODEV; | 689 | return -ENODEV; |
| 658 | 690 | ||
| 691 | data = kzalloc(TPM_INTERNAL_RESULT_SIZE, GFP_KERNEL); | ||
| 692 | if (!data) | ||
| 693 | return -ENOMEM; | ||
| 694 | |||
| 659 | memcpy(data, tpm_cap, sizeof(tpm_cap)); | 695 | memcpy(data, tpm_cap, sizeof(tpm_cap)); |
| 660 | data[TPM_CAP_IDX] = TPM_CAP_FLAG; | 696 | data[TPM_CAP_IDX] = TPM_CAP_FLAG; |
| 661 | data[TPM_CAP_SUBCAP_IDX] = TPM_CAP_FLAG_VOL; | 697 | data[TPM_CAP_SUBCAP_IDX] = TPM_CAP_FLAG_VOL; |
| 662 | 698 | ||
| 663 | rc = transmit_cmd(chip, data, sizeof(data), | 699 | rc = transmit_cmd(chip, data, TPM_INTERNAL_RESULT_SIZE, |
| 664 | "attempting to determine the temporary state"); | 700 | "attempting to determine the temporary state"); |
| 665 | if (rc) | 701 | if (rc) { |
| 702 | kfree(data); | ||
| 666 | return 0; | 703 | return 0; |
| 667 | return sprintf(buf, "%d\n", data[TPM_GET_CAP_TEMP_INACTIVE_IDX]); | 704 | } |
| 705 | |||
| 706 | rc = sprintf(buf, "%d\n", data[TPM_GET_CAP_TEMP_INACTIVE_IDX]); | ||
| 707 | |||
| 708 | kfree(data); | ||
| 709 | return rc; | ||
| 668 | } | 710 | } |
| 669 | EXPORT_SYMBOL_GPL(tpm_show_temp_deactivated); | 711 | EXPORT_SYMBOL_GPL(tpm_show_temp_deactivated); |
| 670 | 712 | ||
| @@ -678,7 +720,7 @@ static const u8 pcrread[] = { | |||
| 678 | ssize_t tpm_show_pcrs(struct device *dev, struct device_attribute *attr, | 720 | ssize_t tpm_show_pcrs(struct device *dev, struct device_attribute *attr, |
| 679 | char *buf) | 721 | char *buf) |
| 680 | { | 722 | { |
| 681 | u8 data[max_t(int, max(ARRAY_SIZE(tpm_cap), ARRAY_SIZE(pcrread)), 30)]; | 723 | u8 *data; |
| 682 | ssize_t rc; | 724 | ssize_t rc; |
| 683 | int i, j, num_pcrs; | 725 | int i, j, num_pcrs; |
| 684 | __be32 index; | 726 | __be32 index; |
| @@ -688,21 +730,27 @@ ssize_t tpm_show_pcrs(struct device *dev, struct device_attribute *attr, | |||
| 688 | if (chip == NULL) | 730 | if (chip == NULL) |
| 689 | return -ENODEV; | 731 | return -ENODEV; |
| 690 | 732 | ||
| 733 | data = kzalloc(TPM_INTERNAL_RESULT_SIZE, GFP_KERNEL); | ||
| 734 | if (!data) | ||
| 735 | return -ENOMEM; | ||
| 736 | |||
| 691 | memcpy(data, tpm_cap, sizeof(tpm_cap)); | 737 | memcpy(data, tpm_cap, sizeof(tpm_cap)); |
| 692 | data[TPM_CAP_IDX] = TPM_CAP_PROP; | 738 | data[TPM_CAP_IDX] = TPM_CAP_PROP; |
| 693 | data[TPM_CAP_SUBCAP_IDX] = TPM_CAP_PROP_PCR; | 739 | data[TPM_CAP_SUBCAP_IDX] = TPM_CAP_PROP_PCR; |
| 694 | 740 | ||
| 695 | rc = transmit_cmd(chip, data, sizeof(data), | 741 | rc = transmit_cmd(chip, data, TPM_INTERNAL_RESULT_SIZE, |
| 696 | "attempting to determine the number of PCRS"); | 742 | "attempting to determine the number of PCRS"); |
| 697 | if (rc) | 743 | if (rc) { |
| 744 | kfree(data); | ||
| 698 | return 0; | 745 | return 0; |
| 746 | } | ||
| 699 | 747 | ||
| 700 | num_pcrs = be32_to_cpu(*((__be32 *) (data + 14))); | 748 | num_pcrs = be32_to_cpu(*((__be32 *) (data + 14))); |
| 701 | for (i = 0; i < num_pcrs; i++) { | 749 | for (i = 0; i < num_pcrs; i++) { |
| 702 | memcpy(data, pcrread, sizeof(pcrread)); | 750 | memcpy(data, pcrread, sizeof(pcrread)); |
| 703 | index = cpu_to_be32(i); | 751 | index = cpu_to_be32(i); |
| 704 | memcpy(data + 10, &index, 4); | 752 | memcpy(data + 10, &index, 4); |
| 705 | rc = transmit_cmd(chip, data, sizeof(data), | 753 | rc = transmit_cmd(chip, data, TPM_INTERNAL_RESULT_SIZE, |
| 706 | "attempting to read a PCR"); | 754 | "attempting to read a PCR"); |
| 707 | if (rc) | 755 | if (rc) |
| 708 | goto out; | 756 | goto out; |
| @@ -712,6 +760,7 @@ ssize_t tpm_show_pcrs(struct device *dev, struct device_attribute *attr, | |||
| 712 | str += sprintf(str, "\n"); | 760 | str += sprintf(str, "\n"); |
| 713 | } | 761 | } |
| 714 | out: | 762 | out: |
| 763 | kfree(data); | ||
| 715 | return str - buf; | 764 | return str - buf; |
| 716 | } | 765 | } |
| 717 | EXPORT_SYMBOL_GPL(tpm_show_pcrs); | 766 | EXPORT_SYMBOL_GPL(tpm_show_pcrs); |
| @@ -795,7 +844,7 @@ static const u8 cap_version[] = { | |||
| 795 | ssize_t tpm_show_caps(struct device *dev, struct device_attribute *attr, | 844 | ssize_t tpm_show_caps(struct device *dev, struct device_attribute *attr, |
| 796 | char *buf) | 845 | char *buf) |
| 797 | { | 846 | { |
| 798 | u8 data[max_t(int, max(ARRAY_SIZE(tpm_cap), ARRAY_SIZE(cap_version)), 30)]; | 847 | u8 *data; |
| 799 | ssize_t rc; | 848 | ssize_t rc; |
| 800 | char *str = buf; | 849 | char *str = buf; |
| 801 | 850 | ||
| @@ -803,21 +852,27 @@ ssize_t tpm_show_caps(struct device *dev, struct device_attribute *attr, | |||
| 803 | if (chip == NULL) | 852 | if (chip == NULL) |
| 804 | return -ENODEV; | 853 | return -ENODEV; |
| 805 | 854 | ||
| 855 | data = kzalloc(TPM_INTERNAL_RESULT_SIZE, GFP_KERNEL); | ||
| 856 | if (!data) | ||
| 857 | return -ENOMEM; | ||
| 858 | |||
| 806 | memcpy(data, tpm_cap, sizeof(tpm_cap)); | 859 | memcpy(data, tpm_cap, sizeof(tpm_cap)); |
| 807 | data[TPM_CAP_IDX] = TPM_CAP_PROP; | 860 | data[TPM_CAP_IDX] = TPM_CAP_PROP; |
| 808 | data[TPM_CAP_SUBCAP_IDX] = TPM_CAP_PROP_MANUFACTURER; | 861 | data[TPM_CAP_SUBCAP_IDX] = TPM_CAP_PROP_MANUFACTURER; |
| 809 | 862 | ||
| 810 | rc = transmit_cmd(chip, data, sizeof(data), | 863 | rc = transmit_cmd(chip, data, TPM_INTERNAL_RESULT_SIZE, |
| 811 | "attempting to determine the manufacturer"); | 864 | "attempting to determine the manufacturer"); |
| 812 | if (rc) | 865 | if (rc) { |
| 866 | kfree(data); | ||
| 813 | return 0; | 867 | return 0; |
| 868 | } | ||
| 814 | 869 | ||
| 815 | str += sprintf(str, "Manufacturer: 0x%x\n", | 870 | str += sprintf(str, "Manufacturer: 0x%x\n", |
| 816 | be32_to_cpu(*((__be32 *) (data + TPM_GET_CAP_RET_UINT32_1_IDX)))); | 871 | be32_to_cpu(*((__be32 *) (data + TPM_GET_CAP_RET_UINT32_1_IDX)))); |
| 817 | 872 | ||
| 818 | memcpy(data, cap_version, sizeof(cap_version)); | 873 | memcpy(data, cap_version, sizeof(cap_version)); |
| 819 | data[CAP_VERSION_IDX] = CAP_VERSION_1_1; | 874 | data[CAP_VERSION_IDX] = CAP_VERSION_1_1; |
| 820 | rc = transmit_cmd(chip, data, sizeof(data), | 875 | rc = transmit_cmd(chip, data, TPM_INTERNAL_RESULT_SIZE, |
| 821 | "attempting to determine the 1.1 version"); | 876 | "attempting to determine the 1.1 version"); |
| 822 | if (rc) | 877 | if (rc) |
| 823 | goto out; | 878 | goto out; |
| @@ -828,6 +883,7 @@ ssize_t tpm_show_caps(struct device *dev, struct device_attribute *attr, | |||
| 828 | (int) data[17]); | 883 | (int) data[17]); |
| 829 | 884 | ||
| 830 | out: | 885 | out: |
| 886 | kfree(data); | ||
| 831 | return str - buf; | 887 | return str - buf; |
| 832 | } | 888 | } |
| 833 | EXPORT_SYMBOL_GPL(tpm_show_caps); | 889 | EXPORT_SYMBOL_GPL(tpm_show_caps); |
| @@ -835,7 +891,7 @@ EXPORT_SYMBOL_GPL(tpm_show_caps); | |||
| 835 | ssize_t tpm_show_caps_1_2(struct device * dev, | 891 | ssize_t tpm_show_caps_1_2(struct device * dev, |
| 836 | struct device_attribute * attr, char *buf) | 892 | struct device_attribute * attr, char *buf) |
| 837 | { | 893 | { |
| 838 | u8 data[max_t(int, max(ARRAY_SIZE(tpm_cap), ARRAY_SIZE(cap_version)), 30)]; | 894 | u8 *data; |
| 839 | ssize_t len; | 895 | ssize_t len; |
| 840 | char *str = buf; | 896 | char *str = buf; |
| 841 | 897 | ||
| @@ -843,15 +899,20 @@ ssize_t tpm_show_caps_1_2(struct device * dev, | |||
| 843 | if (chip == NULL) | 899 | if (chip == NULL) |
| 844 | return -ENODEV; | 900 | return -ENODEV; |
| 845 | 901 | ||
| 902 | data = kzalloc(TPM_INTERNAL_RESULT_SIZE, GFP_KERNEL); | ||
| 903 | if (!data) | ||
| 904 | return -ENOMEM; | ||
| 905 | |||
| 846 | memcpy(data, tpm_cap, sizeof(tpm_cap)); | 906 | memcpy(data, tpm_cap, sizeof(tpm_cap)); |
| 847 | data[TPM_CAP_IDX] = TPM_CAP_PROP; | 907 | data[TPM_CAP_IDX] = TPM_CAP_PROP; |
| 848 | data[TPM_CAP_SUBCAP_IDX] = TPM_CAP_PROP_MANUFACTURER; | 908 | data[TPM_CAP_SUBCAP_IDX] = TPM_CAP_PROP_MANUFACTURER; |
| 849 | 909 | ||
| 850 | if ((len = tpm_transmit(chip, data, sizeof(data))) <= | 910 | len = tpm_transmit(chip, data, TPM_INTERNAL_RESULT_SIZE); |
| 851 | TPM_ERROR_SIZE) { | 911 | if (len <= TPM_ERROR_SIZE) { |
| 852 | dev_dbg(chip->dev, "A TPM error (%d) occurred " | 912 | dev_dbg(chip->dev, "A TPM error (%d) occurred " |
| 853 | "attempting to determine the manufacturer\n", | 913 | "attempting to determine the manufacturer\n", |
| 854 | be32_to_cpu(*((__be32 *) (data + TPM_RET_CODE_IDX)))); | 914 | be32_to_cpu(*((__be32 *) (data + TPM_RET_CODE_IDX)))); |
| 915 | kfree(data); | ||
| 855 | return 0; | 916 | return 0; |
| 856 | } | 917 | } |
| 857 | 918 | ||
| @@ -861,8 +922,8 @@ ssize_t tpm_show_caps_1_2(struct device * dev, | |||
| 861 | memcpy(data, cap_version, sizeof(cap_version)); | 922 | memcpy(data, cap_version, sizeof(cap_version)); |
| 862 | data[CAP_VERSION_IDX] = CAP_VERSION_1_2; | 923 | data[CAP_VERSION_IDX] = CAP_VERSION_1_2; |
| 863 | 924 | ||
| 864 | if ((len = tpm_transmit(chip, data, sizeof(data))) <= | 925 | len = tpm_transmit(chip, data, TPM_INTERNAL_RESULT_SIZE); |
| 865 | TPM_ERROR_SIZE) { | 926 | if (len <= TPM_ERROR_SIZE) { |
| 866 | dev_err(chip->dev, "A TPM error (%d) occurred " | 927 | dev_err(chip->dev, "A TPM error (%d) occurred " |
| 867 | "attempting to determine the 1.2 version\n", | 928 | "attempting to determine the 1.2 version\n", |
| 868 | be32_to_cpu(*((__be32 *) (data + TPM_RET_CODE_IDX)))); | 929 | be32_to_cpu(*((__be32 *) (data + TPM_RET_CODE_IDX)))); |
| @@ -874,6 +935,7 @@ ssize_t tpm_show_caps_1_2(struct device * dev, | |||
| 874 | (int) data[19]); | 935 | (int) data[19]); |
| 875 | 936 | ||
| 876 | out: | 937 | out: |
| 938 | kfree(data); | ||
| 877 | return str - buf; | 939 | return str - buf; |
| 878 | } | 940 | } |
| 879 | EXPORT_SYMBOL_GPL(tpm_show_caps_1_2); | 941 | EXPORT_SYMBOL_GPL(tpm_show_caps_1_2); |
| @@ -966,7 +1028,7 @@ ssize_t tpm_write(struct file *file, const char __user *buf, | |||
| 966 | size_t size, loff_t *off) | 1028 | size_t size, loff_t *off) |
| 967 | { | 1029 | { |
| 968 | struct tpm_chip *chip = file->private_data; | 1030 | struct tpm_chip *chip = file->private_data; |
| 969 | int in_size = size, out_size; | 1031 | size_t in_size = size, out_size; |
| 970 | 1032 | ||
| 971 | /* cannot perform a write until the read has cleared | 1033 | /* cannot perform a write until the read has cleared |
| 972 | either via tpm_read or a user_read_timer timeout */ | 1034 | either via tpm_read or a user_read_timer timeout */ |
| @@ -1001,7 +1063,7 @@ ssize_t tpm_read(struct file *file, char __user *buf, | |||
| 1001 | size_t size, loff_t *off) | 1063 | size_t size, loff_t *off) |
| 1002 | { | 1064 | { |
| 1003 | struct tpm_chip *chip = file->private_data; | 1065 | struct tpm_chip *chip = file->private_data; |
| 1004 | int ret_size; | 1066 | ssize_t ret_size; |
| 1005 | 1067 | ||
| 1006 | del_singleshot_timer_sync(&chip->user_read_timer); | 1068 | del_singleshot_timer_sync(&chip->user_read_timer); |
| 1007 | flush_scheduled_work(); | 1069 | flush_scheduled_work(); |
