All of lore.kernel.org
 help / color / mirror / Atom feed
From: Al Viro <viro@ZenIV.linux.org.uk>
To: Christopher Li <sparse@chrisli.org>
Cc: Derek M Jones <derek@knosof.co.uk>, linux-sparse@vger.kernel.org
Subject: Re: fun with declarations and definitions
Date: Mon, 9 Feb 2009 08:54:01 +0000	[thread overview]
Message-ID: <20090209085400.GT28946@ZenIV.linux.org.uk> (raw)
In-Reply-To: <70318cbf0902082352n32450ca2g87c847bb035baf15@mail.gmail.com>

On Sun, Feb 08, 2009 at 11:52:23PM -0800, Christopher Li wrote:
> > Subject: [PATCH] Handle nested declarators vs. parameter lists correctly
> >
> > Seeing a typedef name after ( means that we have a parameter-type-list
> > only if we are parsing a parameter declaration or a typename; otherwise
> > it might very well be a redeclaration (e.g. int (T); when T had been a
> > typedef in outer scope).
> 
> The patch looks great. Applied.

Still leaves a couple of uglies, BTW.  One (easily fixed):

int [2]*p[3];

is actually (still) accepted.  Nevermind, we just need to set dont_nest
in a few more places (and no, it's not a regression; moreover, similar
crap works with functions instead of arrays).

Nastier one:
#define A __attribute__((address_space(1)))
void (*f)(A int *x, A int *y) = (void *)0;
void g(int A *x)
{
        f(x, x);
}

now try test-parsing on it.  You'll see that f gets type
void (A *)(int *, int A *);
instead of expected
void (*)(int A *, int A *);

Reason: cretinous gcc grammar is fscked in head.  There's a very, _very_
good reason why C doesn't allow e.g.
	int (const x);
Consider seeing
	void f(int (const
What would that "(const" be?  Beginning of parameter list in the first
parameter of f or a beginning of nested declarator in the same?  In
C it's the former and we can tell that immediately.

I really don't want to get into the reasons why gcc decided to allow that with
s/const/__attribute__((....))/ - it's too long a flame, but they did and
so we have to do lookahead from hell in parser.  Namely, eat all attributes
first and only then decide whether this ( starts a nested declarator or a
parameter list.

... except that we do it wrong and these attributes land on what will by
SYM_FN and not its first parameter.

BTW, the longer I'm looking at that, the less I like the original decision
to use __attribute__ for our extensions.  Or continued use of __attribute__
by gcc folks, while we are at it.

One lovely example:
	T __attribute__((whatever)) *p;
is NOT pointer-to-whatever-T; it's whatever-pointer-to-T.  Which is clearly
not what we want for __user et.al.  The only way to get it applied *before*
derivation is, BTW,
	T (__attribute__((whatever)) *p);
(and yes, that's where this crap in syntax has come from).  Mind you,
	T * __attribute__((whatever)) *p;
*is* pointer-to-whatever-pointer-to-T, which makes the situation even more
inconsistent.

While we are at it, our handling of __attribute__((mode(...))) is wrong -
not only
__attribute__((mode(HI)) long x;
is fine, it's actually s16.  Moreover,
int __attribute__((mode(HI)) *x;
is only going to work on 16bit boxen, since it's "16bit pointer to int".
64/32bit analogs of that construct *are* used in the wild on some weird
targets.

  reply	other threads:[~2009-02-09  8:54 UTC|newest]

Thread overview: 18+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2009-02-02  7:30 fun with declarations and definitions Al Viro
2009-02-02 20:17 ` Christopher Li
2009-02-02 20:58   ` Al Viro
2009-02-02 22:25     ` Christopher Li
2009-02-03  3:07 ` Christopher Li
2009-02-03  4:13   ` Al Viro
2009-02-05 18:40     ` Christopher Li
2009-02-05 18:47       ` Derek M Jones
2009-02-05 20:28         ` Al Viro
2009-02-05 21:19           ` Al Viro
2009-02-06  5:36             ` Al Viro
2009-02-09  7:52               ` Christopher Li
2009-02-09  8:54                 ` Al Viro [this message]
2009-02-05 22:41           ` Christopher Li
2009-02-05 23:22             ` Al Viro
2009-02-03  4:41   ` Al Viro
2009-02-03  6:28     ` Ralf Wildenhues
2009-02-05 18:52     ` Christopher Li

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=20090209085400.GT28946@ZenIV.linux.org.uk \
    --to=viro@zeniv.linux.org.uk \
    --cc=derek@knosof.co.uk \
    --cc=linux-sparse@vger.kernel.org \
    --cc=sparse@chrisli.org \
    /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.