I've been thinking and working on a possible fix for bug
http://nagoya.apache.org/bugzilla/show_bug.cgi?id=8290.  The issue concerns
the often deep nesting of try/finally blocks that triggers a bug in the
JVM that result in bad JSP performance.  The proposition is to limit the
number of try/finally blocks by marking what would be the try block as
started and then marking again when the finally block would be entered.  This
bug is mostly evident if a JSP uses a lot of taglibs tags.

More simply put, the proposition replaces code like this:

public class JSPsomething {
        <...>
        
        public void _jspService(HttpServletRequest request, HttpServletResponse 
response)
        throws java.io.IOException, ServletException {

                <...>
                try {
                        <TRY BLOCK 1>

                        try {
                                <TRY BLOCK 2>

                                try {
                                        <TRY BLOCK 3>
                                } finally {
                                        <FINALLY BLOCK 3>
                                }

                                try {
                                        <TRY BLOCK 4>
                                } finally {
                                        <FINALLY BLOCK 4>
                                }
                        } finally {
                                <FINALLY BLOCK 2>
                        }
                } finally {
                        <FINALLY BLOCK 1>
                }
        }
}


To be generated like this:

public class JSPsomething {
        <...>
        
        public void _jspService(HttpServletRequest request, HttpServletResponse 
response)
        throws java.io.IOException, ServletException {

                try {
                        <...>
                        set_bit(1)
                        <TRY BLOCK 1>

                        set_bit(2)
                        <TRY BLOCK 2>

                        set_bit(3)
                        <TRY BLOCK 3>

                        clear_bit(3)
                        <FINALLY BLOCK 3>

                        set_bit(4)
                        <TRY BLOCK 4>

                        clear_bit(4)
                        <FINALLY BLOCK 4>

                        clear_bit(2)
                        <FINALLY BLOCK 2>

                        clear_bit(1)
                        <FINALLY BLOCK 1>
                } finally {
                        doFinally()
                }
        }


        doFinally() {
                if_bit_set(3)
                        <FINALLY BLOCK 3>
                if_bit_set(4)
                        <FINALLY BLOCK 4>
                if_bit_set(2)
                        <FINALLY BLOCK 2>
                if_bit_set(1)
                        <FINALLY BLOCK 1>
        }
}


On a flow control view point both are identical, but the second one has the
advantage of not needlessly nesting try/finally blocks, so it bypasses the
bug of the JVM.  I did a patch that is relatively "fresh", so I can't provide
any hard benchmark to demonstrate the performance gain of the approach.  But
our initial results did show some very encouraging performance results.
With a JSP with 100 taglibs, the "old" code triggered the bug in the JVM
that resulted in frequent JVM stall from 5 to as much as 45 seconds.  the
"new" code did not show this behaviour.  Next week I'll be able to use
JMeter to load test the "new" code and compare it the the "old" code.

Comments or suggestions are welcome.

Thanks!

-- 
Denis Benoit


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

Reply via email to