On Fri, 12 Nov 2010, Andriy Gapon wrote:

> on 12/11/2010 15:32 Nicolas Palix said the following:
> > Hi Andriy,
> > 
> > On Fri, Nov 12, 2010 at 2:26 PM, Andriy Gapon <[email protected]> wrote:
> >>
> >> I wonder if coccinelle can help me with the following issue.
> >> There is a type, let's call it sometype_t, that is typedef-ed to int.
> >> There is an API which uses that type consistently to provide for possible 
> >> future
> >> extensions.  But that there are many lax users of that API which 
> >> frequently use
> >> int instead of sometype_t.
> >> For example, sometimes a sometype_t variable is assigned with int value, or
> >> conversely a sometype_t value is assigned to int variable, or int value is 
> >> passed
> >> in a function parameter where sometype_t is expected.
> >>
> >> I wonder if I could use the power of coccinelle to easily find and perhaps 
> >> even
> >> fix such lax type handling.
> > 
> > Coccinelle should be useful for that purpose, i.e. finding and fixing.
> > 
> > What kind of sometype_t values do you have ?
> > Is it some #define constant ?
> 
> No, it's an enum-ish type, more like a bitmask type that can have various 
> values.
> 
> > Do you already have the set of fonctions that take a sometype_t parameter
> > or should you first find them ?
> 
> The number of such functions is quite large, so it's probably better to detect
> them.  But finding them in advance should also be easily doable.

I just did the return value case.  You can use the metavariable 
declarations:

parameter list[n] ps;
expression list[n] es;

which each declare two metavariables: n for the length of the list and ps 
or es for the list of parameters or expressions itself.  Then, if you have 
for example the prototype of the function, you can do the following (here 
I have used my safer version, because you may need to allow include files 
to find the prototype):

You can thus do the following:

@r@
typedef sometype_t;
parameter list[n] ps;
identifier f;
@@

void f(ps,sometype_t,...);

@@
expression list [r.n] es;
sometype_t x;
int y;
identifier r.f;
@@

(
f(es,x,...)
|
f(es,
*    y,
  ...)
)

It's a little bit awkward, though, because the pattern for a prototype 
with a variable declaration, ie void f(ps,sometype_t x,...);, only matches 
a prototype that mentioned a variable name, and the pattern for a 
prototype without a variable declaration, as shown above, only matches the 
case without a variable.  There is no disjuction for prototypes, so you 
have to duplicate the above two rules.  And then you need another copy of 
the above two rules for the case where the function definition is given, 
rather than a prototype.

julia
_______________________________________________
Cocci mailing list
[email protected]
http://lists.diku.dk/mailman/listinfo/cocci
(Web access from inside DIKUs LAN only)

Reply via email to