diff options
author | Jiri Slaby <jirislaby@gmail.com> | 2009-09-19 16:13:15 -0400 |
---|---|---|
committer | Live-CD User <linux@linux.site> | 2009-09-19 16:13:15 -0400 |
commit | 6c28181cf8b7d5af5f20a7bd102452033e14d946 (patch) | |
tree | fa1efdfa54133bbdc5e146bf1e248f2597253db4 /drivers/char/cyclades.c | |
parent | cc7fdf49d6f06efdf0cb7da8d7abe7eff663aa9b (diff) |
cyclades: ioctls cleanup
- add a cy_ prefix to functions with changed prototypes
- cy_get_serial_info: initialize serial_struct by initializer,
save a memset
- inline simple functions (get_mon_info, {s,g}et_default_threshold,
{s,g}et_default_timeout) directly in the ioctl handler
- add a cy_cflags_changed helper to not copy its code by
wait_event_interruptible
- remove some ret_val = 0 assignments, it's preset to 0
- TIOCGICOUNT: don't do many put_user's, do one copy_to_user
Signed-off-by: Jiri Slaby <jirislaby@gmail.com>
Signed-off-by: Alan Cox <alan@linux.intel.com>
Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
Diffstat (limited to 'drivers/char/cyclades.c')
-rw-r--r-- | drivers/char/cyclades.c | 179 |
1 files changed, 67 insertions, 112 deletions
diff --git a/drivers/char/cyclades.c b/drivers/char/cyclades.c index 47cd7b8d4d97..e1637ad9390e 100644 --- a/drivers/char/cyclades.c +++ b/drivers/char/cyclades.c | |||
@@ -2411,29 +2411,25 @@ static void cy_set_line_char(struct cyclades_port *info, struct tty_struct *tty) | |||
2411 | } | 2411 | } |
2412 | } /* set_line_char */ | 2412 | } /* set_line_char */ |
2413 | 2413 | ||
2414 | static int | 2414 | static int cy_get_serial_info(struct cyclades_port *info, |
2415 | get_serial_info(struct cyclades_port *info, | ||
2416 | struct serial_struct __user *retinfo) | 2415 | struct serial_struct __user *retinfo) |
2417 | { | 2416 | { |
2418 | struct serial_struct tmp; | ||
2419 | struct cyclades_card *cinfo = info->card; | 2417 | struct cyclades_card *cinfo = info->card; |
2420 | 2418 | struct serial_struct tmp = { | |
2421 | if (!retinfo) | 2419 | .type = info->type, |
2422 | return -EFAULT; | 2420 | .line = info->line, |
2423 | memset(&tmp, 0, sizeof(tmp)); | 2421 | .port = (info->card - cy_card) * 0x100 + info->line - |
2424 | tmp.type = info->type; | 2422 | cinfo->first_line, |
2425 | tmp.line = info->line; | 2423 | .irq = cinfo->irq, |
2426 | tmp.port = (info->card - cy_card) * 0x100 + info->line - | 2424 | .flags = info->port.flags, |
2427 | cinfo->first_line; | 2425 | .close_delay = info->port.close_delay, |
2428 | tmp.irq = cinfo->irq; | 2426 | .closing_wait = info->port.closing_wait, |
2429 | tmp.flags = info->port.flags; | 2427 | .baud_base = info->baud, |
2430 | tmp.close_delay = info->port.close_delay; | 2428 | .custom_divisor = info->custom_divisor, |
2431 | tmp.closing_wait = info->port.closing_wait; | 2429 | .hub6 = 0, /*!!! */ |
2432 | tmp.baud_base = info->baud; | 2430 | }; |
2433 | tmp.custom_divisor = info->custom_divisor; | ||
2434 | tmp.hub6 = 0; /*!!! */ | ||
2435 | return copy_to_user(retinfo, &tmp, sizeof(*retinfo)) ? -EFAULT : 0; | 2431 | return copy_to_user(retinfo, &tmp, sizeof(*retinfo)) ? -EFAULT : 0; |
2436 | } /* get_serial_info */ | 2432 | } |
2437 | 2433 | ||
2438 | static int | 2434 | static int |
2439 | cy_set_serial_info(struct cyclades_port *info, struct tty_struct *tty, | 2435 | cy_set_serial_info(struct cyclades_port *info, struct tty_struct *tty, |
@@ -2712,18 +2708,6 @@ static int cy_break(struct tty_struct *tty, int break_state) | |||
2712 | return retval; | 2708 | return retval; |
2713 | } /* cy_break */ | 2709 | } /* cy_break */ |
2714 | 2710 | ||
2715 | static int get_mon_info(struct cyclades_port *info, | ||
2716 | struct cyclades_monitor __user *mon) | ||
2717 | { | ||
2718 | if (copy_to_user(mon, &info->mon, sizeof(struct cyclades_monitor))) | ||
2719 | return -EFAULT; | ||
2720 | info->mon.int_count = 0; | ||
2721 | info->mon.char_count = 0; | ||
2722 | info->mon.char_max = 0; | ||
2723 | info->mon.char_last = 0; | ||
2724 | return 0; | ||
2725 | } /* get_mon_info */ | ||
2726 | |||
2727 | static int set_threshold(struct cyclades_port *info, unsigned long value) | 2711 | static int set_threshold(struct cyclades_port *info, unsigned long value) |
2728 | { | 2712 | { |
2729 | struct cyclades_card *card; | 2713 | struct cyclades_card *card; |
@@ -2773,19 +2757,6 @@ static int get_threshold(struct cyclades_port *info, | |||
2773 | return 0; | 2757 | return 0; |
2774 | } /* get_threshold */ | 2758 | } /* get_threshold */ |
2775 | 2759 | ||
2776 | static int set_default_threshold(struct cyclades_port *info, | ||
2777 | unsigned long value) | ||
2778 | { | ||
2779 | info->default_threshold = value & 0x0f; | ||
2780 | return 0; | ||
2781 | } /* set_default_threshold */ | ||
2782 | |||
2783 | static int get_default_threshold(struct cyclades_port *info, | ||
2784 | unsigned long __user *value) | ||
2785 | { | ||
2786 | return put_user(info->default_threshold, value); | ||
2787 | } /* get_default_threshold */ | ||
2788 | |||
2789 | static int set_timeout(struct cyclades_port *info, unsigned long value) | 2760 | static int set_timeout(struct cyclades_port *info, unsigned long value) |
2790 | { | 2761 | { |
2791 | struct cyclades_card *card; | 2762 | struct cyclades_card *card; |
@@ -2830,17 +2801,26 @@ static int get_timeout(struct cyclades_port *info, | |||
2830 | return 0; | 2801 | return 0; |
2831 | } /* get_timeout */ | 2802 | } /* get_timeout */ |
2832 | 2803 | ||
2833 | static int set_default_timeout(struct cyclades_port *info, unsigned long value) | 2804 | static int cy_cflags_changed(struct cyclades_port *info, unsigned long arg, |
2805 | struct cyclades_icount *cprev) | ||
2834 | { | 2806 | { |
2835 | info->default_timeout = value & 0xff; | 2807 | struct cyclades_icount cnow; |
2836 | return 0; | 2808 | unsigned long flags; |
2837 | } /* set_default_timeout */ | 2809 | int ret; |
2838 | 2810 | ||
2839 | static int get_default_timeout(struct cyclades_port *info, | 2811 | spin_lock_irqsave(&info->card->card_lock, flags); |
2840 | unsigned long __user *value) | 2812 | cnow = info->icount; /* atomic copy */ |
2841 | { | 2813 | spin_unlock_irqrestore(&info->card->card_lock, flags); |
2842 | return put_user(info->default_timeout, value); | 2814 | |
2843 | } /* get_default_timeout */ | 2815 | ret = ((arg & TIOCM_RNG) && (cnow.rng != cprev->rng)) || |
2816 | ((arg & TIOCM_DSR) && (cnow.dsr != cprev->dsr)) || | ||
2817 | ((arg & TIOCM_CD) && (cnow.dcd != cprev->dcd)) || | ||
2818 | ((arg & TIOCM_CTS) && (cnow.cts != cprev->cts)); | ||
2819 | |||
2820 | *cprev = cnow; | ||
2821 | |||
2822 | return ret; | ||
2823 | } | ||
2844 | 2824 | ||
2845 | /* | 2825 | /* |
2846 | * This routine allows the tty driver to implement device- | 2826 | * This routine allows the tty driver to implement device- |
@@ -2852,8 +2832,7 @@ cy_ioctl(struct tty_struct *tty, struct file *file, | |||
2852 | unsigned int cmd, unsigned long arg) | 2832 | unsigned int cmd, unsigned long arg) |
2853 | { | 2833 | { |
2854 | struct cyclades_port *info = tty->driver_data; | 2834 | struct cyclades_port *info = tty->driver_data; |
2855 | struct cyclades_icount cprev, cnow; /* kernel counter temps */ | 2835 | struct cyclades_icount cnow; /* kernel counter temps */ |
2856 | struct serial_icounter_struct __user *p_cuser; /* user space */ | ||
2857 | int ret_val = 0; | 2836 | int ret_val = 0; |
2858 | unsigned long flags; | 2837 | unsigned long flags; |
2859 | void __user *argp = (void __user *)arg; | 2838 | void __user *argp = (void __user *)arg; |
@@ -2869,7 +2848,11 @@ cy_ioctl(struct tty_struct *tty, struct file *file, | |||
2869 | 2848 | ||
2870 | switch (cmd) { | 2849 | switch (cmd) { |
2871 | case CYGETMON: | 2850 | case CYGETMON: |
2872 | ret_val = get_mon_info(info, argp); | 2851 | if (copy_to_user(argp, &info->mon, sizeof(info->mon))) { |
2852 | ret_val = -EFAULT; | ||
2853 | break; | ||
2854 | } | ||
2855 | memset(&info->mon, 0, sizeof(info->mon)); | ||
2873 | break; | 2856 | break; |
2874 | case CYGETTHRESH: | 2857 | case CYGETTHRESH: |
2875 | ret_val = get_threshold(info, argp); | 2858 | ret_val = get_threshold(info, argp); |
@@ -2878,10 +2861,11 @@ cy_ioctl(struct tty_struct *tty, struct file *file, | |||
2878 | ret_val = set_threshold(info, arg); | 2861 | ret_val = set_threshold(info, arg); |
2879 | break; | 2862 | break; |
2880 | case CYGETDEFTHRESH: | 2863 | case CYGETDEFTHRESH: |
2881 | ret_val = get_default_threshold(info, argp); | 2864 | ret_val = put_user(info->default_threshold, |
2865 | (unsigned long __user *)argp); | ||
2882 | break; | 2866 | break; |
2883 | case CYSETDEFTHRESH: | 2867 | case CYSETDEFTHRESH: |
2884 | ret_val = set_default_threshold(info, arg); | 2868 | info->default_threshold = arg & 0x0f; |
2885 | break; | 2869 | break; |
2886 | case CYGETTIMEOUT: | 2870 | case CYGETTIMEOUT: |
2887 | ret_val = get_timeout(info, argp); | 2871 | ret_val = get_timeout(info, argp); |
@@ -2890,21 +2874,20 @@ cy_ioctl(struct tty_struct *tty, struct file *file, | |||
2890 | ret_val = set_timeout(info, arg); | 2874 | ret_val = set_timeout(info, arg); |
2891 | break; | 2875 | break; |
2892 | case CYGETDEFTIMEOUT: | 2876 | case CYGETDEFTIMEOUT: |
2893 | ret_val = get_default_timeout(info, argp); | 2877 | ret_val = put_user(info->default_timeout, |
2878 | (unsigned long __user *)argp); | ||
2894 | break; | 2879 | break; |
2895 | case CYSETDEFTIMEOUT: | 2880 | case CYSETDEFTIMEOUT: |
2896 | ret_val = set_default_timeout(info, arg); | 2881 | info->default_timeout = arg & 0xff; |
2897 | break; | 2882 | break; |
2898 | case CYSETRFLOW: | 2883 | case CYSETRFLOW: |
2899 | info->rflow = (int)arg; | 2884 | info->rflow = (int)arg; |
2900 | ret_val = 0; | ||
2901 | break; | 2885 | break; |
2902 | case CYGETRFLOW: | 2886 | case CYGETRFLOW: |
2903 | ret_val = info->rflow; | 2887 | ret_val = info->rflow; |
2904 | break; | 2888 | break; |
2905 | case CYSETRTSDTR_INV: | 2889 | case CYSETRTSDTR_INV: |
2906 | info->rtsdtr_inv = (int)arg; | 2890 | info->rtsdtr_inv = (int)arg; |
2907 | ret_val = 0; | ||
2908 | break; | 2891 | break; |
2909 | case CYGETRTSDTR_INV: | 2892 | case CYGETRTSDTR_INV: |
2910 | ret_val = info->rtsdtr_inv; | 2893 | ret_val = info->rtsdtr_inv; |
@@ -2915,7 +2898,6 @@ cy_ioctl(struct tty_struct *tty, struct file *file, | |||
2915 | #ifndef CONFIG_CYZ_INTR | 2898 | #ifndef CONFIG_CYZ_INTR |
2916 | case CYZSETPOLLCYCLE: | 2899 | case CYZSETPOLLCYCLE: |
2917 | cyz_polling_cycle = (arg * HZ) / 1000; | 2900 | cyz_polling_cycle = (arg * HZ) / 1000; |
2918 | ret_val = 0; | ||
2919 | break; | 2901 | break; |
2920 | case CYZGETPOLLCYCLE: | 2902 | case CYZGETPOLLCYCLE: |
2921 | ret_val = (cyz_polling_cycle * 1000) / HZ; | 2903 | ret_val = (cyz_polling_cycle * 1000) / HZ; |
@@ -2923,13 +2905,12 @@ cy_ioctl(struct tty_struct *tty, struct file *file, | |||
2923 | #endif /* CONFIG_CYZ_INTR */ | 2905 | #endif /* CONFIG_CYZ_INTR */ |
2924 | case CYSETWAIT: | 2906 | case CYSETWAIT: |
2925 | info->port.closing_wait = (unsigned short)arg * HZ / 100; | 2907 | info->port.closing_wait = (unsigned short)arg * HZ / 100; |
2926 | ret_val = 0; | ||
2927 | break; | 2908 | break; |
2928 | case CYGETWAIT: | 2909 | case CYGETWAIT: |
2929 | ret_val = info->port.closing_wait / (HZ / 100); | 2910 | ret_val = info->port.closing_wait / (HZ / 100); |
2930 | break; | 2911 | break; |
2931 | case TIOCGSERIAL: | 2912 | case TIOCGSERIAL: |
2932 | ret_val = get_serial_info(info, argp); | 2913 | ret_val = cy_get_serial_info(info, argp); |
2933 | break; | 2914 | break; |
2934 | case TIOCSSERIAL: | 2915 | case TIOCSSERIAL: |
2935 | ret_val = cy_set_serial_info(info, tty, argp); | 2916 | ret_val = cy_set_serial_info(info, tty, argp); |
@@ -2948,17 +2929,8 @@ cy_ioctl(struct tty_struct *tty, struct file *file, | |||
2948 | /* note the counters on entry */ | 2929 | /* note the counters on entry */ |
2949 | cnow = info->icount; | 2930 | cnow = info->icount; |
2950 | spin_unlock_irqrestore(&info->card->card_lock, flags); | 2931 | spin_unlock_irqrestore(&info->card->card_lock, flags); |
2951 | ret_val = wait_event_interruptible(info->delta_msr_wait, ({ | 2932 | ret_val = wait_event_interruptible(info->delta_msr_wait, |
2952 | cprev = cnow; | 2933 | cy_cflags_changed(info, arg, &cnow)); |
2953 | spin_lock_irqsave(&info->card->card_lock, flags); | ||
2954 | cnow = info->icount; /* atomic copy */ | ||
2955 | spin_unlock_irqrestore(&info->card->card_lock, flags); | ||
2956 | |||
2957 | ((arg & TIOCM_RNG) && (cnow.rng != cprev.rng)) || | ||
2958 | ((arg & TIOCM_DSR) && (cnow.dsr != cprev.dsr)) || | ||
2959 | ((arg & TIOCM_CD) && (cnow.dcd != cprev.dcd)) || | ||
2960 | ((arg & TIOCM_CTS) && (cnow.cts != cprev.cts)); | ||
2961 | })); | ||
2962 | break; | 2934 | break; |
2963 | 2935 | ||
2964 | /* | 2936 | /* |
@@ -2967,46 +2939,29 @@ cy_ioctl(struct tty_struct *tty, struct file *file, | |||
2967 | * NB: both 1->0 and 0->1 transitions are counted except for | 2939 | * NB: both 1->0 and 0->1 transitions are counted except for |
2968 | * RI where only 0->1 is counted. | 2940 | * RI where only 0->1 is counted. |
2969 | */ | 2941 | */ |
2970 | case TIOCGICOUNT: | 2942 | case TIOCGICOUNT: { |
2943 | struct serial_icounter_struct sic = { }; | ||
2944 | |||
2971 | spin_lock_irqsave(&info->card->card_lock, flags); | 2945 | spin_lock_irqsave(&info->card->card_lock, flags); |
2972 | cnow = info->icount; | 2946 | cnow = info->icount; |
2973 | spin_unlock_irqrestore(&info->card->card_lock, flags); | 2947 | spin_unlock_irqrestore(&info->card->card_lock, flags); |
2974 | p_cuser = argp; | 2948 | |
2975 | ret_val = put_user(cnow.cts, &p_cuser->cts); | 2949 | sic.cts = cnow.cts; |
2976 | if (ret_val) | 2950 | sic.dsr = cnow.dsr; |
2977 | break; | 2951 | sic.rng = cnow.rng; |
2978 | ret_val = put_user(cnow.dsr, &p_cuser->dsr); | 2952 | sic.dcd = cnow.dcd; |
2979 | if (ret_val) | 2953 | sic.rx = cnow.rx; |
2980 | break; | 2954 | sic.tx = cnow.tx; |
2981 | ret_val = put_user(cnow.rng, &p_cuser->rng); | 2955 | sic.frame = cnow.frame; |
2982 | if (ret_val) | 2956 | sic.overrun = cnow.overrun; |
2983 | break; | 2957 | sic.parity = cnow.parity; |
2984 | ret_val = put_user(cnow.dcd, &p_cuser->dcd); | 2958 | sic.brk = cnow.brk; |
2985 | if (ret_val) | 2959 | sic.buf_overrun = cnow.buf_overrun; |
2986 | break; | 2960 | |
2987 | ret_val = put_user(cnow.rx, &p_cuser->rx); | 2961 | if (copy_to_user(argp, &sic, sizeof(sic))) |
2988 | if (ret_val) | 2962 | ret_val = -EFAULT; |
2989 | break; | ||
2990 | ret_val = put_user(cnow.tx, &p_cuser->tx); | ||
2991 | if (ret_val) | ||
2992 | break; | ||
2993 | ret_val = put_user(cnow.frame, &p_cuser->frame); | ||
2994 | if (ret_val) | ||
2995 | break; | ||
2996 | ret_val = put_user(cnow.overrun, &p_cuser->overrun); | ||
2997 | if (ret_val) | ||
2998 | break; | ||
2999 | ret_val = put_user(cnow.parity, &p_cuser->parity); | ||
3000 | if (ret_val) | ||
3001 | break; | ||
3002 | ret_val = put_user(cnow.brk, &p_cuser->brk); | ||
3003 | if (ret_val) | ||
3004 | break; | ||
3005 | ret_val = put_user(cnow.buf_overrun, &p_cuser->buf_overrun); | ||
3006 | if (ret_val) | ||
3007 | break; | ||
3008 | ret_val = 0; | ||
3009 | break; | 2963 | break; |
2964 | } | ||
3010 | default: | 2965 | default: |
3011 | ret_val = -ENOIOCTLCMD; | 2966 | ret_val = -ENOIOCTLCMD; |
3012 | } | 2967 | } |