[
Date Prev][
Date Next][
Thread Prev][
Thread Next][
Date Index][
Thread Index]
[
List Home]
Re: [aspectj-users] cflow(within(C)) vs (within(C) || cflowbelow(within(C)) [BUGZILLA-ed]
|
Reference bug#74952.
Thanks for the replies. I will remember not to use cflow alone.
Chi-Hua
--- Wes Isberg <wes@xxxxxxxxxxxxxx> wrote:
> Hi all -
>
> Some comments but no definitive answers wrt the bugs
>
> 1) see existing code for printing join points
> 2) don't use !cflow(..)
> 3) changing precedence makes the preinitialization advice work
> 4) aspects advising themselves have to be careful
> during instantiation...
>
> To start with the initial concern...
>
> The AspectJ sample code has a program that will print all join
> points.
> The sample code (as distinct from the examples) is only available
> via a link off the AspectJ web site publication page. To make
> it even easier, here's a simple variant:
>
> ---------- AllJoinPoints.java
>
> public class AllJoinPoints {
> static int I = 1;
> int j = 2*I;
> public static void main(String[] a) {
> try {
> new AllJoinPoints().toString();
> throw new Error();
> } catch (Throwable t) {
> System.out.println("Hello, World!");
> }
> }
> static aspect A {
> before(): execution(void main(String[])) {
> System.out.println("This is just to say...");
> }
> }
>
> }
> aspect B {
> pointcut all() : !within(B);
> before() : all() {
> System.out.println("start: " + thisJoinPointStaticPart);
> }
> after () returning : all() && !handler(*) {
> System.out.println(" end: " + thisJoinPointStaticPart);
> }
> }
> ----------
>
> As for the programs, I recommend no one use cflow(..) alone as a
> pointcut used by advice. It means every join point in the world
> has to do this dynamic check. cflow differs from target(), args(),
> and this() in that there's no information in the join point itself
> that would tell you to skip it (e.g., this(Runnable) is
> inapplicable in any execution join point of a class that is not
> Runnable). And since even those possible optimizations are not
> guaranteed, using a purely dynamic pointcut could devolve to the
> worst case in some implementations of AspectJ, so all lone dynamic
> PCD's should be scrutinized...
>
> To back up a bit, cflow(), target(), args() and this() are dynamic.
> You can think of a pointcut as having three components: the kinds,
> the scopes, and any dynamic tests. It is fair to ask for all
> kinds by leaving out call, execution, etc., and for all scopes
> by leaving out within, etc., but "finding all {other} join points"
> is about the only use-case for doing both.
>
> (And if I haven't convinced folks on style grounds, just look
> at what the implementation does *smile*)
>
> Now, to address what's going wrong (though not completely)...
>
> A hint regarding the missing after-advice on the preinitialization
> join point: it re-appears if it's of a lower precedence (and
> hence runs before) the advice in the aspect that's being
> initialized. E.g.,
>
> aspect TraceTrace {
> // our after advice runs before TraceClass advises itself...
> declare precedence : TraceClass, TraceTrace;
> pointcut pc() : within(TraceClass);
> before() : pc() {
> System.out.println("-> " + thisJoinPoint);
> }
> after() returning : pc() {
> System.out.println("<- " + thisJoinPoint);
> }
> }
>
> Finally, in the original code, the singleton aspect is being
> being instantiated in the static initializer of the aspect
> class when something blows up. It so happens that the cflow
> stuff is set up in the class static preinitialization so that
> it's usable but probably not correct; since it returns no/false
> by default, !cflow(..) would run by default, in every join point...
>
> There is a bug or two in here; would anyone care to submit it?
>
> Hope this helps -
> Wes
>
>
> > ------------Original Message------------
> > From: Stephanie <stephaniechc-newsaj@xxxxxxxxx>
> > To: aspectj-users@xxxxxxxxxxx
> > Date: Thu, Sep-23-2004 2:25 PM
> > Subject: [aspectj-users] cflow(within(C)) vs (within(C) ||
> cflowbelow(within(C))
> >
> > I am new to AspectJ and is just trying to understand what each kind
> of
> > pointcut matches. So I wrote a simple class, SomeClass, and a
> simple
> > aspect, TraceClass, and was hoping that the aspect would print out
> all
> > the join points in SomeClass. To avoid infinite recursion, in
> > TraceClass I used "!cflow(within(Trace*))" as the pointcut.
> However, I
> > was not getting any output. Though "!(within(Trace*) ||
> > cflowbelow(within(Trace*)))" worked as I expected (printing
> something).
> > (From the post "cflow ( x()) && !cflowbelow( x()) " confusesme" I
> > gathered that cflow(x()) does not equal to (x() ||
> cflowbelow(x())).
> > However, I still don't understand why my test doesn't work).
> >
> > class SomeClass
> > {
> > static public void main (String [] args) {
> > }
> > } // SomeClass
> >
> > aspect TraceClass {
> >
> > // members
> > static private int level = 0;
> >
> > static private void offset() {
> > int i;
> > for (i = 0; i < level; ++i) {
> > System.out.print(" ");
> > }
> > } // offset
> >
> > pointcut pc() :
> > !cflow(within(Trace*))
> > // !(within(Trace*) || cflowbelow(within(Trace*)))
> > ;
> > before () : pc() {
> > offset();
> > System.out.println("-> " + thisJoinPoint);
> > ++level;
> > }
> > after () : pc() {
> > --level;
> > offset();
> > System.out.println("<- " + thisJoinPoint);
> > }
> > } // TraceClass
> >
> > In order to figure out what is happening with TraceClass, I added a
> > third class, TraceTrace, which prints everything happen
> > "within(TraceClass)". Again, when TraceClass used "!(within(Trace*)
> ||
> > cflowbelow(within(Trace*)))" it worked. However, when TraceClass
> used
> > "!cflow(within(Trace*))", the output was
> >
> > => staticinitialization(TraceClass.<clinit>)
> > => set(int TraceClass.level)
> > <= set(int TraceClass.level)
> > => preinitialization(TraceClass())
> > => initialization(TraceClass())
> > => execution(TraceClass())
> > <= execution(TraceClass())
> > <= initialization(TraceClass())
> > <= staticinitialization(TraceClass.<clinit>)
> >
> > The after advice for preinitialization was never executed and no
> trace
> > for SomeClass was printed.
> >
> > aspect TraceTrace {
> >
> > // members
> > static private int level = 0;
> >
> > static private void offset() {
> > int i;
> > for (i = 0; i < level; ++i) {
> > System.out.print(" ");
> > }
> > } // offset
> >
> > pointcut pc() : within(TraceClass);
> > before () : pc() {
> > offset();
> > System.out.println("=> " + thisJoinPoint);
> > ++level;
> > }
> > after () : pc() {
>
=== message truncated ===