This commit is contained in:
J. Duke 2017-07-05 18:34:39 +02:00
commit b390a90275
187 changed files with 22303 additions and 3839 deletions

View file

@ -191,3 +191,4 @@ b772de306dc24c17f7bd1398531ddeb58723b804 jdk8-b65
9a6ec97ec45c1a62d5233cefa91e8390e380e13a jdk8-b67
cdb401a60cea6ad5ef3f498725ed1decf8dda1ea jdk8-b68
6ee8080a6efe0639fcd00627a5e0f839bf010481 jdk8-b69
105a25ffa4a4f0af70188d4371b4a0385009b7ce jdk8-b70

View file

@ -78,7 +78,8 @@ ATTACH_PKGS = com.sun.tools.attach \
JCONSOLE_PKGS = com.sun.tools.jconsole
TREEAPI_PKGS = com.sun.source.tree \
TREEAPI_PKGS = com.sun.source.doctree \
com.sun.source.tree \
com.sun.source.util
SMARTCARDIO_PKGS = javax.smartcardio

View file

@ -191,3 +191,4 @@ d54dc53e223ed9ce7d5f4d2cd02ad9d5def3c2db jdk8-b59
394515ad2a55d4d54df990b36065505d3e7a3cbb jdk8-b67
82000531feaa7baef76b6406099e5cd88943d635 jdk8-b68
22ddcac208a8dea894a16887d04f3ca4d3c5d267 jdk8-b69
603cceb495c8133d47b26a7502d51c7d8a67d76b jdk8-b70

View file

@ -303,3 +303,4 @@ a35a72dd2e1255239d31f796f9f693e49b36bc9f hs25-b12
b6c9c0109a608eedbb6b868d260952990e3c91fe hs25-b13
cb8a4e04bc8c104de8a2f67463c7e31232bf8d68 jdk8-b69
990bbd393c239d95310ccc38094e57923bbf1d4a hs25-b14
e94068d4ff52849c8aa0786a53a59b63d1312a39 jdk8-b70

View file

@ -191,3 +191,4 @@ e6af1ad464e3d9b1154b9f9ed9a5373b97d129fc jdk8-b66
83df3493ca3cf0be077f1d0dd90119456f266f54 jdk8-b67
b854e70084214e9dcf1b37373f6e4b1a68760e03 jdk8-b68
789a855de959f7e9600e57759c6c3dbb0b24d78b jdk8-b69
6ec9edffc286c9c9ac96c9cd2050b01cb5d514a8 jdk8-b70

View file

@ -1005,7 +1005,7 @@ public class EnvironmentCheck
{
Class clazz = ObjectFactory.findProviderClass(DOM_CLASS, true);
Method method = clazz.getMethod(DOM_LEVEL3_METHOD, null);
Method method = clazz.getMethod(DOM_LEVEL3_METHOD, (Class<?>[])null);
// If we succeeded, we have loaded interfaces from a
// level 3 DOM somewhere

View file

@ -74,7 +74,7 @@ public class Version {
/** Version string.
* @deprecated getVersion() should be used instead. */
public static String fVersion = "Xerces-J 2.7.1";
public static final String fVersion = getVersion();
private static final String fImmutableVersion = "Xerces-J 2.7.1";

View file

@ -193,9 +193,12 @@ public class XMLDocumentFragmentScannerImpl
null,
};
protected static final char [] cdata = {'[','C','D','A','T','A','['};
protected static final char [] xmlDecl = {'<','?','x','m','l'};
protected static final char [] endTag = {'<','/'};
private static final char [] cdata = {'[','C','D','A','T','A','['};
private static final char [] endTag = {'<','/'};
//this variable is also used by XMLDocumentScannerImpl in the same package
static final char [] xmlDecl = {'<','?','x','m','l'};
// debugging
/** Debug scanner state. */

View file

@ -71,7 +71,7 @@ public class XMLEntityScanner implements XMLLocator {
/** Listeners which should know when load is being called */
private Vector listeners = new Vector();
public static final boolean [] VALID_NAMES = new boolean[127];
private static final boolean [] VALID_NAMES = new boolean[127];
/**
* Debug printing of buffer. This debugging flag works best when you

View file

@ -210,7 +210,7 @@ class FactoryFinder {
providerClass.getDeclaredMethod(
"newTransformerFactoryNoServiceLoader"
);
return creationMethod.invoke(null, null);
return creationMethod.invoke(null, (Object[])null);
} catch (NoSuchMethodException exc) {
return null;
} catch (Exception exc) {

View file

@ -357,7 +357,7 @@ class SchemaFactoryFinder {
providerClass.getDeclaredMethod(
"newXMLSchemaFactoryNoServiceLoader"
);
return creationMethod.invoke(null, null);
return creationMethod.invoke(null, (Object[])null);
} catch (NoSuchMethodException exc) {
return null;
} catch (Exception exc) {

View file

@ -333,7 +333,7 @@ class XPathFactoryFinder {
providerClass.getDeclaredMethod(
"newXPathFactoryNoServiceLoader"
);
return creationMethod.invoke(null, null);
return creationMethod.invoke(null, (Object[])null);
} catch (NoSuchMethodException exc) {
return null;
} catch (Exception exc) {

View file

@ -191,3 +191,4 @@ f117a3e06f78a258074674ad17601f99bcb1ce0d jdk8-b63
ce9b02a3a17edd1983201002cfa0f364e4ab7524 jdk8-b67
53fb43e4d614c92310e1fb00ec41d1960fd9facf jdk8-b68
a8012d8d7e9c5035de0bdd4887dc9f7c54008f21 jdk8-b69
a996b57e554198f4592a5f3c30f2f9f4075e545d jdk8-b70

View file

@ -366,6 +366,7 @@ TOOLS = \
com/sun/source \
com/sun/tools/classfile \
com/sun/tools/doclets \
com/sun/tools/doclint \
com/sun/tools/example/debug/expr \
com/sun/tools/example/debug/tty \
com/sun/tools/extcheck \

View file

@ -35,6 +35,7 @@ IMPORT_TOOLS_PACKAGES += \
com/sun/source \
com/sun/tools/classfile \
com/sun/tools/doclets \
com/sun/tools/doclint \
com/sun/tools/javac \
com/sun/tools/javadoc \
com/sun/tools/javah \

View file

@ -76,7 +76,8 @@ ATTACH_PKGS = com.sun.tools.attach \
JCONSOLE_PKGS = com.sun.tools.jconsole
TREEAPI_PKGS = com.sun.source.tree \
TREEAPI_PKGS = com.sunsource.doctree \
com.sun.source.tree \
com.sun.source.util
SMARTCARDIO_PKGS = javax.smartcardio

View file

@ -294,6 +294,7 @@ JAVA_JAVA_java = \
java/util/IdentityHashMap.java \
java/util/EnumMap.java \
java/util/Arrays.java \
java/util/ArraysParallelSortHelpers.java \
java/util/DualPivotQuicksort.java \
java/util/TimSort.java \
java/util/ComparableTimSort.java \
@ -322,6 +323,7 @@ JAVA_JAVA_java = \
java/util/concurrent/CopyOnWriteArrayList.java \
java/util/concurrent/CopyOnWriteArraySet.java \
java/util/concurrent/CountDownLatch.java \
java/util/concurrent/CountedCompleter.java \
java/util/concurrent/CyclicBarrier.java \
java/util/concurrent/DelayQueue.java \
java/util/concurrent/Delayed.java \

View file

@ -1,5 +1,5 @@
#
# Copyright (c) 1997, 2012, Oracle and/or its affiliates. All rights reserved.
# Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
#
# This code is free software; you can redistribute it and/or modify it
@ -23,16 +23,18 @@
# questions.
#
#
# Makefile for building all of java
#
BUILDDIR = ..
PACKAGE = jdk
PRODUCT = jdk
JAVAC_LINT_OPTIONS=-Xlint:all
include $(BUILDDIR)/common/Defs.gmk
SUBDIRS = asm
include $(BUILDDIR)/common/Subdirs.gmk
#
# Files to compile
#
AUTO_FILES_JAVA_DIRS = jdk
all build clean clobber::
$(SUBDIRS-loop)
#
# Rules
#
include $(BUILDDIR)/common/Classes.gmk

View file

@ -1,40 +0,0 @@
#
# Copyright (c) 1995, 2012, Oracle and/or its affiliates. All rights reserved.
# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
#
# This code is free software; you can redistribute it and/or modify it
# under the terms of the GNU General Public License version 2 only, as
# published by the Free Software Foundation. Oracle designates this
# particular file as subject to the "Classpath" exception as provided
# by Oracle in the LICENSE file that accompanied this code.
#
# This code is distributed in the hope that it will be useful, but WITHOUT
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
# version 2 for more details (a copy is included in the LICENSE file that
# accompanied this code).
#
# You should have received a copy of the GNU General Public License version
# 2 along with this work; if not, write to the Free Software Foundation,
# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
#
# Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
# or visit www.oracle.com if you need additional information or have any
# questions.
#
BUILDDIR = ../..
PACKAGE = jdk.internal.org.objectweb.asm
PRODUCT = jdk
JAVAC_LINT_OPTIONS=-Xlint:all
include $(BUILDDIR)/common/Defs.gmk
#
# Files to compile
#
AUTO_FILES_JAVA_DIRS = jdk/internal/org/objectweb/asm
#
# Rules
#
include $(BUILDDIR)/common/Classes.gmk

View file

@ -38,6 +38,7 @@ excludes=\
com/sun/jmx/snmp/
jtreg.tests=\
com/sun/jmx/ \
com/sun/management/ \
java/lang/management/ \
javax/management/

View file

@ -729,6 +729,7 @@ TOOLS_JAR_INCLUDES := \
com/sun/source \
com/sun/tools/classfile \
com/sun/tools/doclets \
com/sun/tools/doclint \
com/sun/tools/example/debug/expr \
com/sun/tools/example/debug/tty \
com/sun/tools/extcheck \

View file

@ -119,7 +119,9 @@ public class CEmbeddedFrame extends EmbeddedFrame {
public void handleWindowFocusEvent(boolean parentWindowActive) {
this.parentWindowActive = parentWindowActive;
if (focused) {
// ignore focus "lost" native request as it may mistakenly
// deactivate active window (see 8001161)
if (focused && parentWindowActive) {
responder.handleWindowFocusEvent(parentWindowActive, null);
}
}

View file

@ -115,6 +115,7 @@ public abstract class ClientCommunicatorAdmin {
// restarted is failed by another thread
throw ioe;
}
return;
} else {
state = RE_CONNECTING;
lock.notifyAll();
@ -195,7 +196,7 @@ public abstract class ClientCommunicatorAdmin {
if (e instanceof IOException &&
!(e instanceof InterruptedIOException)) {
try {
restart((IOException)e);
gotIOException((IOException)e);
} catch (Exception ee) {
logger.warning("Checker-run",
"Failed to check connection: "+ e);

View file

@ -51,6 +51,7 @@ import javax.management.remote.TargetedNotification;
import com.sun.jmx.remote.util.ClassLogger;
import com.sun.jmx.remote.util.EnvHelp;
import java.rmi.UnmarshalException;
public abstract class ClientNotifForwarder {
@ -594,10 +595,7 @@ public abstract class ClientNotifForwarder {
}
return nr;
} catch (ClassNotFoundException e) {
logger.trace("NotifFetcher.fetchNotifs", e);
return fetchOneNotif();
} catch (NotSerializableException e) {
} catch (ClassNotFoundException | NotSerializableException | UnmarshalException e) {
logger.trace("NotifFetcher.fetchNotifs", e);
return fetchOneNotif();
} catch (IOException ioe) {
@ -619,17 +617,18 @@ public abstract class ClientNotifForwarder {
timeout. This allows us to skip sequence numbers for
notifications that don't match our filters. Then we ask
for one notification. If that produces a
ClassNotFoundException or a NotSerializableException, we
increase our sequence number and ask again. Eventually we
will either get a successful notification, or a return with
0 notifications. In either case we can return a
ClassNotFoundException, NotSerializableException or
UnmarshalException, we increase our sequence number and ask again.
Eventually we will either get a successful notification, or a
return with 0 notifications. In either case we can return a
NotificationResult. This algorithm works (albeit less
well) even if the server implementation doesn't optimize a
request for 0 notifications to skip sequence numbers for
notifications that don't match our filters.
If we had at least one ClassNotFoundException, then we
must emit a JMXConnectionNotification.LOST_NOTIFS.
If we had at least one
ClassNotFoundException/NotSerializableException/UnmarshalException,
then we must emit a JMXConnectionNotification.LOST_NOTIFS.
*/
private NotificationResult fetchOneNotif() {
ClientNotifForwarder cnf = ClientNotifForwarder.this;
@ -668,23 +667,20 @@ public abstract class ClientNotifForwarder {
try {
// 1 notif to skip possible missing class
result = cnf.fetchNotifs(startSequenceNumber, 1, 0L);
} catch (Exception e) {
if (e instanceof ClassNotFoundException
|| e instanceof NotSerializableException) {
logger.warning("NotifFetcher.fetchOneNotif",
"Failed to deserialize a notification: "+e.toString());
if (logger.traceOn()) {
logger.trace("NotifFetcher.fetchOneNotif",
"Failed to deserialize a notification.", e);
}
notFoundCount++;
startSequenceNumber++;
} else {
if (!shouldStop())
logger.trace("NotifFetcher.fetchOneNotif", e);
return null;
} catch (ClassNotFoundException | NotSerializableException | UnmarshalException e) {
logger.warning("NotifFetcher.fetchOneNotif",
"Failed to deserialize a notification: "+e.toString());
if (logger.traceOn()) {
logger.trace("NotifFetcher.fetchOneNotif",
"Failed to deserialize a notification.", e);
}
notFoundCount++;
startSequenceNumber++;
} catch (Exception e) {
if (!shouldStop())
logger.trace("NotifFetcher.fetchOneNotif", e);
return null;
}
}
@ -692,7 +688,7 @@ public abstract class ClientNotifForwarder {
final String msg =
"Dropped " + notFoundCount + " notification" +
(notFoundCount == 1 ? "" : "s") +
" because classes were missing locally";
" because classes were missing locally or incompatible";
lostNotifs(msg, notFoundCount);
// Even if result.getEarliestSequenceNumber() is now greater than
// it was initially, meaning some notifs have been dropped

View file

@ -26,13 +26,8 @@
package com.sun.jmx.remote.internal;
import java.util.Properties;
import java.io.IOException;
import java.rmi.Remote;
import java.rmi.RemoteException;
import java.rmi.NoSuchObjectException;
import java.util.Properties;
import java.rmi.Remote;
import java.rmi.RemoteException;
import java.rmi.NoSuchObjectException;
import java.security.AccessController;
@ -115,9 +110,10 @@ public final class IIOPHelper {
* Connects the Stub to the given ORB.
*/
public static void connect(Object stub, Object orb)
throws RemoteException
throws IOException
{
ensureAvailable();
if (proxy == null)
throw new IOException("Connection to ORB failed, RMI/IIOP not available");
proxy.connect(stub, orb);
}
@ -125,15 +121,17 @@ public final class IIOPHelper {
* Returns true if the given object is an ORB.
*/
public static boolean isOrb(Object obj) {
ensureAvailable();
return proxy.isOrb(obj);
return (proxy == null) ? false : proxy.isOrb(obj);
}
/**
* Creates, and returns, a new ORB instance.
*/
public static Object createOrb(String[] args, Properties props) {
ensureAvailable();
public static Object createOrb(String[] args, Properties props)
throws IOException
{
if (proxy == null)
throw new IOException("ORB initialization failed, RMI/IIOP not available");
return proxy.createOrb(args, props);
}
@ -166,24 +164,27 @@ public final class IIOPHelper {
/**
* Makes a server object ready to receive remote calls
*/
public static void exportObject(Remote obj) throws RemoteException {
ensureAvailable();
public static void exportObject(Remote obj) throws IOException {
if (proxy == null)
throw new IOException("RMI object cannot be exported, RMI/IIOP not available");
proxy.exportObject(obj);
}
/**
* Deregisters a server object from the runtime.
*/
public static void unexportObject(Remote obj) throws NoSuchObjectException {
ensureAvailable();
public static void unexportObject(Remote obj) throws IOException {
if (proxy == null)
throw new NoSuchObjectException("Object not exported");
proxy.unexportObject(obj);
}
/**
* Returns a stub for the given server object.
*/
public static Remote toStub(Remote obj) throws NoSuchObjectException {
ensureAvailable();
public static Remote toStub(Remote obj) throws IOException {
if (proxy == null)
throw new NoSuchObjectException("Object not exported");
return proxy.toStub(obj);
}
}

View file

@ -25,16 +25,15 @@
package com.sun.jmx.remote.internal;
import com.sun.jmx.mbeanserver.Util;
import com.sun.jmx.remote.security.NotificationAccessController;
import com.sun.jmx.remote.util.ClassLogger;
import com.sun.jmx.remote.util.EnvHelp;
import java.io.IOException;
import java.security.AccessControlContext;
import java.security.AccessController;
import java.security.PrivilegedAction;
import java.security.PrivilegedActionException;
import java.security.PrivilegedExceptionAction;
import java.util.ArrayList;
import java.util.Collections;
import java.util.HashMap;
import java.util.HashSet;
@ -291,13 +290,18 @@ public class ServerNotifForwarder {
// so that we can know too, and remove the corresponding entry from the listenerMap.
// See 6957378.
private void snoopOnUnregister(NotificationResult nr) {
Set<IdAndFilter> delegateSet = listenerMap.get(MBeanServerDelegate.DELEGATE_NAME);
if (delegateSet == null || delegateSet.isEmpty()) {
return;
List<IdAndFilter> copy = null;
synchronized (listenerMap) {
Set<IdAndFilter> delegateSet = listenerMap.get(MBeanServerDelegate.DELEGATE_NAME);
if (delegateSet == null || delegateSet.isEmpty()) {
return;
}
copy = new ArrayList<>(delegateSet);
}
for (TargetedNotification tn : nr.getTargetedNotifications()) {
Integer id = tn.getListenerID();
for (IdAndFilter idaf : delegateSet) {
for (IdAndFilter idaf : copy) {
if (idaf.id == id) {
// This is a notification from the MBeanServerDelegate.
Notification n = tn.getNotification();

View file

@ -25,41 +25,39 @@
package com.sun.security.auth.login;
import javax.security.auth.AuthPermission;
import javax.security.auth.login.AppConfigurationEntry;
import java.io.*;
import java.util.*;
import javax.security.auth.login.Configuration;
import java.net.URI;
import java.net.URL;
import java.net.MalformedURLException;
import java.text.MessageFormat;
import sun.security.util.Debug;
import sun.security.util.ResourcesMgr;
import sun.security.util.PropertyExpander;
// NOTE: As of JDK 8, this class instantiates
// sun.security.provider.ConfigSpiFile and forwards all methods to that
// implementation. All implementation fixes and enhancements should be made to
// sun.security.provider.ConfigSpiFile and not this class.
// See JDK-8005117 for more information.
/**
* This class represents a default implementation for
* <code>javax.security.auth.login.Configuration</code>.
* {@code javax.security.auth.login.Configuration}.
*
* <p> This object stores the runtime login configuration representation,
* and is the amalgamation of multiple static login
* configurations that resides in files.
* The algorithm for locating the login configuration file(s) and reading their
* information into this <code>Configuration</code> object is:
* information into this {@code Configuration} object is:
*
* <ol>
* <li>
* Loop through the security properties,
* <i>login.config.url.1</i>, <i>login.config.url.2</i>, ...,
* <i>login.config.url.X</i>.
* Each property value specifies a <code>URL</code> pointing to a
* Each property value specifies a {@code URL} pointing to a
* login configuration file to be loaded. Read in and load
* each configuration.
*
* <li>
* The <code>java.lang.System</code> property
* The {@code java.lang.System} property
* <i>java.security.auth.login.config</i>
* may also be set to a <code>URL</code> pointing to another
* may also be set to a {@code URL} pointing to another
* login configuration file
* (which is the case when a user uses the -D switch at runtime).
* If this property is defined, and its use is allowed by the
@ -80,593 +78,63 @@ import sun.security.util.PropertyExpander;
*
* <p> The configuration syntax supported by this implementation
* is exactly that syntax specified in the
* <code>javax.security.auth.login.Configuration</code> class.
* {@code javax.security.auth.login.Configuration} class.
*
* @see javax.security.auth.login.LoginContext
* @see java.security.Security security properties
*/
public class ConfigFile extends javax.security.auth.login.Configuration {
public class ConfigFile extends Configuration {
private StreamTokenizer st;
private int lookahead;
private int linenum;
private HashMap<String, LinkedList<AppConfigurationEntry>> configuration;
private boolean expandProp = true;
private URL url;
private static Debug debugConfig = Debug.getInstance("configfile");
private static Debug debugParser = Debug.getInstance("configparser");
private sun.security.provider.ConfigSpiFile configFile;
/**
* Create a new <code>Configuration</code> object.
* Create a new {@code Configuration} object.
*
* @throws SecurityException if the {@code Configuration} can not be
* initialized
*/
public ConfigFile() {
try {
init(url);
} catch (IOException ioe) {
throw (SecurityException)
new SecurityException(ioe.getMessage()).initCause(ioe);
}
configFile = new sun.security.provider.ConfigSpiFile();
}
/**
* Create a new <code>Configuration</code> object from the specified URI.
* Create a new {@code Configuration} object from the specified {@code URI}.
*
* @param uri Create a new Configuration object from this URI.
* @param uri the {@code URI}
* @throws SecurityException if the {@code Configuration} can not be
* initialized
* @throws NullPointerException if {@code uri} is null
*/
public ConfigFile(URI uri) {
// only load config from the specified URI
try {
url = uri.toURL();
init(url);
} catch (MalformedURLException mue) {
throw (SecurityException)
new SecurityException(mue.getMessage()).initCause(mue);
} catch (IOException ioe) {
throw (SecurityException)
new SecurityException(ioe.getMessage()).initCause(ioe);
}
configFile = new sun.security.provider.ConfigSpiFile(uri);
}
/**
* Read and initialize the entire login Configuration.
* Retrieve an entry from the {@code Configuration} using an application
* name as an index.
*
* <p>
*
* @exception IOException if the Configuration can not be initialized. <p>
* @exception SecurityException if the caller does not have permission
* to initialize the Configuration.
*/
private void init(URL url) throws IOException {
boolean initialized = false;
FileReader fr = null;
String sep = File.separator;
if ("false".equals(System.getProperty("policy.expandProperties"))) {
expandProp = false;
}
// new configuration
HashMap<String, LinkedList<AppConfigurationEntry>> newConfig =
new HashMap<>();
if (url != null) {
/**
* If the caller specified a URI via Configuration.getInstance,
* we only read from that URI
*/
if (debugConfig != null) {
debugConfig.println("reading " + url);
}
init(url, newConfig);
configuration = newConfig;
return;
}
/**
* Caller did not specify URI via Configuration.getInstance.
* Read from URLs listed in the java.security properties file.
*/
String allowSys = java.security.Security.getProperty
("policy.allowSystemProperty");
if ("true".equalsIgnoreCase(allowSys)) {
String extra_config = System.getProperty
("java.security.auth.login.config");
if (extra_config != null) {
boolean overrideAll = false;
if (extra_config.startsWith("=")) {
overrideAll = true;
extra_config = extra_config.substring(1);
}
try {
extra_config = PropertyExpander.expand(extra_config);
} catch (PropertyExpander.ExpandException peee) {
MessageFormat form = new MessageFormat
(ResourcesMgr.getString
("Unable.to.properly.expand.config",
"sun.security.util.AuthResources"));
Object[] source = {extra_config};
throw new IOException(form.format(source));
}
URL configURL = null;
try {
configURL = new URL(extra_config);
} catch (java.net.MalformedURLException mue) {
File configFile = new File(extra_config);
if (configFile.exists()) {
configURL = configFile.toURI().toURL();
} else {
MessageFormat form = new MessageFormat
(ResourcesMgr.getString
("extra.config.No.such.file.or.directory.",
"sun.security.util.AuthResources"));
Object[] source = {extra_config};
throw new IOException(form.format(source));
}
}
if (debugConfig != null) {
debugConfig.println("reading "+configURL);
}
init(configURL, newConfig);
initialized = true;
if (overrideAll) {
if (debugConfig != null) {
debugConfig.println("overriding other policies!");
}
configuration = newConfig;
return;
}
}
}
int n = 1;
String config_url;
while ((config_url = java.security.Security.getProperty
("login.config.url."+n)) != null) {
try {
config_url = PropertyExpander.expand
(config_url).replace(File.separatorChar, '/');
if (debugConfig != null) {
debugConfig.println("\tReading config: " + config_url);
}
init(new URL(config_url), newConfig);
initialized = true;
} catch (PropertyExpander.ExpandException peee) {
MessageFormat form = new MessageFormat
(ResourcesMgr.getString
("Unable.to.properly.expand.config",
"sun.security.util.AuthResources"));
Object[] source = {config_url};
throw new IOException(form.format(source));
}
n++;
}
if (initialized == false && n == 1 && config_url == null) {
// get the config from the user's home directory
if (debugConfig != null) {
debugConfig.println("\tReading Policy " +
"from ~/.java.login.config");
}
config_url = System.getProperty("user.home");
String userConfigFile = config_url +
File.separatorChar + ".java.login.config";
// No longer throws an exception when there's no config file
// at all. Returns an empty Configuration instead.
if (new File(userConfigFile).exists()) {
init(new File(userConfigFile).toURI().toURL(),
newConfig);
}
}
configuration = newConfig;
}
private void init(URL config,
HashMap<String, LinkedList<AppConfigurationEntry>> newConfig)
throws IOException {
InputStreamReader isr = null;
try {
isr = new InputStreamReader(getInputStream(config), "UTF-8");
readConfig(isr, newConfig);
} catch (FileNotFoundException fnfe) {
if (debugConfig != null) {
debugConfig.println(fnfe.toString());
}
throw new IOException(ResourcesMgr.getString
("Configuration.Error.No.such.file.or.directory",
"sun.security.util.AuthResources"));
} finally {
if (isr != null) {
isr.close();
}
}
}
/**
* Retrieve an entry from the Configuration using an application name
* as an index.
*
* <p>
*
* @param applicationName the name used to index the Configuration.
* @return an array of AppConfigurationEntries which correspond to
* the stacked configuration of LoginModules for this
* application, or null if this application has no configured
* LoginModules.
* @param applicationName the name used to index the {@code Configuration}
* @return an array of {@code AppConfigurationEntry} which correspond to
* the stacked configuration of {@code LoginModule}s for this
* application, or null if this application has no configured
* {@code LoginModule}s.
*/
@Override
public AppConfigurationEntry[] getAppConfigurationEntry
(String applicationName) {
(String applicationName) {
LinkedList<AppConfigurationEntry> list = null;
synchronized (configuration) {
list = configuration.get(applicationName);
}
if (list == null || list.size() == 0)
return null;
AppConfigurationEntry[] entries =
new AppConfigurationEntry[list.size()];
Iterator<AppConfigurationEntry> iterator = list.iterator();
for (int i = 0; iterator.hasNext(); i++) {
AppConfigurationEntry e = iterator.next();
entries[i] = new AppConfigurationEntry(e.getLoginModuleName(),
e.getControlFlag(),
e.getOptions());
}
return entries;
return configFile.engineGetAppConfigurationEntry(applicationName);
}
/**
* Refresh and reload the Configuration by re-reading all of the
* Refresh and reload the {@code Configuration} by re-reading all of the
* login configurations.
*
* <p>
*
* @exception SecurityException if the caller does not have permission
* to refresh the Configuration.
* @throws SecurityException if the caller does not have permission
* to refresh the {@code Configuration}
*/
@Override
public synchronized void refresh() {
java.lang.SecurityManager sm = System.getSecurityManager();
if (sm != null)
sm.checkPermission(new AuthPermission("refreshLoginConfiguration"));
java.security.AccessController.doPrivileged
(new java.security.PrivilegedAction<Void>() {
public Void run() {
try {
init(url);
} catch (java.io.IOException ioe) {
throw (SecurityException) new SecurityException
(ioe.getLocalizedMessage()).initCause(ioe);
}
return null;
}
});
}
private void readConfig(Reader reader,
HashMap<String, LinkedList<AppConfigurationEntry>> newConfig)
throws IOException {
int linenum = 1;
if (!(reader instanceof BufferedReader))
reader = new BufferedReader(reader);
st = new StreamTokenizer(reader);
st.quoteChar('"');
st.wordChars('$', '$');
st.wordChars('_', '_');
st.wordChars('-', '-');
st.lowerCaseMode(false);
st.slashSlashComments(true);
st.slashStarComments(true);
st.eolIsSignificant(true);
lookahead = nextToken();
while (lookahead != StreamTokenizer.TT_EOF) {
parseLoginEntry(newConfig);
}
}
private void parseLoginEntry(
HashMap<String, LinkedList<AppConfigurationEntry>> newConfig)
throws IOException {
String appName;
String moduleClass;
String sflag;
AppConfigurationEntry.LoginModuleControlFlag controlFlag;
LinkedList<AppConfigurationEntry> configEntries = new LinkedList<>();
// application name
appName = st.sval;
lookahead = nextToken();
if (debugParser != null) {
debugParser.println("\tReading next config entry: " + appName);
}
match("{");
// get the modules
while (peek("}") == false) {
// get the module class name
moduleClass = match("module class name");
// controlFlag (required, optional, etc)
sflag = match("controlFlag");
if (sflag.equalsIgnoreCase("REQUIRED"))
controlFlag =
AppConfigurationEntry.LoginModuleControlFlag.REQUIRED;
else if (sflag.equalsIgnoreCase("REQUISITE"))
controlFlag =
AppConfigurationEntry.LoginModuleControlFlag.REQUISITE;
else if (sflag.equalsIgnoreCase("SUFFICIENT"))
controlFlag =
AppConfigurationEntry.LoginModuleControlFlag.SUFFICIENT;
else if (sflag.equalsIgnoreCase("OPTIONAL"))
controlFlag =
AppConfigurationEntry.LoginModuleControlFlag.OPTIONAL;
else {
MessageFormat form = new MessageFormat(ResourcesMgr.getString
("Configuration.Error.Invalid.control.flag.flag",
"sun.security.util.AuthResources"));
Object[] source = {sflag};
throw new IOException(form.format(source));
}
// get the args
HashMap<String, String> options = new HashMap<>();
String key;
String value;
while (peek(";") == false) {
key = match("option key");
match("=");
try {
value = expand(match("option value"));
} catch (PropertyExpander.ExpandException peee) {
throw new IOException(peee.getLocalizedMessage());
}
options.put(key, value);
}
lookahead = nextToken();
// create the new element
if (debugParser != null) {
debugParser.println("\t\t" + moduleClass + ", " + sflag);
java.util.Iterator<String> i = options.keySet().iterator();
while (i.hasNext()) {
key = i.next();
debugParser.println("\t\t\t" +
key +
"=" +
options.get(key));
}
}
AppConfigurationEntry entry = new AppConfigurationEntry
(moduleClass,
controlFlag,
options);
configEntries.add(entry);
}
match("}");
match(";");
// add this configuration entry
if (newConfig.containsKey(appName)) {
MessageFormat form = new MessageFormat(ResourcesMgr.getString
("Configuration.Error.Can.not.specify.multiple.entries.for.appName",
"sun.security.util.AuthResources"));
Object[] source = {appName};
throw new IOException(form.format(source));
}
newConfig.put(appName, configEntries);
}
private String match(String expect) throws IOException {
String value = null;
switch(lookahead) {
case StreamTokenizer.TT_EOF:
MessageFormat form1 = new MessageFormat(ResourcesMgr.getString
("Configuration.Error.expected.expect.read.end.of.file.",
"sun.security.util.AuthResources"));
Object[] source1 = {expect};
throw new IOException(form1.format(source1));
case '"':
case StreamTokenizer.TT_WORD:
if (expect.equalsIgnoreCase("module class name") ||
expect.equalsIgnoreCase("controlFlag") ||
expect.equalsIgnoreCase("option key") ||
expect.equalsIgnoreCase("option value")) {
value = st.sval;
lookahead = nextToken();
} else {
MessageFormat form = new MessageFormat(ResourcesMgr.getString
("Configuration.Error.Line.line.expected.expect.found.value.",
"sun.security.util.AuthResources"));
Object[] source = {new Integer(linenum), expect, st.sval};
throw new IOException(form.format(source));
}
break;
case '{':
if (expect.equalsIgnoreCase("{")) {
lookahead = nextToken();
} else {
MessageFormat form = new MessageFormat(ResourcesMgr.getString
("Configuration.Error.Line.line.expected.expect.",
"sun.security.util.AuthResources"));
Object[] source = {new Integer(linenum), expect, st.sval};
throw new IOException(form.format(source));
}
break;
case ';':
if (expect.equalsIgnoreCase(";")) {
lookahead = nextToken();
} else {
MessageFormat form = new MessageFormat(ResourcesMgr.getString
("Configuration.Error.Line.line.expected.expect.",
"sun.security.util.AuthResources"));
Object[] source = {new Integer(linenum), expect, st.sval};
throw new IOException(form.format(source));
}
break;
case '}':
if (expect.equalsIgnoreCase("}")) {
lookahead = nextToken();
} else {
MessageFormat form = new MessageFormat(ResourcesMgr.getString
("Configuration.Error.Line.line.expected.expect.",
"sun.security.util.AuthResources"));
Object[] source = {new Integer(linenum), expect, st.sval};
throw new IOException(form.format(source));
}
break;
case '=':
if (expect.equalsIgnoreCase("=")) {
lookahead = nextToken();
} else {
MessageFormat form = new MessageFormat(ResourcesMgr.getString
("Configuration.Error.Line.line.expected.expect.",
"sun.security.util.AuthResources"));
Object[] source = {new Integer(linenum), expect, st.sval};
throw new IOException(form.format(source));
}
break;
default:
MessageFormat form = new MessageFormat(ResourcesMgr.getString
("Configuration.Error.Line.line.expected.expect.found.value.",
"sun.security.util.AuthResources"));
Object[] source = {new Integer(linenum), expect, st.sval};
throw new IOException(form.format(source));
}
return value;
}
private boolean peek(String expect) {
boolean found = false;
switch (lookahead) {
case ',':
if (expect.equalsIgnoreCase(","))
found = true;
break;
case ';':
if (expect.equalsIgnoreCase(";"))
found = true;
break;
case '{':
if (expect.equalsIgnoreCase("{"))
found = true;
break;
case '}':
if (expect.equalsIgnoreCase("}"))
found = true;
break;
default:
}
return found;
}
private int nextToken() throws IOException {
int tok;
while ((tok = st.nextToken()) == StreamTokenizer.TT_EOL) {
linenum++;
}
return tok;
}
/*
* Fast path reading from file urls in order to avoid calling
* FileURLConnection.connect() which can be quite slow the first time
* it is called. We really should clean up FileURLConnection so that
* this is not a problem but in the meantime this fix helps reduce
* start up time noticeably for the new launcher. -- DAC
*/
private InputStream getInputStream(URL url) throws IOException {
if ("file".equalsIgnoreCase(url.getProtocol())) {
// Compatibility notes:
//
// Code changed from
// String path = url.getFile().replace('/', File.separatorChar);
// return new FileInputStream(path);
//
// The original implementation would search for "/tmp/a%20b"
// when url is "file:///tmp/a%20b". This is incorrect. The
// current codes fix this bug and searches for "/tmp/a b".
// For compatibility reasons, when the file "/tmp/a b" does
// not exist, the file named "/tmp/a%20b" will be tried.
//
// This also means that if both file exists, the behavior of
// this method is changed, and the current codes choose the
// correct one.
try {
return url.openStream();
} catch (Exception e) {
String file = url.getPath();
if (url.getHost().length() > 0) { // For Windows UNC
file = "//" + url.getHost() + file;
}
if (debugConfig != null) {
debugConfig.println("cannot read " + url +
", try " + file);
}
return new FileInputStream(file);
}
} else {
return url.openStream();
}
}
private String expand(String value)
throws PropertyExpander.ExpandException, IOException {
if ("".equals(value)) {
return value;
}
if (expandProp) {
String s = PropertyExpander.expand(value);
if (s == null || s.length() == 0) {
MessageFormat form = new MessageFormat(ResourcesMgr.getString
("Configuration.Error.Line.line.system.property.value.expanded.to.empty.value",
"sun.security.util.AuthResources"));
Object[] source = {new Integer(linenum), value};
throw new IOException(form.format(source));
}
return s;
} else {
return value;
}
configFile.engineRefresh();
}
}

View file

@ -1,5 +1,5 @@
/*
* Copyright (c) 2000, 2011, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2000, 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -58,7 +58,8 @@ import sun.reflect.misc.*;
*/
public class DefaultPersistenceDelegate extends PersistenceDelegate {
private String[] constructor;
private static final String[] EMPTY = {};
private final String[] constructor;
private Boolean definesEquals;
/**
@ -67,7 +68,7 @@ public class DefaultPersistenceDelegate extends PersistenceDelegate {
* @see #DefaultPersistenceDelegate(java.lang.String[])
*/
public DefaultPersistenceDelegate() {
this(new String[0]);
this.constructor = EMPTY;
}
/**
@ -92,7 +93,7 @@ public class DefaultPersistenceDelegate extends PersistenceDelegate {
* @see #instantiate
*/
public DefaultPersistenceDelegate(String[] constructorPropertyNames) {
this.constructor = constructorPropertyNames;
this.constructor = (constructorPropertyNames == null) ? EMPTY : constructorPropertyNames.clone();
}
private static boolean definesEquals(Class<?> type) {

View file

@ -1,5 +1,5 @@
/*
* Copyright (c) 1996, 2010, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 1996, 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -277,7 +277,9 @@ public class EventSetDescriptor extends FeatureDescriptor {
Method removeListenerMethod)
throws IntrospectionException {
setName(eventSetName);
this.listenerMethodDescriptors = listenerMethodDescriptors;
this.listenerMethodDescriptors = (listenerMethodDescriptors != null)
? listenerMethodDescriptors.clone()
: null;
setAddListenerMethod(addListenerMethod);
setRemoveListenerMethod(removeListenerMethod);
setListenerType(listenerType);
@ -347,7 +349,9 @@ public class EventSetDescriptor extends FeatureDescriptor {
* events are fired.
*/
public synchronized MethodDescriptor[] getListenerMethodDescriptors() {
return listenerMethodDescriptors;
return (this.listenerMethodDescriptors != null)
? this.listenerMethodDescriptors.clone()
: null;
}
/**

View file

@ -1,5 +1,5 @@
/*
* Copyright (c) 1996, 2010, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 1996, 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -70,7 +70,9 @@ public class MethodDescriptor extends FeatureDescriptor {
ParameterDescriptor parameterDescriptors[]) {
setName(method.getName());
setMethod(method);
this.parameterDescriptors = parameterDescriptors;
this.parameterDescriptors = (parameterDescriptors != null)
? parameterDescriptors.clone()
: null;
}
/**
@ -161,7 +163,9 @@ public class MethodDescriptor extends FeatureDescriptor {
* a null array if the parameter names aren't known.
*/
public ParameterDescriptor[] getParameterDescriptors() {
return parameterDescriptors;
return (this.parameterDescriptors != null)
? this.parameterDescriptors.clone()
: null;
}
/*

View file

@ -1,5 +1,5 @@
/*
* Copyright (c) 2000, 2010, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2000, 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -92,7 +92,7 @@ public class Statement {
public Statement(Object target, String methodName, Object[] arguments) {
this.target = target;
this.methodName = methodName;
this.arguments = (arguments == null) ? emptyArray : arguments;
this.arguments = (arguments == null) ? emptyArray : arguments.clone();
}
/**
@ -128,7 +128,7 @@ public class Statement {
* @return the array of arguments
*/
public Object[] getArguments() {
return arguments;
return this.arguments.clone();
}
/**

View file

@ -506,6 +506,7 @@ public final
* returns {@code false} otherwise.
* @return {@code true} if and only if this class is a synthetic class as
* defined by the Java Language Specification.
* @jls 13.1 The Form of a Binary
* @since 1.5
*/
public boolean isSynthetic() {

View file

@ -66,6 +66,8 @@ public final class Constructor<T> extends Executable {
private transient ConstructorRepository genericInfo;
private byte[] annotations;
private byte[] parameterAnnotations;
// This is set by the vm at Constructor creation
private byte[] typeAnnotations;
// Generics infrastructure
// Accessor for factory
@ -138,6 +140,8 @@ public final class Constructor<T> extends Executable {
res.root = this;
// Might as well eagerly propagate this if already present
res.constructorAccessor = constructorAccessor;
res.typeAnnotations = typeAnnotations;
return res;
}
@ -407,6 +411,7 @@ public final class Constructor<T> extends Executable {
/**
* {@inheritDoc}
* @jls 13.1 The Form of a Binary
* @since 1.5
*/
@Override

View file

@ -324,6 +324,7 @@ public abstract class Executable extends AccessibleObject
* @return true if and only if this executable is a synthetic
* construct as defined by
* <cite>The Java&trade; Language Specification</cite>.
* @jls 13.1 The Form of a Binary
*/
public boolean isSynthetic() {
return Modifier.isSynthetic(getModifiers());

View file

@ -80,6 +80,8 @@ class Field extends AccessibleObject implements Member {
// currently only two levels deep (i.e., one root Field and
// potentially many Field objects pointing to it.)
private Field root;
// This is set by the vm at Field creation
private byte[] typeAnnotations;
// Generics infrastructure
@ -144,6 +146,8 @@ class Field extends AccessibleObject implements Member {
// Might as well eagerly propagate this if already present
res.fieldAccessor = fieldAccessor;
res.overrideFieldAccessor = overrideFieldAccessor;
res.typeAnnotations = typeAnnotations;
return res;
}

View file

@ -1,5 +1,5 @@
/*
* Copyright (c) 1996, 2006, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 1996, 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -87,6 +87,7 @@ interface Member {
*
* @return true if and only if this member was introduced by
* the compiler.
* @jls 13.1 The Form of a Binary
* @since 1.5
*/
public boolean isSynthetic();

View file

@ -79,7 +79,8 @@ public final class Method extends Executable {
// currently only two levels deep (i.e., one root Method and
// potentially many Method objects pointing to it.)
private Method root;
// This is set by the vm at Method creation
private byte[] typeAnnotations;
// Generics infrastructure
private String getGenericSignature() {return signature;}
@ -150,6 +151,8 @@ public final class Method extends Executable {
res.root = this;
// Might as well eagerly propagate this if already present
res.methodAccessor = methodAccessor;
res.typeAnnotations = typeAnnotations;
return res;
}
@ -497,6 +500,7 @@ public final class Method extends Executable {
/**
* {@inheritDoc}
* @jls 13.1 The Form of a Binary
* @since 1.5
*/
@Override
@ -504,6 +508,22 @@ public final class Method extends Executable {
return super.isSynthetic();
}
/**
* Returns {@code true} if this method is a default
* method; returns {@code false} otherwise.
*
* A default method is a non-abstract method, that is, a method
* with a body, declared in an interface type.
*
* @return true if and only if this method is a default
* method as defined by the Java Language Specification.
* @since 1.8
*/
public boolean isDefault() {
return (getModifiers() & Modifier.ABSTRACT) == 0 &&
getDeclaringClass().isInterface();
}
// NOTE that there is no synchronization used here. It is correct
// (though not efficient) to generate more than one MethodAccessor
// for a given Method. However, avoiding synchronization will

View file

@ -129,15 +129,6 @@ import sun.net.www.MessageHeader;
* <a href="http://www.ietf.org/rfc/rfc2616.txt">http://www.ietf.org/rfc/rfc2616.txt</a>
* </pre></blockquote>
*
* Note about <code>fileNameMap</code>: In versions prior to JDK 1.1.6,
* field <code>fileNameMap</code> of <code>URLConnection</code> was public.
* In JDK 1.1.6 and later, <code>fileNameMap</code> is private; accessor
* and mutator methods {@link #getFileNameMap() getFileNameMap} and
* {@link #setFileNameMap(java.net.FileNameMap) setFileNameMap} are added
* to access it. This change is also described on the <a href=
* "http://java.sun.com/products/jdk/1.2/compatibility.html">
* Compatibility</a> page.
*
* Invoking the <tt>close()</tt> methods on the <tt>InputStream</tt> or <tt>OutputStream</tt> of an
* <tt>URLConnection</tt> after a request may free network resources associated with this
* instance, unless particular protocol specifications specify different behaviours
@ -305,8 +296,7 @@ public abstract class URLConnection {
* Loads filename map (a mimetable) from a data file. It will
* first try to load the user-specific table, defined
* by &quot;content.types.user.table&quot; property. If that fails,
* it tries to load the default built-in table at
* lib/content-types.properties under java home.
* it tries to load the default built-in table.
*
* @return the FileNameMap
* @since 1.2

View file

@ -26,6 +26,7 @@
package java.util;
import java.lang.reflect.*;
import static java.util.ArraysParallelSortHelpers.*;
/**
* This class contains various methods for manipulating arrays (such as
@ -54,6 +55,13 @@ import java.lang.reflect.*;
*/
public class Arrays {
/**
* The minimum array length below which the sorting algorithm will not
* further partition the sorting task.
*/
// reasonable default so that we don't overcreate tasks
private static final int MIN_ARRAY_SORT_GRAN = 256;
// Suppresses default constructor, ensuring non-instantiability.
private Arrays() {}
@ -787,6 +795,613 @@ public class Arrays {
}
}
/*
* Parallel sorting of primitive type arrays.
*/
/**
* Sorts the specified array into ascending numerical order.
*
* <p>Implementation note: The sorting algorithm is a parallel sort-merge
* that breaks the array into sub-arrays that are themselves sorted and then
* merged. When the sub-array length reaches a minimum granularity, the
* sub-array is sorted using the appropriate {@link Arrays#sort(byte[])
* Arrays.sort} method. The algorithm requires a working space equal to the
* size of the original array. The {@link
* java.util.concurrent.ForkJoinPool#commonPool() ForkJoin common pool} is
* used to execute any parallel tasks.
*
* @param a the array to be sorted
*
* @since 1.8
*/
public static void parallelSort(byte[] a) {
parallelSort(a, 0, a.length);
}
/**
* Sorts the specified range of the array into ascending order. The range
* to be sorted extends from the index {@code fromIndex}, inclusive, to
* the index {@code toIndex}, exclusive. If {@code fromIndex == toIndex},
* the range to be sorted is empty.
*
* <p>Implementation note: The sorting algorithm is a parallel sort-merge
* that breaks the array into sub-arrays that are themselves sorted and then
* merged. When the sub-array length reaches a minimum granularity, the
* sub-array is sorted using the appropriate {@link Arrays#sort(byte[])
* Arrays.sort} method. The algorithm requires a working space equal to the
* size of the original array. The {@link
* java.util.concurrent.ForkJoinPool#commonPool() ForkJoin common pool} is
* used to execute any parallel tasks.
*
* @param a the array to be sorted
* @param fromIndex the index of the first element, inclusive, to be sorted
* @param toIndex the index of the last element, exclusive, to be sorted
*
* @throws IllegalArgumentException if {@code fromIndex > toIndex}
* @throws ArrayIndexOutOfBoundsException
* if {@code fromIndex < 0} or {@code toIndex > a.length}
*
* @since 1.8
*/
public static void parallelSort(byte[] a, int fromIndex, int toIndex) {
rangeCheck(a.length, fromIndex, toIndex);
int nelements = toIndex - fromIndex;
int gran = getSplitThreshold(nelements);
FJByte.Sorter task = new FJByte.Sorter(a, new byte[a.length], fromIndex,
nelements, gran);
task.invoke();
}
/**
* Sorts the specified array into ascending numerical order.
*
* <p>Implementation note: The sorting algorithm is a parallel sort-merge
* that breaks the array into sub-arrays that are themselves sorted and then
* merged. When the sub-array length reaches a minimum granularity, the
* sub-array is sorted using the appropriate {@link Arrays#sort(char[])
* Arrays.sort} method. The algorithm requires a working space equal to the
* size of the original array. The {@link
* java.util.concurrent.ForkJoinPool#commonPool() ForkJoin common pool} is
* used to execute any parallel tasks.
*
* @param a the array to be sorted
*
* @since 1.8
*/
public static void parallelSort(char[] a) {
parallelSort(a, 0, a.length);
}
/**
* Sorts the specified range of the array into ascending order. The range
* to be sorted extends from the index {@code fromIndex}, inclusive, to
* the index {@code toIndex}, exclusive. If {@code fromIndex == toIndex},
* the range to be sorted is empty.
*
* <p>Implementation note: The sorting algorithm is a parallel sort-merge
* that breaks the array into sub-arrays that are themselves sorted and then
* merged. When the sub-array length reaches a minimum granularity, the
* sub-array is sorted using the appropriate {@link Arrays#sort(char[])
* Arrays.sort} method. The algorithm requires a working space equal to the
* size of the original array. The {@link
* java.util.concurrent.ForkJoinPool#commonPool() ForkJoin common pool} is
* used to execute any parallel tasks.
*
* @param a the array to be sorted
* @param fromIndex the index of the first element, inclusive, to be sorted
* @param toIndex the index of the last element, exclusive, to be sorted
*
* @throws IllegalArgumentException if {@code fromIndex > toIndex}
* @throws ArrayIndexOutOfBoundsException
* if {@code fromIndex < 0} or {@code toIndex > a.length}
*
* @since 1.8
*/
public static void parallelSort(char[] a, int fromIndex, int toIndex) {
rangeCheck(a.length, fromIndex, toIndex);
int nelements = toIndex - fromIndex;
int gran = getSplitThreshold(nelements);
FJChar.Sorter task = new FJChar.Sorter(a, new char[a.length], fromIndex,
nelements, gran);
task.invoke();
}
/**
* Sorts the specified array into ascending numerical order.
*
* <p>Implementation note: The sorting algorithm is a parallel sort-merge
* that breaks the array into sub-arrays that are themselves sorted and then
* merged. When the sub-array length reaches a minimum granularity, the
* sub-array is sorted using the appropriate {@link Arrays#sort(short[])
* Arrays.sort} method. The algorithm requires a working space equal to the
* size of the original array. The {@link
* java.util.concurrent.ForkJoinPool#commonPool() ForkJoin common pool} is
* used to execute any parallel tasks.
*
* @param a the array to be sorted
*
* @since 1.8
*/
public static void parallelSort(short[] a) {
parallelSort(a, 0, a.length);
}
/**
* Sorts the specified range of the array into ascending order. The range
* to be sorted extends from the index {@code fromIndex}, inclusive, to
* the index {@code toIndex}, exclusive. If {@code fromIndex == toIndex},
* the range to be sorted is empty.
*
* <p>Implementation note: The sorting algorithm is a parallel sort-merge
* that breaks the array into sub-arrays that are themselves sorted and then
* merged. When the sub-array length reaches a minimum granularity, the
* sub-array is sorted using the appropriate {@link Arrays#sort(short[])
* Arrays.sort} method. The algorithm requires a working space equal to the
* size of the original array. The {@link
* java.util.concurrent.ForkJoinPool#commonPool() ForkJoin common pool} is
* used to execute any parallel tasks.
*
* @param a the array to be sorted
* @param fromIndex the index of the first element, inclusive, to be sorted
* @param toIndex the index of the last element, exclusive, to be sorted
*
* @throws IllegalArgumentException if {@code fromIndex > toIndex}
* @throws ArrayIndexOutOfBoundsException
* if {@code fromIndex < 0} or {@code toIndex > a.length}
*
* @since 1.8
*/
public static void parallelSort(short[] a, int fromIndex, int toIndex) {
rangeCheck(a.length, fromIndex, toIndex);
int nelements = toIndex - fromIndex;
int gran = getSplitThreshold(nelements);
FJShort.Sorter task = new FJShort.Sorter(a, new short[a.length], fromIndex,
nelements, gran);
task.invoke();
}
/**
* Sorts the specified array into ascending numerical order.
*
* <p>Implementation note: The sorting algorithm is a parallel sort-merge
* that breaks the array into sub-arrays that are themselves sorted and then
* merged. When the sub-array length reaches a minimum granularity, the
* sub-array is sorted using the appropriate {@link Arrays#sort(int[])
* Arrays.sort} method. The algorithm requires a working space equal to the
* size of the original array. The {@link
* java.util.concurrent.ForkJoinPool#commonPool() ForkJoin common pool} is
* used to execute any parallel tasks.
*
* @param a the array to be sorted
*
* @since 1.8
*/
public static void parallelSort(int[] a) {
parallelSort(a, 0, a.length);
}
/**
* Sorts the specified range of the array into ascending order. The range
* to be sorted extends from the index {@code fromIndex}, inclusive, to
* the index {@code toIndex}, exclusive. If {@code fromIndex == toIndex},
* the range to be sorted is empty.
*
* <p>Implementation note: The sorting algorithm is a parallel sort-merge
* that breaks the array into sub-arrays that are themselves sorted and then
* merged. When the sub-array length reaches a minimum granularity, the
* sub-array is sorted using the appropriate {@link Arrays#sort(int[])
* Arrays.sort} method. The algorithm requires a working space equal to the
* size of the original array. The {@link
* java.util.concurrent.ForkJoinPool#commonPool() ForkJoin common pool} is
* used to execute any parallel tasks.
*
* @param a the array to be sorted
* @param fromIndex the index of the first element, inclusive, to be sorted
* @param toIndex the index of the last element, exclusive, to be sorted
*
* @throws IllegalArgumentException if {@code fromIndex > toIndex}
* @throws ArrayIndexOutOfBoundsException
* if {@code fromIndex < 0} or {@code toIndex > a.length}
*
* @since 1.8
*/
public static void parallelSort(int[] a, int fromIndex, int toIndex) {
rangeCheck(a.length, fromIndex, toIndex);
int nelements = toIndex - fromIndex;
int gran = getSplitThreshold(nelements);
FJInt.Sorter task = new FJInt.Sorter(a, new int[a.length], fromIndex,
nelements, gran);
task.invoke();
}
/**
* Sorts the specified array into ascending numerical order.
*
* <p>Implementation note: The sorting algorithm is a parallel sort-merge
* that breaks the array into sub-arrays that are themselves sorted and then
* merged. When the sub-array length reaches a minimum granularity, the
* sub-array is sorted using the appropriate {@link Arrays#sort(long[])
* Arrays.sort} method. The algorithm requires a working space equal to the
* size of the original array. The {@link
* java.util.concurrent.ForkJoinPool#commonPool() ForkJoin common pool} is
* used to execute any parallel tasks.
*
* @param a the array to be sorted
*
* @since 1.8
*/
public static void parallelSort(long[] a) {
parallelSort(a, 0, a.length);
}
/**
* Sorts the specified range of the array into ascending order. The range
* to be sorted extends from the index {@code fromIndex}, inclusive, to
* the index {@code toIndex}, exclusive. If {@code fromIndex == toIndex},
* the range to be sorted is empty.
*
* <p>Implementation note: The sorting algorithm is a parallel sort-merge
* that breaks the array into sub-arrays that are themselves sorted and then
* merged. When the sub-array length reaches a minimum granularity, the
* sub-array is sorted using the appropriate {@link Arrays#sort(long[])
* Arrays.sort} method. The algorithm requires a working space equal to the
* size of the original array. The {@link
* java.util.concurrent.ForkJoinPool#commonPool() ForkJoin common pool} is
* used to execute any parallel tasks.
*
* @param a the array to be sorted
* @param fromIndex the index of the first element, inclusive, to be sorted
* @param toIndex the index of the last element, exclusive, to be sorted
*
* @throws IllegalArgumentException if {@code fromIndex > toIndex}
* @throws ArrayIndexOutOfBoundsException
* if {@code fromIndex < 0} or {@code toIndex > a.length}
*
* @since 1.8
*/
public static void parallelSort(long[] a, int fromIndex, int toIndex) {
rangeCheck(a.length, fromIndex, toIndex);
int nelements = toIndex - fromIndex;
int gran = getSplitThreshold(nelements);
FJLong.Sorter task = new FJLong.Sorter(a, new long[a.length], fromIndex,
nelements, gran);
task.invoke();
}
/**
* Sorts the specified array into ascending numerical order.
*
* <p>The {@code <} relation does not provide a total order on all float
* values: {@code -0.0f == 0.0f} is {@code true} and a {@code Float.NaN}
* value compares neither less than, greater than, nor equal to any value,
* even itself. This method uses the total order imposed by the method
* {@link Float#compareTo}: {@code -0.0f} is treated as less than value
* {@code 0.0f} and {@code Float.NaN} is considered greater than any
* other value and all {@code Float.NaN} values are considered equal.
*
* <p>Implementation note: The sorting algorithm is a parallel sort-merge
* that breaks the array into sub-arrays that are themselves sorted and then
* merged. When the sub-array length reaches a minimum granularity, the
* sub-array is sorted using the appropriate {@link Arrays#sort(float[])
* Arrays.sort} method. The algorithm requires a working space equal to the
* size of the original array. The {@link
* java.util.concurrent.ForkJoinPool#commonPool() ForkJoin common pool} is
* used to execute any parallel tasks.
*
* @param a the array to be sorted
*
* @since 1.8
*/
public static void parallelSort(float[] a) {
parallelSort(a, 0, a.length);
}
/**
* Sorts the specified range of the array into ascending order. The range
* to be sorted extends from the index {@code fromIndex}, inclusive, to
* the index {@code toIndex}, exclusive. If {@code fromIndex == toIndex},
* the range to be sorted is empty.
*
* <p>The {@code <} relation does not provide a total order on all float
* values: {@code -0.0f == 0.0f} is {@code true} and a {@code Float.NaN}
* value compares neither less than, greater than, nor equal to any value,
* even itself. This method uses the total order imposed by the method
* {@link Float#compareTo}: {@code -0.0f} is treated as less than value
* {@code 0.0f} and {@code Float.NaN} is considered greater than any
* other value and all {@code Float.NaN} values are considered equal.
*
* <p>Implementation note: The sorting algorithm is a parallel sort-merge
* that breaks the array into sub-arrays that are themselves sorted and then
* merged. When the sub-array length reaches a minimum granularity, the
* sub-array is sorted using the appropriate {@link Arrays#sort(float[])
* Arrays.sort} method. The algorithm requires a working space equal to the
* size of the original array. The {@link
* java.util.concurrent.ForkJoinPool#commonPool() ForkJoin common pool} is
* used to execute any parallel tasks.
*
* @param a the array to be sorted
* @param fromIndex the index of the first element, inclusive, to be sorted
* @param toIndex the index of the last element, exclusive, to be sorted
*
* @throws IllegalArgumentException if {@code fromIndex > toIndex}
* @throws ArrayIndexOutOfBoundsException
* if {@code fromIndex < 0} or {@code toIndex > a.length}
*
* @since 1.8
*/
public static void parallelSort(float[] a, int fromIndex, int toIndex) {
rangeCheck(a.length, fromIndex, toIndex);
int nelements = toIndex - fromIndex;
int gran = getSplitThreshold(nelements);
FJFloat.Sorter task = new FJFloat.Sorter(a, new float[a.length], fromIndex,
nelements, gran);
task.invoke();
}
/**
* Sorts the specified array into ascending numerical order.
*
* <p>The {@code <} relation does not provide a total order on all double
* values: {@code -0.0d == 0.0d} is {@code true} and a {@code Double.NaN}
* value compares neither less than, greater than, nor equal to any value,
* even itself. This method uses the total order imposed by the method
* {@link Double#compareTo}: {@code -0.0d} is treated as less than value
* {@code 0.0d} and {@code Double.NaN} is considered greater than any
* other value and all {@code Double.NaN} values are considered equal.
*
* <p>Implementation note: The sorting algorithm is a parallel sort-merge
* that breaks the array into sub-arrays that are themselves sorted and then
* merged. When the sub-array length reaches a minimum granularity, the
* sub-array is sorted using the appropriate {@link Arrays#sort(double[])
* Arrays.sort} method. The algorithm requires a working space equal to the
* size of the original array. The {@link
* java.util.concurrent.ForkJoinPool#commonPool() ForkJoin common pool} is
* used to execute any parallel tasks.
*
* @param a the array to be sorted
*
* @since 1.8
*/
public static void parallelSort(double[] a) {
parallelSort(a, 0, a.length);
}
/**
* Sorts the specified range of the array into ascending order. The range
* to be sorted extends from the index {@code fromIndex}, inclusive, to
* the index {@code toIndex}, exclusive. If {@code fromIndex == toIndex},
* the range to be sorted is empty.
*
* <p>The {@code <} relation does not provide a total order on all double
* values: {@code -0.0d == 0.0d} is {@code true} and a {@code Double.NaN}
* value compares neither less than, greater than, nor equal to any value,
* even itself. This method uses the total order imposed by the method
* {@link Double#compareTo}: {@code -0.0d} is treated as less than value
* {@code 0.0d} and {@code Double.NaN} is considered greater than any
* other value and all {@code Double.NaN} values are considered equal.
*
* <p>Implementation note: The sorting algorithm is a parallel sort-merge
* that breaks the array into sub-arrays that are themselves sorted and then
* merged. When the sub-array length reaches a minimum granularity, the
* sub-array is sorted using the appropriate {@link Arrays#sort(double[])
* Arrays.sort} method. The algorithm requires a working space equal to the
* size of the original array. The {@link
* java.util.concurrent.ForkJoinPool#commonPool() ForkJoin common pool} is
* used to execute any parallel tasks.
*
* @param a the array to be sorted
* @param fromIndex the index of the first element, inclusive, to be sorted
* @param toIndex the index of the last element, exclusive, to be sorted
*
* @throws IllegalArgumentException if {@code fromIndex > toIndex}
* @throws ArrayIndexOutOfBoundsException
* if {@code fromIndex < 0} or {@code toIndex > a.length}
*
* @since 1.8
*/
public static void parallelSort(double[] a, int fromIndex, int toIndex) {
rangeCheck(a.length, fromIndex, toIndex);
int nelements = toIndex - fromIndex;
int gran = getSplitThreshold(nelements);
FJDouble.Sorter task = new FJDouble.Sorter(a, new double[a.length],
fromIndex, nelements, gran);
task.invoke();
}
/*
* Parallel sorting of complex type arrays.
*/
/**
* Sorts the specified array of objects into ascending order, according
* to the {@linkplain Comparable natural ordering} of its elements.
* All elements in the array must implement the {@link Comparable}
* interface. Furthermore, all elements in the array must be
* <i>mutually comparable</i> (that is, {@code e1.compareTo(e2)} must
* not throw a {@code ClassCastException} for any elements {@code e1}
* and {@code e2} in the array).
*
* <p>This sort is not guaranteed to be <i>stable</i>: equal elements
* may be reordered as a result of the sort.
*
* <p>Implementation note: The sorting algorithm is a parallel sort-merge
* that breaks the array into sub-arrays that are themselves sorted and then
* merged. When the sub-array length reaches a minimum granularity, the
* sub-array is sorted using the appropriate {@link Arrays#sort(Object[])
* Arrays.sort} method. The algorithm requires a working space equal to the
* size of the original array. The {@link
* java.util.concurrent.ForkJoinPool#commonPool() ForkJoin common pool} is
* used to execute any parallel tasks.
*
* @param a the array to be sorted
*
* @throws ClassCastException if the array contains elements that are not
* <i>mutually comparable</i> (for example, strings and integers)
* @throws IllegalArgumentException (optional) if the natural
* ordering of the array elements is found to violate the
* {@link Comparable} contract
*
* @since 1.8
*/
public static <T extends Comparable<? super T>> void parallelSort(T[] a) {
parallelSort(a, 0, a.length);
}
/**
* Sorts the specified range of the specified array of objects into
* ascending order, according to the
* {@linkplain Comparable natural ordering} of its
* elements. The range to be sorted extends from index
* {@code fromIndex}, inclusive, to index {@code toIndex}, exclusive.
* (If {@code fromIndex==toIndex}, the range to be sorted is empty.) All
* elements in this range must implement the {@link Comparable}
* interface. Furthermore, all elements in this range must be <i>mutually
* comparable</i> (that is, {@code e1.compareTo(e2)} must not throw a
* {@code ClassCastException} for any elements {@code e1} and
* {@code e2} in the array).
*
* <p>This sort is not guaranteed to be <i>stable</i>: equal elements
* may be reordered as a result of the sort.
*
* <p>Implementation note: The sorting algorithm is a parallel sort-merge
* that breaks the array into sub-arrays that are themselves sorted and then
* merged. When the sub-array length reaches a minimum granularity, the
* sub-array is sorted using the appropriate {@link Arrays#sort(Object[])
* Arrays.sort} method. The algorithm requires a working space equal to the
* size of the original array. The {@link
* java.util.concurrent.ForkJoinPool#commonPool() ForkJoin common pool} is
* used to execute any parallel tasks.
*
* @param a the array to be sorted
* @param fromIndex the index of the first element (inclusive) to be
* sorted
* @param toIndex the index of the last element (exclusive) to be sorted
* @throws IllegalArgumentException if {@code fromIndex > toIndex} or
* (optional) if the natural ordering of the array elements is
* found to violate the {@link Comparable} contract
* @throws ArrayIndexOutOfBoundsException if {@code fromIndex < 0} or
* {@code toIndex > a.length}
* @throws ClassCastException if the array contains elements that are
* not <i>mutually comparable</i> (for example, strings and
* integers).
*
* @since 1.8
*/
public static <T extends Comparable<? super T>>
void parallelSort(T[] a, int fromIndex, int toIndex) {
rangeCheck(a.length, fromIndex, toIndex);
int nelements = toIndex - fromIndex;
Class<?> tc = a.getClass().getComponentType();
@SuppressWarnings("unchecked")
T[] workspace = (T[])Array.newInstance(tc, a.length);
int gran = getSplitThreshold(nelements);
FJComparable.Sorter<T> task = new FJComparable.Sorter<>(a, workspace,
fromIndex,
nelements, gran);
task.invoke();
}
/**
* Sorts the specified array of objects according to the order induced by
* the specified comparator. All elements in the array must be
* <i>mutually comparable</i> by the specified comparator (that is,
* {@code c.compare(e1, e2)} must not throw a {@code ClassCastException}
* for any elements {@code e1} and {@code e2} in the array).
*
* <p>This sort is not guaranteed to be <i>stable</i>: equal elements
* may be reordered as a result of the sort.
*
* <p>Implementation note: The sorting algorithm is a parallel sort-merge
* that breaks the array into sub-arrays that are themselves sorted and then
* merged. When the sub-array length reaches a minimum granularity, the
* sub-array is sorted using the appropriate {@link Arrays#sort(Object[])
* Arrays.sort} method. The algorithm requires a working space equal to the
* size of the original array. The {@link
* java.util.concurrent.ForkJoinPool#commonPool() ForkJoin common pool} is
* used to execute any parallel tasks.
*
* @param a the array to be sorted
* @param c the comparator to determine the order of the array. A
* {@code null} value indicates that the elements'
* {@linkplain Comparable natural ordering} should be used.
* @throws ClassCastException if the array contains elements that are
* not <i>mutually comparable</i> using the specified comparator
* @throws IllegalArgumentException (optional) if the comparator is
* found to violate the {@link java.util.Comparator} contract
*
* @since 1.8
*/
public static <T> void parallelSort(T[] a, Comparator<? super T> c) {
parallelSort(a, 0, a.length, c);
}
/**
* Sorts the specified range of the specified array of objects according
* to the order induced by the specified comparator. The range to be
* sorted extends from index {@code fromIndex}, inclusive, to index
* {@code toIndex}, exclusive. (If {@code fromIndex==toIndex}, the
* range to be sorted is empty.) All elements in the range must be
* <i>mutually comparable</i> by the specified comparator (that is,
* {@code c.compare(e1, e2)} must not throw a {@code ClassCastException}
* for any elements {@code e1} and {@code e2} in the range).
*
* <p>This sort is not guaranteed to be <i>stable</i>: equal elements
* may be reordered as a result of the sort.
*
* <p>Implementation note: The sorting algorithm is a parallel sort-merge
* that breaks the array into sub-arrays that are themselves sorted and then
* merged. When the sub-array length reaches a minimum granularity, the
* sub-array is sorted using the appropriate {@link Arrays#sort(Object[])
* Arrays.sort} method. The algorithm requires a working space equal to the
* size of the original array. The {@link
* java.util.concurrent.ForkJoinPool#commonPool() ForkJoin common pool} is
* used to execute any parallel tasks.
*
* @param a the array to be sorted
* @param fromIndex the index of the first element (inclusive) to be
* sorted
* @param toIndex the index of the last element (exclusive) to be sorted
* @param c the comparator to determine the order of the array. A
* {@code null} value indicates that the elements'
* {@linkplain Comparable natural ordering} should be used.
* @throws IllegalArgumentException if {@code fromIndex > toIndex} or
* (optional) if the natural ordering of the array elements is
* found to violate the {@link Comparable} contract
* @throws ArrayIndexOutOfBoundsException if {@code fromIndex < 0} or
* {@code toIndex > a.length}
* @throws ClassCastException if the array contains elements that are
* not <i>mutually comparable</i> (for example, strings and
* integers).
*
* @since 1.8
*/
public static <T> void parallelSort(T[] a, int fromIndex, int toIndex,
Comparator<? super T> c) {
rangeCheck(a.length, fromIndex, toIndex);
int nelements = toIndex - fromIndex;
Class<?> tc = a.getClass().getComponentType();
@SuppressWarnings("unchecked")
T[] workspace = (T[])Array.newInstance(tc, a.length);
int gran = getSplitThreshold(nelements);
FJComparator.Sorter<T> task = new FJComparator.Sorter<>(a, workspace,
fromIndex,
nelements, gran, c);
task.invoke();
}
/**
* Returns the size threshold for splitting into subtasks.
* By default, uses about 8 times as many tasks as threads
*
* @param n number of elements in the array to be processed
*/
private static int getSplitThreshold(int n) {
int p = java.util.concurrent.ForkJoinPool.getCommonPoolParallelism();
int t = (p > 1) ? (1 + n / (p << 3)) : n;
return t < MIN_ARRAY_SORT_GRAN ? MIN_ARRAY_SORT_GRAN : t;
}
/**
* Checks that {@code fromIndex} and {@code toIndex} are in
* the range and throws an appropriate exception, if they aren't.
@ -1480,9 +2095,9 @@ public class Arrays {
while (low <= high) {
int mid = (low + high) >>> 1;
@SuppressWarnings("rawtypes")
Comparable midVal = (Comparable)a[mid];
Comparable midVal = (Comparable)a[mid];
@SuppressWarnings("unchecked")
int cmp = midVal.compareTo(key);
int cmp = midVal.compareTo(key);
if (cmp < 0)
low = mid + 1;
@ -2847,19 +3462,20 @@ public class Arrays {
private final E[] a;
ArrayList(E[] array) {
if (array==null)
throw new NullPointerException();
a = array;
a = Objects.requireNonNull(array);
}
@Override
public int size() {
return a.length;
}
@Override
public Object[] toArray() {
return a.clone();
}
@Override
@SuppressWarnings("unchecked")
public <T> T[] toArray(T[] a) {
int size = size();
@ -2872,16 +3488,19 @@ public class Arrays {
return a;
}
@Override
public E get(int index) {
return a[index];
}
@Override
public E set(int index, E element) {
E oldValue = a[index];
a[index] = element;
return oldValue;
}
@Override
public int indexOf(Object o) {
if (o==null) {
for (int i=0; i<a.length; i++)
@ -2895,6 +3514,7 @@ public class Arrays {
return -1;
}
@Override
public boolean contains(Object o) {
return indexOf(o) != -1;
}

File diff suppressed because it is too large Load diff

View file

@ -749,7 +749,7 @@ public abstract class Calendar implements Serializable, Cloneable, Comparable<Ca
*
* @see #NARROW_STANDALONE
* @see #SHORT_FORMAT
* @see #LONG_FOTMAT
* @see #LONG_FORMAT
* @since 1.8
*/
public static final int NARROW_FORMAT = 4;

View file

@ -1188,7 +1188,7 @@ class Properties extends Hashtable<Object,Object> {
provider = loadProviderAsService(cl);
if (provider != null)
return provider;
throw new InternalError("No fallback");
return new jdk.internal.util.xml.BasicXmlPropertiesProvider();
}});
}

View file

@ -0,0 +1,743 @@
/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
/*
* This file is available under and governed by the GNU General Public
* License version 2 only, as published by the Free Software Foundation.
* However, the following notice accompanied the original version of this
* file:
*
* Written by Doug Lea with assistance from members of JCP JSR-166
* Expert Group and released to the public domain, as explained at
* http://creativecommons.org/publicdomain/zero/1.0/
*/
package java.util.concurrent;
/**
* A {@link ForkJoinTask} with a completion action performed when
* triggered and there are no remaining pending
* actions. CountedCompleters are in general more robust in the
* presence of subtask stalls and blockage than are other forms of
* ForkJoinTasks, but are less intuitive to program. Uses of
* CountedCompleter are similar to those of other completion based
* components (such as {@link java.nio.channels.CompletionHandler})
* except that multiple <em>pending</em> completions may be necessary
* to trigger the completion action {@link #onCompletion}, not just one.
* Unless initialized otherwise, the {@linkplain #getPendingCount pending
* count} starts at zero, but may be (atomically) changed using
* methods {@link #setPendingCount}, {@link #addToPendingCount}, and
* {@link #compareAndSetPendingCount}. Upon invocation of {@link
* #tryComplete}, if the pending action count is nonzero, it is
* decremented; otherwise, the completion action is performed, and if
* this completer itself has a completer, the process is continued
* with its completer. As is the case with related synchronization
* components such as {@link java.util.concurrent.Phaser Phaser} and
* {@link java.util.concurrent.Semaphore Semaphore}, these methods
* affect only internal counts; they do not establish any further
* internal bookkeeping. In particular, the identities of pending
* tasks are not maintained. As illustrated below, you can create
* subclasses that do record some or all pending tasks or their
* results when needed. As illustrated below, utility methods
* supporting customization of completion traversals are also
* provided. However, because CountedCompleters provide only basic
* synchronization mechanisms, it may be useful to create further
* abstract subclasses that maintain linkages, fields, and additional
* support methods appropriate for a set of related usages.
*
* <p>A concrete CountedCompleter class must define method {@link
* #compute}, that should in most cases (as illustrated below), invoke
* {@code tryComplete()} once before returning. The class may also
* optionally override method {@link #onCompletion} to perform an
* action upon normal completion, and method {@link
* #onExceptionalCompletion} to perform an action upon any exception.
*
* <p>CountedCompleters most often do not bear results, in which case
* they are normally declared as {@code CountedCompleter<Void>}, and
* will always return {@code null} as a result value. In other cases,
* you should override method {@link #getRawResult} to provide a
* result from {@code join(), invoke()}, and related methods. In
* general, this method should return the value of a field (or a
* function of one or more fields) of the CountedCompleter object that
* holds the result upon completion. Method {@link #setRawResult} by
* default plays no role in CountedCompleters. It is possible, but
* rarely applicable, to override this method to maintain other
* objects or fields holding result data.
*
* <p>A CountedCompleter that does not itself have a completer (i.e.,
* one for which {@link #getCompleter} returns {@code null}) can be
* used as a regular ForkJoinTask with this added functionality.
* However, any completer that in turn has another completer serves
* only as an internal helper for other computations, so its own task
* status (as reported in methods such as {@link ForkJoinTask#isDone})
* is arbitrary; this status changes only upon explicit invocations of
* {@link #complete}, {@link ForkJoinTask#cancel}, {@link
* ForkJoinTask#completeExceptionally} or upon exceptional completion
* of method {@code compute}. Upon any exceptional completion, the
* exception may be relayed to a task's completer (and its completer,
* and so on), if one exists and it has not otherwise already
* completed. Similarly, cancelling an internal CountedCompleter has
* only a local effect on that completer, so is not often useful.
*
* <p><b>Sample Usages.</b>
*
* <p><b>Parallel recursive decomposition.</b> CountedCompleters may
* be arranged in trees similar to those often used with {@link
* RecursiveAction}s, although the constructions involved in setting
* them up typically vary. Here, the completer of each task is its
* parent in the computation tree. Even though they entail a bit more
* bookkeeping, CountedCompleters may be better choices when applying
* a possibly time-consuming operation (that cannot be further
* subdivided) to each element of an array or collection; especially
* when the operation takes a significantly different amount of time
* to complete for some elements than others, either because of
* intrinsic variation (for example I/O) or auxiliary effects such as
* garbage collection. Because CountedCompleters provide their own
* continuations, other threads need not block waiting to perform
* them.
*
* <p>For example, here is an initial version of a class that uses
* divide-by-two recursive decomposition to divide work into single
* pieces (leaf tasks). Even when work is split into individual calls,
* tree-based techniques are usually preferable to directly forking
* leaf tasks, because they reduce inter-thread communication and
* improve load balancing. In the recursive case, the second of each
* pair of subtasks to finish triggers completion of its parent
* (because no result combination is performed, the default no-op
* implementation of method {@code onCompletion} is not overridden). A
* static utility method sets up the base task and invokes it
* (here, implicitly using the {@link ForkJoinPool#commonPool()}).
*
* <pre> {@code
* class MyOperation<E> { void apply(E e) { ... } }
*
* class ForEach<E> extends CountedCompleter<Void> {
*
* public static <E> void forEach(E[] array, MyOperation<E> op) {
* new ForEach<E>(null, array, op, 0, array.length).invoke();
* }
*
* final E[] array; final MyOperation<E> op; final int lo, hi;
* ForEach(CountedCompleter<?> p, E[] array, MyOperation<E> op, int lo, int hi) {
* super(p);
* this.array = array; this.op = op; this.lo = lo; this.hi = hi;
* }
*
* public void compute() { // version 1
* if (hi - lo >= 2) {
* int mid = (lo + hi) >>> 1;
* setPendingCount(2); // must set pending count before fork
* new ForEach(this, array, op, mid, hi).fork(); // right child
* new ForEach(this, array, op, lo, mid).fork(); // left child
* }
* else if (hi > lo)
* op.apply(array[lo]);
* tryComplete();
* }
* }}</pre>
*
* This design can be improved by noticing that in the recursive case,
* the task has nothing to do after forking its right task, so can
* directly invoke its left task before returning. (This is an analog
* of tail recursion removal.) Also, because the task returns upon
* executing its left task (rather than falling through to invoke
* {@code tryComplete}) the pending count is set to one:
*
* <pre> {@code
* class ForEach<E> ...
* public void compute() { // version 2
* if (hi - lo >= 2) {
* int mid = (lo + hi) >>> 1;
* setPendingCount(1); // only one pending
* new ForEach(this, array, op, mid, hi).fork(); // right child
* new ForEach(this, array, op, lo, mid).compute(); // direct invoke
* }
* else {
* if (hi > lo)
* op.apply(array[lo]);
* tryComplete();
* }
* }
* }</pre>
*
* As a further improvement, notice that the left task need not even
* exist. Instead of creating a new one, we can iterate using the
* original task, and add a pending count for each fork. Additionally,
* because no task in this tree implements an {@link #onCompletion}
* method, {@code tryComplete()} can be replaced with {@link
* #propagateCompletion}.
*
* <pre> {@code
* class ForEach<E> ...
* public void compute() { // version 3
* int l = lo, h = hi;
* while (h - l >= 2) {
* int mid = (l + h) >>> 1;
* addToPendingCount(1);
* new ForEach(this, array, op, mid, h).fork(); // right child
* h = mid;
* }
* if (h > l)
* op.apply(array[l]);
* propagateCompletion();
* }
* }</pre>
*
* Additional improvements of such classes might entail precomputing
* pending counts so that they can be established in constructors,
* specializing classes for leaf steps, subdividing by say, four,
* instead of two per iteration, and using an adaptive threshold
* instead of always subdividing down to single elements.
*
* <p><b>Searching.</b> A tree of CountedCompleters can search for a
* value or property in different parts of a data structure, and
* report a result in an {@link
* java.util.concurrent.atomic.AtomicReference AtomicReference} as
* soon as one is found. The others can poll the result to avoid
* unnecessary work. (You could additionally {@linkplain #cancel
* cancel} other tasks, but it is usually simpler and more efficient
* to just let them notice that the result is set and if so skip
* further processing.) Illustrating again with an array using full
* partitioning (again, in practice, leaf tasks will almost always
* process more than one element):
*
* <pre> {@code
* class Searcher<E> extends CountedCompleter<E> {
* final E[] array; final AtomicReference<E> result; final int lo, hi;
* Searcher(CountedCompleter<?> p, E[] array, AtomicReference<E> result, int lo, int hi) {
* super(p);
* this.array = array; this.result = result; this.lo = lo; this.hi = hi;
* }
* public E getRawResult() { return result.get(); }
* public void compute() { // similar to ForEach version 3
* int l = lo, h = hi;
* while (result.get() == null && h >= l) {
* if (h - l >= 2) {
* int mid = (l + h) >>> 1;
* addToPendingCount(1);
* new Searcher(this, array, result, mid, h).fork();
* h = mid;
* }
* else {
* E x = array[l];
* if (matches(x) && result.compareAndSet(null, x))
* quietlyCompleteRoot(); // root task is now joinable
* break;
* }
* }
* tryComplete(); // normally complete whether or not found
* }
* boolean matches(E e) { ... } // return true if found
*
* public static <E> E search(E[] array) {
* return new Searcher<E>(null, array, new AtomicReference<E>(), 0, array.length).invoke();
* }
*}}</pre>
*
* In this example, as well as others in which tasks have no other
* effects except to compareAndSet a common result, the trailing
* unconditional invocation of {@code tryComplete} could be made
* conditional ({@code if (result.get() == null) tryComplete();})
* because no further bookkeeping is required to manage completions
* once the root task completes.
*
* <p><b>Recording subtasks.</b> CountedCompleter tasks that combine
* results of multiple subtasks usually need to access these results
* in method {@link #onCompletion}. As illustrated in the following
* class (that performs a simplified form of map-reduce where mappings
* and reductions are all of type {@code E}), one way to do this in
* divide and conquer designs is to have each subtask record its
* sibling, so that it can be accessed in method {@code onCompletion}.
* This technique applies to reductions in which the order of
* combining left and right results does not matter; ordered
* reductions require explicit left/right designations. Variants of
* other streamlinings seen in the above examples may also apply.
*
* <pre> {@code
* class MyMapper<E> { E apply(E v) { ... } }
* class MyReducer<E> { E apply(E x, E y) { ... } }
* class MapReducer<E> extends CountedCompleter<E> {
* final E[] array; final MyMapper<E> mapper;
* final MyReducer<E> reducer; final int lo, hi;
* MapReducer<E> sibling;
* E result;
* MapReducer(CountedCompleter<?> p, E[] array, MyMapper<E> mapper,
* MyReducer<E> reducer, int lo, int hi) {
* super(p);
* this.array = array; this.mapper = mapper;
* this.reducer = reducer; this.lo = lo; this.hi = hi;
* }
* public void compute() {
* if (hi - lo >= 2) {
* int mid = (lo + hi) >>> 1;
* MapReducer<E> left = new MapReducer(this, array, mapper, reducer, lo, mid);
* MapReducer<E> right = new MapReducer(this, array, mapper, reducer, mid, hi);
* left.sibling = right;
* right.sibling = left;
* setPendingCount(1); // only right is pending
* right.fork();
* left.compute(); // directly execute left
* }
* else {
* if (hi > lo)
* result = mapper.apply(array[lo]);
* tryComplete();
* }
* }
* public void onCompletion(CountedCompleter<?> caller) {
* if (caller != this) {
* MapReducer<E> child = (MapReducer<E>)caller;
* MapReducer<E> sib = child.sibling;
* if (sib == null || sib.result == null)
* result = child.result;
* else
* result = reducer.apply(child.result, sib.result);
* }
* }
* public E getRawResult() { return result; }
*
* public static <E> E mapReduce(E[] array, MyMapper<E> mapper, MyReducer<E> reducer) {
* return new MapReducer<E>(null, array, mapper, reducer,
* 0, array.length).invoke();
* }
* }}</pre>
*
* Here, method {@code onCompletion} takes a form common to many
* completion designs that combine results. This callback-style method
* is triggered once per task, in either of the two different contexts
* in which the pending count is, or becomes, zero: (1) by a task
* itself, if its pending count is zero upon invocation of {@code
* tryComplete}, or (2) by any of its subtasks when they complete and
* decrement the pending count to zero. The {@code caller} argument
* distinguishes cases. Most often, when the caller is {@code this},
* no action is necessary. Otherwise the caller argument can be used
* (usually via a cast) to supply a value (and/or links to other
* values) to be combined. Assuming proper use of pending counts, the
* actions inside {@code onCompletion} occur (once) upon completion of
* a task and its subtasks. No additional synchronization is required
* within this method to ensure thread safety of accesses to fields of
* this task or other completed tasks.
*
* <p><b>Completion Traversals</b>. If using {@code onCompletion} to
* process completions is inapplicable or inconvenient, you can use
* methods {@link #firstComplete} and {@link #nextComplete} to create
* custom traversals. For example, to define a MapReducer that only
* splits out right-hand tasks in the form of the third ForEach
* example, the completions must cooperatively reduce along
* unexhausted subtask links, which can be done as follows:
*
* <pre> {@code
* class MapReducer<E> extends CountedCompleter<E> { // version 2
* final E[] array; final MyMapper<E> mapper;
* final MyReducer<E> reducer; final int lo, hi;
* MapReducer<E> forks, next; // record subtask forks in list
* E result;
* MapReducer(CountedCompleter<?> p, E[] array, MyMapper<E> mapper,
* MyReducer<E> reducer, int lo, int hi, MapReducer<E> next) {
* super(p);
* this.array = array; this.mapper = mapper;
* this.reducer = reducer; this.lo = lo; this.hi = hi;
* this.next = next;
* }
* public void compute() {
* int l = lo, h = hi;
* while (h - l >= 2) {
* int mid = (l + h) >>> 1;
* addToPendingCount(1);
* (forks = new MapReducer(this, array, mapper, reducer, mid, h, forks)).fork;
* h = mid;
* }
* if (h > l)
* result = mapper.apply(array[l]);
* // process completions by reducing along and advancing subtask links
* for (CountedCompleter<?> c = firstComplete(); c != null; c = c.nextComplete()) {
* for (MapReducer t = (MapReducer)c, s = t.forks; s != null; s = t.forks = s.next)
* t.result = reducer.apply(t.result, s.result);
* }
* }
* public E getRawResult() { return result; }
*
* public static <E> E mapReduce(E[] array, MyMapper<E> mapper, MyReducer<E> reducer) {
* return new MapReducer<E>(null, array, mapper, reducer,
* 0, array.length, null).invoke();
* }
* }}</pre>
*
* <p><b>Triggers.</b> Some CountedCompleters are themselves never
* forked, but instead serve as bits of plumbing in other designs;
* including those in which the completion of one of more async tasks
* triggers another async task. For example:
*
* <pre> {@code
* class HeaderBuilder extends CountedCompleter<...> { ... }
* class BodyBuilder extends CountedCompleter<...> { ... }
* class PacketSender extends CountedCompleter<...> {
* PacketSender(...) { super(null, 1); ... } // trigger on second completion
* public void compute() { } // never called
* public void onCompletion(CountedCompleter<?> caller) { sendPacket(); }
* }
* // sample use:
* PacketSender p = new PacketSender();
* new HeaderBuilder(p, ...).fork();
* new BodyBuilder(p, ...).fork();
* }</pre>
*
* @since 1.8
* @author Doug Lea
*/
public abstract class CountedCompleter<T> extends ForkJoinTask<T> {
private static final long serialVersionUID = 5232453752276485070L;
/** This task's completer, or null if none */
final CountedCompleter<?> completer;
/** The number of pending tasks until completion */
volatile int pending;
/**
* Creates a new CountedCompleter with the given completer
* and initial pending count.
*
* @param completer this task's completer, or {@code null} if none
* @param initialPendingCount the initial pending count
*/
protected CountedCompleter(CountedCompleter<?> completer,
int initialPendingCount) {
this.completer = completer;
this.pending = initialPendingCount;
}
/**
* Creates a new CountedCompleter with the given completer
* and an initial pending count of zero.
*
* @param completer this task's completer, or {@code null} if none
*/
protected CountedCompleter(CountedCompleter<?> completer) {
this.completer = completer;
}
/**
* Creates a new CountedCompleter with no completer
* and an initial pending count of zero.
*/
protected CountedCompleter() {
this.completer = null;
}
/**
* The main computation performed by this task.
*/
public abstract void compute();
/**
* Performs an action when method {@link #tryComplete} is invoked
* and the pending count is zero, or when the unconditional
* method {@link #complete} is invoked. By default, this method
* does nothing. You can distinguish cases by checking the
* identity of the given caller argument. If not equal to {@code
* this}, then it is typically a subtask that may contain results
* (and/or links to other results) to combine.
*
* @param caller the task invoking this method (which may
* be this task itself).
*/
public void onCompletion(CountedCompleter<?> caller) {
}
/**
* Performs an action when method {@link #completeExceptionally}
* is invoked or method {@link #compute} throws an exception, and
* this task has not otherwise already completed normally. On
* entry to this method, this task {@link
* ForkJoinTask#isCompletedAbnormally}. The return value of this
* method controls further propagation: If {@code true} and this
* task has a completer, then this completer is also completed
* exceptionally. The default implementation of this method does
* nothing except return {@code true}.
*
* @param ex the exception
* @param caller the task invoking this method (which may
* be this task itself).
* @return true if this exception should be propagated to this
* task's completer, if one exists.
*/
public boolean onExceptionalCompletion(Throwable ex, CountedCompleter<?> caller) {
return true;
}
/**
* Returns the completer established in this task's constructor,
* or {@code null} if none.
*
* @return the completer
*/
public final CountedCompleter<?> getCompleter() {
return completer;
}
/**
* Returns the current pending count.
*
* @return the current pending count
*/
public final int getPendingCount() {
return pending;
}
/**
* Sets the pending count to the given value.
*
* @param count the count
*/
public final void setPendingCount(int count) {
pending = count;
}
/**
* Adds (atomically) the given value to the pending count.
*
* @param delta the value to add
*/
public final void addToPendingCount(int delta) {
int c; // note: can replace with intrinsic in jdk8
do {} while (!U.compareAndSwapInt(this, PENDING, c = pending, c+delta));
}
/**
* Sets (atomically) the pending count to the given count only if
* it currently holds the given expected value.
*
* @param expected the expected value
* @param count the new value
* @return true if successful
*/
public final boolean compareAndSetPendingCount(int expected, int count) {
return U.compareAndSwapInt(this, PENDING, expected, count);
}
/**
* If the pending count is nonzero, (atomically) decrements it.
*
* @return the initial (undecremented) pending count holding on entry
* to this method
*/
public final int decrementPendingCountUnlessZero() {
int c;
do {} while ((c = pending) != 0 &&
!U.compareAndSwapInt(this, PENDING, c, c - 1));
return c;
}
/**
* Returns the root of the current computation; i.e., this
* task if it has no completer, else its completer's root.
*
* @return the root of the current computation
*/
public final CountedCompleter<?> getRoot() {
CountedCompleter<?> a = this, p;
while ((p = a.completer) != null)
a = p;
return a;
}
/**
* If the pending count is nonzero, decrements the count;
* otherwise invokes {@link #onCompletion} and then similarly
* tries to complete this task's completer, if one exists,
* else marks this task as complete.
*/
public final void tryComplete() {
CountedCompleter<?> a = this, s = a;
for (int c;;) {
if ((c = a.pending) == 0) {
a.onCompletion(s);
if ((a = (s = a).completer) == null) {
s.quietlyComplete();
return;
}
}
else if (U.compareAndSwapInt(a, PENDING, c, c - 1))
return;
}
}
/**
* Equivalent to {@link #tryComplete} but does not invoke {@link
* #onCompletion} along the completion path: If the pending count
* is nonzero, decrements the count; otherwise, similarly tries to
* complete this task's completer, if one exists, else marks this
* task as complete. This method may be useful in cases where
* {@code onCompletion} should not, or need not, be invoked for
* each completer in a computation.
*/
public final void propagateCompletion() {
CountedCompleter<?> a = this, s = a;
for (int c;;) {
if ((c = a.pending) == 0) {
if ((a = (s = a).completer) == null) {
s.quietlyComplete();
return;
}
}
else if (U.compareAndSwapInt(a, PENDING, c, c - 1))
return;
}
}
/**
* Regardless of pending count, invokes {@link #onCompletion},
* marks this task as complete and further triggers {@link
* #tryComplete} on this task's completer, if one exists. The
* given rawResult is used as an argument to {@link #setRawResult}
* before invoking {@link #onCompletion} or marking this task as
* complete; its value is meaningful only for classes overriding
* {@code setRawResult}.
*
* <p>This method may be useful when forcing completion as soon as
* any one (versus all) of several subtask results are obtained.
* However, in the common (and recommended) case in which {@code
* setRawResult} is not overridden, this effect can be obtained
* more simply using {@code quietlyCompleteRoot();}.
*
* @param rawResult the raw result
*/
public void complete(T rawResult) {
CountedCompleter<?> p;
setRawResult(rawResult);
onCompletion(this);
quietlyComplete();
if ((p = completer) != null)
p.tryComplete();
}
/**
* If this task's pending count is zero, returns this task;
* otherwise decrements its pending count and returns {@code
* null}. This method is designed to be used with {@link
* #nextComplete} in completion traversal loops.
*
* @return this task, if pending count was zero, else {@code null}
*/
public final CountedCompleter<?> firstComplete() {
for (int c;;) {
if ((c = pending) == 0)
return this;
else if (U.compareAndSwapInt(this, PENDING, c, c - 1))
return null;
}
}
/**
* If this task does not have a completer, invokes {@link
* ForkJoinTask#quietlyComplete} and returns {@code null}. Or, if
* this task's pending count is non-zero, decrements its pending
* count and returns {@code null}. Otherwise, returns the
* completer. This method can be used as part of a completion
* traversal loop for homogeneous task hierarchies:
*
* <pre> {@code
* for (CountedCompleter<?> c = firstComplete();
* c != null;
* c = c.nextComplete()) {
* // ... process c ...
* }}</pre>
*
* @return the completer, or {@code null} if none
*/
public final CountedCompleter<?> nextComplete() {
CountedCompleter<?> p;
if ((p = completer) != null)
return p.firstComplete();
else {
quietlyComplete();
return null;
}
}
/**
* Equivalent to {@code getRoot().quietlyComplete()}.
*/
public final void quietlyCompleteRoot() {
for (CountedCompleter<?> a = this, p;;) {
if ((p = a.completer) == null) {
a.quietlyComplete();
return;
}
a = p;
}
}
/**
* Supports ForkJoinTask exception propagation.
*/
void internalPropagateException(Throwable ex) {
CountedCompleter<?> a = this, s = a;
while (a.onExceptionalCompletion(ex, s) &&
(a = (s = a).completer) != null && a.status >= 0)
a.recordExceptionalCompletion(ex);
}
/**
* Implements execution conventions for CountedCompleters.
*/
protected final boolean exec() {
compute();
return false;
}
/**
* Returns the result of the computation. By default
* returns {@code null}, which is appropriate for {@code Void}
* actions, but in other cases should be overridden, almost
* always to return a field or function of a field that
* holds the result upon completion.
*
* @return the result of the computation
*/
public T getRawResult() { return null; }
/**
* A method that result-bearing CountedCompleters may optionally
* use to help maintain result data. By default, does nothing.
* Overrides are not recommended. However, if this method is
* overridden to update existing objects or fields, then it must
* in general be defined to be thread-safe.
*/
protected void setRawResult(T t) { }
// Unsafe mechanics
private static final sun.misc.Unsafe U;
private static final long PENDING;
static {
try {
U = sun.misc.Unsafe.getUnsafe();
PENDING = U.objectFieldOffset
(CountedCompleter.class.getDeclaredField("pending"));
} catch (Exception e) {
throw new Error(e);
}
}
}

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

View file

@ -35,9 +35,6 @@
package java.util.concurrent;
import java.util.Collection;
import java.util.concurrent.RejectedExecutionException;
/**
* A thread managed by a {@link ForkJoinPool}, which executes
* {@link ForkJoinTask}s.
@ -54,238 +51,20 @@ import java.util.concurrent.RejectedExecutionException;
*/
public class ForkJoinWorkerThread extends Thread {
/*
* Overview:
*
* ForkJoinWorkerThreads are managed by ForkJoinPools and perform
* ForkJoinTasks. This class includes bookkeeping in support of
* worker activation, suspension, and lifecycle control described
* in more detail in the internal documentation of class
* ForkJoinPool. And as described further below, this class also
* includes special-cased support for some ForkJoinTask
* methods. But the main mechanics involve work-stealing:
* ForkJoinTasks. For explanation, see the internal documentation
* of class ForkJoinPool.
*
* Work-stealing queues are special forms of Deques that support
* only three of the four possible end-operations -- push, pop,
* and deq (aka steal), under the further constraints that push
* and pop are called only from the owning thread, while deq may
* be called from other threads. (If you are unfamiliar with
* them, you probably want to read Herlihy and Shavit's book "The
* Art of Multiprocessor programming", chapter 16 describing these
* in more detail before proceeding.) The main work-stealing
* queue design is roughly similar to those in the papers "Dynamic
* Circular Work-Stealing Deque" by Chase and Lev, SPAA 2005
* (http://research.sun.com/scalable/pubs/index.html) and
* "Idempotent work stealing" by Michael, Saraswat, and Vechev,
* PPoPP 2009 (http://portal.acm.org/citation.cfm?id=1504186).
* The main differences ultimately stem from gc requirements that
* we null out taken slots as soon as we can, to maintain as small
* a footprint as possible even in programs generating huge
* numbers of tasks. To accomplish this, we shift the CAS
* arbitrating pop vs deq (steal) from being on the indices
* ("queueBase" and "queueTop") to the slots themselves (mainly
* via method "casSlotNull()"). So, both a successful pop and deq
* mainly entail a CAS of a slot from non-null to null. Because
* we rely on CASes of references, we do not need tag bits on
* queueBase or queueTop. They are simple ints as used in any
* circular array-based queue (see for example ArrayDeque).
* Updates to the indices must still be ordered in a way that
* guarantees that queueTop == queueBase means the queue is empty,
* but otherwise may err on the side of possibly making the queue
* appear nonempty when a push, pop, or deq have not fully
* committed. Note that this means that the deq operation,
* considered individually, is not wait-free. One thief cannot
* successfully continue until another in-progress one (or, if
* previously empty, a push) completes. However, in the
* aggregate, we ensure at least probabilistic non-blockingness.
* If an attempted steal fails, a thief always chooses a different
* random victim target to try next. So, in order for one thief to
* progress, it suffices for any in-progress deq or new push on
* any empty queue to complete.
*
* This approach also enables support for "async mode" where local
* task processing is in FIFO, not LIFO order; simply by using a
* version of deq rather than pop when locallyFifo is true (as set
* by the ForkJoinPool). This allows use in message-passing
* frameworks in which tasks are never joined. However neither
* mode considers affinities, loads, cache localities, etc, so
* rarely provide the best possible performance on a given
* machine, but portably provide good throughput by averaging over
* these factors. (Further, even if we did try to use such
* information, we do not usually have a basis for exploiting
* it. For example, some sets of tasks profit from cache
* affinities, but others are harmed by cache pollution effects.)
*
* When a worker would otherwise be blocked waiting to join a
* task, it first tries a form of linear helping: Each worker
* records (in field currentSteal) the most recent task it stole
* from some other worker. Plus, it records (in field currentJoin)
* the task it is currently actively joining. Method joinTask uses
* these markers to try to find a worker to help (i.e., steal back
* a task from and execute it) that could hasten completion of the
* actively joined task. In essence, the joiner executes a task
* that would be on its own local deque had the to-be-joined task
* not been stolen. This may be seen as a conservative variant of
* the approach in Wagner & Calder "Leapfrogging: a portable
* technique for implementing efficient futures" SIGPLAN Notices,
* 1993 (http://portal.acm.org/citation.cfm?id=155354). It differs
* in that: (1) We only maintain dependency links across workers
* upon steals, rather than use per-task bookkeeping. This may
* require a linear scan of workers array to locate stealers, but
* usually doesn't because stealers leave hints (that may become
* stale/wrong) of where to locate them. This isolates cost to
* when it is needed, rather than adding to per-task overhead.
* (2) It is "shallow", ignoring nesting and potentially cyclic
* mutual steals. (3) It is intentionally racy: field currentJoin
* is updated only while actively joining, which means that we
* miss links in the chain during long-lived tasks, GC stalls etc
* (which is OK since blocking in such cases is usually a good
* idea). (4) We bound the number of attempts to find work (see
* MAX_HELP) and fall back to suspending the worker and if
* necessary replacing it with another.
*
* Efficient implementation of these algorithms currently relies
* on an uncomfortable amount of "Unsafe" mechanics. To maintain
* correct orderings, reads and writes of variable queueBase
* require volatile ordering. Variable queueTop need not be
* volatile because non-local reads always follow those of
* queueBase. Similarly, because they are protected by volatile
* queueBase reads, reads of the queue array and its slots by
* other threads do not need volatile load semantics, but writes
* (in push) require store order and CASes (in pop and deq)
* require (volatile) CAS semantics. (Michael, Saraswat, and
* Vechev's algorithm has similar properties, but without support
* for nulling slots.) Since these combinations aren't supported
* using ordinary volatiles, the only way to accomplish these
* efficiently is to use direct Unsafe calls. (Using external
* AtomicIntegers and AtomicReferenceArrays for the indices and
* array is significantly slower because of memory locality and
* indirection effects.)
*
* Further, performance on most platforms is very sensitive to
* placement and sizing of the (resizable) queue array. Even
* though these queues don't usually become all that big, the
* initial size must be large enough to counteract cache
* contention effects across multiple queues (especially in the
* presence of GC cardmarking). Also, to improve thread-locality,
* queues are initialized after starting.
* This class just maintains links to its pool and WorkQueue. The
* pool field is set immediately upon construction, but the
* workQueue field is not set until a call to registerWorker
* completes. This leads to a visibility race, that is tolerated
* by requiring that the workQueue field is only accessed by the
* owning thread.
*/
/**
* Mask for pool indices encoded as shorts
*/
private static final int SMASK = 0xffff;
/**
* Capacity of work-stealing queue array upon initialization.
* Must be a power of two. Initial size must be at least 4, but is
* padded to minimize cache effects.
*/
private static final int INITIAL_QUEUE_CAPACITY = 1 << 13;
/**
* Maximum size for queue array. Must be a power of two
* less than or equal to 1 << (31 - width of array entry) to
* ensure lack of index wraparound, but is capped at a lower
* value to help users trap runaway computations.
*/
private static final int MAXIMUM_QUEUE_CAPACITY = 1 << 24; // 16M
/**
* The work-stealing queue array. Size must be a power of two.
* Initialized when started (as opposed to when constructed), to
* improve memory locality.
*/
ForkJoinTask<?>[] queue;
/**
* The pool this thread works in. Accessed directly by ForkJoinTask.
*/
final ForkJoinPool pool;
/**
* Index (mod queue.length) of next queue slot to push to or pop
* from. It is written only by owner thread, and accessed by other
* threads only after reading (volatile) queueBase. Both queueTop
* and queueBase are allowed to wrap around on overflow, but
* (queueTop - queueBase) still estimates size.
*/
int queueTop;
/**
* Index (mod queue.length) of least valid queue slot, which is
* always the next position to steal from if nonempty.
*/
volatile int queueBase;
/**
* The index of most recent stealer, used as a hint to avoid
* traversal in method helpJoinTask. This is only a hint because a
* worker might have had multiple steals and this only holds one
* of them (usually the most current). Declared non-volatile,
* relying on other prevailing sync to keep reasonably current.
*/
int stealHint;
/**
* Index of this worker in pool array. Set once by pool before
* running, and accessed directly by pool to locate this worker in
* its workers array.
*/
final int poolIndex;
/**
* Encoded record for pool task waits. Usages are always
* surrounded by volatile reads/writes
*/
int nextWait;
/**
* Complement of poolIndex, offset by count of entries of task
* waits. Accessed by ForkJoinPool to manage event waiters.
*/
volatile int eventCount;
/**
* Seed for random number generator for choosing steal victims.
* Uses Marsaglia xorshift. Must be initialized as nonzero.
*/
int seed;
/**
* Number of steals. Directly accessed (and reset) by pool when
* idle.
*/
int stealCount;
/**
* True if this worker should or did terminate
*/
volatile boolean terminate;
/**
* Set to true before LockSupport.park; false on return
*/
volatile boolean parked;
/**
* True if use local fifo, not default lifo, for local polling.
* Shadows value from ForkJoinPool.
*/
final boolean locallyFifo;
/**
* The task most recently stolen from another worker (or
* submission queue). All uses are surrounded by enough volatile
* reads/writes to maintain as non-volatile.
*/
ForkJoinTask<?> currentSteal;
/**
* The task currently being joined, set only when actively trying
* to help other stealers in helpJoinTask. All uses are surrounded
* by enough volatile reads/writes to maintain as non-volatile.
*/
ForkJoinTask<?> currentJoin;
final ForkJoinPool pool; // the pool this thread works in
final ForkJoinPool.WorkQueue workQueue; // work-stealing mechanics
/**
* Creates a ForkJoinWorkerThread operating in the given pool.
@ -294,20 +73,12 @@ public class ForkJoinWorkerThread extends Thread {
* @throws NullPointerException if pool is null
*/
protected ForkJoinWorkerThread(ForkJoinPool pool) {
super(pool.nextWorkerName());
// Use a placeholder until a useful name can be set in registerWorker
super("aForkJoinWorkerThread");
this.pool = pool;
int k = pool.registerWorker(this);
poolIndex = k;
eventCount = ~k & SMASK; // clear wait count
locallyFifo = pool.locallyFifo;
Thread.UncaughtExceptionHandler ueh = pool.ueh;
if (ueh != null)
setUncaughtExceptionHandler(ueh);
setDaemon(true);
this.workQueue = pool.registerWorker(this);
}
// Public methods
/**
* Returns the pool hosting this thread.
*
@ -327,28 +98,9 @@ public class ForkJoinWorkerThread extends Thread {
* @return the index number
*/
public int getPoolIndex() {
return poolIndex;
return workQueue.poolIndex;
}
// Randomization
/**
* Computes next value for random victim probes and backoffs.
* Scans don't require a very high quality generator, but also not
* a crummy one. Marsaglia xor-shift is cheap and works well
* enough. Note: This is manually inlined in FJP.scan() to avoid
* writes inside busy loops.
*/
private int nextSeed() {
int r = seed;
r ^= r << 13;
r ^= r >>> 17;
r ^= r << 5;
return seed = r;
}
// Run State management
/**
* Initializes internal state after construction but before
* processing any tasks. If you override this method, you must
@ -359,9 +111,6 @@ public class ForkJoinWorkerThread extends Thread {
* processing tasks.
*/
protected void onStart() {
queue = new ForkJoinTask<?>[INITIAL_QUEUE_CAPACITY];
int r = ForkJoinPool.workerSeedGenerator.nextInt();
seed = (r == 0) ? 1 : r; // must be nonzero
}
/**
@ -373,17 +122,6 @@ public class ForkJoinWorkerThread extends Thread {
* to an unrecoverable error, or {@code null} if completed normally
*/
protected void onTermination(Throwable exception) {
try {
terminate = true;
cancelTasks();
pool.deregisterWorker(this, exception);
} catch (Throwable ex) { // Shouldn't ever happen
if (exception == null) // but if so, at least rethrown
exception = ex;
} finally {
if (exception != null)
UNSAFE.throwException(exception);
}
}
/**
@ -395,604 +133,18 @@ public class ForkJoinWorkerThread extends Thread {
Throwable exception = null;
try {
onStart();
pool.work(this);
pool.runWorker(workQueue);
} catch (Throwable ex) {
exception = ex;
} finally {
onTermination(exception);
}
}
/*
* Intrinsics-based atomic writes for queue slots. These are
* basically the same as methods in AtomicReferenceArray, but
* specialized for (1) ForkJoinTask elements (2) requirement that
* nullness and bounds checks have already been performed by
* callers and (3) effective offsets are known not to overflow
* from int to long (because of MAXIMUM_QUEUE_CAPACITY). We don't
* need corresponding version for reads: plain array reads are OK
* because they are protected by other volatile reads and are
* confirmed by CASes.
*
* Most uses don't actually call these methods, but instead
* contain inlined forms that enable more predictable
* optimization. We don't define the version of write used in
* pushTask at all, but instead inline there a store-fenced array
* slot write.
*
* Also in most methods, as a performance (not correctness) issue,
* we'd like to encourage compilers not to arbitrarily postpone
* setting queueTop after writing slot. Currently there is no
* intrinsic for arranging this, but using Unsafe putOrderedInt
* may be a preferable strategy on some compilers even though its
* main effect is a pre-, not post- fence. To simplify possible
* changes, the option is left in comments next to the associated
* assignments.
*/
/**
* CASes slot i of array q from t to null. Caller must ensure q is
* non-null and index is in range.
*/
private static final boolean casSlotNull(ForkJoinTask<?>[] q, int i,
ForkJoinTask<?> t) {
return UNSAFE.compareAndSwapObject(q, (i << ASHIFT) + ABASE, t, null);
}
/**
* Performs a volatile write of the given task at given slot of
* array q. Caller must ensure q is non-null and index is in
* range. This method is used only during resets and backouts.
*/
private static final void writeSlot(ForkJoinTask<?>[] q, int i,
ForkJoinTask<?> t) {
UNSAFE.putObjectVolatile(q, (i << ASHIFT) + ABASE, t);
}
// queue methods
/**
* Pushes a task. Call only from this thread.
*
* @param t the task. Caller must ensure non-null.
*/
final void pushTask(ForkJoinTask<?> t) {
ForkJoinTask<?>[] q; int s, m;
if ((q = queue) != null) { // ignore if queue removed
long u = (((s = queueTop) & (m = q.length - 1)) << ASHIFT) + ABASE;
UNSAFE.putOrderedObject(q, u, t);
queueTop = s + 1; // or use putOrderedInt
if ((s -= queueBase) <= 2)
pool.signalWork();
else if (s == m)
growQueue();
}
}
/**
* Creates or doubles queue array. Transfers elements by
* emulating steals (deqs) from old array and placing, oldest
* first, into new array.
*/
private void growQueue() {
ForkJoinTask<?>[] oldQ = queue;
int size = oldQ != null ? oldQ.length << 1 : INITIAL_QUEUE_CAPACITY;
if (size > MAXIMUM_QUEUE_CAPACITY)
throw new RejectedExecutionException("Queue capacity exceeded");
if (size < INITIAL_QUEUE_CAPACITY)
size = INITIAL_QUEUE_CAPACITY;
ForkJoinTask<?>[] q = queue = new ForkJoinTask<?>[size];
int mask = size - 1;
int top = queueTop;
int oldMask;
if (oldQ != null && (oldMask = oldQ.length - 1) >= 0) {
for (int b = queueBase; b != top; ++b) {
long u = ((b & oldMask) << ASHIFT) + ABASE;
Object x = UNSAFE.getObjectVolatile(oldQ, u);
if (x != null && UNSAFE.compareAndSwapObject(oldQ, u, x, null))
UNSAFE.putObjectVolatile
(q, ((b & mask) << ASHIFT) + ABASE, x);
try {
onTermination(exception);
} catch (Throwable ex) {
if (exception == null)
exception = ex;
} finally {
pool.deregisterWorker(this, exception);
}
}
}
/**
* Tries to take a task from the base of the queue, failing if
* empty or contended. Note: Specializations of this code appear
* in locallyDeqTask and elsewhere.
*
* @return a task, or null if none or contended
*/
final ForkJoinTask<?> deqTask() {
ForkJoinTask<?> t; ForkJoinTask<?>[] q; int b, i;
if (queueTop != (b = queueBase) &&
(q = queue) != null && // must read q after b
(i = (q.length - 1) & b) >= 0 &&
(t = q[i]) != null && queueBase == b &&
UNSAFE.compareAndSwapObject(q, (i << ASHIFT) + ABASE, t, null)) {
queueBase = b + 1;
return t;
}
return null;
}
/**
* Tries to take a task from the base of own queue. Called only
* by this thread.
*
* @return a task, or null if none
*/
final ForkJoinTask<?> locallyDeqTask() {
ForkJoinTask<?> t; int m, b, i;
ForkJoinTask<?>[] q = queue;
if (q != null && (m = q.length - 1) >= 0) {
while (queueTop != (b = queueBase)) {
if ((t = q[i = m & b]) != null &&
queueBase == b &&
UNSAFE.compareAndSwapObject(q, (i << ASHIFT) + ABASE,
t, null)) {
queueBase = b + 1;
return t;
}
}
}
return null;
}
/**
* Returns a popped task, or null if empty.
* Called only by this thread.
*/
private ForkJoinTask<?> popTask() {
int m;
ForkJoinTask<?>[] q = queue;
if (q != null && (m = q.length - 1) >= 0) {
for (int s; (s = queueTop) != queueBase;) {
int i = m & --s;
long u = (i << ASHIFT) + ABASE; // raw offset
ForkJoinTask<?> t = q[i];
if (t == null) // lost to stealer
break;
if (UNSAFE.compareAndSwapObject(q, u, t, null)) {
queueTop = s; // or putOrderedInt
return t;
}
}
}
return null;
}
/**
* Specialized version of popTask to pop only if topmost element
* is the given task. Called only by this thread.
*
* @param t the task. Caller must ensure non-null.
*/
final boolean unpushTask(ForkJoinTask<?> t) {
ForkJoinTask<?>[] q;
int s;
if ((q = queue) != null && (s = queueTop) != queueBase &&
UNSAFE.compareAndSwapObject
(q, (((q.length - 1) & --s) << ASHIFT) + ABASE, t, null)) {
queueTop = s; // or putOrderedInt
return true;
}
return false;
}
/**
* Returns next task, or null if empty or contended.
*/
final ForkJoinTask<?> peekTask() {
int m;
ForkJoinTask<?>[] q = queue;
if (q == null || (m = q.length - 1) < 0)
return null;
int i = locallyFifo ? queueBase : (queueTop - 1);
return q[i & m];
}
// Support methods for ForkJoinPool
/**
* Runs the given task, plus any local tasks until queue is empty
*/
final void execTask(ForkJoinTask<?> t) {
currentSteal = t;
for (;;) {
if (t != null)
t.doExec();
if (queueTop == queueBase)
break;
t = locallyFifo ? locallyDeqTask() : popTask();
}
++stealCount;
currentSteal = null;
}
/**
* Removes and cancels all tasks in queue. Can be called from any
* thread.
*/
final void cancelTasks() {
ForkJoinTask<?> cj = currentJoin; // try to cancel ongoing tasks
if (cj != null && cj.status >= 0)
cj.cancelIgnoringExceptions();
ForkJoinTask<?> cs = currentSteal;
if (cs != null && cs.status >= 0)
cs.cancelIgnoringExceptions();
while (queueBase != queueTop) {
ForkJoinTask<?> t = deqTask();
if (t != null)
t.cancelIgnoringExceptions();
}
}
/**
* Drains tasks to given collection c.
*
* @return the number of tasks drained
*/
final int drainTasksTo(Collection<? super ForkJoinTask<?>> c) {
int n = 0;
while (queueBase != queueTop) {
ForkJoinTask<?> t = deqTask();
if (t != null) {
c.add(t);
++n;
}
}
return n;
}
// Support methods for ForkJoinTask
/**
* Returns an estimate of the number of tasks in the queue.
*/
final int getQueueSize() {
return queueTop - queueBase;
}
/**
* Gets and removes a local task.
*
* @return a task, if available
*/
final ForkJoinTask<?> pollLocalTask() {
return locallyFifo ? locallyDeqTask() : popTask();
}
/**
* Gets and removes a local or stolen task.
*
* @return a task, if available
*/
final ForkJoinTask<?> pollTask() {
ForkJoinWorkerThread[] ws;
ForkJoinTask<?> t = pollLocalTask();
if (t != null || (ws = pool.workers) == null)
return t;
int n = ws.length; // cheap version of FJP.scan
int steps = n << 1;
int r = nextSeed();
int i = 0;
while (i < steps) {
ForkJoinWorkerThread w = ws[(i++ + r) & (n - 1)];
if (w != null && w.queueBase != w.queueTop && w.queue != null) {
if ((t = w.deqTask()) != null)
return t;
i = 0;
}
}
return null;
}
/**
* The maximum stolen->joining link depth allowed in helpJoinTask,
* as well as the maximum number of retries (allowing on average
* one staleness retry per level) per attempt to instead try
* compensation. Depths for legitimate chains are unbounded, but
* we use a fixed constant to avoid (otherwise unchecked) cycles
* and bound staleness of traversal parameters at the expense of
* sometimes blocking when we could be helping.
*/
private static final int MAX_HELP = 16;
/**
* Possibly runs some tasks and/or blocks, until joinMe is done.
*
* @param joinMe the task to join
* @return completion status on exit
*/
final int joinTask(ForkJoinTask<?> joinMe) {
ForkJoinTask<?> prevJoin = currentJoin;
currentJoin = joinMe;
for (int s, retries = MAX_HELP;;) {
if ((s = joinMe.status) < 0) {
currentJoin = prevJoin;
return s;
}
if (retries > 0) {
if (queueTop != queueBase) {
if (!localHelpJoinTask(joinMe))
retries = 0; // cannot help
}
else if (retries == MAX_HELP >>> 1) {
--retries; // check uncommon case
if (tryDeqAndExec(joinMe) >= 0)
Thread.yield(); // for politeness
}
else
retries = helpJoinTask(joinMe) ? MAX_HELP : retries - 1;
}
else {
retries = MAX_HELP; // restart if not done
pool.tryAwaitJoin(joinMe);
}
}
}
/**
* If present, pops and executes the given task, or any other
* cancelled task
*
* @return false if any other non-cancelled task exists in local queue
*/
private boolean localHelpJoinTask(ForkJoinTask<?> joinMe) {
int s, i; ForkJoinTask<?>[] q; ForkJoinTask<?> t;
if ((s = queueTop) != queueBase && (q = queue) != null &&
(i = (q.length - 1) & --s) >= 0 &&
(t = q[i]) != null) {
if (t != joinMe && t.status >= 0)
return false;
if (UNSAFE.compareAndSwapObject
(q, (i << ASHIFT) + ABASE, t, null)) {
queueTop = s; // or putOrderedInt
t.doExec();
}
}
return true;
}
/**
* Tries to locate and execute tasks for a stealer of the given
* task, or in turn one of its stealers, Traces
* currentSteal->currentJoin links looking for a thread working on
* a descendant of the given task and with a non-empty queue to
* steal back and execute tasks from. The implementation is very
* branchy to cope with potential inconsistencies or loops
* encountering chains that are stale, unknown, or of length
* greater than MAX_HELP links. All of these cases are dealt with
* by just retrying by caller.
*
* @param joinMe the task to join
* @param canSteal true if local queue is empty
* @return true if ran a task
*/
private boolean helpJoinTask(ForkJoinTask<?> joinMe) {
boolean helped = false;
int m = pool.scanGuard & SMASK;
ForkJoinWorkerThread[] ws = pool.workers;
if (ws != null && ws.length > m && joinMe.status >= 0) {
int levels = MAX_HELP; // remaining chain length
ForkJoinTask<?> task = joinMe; // base of chain
outer:for (ForkJoinWorkerThread thread = this;;) {
// Try to find v, the stealer of task, by first using hint
ForkJoinWorkerThread v = ws[thread.stealHint & m];
if (v == null || v.currentSteal != task) {
for (int j = 0; ;) { // search array
if ((v = ws[j]) != null && v.currentSteal == task) {
thread.stealHint = j;
break; // save hint for next time
}
if (++j > m)
break outer; // can't find stealer
}
}
// Try to help v, using specialized form of deqTask
for (;;) {
ForkJoinTask<?>[] q; int b, i;
if (joinMe.status < 0)
break outer;
if ((b = v.queueBase) == v.queueTop ||
(q = v.queue) == null ||
(i = (q.length-1) & b) < 0)
break; // empty
long u = (i << ASHIFT) + ABASE;
ForkJoinTask<?> t = q[i];
if (task.status < 0)
break outer; // stale
if (t != null && v.queueBase == b &&
UNSAFE.compareAndSwapObject(q, u, t, null)) {
v.queueBase = b + 1;
v.stealHint = poolIndex;
ForkJoinTask<?> ps = currentSteal;
currentSteal = t;
t.doExec();
currentSteal = ps;
helped = true;
}
}
// Try to descend to find v's stealer
ForkJoinTask<?> next = v.currentJoin;
if (--levels > 0 && task.status >= 0 &&
next != null && next != task) {
task = next;
thread = v;
}
else
break; // max levels, stale, dead-end, or cyclic
}
}
return helped;
}
/**
* Performs an uncommon case for joinTask: If task t is at base of
* some workers queue, steals and executes it.
*
* @param t the task
* @return t's status
*/
private int tryDeqAndExec(ForkJoinTask<?> t) {
int m = pool.scanGuard & SMASK;
ForkJoinWorkerThread[] ws = pool.workers;
if (ws != null && ws.length > m && t.status >= 0) {
for (int j = 0; j <= m; ++j) {
ForkJoinTask<?>[] q; int b, i;
ForkJoinWorkerThread v = ws[j];
if (v != null &&
(b = v.queueBase) != v.queueTop &&
(q = v.queue) != null &&
(i = (q.length - 1) & b) >= 0 &&
q[i] == t) {
long u = (i << ASHIFT) + ABASE;
if (v.queueBase == b &&
UNSAFE.compareAndSwapObject(q, u, t, null)) {
v.queueBase = b + 1;
v.stealHint = poolIndex;
ForkJoinTask<?> ps = currentSteal;
currentSteal = t;
t.doExec();
currentSteal = ps;
}
break;
}
}
}
return t.status;
}
/**
* Implements ForkJoinTask.getSurplusQueuedTaskCount(). Returns
* an estimate of the number of tasks, offset by a function of
* number of idle workers.
*
* This method provides a cheap heuristic guide for task
* partitioning when programmers, frameworks, tools, or languages
* have little or no idea about task granularity. In essence by
* offering this method, we ask users only about tradeoffs in
* overhead vs expected throughput and its variance, rather than
* how finely to partition tasks.
*
* In a steady state strict (tree-structured) computation, each
* thread makes available for stealing enough tasks for other
* threads to remain active. Inductively, if all threads play by
* the same rules, each thread should make available only a
* constant number of tasks.
*
* The minimum useful constant is just 1. But using a value of 1
* would require immediate replenishment upon each steal to
* maintain enough tasks, which is infeasible. Further,
* partitionings/granularities of offered tasks should minimize
* steal rates, which in general means that threads nearer the top
* of computation tree should generate more than those nearer the
* bottom. In perfect steady state, each thread is at
* approximately the same level of computation tree. However,
* producing extra tasks amortizes the uncertainty of progress and
* diffusion assumptions.
*
* So, users will want to use values larger, but not much larger
* than 1 to both smooth over transient shortages and hedge
* against uneven progress; as traded off against the cost of
* extra task overhead. We leave the user to pick a threshold
* value to compare with the results of this call to guide
* decisions, but recommend values such as 3.
*
* When all threads are active, it is on average OK to estimate
* surplus strictly locally. In steady-state, if one thread is
* maintaining say 2 surplus tasks, then so are others. So we can
* just use estimated queue length (although note that (queueTop -
* queueBase) can be an overestimate because of stealers lagging
* increments of queueBase). However, this strategy alone leads
* to serious mis-estimates in some non-steady-state conditions
* (ramp-up, ramp-down, other stalls). We can detect many of these
* by further considering the number of "idle" threads, that are
* known to have zero queued tasks, so compensate by a factor of
* (#idle/#active) threads.
*/
final int getEstimatedSurplusTaskCount() {
return queueTop - queueBase - pool.idlePerActive();
}
/**
* Runs tasks until {@code pool.isQuiescent()}. We piggyback on
* pool's active count ctl maintenance, but rather than blocking
* when tasks cannot be found, we rescan until all others cannot
* find tasks either. The bracketing by pool quiescerCounts
* updates suppresses pool auto-shutdown mechanics that could
* otherwise prematurely terminate the pool because all threads
* appear to be inactive.
*/
final void helpQuiescePool() {
boolean active = true;
ForkJoinTask<?> ps = currentSteal; // to restore below
ForkJoinPool p = pool;
p.addQuiescerCount(1);
for (;;) {
ForkJoinWorkerThread[] ws = p.workers;
ForkJoinWorkerThread v = null;
int n;
if (queueTop != queueBase)
v = this;
else if (ws != null && (n = ws.length) > 1) {
ForkJoinWorkerThread w;
int r = nextSeed(); // cheap version of FJP.scan
int steps = n << 1;
for (int i = 0; i < steps; ++i) {
if ((w = ws[(i + r) & (n - 1)]) != null &&
w.queueBase != w.queueTop) {
v = w;
break;
}
}
}
if (v != null) {
ForkJoinTask<?> t;
if (!active) {
active = true;
p.addActiveCount(1);
}
if ((t = (v != this) ? v.deqTask() :
locallyFifo ? locallyDeqTask() : popTask()) != null) {
currentSteal = t;
t.doExec();
currentSteal = ps;
}
}
else {
if (active) {
active = false;
p.addActiveCount(-1);
}
if (p.isQuiescent()) {
p.addActiveCount(1);
p.addQuiescerCount(-1);
break;
}
}
}
}
// Unsafe mechanics
private static final sun.misc.Unsafe UNSAFE;
private static final long ABASE;
private static final int ASHIFT;
static {
int s;
try {
UNSAFE = sun.misc.Unsafe.getUnsafe();
Class<?> a = ForkJoinTask[].class;
ABASE = UNSAFE.arrayBaseOffset(a);
s = UNSAFE.arrayIndexScale(a);
} catch (Exception e) {
throw new Error(e);
}
if ((s & (s-1)) != 0)
throw new Error("data type scale not a power of two");
ASHIFT = 31 - Integer.numberOfLeadingZeros(s);
}
}

View file

@ -239,12 +239,10 @@ public class MBeanFeatureInfo implements Serializable, DescriptorRead {
case 1:
final String[] names = (String[])in.readObject();
if (names.length == 0) {
descriptor = ImmutableDescriptor.EMPTY_DESCRIPTOR;
} else {
final Object[] values = (Object[])in.readObject();
descriptor = new ImmutableDescriptor(names, values);
}
final Object[] values = (Object[]) in.readObject();
descriptor = (names.length == 0) ?
ImmutableDescriptor.EMPTY_DESCRIPTOR :
new ImmutableDescriptor(names, values);
break;
case 0:

View file

@ -704,12 +704,10 @@ public class MBeanInfo implements Cloneable, Serializable, DescriptorRead {
case 1:
final String[] names = (String[])in.readObject();
if (names.length == 0) {
descriptor = ImmutableDescriptor.EMPTY_DESCRIPTOR;
} else {
final Object[] values = (Object[])in.readObject();
descriptor = new ImmutableDescriptor(names, values);
}
final Object[] values = (Object[]) in.readObject();
descriptor = (names.length == 0) ?
ImmutableDescriptor.EMPTY_DESCRIPTOR :
new ImmutableDescriptor(names, values);
break;
case 0:

View file

@ -137,8 +137,10 @@ import com.sun.jmx.remote.util.EnvHelp;
* JAR conventions for service providers</a>, where the service
* interface is <code>JMXConnectorProvider</code>.</p>
*
* <p>Every implementation must support the RMI connector protocols,
* specified with the string <code>rmi</code> or
* <p>Every implementation must support the RMI connector protocol with
* the default RMI transport, specified with string <code>rmi</code>.
* An implementation may optionally support the RMI connector protocol
* with the RMI/IIOP transport, specified with the string
* <code>iiop</code>.</p>
*
* <p>Once a provider is found, the result of the

View file

@ -129,8 +129,10 @@ import javax.management.MBeanServer;
* JAR conventions for service providers</a>, where the service
* interface is <code>JMXConnectorServerProvider</code>.</p>
*
* <p>Every implementation must support the RMI connector protocols,
* specified with the string <code>rmi</code> or
* <p>Every implementation must support the RMI connector protocol with
* the default RMI transport, specified with string <code>rmi</code>.
* An implementation may optionally support the RMI connector protocol
* with the RMI/IIOP transport, specified with the string
* <code>iiop</code>.</p>
*
* <p>Once a provider is found, the result of the

View file

@ -238,10 +238,21 @@ public class RMIConnector implements JMXConnector, Serializable, JMXAddressable
//--------------------------------------------------------------------
// implements JMXConnector interface
//--------------------------------------------------------------------
/**
* @throws IOException if the connection could not be made because of a
* communication problem, or in the case of the {@code iiop} protocol,
* that RMI/IIOP is not supported
*/
public void connect() throws IOException {
connect(null);
}
/**
* @throws IOException if the connection could not be made because of a
* communication problem, or in the case of the {@code iiop} protocol,
* that RMI/IIOP is not supported
*/
public synchronized void connect(Map<String,?> environment)
throws IOException {
final boolean tracing = logger.traceOn();

View file

@ -337,7 +337,8 @@ public class RMIConnectorServer extends JMXConnectorServer {
* @exception IllegalStateException if the connector server has
* not been attached to an MBean server.
* @exception IOException if the connector server cannot be
* started.
* started, or in the case of the {@code iiop} protocol, that
* RMI/IIOP is not supported.
*/
public synchronized void start() throws IOException {
final boolean tracing = logger.traceOn();

View file

@ -36,8 +36,8 @@ questions.
that different implementations of the RMI connector can
interoperate.</p>
<p>The RMI connector supports both the JRMP and the IIOP transports
for RMI.</p>
<p>The RMI connector supports the JRMP transport for RMI, and
optionally the IIOP transport.</p>
<p>Like most connectors in the JMX Remote API, an RMI connector
usually has an address, which

View file

@ -43,10 +43,15 @@ questions.
You can provide the name of your default realm and Key Distribution
Center (KDC) host for that realm using the system properties
java.security.krb5.realm and java.security.krb5.kdc. Alternatively, you
can provide an MIT style configuration file called krb5.conf in
&lt;java-home&gt;/lib/security. If you place this file elsewhere, you can
indicate that location via the system property java.security.krb5.conf.<p>
{@code java.security.krb5.realm} and {@code java.security.krb5.kdc}.
Both properties must be set.
Alternatively, the {@code java.security.krb5.conf} system property can
be set to the location of an MIT style {@code krb5.conf} configuration
file. If none of these system properties are set, the {@code krb5.conf}
file is searched for in an implementation-specific manner. Typically,
an implementation will first look for a {@code krb5.conf} file in
{@code <java-home>/lib/security} and failing that, in an OS-specific
location.<p>
<!--
<h2>Package Specification</h2>

View file

@ -0,0 +1,281 @@
/*
* Copyright (c) 2000, 2005, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
// Attributes.java - attribute list with Namespace support
// http://www.saxproject.org
// Written by David Megginson
// NO WARRANTY! This class is in the public domain.
// $Id: Attributes.java,v 1.2 2004/11/03 22:44:51 jsuttor Exp $
package jdk.internal.org.xml.sax;
/**
* Interface for a list of XML attributes.
*
* <blockquote>
* <em>This module, both source code and documentation, is in the
* Public Domain, and comes with <strong>NO WARRANTY</strong>.</em>
* See <a href='http://www.saxproject.org'>http://www.saxproject.org</a>
* for further information.
* </blockquote>
*
* <p>This interface allows access to a list of attributes in
* three different ways:</p>
*
* <ol>
* <li>by attribute index;</li>
* <li>by Namespace-qualified name; or</li>
* <li>by qualified (prefixed) name.</li>
* </ol>
*
* <p>The list will not contain attributes that were declared
* #IMPLIED but not specified in the start tag. It will also not
* contain attributes used as Namespace declarations (xmlns*) unless
* the <code>http://xml.org/sax/features/namespace-prefixes</code>
* feature is set to <var>true</var> (it is <var>false</var> by
* default).
* Because SAX2 conforms to the original "Namespaces in XML"
* recommendation, it normally does not
* give namespace declaration attributes a namespace URI.
* </p>
*
* <p>Some SAX2 parsers may support using an optional feature flag
* (<code>http://xml.org/sax/features/xmlns-uris</code>) to request
* that those attributes be given URIs, conforming to a later
* backwards-incompatible revision of that recommendation. (The
* attribute's "local name" will be the prefix, or "xmlns" when
* defining a default element namespace.) For portability, handler
* code should always resolve that conflict, rather than requiring
* parsers that can change the setting of that feature flag. </p>
*
* <p>If the namespace-prefixes feature (see above) is
* <var>false</var>, access by qualified name may not be available; if
* the <code>http://xml.org/sax/features/namespaces</code> feature is
* <var>false</var>, access by Namespace-qualified names may not be
* available.</p>
*
* <p>This interface replaces the now-deprecated SAX1 {@link
* org.xml.sax.AttributeList AttributeList} interface, which does not
* contain Namespace support. In addition to Namespace support, it
* adds the <var>getIndex</var> methods (below).</p>
*
* <p>The order of attributes in the list is unspecified, and will
* vary from implementation to implementation.</p>
*
* @since SAX 2.0
* @author David Megginson
* @see org.xml.sax.helpers.AttributesImpl
* @see org.xml.sax.ext.DeclHandler#attributeDecl
*/
public interface Attributes
{
////////////////////////////////////////////////////////////////////
// Indexed access.
////////////////////////////////////////////////////////////////////
/**
* Return the number of attributes in the list.
*
* <p>Once you know the number of attributes, you can iterate
* through the list.</p>
*
* @return The number of attributes in the list.
* @see #getURI(int)
* @see #getLocalName(int)
* @see #getQName(int)
* @see #getType(int)
* @see #getValue(int)
*/
public abstract int getLength ();
/**
* Look up an attribute's Namespace URI by index.
*
* @param index The attribute index (zero-based).
* @return The Namespace URI, or the empty string if none
* is available, or null if the index is out of
* range.
* @see #getLength
*/
public abstract String getURI (int index);
/**
* Look up an attribute's local name by index.
*
* @param index The attribute index (zero-based).
* @return The local name, or the empty string if Namespace
* processing is not being performed, or null
* if the index is out of range.
* @see #getLength
*/
public abstract String getLocalName (int index);
/**
* Look up an attribute's XML qualified (prefixed) name by index.
*
* @param index The attribute index (zero-based).
* @return The XML qualified name, or the empty string
* if none is available, or null if the index
* is out of range.
* @see #getLength
*/
public abstract String getQName (int index);
/**
* Look up an attribute's type by index.
*
* <p>The attribute type is one of the strings "CDATA", "ID",
* "IDREF", "IDREFS", "NMTOKEN", "NMTOKENS", "ENTITY", "ENTITIES",
* or "NOTATION" (always in upper case).</p>
*
* <p>If the parser has not read a declaration for the attribute,
* or if the parser does not report attribute types, then it must
* return the value "CDATA" as stated in the XML 1.0 Recommendation
* (clause 3.3.3, "Attribute-Value Normalization").</p>
*
* <p>For an enumerated attribute that is not a notation, the
* parser will report the type as "NMTOKEN".</p>
*
* @param index The attribute index (zero-based).
* @return The attribute's type as a string, or null if the
* index is out of range.
* @see #getLength
*/
public abstract String getType (int index);
/**
* Look up an attribute's value by index.
*
* <p>If the attribute value is a list of tokens (IDREFS,
* ENTITIES, or NMTOKENS), the tokens will be concatenated
* into a single string with each token separated by a
* single space.</p>
*
* @param index The attribute index (zero-based).
* @return The attribute's value as a string, or null if the
* index is out of range.
* @see #getLength
*/
public abstract String getValue (int index);
////////////////////////////////////////////////////////////////////
// Name-based query.
////////////////////////////////////////////////////////////////////
/**
* Look up the index of an attribute by Namespace name.
*
* @param uri The Namespace URI, or the empty string if
* the name has no Namespace URI.
* @param localName The attribute's local name.
* @return The index of the attribute, or -1 if it does not
* appear in the list.
*/
public int getIndex (String uri, String localName);
/**
* Look up the index of an attribute by XML qualified (prefixed) name.
*
* @param qName The qualified (prefixed) name.
* @return The index of the attribute, or -1 if it does not
* appear in the list.
*/
public int getIndex (String qName);
/**
* Look up an attribute's type by Namespace name.
*
* <p>See {@link #getType(int) getType(int)} for a description
* of the possible types.</p>
*
* @param uri The Namespace URI, or the empty String if the
* name has no Namespace URI.
* @param localName The local name of the attribute.
* @return The attribute type as a string, or null if the
* attribute is not in the list or if Namespace
* processing is not being performed.
*/
public abstract String getType (String uri, String localName);
/**
* Look up an attribute's type by XML qualified (prefixed) name.
*
* <p>See {@link #getType(int) getType(int)} for a description
* of the possible types.</p>
*
* @param qName The XML qualified name.
* @return The attribute type as a string, or null if the
* attribute is not in the list or if qualified names
* are not available.
*/
public abstract String getType (String qName);
/**
* Look up an attribute's value by Namespace name.
*
* <p>See {@link #getValue(int) getValue(int)} for a description
* of the possible values.</p>
*
* @param uri The Namespace URI, or the empty String if the
* name has no Namespace URI.
* @param localName The local name of the attribute.
* @return The attribute value as a string, or null if the
* attribute is not in the list.
*/
public abstract String getValue (String uri, String localName);
/**
* Look up an attribute's value by XML qualified (prefixed) name.
*
* <p>See {@link #getValue(int) getValue(int)} for a description
* of the possible values.</p>
*
* @param qName The XML qualified name.
* @return The attribute value as a string, or null if the
* attribute is not in the list or if qualified names
* are not available.
*/
public abstract String getValue (String qName);
}
// end of Attributes.java

View file

@ -0,0 +1,443 @@
/*
* Copyright (c) 2000, 2005, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
// ContentHandler.java - handle main document content.
// http://www.saxproject.org
// Written by David Megginson
// NO WARRANTY! This class is in the public domain.
// $Id: ContentHandler.java,v 1.2 2004/11/03 22:44:51 jsuttor Exp $
package jdk.internal.org.xml.sax;
/**
* Receive notification of the logical content of a document.
*
* <blockquote>
* <em>This module, both source code and documentation, is in the
* Public Domain, and comes with <strong>NO WARRANTY</strong>.</em>
* See <a href='http://www.saxproject.org'>http://www.saxproject.org</a>
* for further information.
* </blockquote>
*
* <p>This is the main interface that most SAX applications
* implement: if the application needs to be informed of basic parsing
* events, it implements this interface and registers an instance with
* the SAX parser using the {@link org.xml.sax.XMLReader#setContentHandler
* setContentHandler} method. The parser uses the instance to report
* basic document-related events like the start and end of elements
* and character data.</p>
*
* <p>The order of events in this interface is very important, and
* mirrors the order of information in the document itself. For
* example, all of an element's content (character data, processing
* instructions, and/or subelements) will appear, in order, between
* the startElement event and the corresponding endElement event.</p>
*
* <p>This interface is similar to the now-deprecated SAX 1.0
* DocumentHandler interface, but it adds support for Namespaces
* and for reporting skipped entities (in non-validating XML
* processors).</p>
*
* <p>Implementors should note that there is also a
* <code>ContentHandler</code> class in the <code>java.net</code>
* package; that means that it's probably a bad idea to do</p>
*
* <pre>import java.net.*;
* import org.xml.sax.*;
* </pre>
*
* <p>In fact, "import ...*" is usually a sign of sloppy programming
* anyway, so the user should consider this a feature rather than a
* bug.</p>
*
* @since SAX 2.0
* @author David Megginson
* @see org.xml.sax.XMLReader
* @see org.xml.sax.DTDHandler
* @see org.xml.sax.ErrorHandler
*/
public interface ContentHandler
{
/**
* Receive an object for locating the origin of SAX document events.
*
* <p>SAX parsers are strongly encouraged (though not absolutely
* required) to supply a locator: if it does so, it must supply
* the locator to the application by invoking this method before
* invoking any of the other methods in the ContentHandler
* interface.</p>
*
* <p>The locator allows the application to determine the end
* position of any document-related event, even if the parser is
* not reporting an error. Typically, the application will
* use this information for reporting its own errors (such as
* character content that does not match an application's
* business rules). The information returned by the locator
* is probably not sufficient for use with a search engine.</p>
*
* <p>Note that the locator will return correct information only
* during the invocation SAX event callbacks after
* {@link #startDocument startDocument} returns and before
* {@link #endDocument endDocument} is called. The
* application should not attempt to use it at any other time.</p>
*
* @param locator an object that can return the location of
* any SAX document event
* @see org.xml.sax.Locator
*/
public void setDocumentLocator (Locator locator);
/**
* Receive notification of the beginning of a document.
*
* <p>The SAX parser will invoke this method only once, before any
* other event callbacks (except for {@link #setDocumentLocator
* setDocumentLocator}).</p>
*
* @throws org.xml.sax.SAXException any SAX exception, possibly
* wrapping another exception
* @see #endDocument
*/
public void startDocument ()
throws SAXException;
/**
* Receive notification of the end of a document.
*
* <p><strong>There is an apparent contradiction between the
* documentation for this method and the documentation for {@link
* org.xml.sax.ErrorHandler#fatalError}. Until this ambiguity is
* resolved in a future major release, clients should make no
* assumptions about whether endDocument() will or will not be
* invoked when the parser has reported a fatalError() or thrown
* an exception.</strong></p>
*
* <p>The SAX parser will invoke this method only once, and it will
* be the last method invoked during the parse. The parser shall
* not invoke this method until it has either abandoned parsing
* (because of an unrecoverable error) or reached the end of
* input.</p>
*
* @throws org.xml.sax.SAXException any SAX exception, possibly
* wrapping another exception
* @see #startDocument
*/
public void endDocument()
throws SAXException;
/**
* Begin the scope of a prefix-URI Namespace mapping.
*
* <p>The information from this event is not necessary for
* normal Namespace processing: the SAX XML reader will
* automatically replace prefixes for element and attribute
* names when the <code>http://xml.org/sax/features/namespaces</code>
* feature is <var>true</var> (the default).</p>
*
* <p>There are cases, however, when applications need to
* use prefixes in character data or in attribute values,
* where they cannot safely be expanded automatically; the
* start/endPrefixMapping event supplies the information
* to the application to expand prefixes in those contexts
* itself, if necessary.</p>
*
* <p>Note that start/endPrefixMapping events are not
* guaranteed to be properly nested relative to each other:
* all startPrefixMapping events will occur immediately before the
* corresponding {@link #startElement startElement} event,
* and all {@link #endPrefixMapping endPrefixMapping}
* events will occur immediately after the corresponding
* {@link #endElement endElement} event,
* but their order is not otherwise
* guaranteed.</p>
*
* <p>There should never be start/endPrefixMapping events for the
* "xml" prefix, since it is predeclared and immutable.</p>
*
* @param prefix the Namespace prefix being declared.
* An empty string is used for the default element namespace,
* which has no prefix.
* @param uri the Namespace URI the prefix is mapped to
* @throws org.xml.sax.SAXException the client may throw
* an exception during processing
* @see #endPrefixMapping
* @see #startElement
*/
public void startPrefixMapping (String prefix, String uri)
throws SAXException;
/**
* End the scope of a prefix-URI mapping.
*
* <p>See {@link #startPrefixMapping startPrefixMapping} for
* details. These events will always occur immediately after the
* corresponding {@link #endElement endElement} event, but the order of
* {@link #endPrefixMapping endPrefixMapping} events is not otherwise
* guaranteed.</p>
*
* @param prefix the prefix that was being mapped.
* This is the empty string when a default mapping scope ends.
* @throws org.xml.sax.SAXException the client may throw
* an exception during processing
* @see #startPrefixMapping
* @see #endElement
*/
public void endPrefixMapping (String prefix)
throws SAXException;
/**
* Receive notification of the beginning of an element.
*
* <p>The Parser will invoke this method at the beginning of every
* element in the XML document; there will be a corresponding
* {@link #endElement endElement} event for every startElement event
* (even when the element is empty). All of the element's content will be
* reported, in order, before the corresponding endElement
* event.</p>
*
* <p>This event allows up to three name components for each
* element:</p>
*
* <ol>
* <li>the Namespace URI;</li>
* <li>the local name; and</li>
* <li>the qualified (prefixed) name.</li>
* </ol>
*
* <p>Any or all of these may be provided, depending on the
* values of the <var>http://xml.org/sax/features/namespaces</var>
* and the <var>http://xml.org/sax/features/namespace-prefixes</var>
* properties:</p>
*
* <ul>
* <li>the Namespace URI and local name are required when
* the namespaces property is <var>true</var> (the default), and are
* optional when the namespaces property is <var>false</var> (if one is
* specified, both must be);</li>
* <li>the qualified name is required when the namespace-prefixes property
* is <var>true</var>, and is optional when the namespace-prefixes property
* is <var>false</var> (the default).</li>
* </ul>
*
* <p>Note that the attribute list provided will contain only
* attributes with explicit values (specified or defaulted):
* #IMPLIED attributes will be omitted. The attribute list
* will contain attributes used for Namespace declarations
* (xmlns* attributes) only if the
* <code>http://xml.org/sax/features/namespace-prefixes</code>
* property is true (it is false by default, and support for a
* true value is optional).</p>
*
* <p>Like {@link #characters characters()}, attribute values may have
* characters that need more than one <code>char</code> value. </p>
*
* @param uri the Namespace URI, or the empty string if the
* element has no Namespace URI or if Namespace
* processing is not being performed
* @param localName the local name (without prefix), or the
* empty string if Namespace processing is not being
* performed
* @param qName the qualified name (with prefix), or the
* empty string if qualified names are not available
* @param atts the attributes attached to the element. If
* there are no attributes, it shall be an empty
* Attributes object. The value of this object after
* startElement returns is undefined
* @throws org.xml.sax.SAXException any SAX exception, possibly
* wrapping another exception
* @see #endElement
* @see org.xml.sax.Attributes
* @see org.xml.sax.helpers.AttributesImpl
*/
public void startElement (String uri, String localName,
String qName, Attributes atts)
throws SAXException;
/**
* Receive notification of the end of an element.
*
* <p>The SAX parser will invoke this method at the end of every
* element in the XML document; there will be a corresponding
* {@link #startElement startElement} event for every endElement
* event (even when the element is empty).</p>
*
* <p>For information on the names, see startElement.</p>
*
* @param uri the Namespace URI, or the empty string if the
* element has no Namespace URI or if Namespace
* processing is not being performed
* @param localName the local name (without prefix), or the
* empty string if Namespace processing is not being
* performed
* @param qName the qualified XML name (with prefix), or the
* empty string if qualified names are not available
* @throws org.xml.sax.SAXException any SAX exception, possibly
* wrapping another exception
*/
public void endElement (String uri, String localName,
String qName)
throws SAXException;
/**
* Receive notification of character data.
*
* <p>The Parser will call this method to report each chunk of
* character data. SAX parsers may return all contiguous character
* data in a single chunk, or they may split it into several
* chunks; however, all of the characters in any single event
* must come from the same external entity so that the Locator
* provides useful information.</p>
*
* <p>The application must not attempt to read from the array
* outside of the specified range.</p>
*
* <p>Individual characters may consist of more than one Java
* <code>char</code> value. There are two important cases where this
* happens, because characters can't be represented in just sixteen bits.
* In one case, characters are represented in a <em>Surrogate Pair</em>,
* using two special Unicode values. Such characters are in the so-called
* "Astral Planes", with a code point above U+FFFF. A second case involves
* composite characters, such as a base character combining with one or
* more accent characters. </p>
*
* <p> Your code should not assume that algorithms using
* <code>char</code>-at-a-time idioms will be working in character
* units; in some cases they will split characters. This is relevant
* wherever XML permits arbitrary characters, such as attribute values,
* processing instruction data, and comments as well as in data reported
* from this method. It's also generally relevant whenever Java code
* manipulates internationalized text; the issue isn't unique to XML.</p>
*
* <p>Note that some parsers will report whitespace in element
* content using the {@link #ignorableWhitespace ignorableWhitespace}
* method rather than this one (validating parsers <em>must</em>
* do so).</p>
*
* @param ch the characters from the XML document
* @param start the start position in the array
* @param length the number of characters to read from the array
* @throws org.xml.sax.SAXException any SAX exception, possibly
* wrapping another exception
* @see #ignorableWhitespace
* @see org.xml.sax.Locator
*/
public void characters (char ch[], int start, int length)
throws SAXException;
/**
* Receive notification of ignorable whitespace in element content.
*
* <p>Validating Parsers must use this method to report each chunk
* of whitespace in element content (see the W3C XML 1.0
* recommendation, section 2.10): non-validating parsers may also
* use this method if they are capable of parsing and using
* content models.</p>
*
* <p>SAX parsers may return all contiguous whitespace in a single
* chunk, or they may split it into several chunks; however, all of
* the characters in any single event must come from the same
* external entity, so that the Locator provides useful
* information.</p>
*
* <p>The application must not attempt to read from the array
* outside of the specified range.</p>
*
* @param ch the characters from the XML document
* @param start the start position in the array
* @param length the number of characters to read from the array
* @throws org.xml.sax.SAXException any SAX exception, possibly
* wrapping another exception
* @see #characters
*/
public void ignorableWhitespace (char ch[], int start, int length)
throws SAXException;
/**
* Receive notification of a processing instruction.
*
* <p>The Parser will invoke this method once for each processing
* instruction found: note that processing instructions may occur
* before or after the main document element.</p>
*
* <p>A SAX parser must never report an XML declaration (XML 1.0,
* section 2.8) or a text declaration (XML 1.0, section 4.3.1)
* using this method.</p>
*
* <p>Like {@link #characters characters()}, processing instruction
* data may have characters that need more than one <code>char</code>
* value. </p>
*
* @param target the processing instruction target
* @param data the processing instruction data, or null if
* none was supplied. The data does not include any
* whitespace separating it from the target
* @throws org.xml.sax.SAXException any SAX exception, possibly
* wrapping another exception
*/
public void processingInstruction (String target, String data)
throws SAXException;
/**
* Receive notification of a skipped entity.
* This is not called for entity references within markup constructs
* such as element start tags or markup declarations. (The XML
* recommendation requires reporting skipped external entities.
* SAX also reports internal entity expansion/non-expansion, except
* within markup constructs.)
*
* <p>The Parser will invoke this method each time the entity is
* skipped. Non-validating processors may skip entities if they
* have not seen the declarations (because, for example, the
* entity was declared in an external DTD subset). All processors
* may skip external entities, depending on the values of the
* <code>http://xml.org/sax/features/external-general-entities</code>
* and the
* <code>http://xml.org/sax/features/external-parameter-entities</code>
* properties.</p>
*
* @param name the name of the skipped entity. If it is a
* parameter entity, the name will begin with '%', and if
* it is the external DTD subset, it will be the string
* "[dtd]"
* @throws org.xml.sax.SAXException any SAX exception, possibly
* wrapping another exception
*/
public void skippedEntity (String name)
throws SAXException;
}
// end of ContentHandler.java

View file

@ -0,0 +1,141 @@
/*
* Copyright (c) 2000, 2005, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
// SAX DTD handler.
// http://www.saxproject.org
// No warranty; no copyright -- use this as you will.
// $Id: DTDHandler.java,v 1.2 2004/11/03 22:44:51 jsuttor Exp $
package jdk.internal.org.xml.sax;
/**
* Receive notification of basic DTD-related events.
*
* <blockquote>
* <em>This module, both source code and documentation, is in the
* Public Domain, and comes with <strong>NO WARRANTY</strong>.</em>
* See <a href='http://www.saxproject.org'>http://www.saxproject.org</a>
* for further information.
* </blockquote>
*
* <p>If a SAX application needs information about notations and
* unparsed entities, then the application implements this
* interface and registers an instance with the SAX parser using
* the parser's setDTDHandler method. The parser uses the
* instance to report notation and unparsed entity declarations to
* the application.</p>
*
* <p>Note that this interface includes only those DTD events that
* the XML recommendation <em>requires</em> processors to report:
* notation and unparsed entity declarations.</p>
*
* <p>The SAX parser may report these events in any order, regardless
* of the order in which the notations and unparsed entities were
* declared; however, all DTD events must be reported after the
* document handler's startDocument event, and before the first
* startElement event.
* (If the {@link org.xml.sax.ext.LexicalHandler LexicalHandler} is
* used, these events must also be reported before the endDTD event.)
* </p>
*
* <p>It is up to the application to store the information for
* future use (perhaps in a hash table or object tree).
* If the application encounters attributes of type "NOTATION",
* "ENTITY", or "ENTITIES", it can use the information that it
* obtained through this interface to find the entity and/or
* notation corresponding with the attribute value.</p>
*
* @since SAX 1.0
* @author David Megginson
* @see org.xml.sax.XMLReader#setDTDHandler
*/
public interface DTDHandler {
/**
* Receive notification of a notation declaration event.
*
* <p>It is up to the application to record the notation for later
* reference, if necessary;
* notations may appear as attribute values and in unparsed entity
* declarations, and are sometime used with processing instruction
* target names.</p>
*
* <p>At least one of publicId and systemId must be non-null.
* If a system identifier is present, and it is a URL, the SAX
* parser must resolve it fully before passing it to the
* application through this event.</p>
*
* <p>There is no guarantee that the notation declaration will be
* reported before any unparsed entities that use it.</p>
*
* @param name The notation name.
* @param publicId The notation's public identifier, or null if
* none was given.
* @param systemId The notation's system identifier, or null if
* none was given.
* @exception org.xml.sax.SAXException Any SAX exception, possibly
* wrapping another exception.
* @see #unparsedEntityDecl
* @see org.xml.sax.Attributes
*/
public abstract void notationDecl (String name,
String publicId,
String systemId)
throws SAXException;
/**
* Receive notification of an unparsed entity declaration event.
*
* <p>Note that the notation name corresponds to a notation
* reported by the {@link #notationDecl notationDecl} event.
* It is up to the application to record the entity for later
* reference, if necessary;
* unparsed entities may appear as attribute values.
* </p>
*
* <p>If the system identifier is a URL, the parser must resolve it
* fully before passing it to the application.</p>
*
* @exception org.xml.sax.SAXException Any SAX exception, possibly
* wrapping another exception.
* @param name The unparsed entity's name.
* @param publicId The entity's public identifier, or null if none
* was given.
* @param systemId The entity's system identifier.
* @param notationName The name of the associated notation.
* @see #notationDecl
* @see org.xml.sax.Attributes
*/
public abstract void unparsedEntityDecl (String name,
String publicId,
String systemId,
String notationName)
throws SAXException;
}
// end of DTDHandler.java

View file

@ -0,0 +1,143 @@
/*
* Copyright (c) 2000, 2005, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
// SAX entity resolver.
// http://www.saxproject.org
// No warranty; no copyright -- use this as you will.
// $Id: EntityResolver.java,v 1.2 2004/11/03 22:44:52 jsuttor Exp $
package jdk.internal.org.xml.sax;
import java.io.IOException;
/**
* Basic interface for resolving entities.
*
* <blockquote>
* <em>This module, both source code and documentation, is in the
* Public Domain, and comes with <strong>NO WARRANTY</strong>.</em>
* See <a href='http://www.saxproject.org'>http://www.saxproject.org</a>
* for further information.
* </blockquote>
*
* <p>If a SAX application needs to implement customized handling
* for external entities, it must implement this interface and
* register an instance with the SAX driver using the
* {@link org.xml.sax.XMLReader#setEntityResolver setEntityResolver}
* method.</p>
*
* <p>The XML reader will then allow the application to intercept any
* external entities (including the external DTD subset and external
* parameter entities, if any) before including them.</p>
*
* <p>Many SAX applications will not need to implement this interface,
* but it will be especially useful for applications that build
* XML documents from databases or other specialised input sources,
* or for applications that use URI types other than URLs.</p>
*
* <p>The following resolver would provide the application
* with a special character stream for the entity with the system
* identifier "http://www.myhost.com/today":</p>
*
* <pre>
* import org.xml.sax.EntityResolver;
* import org.xml.sax.InputSource;
*
* public class MyResolver implements EntityResolver {
* public InputSource resolveEntity (String publicId, String systemId)
* {
* if (systemId.equals("http://www.myhost.com/today")) {
* // return a special input source
* MyReader reader = new MyReader();
* return new InputSource(reader);
* } else {
* // use the default behaviour
* return null;
* }
* }
* }
* </pre>
*
* <p>The application can also use this interface to redirect system
* identifiers to local URIs or to look up replacements in a catalog
* (possibly by using the public identifier).</p>
*
* @since SAX 1.0
* @author David Megginson
* @see org.xml.sax.XMLReader#setEntityResolver
* @see org.xml.sax.InputSource
*/
public interface EntityResolver {
/**
* Allow the application to resolve external entities.
*
* <p>The parser will call this method before opening any external
* entity except the top-level document entity. Such entities include
* the external DTD subset and external parameter entities referenced
* within the DTD (in either case, only if the parser reads external
* parameter entities), and external general entities referenced
* within the document element (if the parser reads external general
* entities). The application may request that the parser locate
* the entity itself, that it use an alternative URI, or that it
* use data provided by the application (as a character or byte
* input stream).</p>
*
* <p>Application writers can use this method to redirect external
* system identifiers to secure and/or local URIs, to look up
* public identifiers in a catalogue, or to read an entity from a
* database or other input source (including, for example, a dialog
* box). Neither XML nor SAX specifies a preferred policy for using
* public or system IDs to resolve resources. However, SAX specifies
* how to interpret any InputSource returned by this method, and that
* if none is returned, then the system ID will be dereferenced as
* a URL. </p>
*
* <p>If the system identifier is a URL, the SAX parser must
* resolve it fully before reporting it to the application.</p>
*
* @param publicId The public identifier of the external entity
* being referenced, or null if none was supplied.
* @param systemId The system identifier of the external entity
* being referenced.
* @return An InputSource object describing the new input source,
* or null to request that the parser open a regular
* URI connection to the system identifier.
* @exception org.xml.sax.SAXException Any SAX exception, possibly
* wrapping another exception.
* @exception java.io.IOException A Java-specific IO exception,
* possibly the result of creating a new InputStream
* or Reader for the InputSource.
* @see org.xml.sax.InputSource
*/
public abstract InputSource resolveEntity (String publicId,
String systemId)
throws SAXException, IOException;
}
// end of EntityResolver.java

View file

@ -0,0 +1,163 @@
/*
* Copyright (c) 2000, 2005, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
// SAX error handler.
// http://www.saxproject.org
// No warranty; no copyright -- use this as you will.
// $Id: ErrorHandler.java,v 1.2 2004/11/03 22:44:52 jsuttor Exp $
package jdk.internal.org.xml.sax;
/**
* Basic interface for SAX error handlers.
*
* <blockquote>
* <em>This module, both source code and documentation, is in the
* Public Domain, and comes with <strong>NO WARRANTY</strong>.</em>
* See <a href='http://www.saxproject.org'>http://www.saxproject.org</a>
* for further information.
* </blockquote>
*
* <p>If a SAX application needs to implement customized error
* handling, it must implement this interface and then register an
* instance with the XML reader using the
* {@link org.xml.sax.XMLReader#setErrorHandler setErrorHandler}
* method. The parser will then report all errors and warnings
* through this interface.</p>
*
* <p><strong>WARNING:</strong> If an application does <em>not</em>
* register an ErrorHandler, XML parsing errors will go unreported,
* except that <em>SAXParseException</em>s will be thrown for fatal errors.
* In order to detect validity errors, an ErrorHandler that does something
* with {@link #error error()} calls must be registered.</p>
*
* <p>For XML processing errors, a SAX driver must use this interface
* in preference to throwing an exception: it is up to the application
* to decide whether to throw an exception for different types of
* errors and warnings. Note, however, that there is no requirement that
* the parser continue to report additional errors after a call to
* {@link #fatalError fatalError}. In other words, a SAX driver class
* may throw an exception after reporting any fatalError.
* Also parsers may throw appropriate exceptions for non-XML errors.
* For example, {@link XMLReader#parse XMLReader.parse()} would throw
* an IOException for errors accessing entities or the document.</p>
*
* @since SAX 1.0
* @author David Megginson
* @see org.xml.sax.XMLReader#setErrorHandler
* @see org.xml.sax.SAXParseException
*/
public interface ErrorHandler {
/**
* Receive notification of a warning.
*
* <p>SAX parsers will use this method to report conditions that
* are not errors or fatal errors as defined by the XML
* recommendation. The default behaviour is to take no
* action.</p>
*
* <p>The SAX parser must continue to provide normal parsing events
* after invoking this method: it should still be possible for the
* application to process the document through to the end.</p>
*
* <p>Filters may use this method to report other, non-XML warnings
* as well.</p>
*
* @param exception The warning information encapsulated in a
* SAX parse exception.
* @exception org.xml.sax.SAXException Any SAX exception, possibly
* wrapping another exception.
* @see org.xml.sax.SAXParseException
*/
public abstract void warning (SAXParseException exception)
throws SAXException;
/**
* Receive notification of a recoverable error.
*
* <p>This corresponds to the definition of "error" in section 1.2
* of the W3C XML 1.0 Recommendation. For example, a validating
* parser would use this callback to report the violation of a
* validity constraint. The default behaviour is to take no
* action.</p>
*
* <p>The SAX parser must continue to provide normal parsing
* events after invoking this method: it should still be possible
* for the application to process the document through to the end.
* If the application cannot do so, then the parser should report
* a fatal error even if the XML recommendation does not require
* it to do so.</p>
*
* <p>Filters may use this method to report other, non-XML errors
* as well.</p>
*
* @param exception The error information encapsulated in a
* SAX parse exception.
* @exception org.xml.sax.SAXException Any SAX exception, possibly
* wrapping another exception.
* @see org.xml.sax.SAXParseException
*/
public abstract void error (SAXParseException exception)
throws SAXException;
/**
* Receive notification of a non-recoverable error.
*
* <p><strong>There is an apparent contradiction between the
* documentation for this method and the documentation for {@link
* org.xml.sax.ContentHandler#endDocument}. Until this ambiguity
* is resolved in a future major release, clients should make no
* assumptions about whether endDocument() will or will not be
* invoked when the parser has reported a fatalError() or thrown
* an exception.</strong></p>
*
* <p>This corresponds to the definition of "fatal error" in
* section 1.2 of the W3C XML 1.0 Recommendation. For example, a
* parser would use this callback to report the violation of a
* well-formedness constraint.</p>
*
* <p>The application must assume that the document is unusable
* after the parser has invoked this method, and should continue
* (if at all) only for the sake of collecting additional error
* messages: in fact, SAX parsers are free to stop reporting any
* other events once this method has been invoked.</p>
*
* @param exception The error information encapsulated in a
* SAX parse exception.
* @exception org.xml.sax.SAXException Any SAX exception, possibly
* wrapping another exception.
* @see org.xml.sax.SAXParseException
*/
public abstract void fatalError (SAXParseException exception)
throws SAXException;
}
// end of ErrorHandler.java

View file

@ -0,0 +1,360 @@
/*
* Copyright (c) 2000, 2005, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
// SAX input source.
// http://www.saxproject.org
// No warranty; no copyright -- use this as you will.
// $Id: InputSource.java,v 1.2 2004/11/03 22:55:32 jsuttor Exp $
package jdk.internal.org.xml.sax;
import java.io.Reader;
import java.io.InputStream;
/**
* A single input source for an XML entity.
*
* <blockquote>
* <em>This module, both source code and documentation, is in the
* Public Domain, and comes with <strong>NO WARRANTY</strong>.</em>
* See <a href='http://www.saxproject.org'>http://www.saxproject.org</a>
* for further information.
* </blockquote>
*
* <p>This class allows a SAX application to encapsulate information
* about an input source in a single object, which may include
* a public identifier, a system identifier, a byte stream (possibly
* with a specified encoding), and/or a character stream.</p>
*
* <p>There are two places that the application can deliver an
* input source to the parser: as the argument to the Parser.parse
* method, or as the return value of the EntityResolver.resolveEntity
* method.</p>
*
* <p>The SAX parser will use the InputSource object to determine how
* to read XML input. If there is a character stream available, the
* parser will read that stream directly, disregarding any text
* encoding declaration found in that stream.
* If there is no character stream, but there is
* a byte stream, the parser will use that byte stream, using the
* encoding specified in the InputSource or else (if no encoding is
* specified) autodetecting the character encoding using an algorithm
* such as the one in the XML specification. If neither a character
* stream nor a
* byte stream is available, the parser will attempt to open a URI
* connection to the resource identified by the system
* identifier.</p>
*
* <p>An InputSource object belongs to the application: the SAX parser
* shall never modify it in any way (it may modify a copy if
* necessary). However, standard processing of both byte and
* character streams is to close them on as part of end-of-parse cleanup,
* so applications should not attempt to re-use such streams after they
* have been handed to a parser. </p>
*
* @since SAX 1.0
* @author David Megginson
* @see org.xml.sax.XMLReader#parse(org.xml.sax.InputSource)
* @see org.xml.sax.EntityResolver#resolveEntity
* @see java.io.InputStream
* @see java.io.Reader
*/
public class InputSource {
/**
* Zero-argument default constructor.
*
* @see #setPublicId
* @see #setSystemId
* @see #setByteStream
* @see #setCharacterStream
* @see #setEncoding
*/
public InputSource ()
{
}
/**
* Create a new input source with a system identifier.
*
* <p>Applications may use setPublicId to include a
* public identifier as well, or setEncoding to specify
* the character encoding, if known.</p>
*
* <p>If the system identifier is a URL, it must be fully
* resolved (it may not be a relative URL).</p>
*
* @param systemId The system identifier (URI).
* @see #setPublicId
* @see #setSystemId
* @see #setByteStream
* @see #setEncoding
* @see #setCharacterStream
*/
public InputSource (String systemId)
{
setSystemId(systemId);
}
/**
* Create a new input source with a byte stream.
*
* <p>Application writers should use setSystemId() to provide a base
* for resolving relative URIs, may use setPublicId to include a
* public identifier, and may use setEncoding to specify the object's
* character encoding.</p>
*
* @param byteStream The raw byte stream containing the document.
* @see #setPublicId
* @see #setSystemId
* @see #setEncoding
* @see #setByteStream
* @see #setCharacterStream
*/
public InputSource (InputStream byteStream)
{
setByteStream(byteStream);
}
/**
* Create a new input source with a character stream.
*
* <p>Application writers should use setSystemId() to provide a base
* for resolving relative URIs, and may use setPublicId to include a
* public identifier.</p>
*
* <p>The character stream shall not include a byte order mark.</p>
*
* @see #setPublicId
* @see #setSystemId
* @see #setByteStream
* @see #setCharacterStream
*/
public InputSource (Reader characterStream)
{
setCharacterStream(characterStream);
}
/**
* Set the public identifier for this input source.
*
* <p>The public identifier is always optional: if the application
* writer includes one, it will be provided as part of the
* location information.</p>
*
* @param publicId The public identifier as a string.
* @see #getPublicId
* @see org.xml.sax.Locator#getPublicId
* @see org.xml.sax.SAXParseException#getPublicId
*/
public void setPublicId (String publicId)
{
this.publicId = publicId;
}
/**
* Get the public identifier for this input source.
*
* @return The public identifier, or null if none was supplied.
* @see #setPublicId
*/
public String getPublicId ()
{
return publicId;
}
/**
* Set the system identifier for this input source.
*
* <p>The system identifier is optional if there is a byte stream
* or a character stream, but it is still useful to provide one,
* since the application can use it to resolve relative URIs
* and can include it in error messages and warnings (the parser
* will attempt to open a connection to the URI only if
* there is no byte stream or character stream specified).</p>
*
* <p>If the application knows the character encoding of the
* object pointed to by the system identifier, it can register
* the encoding using the setEncoding method.</p>
*
* <p>If the system identifier is a URL, it must be fully
* resolved (it may not be a relative URL).</p>
*
* @param systemId The system identifier as a string.
* @see #setEncoding
* @see #getSystemId
* @see org.xml.sax.Locator#getSystemId
* @see org.xml.sax.SAXParseException#getSystemId
*/
public void setSystemId (String systemId)
{
this.systemId = systemId;
}
/**
* Get the system identifier for this input source.
*
* <p>The getEncoding method will return the character encoding
* of the object pointed to, or null if unknown.</p>
*
* <p>If the system ID is a URL, it will be fully resolved.</p>
*
* @return The system identifier, or null if none was supplied.
* @see #setSystemId
* @see #getEncoding
*/
public String getSystemId ()
{
return systemId;
}
/**
* Set the byte stream for this input source.
*
* <p>The SAX parser will ignore this if there is also a character
* stream specified, but it will use a byte stream in preference
* to opening a URI connection itself.</p>
*
* <p>If the application knows the character encoding of the
* byte stream, it should set it with the setEncoding method.</p>
*
* @param byteStream A byte stream containing an XML document or
* other entity.
* @see #setEncoding
* @see #getByteStream
* @see #getEncoding
* @see java.io.InputStream
*/
public void setByteStream (InputStream byteStream)
{
this.byteStream = byteStream;
}
/**
* Get the byte stream for this input source.
*
* <p>The getEncoding method will return the character
* encoding for this byte stream, or null if unknown.</p>
*
* @return The byte stream, or null if none was supplied.
* @see #getEncoding
* @see #setByteStream
*/
public InputStream getByteStream ()
{
return byteStream;
}
/**
* Set the character encoding, if known.
*
* <p>The encoding must be a string acceptable for an
* XML encoding declaration (see section 4.3.3 of the XML 1.0
* recommendation).</p>
*
* <p>This method has no effect when the application provides a
* character stream.</p>
*
* @param encoding A string describing the character encoding.
* @see #setSystemId
* @see #setByteStream
* @see #getEncoding
*/
public void setEncoding (String encoding)
{
this.encoding = encoding;
}
/**
* Get the character encoding for a byte stream or URI.
* This value will be ignored when the application provides a
* character stream.
*
* @return The encoding, or null if none was supplied.
* @see #setByteStream
* @see #getSystemId
* @see #getByteStream
*/
public String getEncoding ()
{
return encoding;
}
/**
* Set the character stream for this input source.
*
* <p>If there is a character stream specified, the SAX parser
* will ignore any byte stream and will not attempt to open
* a URI connection to the system identifier.</p>
*
* @param characterStream The character stream containing the
* XML document or other entity.
* @see #getCharacterStream
* @see java.io.Reader
*/
public void setCharacterStream (Reader characterStream)
{
this.characterStream = characterStream;
}
/**
* Get the character stream for this input source.
*
* @return The character stream, or null if none was supplied.
* @see #setCharacterStream
*/
public Reader getCharacterStream ()
{
return characterStream;
}
////////////////////////////////////////////////////////////////////
// Internal state.
////////////////////////////////////////////////////////////////////
private String publicId;
private String systemId;
private InputStream byteStream;
private String encoding;
private Reader characterStream;
}
// end of InputSource.java

View file

@ -0,0 +1,160 @@
/*
* Copyright (c) 2000, 2005, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
// SAX locator interface for document events.
// http://www.saxproject.org
// No warranty; no copyright -- use this as you will.
// $Id: Locator.java,v 1.2 2004/11/03 22:55:32 jsuttor Exp $
package jdk.internal.org.xml.sax;
/**
* Interface for associating a SAX event with a document location.
*
* <blockquote>
* <em>This module, both source code and documentation, is in the
* Public Domain, and comes with <strong>NO WARRANTY</strong>.</em>
* See <a href='http://www.saxproject.org'>http://www.saxproject.org</a>
* for further information.
* </blockquote>
*
* <p>If a SAX parser provides location information to the SAX
* application, it does so by implementing this interface and then
* passing an instance to the application using the content
* handler's {@link org.xml.sax.ContentHandler#setDocumentLocator
* setDocumentLocator} method. The application can use the
* object to obtain the location of any other SAX event
* in the XML source document.</p>
*
* <p>Note that the results returned by the object will be valid only
* during the scope of each callback method: the application
* will receive unpredictable results if it attempts to use the
* locator at any other time, or after parsing completes.</p>
*
* <p>SAX parsers are not required to supply a locator, but they are
* very strongly encouraged to do so. If the parser supplies a
* locator, it must do so before reporting any other document events.
* If no locator has been set by the time the application receives
* the {@link org.xml.sax.ContentHandler#startDocument startDocument}
* event, the application should assume that a locator is not
* available.</p>
*
* @since SAX 1.0
* @author David Megginson
* @see org.xml.sax.ContentHandler#setDocumentLocator
*/
public interface Locator {
/**
* Return the public identifier for the current document event.
*
* <p>The return value is the public identifier of the document
* entity or of the external parsed entity in which the markup
* triggering the event appears.</p>
*
* @return A string containing the public identifier, or
* null if none is available.
* @see #getSystemId
*/
public abstract String getPublicId ();
/**
* Return the system identifier for the current document event.
*
* <p>The return value is the system identifier of the document
* entity or of the external parsed entity in which the markup
* triggering the event appears.</p>
*
* <p>If the system identifier is a URL, the parser must resolve it
* fully before passing it to the application. For example, a file
* name must always be provided as a <em>file:...</em> URL, and other
* kinds of relative URI are also resolved against their bases.</p>
*
* @return A string containing the system identifier, or null
* if none is available.
* @see #getPublicId
*/
public abstract String getSystemId ();
/**
* Return the line number where the current document event ends.
* Lines are delimited by line ends, which are defined in
* the XML specification.
*
* <p><strong>Warning:</strong> The return value from the method
* is intended only as an approximation for the sake of diagnostics;
* it is not intended to provide sufficient information
* to edit the character content of the original XML document.
* In some cases, these "line" numbers match what would be displayed
* as columns, and in others they may not match the source text
* due to internal entity expansion. </p>
*
* <p>The return value is an approximation of the line number
* in the document entity or external parsed entity where the
* markup triggering the event appears.</p>
*
* <p>If possible, the SAX driver should provide the line position
* of the first character after the text associated with the document
* event. The first line is line 1.</p>
*
* @return The line number, or -1 if none is available.
* @see #getColumnNumber
*/
public abstract int getLineNumber ();
/**
* Return the column number where the current document event ends.
* This is one-based number of Java <code>char</code> values since
* the last line end.
*
* <p><strong>Warning:</strong> The return value from the method
* is intended only as an approximation for the sake of diagnostics;
* it is not intended to provide sufficient information
* to edit the character content of the original XML document.
* For example, when lines contain combining character sequences, wide
* characters, surrogate pairs, or bi-directional text, the value may
* not correspond to the column in a text editor's display. </p>
*
* <p>The return value is an approximation of the column number
* in the document entity or external parsed entity where the
* markup triggering the event appears.</p>
*
* <p>If possible, the SAX driver should provide the line position
* of the first character after the text associated with the document
* event. The first column in each line is column 1.</p>
*
* @return The column number, or -1 if none is available.
* @see #getLineNumber
*/
public abstract int getColumnNumber ();
}
// end of Locator.java

View file

@ -0,0 +1,188 @@
/*
* Copyright (c) 2000, 2005, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
// SAX exception class.
// http://www.saxproject.org
// No warranty; no copyright -- use this as you will.
// $Id: SAXException.java,v 1.3 2004/11/03 22:55:32 jsuttor Exp $
package jdk.internal.org.xml.sax;
/**
* Encapsulate a general SAX error or warning.
*
* <blockquote>
* <em>This module, both source code and documentation, is in the
* Public Domain, and comes with <strong>NO WARRANTY</strong>.</em>
* See <a href='http://www.saxproject.org'>http://www.saxproject.org</a>
* for further information.
* </blockquote>
*
* <p>This class can contain basic error or warning information from
* either the XML parser or the application: a parser writer or
* application writer can subclass it to provide additional
* functionality. SAX handlers may throw this exception or
* any exception subclassed from it.</p>
*
* <p>If the application needs to pass through other types of
* exceptions, it must wrap those exceptions in a SAXException
* or an exception derived from a SAXException.</p>
*
* <p>If the parser or application needs to include information about a
* specific location in an XML document, it should use the
* {@link org.xml.sax.SAXParseException SAXParseException} subclass.</p>
*
* @since SAX 1.0
* @author David Megginson
* @version 2.0.1 (sax2r2)
* @see org.xml.sax.SAXParseException
*/
public class SAXException extends Exception {
/**
* Create a new SAXException.
*/
public SAXException ()
{
super();
this.exception = null;
}
/**
* Create a new SAXException.
*
* @param message The error or warning message.
*/
public SAXException (String message) {
super(message);
this.exception = null;
}
/**
* Create a new SAXException wrapping an existing exception.
*
* <p>The existing exception will be embedded in the new
* one, and its message will become the default message for
* the SAXException.</p>
*
* @param e The exception to be wrapped in a SAXException.
*/
public SAXException (Exception e)
{
super();
this.exception = e;
}
/**
* Create a new SAXException from an existing exception.
*
* <p>The existing exception will be embedded in the new
* one, but the new exception will have its own message.</p>
*
* @param message The detail message.
* @param e The exception to be wrapped in a SAXException.
*/
public SAXException (String message, Exception e)
{
super(message);
this.exception = e;
}
/**
* Return a detail message for this exception.
*
* <p>If there is an embedded exception, and if the SAXException
* has no detail message of its own, this method will return
* the detail message from the embedded exception.</p>
*
* @return The error or warning message.
*/
public String getMessage ()
{
String message = super.getMessage();
if (message == null && exception != null) {
return exception.getMessage();
} else {
return message;
}
}
/**
* Return the embedded exception, if any.
*
* @return The embedded exception, or null if there is none.
*/
public Exception getException ()
{
return exception;
}
/**
* Return the cause of the exception
*
* @return Return the cause of the exception
*/
public Throwable getCause() {
return exception;
}
/**
* Override toString to pick up any embedded exception.
*
* @return A string representation of this exception.
*/
public String toString ()
{
if (exception != null) {
return super.toString() + "\n" + exception.toString();
} else {
return super.toString();
}
}
//////////////////////////////////////////////////////////////////////
// Internal state.
//////////////////////////////////////////////////////////////////////
/**
* @serial The embedded exception if tunnelling, or null.
*/
private Exception exception;
// Added serialVersionUID to preserve binary compatibility
static final long serialVersionUID = 583241635256073760L;
}
// end of SAXException.java

View file

@ -0,0 +1,79 @@
/*
* Copyright (c) 2000, 2005, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
// SAXNotRecognizedException.java - unrecognized feature or value.
// http://www.saxproject.org
// Written by David Megginson
// NO WARRANTY! This class is in the Public Domain.
// $Id: SAXNotRecognizedException.java,v 1.3 2004/11/03 22:55:32 jsuttor Exp $
package jdk.internal.org.xml.sax;
/**
* Exception class for an unrecognized identifier.
*
* <blockquote>
* <em>This module, both source code and documentation, is in the
* Public Domain, and comes with <strong>NO WARRANTY</strong>.</em>
* See <a href='http://www.saxproject.org'>http://www.saxproject.org</a>
* for further information.
* </blockquote>
*
* <p>An XMLReader will throw this exception when it finds an
* unrecognized feature or property identifier; SAX applications and
* extensions may use this class for other, similar purposes.</p>
*
* @since SAX 2.0
* @author David Megginson
* @see org.xml.sax.SAXNotSupportedException
*/
public class SAXNotRecognizedException extends SAXException
{
/**
* Default constructor.
*/
public SAXNotRecognizedException ()
{
super();
}
/**
* Construct a new exception with the given message.
*
* @param message The text message of the exception.
*/
public SAXNotRecognizedException (String message)
{
super(message);
}
// Added serialVersionUID to preserve binary compatibility
static final long serialVersionUID = 5440506620509557213L;
}
// end of SAXNotRecognizedException.java

View file

@ -0,0 +1,79 @@
/*
* Copyright (c) 2000, 2005, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
// SAXNotSupportedException.java - unsupported feature or value.
// http://www.saxproject.org
// Written by David Megginson
// NO WARRANTY! This class is in the Public Domain.
// $Id: SAXNotSupportedException.java,v 1.4 2004/11/03 22:55:32 jsuttor Exp $
package jdk.internal.org.xml.sax;
/**
* Exception class for an unsupported operation.
*
* <blockquote>
* <em>This module, both source code and documentation, is in the
* Public Domain, and comes with <strong>NO WARRANTY</strong>.</em>
* See <a href='http://www.saxproject.org'>http://www.saxproject.org</a>
* for further information.
* </blockquote>
*
* <p>An XMLReader will throw this exception when it recognizes a
* feature or property identifier, but cannot perform the requested
* operation (setting a state or value). Other SAX2 applications and
* extensions may use this class for similar purposes.</p>
*
* @since SAX 2.0
* @author David Megginson
* @see org.xml.sax.SAXNotRecognizedException
*/
public class SAXNotSupportedException extends SAXException
{
/**
* Construct a new exception with no message.
*/
public SAXNotSupportedException ()
{
super();
}
/**
* Construct a new exception with the given message.
*
* @param message The text message of the exception.
*/
public SAXNotSupportedException (String message)
{
super(message);
}
// Added serialVersionUID to preserve binary compatibility
static final long serialVersionUID = -1422818934641823846L;
}
// end of SAXNotSupportedException.java

View file

@ -0,0 +1,313 @@
/*
* Copyright (c) 2000, 2005, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
// SAX exception class.
// http://www.saxproject.org
// No warranty; no copyright -- use this as you will.
// $Id: SAXParseException.java,v 1.2 2004/11/03 22:55:32 jsuttor Exp $
package jdk.internal.org.xml.sax;
/**
* Encapsulate an XML parse error or warning.
*
* <blockquote>
* <em>This module, both source code and documentation, is in the
* Public Domain, and comes with <strong>NO WARRANTY</strong>.</em>
* See <a href='http://www.saxproject.org'>http://www.saxproject.org</a>
* for further information.
* </blockquote>
*
* <p>This exception may include information for locating the error
* in the original XML document, as if it came from a {@link Locator}
* object. Note that although the application
* will receive a SAXParseException as the argument to the handlers
* in the {@link org.xml.sax.ErrorHandler ErrorHandler} interface,
* the application is not actually required to throw the exception;
* instead, it can simply read the information in it and take a
* different action.</p>
*
* <p>Since this exception is a subclass of {@link org.xml.sax.SAXException
* SAXException}, it inherits the ability to wrap another exception.</p>
*
* @since SAX 1.0
* @author David Megginson
* @version 2.0.1 (sax2r2)
* @see org.xml.sax.SAXException
* @see org.xml.sax.Locator
* @see org.xml.sax.ErrorHandler
*/
public class SAXParseException extends SAXException {
//////////////////////////////////////////////////////////////////////
// Constructors.
//////////////////////////////////////////////////////////////////////
/**
* Create a new SAXParseException from a message and a Locator.
*
* <p>This constructor is especially useful when an application is
* creating its own exception from within a {@link org.xml.sax.ContentHandler
* ContentHandler} callback.</p>
*
* @param message The error or warning message.
* @param locator The locator object for the error or warning (may be
* null).
* @see org.xml.sax.Locator
*/
public SAXParseException (String message, Locator locator) {
super(message);
if (locator != null) {
init(locator.getPublicId(), locator.getSystemId(),
locator.getLineNumber(), locator.getColumnNumber());
} else {
init(null, null, -1, -1);
}
}
/**
* Wrap an existing exception in a SAXParseException.
*
* <p>This constructor is especially useful when an application is
* creating its own exception from within a {@link org.xml.sax.ContentHandler
* ContentHandler} callback, and needs to wrap an existing exception that is not a
* subclass of {@link org.xml.sax.SAXException SAXException}.</p>
*
* @param message The error or warning message, or null to
* use the message from the embedded exception.
* @param locator The locator object for the error or warning (may be
* null).
* @param e Any exception.
* @see org.xml.sax.Locator
*/
public SAXParseException (String message, Locator locator,
Exception e) {
super(message, e);
if (locator != null) {
init(locator.getPublicId(), locator.getSystemId(),
locator.getLineNumber(), locator.getColumnNumber());
} else {
init(null, null, -1, -1);
}
}
/**
* Create a new SAXParseException.
*
* <p>This constructor is most useful for parser writers.</p>
*
* <p>All parameters except the message are as if
* they were provided by a {@link Locator}. For example, if the
* system identifier is a URL (including relative filename), the
* caller must resolve it fully before creating the exception.</p>
*
*
* @param message The error or warning message.
* @param publicId The public identifier of the entity that generated
* the error or warning.
* @param systemId The system identifier of the entity that generated
* the error or warning.
* @param lineNumber The line number of the end of the text that
* caused the error or warning.
* @param columnNumber The column number of the end of the text that
* cause the error or warning.
*/
public SAXParseException (String message, String publicId, String systemId,
int lineNumber, int columnNumber)
{
super(message);
init(publicId, systemId, lineNumber, columnNumber);
}
/**
* Create a new SAXParseException with an embedded exception.
*
* <p>This constructor is most useful for parser writers who
* need to wrap an exception that is not a subclass of
* {@link org.xml.sax.SAXException SAXException}.</p>
*
* <p>All parameters except the message and exception are as if
* they were provided by a {@link Locator}. For example, if the
* system identifier is a URL (including relative filename), the
* caller must resolve it fully before creating the exception.</p>
*
* @param message The error or warning message, or null to use
* the message from the embedded exception.
* @param publicId The public identifier of the entity that generated
* the error or warning.
* @param systemId The system identifier of the entity that generated
* the error or warning.
* @param lineNumber The line number of the end of the text that
* caused the error or warning.
* @param columnNumber The column number of the end of the text that
* cause the error or warning.
* @param e Another exception to embed in this one.
*/
public SAXParseException (String message, String publicId, String systemId,
int lineNumber, int columnNumber, Exception e)
{
super(message, e);
init(publicId, systemId, lineNumber, columnNumber);
}
/**
* Internal initialization method.
*
* @param publicId The public identifier of the entity which generated the exception,
* or null.
* @param systemId The system identifier of the entity which generated the exception,
* or null.
* @param lineNumber The line number of the error, or -1.
* @param columnNumber The column number of the error, or -1.
*/
private void init (String publicId, String systemId,
int lineNumber, int columnNumber)
{
this.publicId = publicId;
this.systemId = systemId;
this.lineNumber = lineNumber;
this.columnNumber = columnNumber;
}
/**
* Get the public identifier of the entity where the exception occurred.
*
* @return A string containing the public identifier, or null
* if none is available.
* @see org.xml.sax.Locator#getPublicId
*/
public String getPublicId ()
{
return this.publicId;
}
/**
* Get the system identifier of the entity where the exception occurred.
*
* <p>If the system identifier is a URL, it will have been resolved
* fully.</p>
*
* @return A string containing the system identifier, or null
* if none is available.
* @see org.xml.sax.Locator#getSystemId
*/
public String getSystemId ()
{
return this.systemId;
}
/**
* The line number of the end of the text where the exception occurred.
*
* <p>The first line is line 1.</p>
*
* @return An integer representing the line number, or -1
* if none is available.
* @see org.xml.sax.Locator#getLineNumber
*/
public int getLineNumber ()
{
return this.lineNumber;
}
/**
* The column number of the end of the text where the exception occurred.
*
* <p>The first column in a line is position 1.</p>
*
* @return An integer representing the column number, or -1
* if none is available.
* @see org.xml.sax.Locator#getColumnNumber
*/
public int getColumnNumber ()
{
return this.columnNumber;
}
/**
* Override toString to provide more detailed error message.
*
* @return A string representation of this exception.
*/
public String toString() {
StringBuilder buf = new StringBuilder(getClass().getName());
String message = getLocalizedMessage();
if (publicId!=null) buf.append("publicId: ").append(publicId);
if (systemId!=null) buf.append("; systemId: ").append(systemId);
if (lineNumber!=-1) buf.append("; lineNumber: ").append(lineNumber);
if (columnNumber!=-1) buf.append("; columnNumber: ").append(columnNumber);
//append the exception message at the end
if (message!=null) buf.append("; ").append(message);
return buf.toString();
}
//////////////////////////////////////////////////////////////////////
// Internal state.
//////////////////////////////////////////////////////////////////////
/**
* @serial The public identifier, or null.
* @see #getPublicId
*/
private String publicId;
/**
* @serial The system identifier, or null.
* @see #getSystemId
*/
private String systemId;
/**
* @serial The line number, or -1.
* @see #getLineNumber
*/
private int lineNumber;
/**
* @serial The column number, or -1.
* @see #getColumnNumber
*/
private int columnNumber;
// Added serialVersionUID to preserve binary compatibility
static final long serialVersionUID = -5651165872476709336L;
}
// end of SAXParseException.java

View file

@ -0,0 +1,428 @@
/*
* Copyright (c) 2000, 2005, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
// XMLReader.java - read an XML document.
// http://www.saxproject.org
// Written by David Megginson
// NO WARRANTY! This class is in the Public Domain.
// $Id: XMLReader.java,v 1.3 2004/11/03 22:55:32 jsuttor Exp $
package jdk.internal.org.xml.sax;
import java.io.IOException;
/**
* Interface for reading an XML document using callbacks.
*
* <blockquote>
* <em>This module, both source code and documentation, is in the
* Public Domain, and comes with <strong>NO WARRANTY</strong>.</em>
* See <a href='http://www.saxproject.org'>http://www.saxproject.org</a>
* for further information.
* </blockquote>
*
* <p><strong>Note:</strong> despite its name, this interface does
* <em>not</em> extend the standard Java {@link java.io.Reader Reader}
* interface, because reading XML is a fundamentally different activity
* than reading character data.</p>
*
* <p>XMLReader is the interface that an XML parser's SAX2 driver must
* implement. This interface allows an application to set and
* query features and properties in the parser, to register
* event handlers for document processing, and to initiate
* a document parse.</p>
*
* <p>All SAX interfaces are assumed to be synchronous: the
* {@link #parse parse} methods must not return until parsing
* is complete, and readers must wait for an event-handler callback
* to return before reporting the next event.</p>
*
* <p>This interface replaces the (now deprecated) SAX 1.0 {@link
* org.xml.sax.Parser Parser} interface. The XMLReader interface
* contains two important enhancements over the old Parser
* interface (as well as some minor ones):</p>
*
* <ol>
* <li>it adds a standard way to query and set features and
* properties; and</li>
* <li>it adds Namespace support, which is required for many
* higher-level XML standards.</li>
* </ol>
*
* <p>There are adapters available to convert a SAX1 Parser to
* a SAX2 XMLReader and vice-versa.</p>
*
* @since SAX 2.0
* @author David Megginson
* @see org.xml.sax.XMLFilter
* @see org.xml.sax.helpers.ParserAdapter
* @see org.xml.sax.helpers.XMLReaderAdapter
*/
public interface XMLReader
{
////////////////////////////////////////////////////////////////////
// Configuration.
////////////////////////////////////////////////////////////////////
/**
* Look up the value of a feature flag.
*
* <p>The feature name is any fully-qualified URI. It is
* possible for an XMLReader to recognize a feature name but
* temporarily be unable to return its value.
* Some feature values may be available only in specific
* contexts, such as before, during, or after a parse.
* Also, some feature values may not be programmatically accessible.
* (In the case of an adapter for SAX1 {@link Parser}, there is no
* implementation-independent way to expose whether the underlying
* parser is performing validation, expanding external entities,
* and so forth.) </p>
*
* <p>All XMLReaders are required to recognize the
* http://xml.org/sax/features/namespaces and the
* http://xml.org/sax/features/namespace-prefixes feature names.</p>
*
* <p>Typical usage is something like this:</p>
*
* <pre>
* XMLReader r = new MySAXDriver();
*
* // try to activate validation
* try {
* r.setFeature("http://xml.org/sax/features/validation", true);
* } catch (SAXException e) {
* System.err.println("Cannot activate validation.");
* }
*
* // register event handlers
* r.setContentHandler(new MyContentHandler());
* r.setErrorHandler(new MyErrorHandler());
*
* // parse the first document
* try {
* r.parse("http://www.foo.com/mydoc.xml");
* } catch (IOException e) {
* System.err.println("I/O exception reading XML document");
* } catch (SAXException e) {
* System.err.println("XML exception reading document.");
* }
* </pre>
*
* <p>Implementors are free (and encouraged) to invent their own features,
* using names built on their own URIs.</p>
*
* @param name The feature name, which is a fully-qualified URI.
* @return The current value of the feature (true or false).
* @exception org.xml.sax.SAXNotRecognizedException If the feature
* value can't be assigned or retrieved.
* @exception org.xml.sax.SAXNotSupportedException When the
* XMLReader recognizes the feature name but
* cannot determine its value at this time.
* @see #setFeature
*/
public boolean getFeature (String name)
throws SAXNotRecognizedException, SAXNotSupportedException;
/**
* Set the value of a feature flag.
*
* <p>The feature name is any fully-qualified URI. It is
* possible for an XMLReader to expose a feature value but
* to be unable to change the current value.
* Some feature values may be immutable or mutable only
* in specific contexts, such as before, during, or after
* a parse.</p>
*
* <p>All XMLReaders are required to support setting
* http://xml.org/sax/features/namespaces to true and
* http://xml.org/sax/features/namespace-prefixes to false.</p>
*
* @param name The feature name, which is a fully-qualified URI.
* @param value The requested value of the feature (true or false).
* @exception org.xml.sax.SAXNotRecognizedException If the feature
* value can't be assigned or retrieved.
* @exception org.xml.sax.SAXNotSupportedException When the
* XMLReader recognizes the feature name but
* cannot set the requested value.
* @see #getFeature
*/
public void setFeature (String name, boolean value)
throws SAXNotRecognizedException, SAXNotSupportedException;
/**
* Look up the value of a property.
*
* <p>The property name is any fully-qualified URI. It is
* possible for an XMLReader to recognize a property name but
* temporarily be unable to return its value.
* Some property values may be available only in specific
* contexts, such as before, during, or after a parse.</p>
*
* <p>XMLReaders are not required to recognize any specific
* property names, though an initial core set is documented for
* SAX2.</p>
*
* <p>Implementors are free (and encouraged) to invent their own properties,
* using names built on their own URIs.</p>
*
* @param name The property name, which is a fully-qualified URI.
* @return The current value of the property.
* @exception org.xml.sax.SAXNotRecognizedException If the property
* value can't be assigned or retrieved.
* @exception org.xml.sax.SAXNotSupportedException When the
* XMLReader recognizes the property name but
* cannot determine its value at this time.
* @see #setProperty
*/
public Object getProperty (String name)
throws SAXNotRecognizedException, SAXNotSupportedException;
/**
* Set the value of a property.
*
* <p>The property name is any fully-qualified URI. It is
* possible for an XMLReader to recognize a property name but
* to be unable to change the current value.
* Some property values may be immutable or mutable only
* in specific contexts, such as before, during, or after
* a parse.</p>
*
* <p>XMLReaders are not required to recognize setting
* any specific property names, though a core set is defined by
* SAX2.</p>
*
* <p>This method is also the standard mechanism for setting
* extended handlers.</p>
*
* @param name The property name, which is a fully-qualified URI.
* @param value The requested value for the property.
* @exception org.xml.sax.SAXNotRecognizedException If the property
* value can't be assigned or retrieved.
* @exception org.xml.sax.SAXNotSupportedException When the
* XMLReader recognizes the property name but
* cannot set the requested value.
*/
public void setProperty (String name, Object value)
throws SAXNotRecognizedException, SAXNotSupportedException;
////////////////////////////////////////////////////////////////////
// Event handlers.
////////////////////////////////////////////////////////////////////
/**
* Allow an application to register an entity resolver.
*
* <p>If the application does not register an entity resolver,
* the XMLReader will perform its own default resolution.</p>
*
* <p>Applications may register a new or different resolver in the
* middle of a parse, and the SAX parser must begin using the new
* resolver immediately.</p>
*
* @param resolver The entity resolver.
* @see #getEntityResolver
*/
public void setEntityResolver (EntityResolver resolver);
/**
* Return the current entity resolver.
*
* @return The current entity resolver, or null if none
* has been registered.
* @see #setEntityResolver
*/
public EntityResolver getEntityResolver ();
/**
* Allow an application to register a DTD event handler.
*
* <p>If the application does not register a DTD handler, all DTD
* events reported by the SAX parser will be silently ignored.</p>
*
* <p>Applications may register a new or different handler in the
* middle of a parse, and the SAX parser must begin using the new
* handler immediately.</p>
*
* @param handler The DTD handler.
* @see #getDTDHandler
*/
public void setDTDHandler (DTDHandler handler);
/**
* Return the current DTD handler.
*
* @return The current DTD handler, or null if none
* has been registered.
* @see #setDTDHandler
*/
public DTDHandler getDTDHandler ();
/**
* Allow an application to register a content event handler.
*
* <p>If the application does not register a content handler, all
* content events reported by the SAX parser will be silently
* ignored.</p>
*
* <p>Applications may register a new or different handler in the
* middle of a parse, and the SAX parser must begin using the new
* handler immediately.</p>
*
* @param handler The content handler.
* @see #getContentHandler
*/
public void setContentHandler (ContentHandler handler);
/**
* Return the current content handler.
*
* @return The current content handler, or null if none
* has been registered.
* @see #setContentHandler
*/
public ContentHandler getContentHandler ();
/**
* Allow an application to register an error event handler.
*
* <p>If the application does not register an error handler, all
* error events reported by the SAX parser will be silently
* ignored; however, normal processing may not continue. It is
* highly recommended that all SAX applications implement an
* error handler to avoid unexpected bugs.</p>
*
* <p>Applications may register a new or different handler in the
* middle of a parse, and the SAX parser must begin using the new
* handler immediately.</p>
*
* @param handler The error handler.
* @see #getErrorHandler
*/
public void setErrorHandler (ErrorHandler handler);
/**
* Return the current error handler.
*
* @return The current error handler, or null if none
* has been registered.
* @see #setErrorHandler
*/
public ErrorHandler getErrorHandler ();
////////////////////////////////////////////////////////////////////
// Parsing.
////////////////////////////////////////////////////////////////////
/**
* Parse an XML document.
*
* <p>The application can use this method to instruct the XML
* reader to begin parsing an XML document from any valid input
* source (a character stream, a byte stream, or a URI).</p>
*
* <p>Applications may not invoke this method while a parse is in
* progress (they should create a new XMLReader instead for each
* nested XML document). Once a parse is complete, an
* application may reuse the same XMLReader object, possibly with a
* different input source.
* Configuration of the XMLReader object (such as handler bindings and
* values established for feature flags and properties) is unchanged
* by completion of a parse, unless the definition of that aspect of
* the configuration explicitly specifies other behavior.
* (For example, feature flags or properties exposing
* characteristics of the document being parsed.)
* </p>
*
* <p>During the parse, the XMLReader will provide information
* about the XML document through the registered event
* handlers.</p>
*
* <p>This method is synchronous: it will not return until parsing
* has ended. If a client application wants to terminate
* parsing early, it should throw an exception.</p>
*
* @param input The input source for the top-level of the
* XML document.
* @exception org.xml.sax.SAXException Any SAX exception, possibly
* wrapping another exception.
* @exception java.io.IOException An IO exception from the parser,
* possibly from a byte stream or character stream
* supplied by the application.
* @see org.xml.sax.InputSource
* @see #parse(java.lang.String)
* @see #setEntityResolver
* @see #setDTDHandler
* @see #setContentHandler
* @see #setErrorHandler
*/
public void parse (InputSource input)
throws IOException, SAXException;
/**
* Parse an XML document from a system identifier (URI).
*
* <p>This method is a shortcut for the common case of reading a
* document from a system identifier. It is the exact
* equivalent of the following:</p>
*
* <pre>
* parse(new InputSource(systemId));
* </pre>
*
* <p>If the system identifier is a URL, it must be fully resolved
* by the application before it is passed to the parser.</p>
*
* @param systemId The system identifier (URI).
* @exception org.xml.sax.SAXException Any SAX exception, possibly
* wrapping another exception.
* @exception java.io.IOException An IO exception from the parser,
* possibly from a byte stream or character stream
* supplied by the application.
* @see #parse(org.xml.sax.InputSource)
*/
public void parse (String systemId)
throws IOException, SAXException;
}

View file

@ -0,0 +1,491 @@
/*
* Copyright (c) 2000, 2006, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
// DefaultHandler.java - default implementation of the core handlers.
// http://www.saxproject.org
// Written by David Megginson
// NO WARRANTY! This class is in the public domain.
// $Id: DefaultHandler.java,v 1.3 2006/04/13 02:06:32 jeffsuttor Exp $
package jdk.internal.org.xml.sax.helpers;
import java.io.IOException;
import jdk.internal.org.xml.sax.InputSource;
import jdk.internal.org.xml.sax.Locator;
import jdk.internal.org.xml.sax.Attributes;
import jdk.internal.org.xml.sax.EntityResolver;
import jdk.internal.org.xml.sax.DTDHandler;
import jdk.internal.org.xml.sax.ContentHandler;
import jdk.internal.org.xml.sax.ErrorHandler;
import jdk.internal.org.xml.sax.SAXException;
import jdk.internal.org.xml.sax.SAXParseException;
/**
* Default base class for SAX2 event handlers.
*
* <blockquote>
* <em>This module, both source code and documentation, is in the
* Public Domain, and comes with <strong>NO WARRANTY</strong>.</em>
* See <a href='http://www.saxproject.org'>http://www.saxproject.org</a>
* for further information.
* </blockquote>
*
* <p>This class is available as a convenience base class for SAX2
* applications: it provides default implementations for all of the
* callbacks in the four core SAX2 handler classes:</p>
*
* <ul>
* <li>{@link org.xml.sax.EntityResolver EntityResolver}</li>
* <li>{@link org.xml.sax.DTDHandler DTDHandler}</li>
* <li>{@link org.xml.sax.ContentHandler ContentHandler}</li>
* <li>{@link org.xml.sax.ErrorHandler ErrorHandler}</li>
* </ul>
*
* <p>Application writers can extend this class when they need to
* implement only part of an interface; parser writers can
* instantiate this class to provide default handlers when the
* application has not supplied its own.</p>
*
* <p>This class replaces the deprecated SAX1
* {@link org.xml.sax.HandlerBase HandlerBase} class.</p>
*
* @since SAX 2.0
* @author David Megginson,
* @see org.xml.sax.EntityResolver
* @see org.xml.sax.DTDHandler
* @see org.xml.sax.ContentHandler
* @see org.xml.sax.ErrorHandler
*/
public class DefaultHandler
implements EntityResolver, DTDHandler, ContentHandler, ErrorHandler
{
////////////////////////////////////////////////////////////////////
// Default implementation of the EntityResolver interface.
////////////////////////////////////////////////////////////////////
/**
* Resolve an external entity.
*
* <p>Always return null, so that the parser will use the system
* identifier provided in the XML document. This method implements
* the SAX default behaviour: application writers can override it
* in a subclass to do special translations such as catalog lookups
* or URI redirection.</p>
*
* @param publicId The public identifier, or null if none is
* available.
* @param systemId The system identifier provided in the XML
* document.
* @return The new input source, or null to require the
* default behaviour.
* @exception java.io.IOException If there is an error setting
* up the new input source.
* @exception org.xml.sax.SAXException Any SAX exception, possibly
* wrapping another exception.
* @see org.xml.sax.EntityResolver#resolveEntity
*/
public InputSource resolveEntity (String publicId, String systemId)
throws IOException, SAXException
{
return null;
}
////////////////////////////////////////////////////////////////////
// Default implementation of DTDHandler interface.
////////////////////////////////////////////////////////////////////
/**
* Receive notification of a notation declaration.
*
* <p>By default, do nothing. Application writers may override this
* method in a subclass if they wish to keep track of the notations
* declared in a document.</p>
*
* @param name The notation name.
* @param publicId The notation public identifier, or null if not
* available.
* @param systemId The notation system identifier.
* @exception org.xml.sax.SAXException Any SAX exception, possibly
* wrapping another exception.
* @see org.xml.sax.DTDHandler#notationDecl
*/
public void notationDecl (String name, String publicId, String systemId)
throws SAXException
{
// no op
}
/**
* Receive notification of an unparsed entity declaration.
*
* <p>By default, do nothing. Application writers may override this
* method in a subclass to keep track of the unparsed entities
* declared in a document.</p>
*
* @param name The entity name.
* @param publicId The entity public identifier, or null if not
* available.
* @param systemId The entity system identifier.
* @param notationName The name of the associated notation.
* @exception org.xml.sax.SAXException Any SAX exception, possibly
* wrapping another exception.
* @see org.xml.sax.DTDHandler#unparsedEntityDecl
*/
public void unparsedEntityDecl (String name, String publicId,
String systemId, String notationName)
throws SAXException
{
// no op
}
////////////////////////////////////////////////////////////////////
// Default implementation of ContentHandler interface.
////////////////////////////////////////////////////////////////////
/**
* Receive a Locator object for document events.
*
* <p>By default, do nothing. Application writers may override this
* method in a subclass if they wish to store the locator for use
* with other document events.</p>
*
* @param locator A locator for all SAX document events.
* @see org.xml.sax.ContentHandler#setDocumentLocator
* @see org.xml.sax.Locator
*/
public void setDocumentLocator (Locator locator)
{
// no op
}
/**
* Receive notification of the beginning of the document.
*
* <p>By default, do nothing. Application writers may override this
* method in a subclass to take specific actions at the beginning
* of a document (such as allocating the root node of a tree or
* creating an output file).</p>
*
* @exception org.xml.sax.SAXException Any SAX exception, possibly
* wrapping another exception.
* @see org.xml.sax.ContentHandler#startDocument
*/
public void startDocument ()
throws SAXException
{
// no op
}
/**
* Receive notification of the end of the document.
*
* <p>By default, do nothing. Application writers may override this
* method in a subclass to take specific actions at the end
* of a document (such as finalising a tree or closing an output
* file).</p>
*
* @exception org.xml.sax.SAXException Any SAX exception, possibly
* wrapping another exception.
* @see org.xml.sax.ContentHandler#endDocument
*/
public void endDocument ()
throws SAXException
{
// no op
}
/**
* Receive notification of the start of a Namespace mapping.
*
* <p>By default, do nothing. Application writers may override this
* method in a subclass to take specific actions at the start of
* each Namespace prefix scope (such as storing the prefix mapping).</p>
*
* @param prefix The Namespace prefix being declared.
* @param uri The Namespace URI mapped to the prefix.
* @exception org.xml.sax.SAXException Any SAX exception, possibly
* wrapping another exception.
* @see org.xml.sax.ContentHandler#startPrefixMapping
*/
public void startPrefixMapping (String prefix, String uri)
throws SAXException
{
// no op
}
/**
* Receive notification of the end of a Namespace mapping.
*
* <p>By default, do nothing. Application writers may override this
* method in a subclass to take specific actions at the end of
* each prefix mapping.</p>
*
* @param prefix The Namespace prefix being declared.
* @exception org.xml.sax.SAXException Any SAX exception, possibly
* wrapping another exception.
* @see org.xml.sax.ContentHandler#endPrefixMapping
*/
public void endPrefixMapping (String prefix)
throws SAXException
{
// no op
}
/**
* Receive notification of the start of an element.
*
* <p>By default, do nothing. Application writers may override this
* method in a subclass to take specific actions at the start of
* each element (such as allocating a new tree node or writing
* output to a file).</p>
*
* @param uri The Namespace URI, or the empty string if the
* element has no Namespace URI or if Namespace
* processing is not being performed.
* @param localName The local name (without prefix), or the
* empty string if Namespace processing is not being
* performed.
* @param qName The qualified name (with prefix), or the
* empty string if qualified names are not available.
* @param attributes The attributes attached to the element. If
* there are no attributes, it shall be an empty
* Attributes object.
* @exception org.xml.sax.SAXException Any SAX exception, possibly
* wrapping another exception.
* @see org.xml.sax.ContentHandler#startElement
*/
public void startElement (String uri, String localName,
String qName, Attributes attributes)
throws SAXException
{
// no op
}
/**
* Receive notification of the end of an element.
*
* <p>By default, do nothing. Application writers may override this
* method in a subclass to take specific actions at the end of
* each element (such as finalising a tree node or writing
* output to a file).</p>
*
* @param uri The Namespace URI, or the empty string if the
* element has no Namespace URI or if Namespace
* processing is not being performed.
* @param localName The local name (without prefix), or the
* empty string if Namespace processing is not being
* performed.
* @param qName The qualified name (with prefix), or the
* empty string if qualified names are not available.
* @exception org.xml.sax.SAXException Any SAX exception, possibly
* wrapping another exception.
* @see org.xml.sax.ContentHandler#endElement
*/
public void endElement (String uri, String localName, String qName)
throws SAXException
{
// no op
}
/**
* Receive notification of character data inside an element.
*
* <p>By default, do nothing. Application writers may override this
* method to take specific actions for each chunk of character data
* (such as adding the data to a node or buffer, or printing it to
* a file).</p>
*
* @param ch The characters.
* @param start The start position in the character array.
* @param length The number of characters to use from the
* character array.
* @exception org.xml.sax.SAXException Any SAX exception, possibly
* wrapping another exception.
* @see org.xml.sax.ContentHandler#characters
*/
public void characters (char ch[], int start, int length)
throws SAXException
{
// no op
}
/**
* Receive notification of ignorable whitespace in element content.
*
* <p>By default, do nothing. Application writers may override this
* method to take specific actions for each chunk of ignorable
* whitespace (such as adding data to a node or buffer, or printing
* it to a file).</p>
*
* @param ch The whitespace characters.
* @param start The start position in the character array.
* @param length The number of characters to use from the
* character array.
* @exception org.xml.sax.SAXException Any SAX exception, possibly
* wrapping another exception.
* @see org.xml.sax.ContentHandler#ignorableWhitespace
*/
public void ignorableWhitespace (char ch[], int start, int length)
throws SAXException
{
// no op
}
/**
* Receive notification of a processing instruction.
*
* <p>By default, do nothing. Application writers may override this
* method in a subclass to take specific actions for each
* processing instruction, such as setting status variables or
* invoking other methods.</p>
*
* @param target The processing instruction target.
* @param data The processing instruction data, or null if
* none is supplied.
* @exception org.xml.sax.SAXException Any SAX exception, possibly
* wrapping another exception.
* @see org.xml.sax.ContentHandler#processingInstruction
*/
public void processingInstruction (String target, String data)
throws SAXException
{
// no op
}
/**
* Receive notification of a skipped entity.
*
* <p>By default, do nothing. Application writers may override this
* method in a subclass to take specific actions for each
* processing instruction, such as setting status variables or
* invoking other methods.</p>
*
* @param name The name of the skipped entity.
* @exception org.xml.sax.SAXException Any SAX exception, possibly
* wrapping another exception.
* @see org.xml.sax.ContentHandler#processingInstruction
*/
public void skippedEntity (String name)
throws SAXException
{
// no op
}
////////////////////////////////////////////////////////////////////
// Default implementation of the ErrorHandler interface.
////////////////////////////////////////////////////////////////////
/**
* Receive notification of a parser warning.
*
* <p>The default implementation does nothing. Application writers
* may override this method in a subclass to take specific actions
* for each warning, such as inserting the message in a log file or
* printing it to the console.</p>
*
* @param e The warning information encoded as an exception.
* @exception org.xml.sax.SAXException Any SAX exception, possibly
* wrapping another exception.
* @see org.xml.sax.ErrorHandler#warning
* @see org.xml.sax.SAXParseException
*/
public void warning (SAXParseException e)
throws SAXException
{
// no op
}
/**
* Receive notification of a recoverable parser error.
*
* <p>The default implementation does nothing. Application writers
* may override this method in a subclass to take specific actions
* for each error, such as inserting the message in a log file or
* printing it to the console.</p>
*
* @param e The error information encoded as an exception.
* @exception org.xml.sax.SAXException Any SAX exception, possibly
* wrapping another exception.
* @see org.xml.sax.ErrorHandler#warning
* @see org.xml.sax.SAXParseException
*/
public void error (SAXParseException e)
throws SAXException
{
// no op
}
/**
* Report a fatal XML parsing error.
*
* <p>The default implementation throws a SAXParseException.
* Application writers may override this method in a subclass if
* they need to take specific actions for each fatal error (such as
* collecting all of the errors into a single report): in any case,
* the application must stop all regular processing when this
* method is invoked, since the document is no longer reliable, and
* the parser may no longer report parsing events.</p>
*
* @param e The error information encoded as an exception.
* @exception org.xml.sax.SAXException Any SAX exception, possibly
* wrapping another exception.
* @see org.xml.sax.ErrorHandler#fatalError
* @see org.xml.sax.SAXParseException
*/
public void fatalError (SAXParseException e)
throws SAXException
{
throw e;
}
}
// end of DefaultHandler.java

View file

@ -0,0 +1,59 @@
/*
* Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package jdk.internal.util.xml;
import java.util.Properties;
import java.util.InvalidPropertiesFormatException;
import java.io.InputStream;
import java.io.OutputStream;
import java.io.IOException;
import sun.util.spi.XmlPropertiesProvider;
/**
* A {@code XmlPropertiesProvider} implementation that uses the UKit XML parser.
*/
public class BasicXmlPropertiesProvider extends XmlPropertiesProvider {
public BasicXmlPropertiesProvider() { }
@Override
public void load(Properties props, InputStream in)
throws IOException, InvalidPropertiesFormatException
{
PropertiesDefaultHandler handler = new PropertiesDefaultHandler();
handler.load(props, in);
}
@Override
public void store(Properties props, OutputStream os, String comment,
String encoding)
throws IOException
{
PropertiesDefaultHandler handler = new PropertiesDefaultHandler();
handler.store(props, os, comment, encoding);
}
}

View file

@ -0,0 +1,232 @@
/*
* Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package jdk.internal.util.xml;
import java.io.*;
import java.util.InvalidPropertiesFormatException;
import java.util.Properties;
import jdk.internal.org.xml.sax.Attributes;
import jdk.internal.org.xml.sax.InputSource;
import jdk.internal.org.xml.sax.SAXException;
import jdk.internal.org.xml.sax.SAXParseException;
import jdk.internal.org.xml.sax.helpers.DefaultHandler;
import jdk.internal.util.xml.impl.SAXParserImpl;
import jdk.internal.util.xml.impl.XMLStreamWriterImpl;
/**
* A class used to aid in Properties load and save in XML. This class is
* re-implemented using a subset of SAX
*
* @author Joe Wang
* @since 8
*/
public class PropertiesDefaultHandler extends DefaultHandler {
// Elements specified in the properties.dtd
private static final String ELEMENT_ROOT = "properties";
private static final String ELEMENT_COMMENT = "comment";
private static final String ELEMENT_ENTRY = "entry";
private static final String ATTR_KEY = "key";
// The required DTD URI for exported properties
private static final String PROPS_DTD_DECL =
"<!DOCTYPE properties SYSTEM \"http://java.sun.com/dtd/properties.dtd\">";
private static final String PROPS_DTD_URI =
"http://java.sun.com/dtd/properties.dtd";
private static final String PROPS_DTD =
"<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
+ "<!-- DTD for properties -->"
+ "<!ELEMENT properties ( comment?, entry* ) >"
+ "<!ATTLIST properties"
+ " version CDATA #FIXED \"1.0\">"
+ "<!ELEMENT comment (#PCDATA) >"
+ "<!ELEMENT entry (#PCDATA) >"
+ "<!ATTLIST entry "
+ " key CDATA #REQUIRED>";
/**
* Version number for the format of exported properties files.
*/
private static final String EXTERNAL_XML_VERSION = "1.0";
private Properties properties;
public void load(Properties props, InputStream in)
throws IOException, InvalidPropertiesFormatException, UnsupportedEncodingException
{
this.properties = props;
try {
SAXParser parser = new SAXParserImpl();
parser.parse(in, this);
} catch (SAXException saxe) {
throw new InvalidPropertiesFormatException(saxe);
}
/**
* String xmlVersion = propertiesElement.getAttribute("version"); if
* (xmlVersion.compareTo(EXTERNAL_XML_VERSION) > 0) throw new
* InvalidPropertiesFormatException( "Exported Properties file format
* version " + xmlVersion + " is not supported. This java installation
* can read" + " versions " + EXTERNAL_XML_VERSION + " or older. You" +
* " may need to install a newer version of JDK.");
*/
}
public void store(Properties props, OutputStream os, String comment, String encoding)
throws IOException
{
try {
XMLStreamWriter writer = new XMLStreamWriterImpl(os, encoding);
writer.writeStartDocument();
writer.writeDTD(PROPS_DTD_DECL);
writer.writeStartElement(ELEMENT_ROOT);
if (comment != null && comment.length() > 0) {
writer.writeStartElement(ELEMENT_COMMENT);
writer.writeCharacters(comment);
writer.writeEndElement();
}
for (String key : props.stringPropertyNames()) {
String val = props.getProperty(key);
writer.writeStartElement(ELEMENT_ENTRY);
writer.writeAttribute(ATTR_KEY, key);
writer.writeCharacters(val);
writer.writeEndElement();
}
writer.writeEndElement();
writer.writeEndDocument();
writer.close();
} catch (XMLStreamException e) {
if (e.getCause() instanceof UnsupportedEncodingException) {
throw (UnsupportedEncodingException) e.getCause();
}
throw new IOException(e);
}
}
////////////////////////////////////////////////////////////////////
// Validate while parsing
////////////////////////////////////////////////////////////////////
final static String ALLOWED_ELEMENTS = "properties, comment, entry";
final static String ALLOWED_COMMENT = "comment";
////////////////////////////////////////////////////////////////////
// Handler methods
////////////////////////////////////////////////////////////////////
StringBuffer buf = new StringBuffer();
boolean sawComment = false;
boolean validEntry = false;
int rootElem = 0;
String key;
String rootElm;
@Override
public void startElement(String uri, String localName, String qName, Attributes attributes)
throws SAXException
{
if (rootElem < 2) {
rootElem++;
}
if (rootElm == null) {
fatalError(new SAXParseException("An XML properties document must contain"
+ " the DOCTYPE declaration as defined by java.util.Properties.", null));
}
if (rootElem == 1 && !rootElm.equals(qName)) {
fatalError(new SAXParseException("Document root element \"" + qName
+ "\", must match DOCTYPE root \"" + rootElm + "\"", null));
}
if (!ALLOWED_ELEMENTS.contains(qName)) {
fatalError(new SAXParseException("Element type \"" + qName + "\" must be declared.", null));
}
if (qName.equals(ELEMENT_ENTRY)) {
validEntry = true;
key = attributes.getValue(ATTR_KEY);
if (key == null) {
fatalError(new SAXParseException("Attribute \"key\" is required and must be specified for element type \"entry\"", null));
}
} else if (qName.equals(ALLOWED_COMMENT)) {
if (sawComment) {
fatalError(new SAXParseException("Only one comment element may be allowed. "
+ "The content of element type \"properties\" must match \"(comment?,entry*)\"", null));
}
sawComment = true;
}
}
@Override
public void characters(char[] ch, int start, int length) throws SAXException {
if (validEntry) {
buf.append(ch, start, length);
}
}
@Override
public void endElement(String uri, String localName, String qName) throws SAXException {
if (!ALLOWED_ELEMENTS.contains(qName)) {
fatalError(new SAXParseException("Element: " + qName + " is invalid, must match \"(comment?,entry*)\".", null));
}
if (validEntry) {
properties.setProperty(key, buf.toString());
buf.delete(0, buf.length());
validEntry = false;
}
}
@Override
public void notationDecl(String name, String publicId, String systemId) throws SAXException {
rootElm = name;
}
@Override
public InputSource resolveEntity(String pubid, String sysid)
throws SAXException, IOException {
{
if (sysid.equals(PROPS_DTD_URI)) {
InputSource is;
is = new InputSource(new StringReader(PROPS_DTD));
is.setSystemId(PROPS_DTD_URI);
return is;
}
throw new SAXException("Invalid system identifier: " + sysid);
}
}
@Override
public void error(SAXParseException x) throws SAXException {
throw x;
}
@Override
public void fatalError(SAXParseException x) throws SAXException {
throw x;
}
@Override
public void warning(SAXParseException x) throws SAXException {
throw x;
}
}

View file

@ -0,0 +1,246 @@
/*
* Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package jdk.internal.util.xml;
import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import jdk.internal.org.xml.sax.InputSource;
import jdk.internal.org.xml.sax.SAXException;
import jdk.internal.org.xml.sax.XMLReader;
import jdk.internal.org.xml.sax.helpers.DefaultHandler;
/**
* Defines the API that wraps an {@link org.xml.sax.XMLReader}
* implementation class. In JAXP 1.0, this class wrapped the
* {@link org.xml.sax.Parser} interface, however this interface was
* replaced by the {@link org.xml.sax.XMLReader}. For ease
* of transition, this class continues to support the same name
* and interface as well as supporting new methods.
*
* An instance of this class can be obtained from the
* {@link javax.xml.parsers.SAXParserFactory#newSAXParser()} method.
* Once an instance of this class is obtained, XML can be parsed from
* a variety of input sources. These input sources are InputStreams,
* Files, URLs, and SAX InputSources.<p>
*
* This static method creates a new factory instance based
* on a system property setting or uses the platform default
* if no property has been defined.<p>
*
* The system property that controls which Factory implementation
* to create is named <code>&quot;javax.xml.parsers.SAXParserFactory&quot;</code>.
* This property names a class that is a concrete subclass of this
* abstract class. If no property is defined, a platform default
* will be used.</p>
*
* As the content is parsed by the underlying parser, methods of the
* given
* {@link org.xml.sax.helpers.DefaultHandler} are called.<p>
*
* Implementors of this class which wrap an underlaying implementation
* can consider using the {@link org.xml.sax.helpers.ParserAdapter}
* class to initially adapt their SAX1 implementation to work under
* this revised class.
*
* @author <a href="mailto:Jeff.Suttor@Sun.com">Jeff Suttor</a>
* @version $Revision: 1.8 $, $Date: 2010-11-01 04:36:09 $
*
* @author Joe Wang
* This is a subset of that in JAXP, javax.xml.parsers.SAXParser
*
*/
public abstract class SAXParser {
/**
* <p>Protected constructor to prevent instantiation.</p>
*/
protected SAXParser() {
}
/**
* Parse the content of the given {@link java.io.InputStream}
* instance as XML using the specified
* {@link org.xml.sax.helpers.DefaultHandler}.
*
* @param is InputStream containing the content to be parsed.
* @param dh The SAX DefaultHandler to use.
*
* @throws IllegalArgumentException If the given InputStream is null.
* @throws IOException If any IO errors occur.
* @throws SAXException If any SAX errors occur during processing.
*
* @see org.xml.sax.DocumentHandler
*/
public void parse(InputStream is, DefaultHandler dh)
throws SAXException, IOException
{
if (is == null) {
throw new IllegalArgumentException("InputStream cannot be null");
}
InputSource input = new InputSource(is);
this.parse(input, dh);
}
/**
* Parse the content described by the giving Uniform Resource
* Identifier (URI) as XML using the specified
* {@link org.xml.sax.helpers.DefaultHandler}.
*
* @param uri The location of the content to be parsed.
* @param dh The SAX DefaultHandler to use.
*
* @throws IllegalArgumentException If the uri is null.
* @throws IOException If any IO errors occur.
* @throws SAXException If any SAX errors occur during processing.
*
* @see org.xml.sax.DocumentHandler
*/
public void parse(String uri, DefaultHandler dh)
throws SAXException, IOException
{
if (uri == null) {
throw new IllegalArgumentException("uri cannot be null");
}
InputSource input = new InputSource(uri);
this.parse(input, dh);
}
/**
* Parse the content of the file specified as XML using the
* specified {@link org.xml.sax.helpers.DefaultHandler}.
*
* @param f The file containing the XML to parse
* @param dh The SAX DefaultHandler to use.
*
* @throws IllegalArgumentException If the File object is null.
* @throws IOException If any IO errors occur.
* @throws SAXException If any SAX errors occur during processing.
*
* @see org.xml.sax.DocumentHandler
*/
public void parse(File f, DefaultHandler dh)
throws SAXException, IOException
{
if (f == null) {
throw new IllegalArgumentException("File cannot be null");
}
//convert file to appropriate URI, f.toURI().toASCIIString()
//converts the URI to string as per rule specified in
//RFC 2396,
InputSource input = new InputSource(f.toURI().toASCIIString());
this.parse(input, dh);
}
/**
* Parse the content given {@link org.xml.sax.InputSource}
* as XML using the specified
* {@link org.xml.sax.helpers.DefaultHandler}.
*
* @param is The InputSource containing the content to be parsed.
* @param dh The SAX DefaultHandler to use.
*
* @throws IllegalArgumentException If the <code>InputSource</code> object
* is <code>null</code>.
* @throws IOException If any IO errors occur.
* @throws SAXException If any SAX errors occur during processing.
*
* @see org.xml.sax.DocumentHandler
*/
public void parse(InputSource is, DefaultHandler dh)
throws SAXException, IOException
{
if (is == null) {
throw new IllegalArgumentException("InputSource cannot be null");
}
XMLReader reader = this.getXMLReader();
if (dh != null) {
reader.setContentHandler(dh);
reader.setEntityResolver(dh);
reader.setErrorHandler(dh);
reader.setDTDHandler(dh);
}
reader.parse(is);
}
/**
* Returns the {@link org.xml.sax.XMLReader} that is encapsulated by the
* implementation of this class.
*
* @return The XMLReader that is encapsulated by the
* implementation of this class.
*
* @throws SAXException If any SAX errors occur during processing.
*/
public abstract XMLReader getXMLReader() throws SAXException;
/**
* Indicates whether or not this parser is configured to
* understand namespaces.
*
* @return true if this parser is configured to
* understand namespaces; false otherwise.
*/
public abstract boolean isNamespaceAware();
/**
* Indicates whether or not this parser is configured to
* validate XML documents.
*
* @return true if this parser is configured to
* validate XML documents; false otherwise.
*/
public abstract boolean isValidating();
/**
* <p>Get the XInclude processing mode for this parser.</p>
*
* @return
* the return value of
* the {@link SAXParserFactory#isXIncludeAware()}
* when this parser was created from factory.
*
* @throws UnsupportedOperationException When implementation does not
* override this method
*
* @since 1.5
*
* @see SAXParserFactory#setXIncludeAware(boolean)
*/
public boolean isXIncludeAware() {
throw new UnsupportedOperationException(
"This parser does not support specification \""
+ this.getClass().getPackage().getSpecificationTitle()
+ "\" version \""
+ this.getClass().getPackage().getSpecificationVersion()
+ "\"");
}
}

View file

@ -0,0 +1,90 @@
/*
* Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package jdk.internal.util.xml;
/**
* A copy of the StAX XMLStreamException without Location support
*
* The base exception for unexpected processing errors. This Exception
* class is used to report well-formedness errors as well as unexpected
* processing conditions.
* @version 1.0
* @author Copyright (c) 2009 by Oracle Corporation. All Rights Reserved.
* @since 1.6
*/
public class XMLStreamException extends Exception {
private static final long serialVersionUID = 1L;
protected Throwable nested;
/**
* Default constructor
*/
public XMLStreamException() {
super();
}
/**
* Construct an exception with the assocated message.
*
* @param msg the message to report
*/
public XMLStreamException(String msg) {
super(msg);
}
/**
* Construct an exception with the assocated exception
*
* @param th a nested exception
*/
public XMLStreamException(Throwable th) {
super(th);
nested = th;
}
/**
* Construct an exception with the assocated message and exception
*
* @param th a nested exception
* @param msg the message to report
*/
public XMLStreamException(String msg, Throwable th) {
super(msg, th);
nested = th;
}
/**
* Gets the nested exception.
*
* @return Nested exception
*/
public Throwable getNestedException() {
return nested;
}
}

View file

@ -0,0 +1,154 @@
/*
* Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package jdk.internal.util.xml;
/**
* Basic XMLStreamWriter for writing simple XML files such as those
* defined in java.util.Properties
*
* This is a subset of javax.xml.stream.XMLStreamWriter
*
* @author Joe Wang
*/
public interface XMLStreamWriter {
//Defaults the XML version to 1.0, and the encoding to utf-8
public final static String DEFAULT_XML_VERSION = "1.0";
public final static String DEFAULT_ENCODING = "UTF-8";
/**
* Writes a start tag to the output. All writeStartElement methods
* open a new scope in the internal namespace context. Writing the
* corresponding EndElement causes the scope to be closed.
* @param localName local name of the tag, may not be null
* @throws XMLStreamException
*/
public void writeStartElement(String localName) throws XMLStreamException;
/**
* Writes an empty element tag to the output
* @param localName local name of the tag, may not be null
* @throws XMLStreamException
*/
public void writeEmptyElement(String localName) throws XMLStreamException;
/**
* Writes an end tag to the output relying on the internal
* state of the writer to determine the prefix and local name
* of the event.
* @throws XMLStreamException
*/
public void writeEndElement() throws XMLStreamException;
/**
* Closes any start tags and writes corresponding end tags.
* @throws XMLStreamException
*/
public void writeEndDocument() throws XMLStreamException;
/**
* Close this writer and free any resources associated with the
* writer. This must not close the underlying output stream.
* @throws XMLStreamException
*/
public void close() throws XMLStreamException;
/**
* Write any cached data to the underlying output mechanism.
* @throws XMLStreamException
*/
public void flush() throws XMLStreamException;
/**
* Writes an attribute to the output stream without
* a prefix.
* @param localName the local name of the attribute
* @param value the value of the attribute
* @throws IllegalStateException if the current state does not allow Attribute writing
* @throws XMLStreamException
*/
public void writeAttribute(String localName, String value)
throws XMLStreamException;
/**
* Writes a CData section
* @param data the data contained in the CData Section, may not be null
* @throws XMLStreamException
*/
public void writeCData(String data) throws XMLStreamException;
/**
* Write a DTD section. This string represents the entire doctypedecl production
* from the XML 1.0 specification.
*
* @param dtd the DTD to be written
* @throws XMLStreamException
*/
public void writeDTD(String dtd) throws XMLStreamException;
/**
* Write the XML Declaration. Defaults the XML version to 1.0, and the encoding to utf-8
* @throws XMLStreamException
*/
public void writeStartDocument() throws XMLStreamException;
/**
* Write the XML Declaration. Defaults the the encoding to utf-8
* @param version version of the xml document
* @throws XMLStreamException
*/
public void writeStartDocument(String version) throws XMLStreamException;
/**
* Write the XML Declaration. Note that the encoding parameter does
* not set the actual encoding of the underlying output. That must
* be set when the instance of the XMLStreamWriter is created using the
* XMLOutputFactory
* @param encoding encoding of the xml declaration
* @param version version of the xml document
* @throws XMLStreamException If given encoding does not match encoding
* of the underlying stream
*/
public void writeStartDocument(String encoding, String version)
throws XMLStreamException;
/**
* Write text to the output
* @param text the value to write
* @throws XMLStreamException
*/
public void writeCharacters(String text) throws XMLStreamException;
/**
* Write text to the output
* @param text the value to write
* @param start the starting position in the array
* @param len the number of characters to write
* @throws XMLStreamException
*/
public void writeCharacters(char[] text, int start, int len)
throws XMLStreamException;
}

View file

@ -0,0 +1,430 @@
/*
* Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package jdk.internal.util.xml.impl;
import jdk.internal.org.xml.sax.Attributes;
public class Attrs implements Attributes {
/**
* Attributes string array. Each individual attribute is represented by four
* strings: namespace URL(+0), qname(+1), local name(+2), value(+3),
* type(+4), declared["d"] and default["D"](+5). In order to find attribute
* by the attrubute index, the attribute index MUST be multiplied by 8. The
* result will point to the attribute namespace URL.
*/
/* pkg */ String[] mItems;
/**
* Number of attributes in the attributes string array.
*/
private char mLength;
/**
* current index
*/
private char mAttrIdx = 0;
/**
* Constructor.
*/
public Attrs() {
// The default number of attributies capacity is 8.
mItems = new String[(8 << 3)];
}
/**
* Sets up the number of attributes and ensure the capacity of the attribute
* string array.
*
* @param length The number of attributes in the object.
*/
public void setLength(char length) {
if (length > ((char) (mItems.length >> 3))) {
mItems = new String[length << 3];
}
mLength = length;
}
/**
* Return the number of attributes in the list.
*
* <p>Once you know the number of attributes, you can iterate through the
* list.</p>
*
* @return The number of attributes in the list.
* @see #getURI(int)
* @see #getLocalName(int)
* @see #getQName(int)
* @see #getType(int)
* @see #getValue(int)
*/
public int getLength() {
return mLength;
}
/**
* Look up an attribute's Namespace URI by index.
*
* @param index The attribute index (zero-based).
* @return The Namespace URI, or the empty string if none is available, or
* null if the index is out of range.
* @see #getLength
*/
public String getURI(int index) {
return ((index >= 0) && (index < mLength))
? (mItems[index << 3])
: null;
}
/**
* Look up an attribute's local name by index.
*
* @param index The attribute index (zero-based).
* @return The local name, or the empty string if Namespace processing is
* not being performed, or null if the index is out of range.
* @see #getLength
*/
public String getLocalName(int index) {
return ((index >= 0) && (index < mLength))
? (mItems[(index << 3) + 2])
: null;
}
/**
* Look up an attribute's XML 1.0 qualified name by index.
*
* @param index The attribute index (zero-based).
* @return The XML 1.0 qualified name, or the empty string if none is
* available, or null if the index is out of range.
* @see #getLength
*/
public String getQName(int index) {
if ((index < 0) || (index >= mLength)) {
return null;
}
return mItems[(index << 3) + 1];
}
/**
* Look up an attribute's type by index.
*
* <p>The attribute type is one of the strings "CDATA", "ID", "IDREF",
* "IDREFS", "NMTOKEN", "NMTOKENS", "ENTITY", "ENTITIES", or "NOTATION"
* (always in upper case).</p>
*
* <p>If the parser has not read a declaration for the attribute, or if the
* parser does not report attribute types, then it must return the value
* "CDATA" as stated in the XML 1.0 Recommentation (clause 3.3.3,
* "Attribute-Value Normalization").</p>
*
* <p>For an enumerated attribute that is not a notation, the parser will
* report the type as "NMTOKEN".</p>
*
* @param index The attribute index (zero-based).
* @return The attribute's type as a string, or null if the index is out of
* range.
* @see #getLength
*/
public String getType(int index) {
return ((index >= 0) && (index < (mItems.length >> 3)))
? (mItems[(index << 3) + 4])
: null;
}
/**
* Look up an attribute's value by index.
*
* <p>If the attribute value is a list of tokens (IDREFS, ENTITIES, or
* NMTOKENS), the tokens will be concatenated into a single string with each
* token separated by a single space.</p>
*
* @param index The attribute index (zero-based).
* @return The attribute's value as a string, or null if the index is out of
* range.
* @see #getLength
*/
public String getValue(int index) {
return ((index >= 0) && (index < mLength))
? (mItems[(index << 3) + 3])
: null;
}
/**
* Look up the index of an attribute by Namespace name.
*
* @param uri The Namespace URI, or the empty string if the name has no
* Namespace URI.
* @param localName The attribute's local name.
* @return The index of the attribute, or -1 if it does not appear in the
* list.
*/
public int getIndex(String uri, String localName) {
char len = mLength;
for (char idx = 0; idx < len; idx++) {
if ((mItems[idx << 3]).equals(uri)
&& mItems[(idx << 3) + 2].equals(localName)) {
return idx;
}
}
return -1;
}
/**
* Look up the index of an attribute by Namespace name.
*
* @param uri The Namespace URI, or the empty string if the name has no
* Namespace URI. <code>null</code> value enforce the search by the local
* name only.
* @param localName The attribute's local name.
* @return The index of the attribute, or -1 if it does not appear in the
* list.
*/
/* pkg */ int getIndexNullNS(String uri, String localName) {
char len = mLength;
if (uri != null) {
for (char idx = 0; idx < len; idx++) {
if ((mItems[idx << 3]).equals(uri)
&& mItems[(idx << 3) + 2].equals(localName)) {
return idx;
}
}
} else {
for (char idx = 0; idx < len; idx++) {
if (mItems[(idx << 3) + 2].equals(localName)) {
return idx;
}
}
}
return -1;
}
/**
* Look up the index of an attribute by XML 1.0 qualified name.
*
* @param qName The qualified (prefixed) name.
* @return The index of the attribute, or -1 if it does not appear in the
* list.
*/
public int getIndex(String qName) {
char len = mLength;
for (char idx = 0; idx < len; idx++) {
if (mItems[(idx << 3) + 1].equals(qName)) {
return idx;
}
}
return -1;
}
/**
* Look up an attribute's type by Namespace name.
*
* <p>See {@link #getType(int) getType(int)} for a description of the
* possible types.</p>
*
* @param uri The Namespace URI, or the empty String if the name has no
* Namespace URI.
* @param localName The local name of the attribute.
* @return The attribute type as a string, or null if the attribute is not
* in the list or if Namespace processing is not being performed.
*/
public String getType(String uri, String localName) {
int idx = getIndex(uri, localName);
return (idx >= 0) ? (mItems[(idx << 3) + 4]) : null;
}
/**
* Look up an attribute's type by XML 1.0 qualified name.
*
* <p>See {@link #getType(int) getType(int)} for a description of the
* possible types.</p>
*
* @param qName The XML 1.0 qualified name.
* @return The attribute type as a string, or null if the attribute is not
* in the list or if qualified names are not available.
*/
public String getType(String qName) {
int idx = getIndex(qName);
return (idx >= 0) ? (mItems[(idx << 3) + 4]) : null;
}
/**
* Look up an attribute's value by Namespace name.
*
* <p>See {@link #getValue(int) getValue(int)} for a description of the
* possible values.</p>
*
* @param uri The Namespace URI, or the empty String if the name has no
* Namespace URI.
* @param localName The local name of the attribute.
* @return The attribute value as a string, or null if the attribute is not
* in the list.
*/
public String getValue(String uri, String localName) {
int idx = getIndex(uri, localName);
return (idx >= 0) ? (mItems[(idx << 3) + 3]) : null;
}
/**
* Look up an attribute's value by XML 1.0 qualified name.
*
* <p>See {@link #getValue(int) getValue(int)} for a description of the
* possible values.</p>
*
* @param qName The XML 1.0 qualified name.
* @return The attribute value as a string, or null if the attribute is not
* in the list or if qualified names are not available.
*/
public String getValue(String qName) {
int idx = getIndex(qName);
return (idx >= 0) ? (mItems[(idx << 3) + 3]) : null;
}
/**
* Returns false unless the attribute was declared in the DTD. This helps
* distinguish two kinds of attributes that SAX reports as CDATA: ones that
* were declared (and hence are usually valid), and those that were not (and
* which are never valid).
*
* @param index The attribute index (zero-based).
* @return true if the attribute was declared in the DTD, false otherwise.
* @exception java.lang.ArrayIndexOutOfBoundsException When the supplied
* index does not identify an attribute.
*/
public boolean isDeclared(int index) {
if ((index < 0) || (index >= mLength)) {
throw new ArrayIndexOutOfBoundsException("");
}
return ((mItems[(index << 3) + 5]) != null);
}
/**
* Returns false unless the attribute was declared in the DTD. This helps
* distinguish two kinds of attributes that SAX reports as CDATA: ones that
* were declared (and hence are usually valid), and those that were not (and
* which are never valid).
*
* @param qName The XML qualified (prefixed) name.
* @return true if the attribute was declared in the DTD, false otherwise.
* @exception java.lang.IllegalArgumentException When the supplied name does
* not identify an attribute.
*/
public boolean isDeclared(String qName) {
int idx = getIndex(qName);
if (idx < 0) {
throw new IllegalArgumentException("");
}
return ((mItems[(idx << 3) + 5]) != null);
}
/**
* Returns false unless the attribute was declared in the DTD. This helps
* distinguish two kinds of attributes that SAX reports as CDATA: ones that
* were declared (and hence are usually valid), and those that were not (and
* which are never valid).
*
* <p>Remember that since DTDs do not "understand" namespaces, the namespace
* URI associated with an attribute may not have come from the DTD. The
* declaration will have applied to the attribute's <em>qName</em>.
*
* @param uri The Namespace URI, or the empty string if the name has no
* Namespace URI.
* @param localName The attribute's local name.
* @return true if the attribute was declared in the DTD, false otherwise.
* @exception java.lang.IllegalArgumentException When the supplied names do
* not identify an attribute.
*/
public boolean isDeclared(String uri, String localName) {
int idx = getIndex(uri, localName);
if (idx < 0) {
throw new IllegalArgumentException("");
}
return ((mItems[(idx << 3) + 5]) != null);
}
/**
* Returns true unless the attribute value was provided by DTD defaulting.
*
* @param index The attribute index (zero-based).
* @return true if the value was found in the XML text, false if the value
* was provided by DTD defaulting.
* @exception java.lang.ArrayIndexOutOfBoundsException When the supplied
* index does not identify an attribute.
*/
public boolean isSpecified(int index) {
if ((index < 0) || (index >= mLength)) {
throw new ArrayIndexOutOfBoundsException("");
}
String str = mItems[(index << 3) + 5];
return ((str != null) ? (str.charAt(0) == 'd') : true);
}
/**
* Returns true unless the attribute value was provided by DTD defaulting.
*
* <p>Remember that since DTDs do not "understand" namespaces, the namespace
* URI associated with an attribute may not have come from the DTD. The
* declaration will have applied to the attribute's <em>qName</em>.
*
* @param uri The Namespace URI, or the empty string if the name has no
* Namespace URI.
* @param localName The attribute's local name.
* @return true if the value was found in the XML text, false if the value
* was provided by DTD defaulting.
* @exception java.lang.IllegalArgumentException When the supplied names do
* not identify an attribute.
*/
public boolean isSpecified(String uri, String localName) {
int idx = getIndex(uri, localName);
if (idx < 0) {
throw new IllegalArgumentException("");
}
String str = mItems[(idx << 3) + 5];
return ((str != null) ? (str.charAt(0) == 'd') : true);
}
/**
* Returns true unless the attribute value was provided by DTD defaulting.
*
* @param qName The XML qualified (prefixed) name.
* @return true if the value was found in the XML text, false if the value
* was provided by DTD defaulting.
* @exception java.lang.IllegalArgumentException When the supplied name does
* not identify an attribute.
*/
public boolean isSpecified(String qName) {
int idx = getIndex(qName);
if (idx < 0) {
throw new IllegalArgumentException("");
}
String str = mItems[(idx << 3) + 5];
return ((str != null) ? (str.charAt(0) == 'd') : true);
}
}

View file

@ -0,0 +1,83 @@
/*
* Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package jdk.internal.util.xml.impl;
import java.io.Reader;
/**
* A parsed entity input state.
*
* This class represents a parsed entity input state. The parser uses
* an instance of this class to manage input.
*/
public class Input {
/** The entity public identifier or null. */
public String pubid;
/** The entity systen identifier or null. */
public String sysid;
/** The encoding from XML declaration or null */
public String xmlenc;
/** The XML version from XML declaration or 0x0000 */
public char xmlver;
/** The entity reader. */
public Reader src;
/** The character buffer. */
public char[] chars;
/** The length of the character buffer. */
public int chLen;
/** The index of the next character to read. */
public int chIdx;
/** The next input in a chain. */
public Input next;
/**
* Constructor.
*
* @param buffsize The input buffer size.
*/
public Input(int buffsize) {
chars = new char[buffsize];
chLen = chars.length;
}
/**
* Constructor.
*
* @param buff The input buffer.
*/
public Input(char[] buff) {
chars = buff;
chLen = chars.length;
}
/**
* Constructor.
*/
public Input() {
}
}

View file

@ -0,0 +1,122 @@
/*
* Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package jdk.internal.util.xml.impl;
/**
* A name with value pair.
*
* This class keeps name with value pair with additional information and
* supports pair chaining.
*/
public class Pair {
/** The pair name. */
public String name;
/** The pair value. */
public String value;
/** The pair numeric value. */
public int num;
/** The characters of name. */
public char[] chars;
/** The pair identifier. */
public int id;
/** The list of associated pairs. */
public Pair list;
/** The next pair in a chain. */
public Pair next;
/**
* Creates a qualified name string from qualified name.
*
* @return The qualified name string.
*/
public String qname() {
return new String(chars, 1, chars.length - 1);
}
/**
* Creates a local name string from qualified name.
*
* @return The local name string.
*/
public String local() {
if (chars[0] != 0) {
return new String(chars, chars[0] + 1, chars.length - chars[0] - 1);
}
return new String(chars, 1, chars.length - 1);
}
/**
* Creates a prefix string from qualified name.
*
* @return The prefix string.
*/
public String pref() {
if (chars[0] != 0) {
return new String(chars, 1, chars[0] - 1);
}
return "";
}
/**
* Compares two qualified name prefixes.
*
* @param qname A qualified name.
* @return true if prefixes are equal.
*/
public boolean eqpref(char[] qname) {
if (chars[0] == qname[0]) {
char len = chars[0];
for (char i = 1; i < len; i += 1) {
if (chars[i] != qname[i]) {
return false;
}
}
return true;
}
return false;
}
/**
* Compares two qualified names.
*
* @param qname A qualified name.
* @return true if qualified names are equal.
*/
public boolean eqname(char[] qname) {
char len = (char) chars.length;
if (len == qname.length) {
for (char i = 0; i < len; i += 1) {
if (chars[i] != qname[i]) {
return false;
}
}
return true;
}
return false;
}
}

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,695 @@
/*
* Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package jdk.internal.util.xml.impl;
import java.io.IOException;
import java.io.InputStream;
import jdk.internal.org.xml.sax.ContentHandler;
import jdk.internal.org.xml.sax.DTDHandler;
import jdk.internal.org.xml.sax.EntityResolver;
import jdk.internal.org.xml.sax.ErrorHandler;
import jdk.internal.org.xml.sax.InputSource;
import jdk.internal.org.xml.sax.Locator;
import jdk.internal.org.xml.sax.SAXException;
import jdk.internal.org.xml.sax.SAXParseException;
import jdk.internal.org.xml.sax.XMLReader;
import jdk.internal.org.xml.sax.helpers.DefaultHandler;
/**
* XML non-validating push parser.
*
* This non-validating parser conforms to <a href="http://www.w3.org/TR/REC-xml"
* >Extensible Markup Language (XML) 1.0</a> and <a
* href="http://www.w3.org/TR/REC-xml-names" >"Namespaces in XML"</a>
* specifications. The API supported by the parser are <a
* href="http://java.sun.com/aboutJava/communityprocess/final/jsr030/index.html">CLDC
* 1.0</a> and <a href="http://www.jcp.org/en/jsr/detail?id=280">JSR-280</a>, a
* JavaME subset of <a href="http://java.sun.com/xml/jaxp/index.html">JAXP</a>
* and <a href="http://www.saxproject.org/">SAX2</a>.
*
* @see org.xml.sax.XMLReader
*/
final class ParserSAX
extends Parser implements XMLReader, Locator
{
public final static String FEATURE_NS =
"http://xml.org/sax/features/namespaces";
public final static String FEATURE_PREF =
"http://xml.org/sax/features/namespace-prefixes";
// SAX feature flags
private boolean mFNamespaces;
private boolean mFPrefixes;
// SAX handlers
private DefaultHandler mHand; // the default handler
private ContentHandler mHandCont; // the content handler
private DTDHandler mHandDtd; // the DTD handler
private ErrorHandler mHandErr; // the error handler
private EntityResolver mHandEnt; // the entity resolver
/**
* Constructor.
*/
public ParserSAX() {
super();
// SAX feature defaut values
mFNamespaces = true;
mFPrefixes = false;
// Default handler which will be used in case the application
// do not set one of handlers.
mHand = new DefaultHandler();
mHandCont = mHand;
mHandDtd = mHand;
mHandErr = mHand;
mHandEnt = mHand;
}
/**
* Return the current content handler.
*
* @return The current content handler, or null if none has been registered.
* @see #setContentHandler
*/
public ContentHandler getContentHandler() {
return (mHandCont != mHand) ? mHandCont : null;
}
/**
* Allow an application to register a content event handler.
*
* <p>If the application does not register a content handler, all content
* events reported by the SAX parser will be silently ignored.</p>
*
* <p>Applications may register a new or different handler in the middle of
* a parse, and the SAX parser must begin using the new handler
* immediately.</p>
*
* @param handler The content handler.
* @exception java.lang.NullPointerException If the handler argument is
* null.
* @see #getContentHandler
*/
public void setContentHandler(ContentHandler handler) {
if (handler == null) {
throw new NullPointerException();
}
mHandCont = handler;
}
/**
* Return the current DTD handler.
*
* @return The current DTD handler, or null if none has been registered.
* @see #setDTDHandler
*/
public DTDHandler getDTDHandler() {
return (mHandDtd != mHand) ? mHandDtd : null;
}
/**
* Allow an application to register a DTD event handler.
*
* <p>If the application does not register a DTD handler, all DTD events
* reported by the SAX parser will be silently ignored.</p>
*
* <p>Applications may register a new or different handler in the middle of
* a parse, and the SAX parser must begin using the new handler
* immediately.</p>
*
* @param handler The DTD handler.
* @exception java.lang.NullPointerException If the handler argument is
* null.
* @see #getDTDHandler
*/
public void setDTDHandler(DTDHandler handler) {
if (handler == null) {
throw new NullPointerException();
}
mHandDtd = handler;
}
/**
* Return the current error handler.
*
* @return The current error handler, or null if none has been registered.
* @see #setErrorHandler
*/
public ErrorHandler getErrorHandler() {
return (mHandErr != mHand) ? mHandErr : null;
}
/**
* Allow an application to register an error event handler.
*
* <p>If the application does not register an error handler, all error
* events reported by the SAX parser will be silently ignored; however,
* normal processing may not continue. It is highly recommended that all SAX
* applications implement an error handler to avoid unexpected bugs.</p>
*
* <p>Applications may register a new or different handler in the middle of
* a parse, and the SAX parser must begin using the new handler
* immediately.</p>
*
* @param handler The error handler.
* @exception java.lang.NullPointerException If the handler argument is
* null.
* @see #getErrorHandler
*/
public void setErrorHandler(ErrorHandler handler) {
if (handler == null) {
throw new NullPointerException();
}
mHandErr = handler;
}
/**
* Return the current entity resolver.
*
* @return The current entity resolver, or null if none has been registered.
* @see #setEntityResolver
*/
public EntityResolver getEntityResolver() {
return (mHandEnt != mHand) ? mHandEnt : null;
}
/**
* Allow an application to register an entity resolver.
*
* <p>If the application does not register an entity resolver, the XMLReader
* will perform its own default resolution.</p>
*
* <p>Applications may register a new or different resolver in the middle of
* a parse, and the SAX parser must begin using the new resolver
* immediately.</p>
*
* @param resolver The entity resolver.
* @exception java.lang.NullPointerException If the resolver argument is
* null.
* @see #getEntityResolver
*/
public void setEntityResolver(EntityResolver resolver) {
if (resolver == null) {
throw new NullPointerException();
}
mHandEnt = resolver;
}
/**
* Return the public identifier for the current document event.
*
* <p>The return value is the public identifier of the document entity or of
* the external parsed entity in which the markup triggering the event
* appears.</p>
*
* @return A string containing the public identifier, or null if none is
* available.
*
* @see #getSystemId
*/
public String getPublicId() {
return (mInp != null) ? mInp.pubid : null;
}
/**
* Return the system identifier for the current document event.
*
* <p>The return value is the system identifier of the document entity or of
* the external parsed entity in which the markup triggering the event
* appears.</p>
*
* <p>If the system identifier is a URL, the parser must resolve it fully
* before passing it to the application.</p>
*
* @return A string containing the system identifier, or null if none is
* available.
*
* @see #getPublicId
*/
public String getSystemId() {
return (mInp != null) ? mInp.sysid : null;
}
/**
* Return the line number where the current document event ends.
*
* @return Always returns -1 indicating the line number is not available.
*
* @see #getColumnNumber
*/
public int getLineNumber() {
return -1;
}
/**
* Return the column number where the current document event ends.
*
* @return Always returns -1 indicating the column number is not available.
*
* @see #getLineNumber
*/
public int getColumnNumber() {
return -1;
}
/**
* Parse an XML document from a system identifier (URI).
*
* <p>This method is a shortcut for the common case of reading a document
* from a system identifier. It is the exact equivalent of the
* following:</p>
*
* <pre>
* parse(new InputSource(systemId));
* </pre>
*
* <p>If the system identifier is a URL, it must be fully resolved by the
* application before it is passed to the parser.</p>
*
* @param systemId The system identifier (URI).
* @exception org.xml.sax.SAXException Any SAX exception, possibly wrapping
* another exception.
* @exception java.io.IOException An IO exception from the parser, possibly
* from a byte stream or character stream supplied by the application.
* @see #parse(org.xml.sax.InputSource)
*/
public void parse(String systemId) throws IOException, SAXException {
parse(new InputSource(systemId));
}
/**
* Parse an XML document.
*
* <p>The application can use this method to instruct the XML reader to
* begin parsing an XML document from any valid input source (a character
* stream, a byte stream, or a URI).</p>
*
* <p>Applications may not invoke this method while a parse is in progress
* (they should create a new XMLReader instead for each nested XML
* document). Once a parse is complete, an application may reuse the same
* XMLReader object, possibly with a different input source.</p>
*
* <p>During the parse, the XMLReader will provide information about the XML
* document through the registered event handlers.</p>
*
* <p>This method is synchronous: it will not return until parsing has
* ended. If a client application wants to terminate parsing early, it
* should throw an exception.</p>
*
* @param is The input source for the top-level of the XML document.
* @exception org.xml.sax.SAXException Any SAX exception, possibly wrapping
* another exception.
* @exception java.io.IOException An IO exception from the parser, possibly
* from a byte stream or character stream supplied by the application.
* @see org.xml.sax.InputSource
* @see #parse(java.lang.String)
* @see #setEntityResolver
* @see #setDTDHandler
* @see #setContentHandler
* @see #setErrorHandler
*/
public void parse(InputSource is) throws IOException, SAXException {
if (is == null) {
throw new IllegalArgumentException("");
}
// Set up the document
mInp = new Input(BUFFSIZE_READER);
mPh = PH_BEFORE_DOC; // before parsing
try {
setinp(is);
} catch (SAXException saxe) {
throw saxe;
} catch (IOException ioe) {
throw ioe;
} catch (RuntimeException rte) {
throw rte;
} catch (Exception e) {
panic(e.toString());
}
parse();
}
/**
* Parse the content of the given {@link java.io.InputStream} instance as
* XML using the specified {@link org.xml.sax.helpers.DefaultHandler}.
*
* @param src InputStream containing the content to be parsed.
* @param handler The SAX DefaultHandler to use.
* @exception IOException If any IO errors occur.
* @exception IllegalArgumentException If the given InputStream or handler
* is null.
* @exception SAXException If the underlying parser throws a SAXException
* while parsing.
* @see org.xml.sax.helpers.DefaultHandler
*/
public void parse(InputStream src, DefaultHandler handler)
throws SAXException, IOException {
if ((src == null) || (handler == null)) {
throw new IllegalArgumentException("");
}
parse(new InputSource(src), handler);
}
/**
* Parse the content given {@link org.xml.sax.InputSource} as XML using the
* specified {@link org.xml.sax.helpers.DefaultHandler}.
*
* @param is The InputSource containing the content to be parsed.
* @param handler The SAX DefaultHandler to use.
* @exception IOException If any IO errors occur.
* @exception IllegalArgumentException If the InputSource or handler is
* null.
* @exception SAXException If the underlying parser throws a SAXException
* while parsing.
* @see org.xml.sax.helpers.DefaultHandler
*/
public void parse(InputSource is, DefaultHandler handler)
throws SAXException, IOException
{
if ((is == null) || (handler == null)) {
throw new IllegalArgumentException("");
}
// Set up the handler
mHandCont = handler;
mHandDtd = handler;
mHandErr = handler;
mHandEnt = handler;
// Set up the document
mInp = new Input(BUFFSIZE_READER);
mPh = PH_BEFORE_DOC; // before parsing
try {
setinp(is);
} catch (SAXException | IOException | RuntimeException saxe) {
throw saxe;
} catch (Exception e) {
panic(e.toString());
}
parse();
}
/**
* Parse the XML document content using specified handlers and an input
* source.
*
* @exception IOException If any IO errors occur.
* @exception SAXException If the underlying parser throws a SAXException
* while parsing.
*/
@SuppressWarnings("fallthrough")
private void parse() throws SAXException, IOException {
init();
try {
mHandCont.setDocumentLocator(this);
mHandCont.startDocument();
if (mPh != PH_MISC_DTD) {
mPh = PH_MISC_DTD; // misc before DTD
}
int evt = EV_NULL;
// XML document prolog
do {
wsskip();
switch (evt = step()) {
case EV_ELM:
case EV_ELMS:
mPh = PH_DOCELM;
break;
case EV_COMM:
case EV_PI:
break;
case EV_DTD:
if (mPh >= PH_DTD_MISC) {
panic(FAULT);
}
mPh = PH_DTD_MISC; // misc after DTD
break;
default:
panic(FAULT);
}
} while (mPh < PH_DOCELM); // misc before DTD
// XML document starting with document's element
do {
switch (evt) {
case EV_ELM:
case EV_ELMS:
// Report the element
if (mIsNSAware == true) {
mHandCont.startElement(
mElm.value,
mElm.name,
"",
mAttrs);
} else {
mHandCont.startElement(
"",
"",
mElm.name,
mAttrs);
}
if (evt == EV_ELMS) {
evt = step();
break;
}
case EV_ELME:
// Report the end of element
if (mIsNSAware == true) {
mHandCont.endElement(mElm.value, mElm.name, "");
} else {
mHandCont.endElement("", "", mElm.name);
}
// Restore the top of the prefix stack
while (mPref.list == mElm) {
mHandCont.endPrefixMapping(mPref.name);
mPref = del(mPref);
}
// Remove the top element tag
mElm = del(mElm);
if (mElm == null) {
mPh = PH_DOCELM_MISC;
} else {
evt = step();
}
break;
case EV_TEXT:
case EV_WSPC:
case EV_CDAT:
case EV_COMM:
case EV_PI:
case EV_ENT:
evt = step();
break;
default:
panic(FAULT);
}
} while (mPh == PH_DOCELM);
// Misc after document's element
do {
if (wsskip() == EOS) {
break;
}
switch (step()) {
case EV_COMM:
case EV_PI:
break;
default:
panic(FAULT);
}
} while (mPh == PH_DOCELM_MISC);
mPh = PH_AFTER_DOC; // parsing is completed
} catch (SAXException saxe) {
throw saxe;
} catch (IOException ioe) {
throw ioe;
} catch (RuntimeException rte) {
throw rte;
} catch (Exception e) {
panic(e.toString());
} finally {
mHandCont.endDocument();
cleanup();
}
}
/**
* Reports document type.
*
* @param name The name of the entity.
* @param pubid The public identifier of the entity or <code>null</code>.
* @param sysid The system identifier of the entity or <code>null</code>.
*/
protected void docType(String name, String pubid, String sysid) throws SAXException {
mHandDtd.notationDecl(name, pubid, sysid);
}
/**
* Reports a comment.
*
* @param text The comment text starting from first charcater.
* @param length The number of characters in comment.
*/
protected void comm(char[] text, int length) {
}
/**
* Reports a processing instruction.
*
* @param target The processing instruction target name.
* @param body The processing instruction body text.
*/
protected void pi(String target, String body) throws SAXException {
mHandCont.processingInstruction(target, body);
}
/**
* Reports new namespace prefix. The Namespace prefix (
* <code>mPref.name</code>) being declared and the Namespace URI (
* <code>mPref.value</code>) the prefix is mapped to. An empty string is
* used for the default element namespace, which has no prefix.
*/
protected void newPrefix() throws SAXException {
mHandCont.startPrefixMapping(mPref.name, mPref.value);
}
/**
* Reports skipped entity name.
*
* @param name The entity name.
*/
protected void skippedEnt(String name) throws SAXException {
mHandCont.skippedEntity(name);
}
/**
* Returns an
* <code>InputSource</code> for specified entity or
* <code>null</code>.
*
* @param name The name of the entity.
* @param pubid The public identifier of the entity.
* @param sysid The system identifier of the entity.
*/
protected InputSource resolveEnt(String name, String pubid, String sysid)
throws SAXException, IOException
{
return mHandEnt.resolveEntity(pubid, sysid);
}
/**
* Reports notation declaration.
*
* @param name The notation's name.
* @param pubid The notation's public identifier, or null if none was given.
* @param sysid The notation's system identifier, or null if none was given.
*/
protected void notDecl(String name, String pubid, String sysid)
throws SAXException
{
mHandDtd.notationDecl(name, pubid, sysid);
}
/**
* Reports unparsed entity name.
*
* @param name The unparsed entity's name.
* @param pubid The entity's public identifier, or null if none was given.
* @param sysid The entity's system identifier.
* @param notation The name of the associated notation.
*/
protected void unparsedEntDecl(String name, String pubid, String sysid, String notation)
throws SAXException
{
mHandDtd.unparsedEntityDecl(name, pubid, sysid, notation);
}
/**
* Notifies the handler about fatal parsing error.
*
* @param msg The problem description message.
*/
protected void panic(String msg) throws SAXException {
SAXParseException spe = new SAXParseException(msg, this);
mHandErr.fatalError(spe);
throw spe; // [#1.2] fatal error definition
}
/**
* Reports characters and empties the parser's buffer. This method is called
* only if parser is going to return control to the main loop. This means
* that this method may use parser buffer to report white space without
* copeing characters to temporary buffer.
*/
protected void bflash() throws SAXException {
if (mBuffIdx >= 0) {
// Textual data has been read
mHandCont.characters(mBuff, 0, (mBuffIdx + 1));
mBuffIdx = -1;
}
}
/**
* Reports white space characters and empties the parser's buffer. This
* method is called only if parser is going to return control to the main
* loop. This means that this method may use parser buffer to report white
* space without copeing characters to temporary buffer.
*/
protected void bflash_ws() throws SAXException {
if (mBuffIdx >= 0) {
// BUG: With additional info from DTD and xml:space attr [#2.10]
// the following call can be supported:
// mHandCont.ignorableWhitespace(mBuff, 0, (mBuffIdx + 1));
// Textual data has been read
mHandCont.characters(mBuff, 0, (mBuffIdx + 1));
mBuffIdx = -1;
}
}
public boolean getFeature(String name) {
throw new UnsupportedOperationException("Not supported yet.");
}
public void setFeature(String name, boolean value) {
throw new UnsupportedOperationException("Not supported yet.");
}
public Object getProperty(String name) {
throw new UnsupportedOperationException("Not supported yet.");
}
public void setProperty(String name, Object value) {
throw new UnsupportedOperationException("Not supported yet.");
}
}

View file

@ -0,0 +1,122 @@
/*
* Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package jdk.internal.util.xml.impl;
import java.io.Reader;
import java.io.InputStream;
import java.io.IOException;
/**
* UTF-16 encoded stream reader.
*/
public class ReaderUTF16 extends Reader {
private InputStream is;
private char bo;
/**
* Constructor.
*
* Byte order argument can be: 'l' for little-endian or 'b' for big-endian.
*
* @param is A byte input stream.
* @param bo A byte order in the input stream.
*/
public ReaderUTF16(InputStream is, char bo) {
switch (bo) {
case 'l':
break;
case 'b':
break;
default:
throw new IllegalArgumentException("");
}
this.bo = bo;
this.is = is;
}
/**
* Reads characters into a portion of an array.
*
* @param cbuf Destination buffer.
* @param off Offset at which to start storing characters.
* @param len Maximum number of characters to read.
* @exception IOException If any IO errors occur.
*/
public int read(char[] cbuf, int off, int len) throws IOException {
int num = 0;
int val;
if (bo == 'b') {
while (num < len) {
if ((val = is.read()) < 0) {
return (num != 0) ? num : -1;
}
cbuf[off++] = (char) ((val << 8) | (is.read() & 0xff));
num++;
}
} else {
while (num < len) {
if ((val = is.read()) < 0) {
return (num != 0) ? num : -1;
}
cbuf[off++] = (char) ((is.read() << 8) | (val & 0xff));
num++;
}
}
return num;
}
/**
* Reads a single character.
*
* @return The character read, as an integer in the range 0 to 65535
* (0x0000-0xffff), or -1 if the end of the stream has been reached.
* @exception IOException If any IO errors occur.
*/
public int read() throws IOException {
int val;
if ((val = is.read()) < 0) {
return -1;
}
if (bo == 'b') {
val = (char) ((val << 8) | (is.read() & 0xff));
} else {
val = (char) ((is.read() << 8) | (val & 0xff));
}
return val;
}
/**
* Closes the stream.
*
* @exception IOException If any IO errors occur.
*/
public void close() throws IOException {
is.close();
}
}

View file

@ -0,0 +1,138 @@
/*
* Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package jdk.internal.util.xml.impl;
import java.io.Reader;
import java.io.InputStream;
import java.io.IOException;
import java.io.UnsupportedEncodingException;
/**
* UTF-8 transformed UCS-2 character stream reader.
*
* This reader converts UTF-8 transformed UCS-2 characters to Java characters.
* The UCS-2 subset of UTF-8 transformation is described in RFC-2279 #2
* "UTF-8 definition":
* 0000 0000-0000 007F 0xxxxxxx
* 0000 0080-0000 07FF 110xxxxx 10xxxxxx
* 0000 0800-0000 FFFF 1110xxxx 10xxxxxx 10xxxxxx
*
* This reader will return incorrect last character on broken UTF-8 stream.
*/
public class ReaderUTF8 extends Reader {
private InputStream is;
/**
* Constructor.
*
* @param is A byte input stream.
*/
public ReaderUTF8(InputStream is) {
this.is = is;
}
/**
* Reads characters into a portion of an array.
*
* @param cbuf Destination buffer.
* @param off Offset at which to start storing characters.
* @param len Maximum number of characters to read.
* @exception IOException If any IO errors occur.
* @exception UnsupportedEncodingException If UCS-4 character occur in the stream.
*/
public int read(char[] cbuf, int off, int len) throws IOException {
int num = 0;
int val;
while (num < len) {
if ((val = is.read()) < 0) {
return (num != 0) ? num : -1;
}
switch (val & 0xf0) {
case 0xc0:
case 0xd0:
cbuf[off++] = (char) (((val & 0x1f) << 6) | (is.read() & 0x3f));
break;
case 0xe0:
cbuf[off++] = (char) (((val & 0x0f) << 12)
| ((is.read() & 0x3f) << 6) | (is.read() & 0x3f));
break;
case 0xf0: // UCS-4 character
throw new UnsupportedEncodingException("UTF-32 (or UCS-4) encoding not supported.");
default:
cbuf[off++] = (char) val;
break;
}
num++;
}
return num;
}
/**
* Reads a single character.
*
* @return The character read, as an integer in the range 0 to 65535
* (0x00-0xffff), or -1 if the end of the stream has been reached.
* @exception IOException If any IO errors occur.
* @exception UnsupportedEncodingException If UCS-4 character occur in the stream.
*/
public int read() throws IOException {
int val;
if ((val = is.read()) < 0) {
return -1;
}
switch (val & 0xf0) {
case 0xc0:
case 0xd0:
val = ((val & 0x1f) << 6) | (is.read() & 0x3f);
break;
case 0xe0:
val = ((val & 0x0f) << 12)
| ((is.read() & 0x3f) << 6) | (is.read() & 0x3f);
break;
case 0xf0: // UCS-4 character
throw new UnsupportedEncodingException();
default:
break;
}
return val;
}
/**
* Closes the stream.
*
* @exception IOException If any IO errors occur.
*/
public void close() throws IOException {
is.close();
}
}

View file

@ -0,0 +1,118 @@
/*
* Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package jdk.internal.util.xml.impl;
import java.io.IOException;
import java.io.InputStream;
import jdk.internal.org.xml.sax.InputSource;
import jdk.internal.org.xml.sax.SAXException;
import jdk.internal.org.xml.sax.XMLReader;
import jdk.internal.org.xml.sax.helpers.DefaultHandler;
import jdk.internal.util.xml.SAXParser;
public class SAXParserImpl extends SAXParser {
private ParserSAX parser;
public SAXParserImpl() {
super();
parser = new ParserSAX();
}
/**
* Returns the {@link org.xml.sax.XMLReader} that is encapsulated by the
* implementation of this class.
*
* @return The XMLReader that is encapsulated by the
* implementation of this class.
*
* @throws SAXException If any SAX errors occur during processing.
*/
public XMLReader getXMLReader()
throws SAXException {
return parser;
}
/**
* Indicates whether or not this parser is configured to
* understand namespaces.
*
* @return true if this parser is configured to
* understand namespaces; false otherwise.
*/
public boolean isNamespaceAware() {
return parser.mIsNSAware;
}
/**
* Indicates whether or not this parser is configured to validate
* XML documents.
*
* @return true if this parser is configured to validate XML
* documents; false otherwise.
*/
public boolean isValidating() {
return false;
}
/**
* Parse the content of the given {@link java.io.InputStream}
* instance as XML using the specified
* {@link org.xml.sax.helpers.DefaultHandler}.
*
* @param src InputStream containing the content to be parsed.
* @param handler The SAX DefaultHandler to use.
* @exception IOException If any IO errors occur.
* @exception IllegalArgumentException If the given InputStream or handler is null.
* @exception SAXException If the underlying parser throws a
* SAXException while parsing.
* @see org.xml.sax.helpers.DefaultHandler
*/
public void parse(InputStream src, DefaultHandler handler)
throws SAXException, IOException
{
parser.parse(src, handler);
}
/**
* Parse the content given {@link org.xml.sax.InputSource}
* as XML using the specified
* {@link org.xml.sax.helpers.DefaultHandler}.
*
* @param is The InputSource containing the content to be parsed.
* @param handler The SAX DefaultHandler to use.
* @exception IOException If any IO errors occur.
* @exception IllegalArgumentException If the InputSource or handler is null.
* @exception SAXException If the underlying parser throws a
* SAXException while parsing.
* @see org.xml.sax.helpers.DefaultHandler
*/
public void parse(InputSource is, DefaultHandler handler)
throws SAXException, IOException
{
parser.parse(is, handler);
}
}

View file

@ -0,0 +1,633 @@
/*
* Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package jdk.internal.util.xml.impl;
import java.io.OutputStream;
import java.io.UnsupportedEncodingException;
import java.nio.charset.Charset;
import java.nio.charset.IllegalCharsetNameException;
import java.nio.charset.UnsupportedCharsetException;
import jdk.internal.util.xml.XMLStreamException;
import jdk.internal.util.xml.XMLStreamWriter;
/**
* Implementation of a reduced version of XMLStreamWriter
*
* @author Joe Wang
*/
public class XMLStreamWriterImpl implements XMLStreamWriter {
//Document state
static final int STATE_XML_DECL = 1;
static final int STATE_PROLOG = 2;
static final int STATE_DTD_DECL = 3;
static final int STATE_ELEMENT = 4;
//Element state
static final int ELEMENT_STARTTAG_OPEN = 10;
static final int ELEMENT_STARTTAG_CLOSE = 11;
static final int ELEMENT_ENDTAG_OPEN = 12;
static final int ELEMENT_ENDTAG_CLOSE = 13;
public static final char CLOSE_START_TAG = '>';
public static final char OPEN_START_TAG = '<';
public static final String OPEN_END_TAG = "</";
public static final char CLOSE_END_TAG = '>';
public static final String START_CDATA = "<![CDATA[";
public static final String END_CDATA = "]]>";
public static final String CLOSE_EMPTY_ELEMENT = "/>";
public static final String ENCODING_PREFIX = "&#x";
public static final char SPACE = ' ';
public static final char AMPERSAND = '&';
public static final char DOUBLEQUOT = '"';
public static final char SEMICOLON = ';';
//current state
private int _state = 0;
private Element _currentEle;
private XMLWriter _writer;
private String _encoding;
/**
* This flag can be used to turn escaping off for content. It does
* not apply to attribute content.
*/
boolean _escapeCharacters = true;
//pretty print by default
private boolean _doIndent = true;
//The system line separator for writing out line breaks.
private char[] _lineSep =
System.getProperty("line.separator").toCharArray();
public XMLStreamWriterImpl(OutputStream os) throws XMLStreamException {
this(os, XMLStreamWriter.DEFAULT_ENCODING);
}
public XMLStreamWriterImpl(OutputStream os, String encoding)
throws XMLStreamException
{
Charset cs = null;
if (encoding == null) {
_encoding = XMLStreamWriter.DEFAULT_ENCODING;
} else {
try {
cs = getCharset(encoding);
} catch (UnsupportedEncodingException e) {
throw new XMLStreamException(e);
}
this._encoding = encoding;
}
_writer = new XMLWriter(os, encoding, cs);
}
/**
* Write the XML Declaration. Defaults the XML version to 1.0, and the
* encoding to utf-8.
*
* @throws XMLStreamException
*/
public void writeStartDocument() throws XMLStreamException {
writeStartDocument(_encoding, XMLStreamWriter.DEFAULT_XML_VERSION);
}
/**
* Write the XML Declaration. Defaults the encoding to utf-8
*
* @param version version of the xml document
* @throws XMLStreamException
*/
public void writeStartDocument(String version) throws XMLStreamException {
writeStartDocument(_encoding, version, null);
}
/**
* Write the XML Declaration. Note that the encoding parameter does not set
* the actual encoding of the underlying output. That must be set when the
* instance of the XMLStreamWriter is created
*
* @param encoding encoding of the xml declaration
* @param version version of the xml document
* @throws XMLStreamException If given encoding does not match encoding of the
* underlying stream
*/
public void writeStartDocument(String encoding, String version) throws XMLStreamException {
writeStartDocument(encoding, version, null);
}
/**
* Write the XML Declaration. Note that the encoding parameter does not set
* the actual encoding of the underlying output. That must be set when the
* instance of the XMLStreamWriter is created
*
* @param encoding encoding of the xml declaration
* @param version version of the xml document
* @param standalone indicate if the xml document is standalone
* @throws XMLStreamException If given encoding does not match encoding of the
* underlying stream
*/
public void writeStartDocument(String encoding, String version, String standalone)
throws XMLStreamException
{
if (_state > 0) {
throw new XMLStreamException("XML declaration must be as the first line in the XML document.");
}
_state = STATE_XML_DECL;
String enc = encoding;
if (enc == null) {
enc = _encoding;
} else {
//check if the encoding is supported
try {
getCharset(encoding);
} catch (UnsupportedEncodingException e) {
throw new XMLStreamException(e);
}
}
if (version == null) {
version = XMLStreamWriter.DEFAULT_XML_VERSION;
}
_writer.write("<?xml version=\"");
_writer.write(version);
_writer.write(DOUBLEQUOT);
if (enc != null) {
_writer.write(" encoding=\"");
_writer.write(enc);
_writer.write(DOUBLEQUOT);
}
if (standalone != null) {
_writer.write(" standalone=\"");
_writer.write(standalone);
_writer.write(DOUBLEQUOT);
}
_writer.write("?>");
writeLineSeparator();
}
/**
* Write a DTD section. This string represents the entire doctypedecl production
* from the XML 1.0 specification.
*
* @param dtd the DTD to be written
* @throws XMLStreamException
*/
public void writeDTD(String dtd) throws XMLStreamException {
if (_currentEle != null && _currentEle.getState() == ELEMENT_STARTTAG_OPEN) {
closeStartTag();
}
_writer.write(dtd);
writeLineSeparator();
}
/**
* Writes a start tag to the output.
* @param localName local name of the tag, may not be null
* @throws XMLStreamException
*/
public void writeStartElement(String localName) throws XMLStreamException {
if (localName == null || localName.length() == 0) {
throw new XMLStreamException("Local Name cannot be null or empty");
}
_state = STATE_ELEMENT;
if (_currentEle != null && _currentEle.getState() == ELEMENT_STARTTAG_OPEN) {
closeStartTag();
}
_currentEle = new Element(_currentEle, localName, false);
openStartTag();
_writer.write(localName);
}
/**
* Writes an empty element tag to the output
* @param localName local name of the tag, may not be null
* @throws XMLStreamException
*/
public void writeEmptyElement(String localName) throws XMLStreamException {
if (_currentEle != null && _currentEle.getState() == ELEMENT_STARTTAG_OPEN) {
closeStartTag();
}
_currentEle = new Element(_currentEle, localName, true);
openStartTag();
_writer.write(localName);
}
/**
* Writes an attribute to the output stream without a prefix.
* @param localName the local name of the attribute
* @param value the value of the attribute
* @throws IllegalStateException if the current state does not allow Attribute writing
* @throws XMLStreamException
*/
public void writeAttribute(String localName, String value) throws XMLStreamException {
if (_currentEle.getState() != ELEMENT_STARTTAG_OPEN) {
throw new XMLStreamException(
"Attribute not associated with any element");
}
_writer.write(SPACE);
_writer.write(localName);
_writer.write("=\"");
writeXMLContent(
value,
true, // true = escapeChars
true); // true = escapeDoubleQuotes
_writer.write(DOUBLEQUOT);
}
public void writeEndDocument() throws XMLStreamException {
if (_currentEle != null && _currentEle.getState() == ELEMENT_STARTTAG_OPEN) {
closeStartTag();
}
/**
* close unclosed elements if any
*/
while (_currentEle != null) {
if (!_currentEle.isEmpty()) {
_writer.write(OPEN_END_TAG);
_writer.write(_currentEle.getLocalName());
_writer.write(CLOSE_END_TAG);
}
_currentEle = _currentEle.getParent();
}
}
public void writeEndElement() throws XMLStreamException {
if (_currentEle != null && _currentEle.getState() == ELEMENT_STARTTAG_OPEN) {
closeStartTag();
}
if (_currentEle == null) {
throw new XMLStreamException("No element was found to write");
}
if (_currentEle.isEmpty()) {
return;
}
_writer.write(OPEN_END_TAG);
_writer.write(_currentEle.getLocalName());
_writer.write(CLOSE_END_TAG);
writeLineSeparator();
_currentEle = _currentEle.getParent();
}
public void writeCData(String cdata) throws XMLStreamException {
if (cdata == null) {
throw new XMLStreamException("cdata cannot be null");
}
if (_currentEle != null && _currentEle.getState() == ELEMENT_STARTTAG_OPEN) {
closeStartTag();
}
_writer.write(START_CDATA);
_writer.write(cdata);
_writer.write(END_CDATA);
}
public void writeCharacters(String data) throws XMLStreamException {
if (_currentEle != null && _currentEle.getState() == ELEMENT_STARTTAG_OPEN) {
closeStartTag();
}
writeXMLContent(data);
}
public void writeCharacters(char[] data, int start, int len)
throws XMLStreamException {
if (_currentEle != null && _currentEle.getState() == ELEMENT_STARTTAG_OPEN) {
closeStartTag();
}
writeXMLContent(data, start, len, _escapeCharacters);
}
/**
* Close this XMLStreamWriter by closing underlying writer.
*/
public void close() throws XMLStreamException {
if (_writer != null) {
_writer.close();
}
_writer = null;
_currentEle = null;
_state = 0;
}
/**
* Flush this XMLStreamWriter by flushing underlying writer.
*/
public void flush() throws XMLStreamException {
if (_writer != null) {
_writer.flush();
}
}
/**
* Set the flag to indicate if the writer should add line separator
* @param doIndent
*/
public void setDoIndent(boolean doIndent) {
_doIndent = doIndent;
}
/**
* Writes XML content to underlying writer. Escapes characters unless
* escaping character feature is turned off.
*/
private void writeXMLContent(char[] content, int start, int length, boolean escapeChars)
throws XMLStreamException
{
if (!escapeChars) {
_writer.write(content, start, length);
return;
}
// Index of the next char to be written
int startWritePos = start;
final int end = start + length;
for (int index = start; index < end; index++) {
char ch = content[index];
if (!_writer.canEncode(ch)) {
_writer.write(content, startWritePos, index - startWritePos);
// Escape this char as underlying encoder cannot handle it
_writer.write(ENCODING_PREFIX);
_writer.write(Integer.toHexString(ch));
_writer.write(SEMICOLON);
startWritePos = index + 1;
continue;
}
switch (ch) {
case OPEN_START_TAG:
_writer.write(content, startWritePos, index - startWritePos);
_writer.write("&lt;");
startWritePos = index + 1;
break;
case AMPERSAND:
_writer.write(content, startWritePos, index - startWritePos);
_writer.write("&amp;");
startWritePos = index + 1;
break;
case CLOSE_START_TAG:
_writer.write(content, startWritePos, index - startWritePos);
_writer.write("&gt;");
startWritePos = index + 1;
break;
}
}
// Write any pending data
_writer.write(content, startWritePos, end - startWritePos);
}
private void writeXMLContent(String content) throws XMLStreamException {
if ((content != null) && (content.length() > 0)) {
writeXMLContent(content,
_escapeCharacters, // boolean = escapeChars
false); // false = escapeDoubleQuotes
}
}
/**
* Writes XML content to underlying writer. Escapes characters unless
* escaping character feature is turned off.
*/
private void writeXMLContent(
String content,
boolean escapeChars,
boolean escapeDoubleQuotes)
throws XMLStreamException
{
if (!escapeChars) {
_writer.write(content);
return;
}
// Index of the next char to be written
int startWritePos = 0;
final int end = content.length();
for (int index = 0; index < end; index++) {
char ch = content.charAt(index);
if (!_writer.canEncode(ch)) {
_writer.write(content, startWritePos, index - startWritePos);
// Escape this char as underlying encoder cannot handle it
_writer.write(ENCODING_PREFIX);
_writer.write(Integer.toHexString(ch));
_writer.write(SEMICOLON);
startWritePos = index + 1;
continue;
}
switch (ch) {
case OPEN_START_TAG:
_writer.write(content, startWritePos, index - startWritePos);
_writer.write("&lt;");
startWritePos = index + 1;
break;
case AMPERSAND:
_writer.write(content, startWritePos, index - startWritePos);
_writer.write("&amp;");
startWritePos = index + 1;
break;
case CLOSE_START_TAG:
_writer.write(content, startWritePos, index - startWritePos);
_writer.write("&gt;");
startWritePos = index + 1;
break;
case DOUBLEQUOT:
_writer.write(content, startWritePos, index - startWritePos);
if (escapeDoubleQuotes) {
_writer.write("&quot;");
} else {
_writer.write(DOUBLEQUOT);
}
startWritePos = index + 1;
break;
}
}
// Write any pending data
_writer.write(content, startWritePos, end - startWritePos);
}
/**
* marks open of start tag and writes the same into the writer.
*/
private void openStartTag() throws XMLStreamException {
_currentEle.setState(ELEMENT_STARTTAG_OPEN);
_writer.write(OPEN_START_TAG);
}
/**
* marks close of start tag and writes the same into the writer.
*/
private void closeStartTag() throws XMLStreamException {
if (_currentEle.isEmpty()) {
_writer.write(CLOSE_EMPTY_ELEMENT);
} else {
_writer.write(CLOSE_START_TAG);
}
if (_currentEle.getParent() == null) {
writeLineSeparator();
}
_currentEle.setState(ELEMENT_STARTTAG_CLOSE);
}
/**
* Write a line separator
* @throws XMLStreamException
*/
private void writeLineSeparator() throws XMLStreamException {
if (_doIndent) {
_writer.write(_lineSep, 0, _lineSep.length);
}
}
/**
* Returns a charset object for the specified encoding
* @param encoding
* @return a charset object
* @throws UnsupportedEncodingException if the encoding is not supported
*/
private Charset getCharset(String encoding) throws UnsupportedEncodingException {
if (encoding.equalsIgnoreCase("UTF-32")) {
throw new UnsupportedEncodingException("The basic XMLWriter does "
+ "not support " + encoding);
}
Charset cs;
try {
cs = Charset.forName(encoding);
} catch (IllegalCharsetNameException | UnsupportedCharsetException ex) {
throw new UnsupportedEncodingException(encoding);
}
return cs;
}
/*
* Start of Internal classes.
*
*/
protected class Element {
/**
* the parent element
*/
protected Element _parent;
/**
* The size of the stack.
*/
protected short _Depth;
/**
* indicate if an element is an empty one
*/
boolean _isEmptyElement = false;
String _localpart;
int _state;
/**
* Default constructor.
*/
public Element() {
}
/**
* @param parent the parent of the element
* @param localpart name of the element
* @param isEmpty indicate if the element is an empty one
*/
public Element(Element parent, String localpart, boolean isEmpty) {
_parent = parent;
_localpart = localpart;
_isEmptyElement = isEmpty;
}
public Element getParent() {
return _parent;
}
public String getLocalName() {
return _localpart;
}
/**
* get the state of the element
*/
public int getState() {
return _state;
}
/**
* Set the state of the element
*
* @param state the state of the element
*/
public void setState(int state) {
_state = state;
}
public boolean isEmpty() {
return _isEmptyElement;
}
}
}

View file

@ -0,0 +1,152 @@
/*
* Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package jdk.internal.util.xml.impl;
import java.io.BufferedOutputStream;
import java.io.IOException;
import java.io.OutputStream;
import java.io.OutputStreamWriter;
import java.io.UnsupportedEncodingException;
import java.io.Writer;
import java.nio.charset.Charset;
import java.nio.charset.CharsetEncoder;
import jdk.internal.util.xml.XMLStreamException;
/**
*
* @author huizwang
*/
public class XMLWriter {
private Writer _writer;
/**
* In some cases, this charset encoder is used to determine if a char is
* encodable by underlying writer. For example, an 8-bit char from the
* extended ASCII set is not encodable by 7-bit ASCII encoder. Unencodable
* chars are escaped using XML numeric entities.
*/
private CharsetEncoder _encoder = null;
public XMLWriter(OutputStream os, String encoding, Charset cs) throws XMLStreamException {
_encoder = cs.newEncoder();
try {
_writer = getWriter(os, encoding, cs);
} catch (UnsupportedEncodingException ex) {
throw new XMLStreamException(ex);
}
}
public boolean canEncode(char ch) {
if (_encoder == null) {
return false;
}
return (_encoder.canEncode(ch));
}
public void write(String s)
throws XMLStreamException {
try {
_writer.write(s.toCharArray());
// _writer.write(s.getBytes(Charset.forName(_encoding)));
} catch (IOException e) {
throw new XMLStreamException("I/O error", e);
}
}
public void write(String str, int off, int len)
throws XMLStreamException {
try {
_writer.write(str, off, len);
} catch (IOException e) {
throw new XMLStreamException("I/O error", e);
}
}
public void write(char[] cbuf, int off, int len)
throws XMLStreamException {
try {
_writer.write(cbuf, off, len);
} catch (IOException e) {
throw new XMLStreamException("I/O error", e);
}
}
void write(int b)
throws XMLStreamException {
try {
_writer.write(b);
} catch (IOException e) {
throw new XMLStreamException("I/O error", e);
}
}
void flush() throws XMLStreamException {
try {
_writer.flush();
} catch (IOException ex) {
throw new XMLStreamException(ex);
}
}
void close() throws XMLStreamException {
try {
_writer.close();
} catch (IOException ex) {
throw new XMLStreamException(ex);
}
}
private void nl() throws XMLStreamException {
String lineEnd = System.getProperty("line.separator");
try {
_writer.write(lineEnd);
} catch (IOException e) {
throw new XMLStreamException("I/O error", e);
}
}
/**
* Returns a writer for the specified encoding based on an output stream.
*
* @param output The output stream
* @param encoding The encoding
* @return A suitable writer
* @throws UnsupportedEncodingException There is no convertor to support
* this encoding
*/
private Writer getWriter(OutputStream output, String encoding, Charset cs)
throws XMLStreamException, UnsupportedEncodingException
{
if (cs != null) {
return (new OutputStreamWriter(new BufferedOutputStream(output), cs));
}
return new OutputStreamWriter(new BufferedOutputStream(output), encoding);
}
}

View file

@ -53,7 +53,9 @@ public class LCMS implements PCMM {
public static native long getProfileID(ICC_Profile profile);
public static native long createNativeTransform(
long[] profileIDs, int renderType, int inFormatter, int outFormatter,
long[] profileIDs, int renderType,
int inFormatter, boolean isInIntPacked,
int outFormatter, boolean isOutIntPacked,
Object disposerRef);
/**

View file

@ -196,7 +196,8 @@ class LCMSImageLayout {
case BufferedImage.TYPE_4BYTE_ABGR:
byteRaster = (ByteComponentRaster)image.getRaster();
nextRowOffset = byteRaster.getScanlineStride();
offset = byteRaster.getDataOffset(0);
int firstBand = image.getSampleModel().getNumBands() - 1;
offset = byteRaster.getDataOffset(firstBand);
dataArray = byteRaster.getDataStorage();
dataType = DT_BYTE;
break;

View file

@ -55,8 +55,10 @@ import sun.java2d.cmm.lcms.*;
public class LCMSTransform implements ColorTransform {
long ID;
private int inFormatter;
private int outFormatter;
private int inFormatter = 0;
private boolean isInIntPacked = false;
private int outFormatter = 0;
private boolean isOutIntPacked = false;
ICC_Profile[] profiles;
long [] profileIDs;
@ -135,18 +137,23 @@ public class LCMSTransform implements ColorTransform {
LCMSImageLayout out) {
// update native transfrom if needed
if (ID == 0L ||
inFormatter != in.pixelType ||
outFormatter != out.pixelType) {
inFormatter != in.pixelType || isInIntPacked != in.isIntPacked ||
outFormatter != out.pixelType || isOutIntPacked != out.isIntPacked)
{
if (ID != 0L) {
// Disposer will destroy forgotten transform
disposerReferent = new Object();
}
inFormatter = in.pixelType;
isInIntPacked = in.isIntPacked;
outFormatter = out.pixelType;
isOutIntPacked = out.isIntPacked;
ID = LCMS.createNativeTransform(profileIDs, renderType,
inFormatter, outFormatter,
inFormatter, isInIntPacked,
outFormatter, isOutIntPacked,
disposerReferent);
}

View file

@ -83,11 +83,8 @@ class KeepAliveStream extends MeteredStream implements Hurryable {
if (expected > count) {
long nskip = expected - count;
if (nskip <= available()) {
long n = 0;
while (n < nskip) {
nskip = nskip - n;
n = skip(nskip);
}
do {} while ((nskip = (expected - count)) > 0L
&& skip(Math.min(nskip, available())) > 0L);
} else if (expected <= KeepAliveStreamCleaner.MAX_DATA_REMAINING && !hurried) {
//put this KeepAliveStream on the queue so that the data remaining
//on the socket can be cleanup asyncronously.

View file

@ -555,6 +555,12 @@ public class EncryptionKey
int ktype;
boolean etypeFound = false;
// When no matched kvno is found, returns tke key of the same
// etype with the highest kvno
int kvno_found = 0;
EncryptionKey key_found = null;
for (int i = 0; i < keys.length; i++) {
ktype = keys[i].getEType();
if (EType.isSupported(ktype)) {
@ -563,6 +569,10 @@ public class EncryptionKey
etypeFound = true;
if (versionMatches(kvno, kv)) {
return keys[i];
} else if (kv > kvno_found) {
// kv is not null
key_found = keys[i];
kvno_found = kv;
}
}
}
@ -580,12 +590,17 @@ public class EncryptionKey
etypeFound = true;
if (versionMatches(kvno, kv)) {
return new EncryptionKey(etype, keys[i].getBytes());
} else if (kv > kvno_found) {
key_found = new EncryptionKey(etype, keys[i].getBytes());
kvno_found = kv;
}
}
}
}
if (etypeFound) {
throw new KrbException(Krb5.KRB_AP_ERR_BADKEYVER);
return key_found;
// For compatibility, will not fail here.
//throw new KrbException(Krb5.KRB_AP_ERR_BADKEYVER);
}
return null;
}

View file

@ -1,5 +1,5 @@
/*
* Copyright (c) 2005, 2006, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2000, 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -25,81 +25,668 @@
package sun.security.provider;
import java.io.*;
import java.net.MalformedURLException;
import java.net.URI;
import java.net.URL;
import java.security.AccessController;
import java.security.PrivilegedAction;
import java.security.PrivilegedActionException;
import java.security.PrivilegedExceptionAction;
import java.security.Security;
import java.security.URIParameter;
import java.text.MessageFormat;
import java.util.*;
import javax.security.auth.AuthPermission;
import javax.security.auth.login.AppConfigurationEntry;
import javax.security.auth.login.Configuration;
import javax.security.auth.login.ConfigurationSpi;
import javax.security.auth.login.AppConfigurationEntry;
import com.sun.security.auth.login.ConfigFile;
import sun.security.util.Debug;
import sun.security.util.PropertyExpander;
import sun.security.util.ResourcesMgr;
/**
* This class wraps the ConfigFile subclass implementation of Configuration
* inside a ConfigurationSpi implementation that is available from the
* SUN provider via the Configuration.getInstance calls.
* This class represents a default implementation for
* {@code javax.security.auth.login.Configuration}.
*
* <p> This object stores the runtime login configuration representation,
* and is the amalgamation of multiple static login
* configurations that resides in files.
* The algorithm for locating the login configuration file(s) and reading their
* information into this {@code Configuration} object is:
*
* <ol>
* <li>
* Loop through the security properties,
* <i>login.config.url.1</i>, <i>login.config.url.2</i>, ...,
* <i>login.config.url.X</i>.
* Each property value specifies a <code>URL</code> pointing to a
* login configuration file to be loaded. Read in and load
* each configuration.
*
* <li>
* The {@code java.lang.System} property
* <i>java.security.auth.login.config</i>
* may also be set to a {@code URL} pointing to another
* login configuration file
* (which is the case when a user uses the -D switch at runtime).
* If this property is defined, and its use is allowed by the
* security property file (the Security property,
* <i>policy.allowSystemProperty</i> is set to <i>true</i>),
* also load that login configuration.
*
* <li>
* If the <i>java.security.auth.login.config</i> property is defined using
* "==" (rather than "="), then ignore all other specified
* login configurations and only load this configuration.
*
* <li>
* If no system or security properties were set, try to read from the file,
* ${user.home}/.java.login.config, where ${user.home} is the value
* represented by the "user.home" System property.
* </ol>
*
* <p> The configuration syntax supported by this implementation
* is exactly that syntax specified in the
* {@code javax.security.auth.login.Configuration} class.
*
* @see javax.security.auth.login.LoginContext
* @see java.security.Security security properties
*/
public final class ConfigSpiFile extends ConfigurationSpi {
private ConfigFile cf;
private URL url;
private boolean expandProp = true;
private Map<String, List<AppConfigurationEntry>> configuration;
private int linenum;
private StreamTokenizer st;
private int lookahead;
private static Debug debugConfig = Debug.getInstance("configfile");
private static Debug debugParser = Debug.getInstance("configparser");
/**
* Create a new {@code Configuration} object.
*
* @throws SecurityException if the {@code Configuration} can not be
* initialized
*/
public ConfigSpiFile() {
try {
init();
} catch (IOException ioe) {
throw new SecurityException(ioe);
}
}
/**
* Create a new {@code Configuration} object from the specified {@code URI}.
*
* @param uri the {@code URI}
* @throws SecurityException if the {@code Configuration} can not be
* initialized
* @throws NullPointerException if {@code uri} is null
*/
public ConfigSpiFile(URI uri) {
// only load config from the specified URI
try {
url = uri.toURL();
init();
} catch (IOException ioe) {
throw new SecurityException(ioe);
}
}
public ConfigSpiFile(final Configuration.Parameters params)
throws java.io.IOException {
throws IOException {
// call in a doPrivileged
//
// we have already passed the Configuration.getInstance
// security check. also this class is not freely accessible
// (it is in the "sun" package).
//
// we can not put doPrivileged calls into
// ConfigFile because it is a public com.sun class
try {
AccessController.doPrivileged(new PrivilegedAction<Void>() {
public Void run() {
if (params == null) {
cf = new ConfigFile();
} else {
if (!(params instanceof URIParameter)) {
throw new IllegalArgumentException
("Unrecognized parameter: " + params);
AccessController.doPrivileged(new PrivilegedExceptionAction<Void>() {
public Void run() throws IOException {
if (params == null) {
init();
} else {
if (!(params instanceof URIParameter)) {
throw new IllegalArgumentException
("Unrecognized parameter: " + params);
}
URIParameter uriParam = (URIParameter)params;
url = uriParam.getURI().toURL();
init();
}
URIParameter uriParam = (URIParameter)params;
cf = new ConfigFile(uriParam.getURI());
return null;
}
return null;
}
});
} catch (SecurityException se) {
// if ConfigFile threw a standalone SecurityException
// (no cause), re-throw it.
//
// ConfigFile chains checked IOExceptions to SecurityException.
Throwable cause = se.getCause();
if (cause != null && cause instanceof java.io.IOException) {
throw (java.io.IOException)cause;
}
// unrecognized cause
throw se;
} catch (PrivilegedActionException pae) {
throw (IOException)pae.getException();
}
// if ConfigFile throws some other RuntimeException,
// if init() throws some other RuntimeException,
// let it percolate up naturally.
}
protected AppConfigurationEntry[] engineGetAppConfigurationEntry
(String name) {
return cf.getAppConfigurationEntry(name);
/**
* Read and initialize the entire login Configuration from the configured
* URL.
*
* @throws IOException if the Configuration can not be initialized
* @throws SecurityException if the caller does not have permission
* to initialize the Configuration
*/
private void init() throws IOException {
boolean initialized = false;
// For policy.expandProperties, check if either a security or system
// property is set to false (old code erroneously checked the system
// prop so we must check both to preserve compatibility).
String expand = Security.getProperty("policy.expandProperties");
if (expand == null) {
expand = System.getProperty("policy.expandProperties");
}
if ("false".equals(expand)) {
expandProp = false;
}
// new configuration
Map<String, List<AppConfigurationEntry>> newConfig = new HashMap<>();
if (url != null) {
/**
* If the caller specified a URI via Configuration.getInstance,
* we only read from that URI
*/
if (debugConfig != null) {
debugConfig.println("reading " + url);
}
init(url, newConfig);
configuration = newConfig;
return;
}
/**
* Caller did not specify URI via Configuration.getInstance.
* Read from URLs listed in the java.security properties file.
*/
String allowSys = Security.getProperty("policy.allowSystemProperty");
if ("true".equalsIgnoreCase(allowSys)) {
String extra_config = System.getProperty
("java.security.auth.login.config");
if (extra_config != null) {
boolean overrideAll = false;
if (extra_config.startsWith("=")) {
overrideAll = true;
extra_config = extra_config.substring(1);
}
try {
extra_config = PropertyExpander.expand(extra_config);
} catch (PropertyExpander.ExpandException peee) {
MessageFormat form = new MessageFormat
(ResourcesMgr.getString
("Unable.to.properly.expand.config",
"sun.security.util.AuthResources"));
Object[] source = {extra_config};
throw new IOException(form.format(source));
}
URL configURL = null;
try {
configURL = new URL(extra_config);
} catch (MalformedURLException mue) {
File configFile = new File(extra_config);
if (configFile.exists()) {
configURL = configFile.toURI().toURL();
} else {
MessageFormat form = new MessageFormat
(ResourcesMgr.getString
("extra.config.No.such.file.or.directory.",
"sun.security.util.AuthResources"));
Object[] source = {extra_config};
throw new IOException(form.format(source));
}
}
if (debugConfig != null) {
debugConfig.println("reading "+configURL);
}
init(configURL, newConfig);
initialized = true;
if (overrideAll) {
if (debugConfig != null) {
debugConfig.println("overriding other policies!");
}
configuration = newConfig;
return;
}
}
}
int n = 1;
String config_url;
while ((config_url = Security.getProperty
("login.config.url."+n)) != null) {
try {
config_url = PropertyExpander.expand
(config_url).replace(File.separatorChar, '/');
if (debugConfig != null) {
debugConfig.println("\tReading config: " + config_url);
}
init(new URL(config_url), newConfig);
initialized = true;
} catch (PropertyExpander.ExpandException peee) {
MessageFormat form = new MessageFormat
(ResourcesMgr.getString
("Unable.to.properly.expand.config",
"sun.security.util.AuthResources"));
Object[] source = {config_url};
throw new IOException(form.format(source));
}
n++;
}
if (initialized == false && n == 1 && config_url == null) {
// get the config from the user's home directory
if (debugConfig != null) {
debugConfig.println("\tReading Policy " +
"from ~/.java.login.config");
}
config_url = System.getProperty("user.home");
String userConfigFile = config_url +
File.separatorChar + ".java.login.config";
// No longer throws an exception when there's no config file
// at all. Returns an empty Configuration instead.
if (new File(userConfigFile).exists()) {
init(new File(userConfigFile).toURI().toURL(),
newConfig);
}
}
configuration = newConfig;
}
protected void engineRefresh() {
cf.refresh();
private void init(URL config,
Map<String, List<AppConfigurationEntry>> newConfig)
throws IOException {
try (InputStreamReader isr
= new InputStreamReader(getInputStream(config), "UTF-8")) {
readConfig(isr, newConfig);
} catch (FileNotFoundException fnfe) {
if (debugConfig != null) {
debugConfig.println(fnfe.toString());
}
throw new IOException(ResourcesMgr.getString
("Configuration.Error.No.such.file.or.directory",
"sun.security.util.AuthResources"));
}
}
/**
* Retrieve an entry from the Configuration using an application name
* as an index.
*
* @param applicationName the name used to index the Configuration.
* @return an array of AppConfigurationEntries which correspond to
* the stacked configuration of LoginModules for this
* application, or null if this application has no configured
* LoginModules.
*/
@Override
public AppConfigurationEntry[] engineGetAppConfigurationEntry
(String applicationName) {
List<AppConfigurationEntry> list = null;
synchronized (configuration) {
list = configuration.get(applicationName);
}
if (list == null || list.size() == 0)
return null;
AppConfigurationEntry[] entries =
new AppConfigurationEntry[list.size()];
Iterator<AppConfigurationEntry> iterator = list.iterator();
for (int i = 0; iterator.hasNext(); i++) {
AppConfigurationEntry e = iterator.next();
entries[i] = new AppConfigurationEntry(e.getLoginModuleName(),
e.getControlFlag(),
e.getOptions());
}
return entries;
}
/**
* Refresh and reload the Configuration by re-reading all of the
* login configurations.
*
* @throws SecurityException if the caller does not have permission
* to refresh the Configuration.
*/
@Override
public synchronized void engineRefresh() {
SecurityManager sm = System.getSecurityManager();
if (sm != null)
sm.checkPermission(new AuthPermission("refreshLoginConfiguration"));
AccessController.doPrivileged(new PrivilegedAction<Void>() {
public Void run() {
try {
init();
} catch (IOException ioe) {
throw new SecurityException(ioe.getLocalizedMessage(), ioe);
}
return null;
}
});
}
private void readConfig(Reader reader,
Map<String, List<AppConfigurationEntry>> newConfig)
throws IOException {
linenum = 1;
if (!(reader instanceof BufferedReader))
reader = new BufferedReader(reader);
st = new StreamTokenizer(reader);
st.quoteChar('"');
st.wordChars('$', '$');
st.wordChars('_', '_');
st.wordChars('-', '-');
st.lowerCaseMode(false);
st.slashSlashComments(true);
st.slashStarComments(true);
st.eolIsSignificant(true);
lookahead = nextToken();
while (lookahead != StreamTokenizer.TT_EOF) {
parseLoginEntry(newConfig);
}
}
private void parseLoginEntry(
Map<String, List<AppConfigurationEntry>> newConfig)
throws IOException {
List<AppConfigurationEntry> configEntries = new LinkedList<>();
// application name
String appName = st.sval;
lookahead = nextToken();
if (debugParser != null) {
debugParser.println("\tReading next config entry: " + appName);
}
match("{");
// get the modules
while (peek("}") == false) {
// get the module class name
String moduleClass = match("module class name");
// controlFlag (required, optional, etc)
AppConfigurationEntry.LoginModuleControlFlag controlFlag;
String sflag = match("controlFlag").toUpperCase();
switch (sflag) {
case "REQUIRED":
controlFlag =
AppConfigurationEntry.LoginModuleControlFlag.REQUIRED;
break;
case "REQUISITE":
controlFlag =
AppConfigurationEntry.LoginModuleControlFlag.REQUISITE;
break;
case "SUFFICIENT":
controlFlag =
AppConfigurationEntry.LoginModuleControlFlag.SUFFICIENT;
break;
case "OPTIONAL":
controlFlag =
AppConfigurationEntry.LoginModuleControlFlag.OPTIONAL;
break;
default:
MessageFormat form = new MessageFormat(
ResourcesMgr.getString
("Configuration.Error.Invalid.control.flag.flag",
"sun.security.util.AuthResources"));
Object[] source = {sflag};
throw new IOException(form.format(source));
}
// get the args
Map<String, String> options = new HashMap<>();
while (peek(";") == false) {
String key = match("option key");
match("=");
try {
options.put(key, expand(match("option value")));
} catch (PropertyExpander.ExpandException peee) {
throw new IOException(peee.getLocalizedMessage());
}
}
lookahead = nextToken();
// create the new element
if (debugParser != null) {
debugParser.println("\t\t" + moduleClass + ", " + sflag);
for (String key : options.keySet()) {
debugParser.println("\t\t\t" + key +
"=" + options.get(key));
}
}
configEntries.add(new AppConfigurationEntry(moduleClass,
controlFlag, options));
}
match("}");
match(";");
// add this configuration entry
if (newConfig.containsKey(appName)) {
MessageFormat form = new MessageFormat(ResourcesMgr.getString
("Configuration.Error.Can.not.specify.multiple.entries.for.appName",
"sun.security.util.AuthResources"));
Object[] source = {appName};
throw new IOException(form.format(source));
}
newConfig.put(appName, configEntries);
}
private String match(String expect) throws IOException {
String value = null;
switch(lookahead) {
case StreamTokenizer.TT_EOF:
MessageFormat form1 = new MessageFormat(ResourcesMgr.getString
("Configuration.Error.expected.expect.read.end.of.file.",
"sun.security.util.AuthResources"));
Object[] source1 = {expect};
throw new IOException(form1.format(source1));
case '"':
case StreamTokenizer.TT_WORD:
if (expect.equalsIgnoreCase("module class name") ||
expect.equalsIgnoreCase("controlFlag") ||
expect.equalsIgnoreCase("option key") ||
expect.equalsIgnoreCase("option value")) {
value = st.sval;
lookahead = nextToken();
} else {
MessageFormat form = new MessageFormat(ResourcesMgr.getString
("Configuration.Error.Line.line.expected.expect.found.value.",
"sun.security.util.AuthResources"));
Object[] source = {new Integer(linenum), expect, st.sval};
throw new IOException(form.format(source));
}
break;
case '{':
if (expect.equalsIgnoreCase("{")) {
lookahead = nextToken();
} else {
MessageFormat form = new MessageFormat(ResourcesMgr.getString
("Configuration.Error.Line.line.expected.expect.",
"sun.security.util.AuthResources"));
Object[] source = {new Integer(linenum), expect, st.sval};
throw new IOException(form.format(source));
}
break;
case ';':
if (expect.equalsIgnoreCase(";")) {
lookahead = nextToken();
} else {
MessageFormat form = new MessageFormat(ResourcesMgr.getString
("Configuration.Error.Line.line.expected.expect.",
"sun.security.util.AuthResources"));
Object[] source = {new Integer(linenum), expect, st.sval};
throw new IOException(form.format(source));
}
break;
case '}':
if (expect.equalsIgnoreCase("}")) {
lookahead = nextToken();
} else {
MessageFormat form = new MessageFormat(ResourcesMgr.getString
("Configuration.Error.Line.line.expected.expect.",
"sun.security.util.AuthResources"));
Object[] source = {new Integer(linenum), expect, st.sval};
throw new IOException(form.format(source));
}
break;
case '=':
if (expect.equalsIgnoreCase("=")) {
lookahead = nextToken();
} else {
MessageFormat form = new MessageFormat(ResourcesMgr.getString
("Configuration.Error.Line.line.expected.expect.",
"sun.security.util.AuthResources"));
Object[] source = {new Integer(linenum), expect, st.sval};
throw new IOException(form.format(source));
}
break;
default:
MessageFormat form = new MessageFormat(ResourcesMgr.getString
("Configuration.Error.Line.line.expected.expect.found.value.",
"sun.security.util.AuthResources"));
Object[] source = {new Integer(linenum), expect, st.sval};
throw new IOException(form.format(source));
}
return value;
}
private boolean peek(String expect) {
boolean found = false;
switch (lookahead) {
case ',':
if (expect.equalsIgnoreCase(","))
found = true;
break;
case ';':
if (expect.equalsIgnoreCase(";"))
found = true;
break;
case '{':
if (expect.equalsIgnoreCase("{"))
found = true;
break;
case '}':
if (expect.equalsIgnoreCase("}"))
found = true;
break;
default:
}
return found;
}
private int nextToken() throws IOException {
int tok;
while ((tok = st.nextToken()) == StreamTokenizer.TT_EOL) {
linenum++;
}
return tok;
}
private InputStream getInputStream(URL url) throws IOException {
if ("file".equalsIgnoreCase(url.getProtocol())) {
// Compatibility notes:
//
// Code changed from
// String path = url.getFile().replace('/', File.separatorChar);
// return new FileInputStream(path);
//
// The original implementation would search for "/tmp/a%20b"
// when url is "file:///tmp/a%20b". This is incorrect. The
// current codes fix this bug and searches for "/tmp/a b".
// For compatibility reasons, when the file "/tmp/a b" does
// not exist, the file named "/tmp/a%20b" will be tried.
//
// This also means that if both file exists, the behavior of
// this method is changed, and the current codes choose the
// correct one.
try {
return url.openStream();
} catch (Exception e) {
String file = url.getPath();
if (url.getHost().length() > 0) { // For Windows UNC
file = "//" + url.getHost() + file;
}
if (debugConfig != null) {
debugConfig.println("cannot read " + url +
", try " + file);
}
return new FileInputStream(file);
}
} else {
return url.openStream();
}
}
private String expand(String value)
throws PropertyExpander.ExpandException, IOException {
if (value.isEmpty()) {
return value;
}
if (expandProp) {
String s = PropertyExpander.expand(value);
if (s == null || s.length() == 0) {
MessageFormat form = new MessageFormat(ResourcesMgr.getString
("Configuration.Error.Line.line.system.property.value.expanded.to.empty.value",
"sun.security.util.AuthResources"));
Object[] source = {new Integer(linenum), value};
throw new IOException(form.format(source));
}
return s;
} else {
return value;
}
}
}

View file

@ -3251,10 +3251,9 @@ public class BidiBase {
{
verifyValidParaOrLine();
BidiLine.getRuns(this);
if (runCount == 1) {
if (run < 0 || run >= runCount) {
return getParaLevel();
}
verifyIndex(run, 0, runCount);
getLogicalToVisualRunsMap();
return runs[logicalToVisualRunsMap[run]].level;
}

View file

@ -104,7 +104,7 @@ public abstract class TimeZoneNamesBundle extends OpenListResourceBundle {
if (contents == null) {
return null;
}
int clen = Math.min(n, contents.length);
int clen = Math.min(n - 1, contents.length);
String[] tmpobj = new String[clen+1];
tmpobj[0] = key;
System.arraycopy(contents, 0, tmpobj, 1, clen);

View file

@ -49,7 +49,7 @@
<target name="compile" depends="init"
description="compile the source " >
<!-- Compile the java code from ${src} into ${build} -->
<javac debug="false" source="1.2" target="1.2" srcdir="${src}" destdir="${build}"/>
<javac debug="flase" source="1.5" target="1.5" srcdir="${src}" destdir="${build}"/>
</target>
<target name="run" depends="dist"

View file

@ -69,6 +69,7 @@ import j2dbench.tests.MiscTests;
import j2dbench.tests.RenderTests;
import j2dbench.tests.PixelTests;
import j2dbench.tests.iio.IIOTests;
import j2dbench.tests.cmm.CMMTests;
import j2dbench.tests.text.TextConstructionTests;
import j2dbench.tests.text.TextMeasureTests;
import j2dbench.tests.text.TextRenderTests;
@ -199,6 +200,7 @@ public class J2DBench {
TextMeasureTests.init();
TextConstructionTests.init();
IIOTests.init();
CMMTests.init();
boolean gui = true;
boolean showresults = true;

View file

@ -0,0 +1,153 @@
/*
* Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* - Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* - 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.
*
* - Neither the name of Oracle nor the names of its
* contributors may be used to endorse or promote products derived
* from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
* IS" AND ANY EXPRESS 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 COPYRIGHT OWNER OR
* 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 source code is provided to illustrate the usage of a given feature
* or technique and has been deliberately simplified. Additional steps
* required for a production-quality application, such as security checks,
* input validation and proper error handling, might not be present in
* this sample code.
*/
package j2dbench.tests.cmm;
import j2dbench.Group;
import j2dbench.Option;
import j2dbench.Result;
import j2dbench.Test;
import j2dbench.TestEnvironment;
import java.awt.color.ColorSpace;
import java.awt.color.ICC_ColorSpace;
import java.awt.color.ICC_Profile;
import java.io.IOException;
import java.io.InputStream;
public class CMMTests extends Test {
protected static Group cmmRoot;
protected static Group cmmOptRoot;
protected static Option csList;
protected static Option usePlatfromProfiles;
public static void init() {
cmmRoot = new Group("cmm", "Color Management Benchmarks");
cmmRoot.setTabbed();
cmmOptRoot = new Group(cmmRoot, "opts", "General Options");
/*
usePlatfromProfiles =
new Option.Enable(cmmOptRoot, "csPlatfrom",
"Use Platfrom Profiles", false);
*/
int[] colorspaces = new int[] {
ColorSpace.CS_sRGB,
ColorSpace.CS_GRAY,
ColorSpace.CS_LINEAR_RGB,
ColorSpace.CS_CIEXYZ
};
String[] csNames = new String[]{
"CS_sRGB",
"CS_GRAY",
"CS_LINEAR_RGB",
"CS_CIEXYZ"
};
csList = new Option.IntList(cmmOptRoot,
"profiles", "Color Profiles",
colorspaces, csNames, csNames, 0x8);
ColorConversionTests.init();
ProfileTests.init();
}
protected static ColorSpace getColorSpace(TestEnvironment env) {
ColorSpace cs;
Boolean usePlatfrom = true; //(Boolean)env.getModifier(usePlatfromProfiles);
int cs_code = env.getIntValue(csList);
if (usePlatfrom) {
cs = ColorSpace.getInstance(cs_code);
} else {
String resource = "profiles/";
switch (cs_code) {
case ColorSpace.CS_CIEXYZ:
resource += "CIEXYZ.pf";
break;
case ColorSpace.CS_GRAY:
resource += "GRAY.pf";
break;
case ColorSpace.CS_LINEAR_RGB:
resource += "LINEAR_RGB.pf";
break;
case ColorSpace.CS_PYCC:
resource += "PYCC.pf";
break;
case ColorSpace.CS_sRGB:
resource += "sRGB.pf";
break;
default:
throw new RuntimeException("Unknown color space: " + cs_code);
}
try {
InputStream is = CMMTests.class.getResourceAsStream(resource);
ICC_Profile p = ICC_Profile.getInstance(is);
cs = new ICC_ColorSpace(p);
} catch (IOException e) {
throw new RuntimeException("Unable load profile from resource " + resource, e);
}
}
return cs;
}
protected CMMTests(Group parent, String nodeName, String description) {
super(parent, nodeName, description);
addDependencies(cmmOptRoot, true);
}
@Override
public Object initTest(TestEnvironment te, Result result) {
throw new UnsupportedOperationException("Not supported yet.");
}
@Override
public void runTest(Object o, int i) {
throw new UnsupportedOperationException("Not supported yet.");
}
@Override
public void cleanupTest(TestEnvironment te, Object o) {
throw new UnsupportedOperationException("Not supported yet.");
}
}

View file

@ -0,0 +1,59 @@
/*
* Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* - Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* - 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.
*
* - Neither the name of Oracle nor the names of its
* contributors may be used to endorse or promote products derived
* from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
* IS" AND ANY EXPRESS 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 COPYRIGHT OWNER OR
* 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 source code is provided to illustrate the usage of a given feature
* or technique and has been deliberately simplified. Additional steps
* required for a production-quality application, such as security checks,
* input validation and proper error handling, might not be present in
* this sample code.
*/
package j2dbench.tests.cmm;
import j2dbench.Group;
public class ColorConversionTests extends CMMTests {
protected static Group colorConvRoot;
public static void init() {
colorConvRoot = new Group(cmmRoot, "colorconv", "Color Conversion Benchmarks");
colorConvRoot.setTabbed();
DataConversionTests.init();
ColorConvertOpTests.init();
}
protected ColorConversionTests(Group parent, String nodeName, String description) {
super(parent, nodeName, description);
}
}

View file

@ -0,0 +1,383 @@
/*
* Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* - Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* - 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.
*
* - Neither the name of Oracle nor the names of its
* contributors may be used to endorse or promote products derived
* from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
* IS" AND ANY EXPRESS 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 COPYRIGHT OWNER OR
* 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 source code is provided to illustrate the usage of a given feature
* or technique and has been deliberately simplified. Additional steps
* required for a production-quality application, such as security checks,
* input validation and proper error handling, might not be present in
* this sample code.
*/
package j2dbench.tests.cmm;
import j2dbench.Group;
import j2dbench.Option;
import j2dbench.Result;
import j2dbench.TestEnvironment;
import j2dbench.tests.iio.IIOTests;
import java.awt.AlphaComposite;
import java.awt.Color;
import java.awt.Graphics2D;
import java.awt.Image;
import java.awt.color.ColorSpace;
import java.awt.image.BufferedImage;
import java.awt.image.ColorConvertOp;
import java.awt.image.Raster;
import java.awt.image.WritableRaster;
import javax.imageio.ImageIO;
public class ColorConvertOpTests extends ColorConversionTests {
private static enum ImageContent {
BLANK("bank", "Blank (opaque black)"),
RANDOM("random", "Random"),
VECTOR("vector", "Vector Art"),
PHOTO("photo", "Photograph");
public final String name;
public final String descr;
private ImageContent(String name, String descr) {
this.name = name;
this.descr = descr;
}
}
private static enum ImageType {
INT_ARGB(BufferedImage.TYPE_INT_ARGB, "INT_ARGB", "TYPE_INT_ARGB"),
INT_RGB(BufferedImage.TYPE_INT_RGB, "INT_RGB", "TYPE_INT_RGB"),
INT_BGR(BufferedImage.TYPE_INT_BGR, "INT_BGR", "TYPE_INT_BGR"),
BYTE_3BYTE_BGR(BufferedImage.TYPE_3BYTE_BGR, "3BYTE_BGR", "TYPE_3BYTE_BGR"),
BYTE_4BYTE_ABGR(BufferedImage.TYPE_4BYTE_ABGR, "4BYTE_BGR", "TYPE_4BYTE_BGR"),
COMPATIBLE_DST(0, "Compatible", "Compatible destination");
private ImageType(int type, String abbr, String descr) {
this.type = type;
this.abbrev = abbr;
this.descr = descr;
}
public final int type;
public final String abbrev;
public final String descr;
}
private static enum ListType {
SRC("srcType", "Source Images"),
DST("dstType", "Destination Images");
private ListType(String name, String description) {
this.name = name;
this.description = description;
}
public final String name;
public final String description;
}
public static Option createImageTypeList(ListType listType) {
ImageType[] allTypes = ImageType.values();
int num = allTypes.length;
if (listType == ListType.SRC) {
num -= 1; // exclude compatible destination
}
ImageType[] t = new ImageType[num];
String[] names = new String[num];
String[] abbrev = new String[num];
String[] descr = new String[num];
for (int i = 0; i < num; i++) {
t[i] = allTypes[i];
names[i] = t[i].toString();
abbrev[i] = t[i].abbrev;
descr[i] = t[i].descr;
}
Option list = new Option.ObjectList(opOptionsRoot,
listType.name, listType.description,
names, t, abbrev, descr, 1);
return list;
}
protected static Group opConvRoot;
protected static Group opOptionsRoot;
protected static Option sizeList;
protected static Option contentList;
protected static Option sourceType;
protected static Option destinationType;
public static void init() {
opConvRoot = new Group(colorConvRoot, "ccop", "ColorConvertOp Tests");
opOptionsRoot = new Group(opConvRoot, "ccopOptions", "Options");
// size list
int[] sizes = new int[] {1, 20, 250, 1000, 4000};
String[] sizeStrs = new String[] {
"1x1", "20x20", "250x250", "1000x1000", "4000x4000"
};
String[] sizeDescs = new String[] {
"Tiny Images (1x1)",
"Small Images (20x20)",
"Medium Images (250x250)",
"Large Images (1000x1000)",
"Huge Images (4000x4000)",
};
sizeList = new Option.IntList(opOptionsRoot,
"size", "Image Size",
sizes, sizeStrs, sizeDescs, 0x4);
((Option.ObjectList) sizeList).setNumRows(5);
// image content
ImageContent[] c = ImageContent.values();
String[] contentStrs = new String[c.length];
String[] contentDescs = new String[c.length];
for (int i = 0; i < c.length; i++) {
contentStrs[i] = c[i].name;
contentDescs[i] = c[i].descr;
};
contentList = new Option.ObjectList(opOptionsRoot,
"content", "Image Content",
contentStrs, c,
contentStrs, contentDescs,
0x8);
sourceType = createImageTypeList(ListType.SRC);
destinationType = createImageTypeList(ListType.DST);
new ConvertImageTest();
new ConvertRasterTest();
new DrawImageTest();
}
public ColorConvertOpTests(Group parent, String nodeName, String description) {
super(parent, nodeName, description);
addDependencies(opOptionsRoot, true);
}
public Object initTest(TestEnvironment env, Result res) {
return new Context(env, res);
}
public void cleanupTest(TestEnvironment env, Object o) {
Context ctx = (Context)o;
ctx.cs = null;
ctx.op_img = null;
ctx.op_rst = null;
ctx.dst = null;
ctx.src = null;
ctx.graphics = null;
}
private static class Context {
ColorSpace cs;
Graphics2D graphics;
ColorConvertOp op_img;
ColorConvertOp op_rst;
BufferedImage src;
BufferedImage dst;
WritableRaster rsrc;
WritableRaster rdst;
public Context(TestEnvironment env, Result res) {
graphics = (Graphics2D)env.getGraphics();
cs = getColorSpace(env);
// TODO: provide rendering hints
op_img = new ColorConvertOp(cs, null);
ColorSpace sRGB = ColorSpace.getInstance(ColorSpace.CS_sRGB);
op_rst = new ColorConvertOp(sRGB, cs, null);
int size = env.getIntValue(sizeList);
ImageContent content = (ImageContent)env.getModifier(contentList);
ImageType srcType = (ImageType)env.getModifier(sourceType);
src = createBufferedImage(size, size, content, srcType.type);
rsrc = src.getRaster();
ImageType dstType = (ImageType)env.getModifier(destinationType);
if (dstType == ImageType.COMPATIBLE_DST) {
dst = op_img.createCompatibleDestImage(src, null);
} else {
dst = createBufferedImage(size, size, content, dstType.type);
}
// raster always has to be comatible
rdst = op_rst.createCompatibleDestRaster(rsrc);
}
}
private static class ConvertImageTest extends ColorConvertOpTests {
public ConvertImageTest() {
super(opConvRoot, "op_img", "op.filetr(BufferedImage)");
}
public void runTest(Object octx, int numReps) {
final Context ctx = (Context)octx;
final ColorConvertOp op = ctx.op_img;
final BufferedImage src = ctx.src;
BufferedImage dst = ctx.dst;
do {
try {
dst = op.filter(src, dst);
} catch (Exception e) {
e.printStackTrace();
}
} while (--numReps >= 0);
}
}
private static class ConvertRasterTest extends ColorConvertOpTests {
public ConvertRasterTest() {
super(opConvRoot, "op_rst", "op.filetr(Raster)");
}
public void runTest(Object octx, int numReps) {
final Context ctx = (Context)octx;
final ColorConvertOp op = ctx.op_rst;
final Raster src = ctx.rsrc;
WritableRaster dst = ctx.rdst;
do {
try {
dst = op.filter(src, dst);
} catch (Exception e) {
e.printStackTrace();
}
} while (--numReps >= 0);
}
}
private static class DrawImageTest extends ColorConvertOpTests {
public DrawImageTest() {
super(opConvRoot, "op_draw", "drawImage(ColorConvertOp)");
}
public void runTest(Object octx, int numReps) {
final Context ctx = (Context)octx;
final ColorConvertOp op = ctx.op_img;
final Graphics2D g = ctx.graphics;
final BufferedImage src = ctx.src;
do {
g.drawImage(src, op, 0, 0);
} while (--numReps >= 0);
}
}
/**************************************************************************
****** Helper routines
*************************************************************************/
protected static BufferedImage createBufferedImage(int width,
int height,
ImageContent contentType,
int type)
{
BufferedImage image;
image = new BufferedImage(width, height, type);
boolean hasAlpha = image.getColorModel().hasAlpha();
switch (contentType) {
case RANDOM:
for (int y = 0; y < height; y++) {
for (int x = 0; x < width; x++) {
int rgb = (int)(Math.random() * 0xffffff);
if (hasAlpha) {
rgb |= 0x7f000000;
}
image.setRGB(x, y, rgb);
}
}
break;
case VECTOR:
{
Graphics2D g = image.createGraphics();
if (hasAlpha) {
// fill background with a translucent color
g.setComposite(AlphaComposite.getInstance(
AlphaComposite.SRC, 0.5f));
}
g.setColor(Color.blue);
g.fillRect(0, 0, width, height);
g.setComposite(AlphaComposite.Src);
g.setColor(Color.yellow);
g.fillOval(2, 2, width-4, height-4);
g.setColor(Color.red);
g.fillOval(4, 4, width-8, height-8);
g.setColor(Color.green);
g.fillRect(8, 8, width-16, height-16);
g.setColor(Color.white);
g.drawLine(0, 0, width, height);
g.drawLine(0, height, width, 0);
g.dispose();
break;
}
case PHOTO:
{
Image photo = null;
try {
photo = ImageIO.read(
IIOTests.class.getResourceAsStream("images/photo.jpg"));
} catch (Exception e) {
System.err.println("error loading photo");
e.printStackTrace();
}
Graphics2D g = image.createGraphics();
if (hasAlpha) {
g.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC,
0.5f));
}
g.drawImage(photo, 0, 0, width, height, null);
g.dispose();
break;
}
default:
break;
}
return image;
}
}

View file

@ -0,0 +1,198 @@
/*
* Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* - Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* - 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.
*
* - Neither the name of Oracle nor the names of its
* contributors may be used to endorse or promote products derived
* from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
* IS" AND ANY EXPRESS 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 COPYRIGHT OWNER OR
* 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 source code is provided to illustrate the usage of a given feature
* or technique and has been deliberately simplified. Additional steps
* required for a production-quality application, such as security checks,
* input validation and proper error handling, might not be present in
* this sample code.
*/
package j2dbench.tests.cmm;
import j2dbench.Group;
import j2dbench.Result;
import j2dbench.TestEnvironment;
import java.awt.color.ColorSpace;
public class DataConversionTests extends ColorConversionTests {
protected static Group dataConvRoot;
public static void init() {
dataConvRoot = new Group(colorConvRoot, "data", "Data Conversoion Tests");
new FromRGBTest();
new ToRGBTest();
new FromCIEXYZTest();
new ToCIEXYZTest();
}
public DataConversionTests(Group parent, String nodeName, String description) {
super(parent, nodeName, description);
}
protected static class Context {
ColorSpace cs;
int numComponents;
float[] val;
float[] rgb;
float[] cie;
TestEnvironment env;
Result res;
public Context(TestEnvironment env, Result result, ColorSpace cs) {
this.cs = cs;
this.env = env;
this.res = result;
numComponents = cs.getNumComponents();
val = new float[numComponents];
for (int i = 0; i < numComponents; i++) {
float min = cs.getMinValue(i);
float max = cs.getMaxValue(i);
val[i] = 0.5f * (max - min);
}
rgb = new float[]{0.5f, 0.5f, 0.5f};
cie = new float[]{0.5f, 0.5f, 0.5f};
}
}
@Override
public Object initTest(TestEnvironment env, Result result) {
ColorSpace cs = getColorSpace(env);
return new Context(env, result, cs);
}
@Override
public void cleanupTest(TestEnvironment te, Object o) {
}
private static class FromRGBTest extends DataConversionTests {
public FromRGBTest() {
super(dataConvRoot,
"fromRGB",
"ColorSpace.fromRGB()");
}
public void runTest(Object ctx, int numReps) {
final Context ictx = (Context) ctx;
final ColorSpace cs = ictx.cs;
final float[] rgb = ictx.rgb;
do {
try {
cs.fromRGB(rgb);
} catch (Exception e) {
e.printStackTrace();
}
} while (--numReps >= 0);
}
}
private static class FromCIEXYZTest extends DataConversionTests {
public FromCIEXYZTest() {
super(dataConvRoot,
"fromCIEXYZ",
"ColorSpace.fromCIEXYZ()");
}
public void runTest(Object ctx, int numReps) {
final Context ictx = (Context) ctx;
final ColorSpace cs = ictx.cs;
final float[] val = ictx.cie;
do {
try {
cs.fromCIEXYZ(val);
} catch (Exception e) {
e.printStackTrace();
}
} while (--numReps >= 0);
}
}
private static class ToCIEXYZTest extends DataConversionTests {
public ToCIEXYZTest() {
super(dataConvRoot,
"toCIEXYZ",
"ColorSpace.toCIEXYZ()");
}
public void runTest(Object ctx, int numReps) {
final Context ictx = (Context) ctx;
final ColorSpace cs = ictx.cs;
final float[] val = ictx.val;
do {
try {
cs.toCIEXYZ(val);
} catch (Exception e) {
e.printStackTrace();
}
} while (--numReps >= 0);
}
}
private static class ToRGBTest extends DataConversionTests {
public ToRGBTest() {
super(dataConvRoot,
"toRGB",
"ColorSpace.toRGB()");
}
public void runTest(Object ctx, int numReps) {
final Context ictx = (Context) ctx;
final ColorSpace cs = ictx.cs;
final float[] val = ictx.val;
do {
try {
cs.toRGB(val);
} catch (Exception e) {
e.printStackTrace();
}
} while (--numReps >= 0);
}
}
}

View file

@ -0,0 +1,132 @@
/*
* Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* - Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* - 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.
*
* - Neither the name of Oracle nor the names of its
* contributors may be used to endorse or promote products derived
* from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
* IS" AND ANY EXPRESS 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 COPYRIGHT OWNER OR
* 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 source code is provided to illustrate the usage of a given feature
* or technique and has been deliberately simplified. Additional steps
* required for a production-quality application, such as security checks,
* input validation and proper error handling, might not be present in
* this sample code.
*/
package j2dbench.tests.cmm;
import j2dbench.Group;
import j2dbench.Result;
import j2dbench.TestEnvironment;
import java.awt.color.ColorSpace;
import java.awt.color.ICC_ColorSpace;
import java.awt.color.ICC_Profile;
public class ProfileTests extends CMMTests {
protected static Group profileRoot;
public static void init() {
profileRoot = new Group(cmmRoot, "profiles", "Profile Handling Benchmarks");
new ReadHeaderTest();
new GetNumComponentsTest();
}
protected ProfileTests(Group parent, String nodeName, String description) {
super(parent, nodeName, description);
}
protected static class Context {
ICC_Profile profile;
TestEnvironment env;
Result res;
public Context(ICC_Profile profile, TestEnvironment env, Result res) {
this.profile = profile;
this.env = env;
this.res = res;
}
}
@Override
public Object initTest(TestEnvironment env, Result res) {
ICC_ColorSpace cs = (ICC_ColorSpace) getColorSpace(env);
return new Context(cs.getProfile(), env, res);
}
@Override
public void cleanupTest(TestEnvironment env, Object o) {
}
private static class ReadHeaderTest extends ProfileTests {
public ReadHeaderTest() {
super(profileRoot,
"getHeader",
"getData(icSigHead)");
}
@Override
public void runTest(Object ctx, int numReps) {
final Context ictx = (Context) ctx;
final ICC_Profile profile = ictx.profile;
byte[] data = null;
do {
try {
data = profile.getData(ICC_Profile.icSigHead);
} catch (Exception e) {
e.printStackTrace();
}
} while (--numReps >= 0);
}
}
private static class GetNumComponentsTest extends ProfileTests {
public GetNumComponentsTest() {
super(profileRoot,
"getNumComponents",
"getNumComponents");
}
@Override
public void runTest(Object ctx, int numReps) {
final Context ictx = (Context) ctx;
final ICC_Profile profile = ictx.profile;
do {
try {
int num = profile.getNumComponents();
} catch (Exception e) {
e.printStackTrace();
}
} while (--numReps >= 0);
}
}
}

View file

@ -371,7 +371,7 @@ krb5.kdc.bad.policy = tryLast
# jdk.certpath.disabledAlgorithms=MD2, DSA, RSA keySize < 2048
#
#
jdk.certpath.disabledAlgorithms=MD2
jdk.certpath.disabledAlgorithms=MD2, RSA keySize < 1024
# Algorithm restrictions for Secure Socket Layer/Transport Layer Security
# (SSL/TLS) processing

View file

@ -372,7 +372,7 @@ krb5.kdc.bad.policy = tryLast
# jdk.certpath.disabledAlgorithms=MD2, DSA, RSA keySize < 2048
#
#
jdk.certpath.disabledAlgorithms=MD2
jdk.certpath.disabledAlgorithms=MD2, RSA keySize < 1024
# Algorithm restrictions for Secure Socket Layer/Transport Layer Security
# (SSL/TLS) processing

View file

@ -373,7 +373,7 @@ krb5.kdc.bad.policy = tryLast
# jdk.certpath.disabledAlgorithms=MD2, DSA, RSA keySize < 2048
#
#
jdk.certpath.disabledAlgorithms=MD2
jdk.certpath.disabledAlgorithms=MD2, RSA keySize < 1024
# Algorithm restrictions for Secure Socket Layer/Transport Layer Security
# (SSL/TLS) processing

Some files were not shown because too many files have changed in this diff Show more