On 06.09.2004 22:31:24 Glen Mazza wrote:
> Jeremias Maerki wrote:
> >Ok, the FOEventHandler is created in the FOTreeBuilder. One FO
> >TreeBuilder is instantiated per processing run. The FOEventHandler is
> >set on FONode's static variable during startDocument(). The
> >FOEventHandler keeps track of used fonts, number of pages, tracking IDs
> >etc. which are all relevant to one document run.
> >  
> >
> Incidentally, I'd like to get the fonts out of FOEventHandler, I think 
> they should be declared only within those subclasses of FOEventHandler 
> that need them.  But we can take up that issue later.

Here you need to be more precise. Are you talking about the set of
available fonts or the set of used fonts within the document/processing
run? The former is not a problem in this matter, but the other is as are
the other examples I mentioned. They are specific to the rendering run.

> >Now imagine a situation where multiple processing runs occur and just
> >after the TreeBuilder sets the FOEventHandler on FONode in
> >startDocument() and continues layout, another thread starts another
> >processing run and runs through FOTreeBuilder.startDocument() before the
> >whole layout process of the first processing run is finished. 
> >
> But that would be another instance of the application, so that would be 
> another instance's FOEventHandler that would be altered.  Statics are 
> common to a running instance, not all running instances of the same 
> application in general.  Please continue to elaborate.

A static variable is unique within the same classloader. If you deploy
FOP as a servlet there is one classloader loading the FOP classes and
FONode's static foEventHandler variable is shared between all instances
of the Fop class and therefore between rendering runs. Now Tomcat can
initiate multiple FOP rendering runs in multiple threads and that's
where the trouble begins.

What is an application in your terminology? I don't think there is such
a thing in Java. At least it's not a technical term but only a logical
one. If you deploy fop.jar using the boot classloader in Tomcat and
deploy two "applications" (each using a separate classloader for each
WAR file). Both webapps are using FOP in a different way, you still have
only one static foEventHandler variable which is shared between two
applications. That's probably a non-realistic approach for FOP, but
Xerces and Xalan are usually deployed this way.

A figure showing Tomcat's classloader hierarchy:

I think in your view of the things you'd have to provide a classloader
for each instance of Fop to they don't bump into each other, but that's
not what you will want.

> Also, are you aware of why I switched to a static?  To end the 
> continuous recursion to the fo:root each time any of the child nodes 
> need to call getFOEventHandler().startThisFormattingObject() and/or 
> getFOEventHandler().endSomeFormattingObject().

Yes, I realize that. That's why I proposed looking at ThreadLocal after
thinking some more about the problem. On the other side have you done
speed checks to figure out if the recursion is really a problem? Java
can optimize pretty well by itself and often it's not worth
breaking your head. Also something I learned on this list.

Jeremias Maerki (off to bed...)

Reply via email to