You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@tomcat.apache.org by ma...@apache.org on 2013/11/14 17:28:51 UTC
svn commit: r1541962 - in /tomcat/trunk/java/org/apache/jasper: JspC.java
compiler/TldCache.java servlet/JasperInitializer.java
Author: markt
Date: Thu Nov 14 16:28:51 2013
New Revision: 1541962
URL: http://svn.apache.org/r1541962
Log:
Check the parsed TLD cache entries are not stale.
Modified:
tomcat/trunk/java/org/apache/jasper/JspC.java
tomcat/trunk/java/org/apache/jasper/compiler/TldCache.java
tomcat/trunk/java/org/apache/jasper/servlet/JasperInitializer.java
Modified: tomcat/trunk/java/org/apache/jasper/JspC.java
URL: http://svn.apache.org/viewvc/tomcat/trunk/java/org/apache/jasper/JspC.java?rev=1541962&r1=1541961&r2=1541962&view=diff
==============================================================================
--- tomcat/trunk/java/org/apache/jasper/JspC.java (original)
+++ tomcat/trunk/java/org/apache/jasper/JspC.java Thu Nov 14 16:28:51 2013
@@ -847,6 +847,10 @@ public class JspC extends Task implement
org.apache.jasper.xmlparser.ParserUtils.validating=b;
}
+ public boolean isValidateXml() {
+ return validateXml;
+ }
+
public void setListErrors( boolean b ) {
listErrors = b;
}
@@ -1432,7 +1436,7 @@ public class JspC extends Task implement
} catch (SAXException e) {
throw new JasperException(e);
}
- tldCache = new TldCache(scanner.getUriTldResourcePathMap(),
+ tldCache = new TldCache(context, scanner.getUriTldResourcePathMap(),
scanner.getTldResourcePathTaglibXmlMap());
context.setAttribute(TldCache.SERVLET_CONTEXT_ATTRIBUTE_NAME, tldCache);
rctxt = new JspRuntimeContext(context, this);
Modified: tomcat/trunk/java/org/apache/jasper/compiler/TldCache.java
URL: http://svn.apache.org/viewvc/tomcat/trunk/java/org/apache/jasper/compiler/TldCache.java?rev=1541962&r1=1541961&r2=1541962&view=diff
==============================================================================
--- tomcat/trunk/java/org/apache/jasper/compiler/TldCache.java (original)
+++ tomcat/trunk/java/org/apache/jasper/compiler/TldCache.java Thu Nov 14 16:28:51 2013
@@ -16,13 +16,22 @@
*/
package org.apache.jasper.compiler;
+import java.io.IOException;
+import java.net.URL;
+import java.net.URLConnection;
import java.util.HashMap;
import java.util.Map;
+import java.util.Map.Entry;
import javax.servlet.ServletContext;
+import org.apache.jasper.JasperException;
+import org.apache.jasper.servlet.JasperInitializer;
import org.apache.tomcat.util.descriptor.tld.TaglibXml;
+import org.apache.tomcat.util.descriptor.tld.TldParser;
import org.apache.tomcat.util.descriptor.tld.TldResourcePath;
+import org.apache.tomcat.util.scan.Jar;
+import org.xml.sax.SAXException;
/**
* This class caches parsed instances of TLD files to remove the need for the
@@ -35,8 +44,11 @@ public class TldCache {
public static final String SERVLET_CONTEXT_ATTRIBUTE_NAME =
TldCache.class.getName();
- private final Map<String, TldResourcePath> uriTldResourcePathMap = new HashMap<>();
- private final Map<TldResourcePath, TaglibXml> tldResourcePathTaglibXmlMap = new HashMap<>();
+ private final ServletContext servletContext;
+ private final Map<String,TldResourcePath> uriTldResourcePathMap = new HashMap<>();
+ private final Map<TldResourcePath,TaglibXmlCacheEntry> tldResourcePathTaglibXmlMap =
+ new HashMap<>();
+ private final TldParser tldParser;
public static TldCache getInstance(ServletContext servletContext) {
@@ -48,10 +60,21 @@ public class TldCache {
}
- public TldCache(Map<String, TldResourcePath> uriTldResourcePathMap,
+ public TldCache(ServletContext servletContext,
+ Map<String, TldResourcePath> uriTldResourcePathMap,
Map<TldResourcePath, TaglibXml> tldResourcePathTaglibXmlMap) {
+ this.servletContext = servletContext;
this.uriTldResourcePathMap.putAll(uriTldResourcePathMap);
- this.tldResourcePathTaglibXmlMap.putAll(tldResourcePathTaglibXmlMap);
+ for (Entry<TldResourcePath, TaglibXml> entry : tldResourcePathTaglibXmlMap.entrySet()) {
+ TldResourcePath tldResourcePath = entry.getKey();
+ long lastModified[] = getLastModified(tldResourcePath);
+ TaglibXmlCacheEntry cacheEntry = new TaglibXmlCacheEntry(
+ entry.getValue(), lastModified[0], lastModified[1]);
+ this.tldResourcePathTaglibXmlMap.put(tldResourcePath, cacheEntry);
+ }
+ boolean validate = Boolean.parseBoolean(
+ servletContext.getInitParameter(JasperInitializer.VALIDATE));
+ tldParser = new TldParser(true, validate);
}
@@ -60,7 +83,83 @@ public class TldCache {
}
- public TaglibXml getTaglibXml(TldResourcePath tldResourcePath) {
- return tldResourcePathTaglibXmlMap.get(tldResourcePath);
+ public TaglibXml getTaglibXml(TldResourcePath tldResourcePath) throws JasperException {
+ TaglibXmlCacheEntry cacheEntry = tldResourcePathTaglibXmlMap.get(tldResourcePath);
+ long lastModified[] = getLastModified(tldResourcePath);
+ if (lastModified[0] != cacheEntry.getWebAppPathLastModified() ||
+ lastModified[1] != cacheEntry.getEntryLastModified()) {
+ synchronized (cacheEntry) {
+ if (lastModified[0] != cacheEntry.getWebAppPathLastModified() ||
+ lastModified[1] != cacheEntry.getEntryLastModified()) {
+ // Re-parse TLD
+ TaglibXml updatedTaglibXml;
+ try {
+ updatedTaglibXml = tldParser.parse(tldResourcePath);
+ } catch (IOException | SAXException e) {
+ throw new JasperException(e);
+ }
+ cacheEntry.setTaglibXml(updatedTaglibXml);
+ cacheEntry.setWebAppPathLastModified(lastModified[0]);
+ cacheEntry.setEntryLastModified(lastModified[1]);
+ }
+ }
+ }
+ return cacheEntry.getTaglibXml();
+ }
+
+
+ private long[] getLastModified(TldResourcePath tldResourcePath) {
+ long[] result = new long[2];
+ result[0] = -1;
+ result[1] = -1;
+ try {
+ URL url = servletContext.getResource(tldResourcePath.getWebappPath());
+ URLConnection conn = url.openConnection();
+ result[0] = conn.getLastModified();
+ Jar jar = tldResourcePath.getJar();
+ if (jar != null) {
+ result[1] = jar.getLastModified(tldResourcePath.getEntryName());
+ }
+ } catch (IOException e) {
+ // Ignore (shouldn't happen)
+ }
+ return result;
+ }
+
+ private static class TaglibXmlCacheEntry {
+ private volatile TaglibXml taglibXml;
+ private volatile long webAppPathLastModified;
+ private volatile long entryLastModified;
+
+ public TaglibXmlCacheEntry(TaglibXml taglibXml, long webAppPathLastModified,
+ long entryLastModified) {
+ this.taglibXml = taglibXml;
+ this.webAppPathLastModified = webAppPathLastModified;
+ this.entryLastModified = entryLastModified;
+ }
+
+ public TaglibXml getTaglibXml() {
+ return taglibXml;
+ }
+
+ public void setTaglibXml(TaglibXml taglibXml) {
+ this.taglibXml = taglibXml;
+ }
+
+ public long getWebAppPathLastModified() {
+ return webAppPathLastModified;
+ }
+
+ public void setWebAppPathLastModified(long webAppPathLastModified) {
+ this.webAppPathLastModified = webAppPathLastModified;
+ }
+
+ public long getEntryLastModified() {
+ return entryLastModified;
+ }
+
+ public void setEntryLastModified(long entryLastModified) {
+ this.entryLastModified = entryLastModified;
+ }
}
}
Modified: tomcat/trunk/java/org/apache/jasper/servlet/JasperInitializer.java
URL: http://svn.apache.org/viewvc/tomcat/trunk/java/org/apache/jasper/servlet/JasperInitializer.java?rev=1541962&r1=1541961&r2=1541962&view=diff
==============================================================================
--- tomcat/trunk/java/org/apache/jasper/servlet/JasperInitializer.java (original)
+++ tomcat/trunk/java/org/apache/jasper/servlet/JasperInitializer.java Thu Nov 14 16:28:51 2013
@@ -63,7 +63,7 @@ public class JasperInitializer implement
}
context.setAttribute(TldCache.SERVLET_CONTEXT_ATTRIBUTE_NAME,
- new TldCache(scanner.getUriTldResourcePathMap(),
+ new TldCache(context, scanner.getUriTldResourcePathMap(),
scanner.getTldResourcePathTaglibXmlMap()));
}
}
---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@tomcat.apache.org
For additional commands, e-mail: dev-help@tomcat.apache.org