After a pattern has matched it is possible to execute Python code. The execution of this code is conditional on any metavariables appearing in the script prelude having been bound to values within the matching pattern.
In the following example the first Python script will not be executed unless the metavariable E_2_2 has been bound to a value and this will only occur when the matched expression-statement has the logical-OR form.
@ if_eq_or_2
@
expression E_2;
constant {char, int, unsigned int, long, unsigned long} E_2_1, E_2_2;
@@
(
( E_2 == E_2_1 ) ;
|
( E_2 == E_2_1 ) || ( E_2 == E_2_2 ) ;
}
@
// First Python script
script:python @ expr_1<< if_eq_or_2.E_2;
const_1 << if_eq_or_2.E_2_1;
@@
print expr_1, " == ", const_1
@
// Second Python script
script:python @ expr_1<< if_eq_or_2.E_2;
const_1 << if_eq_or_2.E_2_1;
const_2 << if_eq_or_2.E_2_2;
@@
print expr_1, " == ", const_1, " || ", expr_1, " == ", const_2
Note that when the matched expression-statement has the logical-OR form both the first and second Python scripts will be executed.
How might the Python scripts be written to ensure that only one of them is executed? One solution is to reorder the Python scripts and insert the call cocci.include_match(False) into what has become the first script. This call discards the environment, unbinding any metavariables and preventing any further script preludes succeeding.
@ if_eq_or_2
@
expression E_2;
constant {char, int, unsigned int, long, unsigned long} E_2_1, E_2_2;
@@
(
( E_2 == E_2_1 ) ;
|
( E_2 == E_2_1 ) || ( E_2 == E_2_2 ) ;
}
@
// First (was Second) Python script
script:python @ expr_1<< if_eq_or_2.E_2;
const_1 << if_eq_or_2.E_2_1;
const_2 << if_eq_or_2.E_2_2;
@@
print expr_1, " == ", const_1, " || ", expr_1, " == ", const_2
cocci.include_match(False)
@
// Second (was First) Python script
script:python @ expr_1<< if_eq_or_2.E_2;
const_1 << if_eq_or_2.E_2_1;
@@
print expr_1, " == ", const_1