All of lore.kernel.org
 help / color / mirror / Atom feed
From: Harry Butterworth <harry@hebutterworth.freeserve.co.uk>
To: Muli Ben-Yehuda <mulix@mulix.org>
Cc: xen-devel@lists.xensource.com
Subject: Re: [PATCH][1/17] USB virt 2.6 split driver---xenidc platform
Date: Mon, 21 Nov 2005 21:21:20 +0000	[thread overview]
Message-ID: <1132608080.4739.17.camel@localhost> (raw)
In-Reply-To: <20051121201049.GA22728@granada.merseine.nu>

On Mon, 2005-11-21 at 22:10 +0200, Muli Ben-Yehuda wrote:
> I'm going to give every comment once, not everywhere it
> happens. Please apply as appropriate to all recurring
> occurences. Also, this is my personal opinion of what Linux code
> should like like, please feel free to disagree, provided the
> alternative is just as "Linuxy".

Thanks, this is really good feedback...

> 
> On Mon, Nov 21, 2005 at 01:18:39PM +0000, harry wrote:
> 
> > +/* This program is free software; you can redistribute it and/or modify it   */
> > +/* under the terms of the GNU General Public License as published by the     */
> > +/* Free Software Foundation; either version 2 of the License, or (at your    */
> > +/* option) any later version.
> */
> 
> Do we really need the GPL in every source file?

I asked my team lead to ask the lawyers what to put at the top of the
files.  4 months later I don't have an official reply ;-)

