costin 01/05/27 19:17:58 Added: jasper34/liaison/org/apache/jasper34/servlet EmbededServletOptions.java JasperLoader.java JasperLoader12.java JspEngineContext.java JspLoader.java JspServlet.java ServletEngine.java TomcatServletEngine.java Log: Added the (old) servlet interface. Revision Changes Path 1.1 jakarta-tomcat-jasper/jasper34/liaison/org/apache/jasper34/servlet/EmbededServletOptions.java Index: EmbededServletOptions.java =================================================================== /* * ==================================================================== * * The Apache Software License, Version 1.1 * * Copyright (c) 1999 The Apache Software Foundation. All rights * reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The end-user documentation included with the redistribution, if * any, must include the following acknowlegement: * "This product includes software developed by the * Apache Software Foundation (http://www.apache.org/)." * Alternately, this acknowlegement may appear in the software itself, * if and wherever such third-party acknowlegements normally appear. * * 4. The names "The Jakarta Project", "Tomcat", and "Apache Software * Foundation" must not be used to endorse or promote products derived * from this software without prior written permission. For written * permission, please contact [EMAIL PROTECTED] * * 5. Products derived from this software may not be called "Apache" * nor may "Apache" appear in their names without prior written * permission of the Apache Group. * * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE * DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * ==================================================================== * * This software consists of voluntary contributions made by many * individuals on behalf of the Apache Software Foundation. For more * information on the Apache Software Foundation, please see * <http://www.apache.org/>. * */ package org.apache.jasper34.servlet; import java.io.File; import javax.servlet.ServletConfig; import javax.servlet.ServletContext; import org.apache.jasper34.core.*; import org.apache.tomcat.util.log.*; /** * A class to hold all init parameters specific to the JSP engine. * * @author Anil K. Vijendran * @author Hans Bergsten */ public final class EmbededServletOptions implements Options { /** * Do you want to keep the generated Java files around? */ public boolean keepGenerated = true; /** * Do you want support for "large" files? What this essentially * means is that we generated code so that the HTML data in a JSP * file is stored separately as opposed to those constant string * data being used literally in the generated servlet. */ public boolean largeFile = false; /** * Do you want support for "mapped" files? This will generate * servlet that has a print statement per line of the JSP file. * This seems like a really nice feature to have for debugging. */ public boolean mappedFile = false; /** * Do you want stack traces and such displayed in the client's * browser? If this is false, such messages go to the standard * error or a log file if the standard error is redirected. */ public boolean sendErrorToClient = false; /** * Do we want to include debugging information in the class file? */ public boolean classDebugInfo = false; /** * I want to see my generated servlets. Which directory are they * in? */ public File scratchDir; /** * When used with a Securitymanager, what ProtectionDomain to use. */ private Object protectionDomain; /** * Need to have this as is for versions 4 and 5 of IE. Can be set from * the initParams so if it changes in the future all that is needed is * to have a jsp initParam of type ieClassId="<value>" */ public String ieClassId = "clsid:8AD9C840-044E-11D1-B3E9-00805F499D93"; /** * What classpath should I use while compiling generated servlets? */ public String classpath = null; /** * Plugin class to use to compile JSP pages. */ public Class jspCompilerPlugin = null; /** * Path of the compiler to use for compiling JSP pages. */ public String jspCompilerPath = null; /** * Java platform encoding to generate the JSP * page servlet. */ private String javaEncoding; /** * Are we keeping generated code around? */ public boolean getKeepGenerated() { return keepGenerated; } /** * Are we supporting large files? */ public boolean getLargeFile() { return largeFile; } /** * Are we supporting HTML mapped servlets? */ public boolean getMappedFile() { return mappedFile; } /** * Should errors be sent to client or thrown into stderr? */ public boolean getSendErrorToClient() { return sendErrorToClient; } /** * Should class files be compiled with debug information? */ public boolean getClassDebugInfo() { return classDebugInfo; } /** * Class ID for use in the plugin tag when the browser is IE. */ public String getIeClassId() { return ieClassId; } /** * What is my scratch dir? */ public File getScratchDir() { return scratchDir; } /** * ProtectionDomain for this JSP Context when using a SecurityManager */ public final Object getProtectionDomain() { return protectionDomain; } /** * What classpath should I use while compiling the servlets * generated from JSP files? */ public String getClassPath() { return classpath; } /** * What compiler plugin should I use to compile the servlets * generated from JSP files? */ public Class getJspCompilerPlugin() { return jspCompilerPlugin; } /** * Path of the compiler to use for compiling JSP pages. */ public String getJspCompilerPath() { return jspCompilerPath; } public String getJavaEncoding() { return javaEncoding; } /** * Create an EmbededServletOptions object using data available from * ServletConfig and ServletContext. */ public EmbededServletOptions(ServletConfig config, ServletContext context) { String keepgen = config.getInitParameter("keepgenerated"); if (keepgen != null) { if (keepgen.equalsIgnoreCase("true")) this.keepGenerated = true; else if (keepgen.equalsIgnoreCase("false")) this.keepGenerated = false; else Constants.message ("jsp.warning.keepgen", Log.WARNING); } String largeFile = config.getInitParameter("largefile"); if (largeFile != null) { if (largeFile.equalsIgnoreCase("true")) this.largeFile = true; else if (largeFile.equalsIgnoreCase("false")) this.largeFile = false; else Constants.message ("jsp.warning.largeFile", Log.WARNING); } String mapFile = config.getInitParameter("mappedfile"); if (mapFile != null) { if (mapFile.equalsIgnoreCase("true")) this.mappedFile = true; else if (mapFile.equalsIgnoreCase("false")) this.mappedFile = false; else Constants.message ("jsp.warning.mappedFile", Log.WARNING); } String senderr = config.getInitParameter("sendErrToClient"); if (senderr != null) { if (senderr.equalsIgnoreCase("true")) this.sendErrorToClient = true; else if (senderr.equalsIgnoreCase("false")) this.sendErrorToClient = false; else Constants.message ("jsp.warning.sendErrToClient", Log.WARNING); } String debugInfo = config.getInitParameter("classdebuginfo"); if (debugInfo != null) { if (debugInfo.equalsIgnoreCase("true")) this.classDebugInfo = true; else if (debugInfo.equalsIgnoreCase("false")) this.classDebugInfo = false; else Constants.message ("jsp.warning.classDebugInfo", Log.WARNING); } String ieClassId = config.getInitParameter("ieClassId"); if (ieClassId != null) this.ieClassId = ieClassId; String classpath = config.getInitParameter("classpath"); if (classpath != null) this.classpath = classpath; String dir = config.getInitParameter("scratchdir"); if (dir != null) scratchDir = new File(dir); else { // First we try the Servlet 2.2 javax.servlet.context.tempdir property scratchDir = (File) context.getAttribute(Constants.TMP_DIR); if (scratchDir == null) { // Not running in a Servlet 2.2 container. // Try to get the JDK 1.2 java.io.tmpdir property dir = System.getProperty("java.io.tmpdir"); if (dir != null) scratchDir = new File(dir); } } // Get the ProtectionDomain for this Context in case // we are using a SecurityManager protectionDomain = context.getAttribute(Constants.ATTRIB_JSP_ProtectionDomain); if (this.scratchDir == null) { Constants.message("jsp.error.no.scratch.dir", Log.FATAL); return; } if (!(scratchDir.exists() && scratchDir.canRead() && scratchDir.canWrite() && scratchDir.isDirectory())) Constants.message("jsp.error.bad.scratch.dir", new Object[] { scratchDir.getAbsolutePath() }, Log.FATAL); String jspCompilerPath = config.getInitParameter("jspCompilerPath"); if (jspCompilerPath != null) { if (new File(jspCompilerPath).exists()) { this.jspCompilerPath = jspCompilerPath; } else { Constants.message("jsp.warning.compiler.path.notfound", new Object[] { jspCompilerPath }, Log.FATAL); } } String jspCompilerPlugin = config.getInitParameter("jspCompilerPlugin"); if (jspCompilerPlugin != null) { try { this.jspCompilerPlugin = Class.forName(jspCompilerPlugin); } catch (ClassNotFoundException cnfe) { Constants.message("jsp.warning.compiler.class.notfound", new Object[] { jspCompilerPlugin }, Log.FATAL); } } this.javaEncoding = config.getInitParameter("javaEncoding"); } } 1.1 jakarta-tomcat-jasper/jasper34/liaison/org/apache/jasper34/servlet/JasperLoader.java Index: JasperLoader.java =================================================================== /* * ==================================================================== * * The Apache Software License, Version 1.1 * * Copyright (c) 1999 The Apache Software Foundation. All rights * reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The end-user documentation included with the redistribution, if * any, must include the following acknowlegement: * "This product includes software developed by the * Apache Software Foundation (http://www.apache.org/)." * Alternately, this acknowlegement may appear in the software itself, * if and wherever such third-party acknowlegements normally appear. * * 4. The names "The Jakarta Project", "Tomcat", and "Apache Software * Foundation" must not be used to endorse or promote products derived * from this software without prior written permission. For written * permission, please contact [EMAIL PROTECTED] * * 5. Products derived from this software may not be called "Apache" * nor may "Apache" appear in their names without prior written * permission of the Apache Group. * * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE * DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * ==================================================================== * * This software consists of voluntary contributions made by many * individuals on behalf of the Apache Software Foundation. For more * information on the Apache Software Foundation, please see * <http://www.apache.org/>. * */ package org.apache.jasper34.servlet; import java.io.FileInputStream; import java.io.ByteArrayOutputStream; import java.io.File; import java.io.FileNotFoundException; import java.io.InputStream; import java.io.IOException; import java.util.Hashtable; import java.util.Vector; import java.util.zip.ZipFile; import java.util.zip.ZipEntry; import java.net.URL; import java.security.*; import org.apache.jasper34.core.*; import org.apache.jasper34.runtime.*; import org.apache.jasper34.generator.*; import org.apache.tomcat.util.log.*; import javax.servlet.http.*; /** * This is a class loader that loads JSP files as though they were * Java classes. It calls the compiler to compile the JSP file into a * servlet and then loads the generated class. * * This code is quite fragile and needs careful * treatment/handling/revisiting. I know this doesn't work very well * right now for: * * (a) inner classes * (b) does not work at all for tag handlers that have inner * classes; but that is likely to change with the new JSP PR2 * spec. * * @author Anil K. Vijendran * @author Harish Prabandham */ public class JasperLoader extends JspLoader { // ClassLoader parent; // Options options; Object pd; /* * This should be factoried out */ public JasperLoader() { super(); } // public void setParentClassLoader( ClassLoader cl) // { // this.parent = cl; // } // public void setOptions( Options options) { // this.options = options; // } public void setProtectionDomain( Object pd ) { this.pd=pd; } protected synchronized Class loadClass(String name, boolean resolve) throws ClassNotFoundException { if( debug>0) log("load " + name ); // First, check if the class has already been loaded Class c = findLoadedClass(name); if (c == null) { try { if (parent != null) { if(debug>0) log("load from parent " + name ); c = parent.loadClass(name); } else { if(debug>0) log("load from system " + name ); c = findSystemClass(name); } } catch (ClassNotFoundException e) { // If still not found, then call findClass in order // to find the class. try { if(debug>0) log("local jsp loading " + name ); c = findClass(name); } catch (ClassNotFoundException ex) { throw ex; } } } if (resolve) { resolveClass(c); } return c; } public InputStream getResourceAsStream(String name) { if( debug>0) log("getResourcesAsStream()" + name ); URL url = getResource(name); try { return url != null ? url.openStream() : null; } catch (IOException e) { return null; } } public URL getResource(String name) { if( debug>0) log( "getResource() " + name ); if( parent != null ) return parent.getResource(name); return super.getResource(name); } private static final int debug=0; private void log( String s ) { System.out.println("JspLoader: " + s ); } protected Class findClass(String className) throws ClassNotFoundException { try { int beg = className.lastIndexOf(".") == -1 ? 0 : className.lastIndexOf(".")+1; int end = className.lastIndexOf("_jsp_"); if (end <= 0) { // this is a class that the JSP file depends on // (example: class in a tag library) byte[] classBytes = loadClassDataFromJar(className); if (classBytes == null) throw new ClassNotFoundException(className); return defClass(className, classBytes); } else { String fileName = null; String outputDir = options.getScratchDir().toString(); if (className.indexOf('$', end) != -1) { // this means we're loading an inner class fileName = outputDir + File.separatorChar + className.replace('.', File.separatorChar) + ".class"; } else { fileName = className.substring(beg, end) + ".class"; fileName = outputDir + File.separatorChar + fileName; } byte [] classBytes = null; /** * When using a SecurityManager and a JSP page itself triggers * another JSP due to an errorPage or from a jsp:include, * the loadClass must be performed with the Permissions of * this class using doPriviledged because the parent JSP * may not have sufficient Permissions. */ classBytes = loadClassDataFromFile(fileName); if( classBytes == null ) { throw new ClassNotFoundException(Constants.getString( "jsp.error.unable.loadclass", new Object[] {className})); } return defClass(className, classBytes); } } catch (Exception ex) { throw new ClassNotFoundException(Constants.getString( "jsp.error.unable.loadclass", new Object[] {className})); } } /** * Just a short hand for defineClass now... I suspect we might need to * make this public at some point of time. */ protected Class defClass(String className, byte[] classData) { return defineClass(className, classData, 0, classData.length); } /** * Load JSP class data from file, method may be called from * within a doPriviledged if a SecurityManager is installed. */ protected byte[] loadClassDataFromFile(String fileName) { return doLoadClassDataFromFile( fileName ); } /** * Load JSP class data from file, method may be called from * within a doPriviledged if a SecurityManager is installed. */ protected byte[] doLoadClassDataFromFile(String fileName) { byte[] classBytes = null; try { FileInputStream fin = new FileInputStream(fileName); ByteArrayOutputStream baos = new ByteArrayOutputStream(); byte buf[] = new byte[1024]; for(int i = 0; (i = fin.read(buf)) != -1; ) baos.write(buf, 0, i); fin.close(); baos.close(); classBytes = baos.toByteArray(); } catch(Exception ex) { return null; } return classBytes; } // private Vector jars = new Vector(); private byte[] loadClassDataFromJar(String className) { String entryName = className.replace('.','/')+".class"; InputStream classStream = null; //System.out.println("Loading " + className); for(int i = 0; i < jars.size(); i++) { File thisFile = new File((String) jars.elementAt(i)); try { //System.out.println(" - trying " + thisFile.getAbsolutePath()); // check if it exists... if (!thisFile.exists()) { continue; }; if (thisFile.isFile()) { ZipFile zip = new ZipFile(thisFile); ZipEntry entry = zip.getEntry(entryName); if (entry != null) { classStream = zip.getInputStream(entry); byte[] classData = getClassData(classStream); zip.close(); return classData; } else { zip.close(); } } else { // its a directory... File classFile = new File(thisFile, entryName.replace('/', File.separatorChar)); if (classFile.exists()) { classStream = new FileInputStream(classFile); byte[] classData = getClassData(classStream); classStream.close(); return classData; } } } catch (IOException ioe) { return null; } } return null; } private byte[] getClassData(InputStream istream) throws IOException { byte[] buf = new byte[1024]; ByteArrayOutputStream bout = new ByteArrayOutputStream(); int num = 0; while((num = istream.read(buf)) != -1) { bout.write(buf, 0, num); } return bout.toByteArray(); } public String toString() { Object obj = (options==null)?null: options.getScratchDir(); String s = (obj==null)?"null":obj.toString(); return "JspLoader@"+hashCode()+"( " + s + " ) / " + parent; } boolean loadJSP(JspServlet jspS, String name, String classpath, boolean isErrorPage, HttpServletRequest req, HttpServletResponse res) throws JasperException, FileNotFoundException { return jspS.doLoadJSP( name, classpath, isErrorPage, req, res ); } } 1.1 jakarta-tomcat-jasper/jasper34/liaison/org/apache/jasper34/servlet/JasperLoader12.java Index: JasperLoader12.java =================================================================== /* * ==================================================================== * * The Apache Software License, Version 1.1 * * Copyright (c) 1999 The Apache Software Foundation. All rights * reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The end-user documentation included with the redistribution, if * any, must include the following acknowlegement: * "This product includes software developed by the * Apache Software Foundation (http://www.apache.org/)." * Alternately, this acknowlegement may appear in the software itself, * if and wherever such third-party acknowlegements normally appear. * * 4. The names "The Jakarta Project", "Tomcat", and "Apache Software * Foundation" must not be used to endorse or promote products derived * from this software without prior written permission. For written * permission, please contact [EMAIL PROTECTED] * * 5. Products derived from this software may not be called "Apache" * nor may "Apache" appear in their names without prior written * permission of the Apache Group. * * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE * DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * ==================================================================== * * This software consists of voluntary contributions made by many * individuals on behalf of the Apache Software Foundation. For more * information on the Apache Software Foundation, please see * <http://www.apache.org/>. * */ package org.apache.jasper34.servlet; import java.io.FileInputStream; import java.io.ByteArrayOutputStream; import java.io.File; import java.io.FileNotFoundException; import java.io.InputStream; import java.io.IOException; import java.util.Hashtable; import java.util.Vector; import java.util.zip.ZipFile; import java.util.zip.ZipEntry; import java.net.URL; import java.security.*; import org.apache.jasper34.core.*; import org.apache.jasper34.runtime.*; import org.apache.jasper34.generator.*; import org.apache.tomcat.util.log.*; import javax.servlet.http.*; /** * 1.2 version of the JspLoader * * @author Anil K. Vijendran * @author Harish Prabandham * @author Costin Manolache */ public class JasperLoader12 extends JasperLoader { JasperLoader12() { super(); } /** */ protected Class defClass(String className, byte[] classData) { // If a SecurityManager is being used, set the ProtectionDomain // for this clas when it is defined. // System.out.println("JspLoader12: " + className + " " + // ((ProtectionDomain)pd).getCodeSource() ); if( pd != null ) { return defineClass(className, classData, 0, classData.length, (ProtectionDomain)pd); } return defineClass(className, classData, 0, classData.length); } protected byte[] loadClassDataFromFile( String fileName ) { /** * When using a SecurityManager and a JSP page itself triggers * another JSP due to an errorPage or from a jsp:include, * the loadClass must be performed with the Permissions of * this class using doPriviledged because the parent JSP * may not have sufficient Permissions. */ if( System.getSecurityManager() != null ) { class doInit implements PrivilegedAction { private String fileName; public doInit(String file) { fileName = file; } public Object run() { return doLoadClassDataFromFile(fileName); } } doInit di = new doInit(fileName); return (byte [])AccessController.doPrivileged(di); } else { return doLoadClassDataFromFile( fileName ); } } // Hack - we want to keep JDK1.2 dependencies in fewer places, // and same for doPriviledged. boolean loadJSP(JspServlet jspS, String name, String classpath, boolean isErrorPage, HttpServletRequest req, HttpServletResponse res) throws JasperException, FileNotFoundException { if( System.getSecurityManager() == null ) { return jspS.doLoadJSP( name, classpath, isErrorPage, req, res ); } final JspServlet jspServlet=jspS; final String nameF=name; final String classpathF=classpath; final boolean isErrorPageF=isErrorPage; final HttpServletRequest reqF=req; final HttpServletResponse resF=res; try { Boolean b = (Boolean)AccessController.doPrivileged(new PrivilegedExceptionAction() { public Object run() throws Exception { return new Boolean(jspServlet.doLoadJSP( nameF, classpathF, isErrorPageF, reqF, resF )); } }); return b.booleanValue(); } catch( Exception ex ) { if( ex instanceof PrivilegedActionException ) ex=((PrivilegedActionException)ex).getException(); if( ex instanceof JasperException ) throw (JasperException)ex; if( ex instanceof FileNotFoundException ) throw (FileNotFoundException) ex; throw new JasperException( ex ); } } } 1.1 jakarta-tomcat-jasper/jasper34/liaison/org/apache/jasper34/servlet/JspEngineContext.java Index: JspEngineContext.java =================================================================== /* * * ==================================================================== * * The Apache Software License, Version 1.1 * * Copyright (c) 1999 The Apache Software Foundation. All rights * reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The end-user documentation included with the redistribution, if * any, must include the following acknowlegement: * "This product includes software developed by the * Apache Software Foundation (http://www.apache.org/)." * Alternately, this acknowlegement may appear in the software itself, * if and wherever such third-party acknowlegements normally appear. * * 4. The names "The Jakarta Project", "Tomcat", and "Apache Software * Foundation" must not be used to endorse or promote products derived * from this software without prior written permission. For written * permission, please contact [EMAIL PROTECTED] * * 5. Products derived from this software may not be called "Apache" * nor may "Apache" appear in their names without prior written * permission of the Apache Group. * * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE * DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * ==================================================================== * * This software consists of voluntary contributions made by many * individuals on behalf of the Apache Software Foundation. For more * information on the Apache Software Foundation, please see * <http://www.apache.org/>. * */ package org.apache.jasper34.servlet; import javax.servlet.ServletContext; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import java.io.IOException; import org.apache.jasper34.generator.*; import org.apache.jasper34.generator.Compiler; import org.apache.jasper34.core.*; import org.apache.jasper34.runtime.*; import org.apache.tomcat.util.log.*; /** * A place holder for various things that are used through out the JSP * engine. This is a per-request/per-context data structure. Some of * the instance variables are set at different points. * * JspLoader creates this object and passes this off to the "compiler" * subsystem, which then initializes the rest of the variables. * * @author Anil K. Vijendran * @author Harish Prabandham */ public class JspEngineContext implements JspCompilationContext { JspReader reader; ServletWriter writer; ServletContext context; JasperLoader loader; String classpath; // for compiling JSPs. boolean isErrPage; String jspFile; String servletClassName; String servletPackageName; String servletJavaFileName; String contentType; Options options; HttpServletRequest req; HttpServletResponse res; public JspEngineContext(JasperLoader loader, String classpath, ServletContext context, String jspFile, boolean isErrPage, Options options, HttpServletRequest req, HttpServletResponse res) { this.loader = loader; this.classpath = classpath; this.context = context; this.jspFile = jspFile; this.isErrPage = isErrPage; this.options = options; this.req = req; this.res = res; } /** * Get the http request we are servicing now... */ public HttpServletRequest getRequest() { return req; } /** * Get the http response we are using now... */ public HttpServletResponse getResponse() { return res; } /** * The classpath that is passed off to the Java compiler. */ public String getClassPath() { return loader.getClassPath() + classpath; } /** * Get the input reader for the JSP text. */ public JspReader getReader() { return reader; } /** * Where is the servlet being generated? */ public ServletWriter getWriter() { return writer; } /** * Get the ServletContext for the JSP we're processing now. */ public ServletContext getServletContext() { return context; } /** * What class loader to use for loading classes while compiling * this JSP? I don't think this is used right now -- akv. */ public ClassLoader getClassLoader() { return loader; } public void addJar( String jar ) throws IOException { loader.addJar( jar ); } /** * Are we processing something that has been declared as an * errorpage? */ public boolean isErrorPage() { return isErrPage; } /** * What is the scratch directory we are generating code into? * FIXME: In some places this is called scratchDir and in some * other places it is called outputDir. */ public String getOutputDir() { return options.getScratchDir().toString(); } /** * Path of the JSP URI. Note that this is not a file name. This is * the context rooted URI of the JSP file. */ public String getJspFile() { return jspFile; } /** * Just the class name (does not include package name) of the * generated class. */ public String getServletClassName() { return servletClassName; } /** * The package name into which the servlet class is generated. */ public String getServletPackageName() { return servletPackageName; } /** * Utility method to get the full class name from the package and * class name. */ public final String getFullClassName() { if (servletPackageName == null) return servletClassName; return servletPackageName + "." + servletClassName; } /** * Full path name of the Java file into which the servlet is being * generated. */ public String getServletJavaFileName() { return servletJavaFileName; } /** * Are we keeping generated code around? */ public boolean keepGenerated() { return options.getKeepGenerated(); } /** * What's the content type of this JSP? Content type includes * content type and encoding. */ public String getContentType() { return contentType; } /** * Get hold of the Options object for this context. */ public Options getOptions() { return options; } public void setContentType(String contentType) { this.contentType = contentType; } public void setReader(JspReader reader) { this.reader = reader; } public void setWriter(ServletWriter writer) { this.writer = writer; } public void setServletClassName(String servletClassName) { this.servletClassName = servletClassName; } public void setServletPackageName(String servletPackageName) { this.servletPackageName = servletPackageName; } public void setServletJavaFileName(String servletJavaFileName) { this.servletJavaFileName = servletJavaFileName; } public void setErrorPage(boolean isErrPage) { this.isErrPage = isErrPage; } /** * Create a "Compiler" object based on some init param data. If * jspCompilerPlugin is not specified or is not available, the * SunJavaCompiler is used. */ public Compiler createCompiler() throws JasperException { String compilerPath = options.getJspCompilerPath(); Class jspCompilerPlugin = options.getJspCompilerPlugin(); JavaCompiler javac; if (jspCompilerPlugin != null) { try { javac = (JavaCompiler) jspCompilerPlugin.newInstance(); } catch (Exception ex) { Constants.message("jsp.warning.compiler.class.cantcreate", new Object[] { jspCompilerPlugin, ex }, Log.FATAL); javac = new SunJavaCompiler(); } } else { javac = new SunJavaCompiler(); } if (compilerPath != null) javac.setCompilerPath(compilerPath); Compiler jspCompiler = new JspCompiler(this); jspCompiler.setJavaCompiler(javac); return jspCompiler; } /** * Get the full value of a URI relative to this compilations context */ public String resolveRelativeUri(String uri) { if (uri.charAt(0) == '/') { return uri; } else { String actURI = req.getServletPath(); String baseURI = actURI.substring(0, actURI.lastIndexOf('/')); return baseURI + '/' + uri; } } /** * Gets a resource as a stream, relative to the meanings of this * context's implementation. *@returns a null if the resource cannot be found or represented * as an InputStream. */ public java.io.InputStream getResourceAsStream(String res) { return context.getResourceAsStream(res); } /** * Gets the actual path of a URI relative to the context of * the compilation. */ public String getRealPath(String path) { if (context != null) { return context.getRealPath(path); } else { return path; } } } 1.1 jakarta-tomcat-jasper/jasper34/liaison/org/apache/jasper34/servlet/JspLoader.java Index: JspLoader.java =================================================================== /* * ==================================================================== * * The Apache Software License, Version 1.1 * * Copyright (c) 1999 The Apache Software Foundation. All rights * reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The end-user documentation included with the redistribution, if * any, must include the following acknowlegement: * "This product includes software developed by the * Apache Software Foundation (http://www.apache.org/)." * Alternately, this acknowlegement may appear in the software itself, * if and wherever such third-party acknowlegements normally appear. * * 4. The names "The Jakarta Project", "Tomcat", and "Apache Software * Foundation" must not be used to endorse or promote products derived * from this software without prior written permission. For written * permission, please contact [EMAIL PROTECTED] * * 5. Products derived from this software may not be called "Apache" * nor may "Apache" appear in their names without prior written * permission of the Apache Group. * * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE * DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * ==================================================================== * * This software consists of voluntary contributions made by many * individuals on behalf of the Apache Software Foundation. For more * information on the Apache Software Foundation, please see * <http://www.apache.org/>. * */ package org.apache.jasper34.servlet; import java.io.FileInputStream; import java.io.ByteArrayOutputStream; import java.io.File; import java.io.FileNotFoundException; import java.io.InputStream; import java.io.IOException; import java.util.Hashtable; import java.util.Vector; import java.util.zip.ZipFile; import java.util.zip.ZipEntry; import java.net.URL; import java.security.*; import org.apache.jasper34.core.*; import org.apache.jasper34.runtime.*; import org.apache.tomcat.util.log.*; import javax.servlet.http.*; /** * Jsp compiler and runtime depends on special features from the * ClassLoader. * * It has to allow run-time addition of class paths and provide * access to the class path. * * The loader is also responsible for detecting changes and reloading. * * @author Anil K. Vijendran * @author Harish Prabandham * @author Costin Manolache */ public abstract class JspLoader extends ClassLoader { protected ClassLoader parent; protected Options options; // Object pd; /* * This should be factoried out */ protected JspLoader() { super(); } public void setParentClassLoader( ClassLoader cl) { this.parent = cl; } // The only thing we use is getScratchDir ! public void setOptions( Options options) { this.options = options; } protected Vector jars = new Vector(); public void addJar(String jarFileName) throws IOException { if (!jars.contains(jarFileName)) { Constants.message("jsp.message.adding_jar", new Object[] { jarFileName }, Log.INFORMATION); jars.addElement(jarFileName); } } public String getClassPath() { StringBuffer cpath = new StringBuffer(); String sep = System.getProperty("path.separator"); for(int i = 0; i < jars.size(); i++) { cpath.append((String)jars.elementAt(i)+sep); } return cpath.toString(); } } 1.1 jakarta-tomcat-jasper/jasper34/liaison/org/apache/jasper34/servlet/JspServlet.java Index: JspServlet.java =================================================================== /* * The Apache Software License, Version 1.1 * * Copyright (c) 1999 The Apache Software Foundation. All rights * reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The end-user documentation included with the redistribution, if * any, must include the following acknowlegement: * "This product includes software developed by the * Apache Software Foundation (http://www.apache.org/)." * Alternately, this acknowlegement may appear in the software itself, * if and wherever such third-party acknowlegements normally appear. * * 4. The names "The Jakarta Project", "Tomcat", and "Apache Software * Foundation" must not be used to endorse or promote products derived * from this software without prior written permission. For written * permission, please contact [EMAIL PROTECTED] * * 5. Products derived from this software may not be called "Apache" * nor may "Apache" appear in their names without prior written * permission of the Apache Group. * * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE * DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * ==================================================================== * * This software consists of voluntary contributions made by many * individuals on behalf of the Apache Software Foundation. For more * information on the Apache Software Foundation, please see * <http://www.apache.org/>. * */ package org.apache.jasper34.servlet; import javax.servlet.Servlet; import javax.servlet.ServletContext; import javax.servlet.ServletConfig; import javax.servlet.ServletException; import javax.servlet.SingleThreadModel; import javax.servlet.http.HttpServlet; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import javax.servlet.jsp.HttpJspPage; import javax.servlet.jsp.JspFactory; import java.util.Hashtable; import java.util.Enumeration; import java.io.File; import java.io.PrintWriter; import java.io.IOException; import java.io.FileNotFoundException; import org.apache.jasper34.runtime.*; import org.apache.jasper34.core.*; import org.apache.jasper34.generator.*; import org.apache.jasper34.generator.Compiler; import org.apache.tomcat.util.log.Log; /** * The JSP engine (a.k.a Jasper)! * * @author Anil K. Vijendran * @author Harish Prabandham */ public class JspServlet extends HttpServlet { Log loghelper = Log.getLog("JASPER_LOG", "JspServlet"); class JspServletWrapper { Servlet theServlet; String jspUri; boolean isErrorPage; // ServletWrapper will set this Class servletClass; JspServletWrapper(String jspUri, boolean isErrorPage) { this.jspUri = jspUri; this.isErrorPage = isErrorPage; this.theServlet = null; } private void load() throws JasperException, ServletException { try { // Class servletClass = (Class) loadedJSPs.get(jspUri); // This is to maintain the original protocol. destroy(); theServlet = (Servlet) servletClass.newInstance(); } catch (Exception ex) { throw new JasperException(ex); } theServlet.init(JspServlet.this.config); if (theServlet instanceof HttpJspBase) { HttpJspBase h = (HttpJspBase) theServlet; h.setClassLoader(JspServlet.this.parentClassLoader); } } private void loadIfNecessary(HttpServletRequest req, HttpServletResponse res) throws JasperException, ServletException, FileNotFoundException { // First try context attribute; if that fails then use the // classpath init parameter. // Should I try to concatenate them if both are non-null? String cp = (String) context.getAttribute(Constants.SERVLET_CLASSPATH); String accordingto; if (cp == null || cp.equals("")) { accordingto = "according to the init parameter"; cp = options.getClassPath(); } else accordingto = "according to the Servlet Engine"; Constants.message("jsp.message.cp_is", new Object[] { accordingto, cp == null ? "" : cp }, Log.INFORMATION); if (loadJSP(jspUri, cp, isErrorPage, req, res) || theServlet == null) { load(); } } public void service(HttpServletRequest request, HttpServletResponse response, boolean precompile) throws ServletException, IOException, FileNotFoundException { try { loadIfNecessary(request, response); // If a page is to only to be precompiled return. if (precompile) return; if (theServlet instanceof SingleThreadModel) { // sync on the wrapper so that the freshness // of the page is determined right before servicing synchronized (this) { theServlet.service(request, response); } } else { theServlet.service(request, response); } } catch (FileNotFoundException ex) { try { if (insecure_TMI) { response.sendError(HttpServletResponse.SC_NOT_FOUND, Constants.getString ("jsp.error.file.not.found.TMI", new Object[] { ex.getMessage() })); } else { response.sendError(HttpServletResponse.SC_NOT_FOUND, Constants.getString ("jsp.error.file.not.found", new Object[] { // Too Much Information -- ex.getMessage() })); } } catch (IllegalStateException ise) { // logs are presumed to be secure, thus the TMI info can be logged Constants.jasperLog.log(Constants.getString ("jsp.error.file.not.found.TMI", new Object[] { ex.getMessage() }), ex, Log.ERROR); // rethrow FileNotFoundException so someone higher up can handle if (insecure_TMI) throw ex; else throw new FileNotFoundException(Constants.getString ("jsp.error.file.not.found", new Object[] { // Too Much Information -- ex.getMessage() })); } return; } } public void destroy() { if (theServlet != null) theServlet.destroy(); } } protected ServletContext context = null; protected Hashtable jsps = new Hashtable(); // protected Hashtable loadedJSPs = new Hashtable(); protected ServletConfig config; protected JasperLoader loader; protected Options options; protected ClassLoader parentClassLoader; protected ServletEngine engine; protected String serverInfo; /** Set to true to provide Too Much Information on errors */ private final boolean insecure_TMI = false; static boolean firstTime = true; static boolean jdk12=false; static { try { Class.forName( "java.security.PrivilegedAction" ); jdk12=true; } catch(Throwable ex ) { } } public void init(ServletConfig config) throws ServletException { super.init(config); this.config = config; this.context = config.getServletContext(); this.serverInfo = context.getServerInfo(); options = new EmbededServletOptions(config, context); parentClassLoader = (ClassLoader) context.getAttribute(Constants.SERVLET_CLASS_LOADER); if (parentClassLoader == null) parentClassLoader = this.getClass().getClassLoader(); // getClass().getClassLoader() returns null in JDK 1.1.6/1.1.8 if (parentClassLoader != null) { Constants.message("jsp.message.parent_class_loader_is", new Object[] { parentClassLoader.toString() }, Log.DEBUG); } else { Constants.message("jsp.message.parent_class_loader_is", new Object[] { "<none>" }, Log.DEBUG); } // System.out.println("JspServlet: init " + config.getServletName() ); if( loader==null ) { if( jdk12 ) { try { Class ld=Class.forName("org.apache.jasper.servlet.JasperLoader12"); loader=(JasperLoader)ld.newInstance(); } catch(Throwable t ) { loghelper.log("Loading org.apache.jasper.servlet.JasperLoader12", t); } } if( loader==null ) loader = new JasperLoader(); loader.setParentClassLoader(parentClassLoader); loader.setOptions(options); Object pd=context.getAttribute("org.apache.tomcat.protection_domain"); loader.setProtectionDomain( pd ); } if (firstTime) { firstTime = false; Constants.message("jsp.message.scratch.dir.is", new Object[] { options.getScratchDir().toString() }, Log.INFORMATION ); Constants.message("jsp.message.dont.modify.servlets", Log.INFORMATION); JspFactory.setDefaultFactory(new JspFactoryImpl()); } } private void serviceJspFile(HttpServletRequest request, HttpServletResponse response, String jspUri, Throwable exception, boolean precompile) throws ServletException, IOException { boolean isErrorPage = exception != null; JspServletWrapper wrapper = (JspServletWrapper) jsps.get(jspUri); if (wrapper == null) { wrapper = new JspServletWrapper(jspUri, isErrorPage); jsps.put(jspUri, wrapper); } wrapper.service(request, response, precompile); } boolean preCompile(HttpServletRequest request) throws ServletException { boolean precompile = false; String precom = request.getParameter(Constants.PRECOMPILE); String qString = request.getQueryString(); if (precom != null) { if (precom.equals("true")) precompile = true; else if (precom.equals("false")) precompile = false; else { // This is illegal. throw new ServletException("Can't have request parameter " + Constants.PRECOMPILE + " set to " + precom); } } else if (qString != null && (qString.startsWith(Constants.PRECOMPILE) || qString.indexOf("&" + Constants.PRECOMPILE) != -1)) precompile = true; return precompile; } public void service (HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { try { String includeUri = (String) request.getAttribute(Constants.INC_SERVLET_PATH); String jspUri; if (includeUri == null) jspUri = request.getServletPath(); else jspUri = includeUri; // System.out.println("JspServletWrapper: " + includeUri + " " + // jspUri + // (String) request.getAttribute( // Constants.INC_REQUEST_URI)); boolean precompile = preCompile(request); Log jasperLog = Constants.jasperLog; if (jasperLog != null && jasperLog.getLevel() >= Log.INFORMATION) { jasperLog.log("JspEngine --> "+jspUri); jasperLog.log("\t ServletPath: "+request.getServletPath()); jasperLog.log("\t PathInfo: "+request.getPathInfo()); jasperLog.log("\t RealPath: " +getServletConfig().getServletContext().getRealPath(jspUri)); jasperLog.log("\t RequestURI: "+request.getRequestURI()); jasperLog.log("\t QueryString: "+request.getQueryString()); jasperLog.log("\t Request Params: "); Enumeration e = request.getParameterNames(); while (e.hasMoreElements()) { String name = (String) e.nextElement(); jasperLog.log("\t\t "+name+" = "+request.getParameter(name)); } } serviceJspFile(request, response, jspUri, null, precompile); } catch (RuntimeException e) { throw e; } catch (ServletException e) { throw e; } catch (IOException e) { throw e; } catch (Throwable e) { throw new ServletException(e); } // It's better to throw the exception - we don't // know if we can deal with sendError ( buffer may be // commited ) // catch (Throwable t) { // unknownException(response, t); // } } public void destroy() { if (Constants.jasperLog != null) Constants.jasperLog.log("JspServlet.destroy()", Log.INFORMATION); Enumeration servlets = jsps.elements(); while (servlets.hasMoreElements()) ((JspServletWrapper) servlets.nextElement()).destroy(); } /* Check if we need to reload a JSP page. * * Side-effect: re-compile the JSP page. * * @param classpath explicitly set the JSP compilation path. * @return true if JSP files is newer */ boolean loadJSP(String jspUri, String classpath, boolean isErrorPage, HttpServletRequest req, HttpServletResponse res) throws JasperException, FileNotFoundException { // Loader knows how to set the right priviledges, and call // doLoadeJsp return loader.loadJSP( this,jspUri, classpath, isErrorPage, req, res ); } /* Check if we need to reload a JSP page. * * Side-effect: re-compile the JSP page. * * @param classpath explicitly set the JSP compilation path. * @return true if JSP files is newer */ protected boolean doLoadJSP(String jspUri, String classpath, boolean isErrorPage, HttpServletRequest req, HttpServletResponse res) throws JasperException, FileNotFoundException { JspServletWrapper jsw=(JspServletWrapper) jsps.get(jspUri); if( jsw==null ) { throw new JasperException("Can't happen - JspServletWrapper=null"); } // Class jspClass = (Class) loadedJSPs.get(jspUri); boolean firstTime = jsw.servletClass == null; JspCompilationContext ctxt = new JspEngineContext(loader, classpath, context, jspUri, isErrorPage, options, req, res); boolean outDated = false; Compiler compiler = ctxt.createCompiler(); try { outDated = compiler.isOutDated(); if ( (jsw.servletClass == null) || outDated ) { synchronized ( this ) { if ((jsw.servletClass == null) || (compiler.isOutDated() )) { outDated = compiler.compile(); } } } } catch (FileNotFoundException ex) { compiler.removeGeneratedFiles(); throw ex; } catch (JasperException ex) { throw ex; } catch (Exception ex) { throw new JasperException(Constants.getString("jsp.error.unable.compile"), ex); } // Reload only if it's outdated if((jsw.servletClass == null) || outDated) { try { if( null ==ctxt.getServletClassName() ) { compiler.computeServletClassName(); } jsw.servletClass = loader.loadClass(ctxt.getFullClassName()); //loadClass(ctxt.getFullClassName(), true); } catch (ClassNotFoundException cex) { throw new JasperException(Constants.getString("jsp.error.unable.load"), cex); } // loadedJSPs.put(jspUri, jspClass); } return outDated; } /** * Determines whether the current JSP class is older than the JSP file * from whence it came */ public boolean isOutDated(File jsp, JspCompilationContext ctxt, Mangler mangler ) { File jspReal = null; boolean outDated; jspReal = new File(ctxt.getRealPath(jsp.getPath())); File classFile = new File(mangler.getClassFileName()); if (classFile.exists()) { outDated = classFile.lastModified() < jspReal.lastModified(); } else { outDated = true; } return outDated; } } 1.1 jakarta-tomcat-jasper/jasper34/liaison/org/apache/jasper34/servlet/ServletEngine.java Index: ServletEngine.java =================================================================== /* * ==================================================================== * * The Apache Software License, Version 1.1 * * Copyright (c) 1999 The Apache Software Foundation. All rights * reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The end-user documentation included with the redistribution, if * any, must include the following acknowlegement: * "This product includes software developed by the * Apache Software Foundation (http://www.apache.org/)." * Alternately, this acknowlegement may appear in the software itself, * if and wherever such third-party acknowlegements normally appear. * * 4. The names "The Jakarta Project", "Tomcat", and "Apache Software * Foundation" must not be used to endorse or promote products derived * from this software without prior written permission. For written * permission, please contact [EMAIL PROTECTED] * * 5. Products derived from this software may not be called "Apache" * nor may "Apache" appear in their names without prior written * permission of the Apache Group. * * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE * DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * ==================================================================== * * This software consists of voluntary contributions made by many * individuals on behalf of the Apache Software Foundation. For more * information on the Apache Software Foundation, please see * <http://www.apache.org/>. * */ package org.apache.jasper34.servlet; import java.io.File; import javax.servlet.ServletContext; /** * Simple class to factor out servlet runner dependencies from the JSP * engine. There's a few motivations here: * * (a) ability for the JSP engine to be able to run on multiple * servlet engines - 2.1 and 2.2 * (b) ability for the JSP engine to take advantage of specific * servlet engines; this is crucial from a J2EE point of * view. * * @author Anil K. Vijendran * @author Harish Prabandham */ public class ServletEngine { static ServletEngine tomcat; static ServletEngine deflt; /** * Get a specific ServletEngine instance for the particular servlet runner * we are running on. */ static ServletEngine getServletEngine(String serverInfo) { if (serverInfo.startsWith("Tomcat Web Server")) { if (tomcat == null) { try { tomcat = (ServletEngine) Class.forName("org.apache.jasper.runtime.TomcatServletEngine").newInstance(); } catch (Exception ex) { return null; } } return tomcat; } else { if (deflt == null) deflt = new ServletEngine(); return deflt; } } /** * Get the class loader for this ServletContext object. */ public ClassLoader getClassLoader(ServletContext ctx) { return null; } } 1.1 jakarta-tomcat-jasper/jasper34/liaison/org/apache/jasper34/servlet/TomcatServletEngine.java Index: TomcatServletEngine.java =================================================================== /* * ==================================================================== * * The Apache Software License, Version 1.1 * * Copyright (c) 1999 The Apache Software Foundation. All rights * reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The end-user documentation included with the redistribution, if * any, must include the following acknowlegement: * "This product includes software developed by the * Apache Software Foundation (http://www.apache.org/)." * Alternately, this acknowlegement may appear in the software itself, * if and wherever such third-party acknowlegements normally appear. * * 4. The names "The Jakarta Project", "Tomcat", and "Apache Software * Foundation" must not be used to endorse or promote products derived * from this software without prior written permission. For written * permission, please contact [EMAIL PROTECTED] * * 5. Products derived from this software may not be called "Apache" * nor may "Apache" appear in their names without prior written * permission of the Apache Group. * * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE * DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * ==================================================================== * * This software consists of voluntary contributions made by many * individuals on behalf of the Apache Software Foundation. For more * information on the Apache Software Foundation, please see * <http://www.apache.org/>. * */ package org.apache.jasper34.servlet; import java.io.File; import javax.servlet.ServletContext; /** * Implementation of Servlet Engine that is used when the JSP engine * is running with Tomcat. * * @author Anil K. Vijendran */ public class TomcatServletEngine extends ServletEngine { public ClassLoader getClassLoader(ServletContext ctx) { return null;// XXX (ClassLoader)((ServletContextFacade) ctx).getRealContext().getLoader(); } }