Hi all,

We were recently contacted by Markus about merging some of the ideas
from Jiapi (http://jiapi.sf.net) to BCEL. Since you have been
discussing about adding features to BCEL to do class enhancements
(faster reflection, better JavaBeans API etc.), it might be a good
idea to build them on top of a common framework. We have started to do
similar enhancement project. http://www.sf.net/projects/jadoe which
implements JDO enhancer as specified in JDO specification. This is an
email which I sent to Markus last week:


++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
From: [EMAIL PROTECTED]
Date: 06 Jun 2002 09:38:53 +0300

Hi Markus!

This is an interesting suggestion. I browsed through the thread "New
Reflection/Beans API" from bcel-dev list. I assume that you refer
to the discussion there with "since we're currently discussing
additional reflective features for BCEL...".

I understood those ideas so that you would like to add features to
BCEL to do "enhancement" for classes. E.g. enhancements to support
faster reflection, enhancements to support better Java beans
capabilities etc. Please correct me if I'm wrong.

This is very much similar to what we have started to do in a Jadoe
project (http://www.sf.net/projects/jadoe). Jadoe implements a JDO
enhancer by augmenting the target classes so that they implement JDO's
PersistenceCapable interface correctly. This is specified in a JDO
specification. The project utilizes Jiapi framework to do the required
bytecode enhancements.

I'll give you a brief description of Jiapi for you to get better
understanding of our focus and project's state. We know BCEL pretty
well since we build on top of it.


1. Jiapi reflection

This is the lowest layer in Jiapi architecture. Despite the name, this
should not be confused with the ideas about reflection you have been
discussing in bcel-dev list. Jiapi reflection just provides a load
time API which mimics the Java reflection API. This part of Jiapi
significantly overlaps with BCEL. There's many similar concepts which
Jiapi and BCEL share at this level:

      BCEL                               Jiapi

InstructionList                     InstructionList
InstructionFactory                  InstructionFactory
JavaClass and ClassGen              JiapiClass
Method + MethodGen                  JiapiMethod
Field + FieldGen                    JiapiField
Instruction + InstructionHandle     Instruction
...                                 ...

So, Jiapi reflection provides similar functionality than BCEL through
a bit different API. The design principles that we have tried to
follow when designing this API:

- The API should be as closely similar to Java reflection API than
possible/feasible.

- InstructionList should follow Java collection (List's) semantics. In
addition it should provide a way to create a sub list that allows
structural modifications from any of its peers. This requirement came
from the Jiapi framework which is explained below.

- JiapiClass, JiapiMethod and JiapiField must hide the internal
details of Java classfile structure. This allows us to hide concepts
like constant pool, exception table etc. We believe that this hiding
simplifies the API and makes it more accessible to people who are not
familiar with the Java classfile structure.

- When a new abstraction is needed, create it from a Java programmer's
perspective. As an example, when we needed an abstraction for
exceptions we created two concepts: TryBlock and
ExceptionHandler. Conceptually these map against try-catch block in
Java language and internally these are mapped to Java classfile's
exception table structure. 

I am not sure if you would be so interested about this layer since it
really doesn't bring any new functionality what BCEL already
provides? It just wraps the similar functionality to a new API.


2. Jiapi framework

Jiapi instrumentation framework is built on top of Jiapi
reflection. It provides a framework to create "bytecode
enhancers". The framework provides following features at the moment: 

- A mechanism to target instrumentations to a specific set of
classes. e.g.:
InstrumentationDescriptor.addInclusionRule("org.opensource.*");
InstrumentationDescriptor.addExclusionRule("org.closedsource.*");

- A simple and lightweight component model to encapsulate specific
bytecode manipulation. These components implement
alt.jiapi.Instrumentor interface and do their work at method:
  public void instrument(InstructionList il)
There's a couple of built-in instrumentors in alt.jiapi.instrumentor
package. 

- A pipeline to plug instrumentors together. This pipeline is
implemented as a filter design pattern and the analogy which we have
been used, is Unix shell. As in Unix shell. the idea is to pipe simple
components together to achive more complex behaviour. This pipeline is
realized as alt.jiapi.InstrumentorChain and it is used so that the
application developer adds Instrumentors to the chain. The chain is
then dispatched to each class which matches the configuration
(e.g. "org.opensource.*"). 

- A context to group many InstrumentorChains to do their work.

In addition there's some utilities to help development on this
framework (a sample class loader, chain builder and bootstrapper) and
an event based API to get some runtime information from instrumented
classes. 

Our aim has been to create an infrastructure to enable one to create
robust bytecode enhancers in a higher level of abstraction than plain
bytecode is.

OK, that is what there's in Jiapi at the moment. Did this raise any
questions for you? Let's continue the discussion to find out the ways
we could collaborate!

Joni

++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++


Our suggestion is that we would port the Jiapi framework directly on
top of BCEL, leaving out Jiapi reflection layer. This framework could
then be an initial BCEL framework (Java Class Enhancer?) for which to
build all kinds of bytecode enhancers (Reflection, JavaBeans++, JDO
enhancer etc). 

To be able to do that, there's at least two modifications which would
be needed to core BCEL. 

1. The InstrtuctionList must support creation of sub list in such a
way that it allows structural changes from any of its peers. Jiapi
InstructionList has this capability. You might want to take a look at
(specifically InstructionList.View):
http://cvs.sourceforge.net/cgi-bin/viewcvs.cgi/jiapi/jiapi/src/alt/jiapi/reflect/instruction/InstructionList.java?rev=1.6&content-type=text/vnd.viewcvs-markup

2. InstructionList must support copying of instructions from one list
to another in such a way that it can redirect all branches etc. These
InstructionLists may or may not belong to a same class.


The reason for requirement 1. is that the framework relies heavily to
a concept of chopping an InstructionList to smaller pieces. This is
perhaps easiest to describe using a hypothetical example. Let's say we
need to inject a method call "Bar.fieldAccessed()" just before a field
"Foo.foobar" is accessed. Using Jiapi instrumentors this could be
realized as: 

InstrumentorChain chain = new InstrumentorChain();
chain.add(new MethodDispatcherInstrumentor());
chain.add(new GrepInstrumentor(new FieldAccessStrategy("Foo.foobar")));
chain.add(new MethodCallInstrumentor("Bar.fieldAccessed"));

So the chain is formed as:

JavaClass    +-------------------+     +------+     +-------------+
        \--> | method dispatcher | --> | grep | --> | method call |
             +-------------------+     +------+     +-------------+

This is what happens when the chain is dispatched for a target class:

1. Method dispatcher loops over class' methods and forwards each
method's InstructionList to a next component in a chain, one at a time.

2. Grep finds places where a field "Foo.foobar" is accessed from an
InstructionList which is passed to it. It chops down the list from
places where the field is accessed and forwards each InstructionList
piece to a next component in a chain.

3. Method call inserts a bytecode which makes a method call to the end
of each InstructionList which is passed to it.


The reason for requirement 2. is that when doing class enhancements,
it is sometimes easiest to write the enhancement in Java language,
compile the enhancement template to bytecode, and then copy the
resulting bytecode to target classes. 


Before proceeding we would like to get input from BCEL developers. Is
this framework something you could find useful? Do you see the above
mentioned two requirements feasible to implement in BCEL?

Cheers,
Joni Suominen





--
To unsubscribe, e-mail:   <mailto:[EMAIL PROTECTED]>
For additional commands, e-mail: <mailto:[EMAIL PROTECTED]>

Reply via email to