Re: [PATCH 2/2] Port dummy_hcd to hrtimers

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



On Fri, 30 May 2014 pktoss@xxxxxxxxx wrote:

> From: Pantelis Koukousoulas <pktoss@xxxxxxxxx>
> 
> dummy_hcd uses jiffies and seems to assume that HZ=1000 and no
> tickless behavior. This makes for some horrible performance in
> ordinary desktop kernels (tickless / HZ=250) as found in distros.
> 
> This patch ports dummy_hcd to use hrtimers instead, which allows
> for reasonable performance in distro kernels as well.
> (Around 25MB/s for g_mass_storage, around 100MB/s for UAS).
> 
> Implementation uses the tasklet_hrtimer framework. This means
> dummy_timer callback is executed in softirq context (as it was
> with wheel timers) which keeps required changes to a minimum.

Good work.

> -static void dummy_timer(unsigned long _dum_hcd)
> +static enum hrtimer_restart dummy_timer(struct hrtimer *timer)
>  {
> -	struct dummy_hcd	*dum_hcd = (struct dummy_hcd *) _dum_hcd;
> +	struct tasklet_hrtimer *ttimer = container_of(timer,
> +			                              struct tasklet_hrtimer,
> +	                                              timer);
> +	struct dummy_hcd *dum_hcd = container_of(ttimer,
> +	                                         struct dummy_hcd,
> +						 ttimer);

You don't need two statements like this.  Just do:

+	struct dummy_hcd *dum_hcd = container_of(timer,
			struct dummy_hcd, ttimer.timer);

By the way, the style used in this file is that continuation lines are
indented by two tab stops beyond the original line.  (Sometimes four
spaces, if two tab stops would be too much.)  They don't line up with
opening parens or anything like this.

> @@ -2316,9 +2337,7 @@ static DEVICE_ATTR_RO(urbs);
>  
>  static int dummy_start_ss(struct dummy_hcd *dum_hcd)
>  {
> -	init_timer(&dum_hcd->timer);
> -	dum_hcd->timer.function = dummy_timer;
> -	dum_hcd->timer.data = (unsigned long)dum_hcd;
> +	tasklet_hrtimer_init(&dum_hcd->ttimer, dummy_timer, CLOCK_MONOTONIC, HRTIMER_MODE_ABS);
>  	dum_hcd->rh_state = DUMMY_RH_RUNNING;
>  	dum_hcd->stream_en_ep = 0;
>  	INIT_LIST_HEAD(&dum_hcd->urbp_list);
> @@ -2347,9 +2366,7 @@ static int dummy_start(struct usb_hcd *hcd)
>  		return dummy_start_ss(dum_hcd);
>  
>  	spin_lock_init(&dum_hcd->dum->lock);
> -	init_timer(&dum_hcd->timer);
> -	dum_hcd->timer.function = dummy_timer;
> -	dum_hcd->timer.data = (unsigned long)dum_hcd;
> +	tasklet_hrtimer_init(&dum_hcd->ttimer, dummy_timer, CLOCK_MONOTONIC, HRTIMER_MODE_ABS);
>  	dum_hcd->rh_state = DUMMY_RH_RUNNING;

This looks weird, doesn't it?  As far as I can see, the only things 
that are different between dummy_start() and dummy_start_ss() are the 
spin_lock_init, stream_en_ep, and device_create_file.  I'd like to see 
this code refactored.  Maybe in a third patch?

Alan Stern

--
To unsubscribe from this list: send the line "unsubscribe linux-usb" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html




[Index of Archives]     [Linux Media]     [Linux Input]     [Linux Audio Users]     [Yosemite News]     [Linux Kernel]     [Linux SCSI]     [Old Linux USB Devel Archive]

  Powered by Linux