> 
> > +#include "xenidc_callback.h"
> > +#include <linux/module.h>
> 
> local includes after global includes (and asm after linux)
OK
> 
> > +	while ((!list_empty(&serialiser->list))
> > +	       && (!serialiser->running)
> > +	    ) {
> 
> This should be 
> 
>         while ((!list_empty(&serialiser->list)) && !serialiser->running) {
> 
> (no paren around a simple expression, fit it all on one line if
> possible in <80 chars)

Or:

 while (!list_empty(&serialiser->list) && !serialiser->running) {

?

> 
> > +EXPORT_SYMBOL(xenidc_callback_serialiser_function);
> 
> EXPORT_SYMBOL_GPL?

I don't care.  Actually, If the xenidc stuff is going to be really
useful we might want to get agreement from all the copyright holders to
license it under a different license.

> 
> 
> > +#if ( defined( CONFIG_XEN_IDC_TRACE ) || defined( XEN_IDC_TRACE ) )
> 
> No spaces after and before parens

OK. Lindent must have missed this.

> 
> #if (defined(CONFIG_XEN_IDC_TRACE) || defined(XEN_IDC_TRACE))
> 
> > +#define trace0( format ) \
> > +printk( KERN_INFO "xenidc %s:" format "\n", __PRETTY_FUNCTION__ )
> > +
> > +#define trace1( format, a0 ) \
> > +printk( KERN_INFO "xenidc %s:" format "\n", __PRETTY_FUNCTION__, a0 )
> > +
> > +#define trace2( format, a0, a1 ) \
> > +printk( KERN_INFO "xenidc %s:" format "\n", __PRETTY_FUNCTION__, a0, a1 )
> > +
> > +#define trace3( format, a0, a1, a2 ) \
> > +printk( KERN_INFO "xenidc %s:" format "\n", __PRETTY_FUNCTION__, a0, a1, a2 )
> > +
> > +#define trace() trace0( "" )
> 
> gcc has variable argument support in macros, please use it.
OK
> 
> > +#define traceonly( S ) S
> 
> What is this for? lose the parens.

For code which should only be compiled in when tracing is turned on.
The parens are required, no?

> 
> > +void xenidc_work_wake_up(void)
> > +{
> > +	unsigned long flags;
> > +
> > +	spin_lock_irqsave(&xenidc_work_list_lock, flags);
> > +
> > +	while (!list_empty(&xenidc_work_condition)) {
> > +		list_del_init(xenidc_work_condition.next);
> > +	}
> 
> No need for braces here.
OK.
> 
> > +typedef struct xenidc_callback_struct xenidc_callback;
> 
> no typedef for structs.
OK.
> 
> > +#define XENIDC_CALLBACK_LINK work.XENIDC_WORK_LINK
> 
> Please don't, don't hide structure members and don't name them in all
> UPPERCASE.

I didn't like this either. The problem is that the linux list code
list_for_each_entry needs to access the link field of the structres on
the list being iterated over.  If the structures on the list have a
public link field which is nested in a member structure then you don't
necessarily want to make public which nested structure it is in.  So,
this is a definition which says that the public link of the callback
structure is the one in the work member and this definition can be used
in the list_for_each_entry macro. Perhaps there's a better way of doing
this without coupling the code using list_for_each_entry to the
implementation of the structure with the public link.

> 
> > +static inline void xenidc_callback_init
> > +    (xenidc_callback * callback, xenidc_callback_function *
> function) {
> 
> This hsould be
> 
> static inline void
> xenid_callback_init(struct xenid_callback* callback,
> xenidc_callback_function* function)
> {

OK

> {
> 
> > +#define XENIDC_CALLBACK_SERIALISER_INIT( name )                  \
> > +{                                                                \
> > +    SPIN_LOCK_UNLOCKED,                                          \
> > +    LIST_HEAD_INIT( name.list ),                                 \
> > +    XENIDC_WORK_INIT                                             \
> > +      ( name.work, xenidc_callback_serialiser_function, &name ), \
> > +    0                                                            \
> > +}
> 
> Does this really need a macro? I know a bunch of Linux code does it,
> but it's always preferable if you can do it as an inline
> function. Also, what does the SPIN_LOCK_UNLOCKED do there?

This is for initialisation of statics.

i.e.

static xenidc_callback_serialiser fred =
XENIDC_CALLBACK_SERIALISER_INIT( fred );

Can't do this with an inline function.

> 
> > +		list_add_tail
> > +		    (xenidc_callback_to_link(callback),
> &serialiser->list);
> 
> This should be
> 
> 	list_add_tail(xenidc_callback_to_link(callback),
>                       &serialiser->list);

OK.  Lindent messed up a lot of these.

> 
> > +typedef s32 xenidc_error;
> 
> Why? also, why signed, and why just 32 bits even on 64? does it go
> over the wire?

Yes, it goes over the wire.  Of all the code in the patches, I think I'm
least happy about the error codes.

> 
> > +#define XENIDC_ERROR_SUCCESS                   ( (xenidc_error)0 )
> 
> No parens. Also, can you use errno values rather than inventing your
> own? 

Maybe.  The interdomain error codes are communicated potentially between
different operating systems.  Making them look obviously different might
be an advantage.

> 
> > +#define XENIDC_WORK_LINK link
> 
> Why is the renaming necessary?

This is the public link of this structure for use in
list_for_each_entry.

> 
> > +int xenidc_work_schedule(xenidc_work * work);
> 
> The '*' should be aligned to the left.
OK
> 
> > +/* from a work item and works even when the condition will only be satisfied */
> > +/* by another work item.                                                     */
> > +
> > +#define xenidc_work_until( condition )                                  \
> > +do                                                                      \
> > +{                                                                       \
> > +    unsigned long flags;                                                \
> > +                                                                        \
> > +    spin_lock_irqsave( &xenidc_work_list_lock, flags );                 \
> > +                                                                        \
> > +    for( ; ; )                                                          \
> > +    {                                                                   \
> > +        while                                                           \
> > +        (                                                               \
> > +            ( !list_empty( &xenidc_work_list ) )                        \
> > +            &&                                                          \
> > +            ( !( condition ) )                                          \
> > +        )                                                               \
> > +        {                                                               \
> > +            xenidc_work * work = list_entry                             \
> > +            (                                                           \
> > +                xenidc_work_list.next,                                  \
> > +                xenidc_work,                                            \
> > +                link                                                    \
> > +            );                                                          \
> > +                                                                        \
> > +            list_del_init( &work->link );                               \
> > +                                                                        \
> > +            spin_unlock_irqrestore( &xenidc_work_list_lock, flags );    \
> > +                                                                        \
> > +            xenidc_work_perform_synchronously( work );                  \
> > +                                                                        \
> > +            spin_lock_irqsave( &xenidc_work_list_lock, flags );         \
> > +        }                                                               \
> > +                                                                        \
> > +        if( condition )                                                 \
> > +        {                                                               \
> > +            break;                                                      \
> > +        }                                                               \
> > +                                                                        \
> > +        {                                                               \
> > +            struct list_head link;                                      \
> > +                                                                        \
> > +            INIT_LIST_HEAD( &link );                                    \
> > +                                                                        \
> > +            list_add_tail( &link, &xenidc_work_condition );             \
> > +                                                                        \
> > +            spin_unlock_irqrestore( &xenidc_work_list_lock, flags );    \
> > +                                                                        \
> > +            wait_event( xenidc_work_waitqueue, list_empty( &link ) );   \
> > +                                                                        \
> > +            spin_lock_irqsave( &xenidc_work_list_lock, flags );         \
> > +        }                                                               \
> > +    }                                                                   \
> > +                                                                        \
> > +    spin_unlock_irqrestore( &xenidc_work_list_lock, flags );            \
> > +}                                                                       \
> > +while( 0 )
> 
> Argh! I hate these macros with a passion. We could really use a lambda
> here, but how about just passing an int (*func)(void* p) instead of
> the condition and making this into a function? I'm aware of the fact
> that this is how Linux does it (albeit the macros are not quite this
> long) but debugging it is awful.

Yeah, this code sucks.  I would have preferred if the underlying Linux
code worked differently.  I could do the function pointer thing but it
makes the client code harder to write.

> 
> More to come.
> 
> Cheers,
> Muli
-- 
Harry Butterworth <harry@hebutterworth.freeserve.co.uk>

  parent reply	other threads:[~2005-11-21 21:21 UTC|newest]

Thread overview: 9+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2005-11-21 13:18 [PATCH][1/17] USB virt 2.6 split driver---xenidc platform harry
2005-11-21 20:10 ` Muli Ben-Yehuda
2005-11-21 21:03   ` Stephan Seitz
2005-11-21 21:07     ` Muli Ben-Yehuda
2005-11-21 21:21   ` Harry Butterworth [this message]
2005-11-22 10:51     ` Muli Ben-Yehuda
2005-11-22 11:05       ` harry
2005-11-22 15:05         ` Mark Williamson
2005-11-22  0:10   ` Anthony Liguori

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=1132608080.4739.17.camel@localhost \
    --to=harry@hebutterworth.freeserve.co.uk \
    --cc=mulix@mulix.org \
    --cc=xen-devel@lists.xensource.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.