summaryrefslogtreecommitdiff
path: root/libjava/classpath/java
diff options
context:
space:
mode:
Diffstat (limited to 'libjava/classpath/java')
-rw-r--r--libjava/classpath/java/awt/AlphaComposite.java19
-rw-r--r--libjava/classpath/java/awt/BasicStroke.java370
-rw-r--r--libjava/classpath/java/awt/Button.java2
-rw-r--r--libjava/classpath/java/awt/Choice.java11
-rw-r--r--libjava/classpath/java/awt/Component.java173
-rw-r--r--libjava/classpath/java/awt/Container.java144
-rw-r--r--libjava/classpath/java/awt/DefaultFocusTraversalPolicy.java2
-rw-r--r--libjava/classpath/java/awt/DefaultKeyboardFocusManager.java50
-rw-r--r--libjava/classpath/java/awt/Dialog.java893
-rw-r--r--libjava/classpath/java/awt/Frame.java13
-rw-r--r--libjava/classpath/java/awt/GraphicsConfiguration.java4
-rw-r--r--libjava/classpath/java/awt/GridBagLayout.java233
-rw-r--r--libjava/classpath/java/awt/Image.java15
-rw-r--r--libjava/classpath/java/awt/LightweightDispatcher.java78
-rw-r--r--libjava/classpath/java/awt/List.java2
-rw-r--r--libjava/classpath/java/awt/MediaTracker.java3
-rw-r--r--libjava/classpath/java/awt/MenuItem.java2
-rw-r--r--libjava/classpath/java/awt/ScrollPaneAdjustable.java11
-rw-r--r--libjava/classpath/java/awt/TexturePaint.java4
-rw-r--r--libjava/classpath/java/awt/Toolkit.java172
-rw-r--r--libjava/classpath/java/awt/Window.java69
-rw-r--r--libjava/classpath/java/awt/datatransfer/FlavorEvent.java2
-rw-r--r--libjava/classpath/java/awt/datatransfer/SystemFlavorMap.java4
-rw-r--r--libjava/classpath/java/awt/dnd/DragGestureRecognizer.java4
-rw-r--r--libjava/classpath/java/awt/dnd/DragSourceContext.java12
-rw-r--r--libjava/classpath/java/awt/dnd/DropTarget.java4
-rw-r--r--libjava/classpath/java/awt/dnd/DropTargetContext.java4
-rw-r--r--libjava/classpath/java/awt/dnd/DropTargetEvent.java2
-rw-r--r--libjava/classpath/java/awt/event/MouseEvent.java6
-rw-r--r--libjava/classpath/java/awt/font/GlyphMetrics.java4
-rw-r--r--libjava/classpath/java/awt/font/GlyphVector.java8
-rw-r--r--libjava/classpath/java/awt/font/GraphicAttribute.java4
-rw-r--r--libjava/classpath/java/awt/font/ImageGraphicAttribute.java12
-rw-r--r--libjava/classpath/java/awt/font/LineBreakMeasurer.java8
-rw-r--r--libjava/classpath/java/awt/font/NumericShaper.java352
-rw-r--r--libjava/classpath/java/awt/font/ShapeGraphicAttribute.java6
-rw-r--r--libjava/classpath/java/awt/font/TextMeasurer.java7
-rw-r--r--libjava/classpath/java/awt/geom/GeneralPath.java14
-rw-r--r--libjava/classpath/java/awt/geom/Point2D.java10
-rw-r--r--libjava/classpath/java/awt/image/AffineTransformOp.java2
-rw-r--r--libjava/classpath/java/awt/image/AreaAveragingScaleFilter.java291
-rw-r--r--libjava/classpath/java/awt/image/BandCombineOp.java8
-rw-r--r--libjava/classpath/java/awt/image/ColorModel.java14
-rw-r--r--libjava/classpath/java/awt/image/ComponentSampleModel.java886
-rw-r--r--libjava/classpath/java/awt/image/ConvolveOp.java14
-rw-r--r--libjava/classpath/java/awt/image/DirectColorModel.java2
-rw-r--r--libjava/classpath/java/awt/image/LookupOp.java14
-rw-r--r--libjava/classpath/java/awt/image/ReplicateScaleFilter.java1
-rw-r--r--libjava/classpath/java/awt/image/RescaleOp.java2
-rw-r--r--libjava/classpath/java/awt/image/SampleModel.java412
-rw-r--r--libjava/classpath/java/awt/image/renderable/RenderableImageProducer.java93
-rw-r--r--libjava/classpath/java/beans/beancontext/BeanContext.java2
-rw-r--r--libjava/classpath/java/beans/beancontext/BeanContextMembershipEvent.java4
-rw-r--r--libjava/classpath/java/beans/beancontext/BeanContextServiceAvailableEvent.java4
-rw-r--r--libjava/classpath/java/beans/beancontext/BeanContextServiceRevokedEvent.java4
-rw-r--r--libjava/classpath/java/beans/beancontext/BeanContextServicesSupport.java172
-rw-r--r--libjava/classpath/java/beans/beancontext/BeanContextSupport.java222
-rw-r--r--libjava/classpath/java/io/CharArrayWriter.java78
-rw-r--r--libjava/classpath/java/io/DataOutputStream.java105
-rw-r--r--libjava/classpath/java/io/FilePermission.java22
-rw-r--r--libjava/classpath/java/io/InputStream.java4
-rw-r--r--libjava/classpath/java/io/ObjectOutputStream.java60
-rw-r--r--libjava/classpath/java/io/ObjectStreamConstants.java20
-rw-r--r--libjava/classpath/java/io/class-dependencies.conf100
-rw-r--r--libjava/classpath/java/lang/Boolean.java49
-rw-r--r--libjava/classpath/java/lang/Character.java4
-rw-r--r--libjava/classpath/java/lang/Class.java512
-rw-r--r--libjava/classpath/java/lang/ClassLoader.java8
-rw-r--r--libjava/classpath/java/lang/Enum.java248
-rw-r--r--libjava/classpath/java/lang/EnumConstantNotPresentException.java2
-rw-r--r--libjava/classpath/java/lang/Iterable.java59
-rw-r--r--libjava/classpath/java/lang/Math.java101
-rw-r--r--libjava/classpath/java/lang/Package.java106
-rw-r--r--libjava/classpath/java/lang/StackTraceElement.java4
-rw-r--r--libjava/classpath/java/lang/StrictMath.java80
-rw-r--r--libjava/classpath/java/lang/StringBuilder.java22
-rw-r--r--libjava/classpath/java/lang/System.java33
-rw-r--r--libjava/classpath/java/lang/Thread.java193
-rw-r--r--libjava/classpath/java/lang/ThreadGroup.java5
-rw-r--r--libjava/classpath/java/lang/ThreadLocal.java11
-rw-r--r--libjava/classpath/java/lang/TypeNotPresentException.java3
-rw-r--r--libjava/classpath/java/lang/annotation/Annotation.java136
-rw-r--r--libjava/classpath/java/lang/annotation/AnnotationFormatError.java1
-rw-r--r--libjava/classpath/java/lang/class-dependencies.conf58
-rw-r--r--libjava/classpath/java/lang/instrument/ClassDefinition.java88
-rw-r--r--libjava/classpath/java/lang/instrument/ClassFileTransformer.java86
-rw-r--r--libjava/classpath/java/lang/instrument/IllegalClassFormatException.java70
-rw-r--r--libjava/classpath/java/lang/instrument/Instrumentation.java139
-rw-r--r--libjava/classpath/java/lang/instrument/UnmodifiableClassException.java69
-rw-r--r--libjava/classpath/java/lang/reflect/AccessibleObject.java29
-rw-r--r--libjava/classpath/java/lang/reflect/AnnotatedElement.java117
-rw-r--r--libjava/classpath/java/lang/reflect/Array.java23
-rw-r--r--libjava/classpath/java/lang/reflect/GenericDeclaration.java63
-rw-r--r--libjava/classpath/java/lang/reflect/GenericSignatureFormatError.java1
-rw-r--r--libjava/classpath/java/lang/reflect/MalformedParameterizedTypeException.java60
-rw-r--r--libjava/classpath/java/lang/reflect/Member.java9
-rw-r--r--libjava/classpath/java/lang/reflect/Modifier.java34
-rw-r--r--libjava/classpath/java/lang/reflect/ParameterizedType.java2
-rw-r--r--libjava/classpath/java/lang/reflect/TypeVariable.java99
-rw-r--r--libjava/classpath/java/math/class-dependencies.conf58
-rw-r--r--libjava/classpath/java/net/InetSocketAddress.java59
-rw-r--r--libjava/classpath/java/net/MimeTypeMapper.java360
-rw-r--r--libjava/classpath/java/net/URI.java14
-rw-r--r--libjava/classpath/java/net/URLClassLoader.java110
-rw-r--r--libjava/classpath/java/net/URLConnection.java151
-rw-r--r--libjava/classpath/java/net/class-dependencies.conf122
-rw-r--r--libjava/classpath/java/nio/ByteBufferImpl.java17
-rw-r--r--libjava/classpath/java/nio/CharBufferImpl.java13
-rw-r--r--libjava/classpath/java/nio/DoubleBufferImpl.java13
-rw-r--r--libjava/classpath/java/nio/FloatBufferImpl.java13
-rw-r--r--libjava/classpath/java/nio/IntBufferImpl.java13
-rw-r--r--libjava/classpath/java/nio/LongBufferImpl.java13
-rw-r--r--libjava/classpath/java/nio/MappedByteBuffer.java2
-rw-r--r--libjava/classpath/java/nio/ShortBufferImpl.java13
-rw-r--r--libjava/classpath/java/nio/channels/Channels.java4
-rw-r--r--libjava/classpath/java/nio/class-dependencies.conf58
-rw-r--r--libjava/classpath/java/rmi/activation/Activatable.java514
-rw-r--r--libjava/classpath/java/rmi/activation/ActivationDesc.java279
-rw-r--r--libjava/classpath/java/rmi/activation/ActivationGroup.java314
-rw-r--r--libjava/classpath/java/rmi/activation/ActivationGroupDesc.java449
-rw-r--r--libjava/classpath/java/rmi/activation/ActivationGroupID.java96
-rw-r--r--libjava/classpath/java/rmi/activation/ActivationGroup_Stub.java2
-rw-r--r--libjava/classpath/java/rmi/activation/ActivationID.java179
-rw-r--r--libjava/classpath/java/rmi/activation/ActivationInstantiator.java23
-rw-r--r--libjava/classpath/java/rmi/activation/ActivationMonitor.java42
-rw-r--r--libjava/classpath/java/rmi/activation/ActivationSystem.java196
-rw-r--r--libjava/classpath/java/rmi/activation/Activator.java22
-rw-r--r--libjava/classpath/java/rmi/activation/package.html33
-rw-r--r--libjava/classpath/java/rmi/dgc/VMID.java139
-rw-r--r--libjava/classpath/java/rmi/dgc/package.html12
-rw-r--r--libjava/classpath/java/rmi/server/ObjID.java202
-rw-r--r--libjava/classpath/java/rmi/server/Operation.java8
-rw-r--r--libjava/classpath/java/rmi/server/RemoteObject.java124
-rw-r--r--libjava/classpath/java/rmi/server/RemoteObjectInvocationHandler.java10
-rw-r--r--libjava/classpath/java/rmi/server/RemoteServer.java99
-rw-r--r--libjava/classpath/java/rmi/server/UID.java262
-rw-r--r--libjava/classpath/java/security/BasicPermission.java5
-rw-r--r--libjava/classpath/java/security/KeyStore.java4
-rw-r--r--libjava/classpath/java/security/SecureRandom.java108
-rw-r--r--libjava/classpath/java/security/Security.java5
-rw-r--r--libjava/classpath/java/security/cert/CertPathValidatorSpi.java4
-rw-r--r--libjava/classpath/java/security/cert/CertStoreSpi.java3
-rw-r--r--libjava/classpath/java/security/cert/Certificate.java2
-rw-r--r--libjava/classpath/java/security/cert/PKIXCertPathChecker.java2
-rw-r--r--libjava/classpath/java/security/cert/PKIXParameters.java2
-rw-r--r--libjava/classpath/java/security/cert/X509CertSelector.java2
-rw-r--r--libjava/classpath/java/sql/Array.java32
-rw-r--r--libjava/classpath/java/sql/Blob.java96
-rw-r--r--libjava/classpath/java/sql/CallableStatement.java500
-rw-r--r--libjava/classpath/java/sql/Clob.java147
-rw-r--r--libjava/classpath/java/sql/Connection.java136
-rw-r--r--libjava/classpath/java/sql/DatabaseMetaData.java166
-rw-r--r--libjava/classpath/java/sql/Date.java6
-rw-r--r--libjava/classpath/java/sql/Driver.java6
-rw-r--r--libjava/classpath/java/sql/DriverManager.java17
-rw-r--r--libjava/classpath/java/sql/PreparedStatement.java124
-rw-r--r--libjava/classpath/java/sql/ResultSet.java422
-rw-r--r--libjava/classpath/java/sql/ResultSetMetaData.java86
-rw-r--r--libjava/classpath/java/sql/SQLData.java4
-rw-r--r--libjava/classpath/java/sql/SQLOutput.java72
-rw-r--r--libjava/classpath/java/sql/SQLWarning.java6
-rw-r--r--libjava/classpath/java/sql/Statement.java37
-rw-r--r--libjava/classpath/java/sql/Time.java7
-rw-r--r--libjava/classpath/java/sql/Timestamp.java34
-rw-r--r--libjava/classpath/java/text/AttributedCharacterIterator.java6
-rw-r--r--libjava/classpath/java/text/Bidi.java935
-rw-r--r--libjava/classpath/java/text/Collator.java13
-rw-r--r--libjava/classpath/java/text/DateFormatSymbols.java16
-rw-r--r--libjava/classpath/java/text/DecimalFormat.java6
-rw-r--r--libjava/classpath/java/text/RuleBasedCollator.java3
-rw-r--r--libjava/classpath/java/text/SimpleDateFormat.java3
-rw-r--r--libjava/classpath/java/text/class-dependencies.conf220
-rw-r--r--libjava/classpath/java/util/AbstractList.java25
-rw-r--r--libjava/classpath/java/util/Arrays.java575
-rw-r--r--libjava/classpath/java/util/BitSet.java2
-rw-r--r--libjava/classpath/java/util/Calendar.java2
-rw-r--r--libjava/classpath/java/util/Collection.java4
-rw-r--r--libjava/classpath/java/util/GregorianCalendar.java2
-rw-r--r--libjava/classpath/java/util/HashMap.java3
-rw-r--r--libjava/classpath/java/util/Hashtable.java3
-rw-r--r--libjava/classpath/java/util/IdentityHashMap.java3
-rw-r--r--libjava/classpath/java/util/InvalidPropertiesFormatException.java17
-rw-r--r--libjava/classpath/java/util/LinkedHashMap.java3
-rw-r--r--libjava/classpath/java/util/LinkedList.java8
-rw-r--r--libjava/classpath/java/util/Locale.java72
-rw-r--r--libjava/classpath/java/util/SimpleTimeZone.java2
-rw-r--r--libjava/classpath/java/util/TreeMap.java3
-rw-r--r--libjava/classpath/java/util/WeakHashMap.java3
-rw-r--r--libjava/classpath/java/util/class-dependencies.conf78
-rw-r--r--libjava/classpath/java/util/jar/Attributes.java12
-rw-r--r--libjava/classpath/java/util/jar/JarFile.java28
-rw-r--r--libjava/classpath/java/util/jar/Manifest.java287
-rw-r--r--libjava/classpath/java/util/logging/Level.java5
-rw-r--r--libjava/classpath/java/util/logging/LogManager.java293
-rw-r--r--libjava/classpath/java/util/logging/Logger.java32
-rw-r--r--libjava/classpath/java/util/regex/Matcher.java14
-rw-r--r--libjava/classpath/java/util/regex/Pattern.java6
-rw-r--r--libjava/classpath/java/util/zip/Deflater.java1
-rw-r--r--libjava/classpath/java/util/zip/DeflaterEngine.java5
-rw-r--r--libjava/classpath/java/util/zip/GZIPInputStream.java2
-rw-r--r--libjava/classpath/java/util/zip/Inflater.java1
-rw-r--r--libjava/classpath/java/util/zip/ZipConstants.java3
-rw-r--r--libjava/classpath/java/util/zip/ZipFile.java60
203 files changed, 12204 insertions, 4418 deletions
diff --git a/libjava/classpath/java/awt/AlphaComposite.java b/libjava/classpath/java/awt/AlphaComposite.java
index 435cfd054c3..92b9e09a60d 100644
--- a/libjava/classpath/java/awt/AlphaComposite.java
+++ b/libjava/classpath/java/awt/AlphaComposite.java
@@ -38,6 +38,8 @@ exception statement from your version. */
package java.awt;
+import gnu.java.awt.java2d.AlphaCompositeContext;
+
import java.awt.image.ColorModel;
import java.util.LinkedHashMap;
import java.util.Map;
@@ -137,14 +139,25 @@ public final class AlphaComposite implements Composite
}
return a;
}
+
+ /**
+ * Creates a {@link CompositeContext} that can be used to perform
+ * compositing operations according to this AlphaComposite settings.
+ *
+ * @param srcColorModel the color model of the source raster
+ * @param dstColorModel the color model of the destination raster
+ * @param hints the rendering hints to use
+ *
+ * @return a {@link CompositeContext} that can be used to perform
+ * compositing operations according to this AlphaComposite settings
+ */
public CompositeContext createContext(ColorModel srcColorModel,
ColorModel dstColorModel,
RenderingHints hints)
{
- // XXX Implement. Sun uses undocumented implementation class
- // sun.java2d.SunCompositeContext.
- throw new Error("not implemented");
+ return new AlphaCompositeContext(this, srcColorModel, dstColorModel);
}
+
public float getAlpha()
{
return alpha;
diff --git a/libjava/classpath/java/awt/BasicStroke.java b/libjava/classpath/java/awt/BasicStroke.java
index 4eece75c995..bf111d08050 100644
--- a/libjava/classpath/java/awt/BasicStroke.java
+++ b/libjava/classpath/java/awt/BasicStroke.java
@@ -38,6 +38,15 @@ exception statement from your version. */
package java.awt;
+import gnu.java.awt.java2d.CubicSegment;
+import gnu.java.awt.java2d.LineSegment;
+import gnu.java.awt.java2d.QuadSegment;
+import gnu.java.awt.java2d.Segment;
+
+import java.awt.geom.AffineTransform;
+import java.awt.geom.GeneralPath;
+import java.awt.geom.PathIterator;
+import java.awt.geom.Point2D;
import java.util.Arrays;
/**
@@ -109,6 +118,8 @@ public class BasicStroke implements Stroke
/** The dash phase. */
private final float phase;
+ private Segment start, end;
+
/**
* Creates a new <code>BasicStroke</code> instance with the given attributes.
*
@@ -249,8 +260,12 @@ public class BasicStroke implements Stroke
*/
public Shape createStrokedShape(Shape s)
{
- // FIXME: Implement this
- throw new Error("not implemented");
+ PathIterator pi = s.getPathIterator( new AffineTransform() );
+
+ if( dash == null )
+ return solidStroke( pi );
+
+ return dashedStroke( pi );
}
/**
@@ -366,4 +381,355 @@ public class BasicStroke implements Stroke
return width == s.width && cap == s.cap && join == s.join
&& limit == s.limit && Arrays.equals(dash, s.dash) && phase == s.phase;
}
+
+ private Shape solidStroke(PathIterator pi)
+ {
+ double[] coords = new double[6];
+ double x, y, x0, y0;
+ boolean pathOpen = false;
+ GeneralPath output = new GeneralPath( );
+ Segment[] p;
+ x = x0 = y = y0 = 0;
+
+ while( !pi.isDone() )
+ {
+ switch( pi.currentSegment(coords) )
+ {
+ case PathIterator.SEG_MOVETO:
+ x0 = x = coords[0];
+ y0 = y = coords[1];
+ if( pathOpen )
+ {
+ capEnds();
+ convertPath(output, start);
+ start = end = null;
+ pathOpen = false;
+ }
+ break;
+
+ case PathIterator.SEG_LINETO:
+ p = (new LineSegment(x, y, coords[0], coords[1])).
+ getDisplacedSegments(width/2.0);
+ if( !pathOpen )
+ {
+ start = p[0];
+ end = p[1];
+ pathOpen = true;
+ }
+ else
+ addSegments(p);
+
+ x = coords[0];
+ y = coords[1];
+ break;
+
+ case PathIterator.SEG_QUADTO:
+ p = (new QuadSegment(x, y, coords[0], coords[1], coords[2],
+ coords[3])).getDisplacedSegments(width/2.0);
+ if( !pathOpen )
+ {
+ start = p[0];
+ end = p[1];
+ pathOpen = true;
+ }
+ else
+ addSegments(p);
+
+ x = coords[0];
+ y = coords[1];
+ break;
+
+ case PathIterator.SEG_CUBICTO:
+ p = new CubicSegment(x, y, coords[0], coords[1],
+ coords[2], coords[3],
+ coords[4], coords[5]).getDisplacedSegments(width/2.0);
+ if( !pathOpen )
+ {
+ start = p[0];
+ end = p[1];
+ pathOpen = true;
+ }
+ else
+ addSegments(p);
+
+ x = coords[0];
+ y = coords[1];
+ break;
+
+ case PathIterator.SEG_CLOSE:
+ p = (new LineSegment(x, y, x0, y0)).getDisplacedSegments(width/2.0);
+ addSegments(p);
+ convertPath(output, start);
+ convertPath(output, end);
+ start = end = null;
+ pathOpen = false;
+ break;
+ }
+ pi.next();
+ }
+
+ if( pathOpen )
+ {
+ capEnds();
+ convertPath(output, start);
+ }
+ return output;
+ }
+
+ private Shape dashedStroke(PathIterator pi)
+ {
+ GeneralPath out = new GeneralPath();
+ return out;
+ }
+
+ /**
+ * Cap the ends of the path (joining the start and end list of segments)
+ */
+ private void capEnds()
+ {
+ Segment returnPath = end.last;
+
+ end.reverseAll(); // reverse the path.
+ end = null;
+ capEnd(start, returnPath);
+ start.last = returnPath.last;
+ end = null;
+
+ capEnd(start, start);
+ }
+
+ /**
+ * Convert and add the linked list of Segments in s to a GeneralPath p.
+ */
+ private void convertPath(GeneralPath p, Segment s)
+ {
+ Segment v = s;
+ p.moveTo((float)s.P1.getX(), (float)s.P1.getY());
+
+ do
+ {
+ if(v instanceof LineSegment)
+ p.lineTo((float)v.P2.getX(), (float)v.P2.getY());
+ else if(v instanceof QuadSegment)
+ p.quadTo((float)((QuadSegment)v).cp.getX(),
+ (float)((QuadSegment)v).cp.getY(),
+ (float)v.P2.getX(),
+ (float)v.P2.getY());
+ else if(v instanceof CubicSegment)
+ p.curveTo((float)((CubicSegment)v).cp1.getX(),
+ (float)((CubicSegment)v).cp1.getY(),
+ (float)((CubicSegment)v).cp2.getX(),
+ (float)((CubicSegment)v).cp2.getY(),
+ (float)v.P2.getX(),
+ (float)v.P2.getY());
+ v = v.next;
+ } while(v != s && v != null);
+
+ p.closePath();
+ }
+
+ /**
+ * Add to segments to start and end, joining the outer pair and
+ */
+ private void addSegments(Segment[] segments)
+ {
+ double[] p0 = start.last.last();
+ double[] p1 = new double[]{start.last.P2.getX(), start.last.P2.getY()};
+ double[] p2 = new double[]{segments[0].P1.getX(), segments[0].P1.getY()};
+ double[] p3 = segments[0].first();
+ Point2D p;
+
+ double det = (p1[0] - p0[0])*(p3[1] - p2[1]) -
+ (p3[0] - p2[0])*(p1[1] - p0[1]);
+
+ if( det > 0 )
+ {
+ // start and segment[0] form the 'inner' part of a join,
+ // connect the overlapping segments
+ p = lineIntersection(p0[0],p0[1],p1[0],p1[1],p2[0],p2[1],p3[0],p3[1], false);
+ if( p == null )
+ {
+ // Dodgy.
+ start.add(new LineSegment(start.last.P2, segments[0].P1));
+ p = new Point2D.Double((segments[0].P1.getX()+ start.last.P2.getX())/2.0,
+ (segments[0].P1.getY()+ start.last.P2.getY())/2.0);
+ }
+ else
+ segments[0].P1 = start.last.P2 = p;
+
+ start.add( segments[0] );
+ joinSegments(end, segments[1], p);
+ }
+ else
+ {
+ // end and segment[1] form the 'inner' part
+ p0 = end.last.last();
+ p1 = new double[]{end.last.P2.getX(), end.last.P2.getY()};
+ p2 = new double[]{segments[1].P1.getX(), segments[1].P1.getY()};
+ p3 = segments[1].first();
+
+ p = lineIntersection(p0[0],p0[1],p1[0],p1[1],
+ p2[0],p2[1],p3[0],p3[1], false);
+ if( p == null )
+ {
+ // Dodgy.
+ end.add(new LineSegment(end.last.P2, segments[1].P1));
+ p = new Point2D.Double((segments[1].P1.getX()+ end.last.P2.getX())/2.0,
+ (segments[1].P1.getY()+ end.last.P2.getY())/2.0);
+ }
+ else
+ segments[1].P1 = end.last.P2 = p;
+
+ end.add( segments[1] );
+ joinSegments(start, segments[0], p);
+ }
+ }
+
+ /**
+ * Make a cap between a and b segments,
+ * where a-->b is the direction of iteration.
+ */
+ private void capEnd(Segment a, Segment b)
+ {
+ double[] p0, p1;
+ double dx, dy, l;
+ Point2D c1,c2;
+
+ switch( cap )
+ {
+ case CAP_BUTT:
+ a.add(new LineSegment(a.last.P2, b.P1));
+ break;
+
+ case CAP_SQUARE:
+ p0 = a.last.last();
+ p1 = new double[]{a.last.P2.getX(), a.last.P2.getY()};
+ dx = p1[0] - p0[0];
+ dy = p1[1] - p0[1];
+ l = Math.sqrt(dx * dx + dy * dy);
+ dx = 0.5*width*dx/l;
+ dy = 0.5*width*dy/l;
+ c1 = new Point2D.Double(p1[0] + dx, p1[1] + dy);
+ c2 = new Point2D.Double(b.P1.getX() + dx, b.P1.getY() + dy);
+ a.add(new LineSegment(a.last.P2, c1));
+ a.add(new LineSegment(c1, c2));
+ a.add(new LineSegment(c2, b.P1));
+ break;
+
+ case CAP_ROUND:
+ p0 = a.last.last();
+ p1 = new double[]{a.last.P2.getX(), a.last.P2.getY()};
+ dx = p1[0] - p0[0];
+ dy = p1[1] - p0[1];
+ l = Math.sqrt(dx * dx + dy * dy);
+ dx = (2.0/3.0)*width*dx/l;
+ dy = (2.0/3.0)*width*dy/l;
+ c1 = new Point2D.Double(p1[0] + dx, p1[1] + dy);
+ c2 = new Point2D.Double(b.P1.getX() + dx, b.P1.getY() + dy);
+ a.add(new CubicSegment(a.last.P2, c1, c2, b.P1));
+ break;
+ }
+ a.add(b);
+ }
+
+ /**
+ * Returns the intersection of two lines, or null if there isn't one.
+ * @param infinite - true if the lines should be regarded as infinite, false
+ * if the intersection must be within the given segments.
+ * @return a Point2D or null.
+ */
+ private Point2D lineIntersection(double X1, double Y1,
+ double X2, double Y2,
+ double X3, double Y3,
+ double X4, double Y4,
+ boolean infinite)
+ {
+ double x1 = X1;
+ double y1 = Y1;
+ double rx = X2 - x1;
+ double ry = Y2 - y1;
+
+ double x2 = X3;
+ double y2 = Y3;
+ double sx = X4 - x2;
+ double sy = Y4 - y2;
+
+ double determinant = sx * ry - sy * rx;
+ double nom = (sx * (y2 - y1) + sy * (x1 - x2));
+
+ // lines can be considered parallel.
+ if (Math.abs(determinant) < 1E-6)
+ return null;
+
+ nom = nom / determinant;
+
+ // check if lines are within the bounds
+ if(!infinite && (nom > 1.0 || nom < 0.0))
+ return null;
+
+ return new Point2D.Double(x1 + nom * rx, y1 + nom * ry);
+ }
+
+ /**
+ * Join a and b segments, where a-->b is the direction of iteration.
+ *
+ * insideP is the inside intersection point of the join, needed for
+ * calculating miter lengths.
+ */
+ private void joinSegments(Segment a, Segment b, Point2D insideP)
+ {
+ double[] p0, p1;
+ double dx, dy, l;
+ Point2D c1,c2;
+
+ switch( join )
+ {
+ case JOIN_MITER:
+ p0 = a.last.last();
+ p1 = new double[]{a.last.P2.getX(), a.last.P2.getY()};
+ double[] p2 = new double[]{b.P1.getX(), b.P1.getY()};
+ double[] p3 = b.first();
+ Point2D p = lineIntersection(p0[0],p0[1],p1[0],p1[1],p2[0],p2[1],p3[0],p3[1], true);
+ if( p == null || insideP == null )
+ a.add(new LineSegment(a.last.P2, b.P1));
+ else if((p.distance(insideP)/width) < limit)
+ {
+ a.add(new LineSegment(a.last.P2, p));
+ a.add(new LineSegment(p, b.P1));
+ }
+ else
+ {
+ // outside miter limit, do a bevel join.
+ a.add(new LineSegment(a.last.P2, b.P1));
+ }
+ break;
+
+ case JOIN_ROUND:
+ p0 = a.last.last();
+ p1 = new double[]{a.last.P2.getX(), a.last.P2.getY()};
+ dx = p1[0] - p0[0];
+ dy = p1[1] - p0[1];
+ l = Math.sqrt(dx * dx + dy * dy);
+ dx = 0.5*width*dx/l;
+ dy = 0.5*width*dy/l;
+ c1 = new Point2D.Double(p1[0] + dx, p1[1] + dy);
+
+ p0 = new double[]{b.P1.getX(), b.P1.getY()};
+ p1 = b.first();
+
+ dx = p0[0] - p1[0]; // backwards direction.
+ dy = p0[1] - p1[1];
+ l = Math.sqrt(dx * dx + dy * dy);
+ dx = 0.5*width*dx/l;
+ dy = 0.5*width*dy/l;
+ c2 = new Point2D.Double(p0[0] + dx, p0[1] + dy);
+ a.add(new CubicSegment(a.last.P2, c1, c2, b.P1));
+ break;
+
+ case JOIN_BEVEL:
+ a.add(new LineSegment(a.last.P2, b.P1));
+ break;
+ }
+ a.add(b);
+ }
}
diff --git a/libjava/classpath/java/awt/Button.java b/libjava/classpath/java/awt/Button.java
index e788d824ee1..ae897a2f75f 100644
--- a/libjava/classpath/java/awt/Button.java
+++ b/libjava/classpath/java/awt/Button.java
@@ -98,7 +98,7 @@ private transient ActionListener action_listeners;
protected class AccessibleAWTButton extends AccessibleAWTComponent
implements AccessibleAction, AccessibleValue
{
- public static final long serialVersionUID = -5932203980244017102L;
+ private static final long serialVersionUID = -5932203980244017102L;
protected AccessibleAWTButton()
{
diff --git a/libjava/classpath/java/awt/Choice.java b/libjava/classpath/java/awt/Choice.java
index 2e55d19b2d5..90a8d3141c8 100644
--- a/libjava/classpath/java/awt/Choice.java
+++ b/libjava/classpath/java/awt/Choice.java
@@ -556,6 +556,17 @@ processEvent(AWTEvent event)
super.processEvent(event);
}
+void
+dispatchEventImpl(AWTEvent e)
+{
+ if (e.id <= ItemEvent.ITEM_LAST
+ && e.id >= ItemEvent.ITEM_FIRST
+ && (item_listeners != null || (eventMask & AWTEvent.ITEM_EVENT_MASK) != 0))
+ processEvent(e);
+ else
+ super.dispatchEventImpl(e);
+}
+
/*************************************************************************/
/**
diff --git a/libjava/classpath/java/awt/Component.java b/libjava/classpath/java/awt/Component.java
index de01fc1145b..dbbec8ac178 100644
--- a/libjava/classpath/java/awt/Component.java
+++ b/libjava/classpath/java/awt/Component.java
@@ -906,7 +906,7 @@ public abstract class Component
// The JDK repaints the component before invalidating the parent.
// So do we.
- if (isShowing())
+ if (isShowing() && isLightweight())
repaint();
// Invalidate the parent if we have one. The component itself must
// not be invalidated. We also avoid NullPointerException with
@@ -1075,8 +1075,6 @@ public abstract class Component
Component p = parent;
if (p != null)
return p.getFont();
- if (peer != null)
- return peer.getGraphics().getFont();
return null;
}
@@ -2315,6 +2313,10 @@ public abstract class Component
if (oldEvent != null)
postEvent (oldEvent);
+ // Give toolkit a chance to dispatch the event
+ // to globally registered listeners.
+ Toolkit.getDefaultToolkit().globalDispatchEvent(e);
+
// Some subclasses in the AWT package need to override this behavior,
// hence the use of dispatchEventImpl().
dispatchEventImpl(e);
@@ -3089,6 +3091,8 @@ public abstract class Component
mouseListener.mouseClicked(e);
break;
case MouseEvent.MOUSE_ENTERED:
+ if( isLightweight() )
+ setCursor( getCursor() );
mouseListener.mouseEntered(e);
break;
case MouseEvent.MOUSE_EXITED:
@@ -3101,7 +3105,6 @@ public abstract class Component
mouseListener.mouseReleased(e);
break;
}
- e.consume();
}
/**
@@ -4079,14 +4082,9 @@ public abstract class Component
*/
public Container getFocusCycleRootAncestor ()
{
- if (this instanceof Window
- && ((Container) this).isFocusCycleRoot ())
- return (Container) this;
-
Container parent = getParent ();
- while (parent != null
- && !parent.isFocusCycleRoot ())
+ while (parent != null && !parent.isFocusCycleRoot())
parent = parent.getParent ();
return parent;
@@ -4114,9 +4112,32 @@ public abstract class Component
*/
public void nextFocus ()
{
- KeyboardFocusManager manager = KeyboardFocusManager.getCurrentKeyboardFocusManager ();
+ // Find the nearest valid (== showing && focusable && enabled) focus
+ // cycle root ancestor and the focused component in it.
+ Container focusRoot = getFocusCycleRootAncestor();
+ Component focusComp = this;
+ while (focusRoot != null
+ && ! (focusRoot.isShowing() && focusRoot.isFocusable()
+ && focusRoot.isEnabled()))
+ {
+ focusComp = focusRoot;
+ focusRoot = focusComp.getFocusCycleRootAncestor();
+ }
+
+ if (focusRoot != null)
+ {
+ // First try to get the componentBefore from the policy.
+ FocusTraversalPolicy policy = focusRoot.getFocusTraversalPolicy();
+ Component nextFocus = policy.getComponentAfter(focusRoot, focusComp);
+
+ // If this fails, then ask for the defaultComponent.
+ if (nextFocus == null)
+ nextFocus = policy.getDefaultComponent(focusRoot);
- manager.focusNextComponent (this);
+ // Request focus on this component, if not null.
+ if (nextFocus != null)
+ nextFocus.requestFocus();
+ }
}
/**
@@ -4128,9 +4149,32 @@ public abstract class Component
*/
public void transferFocusBackward ()
{
- KeyboardFocusManager manager = KeyboardFocusManager.getCurrentKeyboardFocusManager ();
+ // Find the nearest valid (== showing && focusable && enabled) focus
+ // cycle root ancestor and the focused component in it.
+ Container focusRoot = getFocusCycleRootAncestor();
+ Component focusComp = this;
+ while (focusRoot != null
+ && ! (focusRoot.isShowing() && focusRoot.isFocusable()
+ && focusRoot.isEnabled()))
+ {
+ focusComp = focusRoot;
+ focusRoot = focusComp.getFocusCycleRootAncestor();
+ }
+
+ if (focusRoot != null)
+ {
+ // First try to get the componentBefore from the policy.
+ FocusTraversalPolicy policy = focusRoot.getFocusTraversalPolicy();
+ Component nextFocus = policy.getComponentBefore(focusRoot, focusComp);
+
+ // If this fails, then ask for the defaultComponent.
+ if (nextFocus == null)
+ nextFocus = policy.getDefaultComponent(focusRoot);
- manager.focusPreviousComponent (this);
+ // Request focus on this component, if not null.
+ if (nextFocus != null)
+ nextFocus.requestFocus();
+ }
}
/**
@@ -4144,9 +4188,63 @@ public abstract class Component
*/
public void transferFocusUpCycle ()
{
- KeyboardFocusManager manager = KeyboardFocusManager.getCurrentKeyboardFocusManager ();
+ // Find the nearest focus cycle root ancestor that is itself
+ // focusable, showing and enabled.
+ Container focusCycleRoot = getFocusCycleRootAncestor();
+ while (focusCycleRoot != null &&
+ ! (focusCycleRoot.isShowing() && focusCycleRoot.isFocusable()
+ && focusCycleRoot.isEnabled()))
+ {
+ focusCycleRoot = focusCycleRoot.getFocusCycleRootAncestor();
+ }
+
+ KeyboardFocusManager fm =
+ KeyboardFocusManager.getCurrentKeyboardFocusManager();
+
+ if (focusCycleRoot != null)
+ {
+ // If we found a focus cycle root, then we make this the new
+ // focused component, and make it's focus cycle root the new
+ // global focus cycle root. If the found root has no focus cycle
+ // root ancestor itself, then the component will be both the focused
+ // component and the new global focus cycle root.
+ Container focusCycleAncestor =
+ focusCycleRoot.getFocusCycleRootAncestor();
+ Container globalFocusCycleRoot;
+ if (focusCycleAncestor == null)
+ globalFocusCycleRoot = focusCycleRoot;
+ else
+ globalFocusCycleRoot = focusCycleAncestor;
+
+ fm.setGlobalCurrentFocusCycleRoot(globalFocusCycleRoot);
+ focusCycleRoot.requestFocus();
+ }
+ else
+ {
+ // If this component has no applicable focus cycle root, we try
+ // find the nearest window and set this as the new global focus cycle
+ // root and the default focus component of this window the new focused
+ // component.
+ Container cont;
+ if (this instanceof Container)
+ cont = (Container) this;
+ else
+ cont = getParent();
- manager.upFocusCycle (this);
+ while (cont != null && !(cont instanceof Window))
+ cont = cont.getParent();
+
+ if (cont != null)
+ {
+ FocusTraversalPolicy policy = cont.getFocusTraversalPolicy();
+ Component focusComp = policy.getDefaultComponent(cont);
+ if (focusComp != null)
+ {
+ fm.setGlobalCurrentFocusCycleRoot(cont);
+ focusComp.requestFocus();
+ }
+ }
+ }
}
/**
@@ -4876,7 +4974,7 @@ p * <li>the set of backward traversal keys
oldKey = Event.UP;
break;
default:
- oldKey = newKey;
+ oldKey = (int) ((KeyEvent) e).getKeyChar();
}
translated = new Event (target, when, oldID,
@@ -4922,10 +5020,6 @@ p * <li>the set of backward traversal keys
void dispatchEventImpl(AWTEvent e)
{
- // Give toolkit a chance to dispatch the event
- // to globally registered listeners.
- Toolkit.getDefaultToolkit().globalDispatchEvent(e);
-
// This boolean tells us not to process focus events when the focus
// opposite component is the same as the focus component.
boolean ignoreFocus =
@@ -4934,6 +5028,10 @@ p * <li>the set of backward traversal keys
if (eventTypeEnabled (e.id))
{
+ if (e.id != PaintEvent.PAINT && e.id != PaintEvent.UPDATE
+ && !ignoreFocus)
+ processEvent(e);
+
// the trick we use to communicate between dispatch and redispatch
// is to have KeyboardFocusManager.redispatch synchronize on the
// object itself. we then do not redispatch to KeyboardFocusManager
@@ -4954,14 +5052,11 @@ p * <li>the set of backward traversal keys
.dispatchEvent(e))
return;
case MouseEvent.MOUSE_PRESSED:
- if (isLightweight())
- requestFocus();
+ if (isLightweight() && !e.isConsumed())
+ requestFocus();
break;
}
}
- if (e.id != PaintEvent.PAINT && e.id != PaintEvent.UPDATE
- && !ignoreFocus)
- processEvent(e);
}
if (peer != null)
@@ -4978,6 +5073,15 @@ p * <li>the set of backward traversal keys
switch (type)
{
+ case HierarchyEvent.HIERARCHY_CHANGED:
+ return (hierarchyListener != null
+ || (eventMask & AWTEvent.HIERARCHY_EVENT_MASK) != 0);
+
+ case HierarchyEvent.ANCESTOR_MOVED:
+ case HierarchyEvent.ANCESTOR_RESIZED:
+ return (hierarchyBoundsListener != null
+ || (eventMask & AWTEvent.HIERARCHY_BOUNDS_EVENT_MASK) != 0);
+
case ComponentEvent.COMPONENT_HIDDEN:
case ComponentEvent.COMPONENT_MOVED:
case ComponentEvent.COMPONENT_RESIZED:
@@ -5002,6 +5106,9 @@ p * <li>the set of backward traversal keys
case MouseEvent.MOUSE_DRAGGED:
return (mouseMotionListener != null
|| (eventMask & AWTEvent.MOUSE_MOTION_EVENT_MASK) != 0);
+ case MouseEvent.MOUSE_WHEEL:
+ return (mouseWheelListener != null
+ || (eventMask & AWTEvent.MOUSE_WHEEL_EVENT_MASK) != 0);
case FocusEvent.FOCUS_GAINED:
case FocusEvent.FOCUS_LOST:
@@ -5289,7 +5396,7 @@ p * <li>the set of backward traversal keys
*/
public String getAccessibleName()
{
- return accessibleName == null ? getName() : accessibleName;
+ return accessibleName;
}
/**
@@ -5329,8 +5436,10 @@ p * <li>the set of backward traversal keys
s.add(AccessibleState.FOCUSABLE);
if (isFocusOwner())
s.add(AccessibleState.FOCUSED);
- if (isOpaque())
- s.add(AccessibleState.OPAQUE);
+ // Note: While the java.awt.Component has an 'opaque' property, it
+ // seems that it is not added to the accessible state set here, even
+ // if this property is true. However, it is handled for
+ // javax.swing.JComponent, so we add it there.
if (Component.this.isShowing())
s.add(AccessibleState.SHOWING);
if (Component.this.isVisible())
@@ -5614,7 +5723,7 @@ p * <li>the set of backward traversal keys
*/
public Point getLocation()
{
- return Component.this.isShowing() ? Component.this.getLocation() : null;
+ return Component.this.getLocation();
}
/**
@@ -5638,7 +5747,7 @@ p * <li>the set of backward traversal keys
*/
public Rectangle getBounds()
{
- return Component.this.isShowing() ? Component.this.getBounds() : null;
+ return Component.this.getBounds();
}
/**
@@ -5661,7 +5770,7 @@ p * <li>the set of backward traversal keys
*/
public Dimension getSize()
{
- return Component.this.isShowing() ? Component.this.getSize() : null;
+ return Component.this.getSize();
}
/**
diff --git a/libjava/classpath/java/awt/Container.java b/libjava/classpath/java/awt/Container.java
index 41892caeafa..2419a7bd24a 100644
--- a/libjava/classpath/java/awt/Container.java
+++ b/libjava/classpath/java/awt/Container.java
@@ -388,10 +388,6 @@ public class Container extends Component
ContainerListener[] listeners = getContainerListeners();
for (int i = 0; i < listeners.length; i++)
listeners[i].componentAdded(ce);
-
- // Repaint this container.
- repaint(comp.getX(), comp.getY(), comp.getWidth(),
- comp.getHeight());
}
}
@@ -968,6 +964,13 @@ public class Container extends Component
* child component claims the point, the container itself is returned,
* unless the point does not exist within this container, in which
* case <code>null</code> is returned.
+ *
+ * When components overlap, the first component is returned. The component
+ * that is closest to (x, y), containing that location, is returned.
+ * Heavyweight components take precedence of lightweight components.
+ *
+ * This function does not ignore invisible components. If there is an invisible
+ * component at (x,y), it will be returned.
*
* @param x The X coordinate of the point.
* @param y The Y coordinate of the point.
@@ -987,7 +990,14 @@ public class Container extends Component
* child component claims the point, the container itself is returned,
* unless the point does not exist within this container, in which
* case <code>null</code> is returned.
- *
+ *
+ * When components overlap, the first component is returned. The component
+ * that is closest to (x, y), containing that location, is returned.
+ * Heavyweight components take precedence of lightweight components.
+ *
+ * This function does not ignore invisible components. If there is an invisible
+ * component at (x,y), it will be returned.
+ *
* @param x The x position of the point to return the component at.
* @param y The y position of the point to return the component at.
*
@@ -1002,17 +1012,28 @@ public class Container extends Component
{
if (!contains (x, y))
return null;
+
+ // First find the component closest to (x,y) that is a heavyweight.
for (int i = 0; i < ncomponents; ++i)
{
- // Ignore invisible children...
- if (!component[i].isVisible ())
- continue;
-
- int x2 = x - component[i].x;
- int y2 = y - component[i].y;
- if (component[i].contains (x2, y2))
- return component[i];
+ Component comp = component[i];
+ int x2 = x - comp.x;
+ int y2 = y - comp.y;
+ if (comp.contains (x2, y2) && !comp.isLightweight())
+ return comp;
}
+
+ // if a heavyweight component is not found, look for a lightweight
+ // closest to (x,y).
+ for (int i = 0; i < ncomponents; ++i)
+ {
+ Component comp = component[i];
+ int x2 = x - comp.x;
+ int y2 = y - comp.y;
+ if (comp.contains (x2, y2) && comp.isLightweight())
+ return comp;
+ }
+
return this;
}
}
@@ -1025,6 +1046,13 @@ public class Container extends Component
* unless the point does not exist within this container, in which
* case <code>null</code> is returned.
*
+ * The top-most child component is returned in the case where components overlap.
+ * This is determined by finding the component closest to (x,y) and contains
+ * that location. Heavyweight components take precedence of lightweight components.
+ *
+ * This function does not ignore invisible components. If there is an invisible
+ * component at (x,y), it will be returned.
+ *
* @param p The point to return the component at.
* @return The component containing the specified point, or <code>null</code>
* if there is no such point.
@@ -1034,6 +1062,22 @@ public class Container extends Component
return getComponentAt (p.x, p.y);
}
+ /**
+ * Locates the visible child component that contains the specified position.
+ * The top-most child component is returned in the case where there is overlap
+ * in the components. If the containing child component is a Container,
+ * this method will continue searching for the deepest nested child
+ * component. Components which are not visible are ignored during the search.
+ *
+ * findComponentAt differs from getComponentAt, because it recursively
+ * searches a Container's children.
+ *
+ * @param x - x coordinate
+ * @param y - y coordinate
+ * @return null if the component does not contain the position.
+ * If there is no child component at the requested point and the point is
+ * within the bounds of the container the container itself is returned.
+ */
public Component findComponentAt(int x, int y)
{
synchronized (getTreeLock ())
@@ -1067,53 +1111,20 @@ public class Container extends Component
}
/**
- * Finds the visible child component that contains the specified position.
- * The top-most child is returned in the case where there is overlap.
- * If the top-most child is transparent and has no MouseListeners attached,
- * we discard it and return the next top-most component containing the
- * specified position.
- * @param x the x coordinate
- * @param y the y coordinate
- * @return null if the <code>this</code> does not contain the position,
- * otherwise the top-most component (out of this container itself and
- * its descendants) meeting the criteria above.
+ * Locates the visible child component that contains the specified position.
+ * The top-most child component is returned in the case where there is overlap
+ * in the components. If the containing child component is a Container,
+ * this method will continue searching for the deepest nested child
+ * component. Components which are not visible are ignored during the search.
+ *
+ * findComponentAt differs from getComponentAt, because it recursively
+ * searches a Container's children.
+ *
+ * @param p - the component's location
+ * @return null if the component does not contain the position.
+ * If there is no child component at the requested point and the point is
+ * within the bounds of the container the container itself is returned.
*/
- Component findComponentForMouseEventAt(int x, int y)
- {
- synchronized (getTreeLock())
- {
- if (!contains(x, y))
- return null;
-
- for (int i = 0; i < ncomponents; ++i)
- {
- // Ignore invisible children...
- if (!component[i].isVisible())
- continue;
-
- int x2 = x - component[i].x;
- int y2 = y - component[i].y;
- // We don't do the contains() check right away because
- // findComponentAt would redundantly do it first thing.
- if (component[i] instanceof Container)
- {
- Container k = (Container) component[i];
- Component r = k.findComponentForMouseEventAt(x2, y2);
- if (r != null)
- return r;
- }
- else if (component[i].contains(x2, y2))
- return component[i];
- }
-
- //don't return transparent components with no MouseListeners
- if (getMouseListeners().length == 0
- && getMouseMotionListeners().length == 0)
- return null;
- return this;
- }
- }
-
public Component findComponentAt(Point p)
{
return findComponentAt(p.x, p.y);
@@ -1454,7 +1465,7 @@ public class Container extends Component
{
Container ancestor = getFocusCycleRootAncestor ();
- if (ancestor != this)
+ if (ancestor != this && ancestor != null)
return ancestor.getFocusTraversalPolicy ();
else
{
@@ -1524,9 +1535,16 @@ public class Container extends Component
*/
public void transferFocusDownCycle ()
{
- KeyboardFocusManager manager = KeyboardFocusManager.getCurrentKeyboardFocusManager ();
-
- manager.downFocusCycle (this);
+ if (isFocusCycleRoot())
+ {
+ KeyboardFocusManager fm =
+ KeyboardFocusManager.getCurrentKeyboardFocusManager();
+ fm.setGlobalCurrentFocusCycleRoot(this);
+ FocusTraversalPolicy policy = getFocusTraversalPolicy();
+ Component defaultComponent = policy.getDefaultComponent(this);
+ if (defaultComponent != null)
+ defaultComponent.requestFocus();
+ }
}
/**
diff --git a/libjava/classpath/java/awt/DefaultFocusTraversalPolicy.java b/libjava/classpath/java/awt/DefaultFocusTraversalPolicy.java
index 46b56d3fc29..a5cb7dad16a 100644
--- a/libjava/classpath/java/awt/DefaultFocusTraversalPolicy.java
+++ b/libjava/classpath/java/awt/DefaultFocusTraversalPolicy.java
@@ -61,6 +61,8 @@ package java.awt;
public class DefaultFocusTraversalPolicy
extends ContainerOrderFocusTraversalPolicy
{
+ private static final long serialVersionUID = 8876966522510157497L;
+
/**
* Construct a default focus traversal policy.
*/
diff --git a/libjava/classpath/java/awt/DefaultKeyboardFocusManager.java b/libjava/classpath/java/awt/DefaultKeyboardFocusManager.java
index bce6352a900..a60cefd9c9d 100644
--- a/libjava/classpath/java/awt/DefaultKeyboardFocusManager.java
+++ b/libjava/classpath/java/awt/DefaultKeyboardFocusManager.java
@@ -478,59 +478,25 @@ public class DefaultKeyboardFocusManager extends KeyboardFocusManager
public void focusPreviousComponent (Component comp)
{
- Component focusComp = (comp == null) ? getGlobalFocusOwner () : comp;
- Container focusCycleRoot = focusComp.getFocusCycleRootAncestor ();
- FocusTraversalPolicy policy = focusCycleRoot.getFocusTraversalPolicy ();
-
- Component previous = policy.getComponentBefore (focusCycleRoot, focusComp);
- if (previous != null)
- previous.requestFocusInWindow ();
+ if (comp != null)
+ comp.transferFocusBackward();
}
public void focusNextComponent (Component comp)
{
- Component focusComp = (comp == null) ? getGlobalFocusOwner () : comp;
- Container focusCycleRoot = focusComp.getFocusCycleRootAncestor ();
- FocusTraversalPolicy policy = focusCycleRoot.getFocusTraversalPolicy ();
-
- Component next = policy.getComponentAfter (focusCycleRoot, focusComp);
- if (next != null)
- next.requestFocusInWindow ();
+ if (comp != null)
+ comp.transferFocus();
}
public void upFocusCycle (Component comp)
{
- Component focusComp = (comp == null) ? getGlobalFocusOwner () : comp;
- Container focusCycleRoot = focusComp.getFocusCycleRootAncestor ();
-
- if (focusCycleRoot instanceof Window)
- {
- FocusTraversalPolicy policy = focusCycleRoot.getFocusTraversalPolicy ();
- Component defaultComponent = policy.getDefaultComponent (focusCycleRoot);
- if (defaultComponent != null)
- defaultComponent.requestFocusInWindow ();
- }
- else
- {
- Container parentFocusCycleRoot = focusCycleRoot.getFocusCycleRootAncestor ();
-
- focusCycleRoot.requestFocusInWindow ();
- setGlobalCurrentFocusCycleRoot (parentFocusCycleRoot);
- }
+ if (comp != null)
+ comp.transferFocusUpCycle();
}
public void downFocusCycle (Container cont)
{
- if (cont == null)
- return;
-
- if (cont.isFocusCycleRoot (cont))
- {
- FocusTraversalPolicy policy = cont.getFocusTraversalPolicy ();
- Component defaultComponent = policy.getDefaultComponent (cont);
- if (defaultComponent != null)
- defaultComponent.requestFocusInWindow ();
- setGlobalCurrentFocusCycleRoot (cont);
- }
+ if (cont != null)
+ cont.transferFocusDownCycle();
}
} // class DefaultKeyboardFocusManager
diff --git a/libjava/classpath/java/awt/Dialog.java b/libjava/classpath/java/awt/Dialog.java
index 7e5e7215aac..55c3371e622 100644
--- a/libjava/classpath/java/awt/Dialog.java
+++ b/libjava/classpath/java/awt/Dialog.java
@@ -1,39 +1,40 @@
/* Dialog.java -- An AWT dialog box
- Copyright (C) 1999, 2000, 2001, 2002, 2005 Free Software Foundation, Inc.
-
-This file is part of GNU Classpath.
-
-GNU Classpath is free software; you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation; either version 2, or (at your option)
-any later version.
-
-GNU Classpath 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 for more details.
-
-You should have received a copy of the GNU General Public License
-along with GNU Classpath; see the file COPYING. If not, write to the
-Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
-02110-1301 USA.
-
-Linking this library statically or dynamically with other modules is
-making a combined work based on this library. Thus, the terms and
-conditions of the GNU General Public License cover the whole
-combination.
-
-As a special exception, the copyright holders of this library give you
-permission to link this library with independent modules to produce an
-executable, regardless of the license terms of these independent
-modules, and to copy and distribute the resulting executable under
-terms of your choice, provided that you also meet, for each linked
-independent module, the terms and conditions of the license of that
-module. An independent module is a module which is not derived from
-or based on this library. If you modify this library, you may extend
-this exception to your version of the library, but you are not
-obligated to do so. If you do not wish to do so, delete this
-exception statement from your version. */
+ Copyright (C) 1999, 2000, 2001, 2002, 2005, 2006
+ Free Software Foundation, Inc.
+
+ This file is part of GNU Classpath.
+
+ GNU Classpath is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2, or (at your option)
+ any later version.
+
+ GNU Classpath 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 for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with GNU Classpath; see the file COPYING. If not, write to the
+ Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+ 02110-1301 USA.
+
+ Linking this library statically or dynamically with other modules is
+ making a combined work based on this library. Thus, the terms and
+ conditions of the GNU General Public License cover the whole
+ combination.
+
+ As a special exception, the copyright holders of this library give you
+ permission to link this library with independent modules to produce an
+ executable, regardless of the license terms of these independent
+ modules, and to copy and distribute the resulting executable under
+ terms of your choice, provided that you also meet, for each linked
+ independent module, the terms and conditions of the license of that
+ module. An independent module is a module which is not derived from
+ or based on this library. If you modify this library, you may extend
+ this exception to your version of the library, but you are not
+ obligated to do so. If you do not wish to do so, delete this
+ exception statement from your version. */
package java.awt;
@@ -46,457 +47,422 @@ import javax.accessibility.AccessibleState;
import javax.accessibility.AccessibleStateSet;
/**
- * A dialog box widget class.
- *
+ * <code>Dialog</code> provides a top-level window normally used to receive
+ * user input in applications.
+ * <p>
+ * A dialog always has another top-level window as owner and is only visible
+ * if this owner is visible to the user. The default layout of dialogs is the
+ * <code>BorderLayout</code>. Dialogs can be modal (blocks user input to other
+ * components) or non-modal (user input in other components are allowed).
+ * </p>
+ *
* @author Aaron M. Renn (arenn@urbanophile.com)
* @author Tom Tromey (tromey@redhat.com)
*/
public class Dialog extends Window
{
+ // Serialization constant
+ private static final long serialVersionUID = 5920926903803293709L;
-/*
- * Static Variables
- */
-
-// Serialization constant
-private static final long serialVersionUID = 5920926903803293709L;
-
-/*************************************************************************/
-
-/*
- * Instance Variables
- */
-
-/**
- * @serial Indicates whether or not this dialog box is modal.
- */
-private boolean modal;
-
-/**
- * @serial Indicates whether or not this dialog box is resizable.
- */
-private boolean resizable = true;
-
-/**
- * @serial The title string for this dialog box, which can be
- * <code>null</code>.
- */
-private String title;
-
-/**
- * This field indicates whether the dialog is undecorated or not.
- */
-private boolean undecorated = false;
-
-/**
- * Indicates that we are blocked for modality in show
- */
-private boolean blocked = false;
-
-/**
- * Secondary EventQueue to handle AWT events while
- * we are blocked for modality in show
- */
-private EventQueue eq2 = null;
-
-/*************************************************************************/
-
-/*
- * Constructors
- */
-
-/**
- * Initializes a new instance of <code>Dialog</code> with the specified
- * parent, that is resizable and not modal, and which has no title.
- *
- * @param parent The parent frame of this dialog box.
- *
- * @exception IllegalArgumentException If the owner's GraphicsConfiguration
- * is not from a screen device, or if owner is null. This exception is always
- * thrown when GraphicsEnvironment.isHeadless() returns true.
- */
-public
-Dialog(Frame parent)
-{
- this(parent, "", false);
-}
-
-/*************************************************************************/
-
-/**
- * Initializes a new instance of <code>Dialog</code> with the specified
- * parent and modality, that is resizable and which has no title.
- *
- * @param parent The parent frame of this dialog box.
- * @param modal <code>true</code> if this dialog box is modal,
- * <code>false</code> otherwise.
- *
- * @exception IllegalArgumentException If the owner's GraphicsConfiguration
- * is not from a screen device, or if owner is null. This exception is always
- * thrown when GraphicsEnvironment.isHeadless() returns true.
- */
-public
-Dialog(Frame parent, boolean modal)
-{
- this(parent, "", modal);
-}
-
-/*************************************************************************/
-
-/**
- * Initializes a new instance of <code>Dialog</code> with the specified
- * parent, that is resizable and not modal, and which has the specified
- * title.
- *
- * @param parent The parent frame of this dialog box.
- * @param title The title string for this dialog box.
- *
- * @exception IllegalArgumentException If the owner's GraphicsConfiguration
- * is not from a screen device, or if owner is null. This exception is always
- * thrown when GraphicsEnvironment.isHeadless() returns true.
- */
-public
-Dialog(Frame parent, String title)
-{
- this(parent, title, false);
-}
-
-/*************************************************************************/
-
-/**
- * Initializes a new instance of <code>Dialog</code> with the specified,
- * parent, title, and modality, that is resizable.
- *
- * @param parent The parent frame of this dialog box.
- * @param title The title string for this dialog box.
- * @param modal <code>true</code> if this dialog box is modal,
- * <code>false</code> otherwise.
- *
- * @exception IllegalArgumentException If owner is null or
- * GraphicsEnvironment.isHeadless() returns true.
- */
-public
-Dialog(Frame parent, String title, boolean modal)
-{
- this (parent, title, modal, parent.getGraphicsConfiguration ());
-}
-
-/**
- * Initializes a new instance of <code>Dialog</code> with the specified,
- * parent, title, modality and <code>GraphicsConfiguration</code>,
- * that is resizable.
- *
- * @param parent The parent frame of this dialog box.
- * @param title The title string for this dialog box.
- * @param modal <code>true</code> if this dialog box is modal,
- * <code>false</code> otherwise.
- * @param gc The <code>GraphicsConfiguration</code> object to use.
- *
- * @exception IllegalArgumentException If owner is null, the
- * GraphicsConfiguration is not a screen device or
- * GraphicsEnvironment.isHeadless() returns true.
- *
- * @since 1.4
- */
-public
-Dialog (Frame parent, String title, boolean modal, GraphicsConfiguration gc)
-{
- super (parent, gc);
-
- // A null title is equivalent to an empty title
- this.title = (title != null) ? title : "";
- this.modal = modal;
- visible = false;
-
- setLayout(new BorderLayout());
-}
-
-/**
- * Initializes a new instance of <code>Dialog</code> with the specified,
- * parent, that is resizable.
- *
- * @exception IllegalArgumentException If parent is null. This exception is
- * always thrown when GraphicsEnvironment.isHeadless() returns true.
- *
- * @since 1.2
- */
-public
-Dialog (Dialog owner)
-{
- this (owner, "", false, owner.getGraphicsConfiguration ());
-}
-
-/**
- * Initializes a new instance of <code>Dialog</code> with the specified,
- * parent and title, that is resizable.
- *
- * @exception IllegalArgumentException If parent is null. This exception is
- * always thrown when GraphicsEnvironment.isHeadless() returns true.
- *
- * @since 1.2
- */
-public
-Dialog (Dialog owner, String title)
-{
- this (owner, title, false, owner.getGraphicsConfiguration ());
-}
-
-/**
- * Initializes a new instance of <code>Dialog</code> with the specified,
- * parent, title and modality, that is resizable.
- *
- * @exception IllegalArgumentException If parent is null. This exception is
- * always thrown when GraphicsEnvironment.isHeadless() returns true.
- *
- * @since 1.2
- */
-public
-Dialog (Dialog owner, String title, boolean modal)
-{
- this (owner, title, modal, owner.getGraphicsConfiguration ());
-}
+ /**
+ * @serial Indicates whether or not this dialog box is modal.
+ */
+ private boolean modal;
-/**
- * Initializes a new instance of <code>Dialog</code> with the specified,
- * parent, title, modality and <code>GraphicsConfiguration</code>,
- * that is resizable.
- *
- * @exception IllegalArgumentException If parent is null, the
- * GraphicsConfiguration is not a screen device or
- * GraphicsEnvironment.isHeadless() returns true.
- *
- * @since 1.4
- */
-public
-Dialog (Dialog parent, String title, boolean modal, GraphicsConfiguration gc)
-{
- super (parent, parent.getGraphicsConfiguration ());
+ /**
+ * @serial Indicates whether or not this dialog box is resizable.
+ */
+ private boolean resizable = true;
- // A null title is equivalent to an empty title
- this.title = (title != null) ? title : "";
- this.modal = modal;
- visible = false;
+ /**
+ * @serial The title string for this dialog box, which can be
+ * <code>null</code>.
+ */
+ private String title;
- setLayout (new BorderLayout ());
-}
+ /**
+ * This field indicates whether the dialog is undecorated or not.
+ */
+ private boolean undecorated = false;
-/*************************************************************************/
+ /**
+ * Indicates that we are blocked for modality in show
+ */
+ private boolean blocked = false;
-/*
- * Instance Variables
- */
+ /**
+ * Secondary EventQueue to handle AWT events while we are blocked for
+ * modality in show.
+ */
+ private EventQueue eq2 = null;
-/**
- * Returns the title of this dialog box.
- *
- * @return The title of this dialog box.
- */
-public String
-getTitle()
-{
- return(title);
-}
+ /**
+ * Initializes a new instance of <code>Dialog</code> with the specified
+ * parent, that is resizable and not modal, and which has no title.
+ *
+ * @param parent The parent frame of this dialog box.
+ * @exception IllegalArgumentException If the owner's GraphicsConfiguration
+ * is not from a screen device, or if owner is null. This exception is
+ * always thrown when GraphicsEnvironment.isHeadless() returns true.
+ */
+ public Dialog(Frame parent)
+ {
+ this(parent, "", false);
+ }
-/*************************************************************************/
+ /**
+ * Initializes a new instance of <code>Dialog</code> with the specified
+ * parent and modality, that is resizable and which has no title.
+ *
+ * @param parent The parent frame of this dialog box.
+ * @param modal <code>true</code> if this dialog box is modal,
+ * <code>false</code> otherwise.
+ *
+ * @exception IllegalArgumentException If the owner's GraphicsConfiguration
+ * is not from a screen device, or if owner is null. This exception is
+ * always thrown when GraphicsEnvironment.isHeadless() returns true.
+ */
+ public Dialog(Frame parent, boolean modal)
+ {
+ this(parent, "", modal);
+ }
-/**
- * Sets the title of this dialog box to the specified string.
- *
- * @param title The new title.
- */
-public synchronized void
-setTitle(String title)
-{
- // A null title is equivalent to an empty title
- this.title = (title != null) ? title : "";
+ /**
+ * Initializes a new instance of <code>Dialog</code> with the specified
+ * parent, that is resizable and not modal, and which has the specified
+ * title.
+ *
+ * @param parent The parent frame of this dialog box.
+ * @param title The title string for this dialog box.
+ *
+ * @exception IllegalArgumentException If the owner's GraphicsConfiguration
+ * is not from a screen device, or if owner is null. This exceptionnis
+ * always thrown when GraphicsEnvironment.isHeadless() returns true.
+ */
+ public Dialog(Frame parent, String title)
+ {
+ this(parent, title, false);
+ }
- if (peer != null)
- {
- DialogPeer d = (DialogPeer) peer;
- d.setTitle (title);
- }
-}
+ /**
+ * Initializes a new instance of <code>Dialog</code> with the specified,
+ * parent, title, and modality, that is resizable.
+ *
+ * @param parent The parent frame of this dialog box.
+ * @param title The title string for this dialog box.
+ * @param modal <code>true</code> if this dialog box is modal,
+ * <code>false</code> otherwise.
+ *
+ * @exception IllegalArgumentException If owner is null or
+ * GraphicsEnvironment.isHeadless() returns true.
+ */
+ public Dialog(Frame parent, String title, boolean modal)
+ {
+ this(parent, title, modal, parent.getGraphicsConfiguration());
+ }
-/*************************************************************************/
+ /**
+ * Initializes a new instance of <code>Dialog</code> with the specified,
+ * parent, title, modality and <code>GraphicsConfiguration</code>, that is
+ * resizable.
+ *
+ * @param parent The parent frame of this dialog box.
+ * @param title The title string for this dialog box.
+ * @param modal <code>true</code> if this dialog box is modal,
+ * <code>false</code> otherwise.
+ * @param gc The <code>GraphicsConfiguration</code> object to use. If
+ * <code>null</code> the <code>GraphicsConfiguration</code> of the target
+ * frame is used.
+ *
+ * @exception IllegalArgumentException If owner is null, the
+ * GraphicsConfiguration is not a screen device or
+ * GraphicsEnvironment.isHeadless() returns true.
+ * @since 1.4
+ */
+ public Dialog(Frame parent, String title, boolean modal,
+ GraphicsConfiguration gc)
+ {
+ super(parent, (gc == null) ? parent.getGraphicsConfiguration() : gc);
-/**
- * Tests whether or not this dialog box is modal.
- *
- * @return <code>true</code> if this dialog box is modal,
- * <code>false</code> otherwise.
- */
-public boolean
-isModal()
-{
- return(modal);
-}
+ // A null title is equivalent to an empty title
+ this.title = (title != null) ? title : "";
+ this.modal = modal;
+ visible = false;
-/*************************************************************************/
+ setLayout(new BorderLayout());
+ }
-/**
- * Changes the modality of this dialog box. This can only be done before
- * the peer is created.
- *
- * @param modal <code>true</code> to make this dialog box modal,
- * <code>false</code> to make it non-modal.
- */
-public void
-setModal(boolean modal)
-{
- this.modal = modal;
-}
+ /**
+ * Initializes a new instance of <code>Dialog</code> with the specified,
+ * parent, that is resizable.
+ *
+ * @param owner The parent frame of this dialog box.
+ *
+ * @exception IllegalArgumentException If parent is null. This exception is
+ * always thrown when GraphicsEnvironment.isHeadless() returns true.
+ *
+ * @since 1.2
+ */
+ public Dialog(Dialog owner)
+ {
+ this(owner, "", false, owner.getGraphicsConfiguration());
+ }
-/*************************************************************************/
+ /**
+ * Initializes a new instance of <code>Dialog</code> with the specified,
+ * parent and title, that is resizable.
+ *
+ * @param owner The parent frame of this dialog box.
+ * @param title The title string for this dialog box.
+ *
+ * @exception IllegalArgumentException If parent is null. This exception is
+ * always thrown when GraphicsEnvironment.isHeadless() returns
+ * true.
+ * @since 1.2
+ */
+ public Dialog(Dialog owner, String title)
+ {
+ this(owner, title, false, owner.getGraphicsConfiguration());
+ }
-/**
- * Tests whether or not this dialog box is resizable.
- *
- * @return <code>true</code> if this dialog is resizable, <code>false</code>,
- * otherwise.
- */
-public boolean
-isResizable()
-{
- return(resizable);
-}
+ /**
+ * Initializes a new instance of <code>Dialog</code> with the specified,
+ * parent, title and modality, that is resizable.
+ *
+ * @param owner The parent frame of this dialog box.
+ * @param title The title string for this dialog box.
+ * @param modal <code>true</code> if this dialog box is modal,
+ * <code>false</code> otherwise.
+ *
+ * @exception IllegalArgumentException If parent is null. This exception is
+ * always thrown when GraphicsEnvironment.isHeadless() returns true.
+ * @since 1.2
+ */
+ public Dialog(Dialog owner, String title, boolean modal)
+ {
+ this(owner, title, modal, owner.getGraphicsConfiguration());
+ }
-/*************************************************************************/
+ /**
+ * Initializes a new instance of <code>Dialog</code> with the specified,
+ * parent, title, modality and <code>GraphicsConfiguration</code>, that is
+ * resizable.
+ *
+ * @param parent The parent frame of this dialog box.
+ * @param title The title string for this dialog box.
+ * @param modal <code>true</code> if this dialog box is modal,
+ * <code>false</code> otherwise.
+ * @param gc The <code>GraphicsConfiguration</code> object to use. If
+ * <code>null</code> the <code>GraphicsConfiguration</code> of the target
+ * frame is used.
+ *
+ * @exception IllegalArgumentException If parent is null, the
+ * GraphicsConfiguration is not a screen device or
+ * GraphicsEnvironment.isHeadless() returns true.
+ *
+ * @since 1.4
+ */
+ public Dialog(Dialog parent, String title, boolean modal,
+ GraphicsConfiguration gc)
+ {
+ super(parent, (gc == null) ? parent.getGraphicsConfiguration() : gc);
-/**
- * Changes the resizability of this dialog box.
- *
- * @param resizable <code>true</code> to make this dialog resizable,
- * <code>false</code> to make it non-resizable.
- */
-public synchronized void
-setResizable(boolean resizable)
-{
- this.resizable = resizable;
- if (peer != null)
- {
- DialogPeer d = (DialogPeer) peer;
- d.setResizable (resizable);
- }
-}
+ // A null title is equivalent to an empty title
+ this.title = (title != null) ? title : "";
+ this.modal = modal;
+ visible = false;
-/*************************************************************************/
+ setLayout(new BorderLayout());
+ }
-/**
- * Creates this object's native peer.
- */
-public synchronized void
-addNotify()
-{
- if (peer == null)
- peer = getToolkit ().createDialog (this);
- super.addNotify ();
-}
+ /**
+ * Returns the title of this dialog box.
+ *
+ * @return The title of this dialog box.
+ */
+ public String getTitle()
+ {
+ return title;
+ }
-/*************************************************************************/
+ /**
+ * Sets the title of this dialog box to the specified string.
+ *
+ * @param title the new title. If <code>null</code> an empty
+ * title will be set.
+ */
+ public synchronized void setTitle(String title)
+ {
+ // A null title is equivalent to an empty title
+ this.title = (title != null) ? title : "";
+
+ if (peer != null)
+ {
+ DialogPeer d = (DialogPeer) peer;
+ d.setTitle(title);
+ }
+ }
-/**
- * Makes this dialog visible and brings it to the front.
- * If the dialog is modal and is not already visible, this call will not
- * return until the dialog is hidden by someone calling hide or dispose.
- * If this is the event dispatching thread we must ensure that another event
- * thread runs while the one which invoked this method is blocked.
- */
-public synchronized void
-show()
-{
- super.show();
-
- if (isModal())
- {
- // If already shown (and blocked) just return
- if (blocked)
- return;
-
- /* If show is called in the dispatch thread for a modal dialog it will
- block so we must run another thread so the events keep being
- dispatched.*/
- if (EventQueue.isDispatchThread ())
- {
- EventQueue eq = Toolkit.getDefaultToolkit().getSystemEventQueue();
- eq2 = new EventQueue ();
- eq.push (eq2);
- }
-
- try
- {
- blocked = true;
- wait ();
- blocked = false;
- }
- catch (InterruptedException e)
- {
- blocked = false;
- }
-
- if (eq2 != null)
- {
- eq2.pop ();
- eq2 = null;
- }
- }
-}
+ /**
+ * Tests whether or not this dialog box is modal.
+ *
+ * @return <code>true</code> if this dialog box is modal, <code>false</code>
+ * otherwise.
+ */
+ public boolean isModal()
+ {
+ return modal;
+ }
-/*************************************************************************/
+ /**
+ * Changes the modality of this dialog box. This can only be done before the
+ * peer is created.
+ *
+ * @param modal <code>true</code> to make this dialog box modal,
+ * <code>false</code> to make it non-modal.
+ */
+ public void setModal(boolean modal)
+ {
+ this.modal = modal;
+ }
-/**
- * Hides the Dialog and then
- * causes show() to return if it is currently blocked.
- */
+ /**
+ * Tests whether or not this dialog box is resizable.
+ *
+ * @return <code>true</code> if this dialog is resizable,
+ * <code>false</code> otherwise.
+ */
+ public boolean isResizable()
+ {
+ return resizable;
+ }
-public synchronized void
-hide ()
-{
- if (blocked)
- {
- notifyAll ();
- }
+ /**
+ * Changes the resizability of this dialog box.
+ *
+ * @param resizable <code>true</code> to make this dialog resizable,
+ * <code>false</code> to make it non-resizable.
+ */
+ public synchronized void setResizable(boolean resizable)
+ {
+ this.resizable = resizable;
+ if (peer != null)
+ {
+ DialogPeer d = (DialogPeer) peer;
+ d.setResizable(resizable);
+ }
+ }
- super.hide();
-}
+ /**
+ * Creates this object's native peer.
+ */
+ public synchronized void addNotify()
+ {
+ if (peer == null)
+ peer = getToolkit().createDialog(this);
+ super.addNotify();
+ }
-/*************************************************************************/
+ /**
+ * Makes this dialog visible and brings it to the front. If the dialog is
+ * modal and is not already visible, this call will not return until the
+ * dialog is hidden by someone calling hide or dispose. If this is the event
+ * dispatching thread we must ensure that another event thread runs while the
+ * one which invoked this method is blocked.
+ *
+ * @deprecated Use {@link Component#setVisible(boolean)} instead.
+ */
+ public synchronized void show()
+ {
+ super.show();
+
+ if (isModal())
+ {
+ // If already shown (and blocked) just return
+ if (blocked)
+ return;
+
+ /*
+ * If show is called in the dispatch thread for a modal dialog it will
+ * block so we must run another thread so the events keep being
+ * dispatched.
+ */
+ if (EventQueue.isDispatchThread())
+ {
+ EventQueue eq = Toolkit.getDefaultToolkit().getSystemEventQueue();
+ eq2 = new EventQueue();
+ eq.push(eq2);
+ }
+
+ try
+ {
+ blocked = true;
+ wait();
+ blocked = false;
+ }
+ catch (InterruptedException e)
+ {
+ blocked = false;
+ }
+
+ if (eq2 != null)
+ {
+ eq2.pop();
+ eq2 = null;
+ }
+ }
+ }
-/**
- * Disposes the Dialog and then causes show() to return
- * if it is currently blocked.
- */
+ /**
+ * Hides the Dialog and then causes show() to return if it is currently
+ * blocked.
+ *
+ * @deprecated Use {@link Component#setVisible(boolean)} instead.
+ */
+ public synchronized void hide()
+ {
+ if (blocked)
+ {
+ notifyAll();
+ }
-public synchronized void
-dispose ()
-{
- if (blocked)
- {
- notifyAll ();
- }
+ super.hide();
+ }
- super.dispose();
-}
+ /**
+ * Disposes the Dialog and then causes show() to return if it is currently
+ * blocked.
+ */
+ public synchronized void dispose()
+ {
+ if (blocked)
+ {
+ notifyAll();
+ }
-/*************************************************************************/
+ super.dispose();
+ }
-/**
- * Returns a debugging string for this component.
- *
- * @return A debugging string for this component.
- */
-protected String
-paramString()
-{
- return ("title+" + title + ",modal=" + modal +
- ",resizable=" + resizable + "," + super.paramString());
-}
+ /**
+ * Returns a debugging string for this component.
+ *
+ * @return A debugging string for this component.
+ */
+ protected String paramString()
+ {
+ return "title+" + title + ",modal=" + modal + ",resizable=" + resizable
+ + "," + super.paramString();
+ }
/**
* Returns whether this frame is undecorated or not.
*
+ * @return <code>true</code> if this dialog is undecorated,
+ * <code>false</code> otherwise.
+ *
* @since 1.4
*/
- public boolean isUndecorated ()
+ public boolean isUndecorated()
{
return undecorated;
}
@@ -505,28 +471,42 @@ paramString()
* Disables or enables decorations for this frame. This method can only be
* called while the frame is not displayable.
*
- * @exception IllegalComponentStateException If this frame is displayable.
+ * @param undecorated <code>true</code> to disable dialog decorations,
+ * <code>false</code> otherwise.
*
+ * @exception IllegalComponentStateException If this frame is displayable.
* @since 1.4
*/
- public void setUndecorated (boolean undecorated)
+ public void setUndecorated(boolean undecorated)
{
- if (isDisplayable ())
- throw new IllegalComponentStateException ();
+ if (isDisplayable())
+ throw new IllegalComponentStateException();
this.undecorated = undecorated;
}
-
- protected class AccessibleAWTDialog extends AccessibleAWTWindow
+
+ /**
+ * Accessibility support for <code>Dialog</code>.
+ */
+ protected class AccessibleAWTDialog
+ extends AccessibleAWTWindow
{
private static final long serialVersionUID = 4837230331833941201L;
+ /**
+ * Gets the role of this object.
+ * @return AccessibleRole.DIALOG
+ */
public AccessibleRole getAccessibleRole()
{
return AccessibleRole.DIALOG;
}
-
- public AccessibleStateSet getAccessibleState()
+
+ /**
+ * Gets the state set of this object.
+ * @return The current state of this dialog.
+ */
+ public AccessibleStateSet getAccessibleStateSet()
{
AccessibleStateSet states = super.getAccessibleStateSet();
if (isResizable())
@@ -536,11 +516,11 @@ paramString()
return states;
}
}
-
+
/**
- * Gets the AccessibleContext associated with this <code>Dialog</code>.
- * The context is created, if necessary.
- *
+ * Gets the AccessibleContext associated with this <code>Dialog</code>. The
+ * context is created, if necessary.
+ *
* @return the associated context
*/
public AccessibleContext getAccessibleContext()
@@ -551,5 +531,4 @@ paramString()
return accessibleContext;
}
-} // class Dialog
-
+}
diff --git a/libjava/classpath/java/awt/Frame.java b/libjava/classpath/java/awt/Frame.java
index 7003dac91fb..542013671aa 100644
--- a/libjava/classpath/java/awt/Frame.java
+++ b/libjava/classpath/java/awt/Frame.java
@@ -614,16 +614,27 @@ public class Frame extends Window implements MenuContainer
return next_frame_number++;
}
+ /**
+ * Accessibility support for <code>Frame</code>.
+ */
protected class AccessibleAWTFrame extends AccessibleAWTWindow
{
private static final long serialVersionUID = -6172960752956030250L;
+ /**
+ * Gets the role of this object.
+ * @return AccessibleRole.FRAME
+ */
public AccessibleRole getAccessibleRole()
{
return AccessibleRole.FRAME;
}
- public AccessibleStateSet getAccessibleState()
+ /**
+ * Gets the state set of this object.
+ * @return The current state of this frame.
+ */
+ public AccessibleStateSet getAccessibleStateSet()
{
AccessibleStateSet states = super.getAccessibleStateSet();
if (isResizable())
diff --git a/libjava/classpath/java/awt/GraphicsConfiguration.java b/libjava/classpath/java/awt/GraphicsConfiguration.java
index 1526ad3cfc0..f68a1e6ba4f 100644
--- a/libjava/classpath/java/awt/GraphicsConfiguration.java
+++ b/libjava/classpath/java/awt/GraphicsConfiguration.java
@@ -38,6 +38,8 @@ exception statement from your version. */
package java.awt;
+import gnu.classpath.NotImplementedException;
+
import java.awt.geom.AffineTransform;
import java.awt.image.BufferedImage;
import java.awt.image.ColorModel;
@@ -216,6 +218,7 @@ public abstract class GraphicsConfiguration
* @since 1.4
*/
public BufferCapabilities getBufferCapabilities()
+ throws NotImplementedException
{
throw new Error("not implemented");
}
@@ -227,6 +230,7 @@ public abstract class GraphicsConfiguration
* @since 1.4
*/
public ImageCapabilities getImageCapabilities()
+ throws NotImplementedException
{
throw new Error("not implemented");
}
diff --git a/libjava/classpath/java/awt/GridBagLayout.java b/libjava/classpath/java/awt/GridBagLayout.java
index 714e080d7b2..f827d21ca6a 100644
--- a/libjava/classpath/java/awt/GridBagLayout.java
+++ b/libjava/classpath/java/awt/GridBagLayout.java
@@ -38,6 +38,8 @@ exception statement from your version. */
package java.awt;
+import gnu.classpath.NotImplementedException;
+
import java.io.Serializable;
import java.util.ArrayList;
import java.util.HashMap;
@@ -323,6 +325,7 @@ public class GridBagLayout
* Obsolete.
*/
protected void AdjustForGravity (GridBagConstraints gbc, Rectangle rect)
+ throws NotImplementedException
{
// FIXME
throw new Error ("Not implemented");
@@ -349,107 +352,121 @@ public class GridBagLayout
// be invalidated, clearing the layout information cache,
// layoutInfo. So we wait until after this for loop to set
// layoutInfo.
- for(int i = 0; i < components.length; i++)
- {
- Component component = components [i];
-
- // If component is not visible we dont have to care about it.
- if (!component.isVisible())
- continue;
-
- GridBagConstraints constraints =
- lookupInternalConstraints(component);
-
- int cellx = sumIntArray(info.colWidths, constraints.gridx);
- int celly = sumIntArray(info.rowHeights, constraints.gridy);
- int cellw = sumIntArray(info.colWidths,
- constraints.gridx + constraints.gridwidth) - cellx;
- int cellh = sumIntArray(info.rowHeights,
- constraints.gridy + constraints.gridheight) - celly;
-
- Insets insets = constraints.insets;
- if (insets != null)
- {
- cellx += insets.left;
- celly += insets.top;
- cellw -= insets.left + insets.right;
- cellh -= insets.top + insets.bottom;
- }
-
- Dimension dim = component.getPreferredSize();
-
- // Note: Documentation says that padding is added on both sides, but
- // visual inspection shows that the Sun implementation only adds it
- // once, so we do the same.
- dim.width += constraints.ipadx;
- dim.height += constraints.ipady;
-
- switch(constraints.fill)
- {
- case GridBagConstraints.HORIZONTAL:
- dim.width = cellw;
- break;
- case GridBagConstraints.VERTICAL:
- dim.height = cellh;
- break;
- case GridBagConstraints.BOTH:
- dim.width = cellw;
- dim.height = cellh;
- break;
- }
-
- int x;
- int y;
-
- switch(constraints.anchor)
- {
- case GridBagConstraints.NORTH:
- x = cellx + (cellw - dim.width) / 2;
- y = celly;
- break;
- case GridBagConstraints.SOUTH:
- x = cellx + (cellw - dim.width) / 2;
- y = celly + cellh - dim.height;
- break;
- case GridBagConstraints.WEST:
- x = cellx;
- y = celly + (cellh - dim.height) / 2;
- break;
- case GridBagConstraints.EAST:
- x = cellx + cellw - dim.width;
- y = celly + (cellh - dim.height) / 2;
- break;
- case GridBagConstraints.NORTHEAST:
- x = cellx + cellw - dim.width;
- y = celly;
- break;
- case GridBagConstraints.NORTHWEST:
- x = cellx;
- y = celly;
- break;
- case GridBagConstraints.SOUTHEAST:
- x = cellx + cellw - dim.width;
- y = celly + cellh - dim.height;
- break;
- case GridBagConstraints.SOUTHWEST:
- x = cellx;
- y = celly + cellh - dim.height;
- break;
- default:
- x = cellx + (cellw - dim.width) / 2;
- y = celly + (cellh - dim.height) / 2;
- break;
- }
-
- component.setBounds(info.pos_x + x, info.pos_y + y, dim.width, dim.height);
- }
-
- // DEBUG
- //dumpLayoutInfo (info);
-
- // Cache layout information.
- layoutInfo = getLayoutInfo (parent, PREFERREDSIZE);
- }
+ Component lastComp = null;
+ int cellx = 0;
+ int celly = 0;
+ int cellw = 0;
+ int cellh = 0;
+ for (int i = 0; i < components.length; i++)
+ {
+ Component component = components[i];
+
+ // If component is not visible we dont have to care about it.
+ if (! component.isVisible())
+ continue;
+
+ Dimension dim = component.getPreferredSize();
+ GridBagConstraints constraints = lookupInternalConstraints(component);
+
+ if (lastComp != null
+ && constraints.gridheight == GridBagConstraints.REMAINDER)
+ celly += cellh;
+ else
+ celly = sumIntArray(info.rowHeights, constraints.gridy);
+
+ if (lastComp != null
+ && constraints.gridwidth == GridBagConstraints.REMAINDER)
+ cellx += cellw;
+ else
+ cellx = sumIntArray(info.colWidths, constraints.gridx);
+
+ cellw = sumIntArray(info.colWidths, constraints.gridx
+ + constraints.gridwidth) - cellx;
+ cellh = sumIntArray(info.rowHeights, constraints.gridy
+ + constraints.gridheight) - celly;
+
+ Insets insets = constraints.insets;
+ if (insets != null)
+ {
+ cellx += insets.left;
+ celly += insets.top;
+ cellw -= insets.left + insets.right;
+ cellh -= insets.top + insets.bottom;
+ }
+
+ // Note: Documentation says that padding is added on both sides, but
+ // visual inspection shows that the Sun implementation only adds it
+ // once, so we do the same.
+ dim.width += constraints.ipadx;
+ dim.height += constraints.ipady;
+
+ switch (constraints.fill)
+ {
+ case GridBagConstraints.HORIZONTAL:
+ dim.width = cellw;
+ break;
+ case GridBagConstraints.VERTICAL:
+ dim.height = cellh;
+ break;
+ case GridBagConstraints.BOTH:
+ dim.width = cellw;
+ dim.height = cellh;
+ break;
+ }
+
+ int x = 0;
+ int y = 0;
+
+ switch (constraints.anchor)
+ {
+ case GridBagConstraints.NORTH:
+ x = cellx + (cellw - dim.width) / 2;
+ y = celly;
+ break;
+ case GridBagConstraints.SOUTH:
+ x = cellx + (cellw - dim.width) / 2;
+ y = celly + cellh - dim.height;
+ break;
+ case GridBagConstraints.WEST:
+ x = cellx;
+ y = celly + (cellh - dim.height) / 2;
+ break;
+ case GridBagConstraints.EAST:
+ x = cellx + cellw - dim.width;
+ y = celly + (cellh - dim.height) / 2;
+ break;
+ case GridBagConstraints.NORTHEAST:
+ x = cellx + cellw - dim.width;
+ y = celly;
+ break;
+ case GridBagConstraints.NORTHWEST:
+ x = cellx;
+ y = celly;
+ break;
+ case GridBagConstraints.SOUTHEAST:
+ x = cellx + cellw - dim.width;
+ y = celly + cellh - dim.height;
+ break;
+ case GridBagConstraints.SOUTHWEST:
+ x = cellx;
+ y = celly + cellh - dim.height;
+ break;
+ default:
+ x = cellx + (cellw - dim.width) / 2;
+ y = celly + (cellh - dim.height) / 2;
+ break;
+ }
+ component.setBounds(info.pos_x + x, info.pos_y + y, dim.width,
+ dim.height);
+ lastComp = component;
+ }
+
+ // DEBUG
+ //dumpLayoutInfo(info);
+
+ // Cache layout information.
+ layoutInfo = getLayoutInfo(parent, PREFERREDSIZE);
+ }
/**
* Obsolete.
@@ -485,11 +502,10 @@ public class GridBagLayout
for (int i = 0; i < components.length; i++)
{
Component component = components [i];
-
// If component is not visible we dont have to care about it.
if (!component.isVisible())
continue;
-
+
// When looking up the constraint for the first time, check the
// original unmodified constraint. After the first time, always
// refer to the internal modified constraint.
@@ -516,7 +532,6 @@ public class GridBagLayout
//
// nothing to check; just add it
-
// cases 1 and 2
if(constraints.gridx == GridBagConstraints.RELATIVE)
{
@@ -560,7 +575,9 @@ public class GridBagLayout
// this column. We want to add this component below it.
// If this column is empty, add to the 0 position.
if (!lastInCol.containsKey(new Integer(constraints.gridx)))
- y = 0;
+ {
+ y = current_y;
+ }
else
{
Component lastComponent = (Component)lastInCol.get(new Integer(constraints.gridx));
@@ -596,7 +613,7 @@ public class GridBagLayout
// Update our reference points for RELATIVE gridx and gridy.
if(constraints.gridwidth == GridBagConstraints.REMAINDER)
{
- current_y = constraints.gridy + Math.max(1, constraints.gridheight);
+ current_y = constraints.gridy + Math.max(1, constraints.gridheight);
}
else if (constraints.gridwidth != GridBagConstraints.REMAINDER)
{
@@ -788,7 +805,7 @@ public class GridBagLayout
height += constraints.insets.top + constraints.insets.bottom;
height += constraints.ipady;
-
+
distributeSizeAndWeight(height,
constraints.weighty,
constraints.gridy,
@@ -918,7 +935,7 @@ public class GridBagLayout
sizes[start] = Math.max(sizes[start], size);
weights[start] = Math.max(weights[start], weight);
}
- else if (span > 1)
+ else
{
int numOccupied = span;
int lastOccupied = -1;
diff --git a/libjava/classpath/java/awt/Image.java b/libjava/classpath/java/awt/Image.java
index 93c2c479024..6ade302a147 100644
--- a/libjava/classpath/java/awt/Image.java
+++ b/libjava/classpath/java/awt/Image.java
@@ -166,6 +166,8 @@ public abstract class Image
* loading will be produced according to the hints of the algorithm
* requested. If either the width or height is non-positive, it is adjusted
* to preserve the original aspect ratio.
+ * If an illegal value of <code>flags</code> is passed,
+ * the default algorithm is used.
*
* @param width the width of the scaled image
* @param height the height of the scaled image
@@ -183,18 +185,15 @@ public abstract class Image
ImageFilter filter;
switch (flags)
{
- case SCALE_DEFAULT:
- case SCALE_FAST:
- case SCALE_REPLICATE:
- filter = new ReplicateScaleFilter(width, height);
- break;
case SCALE_AREA_AVERAGING:
+ case SCALE_SMOOTH:
filter = new AreaAveragingScaleFilter(width, height);
break;
- case SCALE_SMOOTH:
- throw new Error("SCALE_SMOOTH: not implemented");
+ case SCALE_DEFAULT:
+ case SCALE_FAST:
+ case SCALE_REPLICATE:
default:
- throw new Error("Unknown flag or not implemented: " + flags);
+ filter = new ReplicateScaleFilter(width, height);
}
ImageProducer producer = new FilteredImageSource(getSource(), filter);
diff --git a/libjava/classpath/java/awt/LightweightDispatcher.java b/libjava/classpath/java/awt/LightweightDispatcher.java
index 6573b128ec4..860646402cc 100644
--- a/libjava/classpath/java/awt/LightweightDispatcher.java
+++ b/libjava/classpath/java/awt/LightweightDispatcher.java
@@ -110,14 +110,12 @@ class LightweightDispatcher
*/
public boolean dispatchEvent(AWTEvent event)
{
- boolean dispatched = false;
if (event instanceof MouseEvent && event.getSource() instanceof Window)
{
MouseEvent mouseEvent = (MouseEvent) event;
- handleMouseEvent(mouseEvent);
- dispatched = true;
+ return handleMouseEvent(mouseEvent);
}
- return dispatched;
+ return false;
}
/**
@@ -125,12 +123,14 @@ class LightweightDispatcher
* (Window instances) and dispatches them to the correct lightweight child.
*
* @param ev the mouse event
+ * @return whether or not we found a lightweight that handled the event.
*/
- private void handleMouseEvent(MouseEvent ev)
+ private boolean handleMouseEvent(MouseEvent ev)
{
Window window = (Window) ev.getSource();
Component target = window.findComponentAt(ev.getX(), ev.getY());
- if (target != null && target.isLightweight())
+ target = findTarget(target);
+ if (target == null || target.isLightweight())
{
// Dispatch additional MOUSE_EXITED and MOUSE_ENTERED if event target
// is different from the last event target.
@@ -146,13 +146,16 @@ class LightweightDispatcher
ev.getClickCount(), ev.isPopupTrigger());
lastTarget.dispatchEvent(mouseExited);
}
- Point p = AWTUtilities.convertPoint(window, ev.getX(), ev.getY(),
- target);
- MouseEvent mouseEntered =
- new MouseEvent(target, MouseEvent.MOUSE_ENTERED, ev.getWhen(),
- ev.getModifiers(), p.x, p.y, ev.getClickCount(),
- ev.isPopupTrigger());
- target.dispatchEvent(mouseEntered);
+ if (target != null)
+ {
+ Point p = AWTUtilities.convertPoint(window, ev.getX(), ev.getY(),
+ target);
+ MouseEvent mouseEntered =
+ new MouseEvent(target, MouseEvent.MOUSE_ENTERED, ev.getWhen(),
+ ev.getModifiers(), p.x, p.y, ev.getClickCount(),
+ ev.isPopupTrigger());
+ target.dispatchEvent(mouseEntered);
+ }
}
switch (ev.getID())
@@ -183,18 +186,43 @@ class LightweightDispatcher
lastTarget = target;
- Point targetCoordinates =
- AWTUtilities.convertPoint(window, ev.getX(), ev.getY(), target);
- int dx = targetCoordinates.x - ev.getX();
- int dy = targetCoordinates.y - ev.getY();
- ev.translatePoint(dx, dy);
- ev.setSource(target);
- target.dispatchEvent(ev);
-
- // We reset the event, so that the normal event dispatching is not
- // influenced by this modified event.
- ev.setSource(window);
- ev.translatePoint(-dx, -dy);
+ if (target != null)
+ {
+ Point targetCoordinates =
+ AWTUtilities.convertPoint(window, ev.getX(), ev.getY(), target);
+ int dx = targetCoordinates.x - ev.getX();
+ int dy = targetCoordinates.y - ev.getY();
+ ev.translatePoint(dx, dy);
+ ev.setSource(target);
+ target.dispatchEvent(ev);
+ // We reset the event, so that the normal event dispatching is not
+ // influenced by this modified event.
+ ev.setSource(window);
+ ev.translatePoint(-dx, -dy);
+ }
+
+ return true;
+ }
+ else
+ return false;
+ }
+
+ /**
+ * Finds the actual target for a mouseevent, starting at <code>c</code>.
+ * This searches upwards the component hierarchy until it finds a component
+ * that has a mouselistener attached.
+ *
+ * @param c the component to start searching from
+ *
+ * @return the actual receiver of the mouse event
+ */
+ private Component findTarget(Component c)
+ {
+ Component target = c;
+ while (target != null && target.getMouseListeners().length == 0)
+ {
+ target = target.getParent();
}
+ return target;
}
}
diff --git a/libjava/classpath/java/awt/List.java b/libjava/classpath/java/awt/List.java
index 00636a0224f..b28e2016d2e 100644
--- a/libjava/classpath/java/awt/List.java
+++ b/libjava/classpath/java/awt/List.java
@@ -446,7 +446,7 @@ preferredSize(int rows)
if (peer != null)
return peer.preferredSize (rows);
else
- return new Dimension (0, 0);
+ return getSize();
}
/*************************************************************************/
diff --git a/libjava/classpath/java/awt/MediaTracker.java b/libjava/classpath/java/awt/MediaTracker.java
index 9abfde6efc2..8792e1d233d 100644
--- a/libjava/classpath/java/awt/MediaTracker.java
+++ b/libjava/classpath/java/awt/MediaTracker.java
@@ -634,7 +634,8 @@ public class MediaTracker implements java.io.Serializable
else
prev.next = e.next;
}
- prev = e;
+ else
+ prev = e;
e = e.next;
}
}
diff --git a/libjava/classpath/java/awt/MenuItem.java b/libjava/classpath/java/awt/MenuItem.java
index 3e39d118a05..a7ac79643be 100644
--- a/libjava/classpath/java/awt/MenuItem.java
+++ b/libjava/classpath/java/awt/MenuItem.java
@@ -111,7 +111,7 @@ private transient ActionListener action_listeners;
private static final long serialVersionUID = -217847831945965825L;
/** Constructor */
- public AccessibleAWTMenuItem()
+ protected AccessibleAWTMenuItem()
{
super();
}
diff --git a/libjava/classpath/java/awt/ScrollPaneAdjustable.java b/libjava/classpath/java/awt/ScrollPaneAdjustable.java
index bec5b5106de..21b58c36ede 100644
--- a/libjava/classpath/java/awt/ScrollPaneAdjustable.java
+++ b/libjava/classpath/java/awt/ScrollPaneAdjustable.java
@@ -178,7 +178,16 @@ public class ScrollPaneAdjustable
public String paramString ()
{
- throw new Error ("not implemented");
+ return ("scrollpane=" + sp + ", orientation=" + orientation
+ + ", value=" + value + ", minimum=" + minimum
+ + ", maximum=" + maximum + ", visibleAmount=" + visibleAmount
+ + ", unitIncrement=" + unitIncrement
+ + ", blockIncrement=" + blockIncrement);
+ }
+
+ public String toString()
+ {
+ return getClass().getName() + "[" + paramString() + "]";
}
/**
diff --git a/libjava/classpath/java/awt/TexturePaint.java b/libjava/classpath/java/awt/TexturePaint.java
index a12e38463f1..57d7574c3d4 100644
--- a/libjava/classpath/java/awt/TexturePaint.java
+++ b/libjava/classpath/java/awt/TexturePaint.java
@@ -38,6 +38,8 @@ exception statement from your version. */
package java.awt;
+import gnu.classpath.NotImplementedException;
+
import java.awt.geom.AffineTransform;
import java.awt.geom.Rectangle2D;
import java.awt.image.BufferedImage;
@@ -65,10 +67,12 @@ public class TexturePaint implements Paint
Rectangle2D userBounds,
AffineTransform xform,
RenderingHints hints)
+ throws NotImplementedException
{
throw new Error("not implemented");
}
public int getTransparency()
+ throws NotImplementedException
{
throw new Error("not implemented");
}
diff --git a/libjava/classpath/java/awt/Toolkit.java b/libjava/classpath/java/awt/Toolkit.java
index e2a4bc92ea7..16f1caf85df 100644
--- a/libjava/classpath/java/awt/Toolkit.java
+++ b/libjava/classpath/java/awt/Toolkit.java
@@ -1,5 +1,5 @@
/* Toolkit.java -- AWT Toolkit superclass
- Copyright (C) 1999, 2000, 2001, 2002, 2003, 2004, 2005
+ Copyright (C) 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006
Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -39,6 +39,7 @@ exception statement from your version. */
package java.awt;
+import gnu.classpath.SystemProperties;
import gnu.java.awt.peer.GLightweightPeer;
import java.awt.datatransfer.Clipboard;
@@ -78,10 +79,15 @@ import java.awt.peer.TextFieldPeer;
import java.awt.peer.WindowPeer;
import java.beans.PropertyChangeListener;
import java.beans.PropertyChangeSupport;
+import java.io.File;
+import java.io.FileInputStream;
import java.net.URL;
+import java.security.AccessController;
+import java.security.PrivilegedAction;
import java.util.ArrayList;
import java.util.Map;
import java.util.Properties;
+import java.util.StringTokenizer;
/**
* The AWT system uses a set of native peer objects to implement its
@@ -525,16 +531,27 @@ public abstract class Toolkit
{
if (toolkit != null)
return toolkit;
- String toolkit_name = System.getProperty("awt.toolkit",
- default_toolkit_name);
+ String toolkit_name = SystemProperties.getProperty("awt.toolkit",
+ default_toolkit_name);
try
{
- Class cls = Class.forName(toolkit_name);
+ ClassLoader cl;
+ cl = (ClassLoader) AccessController.doPrivileged
+ (new PrivilegedAction()
+ {
+ public Object run()
+ {
+ return ClassLoader.getSystemClassLoader();
+ }
+ });
+ Class cls = cl.loadClass(toolkit_name);
Object obj = cls.newInstance();
if (!(obj instanceof Toolkit))
throw new AWTError(toolkit_name + " is not a subclass of " +
"java.awt.Toolkit");
toolkit = (Toolkit) obj;
+
+ initAccessibility();
return toolkit;
}
catch (ThreadDeath death)
@@ -696,9 +713,18 @@ public abstract class Toolkit
public abstract Clipboard getSystemClipboard();
/**
- * Gets the singleton instance of the system selection as a Clipboard object.
+ * Gets the singleton instance of the system selection as a
+ * Clipboard object. The system selection contains the selected text
+ * of the last component/widget that had focus and a text selection.
+ * The default implementation returns null.
*
- * @exception HeadlessException If GraphicsEnvironment.isHeadless() is true.
+ * @return The Clipboard holding the system (text) selection or null
+ * if the Toolkit or system doesn't support a selection clipboard.
+ *
+ * @exception HeadlessException If GraphicsEnvironment.isHeadless()
+ * is true.
+ * @exception SecurityException If the current security manager
+ * checkSystemClipboardAccess() doesn't allow access.
*
* @since 1.4
*/
@@ -1206,4 +1232,138 @@ public abstract class Toolkit
* @since 1.3
*/
public abstract Map mapInputMethodHighlight(InputMethodHighlight highlight);
+
+ /**
+ * Initializes the accessibility framework. In particular, this loads the
+ * properties javax.accessibility.screen_magnifier_present and
+ * javax.accessibility.screen_reader_present and loads
+ * the classes specified in javax.accessibility.assistive_technologies.
+ */
+ private static void initAccessibility()
+ {
+ AccessController.doPrivileged
+ (new PrivilegedAction()
+ {
+ public Object run()
+ {
+ Properties props = new Properties();
+ String sep = File.separator;
+
+ // Try the user configuration.
+ try
+ {
+ File propsFile = new File(System.getProperty("user.home") + sep
+ + ".accessibility.properties");
+ FileInputStream in = new FileInputStream(propsFile);
+ props.load(in);
+ in.close();
+ }
+ catch (Exception ex)
+ {
+ // User configuration not present, ignore.
+ }
+
+ // Try the system configuration if there was no user configuration.
+ if (props.size() == 0)
+ {
+ try
+ {
+ File propsFile =
+ new File(System.getProperty("gnu.classpath.home.url")
+ + sep + "accessibility.properties");
+ FileInputStream in = new FileInputStream(propsFile);
+ props.load(in);
+ in.close();
+ }
+ catch (Exception ex)
+ {
+ // System configuration not present, ignore.
+ }
+ }
+
+ // Fetch the screen_magnifier_present property. Check systen properties
+ // first, then fallback to the configuration file.
+ String magPresent = SystemProperties.getProperty
+ ("javax.accessibility.screen_magnifier_present");
+ if (magPresent == null)
+ {
+ magPresent = props.getProperty("screen_magnifier_present");
+ if (magPresent != null)
+ {
+ SystemProperties.setProperty
+ ("javax.accessibility.screen_magnifier_present", magPresent);
+ }
+ }
+
+ // Fetch the screen_reader_present property. Check systen properties
+ // first, then fallback to the configuration file.
+ String readerPresent = SystemProperties.getProperty
+ ("javax.accessibility.screen_reader_present");
+ if (readerPresent == null)
+ {
+ readerPresent = props.getProperty("screen_reader_present");
+ if (readerPresent != null)
+ {
+ SystemProperties.setProperty
+ ("javax.accessibility.screen_reader_present", readerPresent);
+ }
+ }
+
+ // Fetch the list of classes to be loaded.
+ String classes = SystemProperties.getProperty
+ ("javax.accessibility.assistive_technologies");
+ if (classes == null)
+ {
+ classes = props.getProperty("assistive_technologies");
+ if (classes != null)
+ {
+ SystemProperties.setProperty
+ ("javax.accessibility.assistive_technologies", classes);
+ }
+ }
+
+ // Try to load the assisitive_technologies classes.
+ if (classes != null)
+ {
+ ClassLoader cl = ClassLoader.getSystemClassLoader();
+ StringTokenizer tokenizer = new StringTokenizer(classes, ",");
+ while (tokenizer.hasMoreTokens())
+ {
+ String className = tokenizer.nextToken();
+ try
+ {
+ Class atClass = cl.loadClass(className);
+ atClass.newInstance();
+ }
+ catch (ClassNotFoundException ex)
+ {
+ AWTError err = new AWTError("Assistive Technology class not"
+ + " found: " + className);
+ err.initCause(ex);
+ throw err;
+ }
+ catch (InstantiationException ex)
+ {
+ AWTError err =
+ new AWTError("Assistive Technology class cannot be "
+ + "instantiated: " + className);
+ err.initCause(ex);
+ throw err;
+ }
+ catch (IllegalAccessException ex)
+ {
+ AWTError err =
+ new AWTError("Assistive Technology class cannot be "
+ + "accessed: " + className);
+ err.initCause(err);
+ throw err;
+ }
+ }
+ }
+ return null;
+ }
+ });
+
+ }
+
} // class Toolkit
diff --git a/libjava/classpath/java/awt/Window.java b/libjava/classpath/java/awt/Window.java
index 71a8d388b30..d9e90c0ea4f 100644
--- a/libjava/classpath/java/awt/Window.java
+++ b/libjava/classpath/java/awt/Window.java
@@ -1,5 +1,5 @@
/* Window.java --
- Copyright (C) 1999, 2000, 2002, 2003, 2004 Free Software Foundation
+ Copyright (C) 1999, 2000, 2002, 2003, 2004, 2006 Free Software Foundation
This file is part of GNU Classpath.
@@ -38,6 +38,8 @@ exception statement from your version. */
package java.awt;
+import gnu.classpath.NotImplementedException;
+
import java.awt.event.ComponentEvent;
import java.awt.event.FocusEvent;
import java.awt.event.WindowAdapter;
@@ -620,10 +622,25 @@ public class Window extends Container implements Accessible
|| windowStateListener != null
|| (eventMask & AWTEvent.WINDOW_EVENT_MASK) != 0))
processEvent(e);
- else if (e.id == ComponentEvent.COMPONENT_RESIZED)
- validate ();
- else
- super.dispatchEventImpl(e);
+ else
+ {
+ if (peer != null && (e.id == ComponentEvent.COMPONENT_RESIZED
+ || e.id == ComponentEvent.COMPONENT_MOVED))
+ {
+ Rectangle bounds = peer.getBounds();
+ x = bounds.x;
+ y = bounds.y;
+ height = bounds.height;
+ width = bounds.width;
+
+ if (e.id == ComponentEvent.COMPONENT_RESIZED)
+ {
+ invalidate();
+ validate();
+ }
+ }
+ super.dispatchEventImpl(e);
+ }
}
/**
@@ -1032,6 +1049,7 @@ public class Window extends Container implements Accessible
* @deprecated
*/
public void applyResourceBundle(ResourceBundle rb)
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
@@ -1143,6 +1161,47 @@ public class Window extends Container implements Accessible
{
this.focusableWindowState = focusableWindowState;
}
+
+ /**
+ * Check whether this Container is a focus cycle root.
+ * Returns always <code>true</code> as Windows are the
+ * root of the focus cycle.
+ *
+ * @return Always <code>true</code>.
+ *
+ * @since 1.4
+ */
+ public final boolean isFocusCycleRoot()
+ {
+ return true;
+ }
+
+ /**
+ * Set whether or not this Container is the root of a focus
+ * traversal cycle. Windows are the root of the focus cycle
+ * and therefore this method does nothing.
+ *
+ * @param focusCycleRoot ignored.
+ *
+ * @since 1.4
+ */
+ public final void setFocusCycleRoot(boolean focusCycleRoot)
+ {
+ // calls to the method are ignored
+ }
+
+ /**
+ * Returns the root container that owns the focus cycle where this
+ * component resides. Windows have no ancestors and this method
+ * returns always <code>null</code>.
+ *
+ * @return Always <code>null</code>.
+ * @since 1.4
+ */
+ public final Container getFocusCycleRootAncestor()
+ {
+ return null;
+ }
/**
* Generate a unique name for this window.
diff --git a/libjava/classpath/java/awt/datatransfer/FlavorEvent.java b/libjava/classpath/java/awt/datatransfer/FlavorEvent.java
index 8252dea3bcd..38b48187175 100644
--- a/libjava/classpath/java/awt/datatransfer/FlavorEvent.java
+++ b/libjava/classpath/java/awt/datatransfer/FlavorEvent.java
@@ -45,6 +45,8 @@ import java.util.EventObject;
* Fired by a ClipBoard for registered FlavorListeners.
*
* @author Mark J. Wielaard (mark@klomp.org)
+ *
+ * @since 1.5
*/
public class FlavorEvent extends EventObject
{
diff --git a/libjava/classpath/java/awt/datatransfer/SystemFlavorMap.java b/libjava/classpath/java/awt/datatransfer/SystemFlavorMap.java
index 7b4d2fbd38f..a80665aee98 100644
--- a/libjava/classpath/java/awt/datatransfer/SystemFlavorMap.java
+++ b/libjava/classpath/java/awt/datatransfer/SystemFlavorMap.java
@@ -38,6 +38,8 @@ exception statement from your version. */
package java.awt.datatransfer;
+import gnu.classpath.NotImplementedException;
+
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
@@ -262,11 +264,13 @@ public final class SystemFlavorMap implements FlavorMap, FlavorTable
* version of the native.
*/
public List getFlavorsForNative (String nat)
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
public List getNativesForFlavor (DataFlavor flav)
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
diff --git a/libjava/classpath/java/awt/dnd/DragGestureRecognizer.java b/libjava/classpath/java/awt/dnd/DragGestureRecognizer.java
index 07b822e7a68..37fde917836 100644
--- a/libjava/classpath/java/awt/dnd/DragGestureRecognizer.java
+++ b/libjava/classpath/java/awt/dnd/DragGestureRecognizer.java
@@ -38,6 +38,8 @@ exception statement from your version. */
package java.awt.dnd;
+import gnu.classpath.NotImplementedException;
+
import java.awt.Component;
import java.awt.Point;
import java.awt.event.InputEvent;
@@ -126,6 +128,7 @@ public abstract class DragGestureRecognizer implements Serializable
}
public void resetRecognizer()
+ throws NotImplementedException
{
throw new Error("not implemented");
}
@@ -152,6 +155,7 @@ public abstract class DragGestureRecognizer implements Serializable
}
protected void fireDragGestureRecognized(int dragAction, Point p)
+ throws NotImplementedException
{
throw new Error("not implemented");
}
diff --git a/libjava/classpath/java/awt/dnd/DragSourceContext.java b/libjava/classpath/java/awt/dnd/DragSourceContext.java
index 2cf0d6d0bc9..88607b090ea 100644
--- a/libjava/classpath/java/awt/dnd/DragSourceContext.java
+++ b/libjava/classpath/java/awt/dnd/DragSourceContext.java
@@ -38,6 +38,8 @@ exception statement from your version. */
package java.awt.dnd;
+import gnu.classpath.NotImplementedException;
+
import java.awt.Component;
import java.awt.Cursor;
import java.awt.Image;
@@ -86,6 +88,7 @@ public class DragSourceContext
DragGestureEvent trigger, Cursor cursor,
Image image, Point offset, Transferable trans,
DragSourceListener dsl)
+ throws NotImplementedException
{
if (peer == null
|| trigger == null)
@@ -130,6 +133,7 @@ public class DragSourceContext
}
public void setCursor (Cursor cursor)
+ throws NotImplementedException
{
this.cursor = cursor;
// FIXME: Check if we need to do more here
@@ -162,30 +166,37 @@ public class DragSourceContext
}
public void transferablesFlavorsChanged()
+ throws NotImplementedException
{
}
public void dragEnter(DragSourceDragEvent e)
+ throws NotImplementedException
{
}
public void dragOver(DragSourceDragEvent e)
+ throws NotImplementedException
{
}
public void dragExit(DragSourceEvent e)
+ throws NotImplementedException
{
}
public void dropActionChanged(DragSourceDragEvent e)
+ throws NotImplementedException
{
}
public void dragDropEnd(DragSourceDropEvent e)
+ throws NotImplementedException
{
}
public void dragMouseMoved(DragSourceDragEvent e)
+ throws NotImplementedException
{
}
@@ -195,6 +206,7 @@ public class DragSourceContext
}
protected void updateCurrentCursor(int dropOp, int targetAct, int status)
+ throws NotImplementedException
{
}
} // class DragSourceContext
diff --git a/libjava/classpath/java/awt/dnd/DropTarget.java b/libjava/classpath/java/awt/dnd/DropTarget.java
index 9fd7ef896fb..b0d4c2ae7a1 100644
--- a/libjava/classpath/java/awt/dnd/DropTarget.java
+++ b/libjava/classpath/java/awt/dnd/DropTarget.java
@@ -61,9 +61,7 @@ public class DropTarget
*/
private static final long serialVersionUID = -6283860791671019047L;
- /** @specnote According to the online documentation, this is
- * protected, but in reality it is public. */
- public static class DropTargetAutoScroller
+ protected static class DropTargetAutoScroller
implements ActionListener
{
private Component component;
diff --git a/libjava/classpath/java/awt/dnd/DropTargetContext.java b/libjava/classpath/java/awt/dnd/DropTargetContext.java
index d1fb66e6f35..19e27a9007f 100644
--- a/libjava/classpath/java/awt/dnd/DropTargetContext.java
+++ b/libjava/classpath/java/awt/dnd/DropTargetContext.java
@@ -54,9 +54,7 @@ public class DropTargetContext implements Serializable
{
static final long serialVersionUID = -634158968993743371L;
- /** @specnote According to the online documentation, this is
- * protected, but in reality it is public. */
- public class TransferableProxy implements Transferable
+ protected class TransferableProxy implements Transferable
{
protected boolean isLocal;
protected Transferable transferable;
diff --git a/libjava/classpath/java/awt/dnd/DropTargetEvent.java b/libjava/classpath/java/awt/dnd/DropTargetEvent.java
index 56a4d481a16..f75f756d037 100644
--- a/libjava/classpath/java/awt/dnd/DropTargetEvent.java
+++ b/libjava/classpath/java/awt/dnd/DropTargetEvent.java
@@ -41,6 +41,8 @@ import java.util.EventObject;
public class DropTargetEvent extends EventObject
{
+ private static final long serialVersionUID = 2821229066521922993L;
+
protected DropTargetContext context;
public DropTargetEvent (DropTargetContext context)
diff --git a/libjava/classpath/java/awt/event/MouseEvent.java b/libjava/classpath/java/awt/event/MouseEvent.java
index 3e0fecacf94..f2bcfbcc65f 100644
--- a/libjava/classpath/java/awt/event/MouseEvent.java
+++ b/libjava/classpath/java/awt/event/MouseEvent.java
@@ -402,7 +402,11 @@ public class MouseEvent extends InputEvent
// FIXME: need a mauve test for this method
if (modifiersEx != 0)
s.append(",extModifiers=").append(getModifiersExText(modifiersEx));
- return s.append(",clickCount=").append(clickCount).toString();
+
+ s.append(",clickCount=").append(clickCount);
+ s.append(",consumed=").append(consumed);
+
+ return s.toString();
}
/**
diff --git a/libjava/classpath/java/awt/font/GlyphMetrics.java b/libjava/classpath/java/awt/font/GlyphMetrics.java
index 28b2088cf8e..18aaedc7185 100644
--- a/libjava/classpath/java/awt/font/GlyphMetrics.java
+++ b/libjava/classpath/java/awt/font/GlyphMetrics.java
@@ -38,6 +38,8 @@ exception statement from your version. */
package java.awt.font;
+import gnu.classpath.NotImplementedException;
+
import java.awt.geom.Rectangle2D;
/**
@@ -93,11 +95,13 @@ public final class GlyphMetrics
}
public float getLSB ()
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
public float getRSB ()
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
diff --git a/libjava/classpath/java/awt/font/GlyphVector.java b/libjava/classpath/java/awt/font/GlyphVector.java
index 57e2581edb4..8d8a51d6877 100644
--- a/libjava/classpath/java/awt/font/GlyphVector.java
+++ b/libjava/classpath/java/awt/font/GlyphVector.java
@@ -38,6 +38,8 @@ exception statement from your version. */
package java.awt.font;
+import gnu.classpath.NotImplementedException;
+
import java.awt.Font;
import java.awt.Rectangle;
import java.awt.Shape;
@@ -70,12 +72,14 @@ public abstract class GlyphVector implements Cloneable
public abstract FontRenderContext getFontRenderContext ();
public int getGlyphCharIndex (int glyphIndex)
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
public int[] getGlyphCharIndices (int beginGlyphIndex, int numEntries,
int[] codeReturn)
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
@@ -95,12 +99,14 @@ public abstract class GlyphVector implements Cloneable
public abstract Shape getGlyphOutline (int glyphIndex);
public Shape getGlyphOutline (int glyphIndex, float x, float y)
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
public Rectangle getGlyphPixelBounds (int index, FontRenderContext renderFRC,
float x, float y)
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
@@ -116,6 +122,7 @@ public abstract class GlyphVector implements Cloneable
public abstract Shape getGlyphVisualBounds (int glyphIndex);
public int getLayoutFlags ()
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
@@ -130,6 +137,7 @@ public abstract class GlyphVector implements Cloneable
public Rectangle getPixelBounds (FontRenderContext renderFRC,
float x, float y)
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
diff --git a/libjava/classpath/java/awt/font/GraphicAttribute.java b/libjava/classpath/java/awt/font/GraphicAttribute.java
index 79eae9955f5..107f16dcd18 100644
--- a/libjava/classpath/java/awt/font/GraphicAttribute.java
+++ b/libjava/classpath/java/awt/font/GraphicAttribute.java
@@ -38,6 +38,8 @@ exception statement from your version. */
package java.awt.font;
+import gnu.classpath.NotImplementedException;
+
import java.awt.Graphics2D;
import java.awt.geom.Rectangle2D;
@@ -71,6 +73,7 @@ public abstract class GraphicAttribute
public abstract float getAscent ();
public Rectangle2D getBounds ()
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
@@ -78,6 +81,7 @@ public abstract class GraphicAttribute
public abstract float getDescent ();
public GlyphJustificationInfo getJustificationInfo ()
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
diff --git a/libjava/classpath/java/awt/font/ImageGraphicAttribute.java b/libjava/classpath/java/awt/font/ImageGraphicAttribute.java
index 77413f95dfc..c050255ee97 100644
--- a/libjava/classpath/java/awt/font/ImageGraphicAttribute.java
+++ b/libjava/classpath/java/awt/font/ImageGraphicAttribute.java
@@ -38,6 +38,8 @@ exception statement from your version. */
package java.awt.font;
+import gnu.classpath.NotImplementedException;
+
import java.awt.Graphics2D;
import java.awt.Image;
import java.awt.geom.Rectangle2D;
@@ -57,6 +59,7 @@ public final class ImageGraphicAttribute extends GraphicAttribute
public ImageGraphicAttribute (Image image, int alignment, float originX,
float originY)
+ throws NotImplementedException
{
super (alignment);
this.image = image;
@@ -65,6 +68,7 @@ public final class ImageGraphicAttribute extends GraphicAttribute
}
public void draw (Graphics2D graphics, float x, float y)
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
@@ -78,31 +82,37 @@ public final class ImageGraphicAttribute extends GraphicAttribute
}
public boolean equals (ImageGraphicAttribute rhs)
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
public float getAdvance ()
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
public float getAscent ()
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
- public Rectangle2D getBounds ()
+ public Rectangle2D getBounds ()
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
public float getDescent ()
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
public int hashCode ()
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
diff --git a/libjava/classpath/java/awt/font/LineBreakMeasurer.java b/libjava/classpath/java/awt/font/LineBreakMeasurer.java
index 0a6a96922bd..14985b44cb9 100644
--- a/libjava/classpath/java/awt/font/LineBreakMeasurer.java
+++ b/libjava/classpath/java/awt/font/LineBreakMeasurer.java
@@ -38,6 +38,8 @@ exception statement from your version. */
package java.awt.font;
+import gnu.classpath.NotImplementedException;
+
import java.text.AttributedCharacterIterator;
import java.text.BreakIterator;
@@ -69,6 +71,7 @@ public final class LineBreakMeasurer
public void deleteChar (AttributedCharacterIterator newParagraph,
int deletePos)
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
@@ -80,28 +83,33 @@ public final class LineBreakMeasurer
public void insertChar (AttributedCharacterIterator newParagraph,
int insertPos)
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
public TextLayout nextLayout (float wrappingWidth)
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
public TextLayout nextLayout (float wrappingWidth, int offsetLimit,
boolean requireNextWord)
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
public int nextOffset (float wrappingWidth)
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
public int nextOffset (float wrappingWidth, int offsetLimit,
boolean requireNextWord)
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
diff --git a/libjava/classpath/java/awt/font/NumericShaper.java b/libjava/classpath/java/awt/font/NumericShaper.java
index efbdcd49dc4..add1c6a44ed 100644
--- a/libjava/classpath/java/awt/font/NumericShaper.java
+++ b/libjava/classpath/java/awt/font/NumericShaper.java
@@ -39,99 +39,387 @@ exception statement from your version. */
package java.awt.font;
import java.io.Serializable;
+import java.lang.Character.UnicodeBlock;
/**
+ * This class handles numeric shaping. A shaper can either be contextual
+ * or not. A non-contextual shaper will always translate ASCII digits
+ * in its input into the target Unicode range. A contextual shaper will
+ * change the target Unicode range depending on the characters it has
+ * previously processed.
+ *
* @author Michael Koch
+ * @author Tom Tromey
+ *
* @since 1.4
+ * @specnote This class does not handle LIMBU or OSMANYA.
+ * @specnote The JDK does not seem to properly handle ranges without a
+ * digit zero, such as TAMIL. This implementation does.
*/
public final class NumericShaper implements Serializable
{
private static final long serialVersionUID = -8022764705923730308L;
-
+
+ /** Convenience constant representing all the valid Unicode ranges. */
public static final int ALL_RANGES = 524287;
+
+ /**
+ * Constant representing the Unicode ARABIC range. Shaping done
+ * using this range will translate to the arabic decimal characters.
+ * Use EASTERN_ARABIC if you want to shape to the eastern arabic
+ * (also known as the extended arabic) decimal characters.
+ */
public static final int ARABIC = 2;
+
+ /** Constant representing the Unicode BENGALI range. */
public static final int BENGALI = 16;
+
+ /** Constant representing the Unicode DEVANAGARI range. */
public static final int DEVANAGARI = 8;
+
+ /**
+ * Constant representing the Unicode extended arabic range.
+ * In Unicode there are two different sets of arabic digits;
+ * this selects the extended or eastern set.
+ */
public static final int EASTERN_ARABIC = 4;
+
+ /**
+ * Constant representing the Unicode ETHIOPIC range. Note that
+ * there is no digit zero in this range; an ASCII digit zero
+ * is left unchanged when shaping to this range.
+ */
public static final int ETHIOPIC = 65536;
+
+ /**
+ * Constant representing the Unicode EUROPEAN range. For
+ * contextual shaping purposes, characters in the various
+ * extended Latin character blocks are recognized as EUROPEAN.
+ */
public static final int EUROPEAN = 1;
+
+ /** Constant representing the Unicode GUJARATI range. */
public static final int GUJARATI = 64;
+
+ /** Constant representing the Unicode GURMUKHI range. */
public static final int GURMUKHI = 32;
+
+ /** Constant representing the Unicode KANNADA range. */
public static final int KANNADA = 1024;
+
+ /** Constant representing the Unicode KHMER range. */
public static final int KHMER = 131072;
+
+ /** Constant representing the Unicode LAO range. */
public static final int LAO = 8192;
+
+ /** Constant representing the Unicode MALAYALAM range. */
public static final int MALAYALAM = 2048;
+
+ /** Constant representing the Unicode MONGOLIAN range. */
public static final int MONGOLIAN = 262144;
+
+ /** Constant representing the Unicode MYANMAR range. */
public static final int MYANMAR = 32768;
+
+ /** Constant representing the Unicode ORIYA range. */
public static final int ORIYA = 128;
+
+ /**
+ * Constant representing the Unicode TAMIL range. Note that
+ * there is no digit zero in this range; an ASCII digit zero
+ * is left unchanged when shaping to this range.
+ */
public static final int TAMIL = 256;
+
+ /** Constant representing the Unicode TELUGU range. */
public static final int TELUGU = 512;
+
+ /** Constant representing the Unicode THAI range. */
public static final int THAI = 4096;
+
+ /** Constant representing the Unicode TIBETAN range. */
public static final int TIBETAN = 16384;
- private int ranges;
- private int context;
-
- private NumericShaper (int ranges, int context)
+ /**
+ * This table holds the zero digits for each language. This is hard-coded
+ * because the values will not change and the table layout is tied to the
+ * other constants in this class in any case. In the two places where a
+ * language does not have a zero digit, the character immediately preceeding
+ * the one digit is used instead. These languages are special-cased in
+ * the shaping code.
+ */
+ private static final char[] zeroDigits =
{
- this.ranges = ranges;
- this.context = context;
+ '0', // EUROPEAN
+ '\u0660', // ARABIC
+ '\u06f0', // EASTERN_ARABIC
+ '\u0966', // DEVANAGARI
+ '\u09e6', // BENGALI
+ '\u0a66', // GURMUKHI
+ '\u0ae6', // GUJARATI
+ '\u0b66', // ORIYA
+ '\u0be6', // TAMIL - special case as there is no digit zero
+ '\u0c66', // TELUGU
+ '\u0ce6', // KANNADA
+ '\u0d66', // MALAYALAM
+ '\u0e50', // THAI
+ '\u0ed0', // LAO
+ '\u0f20', // TIBETAN
+ '\u1040', // MYANMAR
+ '\u1368', // ETHIOPIC - special case as there is no digit zero
+ '\u17e0', // KHMER
+ '\u1810' // MONGOLIAN
+ };
+
+ /**
+ * The default initial context for this shaper, specified as
+ * an integer from 0 to 18.
+ */
+ private int key;
+
+ /**
+ * The target ranges handled by this shaper. If the shaper
+ * is not contextual, the high bit of this field will be set.
+ * @specnote This was discovered by reading the serialization spec
+ */
+ private int mask;
+
+ /**
+ * Create a new numeric shaper. The key given is a constant from
+ * this class, the constructor turns it into its internal form.
+ * @param key the key to use, as one of the manifest constants
+ * @param mask a mask of languages to shape for
+ */
+ private NumericShaper (int key, int mask)
+ {
+ // This internal form is a bit goofy, but it is specified by
+ // the serialization spec.
+ this.key = Integer.numberOfTrailingZeros(key);
+ this.mask = mask;
}
- public boolean equals (Object obj)
+ /**
+ * Return an integer representing all the languages for which this
+ * shaper will shape. The result is taken by "or"ing together
+ * the constants representing the various languages.
+ */
+ public int getRanges ()
{
- if (! (obj instanceof NumericShaper))
- return false;
+ return mask & ALL_RANGES;
+ }
- NumericShaper tmp = (NumericShaper) obj;
-
- return (ranges == tmp.ranges
- && context == tmp.context);
+ /**
+ * Return true if this shaper is contextual, false if it is not.
+ */
+ public boolean isContextual ()
+ {
+ return mask > 0;
}
- public static NumericShaper getContextualShaper (int ranges)
+ /**
+ * Shape the text in the given array. The starting context will
+ * be the context passed to the shaper at creation time.
+ * @param text the text to shape
+ * @param start the index of the starting character of the array
+ * @param count the number of characters in the array
+ */
+ public void shape (char[] text, int start, int count)
{
- throw new Error ("not implemented");
+ shape (text, start, count, 1 << key);
}
- public static NumericShaper getContextualShaper (int ranges,
- int defaultContext)
+ /**
+ * Given a unicode block object, return corresponding language constant.
+ * If the block is not recognized, returns zero. Note that as there
+ * is no separate ARABIC block in Character, this case must
+ * be specially handled by the caller; EASTERN_ARABIC is preferred when
+ * both are specified.
+ * @param b the unicode block to classify
+ * @return the language constant, or zero if not recognized
+ */
+ private int classify(UnicodeBlock b)
{
- throw new Error ("not implemented");
+ if (b == null)
+ return 0;
+ // ARABIC is handled by the caller; from testing we know
+ // that EASTERN_ARABIC takes precedence.
+ if (b == UnicodeBlock.ARABIC)
+ return EASTERN_ARABIC;
+ if (b == UnicodeBlock.BENGALI)
+ return BENGALI;
+ if (b == UnicodeBlock.DEVANAGARI)
+ return DEVANAGARI;
+ if (b == UnicodeBlock.ETHIOPIC)
+ return ETHIOPIC;
+ if (b == UnicodeBlock.BASIC_LATIN
+ || b == UnicodeBlock.LATIN_1_SUPPLEMENT
+ || b == UnicodeBlock.LATIN_EXTENDED_A
+ || b == UnicodeBlock.LATIN_EXTENDED_ADDITIONAL
+ || b == UnicodeBlock.LATIN_EXTENDED_B)
+ return EUROPEAN;
+ if (b == UnicodeBlock.GUJARATI)
+ return GUJARATI;
+ if (b == UnicodeBlock.GURMUKHI)
+ return GURMUKHI;
+ if (b == UnicodeBlock.KANNADA)
+ return KANNADA;
+ if (b == UnicodeBlock.KHMER)
+ return KHMER;
+ if (b == UnicodeBlock.LAO)
+ return LAO;
+ if (b == UnicodeBlock.MALAYALAM)
+ return MALAYALAM;
+ if (b == UnicodeBlock.MONGOLIAN)
+ return MONGOLIAN;
+ if (b == UnicodeBlock.MYANMAR)
+ return MYANMAR;
+ if (b == UnicodeBlock.ORIYA)
+ return ORIYA;
+ if (b == UnicodeBlock.TAMIL)
+ return TAMIL;
+ if (b == UnicodeBlock.TELUGU)
+ return TELUGU;
+ if (b == UnicodeBlock.THAI)
+ return THAI;
+ if (b == UnicodeBlock.TIBETAN)
+ return TIBETAN;
+ return 0;
}
- public int getRanges ()
+ /**
+ * Shape the given text, using the indicated initial context.
+ * If this shaper is not a contextual shaper, then the given context
+ * will be ignored.
+ * @param text the text to shape
+ * @param start the index of the first character of the text to shape
+ * @param count the number of characters to shape in the text
+ * @param context the initial context
+ * @throws IllegalArgumentException if the initial context is invalid
+ */
+ public void shape (char[] text, int start, int count, int context)
{
- return ranges;
+ int currentContext;
+ if (isContextual())
+ {
+ if (Integer.bitCount(context) != 1 || (context & ~ALL_RANGES) != 0)
+ throw new IllegalArgumentException("invalid context argument");
+ // If the indicated context is not one we are handling, reset it.
+ if ((context & mask) == 0)
+ currentContext = -1;
+ else
+ currentContext = Integer.numberOfTrailingZeros(context);
+ }
+ else
+ currentContext = key;
+
+ for (int i = 0; i < count; ++i)
+ {
+ char c = text[start + i];
+ if (c >= '0' && c <= '9')
+ {
+ if (currentContext >= 0)
+ {
+ // Shape into the current context.
+ if (c == '0'
+ && ((1 << currentContext) == TAMIL
+ || (1 << currentContext) == ETHIOPIC))
+ {
+ // No digit 0 in this context; do nothing.
+ }
+ else
+ text[start + i]
+ = (char) (zeroDigits[currentContext] + c - '0');
+ }
+ }
+ else if (isContextual())
+ {
+ // if c is in a group, set currentContext; else reset it.
+ int group = classify(UnicodeBlock.of(c));
+ // Specially handle ARABIC.
+ if (group == EASTERN_ARABIC && (mask & EASTERN_ARABIC) == 0
+ && (mask & ARABIC) != 0)
+ group = ARABIC;
+ if ((mask & group) != 0)
+ {
+ // The character was classified as being in a group
+ // we recognize, and it was selected by the shaper.
+ // So, change the context.
+ currentContext = Integer.numberOfTrailingZeros(group);
+ }
+ }
+ }
}
- public static NumericShaper getShaper (int singleRange)
+ public boolean equals (Object obj)
{
- throw new Error ("not implemented");
+ if (! (obj instanceof NumericShaper))
+ return false;
+ NumericShaper tmp = (NumericShaper) obj;
+ return key == tmp.key && mask == tmp.mask;
}
public int hashCode ()
{
- throw new Error ("not implemented");
+ return key ^ mask;
}
- public boolean isContextual ()
+ public String toString ()
{
- throw new Error ("not implemented");
+ // For debugging only.
+ return "key=" + key + "; mask=" + mask;
}
- public void shape (char[] text, int start, int count)
+ /**
+ * Return a non-contextual shaper which can shape to a single range.
+ * All ASCII digits in the input text are translated to this language.
+ * @param singleRange the target language
+ * @return a non-contextual shaper for this language
+ * @throws IllegalArgumentException if the argument does not name a
+ * single language, as specified by the constants declared in this class
+ */
+ public static NumericShaper getShaper (int singleRange)
{
- shape (text, start, count, context);
+ if (Integer.bitCount(singleRange) != 1)
+ throw new IllegalArgumentException("more than one bit set in argument");
+ if ((singleRange & ~ALL_RANGES) != 0)
+ throw new IllegalArgumentException("argument out of range");
+ return new NumericShaper(singleRange, Integer.MIN_VALUE | singleRange);
}
- public void shape (char[] text, int start, int count, int context)
+ /**
+ * Return a contextual shaper which can shape to any of the indicated
+ * languages. The default initial context for this shaper is EUROPEAN.
+ * @param ranges the ranges to shape to
+ * @return a contextual shaper which will target any of these ranges
+ * @throws IllegalArgumentException if the argument specifies an
+ * unrecognized range
+ */
+ public static NumericShaper getContextualShaper (int ranges)
{
- throw new Error ("not implemented");
+ if ((ranges & ~ALL_RANGES) != 0)
+ throw new IllegalArgumentException("argument out of range");
+ return new NumericShaper(EUROPEAN, ranges);
}
- public String toString ()
+ /**
+ * Return a contextual shaper which can shape to any of the indicated
+ * languages. The default initial context for this shaper is given as
+ * an argument.
+ * @param ranges the ranges to shape to
+ * @param defaultContext the default initial context
+ * @return a contextual shaper which will target any of these ranges
+ * @throws IllegalArgumentException if the ranges argument specifies an
+ * unrecognized range, or if the defaultContext argument does not specify
+ * a single valid range
+ */
+ public static NumericShaper getContextualShaper (int ranges,
+ int defaultContext)
{
- throw new Error ("not implemented");
+ if (Integer.bitCount(defaultContext) != 1)
+ throw new IllegalArgumentException("more than one bit set in context");
+ if ((ranges & ~ALL_RANGES) != 0 || (defaultContext & ~ALL_RANGES) != 0)
+ throw new IllegalArgumentException("argument out of range");
+ return new NumericShaper(defaultContext, ranges);
}
}
diff --git a/libjava/classpath/java/awt/font/ShapeGraphicAttribute.java b/libjava/classpath/java/awt/font/ShapeGraphicAttribute.java
index 6d64dece5d8..d5320854c38 100644
--- a/libjava/classpath/java/awt/font/ShapeGraphicAttribute.java
+++ b/libjava/classpath/java/awt/font/ShapeGraphicAttribute.java
@@ -38,6 +38,8 @@ exception statement from your version. */
package java.awt.font;
+import gnu.classpath.NotImplementedException;
+
import java.awt.Graphics2D;
import java.awt.Shape;
import java.awt.geom.Rectangle2D;
@@ -58,6 +60,7 @@ public final class ShapeGraphicAttribute extends GraphicAttribute
}
public void draw (Graphics2D graphics, float x, float y)
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
@@ -78,11 +81,13 @@ public final class ShapeGraphicAttribute extends GraphicAttribute
}
public float getAdvance ()
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
public float getAscent ()
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
@@ -93,6 +98,7 @@ public final class ShapeGraphicAttribute extends GraphicAttribute
}
public float getDescent ()
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
diff --git a/libjava/classpath/java/awt/font/TextMeasurer.java b/libjava/classpath/java/awt/font/TextMeasurer.java
index 7fcdc87a83c..18c286c57c1 100644
--- a/libjava/classpath/java/awt/font/TextMeasurer.java
+++ b/libjava/classpath/java/awt/font/TextMeasurer.java
@@ -38,6 +38,8 @@ exception statement from your version. */
package java.awt.font;
+import gnu.classpath.NotImplementedException;
+
import java.text.AttributedCharacterIterator;
/**
@@ -70,27 +72,32 @@ public final class TextMeasurer implements Cloneable
public void deleteChar (AttributedCharacterIterator newParagraph,
int deletePos)
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
public float getAdvanceBetween (int start, int limit)
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
public TextLayout getLayout (int start, int limit)
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
public int getLineBreakIndex (int start, float maxAdvance)
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
public void insertChar (AttributedCharacterIterator newParagraph,
int insertPos)
+ throws NotImplementedException
{
throw new Error ("not implemented");
}
diff --git a/libjava/classpath/java/awt/geom/GeneralPath.java b/libjava/classpath/java/awt/geom/GeneralPath.java
index 15fb8aba811..123833b118b 100644
--- a/libjava/classpath/java/awt/geom/GeneralPath.java
+++ b/libjava/classpath/java/awt/geom/GeneralPath.java
@@ -1,5 +1,5 @@
/* GeneralPath.java -- represents a shape built from subpaths
- Copyright (C) 2002, 2003, 2004 Free Software Foundation
+ Copyright (C) 2002, 2003, 2004, 2006 Free Software Foundation
This file is part of GNU Classpath.
@@ -79,8 +79,16 @@ import java.awt.Shape;
*/
public final class GeneralPath implements Shape, Cloneable
{
- public static final int WIND_EVEN_ODD = PathIterator.WIND_EVEN_ODD;
- public static final int WIND_NON_ZERO = PathIterator.WIND_NON_ZERO;
+ // WORKAROUND for gcj 4.0.x (x < 3)
+ // fully qualify PathIterator constants.
+
+ /** Same constant as {@link PathIterator#WIND_EVEN_ODD}. */
+ public static final int WIND_EVEN_ODD
+ = java.awt.geom.PathIterator.WIND_EVEN_ODD;
+
+ /** Same constant as {@link PathIterator.WIND_NON_ZERO}. */
+ public static final int WIND_NON_ZERO
+ = java.awt.geom.PathIterator.WIND_NON_ZERO;
/** Initial size if not specified. */
private static final int INIT_SIZE = 10;
diff --git a/libjava/classpath/java/awt/geom/Point2D.java b/libjava/classpath/java/awt/geom/Point2D.java
index 9f22a5a67c9..a2689abf80c 100644
--- a/libjava/classpath/java/awt/geom/Point2D.java
+++ b/libjava/classpath/java/awt/geom/Point2D.java
@@ -1,5 +1,5 @@
/* Point2D.java -- generic point in 2-D space
- Copyright (C) 1999, 2000, 2002, 2004 Free Software Foundation
+ Copyright (C) 1999, 2000, 2002, 2004, 2006, Free Software Foundation
This file is part of GNU Classpath.
@@ -135,7 +135,7 @@ public abstract class Point2D implements Cloneable
*/
public double distanceSq(double x, double y)
{
- return distanceSq(getX(), x, getY(), y);
+ return distanceSq(getX(), getY(), x, y);
}
/**
@@ -147,7 +147,7 @@ public abstract class Point2D implements Cloneable
*/
public double distanceSq(Point2D p)
{
- return distanceSq(getX(), p.getX(), getY(), p.getY());
+ return distanceSq(getX(), getY(), p.getX(), p.getY());
}
/**
@@ -159,7 +159,7 @@ public abstract class Point2D implements Cloneable
*/
public double distance(double x, double y)
{
- return distance(getX(), x, getY(), y);
+ return distance(getX(), getY(), x, y);
}
/**
@@ -171,7 +171,7 @@ public abstract class Point2D implements Cloneable
*/
public double distance(Point2D p)
{
- return distance(getX(), p.getX(), getY(), p.getY());
+ return distance(getX(), getY(), p.getX(), p.getY());
}
/**
diff --git a/libjava/classpath/java/awt/image/AffineTransformOp.java b/libjava/classpath/java/awt/image/AffineTransformOp.java
index f11066e4e3d..bb4b795231b 100644
--- a/libjava/classpath/java/awt/image/AffineTransformOp.java
+++ b/libjava/classpath/java/awt/image/AffineTransformOp.java
@@ -347,7 +347,7 @@ public class AffineTransformOp implements BufferedImageOp, RasterOp
* @param dstPt destination point
* @return the location of the transformed source point.
*/
- public Point2D getPoint2D (Point2D srcPt, Point2D dstPt)
+ public final Point2D getPoint2D (Point2D srcPt, Point2D dstPt)
{
return transform.transform (srcPt, dstPt);
}
diff --git a/libjava/classpath/java/awt/image/AreaAveragingScaleFilter.java b/libjava/classpath/java/awt/image/AreaAveragingScaleFilter.java
index 6333ce9e7f9..44d5cec9d5f 100644
--- a/libjava/classpath/java/awt/image/AreaAveragingScaleFilter.java
+++ b/libjava/classpath/java/awt/image/AreaAveragingScaleFilter.java
@@ -1,5 +1,5 @@
/* AreaAveragingScaleFilter.java -- Java class for filtering images
- Copyright (C) 1999 Free Software Foundation, Inc.
+ Copyright (C) 1999,2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -45,86 +45,225 @@ package java.awt.image;
* points should give the desired results although Sun does not
* specify what the exact algorithm should be.
* <br>
- * FIXME: Currently this filter does nothing and needs to be implemented.
*
* @author C. Brian Jones (cbj@gnu.org)
*/
public class AreaAveragingScaleFilter extends ReplicateScaleFilter
{
- /**
- * Construct an instance of <code>AreaAveragingScaleFilter</code> which
- * should be used in conjunction with a <code>FilteredImageSource</code>
- * object.
- *
- * @param width the width of the destination image
- * @param height the height of the destination image
- */
- public AreaAveragingScaleFilter(int width, int height) {
- super(width, height);
- }
-
- /**
- * The <code>ImageProducer</code> should call this method with a
- * bit mask of hints from any of <code>RANDOMPIXELORDER</code>,
- * <code>TOPDOWNLEFTRIGHT</code>, <code>COMPLETESCANLINES</code>,
- * <code>SINGLEPASS</code>, <code>SINGLEFRAME</code> from the
- * <code>ImageConsumer</code> interface.
- * <br>
- * FIXME - more than likely Sun's implementation desires
- * <code>TOPDOWNLEFTRIGHT</code> order and this method is overloaded here
- * in order to assure that mask is part of the hints added to
- * the consumer.
- *
- * @param flags a bit mask of hints
- * @see ImageConsumer
- */
- public void setHints(int flags)
- {
- if (consumer != null)
- consumer.setHints(flags);
- }
-
- /**
- * This function delivers a rectangle of pixels where any
- * pixel(m,n) is stored in the array as a <code>byte</code> at
- * index (n * scansize + m + offset).
- *
- * @param x the x coordinate of the rectangle
- * @param y the y coordinate of the rectangle
- * @param w the width of the rectangle
- * @param h the height of the rectangle
- * @param model the <code>ColorModel</code> used to translate the pixels
- * @param pixels the array of pixel values
- * @param offset the index of the first pixels in the <code>pixels</code> array
- * @param scansize the width to use in extracting pixels from the <code>pixels</code> array
- */
- public void setPixels(int x, int y, int w, int h,
- ColorModel model, byte[] pixels, int offset, int scansize)
- {
- if (consumer != null)
- consumer.setPixels(x, y, w, h, model, pixels, offset, scansize);
- }
-
- /**
- * This function delivers a rectangle of pixels where any
- * pixel(m,n) is stored in the array as an <code>int</code> at
- * index (n * scansize + m + offset).
- *
- * @param x the x coordinate of the rectangle
- * @param y the y coordinate of the rectangle
- * @param w the width of the rectangle
- * @param h the height of the rectangle
- * @param model the <code>ColorModel</code> used to translate the pixels
- * @param pixels the array of pixel values
- * @param offset the index of the first pixels in the <code>pixels</code> array
- * @param scansize the width to use in extracting pixels from the <code>pixels</code> array
- */
- public void setPixels(int x, int y, int w, int h,
- ColorModel model, int[] pixels, int offset, int scansize)
- {
- if (consumer != null)
- consumer.setPixels(x, y, w, h, model, pixels, offset, scansize);
- }
+ /**
+ * Construct an instance of <code>AreaAveragingScaleFilter</code> which
+ * should be used in conjunction with a <code>FilteredImageSource</code>
+ * object.
+ *
+ * @param width the width of the destination image
+ * @param height the height of the destination image
+ */
+ public AreaAveragingScaleFilter(int width, int height) {
+ super(width, height);
+ }
+ /**
+ * The <code>ImageProducer</code> should call this method with a
+ * bit mask of hints from any of <code>RANDOMPIXELORDER</code>,
+ * <code>TOPDOWNLEFTRIGHT</code>, <code>COMPLETESCANLINES</code>,
+ * <code>SINGLEPASS</code>, <code>SINGLEFRAME</code> from the
+ * <code>ImageConsumer</code> interface.
+ * <br>
+ * FIXME - more than likely Sun's implementation desires
+ * <code>TOPDOWNLEFTRIGHT</code> order and this method is overloaded here
+ * in order to assure that mask is part of the hints added to
+ * the consumer.
+ *
+ * @param flags a bit mask of hints
+ * @see ImageConsumer
+ */
+ public void setHints(int flags)
+ {
+ if (consumer != null)
+ consumer.setHints(flags);
+ }
+
+ /**
+ * This function delivers a rectangle of pixels where any
+ * pixel(m,n) is stored in the array as a <code>byte</code> at
+ * index (n * scansize + m + offset).
+ *
+ * @param x the x coordinate of the rectangle
+ * @param y the y coordinate of the rectangle
+ * @param w the width of the rectangle
+ * @param h the height of the rectangle
+ * @param model the <code>ColorModel</code> used to translate the pixels
+ * @param pixels the array of pixel values
+ * @param offset the index of the first pixels in the <code>pixels</code> array
+ * @param scansize the width to use in extracting pixels from the <code>pixels</code> array
+ */
+ public void setPixels(int x, int y, int w, int h,
+ ColorModel model, byte[] pixels, int offset, int scansize)
+ {
+ double rx = ((double) srcWidth) / destWidth;
+ double ry = ((double) srcHeight) / destHeight;
+
+ int destScansize = (int) Math.round(scansize / rx);
+
+ byte[] destPixels = averagePixels(x, y, w, h,
+ model, pixels, offset, scansize,
+ rx, ry, destScansize);
+
+ if (consumer != null)
+ consumer.setPixels((int) Math.floor(x/rx), (int) Math.floor(y/ry),
+ (int) Math.ceil(w/rx), (int) Math.ceil(h/ry),
+ model, destPixels, 0, destScansize);
+ }
+
+ /**
+ * This function delivers a rectangle of pixels where any
+ * pixel(m,n) is stored in the array as an <code>int</code> at
+ * index (n * scansize + m + offset).
+ *
+ * @param x the x coordinate of the rectangle
+ * @param y the y coordinate of the rectangle
+ * @param w the width of the rectangle
+ * @param h the height of the rectangle
+ * @param model the <code>ColorModel</code> used to translate the pixels
+ * @param pixels the array of pixel values
+ * @param offset the index of the first pixels in the <code>pixels</code> array
+ * @param scansize the width to use in extracting pixels from the <code>pixels</code> array
+ */
+ public void setPixels(int x, int y, int w, int h,
+ ColorModel model, int[] pixels, int offset, int scansize)
+ {
+ double rx = ((double) srcWidth) / destWidth;
+ double ry = ((double) srcHeight) / destHeight;
+
+ int destScansize = (int) Math.round(scansize / rx);
+
+ int[] destPixels = averagePixels(x, y, w, h,
+ model, pixels, offset, scansize,
+ rx, ry, destScansize);
+
+ if (consumer != null)
+ consumer.setPixels((int) Math.floor(x/rx), (int) Math.floor(y/ry),
+ (int) Math.ceil(w/rx), (int) Math.ceil(h/ry),
+ model, destPixels, 0, destScansize);
+ }
+
+ /**
+ * This is a really terrible implementation,
+ * since it uses the nearest-neighbor method. This filter is rarely used though.
+ *
+ * @param srcx, srcy - Source rectangle upper-left corner
+ * @param srcw, srch - Source rectangle width and height
+ * @param model - Pixel color model
+ * @param srcPixels - Source pixel data.
+ * @param srcOffset - Starting offset into the source pixel data array.
+ * @param srcScansize - Source array scanline size.
+ * @param rx,ry - Scaling factor.
+ * @param dstScansize - Destination array scanline size.
+ */
+ private byte[] averagePixels(int srcx, int srcy, int srcw, int srch,
+ ColorModel model, byte[] srcPixels,
+ int srcOffset, int srcScansize,
+ double rx, double ry, int destScansize)
+ {
+ int destW = (int) Math.ceil(srcw/rx);
+ int destH = (int) Math.ceil(srch/ry);
+ byte[] destPixels = new byte[ destW * destH ];
+ int sx, sy;
+
+ int w = (int)Math.ceil(rx);
+ int h = (int)Math.ceil(ry);
+
+ for(int x = 0; x < destW; x++)
+ for(int y = 0; y < destH; y++)
+ {
+ sx = (int) (x * rx);
+ sy = (int) (y * ry);
+
+ int r,g,b,a;
+ r = g = b = a = 0;
+
+ for(int i = 0; i < w; i++)
+ {
+ for(int j = 0; j < h; j++)
+ {
+ int idx = srcx + sx + i + (srcy + sy + j)*srcScansize;
+ r += model.getRed(srcPixels[ idx ]);
+ g += model.getGreen(srcPixels[ idx ]);
+ b += model.getBlue(srcPixels[ idx ]);
+ a += model.getAlpha(srcPixels[ idx ]);
+ }
+ }
+
+ r = r / (w * h);
+ g = g / (w * h);
+ b = b / (w * h);
+ a = a / (w * h);
+
+ // Does this really work?
+ destPixels[x + destScansize*y] = (byte)model.getDataElement
+ (new int[]{r, g, b, a}, 0);
+ }
+
+ return destPixels;
+ }
+
+ /**
+ * This is a really terrible implementation,
+ * since it uses the nearest-neighbor method. This filter is rarely used though.
+ *
+ * @param srcx, srcy - Source rectangle upper-left corner
+ * @param srcw, srch - Source rectangle width and height
+ * @param model - Pixel color model
+ * @param srcPixels - Source pixel data.
+ * @param srcOffset - Starting offset into the source pixel data array.
+ * @param srcScansize - Source array scanline size.
+ * @param rx,ry - Scaling factor.
+ * @param dstScansize - Destination array scanline size.
+ */
+ private int[] averagePixels(int srcx, int srcy, int srcw, int srch,
+ ColorModel model, int[] srcPixels,
+ int srcOffset, int srcScansize,
+ double rx, double ry, int destScansize)
+ {
+ int destW = (int) Math.ceil(srcw/rx);
+ int destH = (int) Math.ceil(srch/ry);
+ int[] destPixels = new int[ destW * destH ];
+ int sx, sy;
+
+ int w = (int)Math.ceil(rx);
+ int h = (int)Math.ceil(ry);
+
+ for(int x = 0; x < destW; x++)
+ for(int y = 0; y < destH; y++)
+ {
+ sx = (int) (x * rx);
+ sy = (int) (y * ry);
+
+ int r,g,b,a;
+ r = g = b = a = 0;
+
+ for(int i = 0; i < w; i++)
+ {
+ for(int j = 0; j < h; j++)
+ {
+ int idx = srcx + sx + i + (srcy + sy + j)*srcScansize;
+ r += model.getRed(srcPixels[ idx ]);
+ g += model.getGreen(srcPixels[ idx ]);
+ b += model.getBlue(srcPixels[ idx ]);
+ a += model.getAlpha(srcPixels[ idx ]);
+ }
+ }
+
+ r = r / (w * h);
+ g = g / (w * h);
+ b = b / (w * h);
+ a = a / (w * h);
+
+ destPixels[x + destScansize*y] = model.getDataElement
+ (new int[]{r, g, b, a}, 0);
+ }
+
+ return destPixels;
+ }
}
diff --git a/libjava/classpath/java/awt/image/BandCombineOp.java b/libjava/classpath/java/awt/image/BandCombineOp.java
index 79efb02e713..634125ed23f 100644
--- a/libjava/classpath/java/awt/image/BandCombineOp.java
+++ b/libjava/classpath/java/awt/image/BandCombineOp.java
@@ -118,7 +118,7 @@ public class BandCombineOp implements RasterOp
/* (non-Javadoc)
* @see java.awt.image.RasterOp#getBounds2D(java.awt.image.Raster)
*/
- public Rectangle2D getBounds2D(Raster src)
+ public final Rectangle2D getBounds2D(Raster src)
{
return src.getBounds();
}
@@ -144,7 +144,7 @@ public class BandCombineOp implements RasterOp
* @see java.awt.image.RasterOp#getPoint2D(java.awt.geom.Point2D,
*java.awt.geom.Point2D)
*/
- public Point2D getPoint2D(Point2D src, Point2D dst)
+ public final Point2D getPoint2D(Point2D src, Point2D dst)
{
if (dst == null) return (Point2D)src.clone();
dst.setLocation(src);
@@ -154,13 +154,13 @@ public class BandCombineOp implements RasterOp
/* (non-Javadoc)
* @see java.awt.image.RasterOp#getRenderingHints()
*/
- public RenderingHints getRenderingHints()
+ public final RenderingHints getRenderingHints()
{
return hints;
}
/** Return the matrix for this Op. */
- public float[][] getMatrix()
+ public final float[][] getMatrix()
{
return matrix;
}
diff --git a/libjava/classpath/java/awt/image/ColorModel.java b/libjava/classpath/java/awt/image/ColorModel.java
index 1ced2a04366..40307f2b95d 100644
--- a/libjava/classpath/java/awt/image/ColorModel.java
+++ b/libjava/classpath/java/awt/image/ColorModel.java
@@ -452,8 +452,14 @@ public abstract class ColorModel implements Transparency
* This method is typically overriden in subclasses to provide a
* more efficient implementation.
*
- * @param array of transferType containing a single pixel. The
- * pixel should be encoded in the natural way of the color model.
+ * @param pixel an array of transferType containing a single pixel. The
+ * pixel should be encoded in the natural way of the color model. If
+ * this argument is not an array, as expected, a {@link ClassCastException}
+ * will be thrown.
+ * @param components an array that will be filled with the color component
+ * of the pixel. If this is null, a new array will be allocated
+ * @param offset index into the components array at which the result
+ * will be stored
*
* @return arrays of unnormalized component samples of single
* pixel. The scale and multiplication state of the samples are
@@ -521,8 +527,8 @@ public abstract class ColorModel implements Transparency
float[] normComponents,
int normOffset)
{
- // subclasses has to implement this method.
- throw new UnsupportedOperationException();
+ int[] components = getComponents(pixel, null, 0);
+ return getNormalizedComponents(components, 0, normComponents, normOffset);
}
/**
diff --git a/libjava/classpath/java/awt/image/ComponentSampleModel.java b/libjava/classpath/java/awt/image/ComponentSampleModel.java
index 5cf06e4a17f..b4e9450b060 100644
--- a/libjava/classpath/java/awt/image/ComponentSampleModel.java
+++ b/libjava/classpath/java/awt/image/ComponentSampleModel.java
@@ -1,4 +1,4 @@
-/* Copyright (C) 2000, 2002 Free Software Foundation
+/* Copyright (C) 2000, 2002, 2006, Free Software Foundation
This file is part of GNU Classpath.
@@ -38,6 +38,8 @@ package java.awt.image;
import gnu.java.awt.Buffers;
+import java.util.Arrays;
+
/* FIXME: This class does not yet support data type TYPE_SHORT */
/**
@@ -60,11 +62,14 @@ import gnu.java.awt.Buffers;
*/
public class ComponentSampleModel extends SampleModel
{
+ /** The offsets to the first sample for each band. */
protected int[] bandOffsets;
+
+ /** The indices of the bank used to store each band in a data buffer. */
protected int[] bankIndices;
/**
- * Number of bands in the image described.
+ * The number of bands in the image.
* @specnote This field shadows the protected numBands in SampleModel.
*/
protected int numBands;
@@ -72,42 +77,128 @@ public class ComponentSampleModel extends SampleModel
/** Used when creating data buffers. */
protected int numBanks;
+ /**
+ * The number of data elements between a sample in one row and the
+ * corresponding sample in the next row.
+ */
protected int scanlineStride;
+ /**
+ * The number of data elements between a sample for one pixel and the
+ * corresponding sample for the next pixel in the same row.
+ */
protected int pixelStride;
private boolean tightPixelPacking = false;
+ /**
+ * Creates a new sample model that assumes that all bands are stored in a
+ * single bank of the {@link DataBuffer}.
+ * <p>
+ * Note that the <code>bandOffsets</code> array is copied to internal storage
+ * to prevent subsequent changes to the array from affecting this object.
+ *
+ * @param dataType the data type (one of {@link DataBuffer#TYPE_BYTE},
+ * {@link DataBuffer#TYPE_USHORT}, {@link DataBuffer#TYPE_SHORT},
+ * {@link DataBuffer#TYPE_INT}, {@link DataBuffer#TYPE_FLOAT} or
+ * {@link DataBuffer#TYPE_DOUBLE}).
+ * @param w the width in pixels.
+ * @param h the height in pixels.
+ * @param pixelStride the number of data elements in the step from a sample
+ * in one pixel to the corresponding sample in the next pixel.
+ * @param scanlineStride the number of data elements in the step from a
+ * sample in a pixel to the corresponding sample in the pixel in the next
+ * row.
+ * @param bandOffsets the offset to the first element for each band, with
+ * the size of the array defining the number of bands (<code>null</code>
+ * not permitted).
+ *
+ * @throws IllegalArgumentException if <code>dataType</code> is not one of
+ * the specified values.
+ * @throws IllegalArgumentException if <code>w</code> is less than or equal
+ * to zero.
+ * @throws IllegalArgumentException if <code>h</code> is less than or equal
+ * to zero.
+ * @throws IllegalArgumentException if <code>w * h</code> exceeds
+ * {@link Integer#MAX_VALUE}.
+ * @throws IllegalArgumentException if <code>pixelStride</code> is negative.
+ * @throws IllegalArgumentException if <code>scanlineStride</code> is less
+ * than or equal to zero.
+ * @throws IllegalArgumentException if <code>bandOffsets</code> has zero
+ * length.
+ */
public ComponentSampleModel(int dataType,
- int w, int h,
- int pixelStride,
- int scanlineStride,
- int[] bandOffsets)
+ int w, int h,
+ int pixelStride,
+ int scanlineStride,
+ int[] bandOffsets)
{
this(dataType, w, h, pixelStride, scanlineStride,
- new int[bandOffsets.length], bandOffsets);
+ new int[bandOffsets.length], bandOffsets);
}
+ /**
+ * Creates a new sample model that assumes that all bands are stored in a
+ * single bank of the {@link DataBuffer}.
+ *
+ * @param dataType the data type (one of {@link DataBuffer#TYPE_BYTE},
+ * {@link DataBuffer#TYPE_USHORT}, {@link DataBuffer#TYPE_SHORT},
+ * {@link DataBuffer#TYPE_INT}, {@link DataBuffer#TYPE_FLOAT} or
+ * {@link DataBuffer#TYPE_DOUBLE}).
+ * @param w the width in pixels.
+ * @param h the height in pixels.
+ * @param pixelStride the number of data elements in the step from a sample
+ * in one pixel to the corresponding sample in the next pixel.
+ * @param scanlineStride the number of data elements in the step from a
+ * sample in a pixel to the corresponding sample in the pixel in the next
+ * row.
+ * @param bankIndices the index of the bank in which each band is stored
+ * (<code>null</code> not permitted). This array is copied to internal
+ * storage so that subsequent updates to the array do not affect the sample
+ * model.
+ * @param bandOffsets the offset to the first element for each band, with
+ * the size of the array defining the number of bands (<code>null</code>
+ * not permitted). This array is copied to internal storage so that
+ * subsequent updates to the array do not affect the sample model.
+ *
+ * @throws IllegalArgumentException if <code>dataType</code> is not one of
+ * the specified values.
+ * @throws IllegalArgumentException if <code>w</code> is less than or equal
+ * to zero.
+ * @throws IllegalArgumentException if <code>h</code> is less than or equal
+ * to zero.
+ * @throws IllegalArgumentException if <code>w * h</code> exceeds
+ * {@link Integer#MAX_VALUE}.
+ * @throws IllegalArgumentException if <code>pixelStride</code> is negative.
+ * @throws IllegalArgumentException if <code>scanlineStride</code> is less
+ * than or equal to zero.
+ * @throws IllegalArgumentException if <code>bandOffsets</code> has zero
+ * length.
+ */
public ComponentSampleModel(int dataType,
- int w, int h,
- int pixelStride,
- int scanlineStride,
- int[] bankIndices,
- int[] bandOffsets)
+ int w, int h,
+ int pixelStride,
+ int scanlineStride,
+ int[] bankIndices,
+ int[] bandOffsets)
{
super(dataType, w, h, bandOffsets.length);
- if ((pixelStride<0) || (scanlineStride<0) ||
- (bandOffsets.length<1) ||
- (bandOffsets.length != bankIndices.length))
+
+ // super permits DataBuffer.TYPE_UNDEFINED but this class doesn't...
+ if (dataType == DataBuffer.TYPE_UNDEFINED)
+ throw new IllegalArgumentException("Unsupported dataType.");
+
+ if ((pixelStride < 0) || (scanlineStride < 0) || (bandOffsets.length < 1)
+ || (bandOffsets.length != bankIndices.length))
throw new IllegalArgumentException();
- this.bandOffsets = bandOffsets;
- this.bankIndices = bankIndices;
+ this.bandOffsets = (int[]) bandOffsets.clone();
+ this.bankIndices = (int[]) bankIndices.clone();
this.numBands = bandOffsets.length;
this.numBanks = 0;
- for (int b=0; b<bankIndices.length; b++)
- this.numBanks = Math.max(this.numBanks, bankIndices[b]+1);
+ for (int b = 0; b < bankIndices.length; b++)
+ this.numBanks = Math.max(this.numBanks, bankIndices[b] + 1);
this.scanlineStride = scanlineStride;
this.pixelStride = pixelStride;
@@ -116,68 +207,122 @@ public class ComponentSampleModel extends SampleModel
/* FIXME: May these checks should be reserved for the
PixelInterleavedSampleModel? */
-
+
if (pixelStride == numBands)
{
- tightPixelPacking = true;
- for (int b=0; b<numBands; b++) {
- if ((bandOffsets[b] != b) || (bankIndices[b] !=0))
- {
- tightPixelPacking = false;
- break;
- }
- }
+ tightPixelPacking = true;
+ for (int b = 0; b < numBands; b++) {
+ if ((bandOffsets[b] != b) || (bankIndices[b] != 0))
+ {
+ tightPixelPacking = false;
+ break;
+ }
+ }
}
- }
-
+ }
+
+ /**
+ * Creates a new sample model that is compatible with this one, but with the
+ * specified dimensions.
+ *
+ * @param w the width (must be greater than zero).
+ * @param h the height (must be greater than zero).
+ *
+ * @return A new sample model.
+ */
public SampleModel createCompatibleSampleModel(int w, int h)
{
return new ComponentSampleModel(dataType, w, h, pixelStride,
- scanlineStride, bankIndices,
- bandOffsets);
+ scanlineStride, bankIndices,
+ bandOffsets);
}
+ /**
+ * Creates a new sample model that provides access to a subset of the bands
+ * that this sample model supports.
+ *
+ * @param bands the bands (<code>null</code> not permitted).
+ *
+ * @return The new sample model.
+ */
public SampleModel createSubsetSampleModel(int[] bands)
{
int numBands = bands.length;
int[] bankIndices = new int[numBands];
int[] bandOffsets = new int[numBands];
- for (int b=0; b<numBands; b++)
+ for (int b = 0; b < numBands; b++)
{
- bankIndices[b] = this.bankIndices[bands[b]];
- bandOffsets[b] = this.bandOffsets[bands[b]];
+ bankIndices[b] = this.bankIndices[bands[b]];
+ bandOffsets[b] = this.bandOffsets[bands[b]];
}
return new ComponentSampleModel(dataType, width, height, pixelStride,
- scanlineStride, bankIndices,
- bandOffsets);
+ scanlineStride, bankIndices,
+ bandOffsets);
}
+ /**
+ * Creates a new data buffer that is compatible with this sample model.
+ *
+ * @return The new data buffer.
+ */
public DataBuffer createDataBuffer()
{
// Maybe this value should be precalculated in the constructor?
int highestOffset = 0;
- for (int b=0; b<numBands; b++)
+ for (int b = 0; b < numBands; b++)
{
- highestOffset = Math.max(highestOffset, bandOffsets[b]);
+ highestOffset = Math.max(highestOffset, bandOffsets[b]);
}
- int size = pixelStride*(width-1) + scanlineStride*(height-1) +
- highestOffset + 1;
+ int size = pixelStride * (width - 1) + scanlineStride * (height - 1)
+ + highestOffset + 1;
return Buffers.createBuffer(getDataType(), size, numBanks);
}
+ /**
+ * Returns the offset of the sample in band 0 for the pixel at location
+ * <code>(x, y)</code>. This offset can be used to read a sample value from
+ * a {@link DataBuffer}.
+ *
+ * @param x the x-coordinate.
+ * @param y the y-coordinate.
+ *
+ * @return The offset.
+ *
+ * @see #getOffset(int, int, int)
+ */
public int getOffset(int x, int y)
{
return getOffset(x, y, 0);
}
+ /**
+ * Returns the offset of the sample in band <code>b</code> for the pixel at
+ * location <code>(x, y)</code>. This offset can be used to read a sample
+ * value from a {@link DataBuffer}.
+ *
+ * @param x the x-coordinate.
+ * @param y the y-coordinate.
+ * @param b the band index.
+ *
+ * @return The offset.
+ */
public int getOffset(int x, int y, int b)
{
- return bandOffsets[b] + pixelStride*x + scanlineStride*y;
+ return bandOffsets[b] + pixelStride * x + scanlineStride * y;
}
+ /**
+ * Returns the size in bits for each sample (one per band). For this sample
+ * model, each band has the same sample size and this is determined by the
+ * data type for the sample model.
+ *
+ * @return The sample sizes.
+ *
+ * @see SampleModel#getDataType()
+ */
public final int[] getSampleSize()
{
int size = DataBuffer.getDataTypeSize(getDataType());
@@ -187,39 +332,101 @@ public class ComponentSampleModel extends SampleModel
return sizes;
}
+ /**
+ * Returns the size in bits for the samples in the specified band. In this
+ * class, the sample size is the same for every band and is determined from
+ * the data type for the model.
+ *
+ * @param band the band index (ignored here).
+ *
+ * @return The sample size in bits.
+ *
+ * @see SampleModel#getDataType()
+ */
public final int getSampleSize(int band)
{
return DataBuffer.getDataTypeSize(getDataType());
}
+ /**
+ * Returns the indices of the bank(s) in the {@link DataBuffer} used to
+ * store the samples for each band. The returned array is a copy, so that
+ * altering it will not impact the sample model.
+ *
+ * @return The bank indices.
+ */
public final int[] getBankIndices()
{
- return bankIndices;
+ return (int[]) bankIndices.clone();
}
+ /**
+ * Returns the offsets to the first sample in each band. The returned array
+ * is a copy, so that altering it will not impact the sample model.
+ *
+ * @return The offsets.
+ */
public final int[] getBandOffsets()
{
- return bandOffsets;
+ return (int[]) bandOffsets.clone();
}
+ /**
+ * Returns the distance (in terms of element indices) between the sample for
+ * one pixel and the corresponding sample for the equivalent pixel in the
+ * next row. This is used in the calculation of the element offset for
+ * retrieving samples from a {@link DataBuffer}.
+ *
+ * @return The distance between pixel samples in consecutive rows.
+ */
public final int getScanlineStride()
{
return scanlineStride;
}
+ /**
+ * Returns the distance (in terms of element indices) between the sample for
+ * one pixel and the corresponding sample for the next pixel in a row. This
+ * is used in the calculation of the element offset for retrieving samples
+ * from a {@link DataBuffer}.
+ *
+ * @return The distance between pixel samples in the same row.
+ */
public final int getPixelStride()
{
return pixelStride;
}
+ /**
+ * Returns the number of data elements used to store the samples for one
+ * pixel. In this model, this is the same as the number of bands.
+ *
+ * @return The number of data elements used to store the samples for one
+ * pixel.
+ */
public final int getNumDataElements()
{
return numBands;
}
+ /**
+ * Returns the samples for the pixel at location <code>(x, y)</code> in
+ * a primitive array (the array type is determined by the data type for
+ * this model). The <code>obj</code> argument provides an option to supply
+ * an existing array to hold the result, if this is <code>null</code> a new
+ * array will be allocated.
+ *
+ * @param x the x-coordinate.
+ * @param y the y-coordinate.
+ * @param obj a primitive array that, if not <code>null</code>, will be
+ * used to store and return the sample values.
+ * @param data the data buffer (<code>null</code> not permitted).
+ *
+ * @return An array of sample values for the specified pixel.
+ */
public Object getDataElements(int x, int y, Object obj, DataBuffer data)
{
- int xyOffset = pixelStride*x + scanlineStride*y;
+ int xyOffset = pixelStride * x + scanlineStride * y;
int[] totalBandDataOffsets = new int[numBands];
@@ -235,124 +442,147 @@ public class ComponentSampleModel extends SampleModel
int[] bankOffsets = data.getOffsets();
- for (int b=0; b<numBands; b++)
+ for (int b = 0; b < numBands; b++)
{
- totalBandDataOffsets[b] =
- bandOffsets[b]+bankOffsets[bankIndices[b]] + xyOffset;
+ totalBandDataOffsets[b] = bandOffsets[b] + bankOffsets[bankIndices[b]]
+ + xyOffset;
}
-
+
try
{
- switch (getTransferType())
- {
- case DataBuffer.TYPE_BYTE:
- DataBufferByte inByte = (DataBufferByte) data;
- byte[] outByte = (byte[]) obj;
- if (outByte == null) outByte = new byte[numBands];
-
- for (int b=0; b<numBands; b++)
- {
- int dOffset = totalBandDataOffsets[b];
- outByte[b] = inByte.getData(bankIndices[b])[dOffset];
- }
- return outByte;
-
- case DataBuffer.TYPE_USHORT:
- DataBufferUShort inUShort = (DataBufferUShort) data;
- short[] outUShort = (short[]) obj;
- if (outUShort == null) outUShort = new short[numBands];
-
- for (int b=0; b<numBands; b++)
- {
- int dOffset = totalBandDataOffsets[b];
- outUShort[b] = inUShort.getData(bankIndices[b])[dOffset];
- }
- return outUShort;
-
- case DataBuffer.TYPE_SHORT:
- DataBufferShort inShort = (DataBufferShort) data;
- short[] outShort = (short[]) obj;
- if (outShort == null) outShort = new short[numBands];
-
- for (int b=0; b<numBands; b++)
- {
- int dOffset = totalBandDataOffsets[b];
- outShort[b] = inShort.getData(bankIndices[b])[dOffset];
- }
- return outShort;
-
- case DataBuffer.TYPE_INT:
- DataBufferInt inInt = (DataBufferInt) data;
- int[] outInt = (int[]) obj;
- if (outInt == null) outInt = new int[numBands];
-
- for (int b=0; b<numBands; b++)
- {
- int dOffset = totalBandDataOffsets[b];
- outInt[b] = inInt.getData(bankIndices[b])[dOffset];
- }
- return outInt;
-
- case DataBuffer.TYPE_FLOAT:
- DataBufferFloat inFloat = (DataBufferFloat) data;
- float[] outFloat = (float[]) obj;
- if (outFloat == null) outFloat = new float[numBands];
-
- for (int b=0; b<numBands; b++)
- {
- int dOffset = totalBandDataOffsets[b];
- outFloat[b] = inFloat.getData(bankIndices[b])[dOffset];
- }
- return outFloat;
-
- case DataBuffer.TYPE_DOUBLE:
- DataBufferDouble inDouble = (DataBufferDouble) data;
- double[] outDouble = (double[]) obj;
- if (outDouble == null) outDouble = new double[numBands];
-
- for (int b=0; b<numBands; b++)
- {
- int dOffset = totalBandDataOffsets[b];
- outDouble[b] = inDouble.getData(bankIndices[b])[dOffset];
- }
- return outDouble;
-
- default:
- throw new IllegalStateException("unknown transfer type " +
- getTransferType());
- }
+ switch (getTransferType())
+ {
+ case DataBuffer.TYPE_BYTE:
+ DataBufferByte inByte = (DataBufferByte) data;
+ byte[] outByte = (byte[]) obj;
+ if (outByte == null)
+ outByte = new byte[numBands];
+
+ for (int b = 0; b < numBands; b++)
+ {
+ int dOffset = totalBandDataOffsets[b];
+ outByte[b] = inByte.getData(bankIndices[b])[dOffset];
+ }
+ return outByte;
+
+ case DataBuffer.TYPE_USHORT:
+ DataBufferUShort inUShort = (DataBufferUShort) data;
+ short[] outUShort = (short[]) obj;
+ if (outUShort == null)
+ outUShort = new short[numBands];
+
+ for (int b = 0; b < numBands; b++)
+ {
+ int dOffset = totalBandDataOffsets[b];
+ outUShort[b] = inUShort.getData(bankIndices[b])[dOffset];
+ }
+ return outUShort;
+
+ case DataBuffer.TYPE_SHORT:
+ DataBufferShort inShort = (DataBufferShort) data;
+ short[] outShort = (short[]) obj;
+ if (outShort == null)
+ outShort = new short[numBands];
+
+ for (int b = 0; b < numBands; b++)
+ {
+ int dOffset = totalBandDataOffsets[b];
+ outShort[b] = inShort.getData(bankIndices[b])[dOffset];
+ }
+ return outShort;
+
+ case DataBuffer.TYPE_INT:
+ DataBufferInt inInt = (DataBufferInt) data;
+ int[] outInt = (int[]) obj;
+ if (outInt == null)
+ outInt = new int[numBands];
+
+ for (int b = 0; b < numBands; b++)
+ {
+ int dOffset = totalBandDataOffsets[b];
+ outInt[b] = inInt.getData(bankIndices[b])[dOffset];
+ }
+ return outInt;
+
+ case DataBuffer.TYPE_FLOAT:
+ DataBufferFloat inFloat = (DataBufferFloat) data;
+ float[] outFloat = (float[]) obj;
+ if (outFloat == null)
+ outFloat = new float[numBands];
+
+ for (int b = 0; b < numBands; b++)
+ {
+ int dOffset = totalBandDataOffsets[b];
+ outFloat[b] = inFloat.getData(bankIndices[b])[dOffset];
+ }
+ return outFloat;
+
+ case DataBuffer.TYPE_DOUBLE:
+ DataBufferDouble inDouble = (DataBufferDouble) data;
+ double[] outDouble = (double[]) obj;
+ if (outDouble == null)
+ outDouble = new double[numBands];
+
+ for (int b = 0; b < numBands; b++)
+ {
+ int dOffset = totalBandDataOffsets[b];
+ outDouble[b] = inDouble.getData(bankIndices[b])[dOffset];
+ }
+ return outDouble;
+
+ default:
+ throw new IllegalStateException("unknown transfer type "
+ + getTransferType());
+ }
}
catch (ArrayIndexOutOfBoundsException aioobe)
{
- String msg = "While reading data elements, " +
- "x=" + x + ", y=" + y +", " + ", xyOffset=" + xyOffset +
- ", data.getSize()=" + data.getSize() + ": " + aioobe;
- throw new ArrayIndexOutOfBoundsException(msg);
+ String msg = "While reading data elements, " +
+ "x=" + x + ", y=" + y +", " + ", xyOffset=" + xyOffset +
+ ", data.getSize()=" + data.getSize() + ": " + aioobe;
+ throw new ArrayIndexOutOfBoundsException(msg);
}
}
+ /**
+ * Returns the samples for the pixels in the region defined by
+ * <code>(x, y, w, h)</code> in a primitive array (the array type is
+ * determined by the data type for this model). The <code>obj</code>
+ * argument provides an option to supply an existing array to hold the
+ * result, if this is <code>null</code> a new array will be allocated.
+ *
+ * @param x the x-coordinate.
+ * @param y the y-coordinate.
+ * @param w the width.
+ * @param h the height.
+ * @param obj a primitive array that, if not <code>null</code>, will be
+ * used to store and return the sample values.
+ * @param data the data buffer (<code>null</code> not permitted).
+ *
+ * @return An array of sample values for the specified pixels.
+ *
+ * @see #setDataElements(int, int, int, int, Object, DataBuffer)
+ */
public Object getDataElements(int x, int y, int w, int h, Object obj,
- DataBuffer data)
+ DataBuffer data)
{
if (!tightPixelPacking)
{
- return super.getDataElements(x, y, w, h, obj, data);
+ return super.getDataElements(x, y, w, h, obj, data);
}
// using get speedup
// We can copy whole rows
- int rowSize = w*numBands;
- int dataSize = rowSize*h;
+ int rowSize = w * numBands;
+ int dataSize = rowSize * h;
- DataBuffer transferBuffer =
- Buffers.createBuffer(getTransferType(), obj, dataSize);
+ DataBuffer transferBuffer = Buffers.createBuffer(getTransferType(), obj,
+ dataSize);
obj = Buffers.getData(transferBuffer);
- int inOffset =
- pixelStride*x +
- scanlineStride*y +
- data.getOffset(); // Assumes only one band is used
+ int inOffset = pixelStride * x + scanlineStride * y + data.getOffset();
+ // Assumes only one band is used
/* We don't add band offsets since we assume that bands have
offsets 0, 1, 2, ... */
@@ -360,189 +590,345 @@ public class ComponentSampleModel extends SampleModel
// See if we can copy everything in one go
if (scanlineStride == rowSize)
{
- // Collapse scan lines:
- rowSize *= h;
- // We ignore scanlineStride since it won't be of any use
- h = 1;
+ // Collapse scan lines:
+ rowSize *= h;
+ // We ignore scanlineStride since it won't be of any use
+ h = 1;
}
int outOffset = 0;
Object inArray = Buffers.getData(data);
- for (int yd = 0; yd<h; yd++)
+ for (int yd = 0; yd < h; yd++)
{
- System.arraycopy(inArray, inOffset, obj, outOffset, rowSize);
- inOffset += scanlineStride;
- outOffset += rowSize;
+ System.arraycopy(inArray, inOffset, obj, outOffset, rowSize);
+ inOffset += scanlineStride;
+ outOffset += rowSize;
}
return obj;
}
+ /**
+ * Sets the samples for the pixels in the region defined by
+ * <code>(x, y, w, h)</code> from a supplied primitive array (the array type
+ * must be consistent with the data type for this model).
+ *
+ * @param x the x-coordinate.
+ * @param y the y-coordinate.
+ * @param w the width.
+ * @param h the height.
+ * @param obj a primitive array containing the sample values.
+ * @param data the data buffer (<code>null</code> not permitted).
+ *
+ * @see #getDataElements(int, int, int, int, Object, DataBuffer)
+ */
public void setDataElements(int x, int y, int w, int h,
- Object obj, DataBuffer data)
+ Object obj, DataBuffer data)
{
if (!tightPixelPacking)
{
- super.setDataElements(x, y, w, h, obj, data);
- return;
+ super.setDataElements(x, y, w, h, obj, data);
+ return;
}
// using set speedup, we can copy whole rows
- int rowSize = w*numBands;
- int dataSize = rowSize*h;
+ int rowSize = w * numBands;
+ int dataSize = rowSize * h;
- DataBuffer transferBuffer =
- Buffers.createBufferFromData(getTransferType(), obj, dataSize);
+ DataBuffer transferBuffer
+ = Buffers.createBufferFromData(getTransferType(), obj, dataSize);
int[] bankOffsets = data.getOffsets();
- int outOffset =
- pixelStride*x +
- scanlineStride*y +
- bankOffsets[0]; // same assuptions as in get...
+ int outOffset = pixelStride * x + scanlineStride * y + bankOffsets[0];
+ // same assumptions as in get...
// See if we can copy everything in one go
if (scanlineStride == rowSize)
{
- // Collapse scan lines:
- rowSize *= h;
- h = 1;
+ // Collapse scan lines:
+ rowSize *= h;
+ h = 1;
}
int inOffset = 0;
Object outArray = Buffers.getData(data);
- for (int yd = 0; yd<h; yd++)
+ for (int yd = 0; yd < h; yd++)
{
- System.arraycopy(obj, inOffset, outArray, outOffset, rowSize);
- outOffset += scanlineStride;
- inOffset += rowSize;
+ System.arraycopy(obj, inOffset, outArray, outOffset, rowSize);
+ outOffset += scanlineStride;
+ inOffset += rowSize;
}
}
+ /**
+ * Returns all the samples for the pixel at location <code>(x, y)</code>
+ * stored in the specified data buffer.
+ *
+ * @param x the x-coordinate.
+ * @param y the y-coordinate.
+ * @param iArray an array that will be populated with the sample values and
+ * returned as the result. The size of this array should be equal to the
+ * number of bands in the model. If the array is <code>null</code>, a new
+ * array is created.
+ * @param data the data buffer (<code>null</code> not permitted).
+ *
+ * @return The samples for the specified pixel.
+ *
+ * @see #setPixel(int, int, int[], DataBuffer)
+ */
public int[] getPixel(int x, int y, int[] iArray, DataBuffer data)
{
- int offset = pixelStride*x + scanlineStride*y;
- if (iArray == null) iArray = new int[numBands];
- for (int b=0; b<numBands; b++)
+ int offset = pixelStride * x + scanlineStride * y;
+ if (iArray == null)
+ iArray = new int[numBands];
+ for (int b = 0; b < numBands; b++)
{
- iArray[b] = data.getElem(bankIndices[b], offset+bandOffsets[b]);
+ iArray[b] = data.getElem(bankIndices[b], offset + bandOffsets[b]);
}
return iArray;
}
+ /**
+ * Returns the samples for all the pixels in a rectangular region.
+ *
+ * @param x the x-coordinate.
+ * @param y the y-coordinate.
+ * @param w the width.
+ * @param h the height.
+ * @param iArray an array that if non-<code>null</code> will be populated
+ * with the sample values and returned as the result.
+ * @param data the data buffer (<code>null</code> not permitted).
+ *
+ * @return The samples for all the pixels in the rectangle.
+ */
public int[] getPixels(int x, int y, int w, int h, int[] iArray,
- DataBuffer data)
+ DataBuffer data)
{
- int offset = pixelStride*x + scanlineStride*y;
- if (iArray == null) iArray = new int[numBands*w*h];
+ int offset = pixelStride * x + scanlineStride * y;
+ if (iArray == null)
+ iArray = new int[numBands * w * h];
int outOffset = 0;
- for (y=0; y<h; y++)
+ for (y = 0; y < h; y++)
{
- int lineOffset = offset;
- for (x=0; x<w; x++)
- {
- for (int b=0; b<numBands; b++)
- {
- iArray[outOffset++] =
- data.getElem(bankIndices[b], lineOffset+bandOffsets[b]);
- }
- lineOffset += pixelStride;
- }
- offset += scanlineStride;
+ int lineOffset = offset;
+ for (x = 0; x < w; x++)
+ {
+ for (int b = 0; b < numBands; b++)
+ {
+ iArray[outOffset++]
+ = data.getElem(bankIndices[b], lineOffset+bandOffsets[b]);
+ }
+ lineOffset += pixelStride;
+ }
+ offset += scanlineStride;
}
return iArray;
}
-
+
+ /**
+ * Returns the sample for band <code>b</code> of the pixel at
+ * <code>(x, y)</code> that is stored in the specified data buffer.
+ *
+ * @param x the x-coordinate.
+ * @param y the y-coordinate.
+ * @param b the band index.
+ * @param data the data buffer (<code>null</code> not permitted).
+ *
+ * @return The sample value.
+ *
+ * @see #setSample(int, int, int, int, DataBuffer)
+ */
public int getSample(int x, int y, int b, DataBuffer data)
{
return data.getElem(bankIndices[b], getOffset(x, y, b));
}
+ /**
+ * Sets the samples for the pixel at location <code>(x, y)</code> from the
+ * supplied primitive array (the array type must be consistent with the data
+ * type for this model).
+ *
+ * @param x the x-coordinate.
+ * @param y the y-coordinate.
+ * @param obj a primitive array containing the pixel's sample values.
+ * @param data the data buffer (<code>null</code> not permitted).
+ *
+ * @see #setDataElements(int, int, Object, DataBuffer)
+ */
public void setDataElements(int x, int y, Object obj, DataBuffer data)
{
- int offset = pixelStride*x + scanlineStride*y;
+ int offset = pixelStride * x + scanlineStride * y;
int[] totalBandDataOffsets = new int[numBands];
int[] bankOffsets = data.getOffsets();
- for (int b=0; b<numBands; b++)
- totalBandDataOffsets[b] =
- bandOffsets[b]+bankOffsets[bankIndices[b]] + offset;
+ for (int b = 0; b < numBands; b++)
+ totalBandDataOffsets[b] = bandOffsets[b] + bankOffsets[bankIndices[b]]
+ + offset;
switch (getTransferType())
{
case DataBuffer.TYPE_BYTE:
- {
- DataBufferByte out = (DataBufferByte) data;
- byte[] in = (byte[]) obj;
-
- for (int b=0; b<numBands; b++)
- out.getData(bankIndices[b])[totalBandDataOffsets[b]] = in[b];
-
- return;
- }
+ {
+ DataBufferByte out = (DataBufferByte) data;
+ byte[] in = (byte[]) obj;
+
+ for (int b = 0; b < numBands; b++)
+ out.getData(bankIndices[b])[totalBandDataOffsets[b]] = in[b];
+
+ return;
+ }
case DataBuffer.TYPE_USHORT:
- {
- DataBufferUShort out = (DataBufferUShort) data;
- short[] in = (short[]) obj;
-
- for (int b=0; b<numBands; b++)
- out.getData(bankIndices[b])[totalBandDataOffsets[b]] = in[b];
-
- return;
- }
+ {
+ DataBufferUShort out = (DataBufferUShort) data;
+ short[] in = (short[]) obj;
+
+ for (int b = 0; b < numBands; b++)
+ out.getData(bankIndices[b])[totalBandDataOffsets[b]] = in[b];
+
+ return;
+ }
case DataBuffer.TYPE_SHORT:
- {
- DataBufferShort out = (DataBufferShort) data;
- short[] in = (short[]) obj;
-
- for (int b=0; b<numBands; b++)
- out.getData(bankIndices[b])[totalBandDataOffsets[b]] = in[b];
-
- return;
- }
+ {
+ DataBufferShort out = (DataBufferShort) data;
+ short[] in = (short[]) obj;
+
+ for (int b = 0; b < numBands; b++)
+ out.getData(bankIndices[b])[totalBandDataOffsets[b]] = in[b];
+
+ return;
+ }
case DataBuffer.TYPE_INT:
- {
- DataBufferInt out = (DataBufferInt) data;
- int[] in = (int[]) obj;
-
- for (int b=0; b<numBands; b++)
- out.getData(bankIndices[b])[totalBandDataOffsets[b]] = in[b];
-
- return;
- }
+ {
+ DataBufferInt out = (DataBufferInt) data;
+ int[] in = (int[]) obj;
+
+ for (int b = 0; b < numBands; b++)
+ out.getData(bankIndices[b])[totalBandDataOffsets[b]] = in[b];
+
+ return;
+ }
case DataBuffer.TYPE_FLOAT:
- {
- DataBufferFloat out = (DataBufferFloat) data;
- float[] in = (float[]) obj;
-
- for (int b=0; b<numBands; b++)
- out.getData(bankIndices[b])[totalBandDataOffsets[b]] = in[b];
-
- return;
- }
+ {
+ DataBufferFloat out = (DataBufferFloat) data;
+ float[] in = (float[]) obj;
+
+ for (int b = 0; b < numBands; b++)
+ out.getData(bankIndices[b])[totalBandDataOffsets[b]] = in[b];
+
+ return;
+ }
case DataBuffer.TYPE_DOUBLE:
- {
- DataBufferDouble out = (DataBufferDouble) data;
- double[] in = (double[]) obj;
-
- for (int b=0; b<numBands; b++)
- out.getData(bankIndices[b])[totalBandDataOffsets[b]] = in[b];
-
- return;
- }
+ {
+ DataBufferDouble out = (DataBufferDouble) data;
+ double[] in = (double[]) obj;
+
+ for (int b = 0; b < numBands; b++)
+ out.getData(bankIndices[b])[totalBandDataOffsets[b]] = in[b];
+
+ return;
+ }
default:
- throw new UnsupportedOperationException("transfer type not " +
- "implemented");
+ throw new UnsupportedOperationException("transfer type not " +
+ "implemented");
}
}
+ /**
+ * Sets the sample values for the pixel at location <code>(x, y)</code>
+ * stored in the specified data buffer.
+ *
+ * @param x the x-coordinate.
+ * @param y the y-coordinate.
+ * @param iArray the pixel sample values (<code>null</code> not permitted).
+ * @param data the data buffer (<code>null</code> not permitted).
+ *
+ * @see #getPixel(int, int, int[], DataBuffer)
+ */
public void setPixel(int x, int y, int[] iArray, DataBuffer data)
{
- int offset = pixelStride*x + scanlineStride*y;
- for (int b=0; b<numBands; b++)
- data.setElem(bankIndices[b], offset+bandOffsets[b], iArray[b]);
+ int offset = pixelStride * x + scanlineStride * y;
+ for (int b = 0; b < numBands; b++)
+ data.setElem(bankIndices[b], offset + bandOffsets[b], iArray[b]);
}
+ /**
+ * Sets the sample value for band <code>b</code> of the pixel at location
+ * <code>(x, y)</code> in the specified data buffer.
+ *
+ * @param x the x-coordinate.
+ * @param y the y-coordinate.
+ * @param b the band index.
+ * @param s the sample value.
+ * @param data the data buffer (<code>null</code> not permitted).
+ *
+ * @see #getSample(int, int, int, DataBuffer)
+ */
public void setSample(int x, int y, int b, int s, DataBuffer data)
{
data.setElem(bankIndices[b], getOffset(x, y, b), s);
}
+
+ /**
+ * Tests this sample model for equality with an arbitrary object. Returns
+ * <code>true</code> if and only if:
+ * <ul>
+ * <li><code>obj</code> is not <code>null</code>;</li>
+ * <li><code>obj</code> is an instance of <code>ComponentSampleModel</code>;
+ * </li>
+ * <li>both models have the same values for the <code>dataType</code>,
+ * <code>width</code>, <code>height</code>, <code>pixelStride</code>,
+ * <code>scanlineStride</code>, <code>bandOffsets</code> and
+ * <code>bankIndices</code> fields.</li>
+ * </ul>
+ *
+ * @param obj the object to test (<code>null</code> permitted).
+ *
+ * @return <code>true</code> if this sample model is equal to
+ * <code>obj</code>, and <code>false</code> otherwise.
+ */
+ public boolean equals(Object obj)
+ {
+ if (obj == null)
+ return false;
+ if (! (obj instanceof ComponentSampleModel))
+ return false;
+ ComponentSampleModel that = (ComponentSampleModel) obj;
+ if (this.dataType != that.dataType)
+ return false;
+ if (this.width != that.width)
+ return false;
+ if (this.height != that.height)
+ return false;
+ if (this.pixelStride != that.pixelStride)
+ return false;
+ if (this.scanlineStride != that.scanlineStride)
+ return false;
+ if (! Arrays.equals(this.bandOffsets, that.bandOffsets))
+ return false;
+ if (! Arrays.equals(this.bankIndices, that.bankIndices))
+ return false;
+ // couldn't find any difference, so...
+ return true;
+ }
+
+ /**
+ * Returns a hash code for this sample model.
+ *
+ * @return The hash code.
+ */
+ public int hashCode()
+ {
+ // this computation is based on the method described in Chapter 3
+ // of Joshua Bloch's Effective Java...
+ int result = 17;
+ result = 37 * result + dataType;
+ result = 37 * result + width;
+ result = 37 * result + height;
+ result = 37 * result + pixelStride;
+ result = 37 * result + scanlineStride;
+ for (int i = 0; i < bandOffsets.length; i++)
+ result = 37 * result + bandOffsets[i];
+ for (int i = 0; i < bankIndices.length; i++)
+ result = 37 * result + bankIndices[i];
+ return result;
+ }
}
diff --git a/libjava/classpath/java/awt/image/ConvolveOp.java b/libjava/classpath/java/awt/image/ConvolveOp.java
index 49ca2a6ea77..1f73f75b233 100644
--- a/libjava/classpath/java/awt/image/ConvolveOp.java
+++ b/libjava/classpath/java/awt/image/ConvolveOp.java
@@ -110,7 +110,7 @@ public class ConvolveOp implements BufferedImageOp, RasterOp
* @see java.awt.image.BufferedImageOp#filter(java.awt.image.BufferedImage,
* java.awt.image.BufferedImage)
*/
- public BufferedImage filter(BufferedImage src, BufferedImage dst)
+ public final BufferedImage filter(BufferedImage src, BufferedImage dst)
{
if (src == dst)
throw new IllegalArgumentException();
@@ -163,7 +163,7 @@ public class ConvolveOp implements BufferedImageOp, RasterOp
/* (non-Javadoc)
* @see java.awt.image.RasterOp#getRenderingHints()
*/
- public RenderingHints getRenderingHints()
+ public final RenderingHints getRenderingHints()
{
return hints;
}
@@ -181,7 +181,7 @@ public class ConvolveOp implements BufferedImageOp, RasterOp
*
* @return The convolution kernel.
*/
- public Kernel getKernel()
+ public final Kernel getKernel()
{
return (Kernel) kernel.clone();
}
@@ -190,7 +190,7 @@ public class ConvolveOp implements BufferedImageOp, RasterOp
* @see java.awt.image.RasterOp#filter(java.awt.image.Raster,
* java.awt.image.WritableRaster)
*/
- public WritableRaster filter(Raster src, WritableRaster dest) {
+ public final WritableRaster filter(Raster src, WritableRaster dest) {
if (src == dest)
throw new IllegalArgumentException();
if (src.getWidth() < kernel.getWidth() ||
@@ -309,7 +309,7 @@ public class ConvolveOp implements BufferedImageOp, RasterOp
/* (non-Javadoc)
* @see java.awt.image.BufferedImageOp#getBounds2D(java.awt.image.BufferedImage)
*/
- public Rectangle2D getBounds2D(BufferedImage src)
+ public final Rectangle2D getBounds2D(BufferedImage src)
{
return src.getRaster().getBounds();
}
@@ -317,7 +317,7 @@ public class ConvolveOp implements BufferedImageOp, RasterOp
/* (non-Javadoc)
* @see java.awt.image.RasterOp#getBounds2D(java.awt.image.Raster)
*/
- public Rectangle2D getBounds2D(Raster src)
+ public final Rectangle2D getBounds2D(Raster src)
{
return src.getBounds();
}
@@ -330,7 +330,7 @@ public class ConvolveOp implements BufferedImageOp, RasterOp
* @see java.awt.image.RasterOp#getPoint2D(java.awt.geom.Point2D,
* java.awt.geom.Point2D)
*/
- public Point2D getPoint2D(Point2D src, Point2D dst)
+ public final Point2D getPoint2D(Point2D src, Point2D dst)
{
if (dst == null) return (Point2D)src.clone();
dst.setLocation(src);
diff --git a/libjava/classpath/java/awt/image/DirectColorModel.java b/libjava/classpath/java/awt/image/DirectColorModel.java
index 4f371517818..579dc97dfc7 100644
--- a/libjava/classpath/java/awt/image/DirectColorModel.java
+++ b/libjava/classpath/java/awt/image/DirectColorModel.java
@@ -167,7 +167,7 @@ public class DirectColorModel extends PackedColorModel
private int extractAndNormalizeSample(int pixel, int component)
{
int value = extractAndScaleSample(pixel, component);
- if (hasAlpha() && isAlphaPremultiplied())
+ if (hasAlpha() && isAlphaPremultiplied() && getAlpha(pixel) != 0)
value = value*255/getAlpha(pixel);
return value;
}
diff --git a/libjava/classpath/java/awt/image/LookupOp.java b/libjava/classpath/java/awt/image/LookupOp.java
index f131daabae3..46e72fe6183 100644
--- a/libjava/classpath/java/awt/image/LookupOp.java
+++ b/libjava/classpath/java/awt/image/LookupOp.java
@@ -81,7 +81,7 @@ public class LookupOp implements BufferedImageOp, RasterOp
/* (non-Javadoc)
* @see java.awt.image.BufferedImageOp#filter(java.awt.image.BufferedImage, java.awt.image.BufferedImage)
*/
- public BufferedImage filter(BufferedImage src, BufferedImage dst)
+ public final BufferedImage filter(BufferedImage src, BufferedImage dst)
{
if (src.getColorModel() instanceof IndexColorModel)
throw new IllegalArgumentException("LookupOp.filter: IndexColorModel "
@@ -149,7 +149,7 @@ public class LookupOp implements BufferedImageOp, RasterOp
/* (non-Javadoc)
* @see java.awt.image.BufferedImageOp#getBounds2D(java.awt.image.BufferedImage)
*/
- public Rectangle2D getBounds2D(BufferedImage src)
+ public final Rectangle2D getBounds2D(BufferedImage src)
{
return src.getRaster().getBounds();
}
@@ -173,7 +173,7 @@ public class LookupOp implements BufferedImageOp, RasterOp
* @param dst The destination point.
* @see java.awt.image.RasterOp#getPoint2D(java.awt.geom.Point2D, java.awt.geom.Point2D)
*/
- public Point2D getPoint2D(Point2D src, Point2D dst)
+ public final Point2D getPoint2D(Point2D src, Point2D dst)
{
if (dst == null)
return (Point2D) src.clone();
@@ -183,7 +183,7 @@ public class LookupOp implements BufferedImageOp, RasterOp
}
/** Return the LookupTable for this op. */
- public LookupTable getTable()
+ public final LookupTable getTable()
{
return lut;
}
@@ -191,7 +191,7 @@ public class LookupOp implements BufferedImageOp, RasterOp
/* (non-Javadoc)
* @see java.awt.image.RasterOp#getRenderingHints()
*/
- public RenderingHints getRenderingHints()
+ public final RenderingHints getRenderingHints()
{
return hints;
}
@@ -209,7 +209,7 @@ public class LookupOp implements BufferedImageOp, RasterOp
* component but not the same as src and dest.
* @see java.awt.image.RasterOp#filter(java.awt.image.Raster, java.awt.image.WritableRaster)
*/
- public WritableRaster filter(Raster src, WritableRaster dest)
+ public final WritableRaster filter(Raster src, WritableRaster dest)
{
if (dest == null)
// Allocate a raster if needed
@@ -236,7 +236,7 @@ public class LookupOp implements BufferedImageOp, RasterOp
/* (non-Javadoc)
* @see java.awt.image.RasterOp#getBounds2D(java.awt.image.Raster)
*/
- public Rectangle2D getBounds2D(Raster src)
+ public final Rectangle2D getBounds2D(Raster src)
{
return src.getBounds();
}
diff --git a/libjava/classpath/java/awt/image/ReplicateScaleFilter.java b/libjava/classpath/java/awt/image/ReplicateScaleFilter.java
index d76f9db4b5e..6d5099dead2 100644
--- a/libjava/classpath/java/awt/image/ReplicateScaleFilter.java
+++ b/libjava/classpath/java/awt/image/ReplicateScaleFilter.java
@@ -46,7 +46,6 @@ import java.util.Hashtable;
* exact method is not defined by Sun but some sort of fast Box filter should
* probably be correct.
* <br>
- * Currently this filter does nothing and needs to be implemented.
*
* @author C. Brian Jones (cbj@gnu.org)
*/
diff --git a/libjava/classpath/java/awt/image/RescaleOp.java b/libjava/classpath/java/awt/image/RescaleOp.java
index 35b42f79ccd..d5b29693caf 100644
--- a/libjava/classpath/java/awt/image/RescaleOp.java
+++ b/libjava/classpath/java/awt/image/RescaleOp.java
@@ -93,7 +93,7 @@ public class RescaleOp implements BufferedImageOp, RasterOp
/* (non-Javadoc)
* @see java.awt.image.BufferedImageOp#getRenderingHints()
*/
- public RenderingHints getRenderingHints()
+ public final RenderingHints getRenderingHints()
{
return hints;
}
diff --git a/libjava/classpath/java/awt/image/SampleModel.java b/libjava/classpath/java/awt/image/SampleModel.java
index 1159662223c..6e3fd4069a3 100644
--- a/libjava/classpath/java/awt/image/SampleModel.java
+++ b/libjava/classpath/java/awt/image/SampleModel.java
@@ -1,4 +1,4 @@
-/* Copyright (C) 2000, 2001, 2002, 2005 Free Software Foundation
+/* Copyright (C) 2000, 2001, 2002, 2005, 2006, Free Software Foundation
This file is part of GNU Classpath.
@@ -57,15 +57,43 @@ public abstract class SampleModel
*/
protected int dataType;
+ /**
+ * Creates a new sample model with the specified attributes.
+ *
+ * @param dataType the data type (one of {@link DataBuffer#TYPE_BYTE},
+ * {@link DataBuffer#TYPE_USHORT}, {@link DataBuffer#TYPE_SHORT},
+ * {@link DataBuffer#TYPE_INT}, {@link DataBuffer#TYPE_FLOAT},
+ * {@link DataBuffer#TYPE_DOUBLE} or {@link DataBuffer#TYPE_UNDEFINED}).
+ * @param w the width in pixels (must be greater than zero).
+ * @param h the height in pixels (must be greater than zero).
+ * @param numBands the number of bands (must be greater than zero).
+ *
+ * @throws IllegalArgumentException if <code>dataType</code> is not one of
+ * the listed values.
+ * @throws IllegalArgumentException if <code>w</code> is less than or equal
+ * to zero.
+ * @throws IllegalArgumentException if <code>h</code> is less than or equal
+ * to zero.
+ * @throws IllegalArgumentException if <code>w * h</code> is greater than
+ * {@link Integer#MAX_VALUE}.
+ */
public SampleModel(int dataType, int w, int h, int numBands)
{
+ if (dataType != DataBuffer.TYPE_UNDEFINED)
+ if (dataType < DataBuffer.TYPE_BYTE || dataType > DataBuffer.TYPE_DOUBLE)
+ throw new IllegalArgumentException("Unrecognised 'dataType' argument.");
+
if ((w <= 0) || (h <= 0))
throw new IllegalArgumentException((w <= 0 ? " width<=0" : " width is ok")
- +(h <= 0 ? " height<=0" : " height is ok"));
-
- // FIXME: How can an int be greater than Integer.MAX_VALUE?
- // FIXME: How do we identify an unsupported data type?
-
+ + (h <= 0 ? " height<=0" : " height is ok"));
+
+ long area = (long) w * (long) h;
+ if (area > Integer.MAX_VALUE)
+ throw new IllegalArgumentException("w * h exceeds Integer.MAX_VALUE.");
+
+ if (numBands <= 0)
+ throw new IllegalArgumentException("Requires numBands > 0.");
+
this.dataType = dataType;
this.width = w;
this.height = h;
@@ -102,8 +130,10 @@ public abstract class SampleModel
public int[] getPixel(int x, int y, int[] iArray, DataBuffer data)
{
- if (iArray == null) iArray = new int[numBands];
- for (int b=0; b<numBands; b++) iArray[b] = getSample(x, y, b, data);
+ if (iArray == null)
+ iArray = new int[numBands];
+ for (int b = 0; b < numBands; b++)
+ iArray[b] = getSample(x, y, b, data);
return iArray;
}
@@ -121,94 +151,95 @@ public abstract class SampleModel
* DataBuffer.TYPE_USHORT, then a short[] object is returned.
*/
public abstract Object getDataElements(int x, int y, Object obj,
- DataBuffer data);
+ DataBuffer data);
public Object getDataElements(int x, int y, int w, int h, Object obj,
- DataBuffer data)
+ DataBuffer data)
{
- int size = w*h;
+ int size = w * h;
int numDataElements = getNumDataElements();
- int dataSize = numDataElements*size;
+ int dataSize = numDataElements * size;
if (obj == null)
{
- switch (getTransferType())
- {
- case DataBuffer.TYPE_BYTE:
- obj = new byte[dataSize];
- break;
- case DataBuffer.TYPE_USHORT:
- obj = new short[dataSize];
- break;
- case DataBuffer.TYPE_INT:
- obj = new int[dataSize];
- break;
- default:
- // Seems like the only sensible thing to do.
- throw new ClassCastException();
- }
+ switch (getTransferType())
+ {
+ case DataBuffer.TYPE_BYTE:
+ obj = new byte[dataSize];
+ break;
+ case DataBuffer.TYPE_USHORT:
+ obj = new short[dataSize];
+ break;
+ case DataBuffer.TYPE_INT:
+ obj = new int[dataSize];
+ break;
+ default:
+ // Seems like the only sensible thing to do.
+ throw new ClassCastException();
+ }
}
Object pixelData = null;
int outOffset = 0;
- for (int yy = y; yy<(y+h); yy++)
+ for (int yy = y; yy < (y + h); yy++)
{
- for (int xx = x; xx<(x+w); xx++)
- {
- pixelData = getDataElements(xx, yy, pixelData, data);
- System.arraycopy(pixelData, 0, obj, outOffset,
- numDataElements);
- outOffset += numDataElements;
- }
+ for (int xx = x; xx < (x + w); xx++)
+ {
+ pixelData = getDataElements(xx, yy, pixelData, data);
+ System.arraycopy(pixelData, 0, obj, outOffset,
+ numDataElements);
+ outOffset += numDataElements;
+ }
}
return obj;
}
public abstract void setDataElements(int x, int y, Object obj,
- DataBuffer data);
+ DataBuffer data);
public void setDataElements(int x, int y, int w, int h,
- Object obj, DataBuffer data)
+ Object obj, DataBuffer data)
{
- int size = w*h;
+ int size = w * h;
int numDataElements = getNumDataElements();
- int dataSize = numDataElements*size;
+ int dataSize = numDataElements * size;
Object pixelData;
switch (getTransferType())
{
case DataBuffer.TYPE_BYTE:
- pixelData = new byte[numDataElements];
- break;
+ pixelData = new byte[numDataElements];
+ break;
case DataBuffer.TYPE_USHORT:
- pixelData = new short[numDataElements];
- break;
+ pixelData = new short[numDataElements];
+ break;
case DataBuffer.TYPE_INT:
- pixelData = new int[numDataElements];
- break;
+ pixelData = new int[numDataElements];
+ break;
default:
- // Seems like the only sensible thing to do.
- throw new ClassCastException();
+ // Seems like the only sensible thing to do.
+ throw new ClassCastException();
}
int inOffset = 0;
- for (int yy=y; yy<(y+h); yy++)
+ for (int yy = y; yy < (y + h); yy++)
{
- for (int xx=x; xx<(x+w); xx++)
- {
- System.arraycopy(obj, inOffset, pixelData, 0,
- numDataElements);
- setDataElements(xx, yy, pixelData, data);
- inOffset += numDataElements;
- }
+ for (int xx = x; xx < (x + w); xx++)
+ {
+ System.arraycopy(obj, inOffset, pixelData, 0,
+ numDataElements);
+ setDataElements(xx, yy, pixelData, data);
+ inOffset += numDataElements;
+ }
}
}
public float[] getPixel(int x, int y, float[] fArray, DataBuffer data)
{
- if (fArray == null) fArray = new float[numBands];
+ if (fArray == null)
+ fArray = new float[numBands];
- for (int b=0; b<numBands; b++)
+ for (int b = 0; b < numBands; b++)
{
fArray[b] = getSampleFloat(x, y, b, data);
}
@@ -216,10 +247,11 @@ public abstract class SampleModel
}
public double[] getPixel(int x, int y, double[] dArray, DataBuffer data) {
- if (dArray == null) dArray = new double[numBands];
- for (int b=0; b<numBands; b++)
+ if (dArray == null)
+ dArray = new double[numBands];
+ for (int b = 0; b < numBands; b++)
{
- dArray[b] = getSampleDouble(x, y, b, data);
+ dArray[b] = getSampleDouble(x, y, b, data);
}
return dArray;
}
@@ -227,20 +259,21 @@ public abstract class SampleModel
/* FIXME: Should it return a banded or pixel interleaved array of
samples? (Assume interleaved.) */
public int[] getPixels(int x, int y, int w, int h, int[] iArray,
- DataBuffer data)
+ DataBuffer data)
{
- int size = w*h;
+ int size = w * h;
int outOffset = 0;
int[] pixel = null;
- if (iArray == null) iArray = new int[w*h*numBands];
- for (int yy=y; yy<(y+h); yy++)
+ if (iArray == null)
+ iArray = new int[w * h * numBands];
+ for (int yy = y; yy < (y + h); yy++)
{
- for (int xx=x; xx<(x+w); xx++)
- {
- pixel = getPixel(xx, yy, pixel, data);
- System.arraycopy(pixel, 0, iArray, outOffset, numBands);
- outOffset += numBands;
- }
+ for (int xx = x; xx < (x + w); xx++)
+ {
+ pixel = getPixel(xx, yy, pixel, data);
+ System.arraycopy(pixel, 0, iArray, outOffset, numBands);
+ outOffset += numBands;
+ }
}
return iArray;
}
@@ -248,20 +281,20 @@ public abstract class SampleModel
/* FIXME: Should it return a banded or pixel interleaved array of
samples? (Assume interleaved.) */
public float[] getPixels(int x, int y, int w, int h, float[] fArray,
- DataBuffer data)
+ DataBuffer data)
{
- int size = w*h;
+ int size = w * h;
int outOffset = 0;
float[] pixel = null;
- if (fArray == null) fArray = new float[w*h*numBands];
- for (int yy=y; yy<(y+h); yy++)
+ if (fArray == null) fArray = new float[w * h * numBands];
+ for (int yy = y; yy < (y + h); yy++)
{
- for (int xx=x; xx<(x+w); xx++)
- {
- pixel = getPixel(xx, yy, pixel, data);
- System.arraycopy(pixel, 0, fArray, outOffset, numBands);
- outOffset += numBands;
- }
+ for (int xx = x; xx < (x + w); xx++)
+ {
+ pixel = getPixel(xx, yy, pixel, data);
+ System.arraycopy(pixel, 0, fArray, outOffset, numBands);
+ outOffset += numBands;
+ }
}
return fArray;
}
@@ -269,20 +302,21 @@ public abstract class SampleModel
/* FIXME: Should it return a banded or pixel interleaved array of
samples? (Assume interleaved.) */
public double[] getPixels(int x, int y, int w, int h, double[] dArray,
- DataBuffer data)
+ DataBuffer data)
{
- int size = w*h;
+ int size = w * h;
int outOffset = 0;
double[] pixel = null;
- if (dArray == null) dArray = new double[w*h*numBands];
- for (int yy=y; yy<(y+h); yy++)
+ if (dArray == null)
+ dArray = new double[w * h * numBands];
+ for (int yy = y; yy < (y + h); yy++)
{
- for (int xx=x; xx<(x+w); xx++)
- {
- pixel = getPixel(xx, yy, pixel, data);
- System.arraycopy(pixel, 0, dArray, outOffset, numBands);
- outOffset += numBands;
- }
+ for (int xx = x; xx < (x + w); xx++)
+ {
+ pixel = getPixel(xx, yy, pixel, data);
+ System.arraycopy(pixel, 0, dArray, outOffset, numBands);
+ outOffset += numBands;
+ }
}
return dArray;
}
@@ -300,179 +334,185 @@ public abstract class SampleModel
}
public int[] getSamples(int x, int y, int w, int h, int b,
- int[] iArray, DataBuffer data)
+ int[] iArray, DataBuffer data)
{
- int size = w*h;
+ int size = w * h;
int outOffset = 0;
- if (iArray == null) iArray = new int[size];
- for (int yy=y; yy<(y+h); yy++)
+ if (iArray == null)
+ iArray = new int[size];
+ for (int yy = y; yy < (y + h); yy++)
{
- for (int xx=x; xx<(x+w); xx++)
- {
- iArray[outOffset++] = getSample(xx, yy, b, data);
- }
+ for (int xx = x; xx < (x + w); xx++)
+ {
+ iArray[outOffset++] = getSample(xx, yy, b, data);
+ }
}
return iArray;
}
public float[] getSamples(int x, int y, int w, int h, int b,
- float[] fArray, DataBuffer data)
+ float[] fArray, DataBuffer data)
{
- int size = w*h;
+ int size = w * h;
int outOffset = 0;
- if (fArray == null) fArray = new float[size];
- for (int yy=y; yy<(y+h); yy++)
+ if (fArray == null)
+ fArray = new float[size];
+ for (int yy = y; yy < (y + h); yy++)
{
- for (int xx=x; xx<(x+w); xx++)
- {
- fArray[outOffset++] = getSampleFloat(xx, yy, b, data);
- }
+ for (int xx = x; xx < (x + w); xx++)
+ {
+ fArray[outOffset++] = getSampleFloat(xx, yy, b, data);
+ }
}
return fArray;
}
public double[] getSamples(int x, int y, int w, int h, int b,
- double[] dArray, DataBuffer data)
+ double[] dArray, DataBuffer data)
{
- int size = w*h;
+ int size = w * h;
int outOffset = 0;
- if (dArray == null) dArray = new double[size];
- for (int yy=y; yy<(y+h); yy++)
+ if (dArray == null)
+ dArray = new double[size];
+ for (int yy = y; yy < (y + h); yy++)
{
- for (int xx=x; xx<(x+w); xx++)
- {
- dArray[outOffset++] = getSampleDouble(xx, yy, b, data);
- }
+ for (int xx = x; xx < (x + w); xx++)
+ {
+ dArray[outOffset++] = getSampleDouble(xx, yy, b, data);
+ }
}
return dArray;
}
public void setPixel(int x, int y, int[] iArray, DataBuffer data)
{
- for (int b=0; b<numBands; b++) setSample(x, y, b, iArray[b], data);
+ for (int b = 0; b < numBands; b++)
+ setSample(x, y, b, iArray[b], data);
}
public void setPixel(int x, int y, float[] fArray, DataBuffer data)
{
- for (int b=0; b<numBands; b++) setSample(x, y, b, fArray[b], data);
+ for (int b = 0; b < numBands; b++)
+ setSample(x, y, b, fArray[b], data);
}
public void setPixel(int x, int y, double[] dArray, DataBuffer data)
{
- for (int b=0; b<numBands; b++) setSample(x, y, b, dArray[b], data);
+ for (int b = 0; b < numBands; b++)
+ setSample(x, y, b, dArray[b], data);
}
public void setPixels(int x, int y, int w, int h, int[] iArray,
- DataBuffer data)
+ DataBuffer data)
{
int inOffset = 0;
int[] pixel = new int[numBands];
- for (int yy=y; yy<(y+h); yy++)
+ for (int yy = y; yy < (y + h); yy++)
{
- for (int xx=x; xx<(x+w); xx++)
- {
- System.arraycopy(iArray, inOffset, pixel, 0, numBands);
- setPixel(xx, yy, pixel, data);
- inOffset += numBands;
- }
+ for (int xx = x; xx < (x + w); xx++)
+ {
+ System.arraycopy(iArray, inOffset, pixel, 0, numBands);
+ setPixel(xx, yy, pixel, data);
+ inOffset += numBands;
+ }
}
}
public void setPixels(int x, int y, int w, int h, float[] fArray,
- DataBuffer data)
+ DataBuffer data)
{
int inOffset = 0;
float[] pixel = new float[numBands];
- for (int yy=y; yy<(y+h); yy++)
+ for (int yy = y; yy < (y + h); yy++)
{
- for (int xx=x; xx<(x+w); xx++)
- {
- System.arraycopy(fArray, inOffset, pixel, 0, numBands);
- setPixel(xx, yy, pixel, data);
- inOffset += numBands;
- }
+ for (int xx = x; xx < (x + w); xx++)
+ {
+ System.arraycopy(fArray, inOffset, pixel, 0, numBands);
+ setPixel(xx, yy, pixel, data);
+ inOffset += numBands;
+ }
}
}
public void setPixels(int x, int y, int w, int h, double[] dArray,
- DataBuffer data)
+ DataBuffer data)
{
int inOffset = 0;
double[] pixel = new double[numBands];
- for (int yy=y; yy<(y+h); yy++)
+ for (int yy = y; yy < (y + h); yy++)
{
- for (int xx=x; xx<(x+w); xx++)
- {
- System.arraycopy(dArray, inOffset, pixel, 0, numBands);
- setPixel(xx, yy, pixel, data);
- inOffset += numBands;
- }
+ for (int xx = x; xx < (x + w); xx++)
+ {
+ System.arraycopy(dArray, inOffset, pixel, 0, numBands);
+ setPixel(xx, yy, pixel, data);
+ inOffset += numBands;
+ }
}
}
public abstract void setSample(int x, int y, int b, int s,
- DataBuffer data);
+ DataBuffer data);
public void setSample(int x, int y, int b, float s,
- DataBuffer data)
+ DataBuffer data)
{
setSample(x, y, b, (int) s, data);
}
public void setSample(int x, int y, int b, double s,
- DataBuffer data)
+ DataBuffer data)
{
setSample(x, y, b, (float) s, data);
}
public void setSamples(int x, int y, int w, int h, int b,
- int[] iArray, DataBuffer data)
+ int[] iArray, DataBuffer data)
{
- int size = w*h;
+ int size = w * h;
int inOffset = 0;
- for (int yy=y; yy<(y+h); yy++)
- for (int xx=x; xx<(x+w); xx++)
- setSample(xx, yy, b, iArray[inOffset++], data);
+ for (int yy = y; yy < (y + h); yy++)
+ for (int xx = x; xx < (x + w); xx++)
+ setSample(xx, yy, b, iArray[inOffset++], data);
}
public void setSamples(int x, int y, int w, int h, int b,
- float[] fArray, DataBuffer data)
+ float[] fArray, DataBuffer data)
{
- int size = w*h;
+ int size = w * h;
+ int inOffset = 0;
+ for (int yy = y; yy < (y + h); yy++)
+ for (int xx = x; xx < (x + w); xx++)
+ setSample(xx, yy, b, fArray[inOffset++], data);
+
+ }
+
+ public void setSamples(int x, int y, int w, int h, int b,
+ double[] dArray, DataBuffer data) {
+ int size = w * h;
int inOffset = 0;
- for (int yy=y; yy<(y+h); yy++)
- for (int xx=x; xx<(x+w); xx++)
- setSample(xx, yy, b, fArray[inOffset++], data);
-
- }
-
- public void setSamples(int x, int y, int w, int h, int b,
- double[] dArray, DataBuffer data) {
- int size = w*h;
- int inOffset = 0;
- for (int yy=y; yy<(y+h); yy++)
- for (int xx=x; xx<(x+w); xx++)
- setSample(xx, yy, b, dArray[inOffset++], data);
- }
-
- public abstract SampleModel createCompatibleSampleModel(int w, int h);
-
- /**
- * Return a SampleModel with a subset of the bands in this model.
- *
- * Selects bands.length bands from this sample model. The bands chosen
- * are specified in the indices of bands[]. This also permits permuting
- * the bands as well as taking a subset. Thus, giving an array with
- * 1, 2, 3, ..., numbands, will give an identical sample model.
- *
- * @param bands Array with band indices to include.
- * @return A new sample model
- */
- public abstract SampleModel createSubsetSampleModel(int[] bands);
-
- public abstract DataBuffer createDataBuffer();
-
- public abstract int[] getSampleSize();
-
- public abstract int getSampleSize(int band);
+ for (int yy = y; yy < (y + h); yy++)
+ for (int xx = x; xx < (x + w); xx++)
+ setSample(xx, yy, b, dArray[inOffset++], data);
+ }
+
+ public abstract SampleModel createCompatibleSampleModel(int w, int h);
+
+ /**
+ * Return a SampleModel with a subset of the bands in this model.
+ *
+ * Selects bands.length bands from this sample model. The bands chosen
+ * are specified in the indices of bands[]. This also permits permuting
+ * the bands as well as taking a subset. Thus, giving an array with
+ * 1, 2, 3, ..., numbands, will give an identical sample model.
+ *
+ * @param bands Array with band indices to include.
+ * @return A new sample model
+ */
+ public abstract SampleModel createSubsetSampleModel(int[] bands);
+
+ public abstract DataBuffer createDataBuffer();
+
+ public abstract int[] getSampleSize();
+
+ public abstract int getSampleSize(int band);
}
diff --git a/libjava/classpath/java/awt/image/renderable/RenderableImageProducer.java b/libjava/classpath/java/awt/image/renderable/RenderableImageProducer.java
index 78f3051ea99..d8cca653527 100644
--- a/libjava/classpath/java/awt/image/renderable/RenderableImageProducer.java
+++ b/libjava/classpath/java/awt/image/renderable/RenderableImageProducer.java
@@ -1,5 +1,5 @@
/* RenderableImageProducer.java --
- Copyright (C) 2002 Free Software Foundation, Inc.
+ Copyright (C) 2002, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -38,42 +38,129 @@ exception statement from your version. */
package java.awt.image.renderable;
+import java.awt.image.ColorModel;
+import java.awt.image.DataBuffer;
import java.awt.image.ImageConsumer;
import java.awt.image.ImageProducer;
+import java.awt.image.Raster;
+import java.awt.image.RenderedImage;
+import java.awt.image.SampleModel;
+import java.util.ArrayList;
+import java.util.Iterator;
public class RenderableImageProducer implements ImageProducer, Runnable
{
+ private RenderableImage image;
+ private RenderContext context;
+ private ArrayList consumers = new ArrayList();
+
public RenderableImageProducer(RenderableImage image, RenderContext context)
{
- throw new Error("not implemented");
+ this.image = image;
+ this.context = context;
}
public void setRenderContext(RenderContext context)
{
+ this.context = context;
}
public void addConsumer(ImageConsumer consumer)
{
+ synchronized (consumers)
+ {
+ if (! consumers.contains(consumer))
+ consumers.add(consumer);
+ }
}
public boolean isConsumer(ImageConsumer consumer)
{
- return false;
+ synchronized (consumers)
+ {
+ return consumers.contains(consumer);
+ }
}
public void removeConsumer(ImageConsumer consumer)
{
+ synchronized (consumers)
+ {
+ consumers.remove(consumer);
+ }
}
public void startProduction(ImageConsumer consumer)
{
+ addConsumer(consumer);
+ Thread t = new Thread(this, "RenderableImageProducerWorker");
+ t.start();
}
public void requestTopDownLeftRightResend(ImageConsumer consumer)
{
+ // Do nothing. The contract says we can ignore this call, so we do.
}
public void run()
{
+ // This isn't ideal but it avoids fail-fast problems.
+ // Alternatively, we could clone 'consumers' here.
+ synchronized (consumers)
+ {
+ RenderedImage newImage;
+ if (context == null)
+ newImage = image.createDefaultRendering();
+ else
+ newImage = image.createRendering(context);
+ Raster newData = newImage.getData();
+ ColorModel colorModel = newImage.getColorModel();
+ if (colorModel == null)
+ colorModel = ColorModel.getRGBdefault();
+ SampleModel sampleModel = newData.getSampleModel();
+ DataBuffer dataBuffer = newData.getDataBuffer();
+ int width = newData.getWidth();
+ int height = newData.getHeight();
+
+ // Initialize the consumers.
+ Iterator it = consumers.iterator();
+ while (it.hasNext())
+ {
+ ImageConsumer target = (ImageConsumer) it.next();
+ target.setHints(ImageConsumer.COMPLETESCANLINES
+ | ImageConsumer.SINGLEFRAME
+ | ImageConsumer.SINGLEPASS
+ | ImageConsumer.TOPDOWNLEFTRIGHT);
+ target.setDimensions(width, height);
+ }
+
+ // Work in scan-line order.
+ int[] newLine = new int[width];
+ int[] bands = new int[sampleModel.getNumBands()];
+ for (int y = 0; y < height; ++y)
+ {
+ for (int x = 0; x < width; ++x)
+ {
+ sampleModel.getPixel(x, y, bands, dataBuffer);
+ newLine[x] = colorModel.getDataElement(bands, 0);
+ }
+
+ // Tell the consumers about the new scan line.
+ it = consumers.iterator();
+ while (it.hasNext())
+ {
+ ImageConsumer target = (ImageConsumer) it.next();
+ target.setPixels(0, y, width, 1, colorModel, newLine, 0, width);
+ }
+ }
+
+ // Tell the consumers that we're done.
+ it = consumers.iterator();
+ while (it.hasNext())
+ {
+ ImageConsumer target = (ImageConsumer) it.next();
+ target.imageComplete(ImageConsumer.STATICIMAGEDONE);
+ }
+ }
}
} // class RenderableImageProducer
diff --git a/libjava/classpath/java/beans/beancontext/BeanContext.java b/libjava/classpath/java/beans/beancontext/BeanContext.java
index 3d1be7fc8e9..02f4a1a4011 100644
--- a/libjava/classpath/java/beans/beancontext/BeanContext.java
+++ b/libjava/classpath/java/beans/beancontext/BeanContext.java
@@ -198,7 +198,7 @@ public interface BeanContext
* @return the created Bean
*
* @see java.beans.Beans#instantiate(java.lang.ClassLoader,java.lang.String)
- * @see java.beans.Beans#instantiate(java.lang.ClassLoader,java.lang.String,java.lang.BeanContext)
+ * @see java.beans.Beans#instantiate(java.lang.ClassLoader,java.lang.String,java.beans.beancontext.BeanContext)
* @exception IOException if there is an I/O problem during
* instantiation.
* @exception ClassNotFoundException if a serialized Bean's class
diff --git a/libjava/classpath/java/beans/beancontext/BeanContextMembershipEvent.java b/libjava/classpath/java/beans/beancontext/BeanContextMembershipEvent.java
index 31765426622..9560889f8f2 100644
--- a/libjava/classpath/java/beans/beancontext/BeanContextMembershipEvent.java
+++ b/libjava/classpath/java/beans/beancontext/BeanContextMembershipEvent.java
@@ -52,7 +52,9 @@ import java.util.Iterator;
* @see java.beans.beancontext.BeanContextMembershipListener
*/
public class BeanContextMembershipEvent extends BeanContextEvent {
- /**
+ private static final long serialVersionUID = 3499346510334590959L;
+
+ /**
* The children that were added or removed.
*/
protected Collection children;
diff --git a/libjava/classpath/java/beans/beancontext/BeanContextServiceAvailableEvent.java b/libjava/classpath/java/beans/beancontext/BeanContextServiceAvailableEvent.java
index eea10f261b6..6dc2c38ab39 100644
--- a/libjava/classpath/java/beans/beancontext/BeanContextServiceAvailableEvent.java
+++ b/libjava/classpath/java/beans/beancontext/BeanContextServiceAvailableEvent.java
@@ -49,7 +49,9 @@ import java.util.Iterator;
*/
public class BeanContextServiceAvailableEvent extends BeanContextEvent {
- /**
+ private static final long serialVersionUID = -5333985775656400778L;
+
+ /**
* The <code>Class</code> representing the service which is now
* available.
*/
diff --git a/libjava/classpath/java/beans/beancontext/BeanContextServiceRevokedEvent.java b/libjava/classpath/java/beans/beancontext/BeanContextServiceRevokedEvent.java
index dfa2b89b3ae..1f5ebd3cd83 100644
--- a/libjava/classpath/java/beans/beancontext/BeanContextServiceRevokedEvent.java
+++ b/libjava/classpath/java/beans/beancontext/BeanContextServiceRevokedEvent.java
@@ -47,7 +47,9 @@ package java.beans.beancontext;
*/
public class BeanContextServiceRevokedEvent extends BeanContextEvent {
- /**
+ private static final long serialVersionUID = -1295543154724961754L;
+
+ /**
* The <code>Class</code> representing the service which is now
* available.
*/
diff --git a/libjava/classpath/java/beans/beancontext/BeanContextServicesSupport.java b/libjava/classpath/java/beans/beancontext/BeanContextServicesSupport.java
index 5455adbaec3..4da523eeb06 100644
--- a/libjava/classpath/java/beans/beancontext/BeanContextServicesSupport.java
+++ b/libjava/classpath/java/beans/beancontext/BeanContextServicesSupport.java
@@ -38,6 +38,8 @@ exception statement from your version. */
package java.beans.beancontext;
+import gnu.classpath.NotImplementedException;
+
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
@@ -62,6 +64,11 @@ public class BeanContextServicesSupport
extends BeanContextSupport.BCSChild
{
private static final long serialVersionUID = -3263851306889194873L;
+
+ BCSSChild(Object targetChild, Object peer)
+ {
+ super(targetChild, peer);
+ }
}
protected class BCSSProxyServiceProvider
@@ -69,9 +76,14 @@ public class BeanContextServicesSupport
BeanContextServiceRevokedListener
{
private static final long serialVersionUID = 7078212910685744490L;
-
+
+ private BCSSProxyServiceProvider()
+ {
+ }
+
public Iterator getCurrentServiceSelectors (BeanContextServices bcs,
Class serviceClass)
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
@@ -80,6 +92,7 @@ public class BeanContextServicesSupport
Object requestor,
Class serviceClass,
Object serviceSelector)
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
@@ -87,11 +100,13 @@ public class BeanContextServicesSupport
public void releaseService (BeanContextServices bcs,
Object requestor,
Object service)
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
public void serviceRevoked (BeanContextServiceRevokedEvent bcsre)
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
@@ -104,6 +119,10 @@ public class BeanContextServicesSupport
protected BeanContextServiceProvider serviceProvider;
+ private BCSSServiceProvider()
+ {
+ }
+
protected BeanContextServiceProvider getServiceProvider()
{
return serviceProvider;
@@ -148,105 +167,154 @@ public class BeanContextServicesSupport
public void addBeanContextServicesListener
(BeanContextServicesListener listener)
{
- if (! bcsListeners.contains(listener))
- bcsListeners.add(listener);
+ synchronized (bcsListeners)
+ {
+ if (! bcsListeners.contains(listener))
+ bcsListeners.add(listener);
+ }
}
- public boolean addService (Class serviceClass, BeanContextServiceProvider bcsp)
+ public boolean addService (Class serviceClass,
+ BeanContextServiceProvider bcsp)
{
- throw new Error ("Not implemented");
+ return addService(serviceClass, bcsp, true);
}
protected boolean addService (Class serviceClass,
BeanContextServiceProvider bcsp,
boolean fireEvent)
{
- throw new Error ("Not implemented");
+ synchronized (services)
+ {
+ if (services.containsKey(serviceClass))
+ return false;
+ services.put(serviceClass, bcsp);
+ if (bcsp instanceof Serializable)
+ ++serializable;
+ fireServiceAdded(serviceClass);
+ return true;
+ }
}
protected void bcsPreDeserializationHook (ObjectInputStream ois)
- throws ClassNotFoundException, IOException
+ throws ClassNotFoundException, IOException, NotImplementedException
{
throw new Error ("Not implemented");
}
protected void bcsPreSerializationHook (ObjectOutputStream oos)
- throws IOException
+ throws IOException, NotImplementedException
{
throw new Error ("Not implemented");
}
protected void childJustRemovedHook (Object child,
BeanContextSupport.BCSChild bcsc)
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
protected BeanContextSupport.BCSChild createBCSChild (Object targetChild,
- Object peer)
+ Object peer)
{
- throw new Error ("Not implemented");
+ return new BCSSChild(targetChild, peer);
}
protected BeanContextServicesSupport.BCSSServiceProvider
createBCSSServiceProvider (Class sc, BeanContextServiceProvider bcsp)
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
protected final void fireServiceAdded (BeanContextServiceAvailableEvent bcssae)
{
- throw new Error ("Not implemented");
+ synchronized (bcsListeners)
+ {
+ int size = bcsListeners.size();
+ for (int i = 0; i < size; ++i)
+ {
+ BeanContextServicesListener bcsl
+ = (BeanContextServicesListener) bcsListeners.get(i);
+ bcsl.serviceAvailable(bcssae);
+ }
+ }
}
- protected final void fireServiceAdded (Class serviceClass)
+ protected final void fireServiceAdded (Class serviceClass)
{
- throw new Error ("Not implemented");
+ fireServiceAdded(new BeanContextServiceAvailableEvent(this,
+ serviceClass));
}
protected final void fireServiceRevoked(BeanContextServiceRevokedEvent event)
{
- throw new Error ("Not implemented");
+ synchronized (bcsListeners)
+ {
+ int size = bcsListeners.size();
+ for (int i = 0; i < size; ++i)
+ {
+ BeanContextServicesListener bcsl
+ = (BeanContextServicesListener) bcsListeners.get(i);
+ bcsl.serviceRevoked(event);
+ }
+ }
}
protected final void fireServiceRevoked (Class serviceClass,
boolean revokeNow)
{
- throw new Error ("Not implemented");
+ fireServiceRevoked(new BeanContextServiceRevokedEvent(this, serviceClass,
+ revokeNow));
}
public BeanContextServices getBeanContextServicesPeer ()
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
protected static final BeanContextServicesListener
- getChildBeanContextServicesListener (Object child)
+ getChildBeanContextServicesListener (Object child)
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
- public Iterator getCurrentServiceClasses ()
+ public Iterator getCurrentServiceClasses ()
{
- throw new Error ("Not implemented");
+ synchronized (services)
+ {
+ return services.keySet().iterator();
+ }
}
- public Iterator getCurrentServiceSelectors (Class serviceClass)
+ public Iterator getCurrentServiceSelectors (Class serviceClass)
{
- throw new Error ("Not implemented");
+ synchronized (services)
+ {
+ // FIXME: what if service does not exist? Must write a test.
+ BeanContextServiceProvider bcsp
+ = (BeanContextServiceProvider) services.get(serviceClass);
+ return bcsp.getCurrentServiceSelectors(this, serviceClass);
+ }
}
public Object getService (BeanContextChild child, Object requestor,
Class serviceClass, Object serviceSelector,
BeanContextServiceRevokedListener bcsrl)
- throws TooManyListenersException
+ throws TooManyListenersException, NotImplementedException
{
throw new Error ("Not implemented");
}
public boolean hasService (Class serviceClass)
{
- throw new Error ("Not implemented");
+ synchronized (services)
+ {
+ return services.containsKey(serviceClass);
+ }
}
public void initialize ()
@@ -257,18 +325,21 @@ public class BeanContextServicesSupport
services = new HashMap();
}
- protected void initializeBeanContextResources ()
+ protected void initializeBeanContextResources ()
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
- protected void releaseBeanContextResources ()
+ protected void releaseBeanContextResources ()
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
public void releaseService (BeanContextChild child, Object requestor,
Object service)
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
@@ -276,25 +347,52 @@ public class BeanContextServicesSupport
public void removeBeanContextServicesListener
(BeanContextServicesListener listener)
{
- int index = bcsListeners.indexOf(listener);
-
- if (index > -1)
- bcsListeners.remove(index);
+ synchronized (bcsListeners)
+ {
+ int index = bcsListeners.indexOf(listener);
+ if (index > -1)
+ bcsListeners.remove(index);
+ }
}
public void revokeService (Class serviceClass, BeanContextServiceProvider bcsp,
- boolean revokeCurrentServicesNow)
+ boolean revokeCurrentServicesNow)
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
- public void serviceAvailable (BeanContextServiceAvailableEvent bcssae)
- {
- throw new Error ("Not implemented");
- }
-
- public void serviceRevoked (BeanContextServiceRevokedEvent bcssre)
- {
- throw new Error ("Not implemented");
+ public void serviceAvailable (BeanContextServiceAvailableEvent bcssae)
+ {
+ synchronized (services)
+ {
+ Class klass = bcssae.getServiceClass();
+ if (services.containsKey(klass))
+ return;
+ Iterator it = bcsChildren();
+ while (it.hasNext())
+ {
+ Object obj = it.next();
+ if (obj instanceof BeanContextServices)
+ ((BeanContextServices) obj).serviceAvailable(bcssae);
+ }
+ }
+ }
+
+ public void serviceRevoked (BeanContextServiceRevokedEvent bcssre)
+ {
+ synchronized (services)
+ {
+ Class klass = bcssre.getServiceClass();
+ if (services.containsKey(klass))
+ return;
+ Iterator it = bcsChildren();
+ while (it.hasNext())
+ {
+ Object obj = it.next();
+ if (obj instanceof BeanContextServices)
+ ((BeanContextServices) obj).serviceRevoked(bcssre);
+ }
+ }
}
}
diff --git a/libjava/classpath/java/beans/beancontext/BeanContextSupport.java b/libjava/classpath/java/beans/beancontext/BeanContextSupport.java
index 60ccc3af3e4..f3d5ff6098d 100644
--- a/libjava/classpath/java/beans/beancontext/BeanContextSupport.java
+++ b/libjava/classpath/java/beans/beancontext/BeanContextSupport.java
@@ -38,6 +38,9 @@ exception statement from your version. */
package java.beans.beancontext;
+import gnu.classpath.NotImplementedException;
+
+import java.beans.DesignMode;
import java.beans.PropertyChangeEvent;
import java.beans.PropertyChangeListener;
import java.beans.PropertyVetoException;
@@ -64,15 +67,19 @@ public class BeanContextSupport extends BeanContextChildSupport
VetoableChangeListener
{
private static final long serialVersionUID = -4879613978649577204L;
-
+
+ // This won't show up in japi, but we mark it as a stub anyway,
+ // so that searches for NotImplementedException will find it.
private void readObject (ObjectInputStream s)
- throws ClassNotFoundException, IOException
+ throws ClassNotFoundException, IOException, NotImplementedException
{
throw new Error ("Not implemented");
}
+ // This won't show up in japi, but we mark it as a stub anyway,
+ // so that searches for NotImplementedException will find it.
private void writeObject (ObjectOutputStream s)
- throws ClassNotFoundException, IOException
+ throws ClassNotFoundException, IOException, NotImplementedException
{
throw new Error ("Not implemented");
}
@@ -80,18 +87,34 @@ public class BeanContextSupport extends BeanContextChildSupport
protected class BCSChild implements Serializable
{
private static final long serialVersionUID = -5815286101609939109L;
+
+ private Object targetChild;
+ private Object peer;
+
+ BCSChild(Object targetChild, Object peer)
+ {
+ this.targetChild = targetChild;
+ this.peer = peer;
+ }
}
protected static final class BCSIterator implements Iterator
{
+ private Iterator child;
+
+ BCSIterator(Iterator child)
+ {
+ this.child = child;
+ }
+
public boolean hasNext ()
{
- throw new Error ("Not implemented");
+ return child.hasNext();
}
public Object next ()
{
- throw new Error ("Not implemented");
+ return child.next();
}
public void remove ()
@@ -148,7 +171,9 @@ public class BeanContextSupport extends BeanContextChildSupport
public BeanContextSupport (BeanContext peer, Locale lcle, boolean dtime,
boolean visible)
{
- locale = lcle;
+ super(peer);
+
+ locale = lcle == null ? Locale.getDefault() : lcle;
designTime = dtime;
okToUseGui = visible;
@@ -160,150 +185,214 @@ public class BeanContextSupport extends BeanContextChildSupport
if (targetChild == null)
throw new IllegalArgumentException();
- if (children.containsKey(targetChild))
- return false;
-
- // FIXME: The second argument is surely wrong.
- children.put(targetChild, targetChild);
+ BCSChild child;
+ synchronized (children)
+ {
+ if (children.containsKey(targetChild)
+ || ! validatePendingAdd(targetChild))
+ return false;
+ child = createBCSChild(targetChild, beanContextChildPeer);
+ children.put(targetChild, child);
+ }
+ synchronized (targetChild)
+ {
+ childJustAddedHook(targetChild, child);
+ }
+ fireChildrenAdded(new BeanContextMembershipEvent(this,
+ new Object[] { targetChild }));
return true;
}
public boolean addAll (Collection c)
{
+ // Intentionally throws an exception.
throw new UnsupportedOperationException();
}
public void addBeanContextMembershipListener
(BeanContextMembershipListener listener)
{
- if (! bcmListeners.contains(listener))
- bcmListeners.add(listener);
+ synchronized (bcmListeners)
+ {
+ if (! bcmListeners.contains(listener))
+ bcmListeners.add(listener);
+ }
}
public boolean avoidingGui ()
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
protected Iterator bcsChildren ()
{
- throw new Error ("Not implemented");
+ synchronized (children)
+ {
+ return new BCSIterator(children.values().iterator());
+ }
}
protected void bcsPreDeserializationHook (ObjectInputStream ois)
- throws ClassNotFoundException, IOException
+ throws ClassNotFoundException, IOException, NotImplementedException
{
throw new Error ("Not implemented");
}
protected void bcsPreSerializationHook (ObjectOutputStream oos)
- throws IOException
+ throws IOException, NotImplementedException
{
throw new Error ("Not implemented");
}
protected void childDeserializedHook (Object child, BeanContextSupport.BCSChild bcsc)
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
protected void childJustAddedHook (Object child, BeanContextSupport.BCSChild bcsc)
{
- throw new Error ("Not implemented");
+ // Do nothing in the base class.
}
protected void childJustRemovedHook (Object child, BeanContextSupport.BCSChild bcsc)
{
- throw new Error ("Not implemented");
+ // Do nothing in the base class.
}
protected static final boolean classEquals (Class first, Class second)
{
- throw new Error ("Not implemented");
+ // Lame function!
+ return (first == second || first.getName().equals(second.getName()));
}
public void clear ()
{
+ // This is the right thing to do.
+ // The JDK docs are really bad here.
throw new UnsupportedOperationException();
}
public boolean contains (Object o)
{
- throw new Error ("Not implemented");
+ synchronized (children)
+ {
+ return children.containsKey(o);
+ }
}
public boolean containsAll (Collection c)
{
- throw new Error ("Not implemented");
+ synchronized (children)
+ {
+ Iterator it = c.iterator();
+ while (it.hasNext())
+ if (! children.containsKey(it.next()))
+ return false;
+ }
+ return true;
}
public boolean containsKey (Object o)
{
- throw new Error ("Not implemented");
+ synchronized (children)
+ {
+ return children.containsKey(o);
+ }
}
protected final Object[] copyChildren ()
{
- throw new Error ("Not implemented");
+ synchronized (children)
+ {
+ return children.keySet().toArray();
+ }
}
protected BeanContextSupport.BCSChild createBCSChild (Object targetChild, Object peer)
{
- throw new Error ("Not implemented");
+ return new BCSChild(targetChild, peer);
}
protected final void deserialize (ObjectInputStream ois, Collection coll)
- throws ClassNotFoundException, IOException
+ throws ClassNotFoundException, IOException, NotImplementedException
{
throw new Error ("Not implemented");
}
public void dontUseGui ()
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
protected final void fireChildrenAdded (BeanContextMembershipEvent bcme)
{
- throw new Error ("Not implemented");
+ synchronized (bcmListeners)
+ {
+ Iterator it = bcmListeners.iterator();
+ while (it.hasNext())
+ {
+ BeanContextMembershipListener l
+ = (BeanContextMembershipListener) it.next();
+ l.childrenAdded(bcme);
+ }
+ }
}
protected final void fireChildrenRemoved (BeanContextMembershipEvent bcme)
{
- throw new Error ("Not implemented");
+ synchronized (bcmListeners)
+ {
+ Iterator it = bcmListeners.iterator();
+ while (it.hasNext())
+ {
+ BeanContextMembershipListener l
+ = (BeanContextMembershipListener) it.next();
+ l.childrenRemoved(bcme);
+ }
+ }
}
public BeanContext getBeanContextPeer ()
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
protected static final BeanContextChild getChildBeanContextChild (Object child)
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
protected static final BeanContextMembershipListener getChildBeanContextMembershipListener (Object child)
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
protected static final PropertyChangeListener getChildPropertyChangeListener (Object child)
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
protected static final Serializable getChildSerializable (Object child)
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
protected static final VetoableChangeListener getChildVetoableChangeListener (Object child)
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
protected static final Visibility getChildVisibility (Object child)
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
@@ -315,12 +404,20 @@ public class BeanContextSupport extends BeanContextChildSupport
public URL getResource (String name, BeanContextChild bcc)
{
- throw new Error ("Not implemented");
+ if (! contains(bcc))
+ throw new IllegalArgumentException("argument not a child");
+ ClassLoader loader = bcc.getClass().getClassLoader();
+ return (loader == null ? ClassLoader.getSystemResource(name)
+ : loader.getResource(name));
}
public InputStream getResourceAsStream (String name, BeanContextChild bcc)
{
- throw new Error ("Not implemented");
+ if (! contains(bcc))
+ throw new IllegalArgumentException("argument not a child");
+ ClassLoader loader = bcc.getClass().getClassLoader();
+ return (loader == null ? ClassLoader.getSystemResourceAsStream(name)
+ : loader.getResourceAsStream(name));
}
protected void initialize ()
@@ -330,48 +427,58 @@ public class BeanContextSupport extends BeanContextChildSupport
}
public Object instantiateChild (String beanName)
- throws IOException, ClassNotFoundException
+ throws IOException, ClassNotFoundException, NotImplementedException
{
throw new Error ("Not implemented");
}
public boolean isDesignTime ()
{
- throw new Error ("Not implemented");
+ return designTime;
}
public boolean isEmpty ()
{
- throw new Error ("Not implemented");
+ synchronized (children)
+ {
+ return children.isEmpty();
+ }
}
public boolean isSerializing ()
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
public Iterator iterator ()
{
- return children.keySet().iterator();
+ synchronized (children)
+ {
+ return children.keySet().iterator();
+ }
}
public boolean needsGui ()
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
public void okToUseGui ()
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
public void propertyChange (PropertyChangeEvent pce)
+ throws NotImplementedException
{
throw new Error ("Not implemented");
}
public final void readChildren (ObjectInputStream ois)
- throws IOException, ClassNotFoundException
+ throws IOException, ClassNotFoundException, NotImplementedException
{
throw new Error ("Not implemented");
}
@@ -382,6 +489,7 @@ public class BeanContextSupport extends BeanContextChildSupport
}
protected boolean remove (Object targetChild, boolean callChildSetBC)
+ throws NotImplementedException
{
if (targetChild == null)
throw new IllegalArgumentException();
@@ -391,69 +499,93 @@ public class BeanContextSupport extends BeanContextChildSupport
public boolean removeAll (Collection c)
{
+ // Intentionally throws an exception.
throw new UnsupportedOperationException();
}
public void removeBeanContextMembershipListener (BeanContextMembershipListener bcml)
{
- throw new Error ("Not implemented");
+ synchronized (bcmListeners)
+ {
+ bcmListeners.remove(bcml);
+ }
}
public boolean retainAll (Collection c)
{
+ // Intentionally throws an exception.
throw new UnsupportedOperationException();
}
protected final void serialize (ObjectOutputStream oos, Collection coll)
- throws IOException
+ throws IOException, NotImplementedException
{
throw new Error ("Not implemented");
}
public void setDesignTime (boolean dtime)
{
- throw new Error ("Not implemented");
+ boolean save = designTime;
+ designTime = dtime;
+ firePropertyChange(DesignMode.PROPERTYNAME, Boolean.valueOf(save),
+ Boolean.valueOf(dtime));
}
public void setLocale (Locale newLocale)
throws PropertyVetoException
{
- throw new Error ("Not implemented");
+ if (newLocale == null || locale == newLocale)
+ return;
+ fireVetoableChange("locale", locale, newLocale);
+ Locale oldLocale = locale;
+ locale = newLocale;
+ firePropertyChange("locale", oldLocale, newLocale);
}
public int size ()
{
- throw new Error ("Not implemented");
+ synchronized (children)
+ {
+ return children.size();
+ }
}
public Object[] toArray ()
{
- return children.keySet().toArray();
+ synchronized (children)
+ {
+ return children.keySet().toArray();
+ }
}
public Object[] toArray(Object[] array)
+ throws NotImplementedException
{
- return children.keySet().toArray(array);
+ // This implementation is incorrect, I think.
+ synchronized (children)
+ {
+ return children.keySet().toArray(array);
+ }
}
protected boolean validatePendingAdd (Object targetChild)
{
- throw new Error ("Not implemented");
+ return true;
}
protected boolean validatePendingRemove (Object targetChild)
{
- throw new Error ("Not implemented");
+ return true;
}
public void vetoableChange (PropertyChangeEvent pce)
- throws PropertyVetoException
+ throws PropertyVetoException, NotImplementedException
{
throw new Error ("Not implemented");
}
public final void writeChildren (ObjectOutputStream oos)
- throws IOException
+ throws IOException, NotImplementedException
{
throw new Error ("Not implemented");
}
diff --git a/libjava/classpath/java/io/CharArrayWriter.java b/libjava/classpath/java/io/CharArrayWriter.java
index f9b338fe0cc..68e693b4a1a 100644
--- a/libjava/classpath/java/io/CharArrayWriter.java
+++ b/libjava/classpath/java/io/CharArrayWriter.java
@@ -242,6 +242,84 @@ public class CharArrayWriter extends Writer
}
}
+ /**
+ * Appends the Unicode character, <code>c</code>, to the output stream
+ * underlying this writer. This is equivalent to <code>write(c)</code>.
+ *
+ * @param c the character to append.
+ * @return a reference to this object.
+ * @since 1.5
+ */
+ public CharArrayWriter append(char c)
+ {
+ write(c);
+ return this;
+ }
+
+ /**
+ * Appends the specified sequence of Unicode characters to the
+ * output stream underlying this writer. This is equivalent to
+ * appending the results of calling <code>toString()</code> on the
+ * character sequence. As a result, the entire sequence may not be
+ * appended, as it depends on the implementation of
+ * <code>toString()</code> provided by the
+ * <code>CharSequence</code>. For example, if the character
+ * sequence is wrapped around an input buffer, the results will
+ * depend on the current position and length of that buffer.
+ *
+ * @param cs the character sequence to append. If cs is null,
+ * then the string "null" (the string representation of null)
+ * is appended.
+ * @return a reference to this object.
+ * @since 1.5
+ */
+ public CharArrayWriter append(CharSequence cs)
+ {
+ try
+ {
+ write(cs == null ? "null" : cs.toString());
+ }
+ catch (IOException _)
+ {
+ // Can't happen.
+ }
+ return this;
+ }
+
+ /**
+ * Appends the specified subsequence of Unicode characters to the
+ * output stream underlying this writer, starting and ending at the
+ * specified positions within the sequence. The behaviour of this
+ * method matches the behaviour of writing the result of
+ * <code>append(cs.subSequence(start,end))</code> when the sequence
+ * is not null.
+ *
+ * @param cs the character sequence to append. If cs is null,
+ * then the string "null" (the string representation of null)
+ * is appended.
+ * @param start the index of the first Unicode character to use from
+ * the sequence.
+ * @param end the index of the last Unicode character to use from the
+ * sequence.
+ * @return a reference to this object.
+ * @throws IndexOutOfBoundsException if either of the indices are negative,
+ * the start index occurs after the end index, or the end index is
+ * beyond the end of the sequence.
+ * @since 1.5
+ */
+ public CharArrayWriter append(CharSequence cs, int start, int end)
+ {
+ try
+ {
+ write(cs == null ? "null" : cs.subSequence(start, end).toString());
+ }
+ catch (IOException _)
+ {
+ // Can't happen.
+ }
+ return this;
+ }
+
/**
* This private method makes the buffer bigger when we run out of room
* by allocating a larger buffer and copying the valid chars from the
diff --git a/libjava/classpath/java/io/DataOutputStream.java b/libjava/classpath/java/io/DataOutputStream.java
index 25178160dc8..6670c2dba13 100644
--- a/libjava/classpath/java/io/DataOutputStream.java
+++ b/libjava/classpath/java/io/DataOutputStream.java
@@ -63,6 +63,11 @@ public class DataOutputStream extends FilterOutputStream implements DataOutput
protected int written;
/**
+ * Utf8 byte buffer, used by writeUTF()
+ */
+ private byte[] buf;
+
+ /**
* This method initializes an instance of <code>DataOutputStream</code> to
* write its data to the specified underlying <code>OutputStream</code>
*
@@ -373,6 +378,37 @@ public class DataOutputStream extends FilterOutputStream implements DataOutput
}
/**
+ * Calculate the length, in bytes, of a <code>String</code> in Utf8 format.
+ *
+ * @param value The <code>String</code> to measure
+ * @param start String index at which to begin count
+ * @param sum Starting Utf8 byte count
+ *
+ * @throws UTFDataFormatException if result would exceed 65535
+ */
+ private int getUTFlength(String value, int start, int sum)
+ throws IOException
+ {
+ int len = value.length();
+
+ for (int i = start; i < len && sum <= 65535; ++i)
+ {
+ char c = value.charAt(i);
+ if (c >= '\u0001' && c <= '\u007f')
+ sum += 1;
+ else if (c == '\u0000' || (c >= '\u0080' && c <= '\u07ff'))
+ sum += 2;
+ else
+ sum += 3;
+ }
+
+ if (sum > 65535)
+ throw new UTFDataFormatException ();
+
+ return sum;
+ }
+
+ /**
* This method writes a Java <code>String</code> to the stream in a modified
* UTF-8 format. First, two bytes are written to the stream indicating the
* number of bytes to follow. Note that this is the number of bytes in the
@@ -407,48 +443,47 @@ public class DataOutputStream extends FilterOutputStream implements DataOutput
public final synchronized void writeUTF(String value) throws IOException
{
int len = value.length();
- int sum = 0;
-
- for (int i = 0; i < len && sum <= 65535; ++i)
- {
- char c = value.charAt(i);
- if (c >= '\u0001' && c <= '\u007f')
- sum += 1;
- else if (c == '\u0000' || (c >= '\u0080' && c <= '\u07ff'))
- sum += 2;
- else
- sum += 3;
- }
-
- if (sum > 65535)
- throw new UTFDataFormatException ();
-
+ int i = 0;
int pos = 0;
- byte[] buf = new byte[sum];
+ boolean lengthWritten = false;
- for (int i = 0; i < len; ++i)
+ if (buf == null)
+ buf = new byte[512];
+
+ do
{
- char c = value.charAt(i);
- if (c >= '\u0001' && c <= '\u007f')
- buf[pos++] = (byte) c;
- else if (c == '\u0000' || (c >= '\u0080' && c <= '\u07ff'))
+ while (i < len && pos < buf.length - 3)
{
- buf[pos++] = (byte) (0xc0 | (0x1f & (c >> 6)));
- buf[pos++] = (byte) (0x80 | (0x3f & c));
+ char c = value.charAt(i++);
+ if (c >= '\u0001' && c <= '\u007f')
+ buf[pos++] = (byte) c;
+ else if (c == '\u0000' || (c >= '\u0080' && c <= '\u07ff'))
+ {
+ buf[pos++] = (byte) (0xc0 | (0x1f & (c >> 6)));
+ buf[pos++] = (byte) (0x80 | (0x3f & c));
+ }
+ else
+ {
+ // JSL says the first byte should be or'd with 0xc0, but
+ // that is a typo. Unicode says 0xe0, and that is what is
+ // consistent with DataInputStream.
+ buf[pos++] = (byte) (0xe0 | (0x0f & (c >> 12)));
+ buf[pos++] = (byte) (0x80 | (0x3f & (c >> 6)));
+ buf[pos++] = (byte) (0x80 | (0x3f & c));
+ }
}
- else
+ if (! lengthWritten)
{
- // JSL says the first byte should be or'd with 0xc0, but
- // that is a typo. Unicode says 0xe0, and that is what is
- // consistent with DataInputStream.
- buf[pos++] = (byte) (0xe0 | (0x0f & (c >> 12)));
- buf[pos++] = (byte) (0x80 | (0x3f & (c >> 6)));
- buf[pos++] = (byte) (0x80 | (0x3f & c));
+ if (i == len)
+ writeShort(pos);
+ else
+ writeShort(getUTFlength(value, i, pos));
+ lengthWritten = true;
}
- }
-
- writeShort (sum);
- write(buf, 0, sum);
+ write(buf, 0, pos);
+ pos = 0;
+ }
+ while (i < len);
}
} // class DataOutputStream
diff --git a/libjava/classpath/java/io/FilePermission.java b/libjava/classpath/java/io/FilePermission.java
index 31802c631d6..9a83efba621 100644
--- a/libjava/classpath/java/io/FilePermission.java
+++ b/libjava/classpath/java/io/FilePermission.java
@@ -1,5 +1,6 @@
/* FilePermission.java --
- Copyright (C) 1998, 2000, 2003, 2004, 2005 Free Software Foundation, Inc.
+ Copyright (C) 1998, 2000, 2003, 2004, 2005, 2006
+ Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -44,9 +45,6 @@ public final class FilePermission extends Permission implements Serializable
{
private static final long serialVersionUID = 7930732926638008763L;
- private static final String CURRENT_DIRECTORY =
- System.getProperty("user.dir");
-
private static final String ALL_FILES = "<<ALL FILES>>";
private boolean readPerm = false;
@@ -213,10 +211,18 @@ public final class FilePermission extends Permission implements Serializable
FilePermission fp = (FilePermission) p;
String f2 = fp.getName();
- if (f1.charAt(0) != File.separatorChar)
- f1 = CURRENT_DIRECTORY + f1;
- if (f2.charAt(0) != File.separatorChar)
- f2 = CURRENT_DIRECTORY + f2;
+ if (f2.equals(ALL_FILES))
+ return false;
+
+ try
+ {
+ f1 = new File(f1).getCanonicalPath();
+ f2 = new File(f2).getCanonicalPath();
+ }
+ catch (IOException ioe)
+ {
+ return false;
+ }
String sub1;
diff --git a/libjava/classpath/java/io/InputStream.java b/libjava/classpath/java/io/InputStream.java
index e56197a837e..2934f0034a5 100644
--- a/libjava/classpath/java/io/InputStream.java
+++ b/libjava/classpath/java/io/InputStream.java
@@ -1,5 +1,5 @@
/* InputStream.java -- Base class for input
- Copyright (C) 1998, 1999, 2001, 2005 Free Software Foundation, Inc.
+ Copyright (C) 1998, 1999, 2001, 2004, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -48,7 +48,7 @@ package java.io;
* @author Aaron M. Renn (arenn@urbanophile.com)
* @author Warren Levy (warrenl@cygnus.com)
*/
-public abstract class InputStream
+public abstract class InputStream implements Closeable
{
/**
* Default, no-arg, public constructor
diff --git a/libjava/classpath/java/io/ObjectOutputStream.java b/libjava/classpath/java/io/ObjectOutputStream.java
index 55a12e4eae8..61f07bc7cfb 100644
--- a/libjava/classpath/java/io/ObjectOutputStream.java
+++ b/libjava/classpath/java/io/ObjectOutputStream.java
@@ -549,53 +549,37 @@ public class ObjectOutputStream extends OutputStream
* different protocols, specified by <code>PROTOCOL_VERSION_1</code>
* and <code>PROTOCOL_VERSION_2</code>. This implementation writes
* data using <code>PROTOCOL_VERSION_2</code> by default, as is done
- * by the JDK 1.2.
- *
- * A non-portable method, <code>setDefaultProtocolVersion (int
- * version)</code> is provided to change the default protocol
- * version.
- *
+ * since the JDK 1.2.
+ * <p>
* For an explanation of the differences between the two protocols
- * see XXX: the Java ObjectSerialization Specification.
- *
- * @exception IOException if <code>version</code> is not a valid
- * protocol
- *
- * @see #setDefaultProtocolVersion(int)
+ * see the Java Object Serialization Specification.
+ * </p>
+ *
+ * @param version the version to use.
+ *
+ * @throws IllegalArgumentException if <code>version</code> is not a valid
+ * protocol.
+ * @throws IllegalStateException if called after the first the first object
+ * was serialized.
+ * @throws IOException if an I/O error occurs.
+ *
+ * @see ObjectStreamConstants#PROTOCOL_VERSION_1
+ * @see ObjectStreamConstants#PROTOCOL_VERSION_2
+ *
+ * @since 1.2
*/
public void useProtocolVersion(int version) throws IOException
{
if (version != PROTOCOL_VERSION_1 && version != PROTOCOL_VERSION_2)
- throw new IOException("Invalid protocol version requested.");
+ throw new IllegalArgumentException("Invalid protocol version requested.");
+
+ if (nextOID != baseWireHandle)
+ throw new IllegalStateException("Protocol version cannot be changed "
+ + "after serialization started.");
protocolVersion = version;
}
-
- /**
- * <em>GNU $classpath specific</em>
- *
- * Changes the default stream protocol used by all
- * <code>ObjectOutputStream</code>s. There are currently two
- * different protocols, specified by <code>PROTOCOL_VERSION_1</code>
- * and <code>PROTOCOL_VERSION_2</code>. The default default is
- * <code>PROTOCOL_VERSION_1</code>.
- *
- * @exception IOException if <code>version</code> is not a valid
- * protocol
- *
- * @see #useProtocolVersion(int)
- */
- public static void setDefaultProtocolVersion(int version)
- throws IOException
- {
- if (version != PROTOCOL_VERSION_1 && version != PROTOCOL_VERSION_2)
- throw new IOException("Invalid protocol version requested.");
-
- defaultProtocolVersion = version;
- }
-
-
/**
* An empty hook that allows subclasses to write extra information
* about classes to the stream. This method is called the first
diff --git a/libjava/classpath/java/io/ObjectStreamConstants.java b/libjava/classpath/java/io/ObjectStreamConstants.java
index f1a4af724e7..04cf79bed3e 100644
--- a/libjava/classpath/java/io/ObjectStreamConstants.java
+++ b/libjava/classpath/java/io/ObjectStreamConstants.java
@@ -1,6 +1,6 @@
/* ObjectStreamConstants.java -- Interface containing constant values
used in reading and writing serialized objects
- Copyright (C) 1998, 1999, 2003 Free Software Foundation, Inc.
+ Copyright (C) 1998, 1999, 2003, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -45,11 +45,29 @@ package java.io;
* <code>ObjectInputStream</code>, and <code>ObjectStreamClass</code>.
* The values for these constants are specified by the Java library
* specification.
+ *
+ * @since 1.1
*/
public interface ObjectStreamConstants
{
// FIXME: Javadoc comment these values.
+
+ /**
+ * The serialization stream protocol version 1. This version was
+ * the default serialization protocol before JDK 1.2.
+ *
+ * @see ObjectOutputStream#useProtocolVersion(int)
+ * @since 1.2
+ */
int PROTOCOL_VERSION_1 = 1;
+
+ /**
+ * The serialization stream protocol version 2. This version is
+ * used as the default serialization protocol since JDK 1.2.
+ *
+ * @see ObjectOutputStream#useProtocolVersion(int)
+ * @since 1.2
+ */
int PROTOCOL_VERSION_2 = 2;
short STREAM_MAGIC = (short)0xaced;
diff --git a/libjava/classpath/java/io/class-dependencies.conf b/libjava/classpath/java/io/class-dependencies.conf
deleted file mode 100644
index 633bb174941..00000000000
--- a/libjava/classpath/java/io/class-dependencies.conf
+++ /dev/null
@@ -1,100 +0,0 @@
-# This property file contains dependencies of classes, methods, and
-# field on other methods or classes.
-#
-# Syntax:
-#
-# <used>: <needed 1> [... <needed N>]
-#
-# means that when <used> is included, <needed 1> (... <needed N>) must
-# be included as well.
-#
-# <needed X> and <used> are of the form
-#
-# <class.methodOrField(signature)>
-#
-# or just
-#
-# <class>
-#
-# Within dependencies, variables can be used. A variable is defined as
-# follows:
-#
-# {variable}: value1 value2 ... value<n>
-#
-# variables can be used on the right side of dependencies as follows:
-#
-# <used>: com.bla.blu.{variable}.Class.m()V
-#
-# The use of the variable will expand to <n> dependencies of the form
-#
-# <used>: com.bla.blu.value1.Class.m()V
-# <used>: com.bla.blu.value2.Class.m()V
-# ...
-# <used>: com.bla.blu.value<n>.Class.m()V
-#
-# Variables can be redefined when building a system to select the
-# required support for features like encodings, protocols, etc.
-#
-# Hints:
-#
-# - For methods and fields, the signature is mandatory. For
-# specification, please see the Java Virtual Machine Specification by
-# SUN. Unlike in the spec, field signatures (types) are in brackets.
-#
-# - Package names must be separated by '/' (and not '.'). E.g.,
-# java/lang/Class (this is necessary, because the '.' is used to
-# separate method or field names from classes)
-#
-# - In case <needed> refers to a class, only the class itself will be
-# included in the resulting binary, NOT necessarily all its methods
-# and fields. If you want to refer to all methods and fields, you can
-# write class.* as an abbreviation.
-#
-# - Abbreviations for packages are also possible: my/package/* means all
-# methods and fields of all classes in my/package.
-#
-# - A line with a trailing '\' continues in the next line.
-
-java/io/File: \
- java/lang/ClassNotFoundException.<init>(Ljava/lang/String;)V \
- java/lang/InternalError.<init>(Ljava/lang/String;)V \
- java/io/IOException.<init>(Ljava/lang/String;)V \
- java/lang/IllegalArgumentException.<init>(Ljava/lang/String;)V
-
-java/io/FileDescriptor: \
- java/lang/ClassNotFoundException.<init>(Ljava/lang/String;)V \
- java/lang/InternalError.<init>(Ljava/lang/String;)V \
- java/lang/IllegalArgumentException.<init>(Ljava/lang/String;)V \
- java/io/IOException.<init>(Ljava/lang/String;)V
-
-java/io/FileInputStream: \
- java/lang/ClassNotFoundException.<init>(Ljava/lang/String;)V \
- java/lang/InternalError.<init>(Ljava/lang/String;)V \
- java/io/IOException.<init>(Ljava/lang/String;)V \
- java/io/FileNotFoundException.<init>(Ljava/lang/String;)V
-
-java/io/FileOutputStream: \
- java/lang/ClassNotFoundException.<init>(Ljava/lang/String;)V \
- java/lang/InternalError.<init>(Ljava/lang/String;)V \
- java/io/FileNotFoundException.<init>(Ljava/lang/String;)V \
- java/io/IOException.<init>(Ljava/lang/String;)V
-
-java/io/ObjectInputStream: \
- java/lang/ClassNotFoundException.<init>(Ljava/lang/String;)V \
- java/lang/InternalError.<init>(Ljava/lang/String;)V \
- java/lang/SecurityManager.currentClassLoader()Ljava/lang/ClassLoader; \
- java/lang/IllegalArgumentException.<init>(Ljava/lang/String;)V
-
-java/io/ObjectOutputStream: \
- java/lang/ClassNotFoundException.<init>(Ljava/lang/String;)V \
- java/lang/InternalError.<init>(Ljava/lang/String;)V \
- java/lang/SecurityManager.currentClassLoader()Ljava/lang/ClassLoader; \
- java/lang/IllegalArgumentException.<init>(Ljava/lang/String;)V
-
-java/io/RandomAccessFile: \
- java/lang/ClassNotFoundException.<init>(Ljava/lang/String;)V \
- java/lang/InternalError.<init>(Ljava/lang/String;)V \
- java/io/FileNotFoundException.<init>(Ljava/lang/String;)V \
- java/io/IOException.<init>(Ljava/lang/String;)V
-
-# end of file
diff --git a/libjava/classpath/java/lang/Boolean.java b/libjava/classpath/java/lang/Boolean.java
index 902c93b3186..23992525c9d 100644
--- a/libjava/classpath/java/lang/Boolean.java
+++ b/libjava/classpath/java/lang/Boolean.java
@@ -1,5 +1,5 @@
/* Boolean.java -- object wrapper for boolean
- Copyright (C) 1998, 2001, 2002, 2005 Free Software Foundation, Inc.
+ Copyright (C) 1998, 2001, 2002, 2005, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -47,9 +47,9 @@ import java.io.Serializable;
* @author Paul Fisher
* @author Eric Blake (ebb9@email.byu.edu)
* @since 1.0
- * @status updated to 1.4
+ * @status updated to 1.5
*/
-public final class Boolean implements Serializable
+public final class Boolean implements Serializable, Comparable
{
/**
* Compatible with JDK 1.0.2+.
@@ -223,34 +223,37 @@ public final class Boolean implements Serializable
}
/**
- * If the String argument is "true", ignoring case, return true.
- * Otherwise, return false.
+ * Compares this Boolean to another.
*
- * @param b String to parse
+ * @param other the Boolean to compare this Boolean to
+ * @return 0 if both Booleans represent the same value, a positive number
+ * if this Boolean represents true and the other false, and a negative
+ * number otherwise.
* @since 1.5
*/
- public static boolean parseBoolean(String b)
+ public int compareTo(Boolean other)
{
- return "true".equalsIgnoreCase(b) ? true : false;
+ return value == other.value ? 0 : (value ? 1 : -1);
}
-
+
/**
- * Compares this Boolean to another.
- * @param b the Boolean to compare this Boolean to
- * @return 0 if both Booleans represent the same value, a positive number
- * if this Boolean represents true and b represents false, or a negative
- * number otherwise.
+ * Bridge method
+ */
+ public int compareTo(Object other)
+ {
+ return compareTo((Boolean)other);
+ }
+
+ /**
+ * If the String argument is "true", ignoring case, return true.
+ * Otherwise, return false.
+ *
+ * @param b String to parse
* @since 1.5
*/
- public int compareTo (Boolean b)
+ public static boolean parseBoolean(String b)
{
- if (b == null)
- throw new NullPointerException("argument passed to compareTo(Boolean) cannot be null");
-
- if (this.value == b.value)
- return 0;
- if (this.value == true)
- return 1;
- return -1;
+ return "true".equalsIgnoreCase(b) ? true : false;
}
+
}
diff --git a/libjava/classpath/java/lang/Character.java b/libjava/classpath/java/lang/Character.java
index 98ad147aaa3..59ae12f7790 100644
--- a/libjava/classpath/java/lang/Character.java
+++ b/libjava/classpath/java/lang/Character.java
@@ -47,7 +47,7 @@ import java.util.Locale;
/**
* Wrapper class for the primitive char data type. In addition, this class
* allows one to retrieve property information and perform transformations
- * on the 57,707 defined characters in the Unicode Standard, Version 3.0.0.
+ * on the defined characters in the Unicode Standard, Version 4.0.0.
* java.lang.Character is designed to be very dynamic, and as such, it
* retrieves information on the Unicode character set from a separate
* database, gnu.java.lang.CharData, which can be easily upgraded.
@@ -55,7 +55,7 @@ import java.util.Locale;
* <p>For predicates, boundaries are used to describe
* the set of characters for which the method will return true.
* This syntax uses fairly normal regular expression notation.
- * See 5.13 of the Unicode Standard, Version 3.0, for the
+ * See 5.13 of the Unicode Standard, Version 4.0, for the
* boundary specification.
*
* <p>See <a href="http://www.unicode.org">http://www.unicode.org</a>
diff --git a/libjava/classpath/java/lang/Class.java b/libjava/classpath/java/lang/Class.java
index c4235e6808c..090ac234a48 100644
--- a/libjava/classpath/java/lang/Class.java
+++ b/libjava/classpath/java/lang/Class.java
@@ -1,5 +1,5 @@
/* Class.java -- Representation of a Java class.
- Copyright (C) 1998, 1999, 2000, 2002, 2003, 2004, 2005
+ Copyright (C) 1998, 1999, 2000, 2002, 2003, 2004, 2005, 2006
Free Software Foundation
This file is part of GNU Classpath.
@@ -39,17 +39,25 @@ exception statement from your version. */
package java.lang;
import gnu.classpath.VMStackWalker;
+import gnu.java.lang.reflect.ClassSignatureParser;
import java.io.InputStream;
import java.io.ObjectStreamClass;
import java.io.Serializable;
+import java.lang.annotation.Annotation;
import java.lang.reflect.Array;
+import java.lang.reflect.AnnotatedElement;
import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
+import java.lang.reflect.GenericDeclaration;
+import java.lang.reflect.GenericSignatureFormatError;
import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.MalformedParameterizedTypeException;
import java.lang.reflect.Member;
import java.lang.reflect.Method;
import java.lang.reflect.Modifier;
+import java.lang.reflect.Type;
+import java.lang.reflect.TypeVariable;
import java.net.URL;
import java.security.AccessController;
import java.security.AllPermission;
@@ -87,17 +95,37 @@ import java.util.HashSet;
*
* @author John Keiser
* @author Eric Blake (ebb9@email.byu.edu)
+ * @author Tom Tromey (tromey@redhat.com)
+ * @author Andrew John Hughes (gnu_andrew@member.fsf.org)
* @author Tom Tromey (tromey@cygnus.com)
* @since 1.0
* @see ClassLoader
*/
-public final class Class implements Serializable
+public final class Class
+ implements Serializable, Type, AnnotatedElement, GenericDeclaration
{
/**
* Compatible with JDK 1.0+.
*/
private static final long serialVersionUID = 3206093459760846163L;
+ /**
+ * Flag indicating a synthetic member.
+ * Note that this duplicates a constant in Modifier.
+ */
+ private static final int SYNTHETIC = 0x1000;
+
+ /**
+ * Flag indiciating an annotation class.
+ */
+ private static final int ANNOTATION = 0x2000;
+
+ /**
+ * Flag indicating an enum constant or an enum class.
+ * Note that this duplicates a constant in Modifier.
+ */
+ private static final int ENUM = 0x4000;
+
/** The class signers. */
private Object[] signers = null;
/** The class protection domain. */
@@ -259,7 +287,7 @@ public final class Class implements Serializable
ClassLoader loader = VMClass.getClassLoader(this);
// Check if we may get the classloader
SecurityManager sm = SecurityManager.current;
- if (sm != null)
+ if (loader != null && sm != null)
{
// Get the calling classloader
ClassLoader cl = VMStackWalker.getCallingClassLoader();
@@ -631,17 +659,16 @@ public final class Class implements Serializable
public boolean equals(Object o)
{
- if(o instanceof MethodKey)
+ if (o instanceof MethodKey)
{
- MethodKey m = (MethodKey)o;
- if(m.name.equals(name) && m.params.length == params.length && m.returnType == returnType)
+ MethodKey m = (MethodKey) o;
+ if (m.name.equals(name) && m.params.length == params.length
+ && m.returnType == returnType)
{
- for(int i = 0; i < params.length; i++)
+ for (int i = 0; i < params.length; i++)
{
- if(m.params[i] != params[i])
- {
- return false;
- }
+ if (m.params[i] != params[i])
+ return false;
}
return true;
}
@@ -1252,8 +1279,60 @@ public final class Class implements Serializable
}
/**
- * Like <code>getField(String)</code> but without the security checks and returns null
- * instead of throwing NoSuchFieldException.
+ * <p>
+ * Casts this class to represent a subclass of the specified class.
+ * This method is useful for `narrowing' the type of a class so that
+ * the class object, and instances of that class, can match the contract
+ * of a more restrictive method. For example, if this class has the
+ * static type of <code>Class&lt;Object&gt;</code>, and a dynamic type of
+ * <code>Class&lt;Rectangle&gt;</code>, then, assuming <code>Shape</code> is
+ * a superclass of <code>Rectangle</code>, this method can be used on
+ * this class with the parameter, <code>Class&lt;Shape&gt;</code>, to retain
+ * the same instance but with the type
+ * <code>Class&lt;? extends Shape&gt;</code>.
+ * </p>
+ * <p>
+ * If this class can be converted to an instance which is parameterised
+ * over a subtype of the supplied type, <code>U</code>, then this method
+ * returns an appropriately cast reference to this object. Otherwise,
+ * a <code>ClassCastException</code> is thrown.
+ * </p>
+ *
+ * @param klass the class object, the parameterized type (<code>U</code>) of
+ * which should be a superclass of the parameterized type of
+ * this instance.
+ * @return a reference to this object, appropriately cast.
+ * @throws ClassCastException if this class can not be converted to one
+ * which represents a subclass of the specified
+ * type, <code>U</code>.
+ * @since 1.5
+ */
+ /* FIXME[GENERICS]: Should be <U> Class<? extends U> asSubClass(Class<U> klass */
+ public Class asSubclass(Class klass)
+ {
+ if (! klass.isAssignableFrom(this))
+ throw new ClassCastException();
+ return this; /* FIXME[GENERICS]: Should cast to Class<? extends U> */
+ }
+
+ /**
+ * Returns the specified object, cast to this <code>Class</code>' type.
+ *
+ * @param obj the object to cast
+ * @throws ClassCastException if obj is not an instance of this class
+ * @since 1.5
+ */
+ /* FIXME[GENERICS]: Should be T cast(Object obj) */
+ public Object cast(Object obj)
+ {
+ if (obj != null && ! isInstance(obj))
+ throw new ClassCastException();
+ return obj; /* FIXME[GENERICS]: Should be cast to T */
+ }
+
+ /**
+ * Like <code>getField(String)</code> but without the security checks and
+ * returns null instead of throwing NoSuchFieldException.
*/
private Field internalGetField(String name)
{
@@ -1306,4 +1385,411 @@ public final class Class implements Serializable
sm.checkPackageAccess(pkg.getName());
}
}
+
+ /**
+ * Returns the enumeration constants of this class, or
+ * null if this class is not an <code>Enum</code>.
+ *
+ * @return an array of <code>Enum</code> constants
+ * associated with this class, or null if this
+ * class is not an <code>enum</code>.
+ * @since 1.5
+ */
+ /* FIXME[GENERICS]: T[] getEnumConstants() */
+ public Object[] getEnumConstants()
+ {
+ if (isEnum())
+ {
+ try
+ {
+ return (Object[])
+ getMethod("values", new Class[0]).invoke(null, new Object[0]);
+ }
+ catch (NoSuchMethodException exception)
+ {
+ throw new Error("Enum lacks values() method");
+ }
+ catch (IllegalAccessException exception)
+ {
+ throw new Error("Unable to access Enum class");
+ }
+ catch (InvocationTargetException exception)
+ {
+ throw new
+ RuntimeException("The values method threw an exception",
+ exception);
+ }
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ /**
+ * Returns true if this class is an <code>Enum</code>.
+ *
+ * @return true if this is an enumeration class.
+ * @since 1.5
+ */
+ public boolean isEnum()
+ {
+ int mod = VMClass.getModifiers (this, true);
+ return (mod & ENUM) != 0;
+ }
+
+ /**
+ * Returns true if this class is a synthetic class, generated by
+ * the compiler.
+ *
+ * @return true if this is a synthetic class.
+ * @since 1.5
+ */
+ public boolean isSynthetic()
+ {
+ int mod = VMClass.getModifiers (this, true);
+ return (mod & SYNTHETIC) != 0;
+ }
+
+ /**
+ * Returns true if this class is an <code>Annotation</code>.
+ *
+ * @return true if this is an annotation class.
+ * @since 1.5
+ */
+ public boolean isAnnotation()
+ {
+ int mod = VMClass.getModifiers (this, true);
+ return (mod & ANNOTATION) != 0;
+ }
+
+ /**
+ * Returns the simple name for this class, as used in the source
+ * code. For normal classes, this is the content returned by
+ * <code>getName()</code> which follows the last ".". Anonymous
+ * classes have no name, and so the result of calling this method is
+ * "". The simple name of an array consists of the simple name of
+ * its component type, followed by "[]". Thus, an array with the
+ * component type of an anonymous class has a simple name of simply
+ * "[]".
+ *
+ * @return the simple name for this class.
+ * @since 1.5
+ */
+ public String getSimpleName()
+ {
+ return VMClass.getSimpleName(this);
+ }
+
+ /**
+ * Returns this class' annotation for the specified annotation type,
+ * or <code>null</code> if no such annotation exists.
+ *
+ * @param annotationClass the type of annotation to look for.
+ * @return this class' annotation for the specified type, or
+ * <code>null</code> if no such annotation exists.
+ * @since 1.5
+ */
+ /* FIXME[GENERICS]: <T extends Annotation> T getAnnotation(Class <T>) */
+ public Annotation getAnnotation(Class annotationClass)
+ {
+ Annotation foundAnnotation = null;
+ Annotation[] annotations = getAnnotations();
+ for (int i = 0; i < annotations.length; i++)
+ if (annotations[i].annotationType() == annotationClass)
+ foundAnnotation = annotations[i];
+ return foundAnnotation;
+ }
+
+ /**
+ * Returns all annotations associated with this class. If there are
+ * no annotations associated with this class, then a zero-length array
+ * will be returned. The returned array may be modified by the client
+ * code, but this will have no effect on the annotation content of this
+ * class, and hence no effect on the return value of this method for
+ * future callers.
+ *
+ * @return this class' annotations.
+ * @since 1.5
+ */
+ public Annotation[] getAnnotations()
+ {
+ HashSet set = new HashSet();
+ set.addAll(Arrays.asList(getDeclaredAnnotations()));
+ Class[] interfaces = getInterfaces();
+ for (int i = 0; i < interfaces.length; i++)
+ set.addAll(Arrays.asList(interfaces[i].getAnnotations()));
+ Class superClass = getSuperclass();
+ if (superClass != null)
+ set.addAll(Arrays.asList(superClass.getAnnotations()));
+ return (Annotation[]) set.toArray(new Annotation[set.size()]);
+ }
+
+ /**
+ * <p>
+ * Returns the canonical name of this class, as defined by section
+ * 6.7 of the Java language specification. Each package, top-level class,
+ * top-level interface and primitive type has a canonical name. A member
+ * class has a canonical name, if its parent class has one. Likewise,
+ * an array type has a canonical name, if its component type does.
+ * Local or anonymous classes do not have canonical names.
+ * </p>
+ * <p>
+ * The canonical name for top-level classes, top-level interfaces and
+ * primitive types is always the same as the fully-qualified name.
+ * For array types, the canonical name is the canonical name of its
+ * component type with `[]' appended.
+ * </p>
+ * <p>
+ * The canonical name of a member class always refers to the place where
+ * the class was defined, and is composed of the canonical name of the
+ * defining class and the simple name of the member class, joined by `.'.
+ * For example, if a <code>Person</code> class has an inner class,
+ * <code>M</code>, then both its fully-qualified name and canonical name
+ * is <code>Person.M</code>. A subclass, <code>Staff</code>, of
+ * <code>Person</code> refers to the same inner class by the fully-qualified
+ * name of <code>Staff.M</code>, but its canonical name is still
+ * <code>Person.M</code>.
+ * </p>
+ * <p>
+ * Where no canonical name is present, <code>null</code> is returned.
+ * </p>
+ *
+ * @return the canonical name of the class, or <code>null</code> if the
+ * class doesn't have a canonical name.
+ * @since 1.5
+ */
+ public String getCanonicalName()
+ {
+ return VMClass.getCanonicalName(this);
+ }
+
+ /**
+ * Returns all annotations directly defined by this class. If there are
+ * no annotations associated with this class, then a zero-length array
+ * will be returned. The returned array may be modified by the client
+ * code, but this will have no effect on the annotation content of this
+ * class, and hence no effect on the return value of this method for
+ * future callers.
+ *
+ * @return the annotations directly defined by this class.
+ * @since 1.5
+ */
+ public Annotation[] getDeclaredAnnotations()
+ {
+ return VMClass.getDeclaredAnnotations(this);
+ }
+
+ /**
+ * Returns the class which immediately encloses this class. If this class
+ * is a top-level class, this method returns <code>null</code>.
+ *
+ * @return the immediate enclosing class, or <code>null</code> if this is
+ * a top-level class.
+ * @since 1.5
+ */
+ /* FIXME[GENERICS]: Should return Class<?> */
+ public Class getEnclosingClass()
+ {
+ return VMClass.getEnclosingClass(this);
+ }
+
+ /**
+ * Returns the constructor which immediately encloses this class. If
+ * this class is a top-level class, or a local or anonymous class
+ * immediately enclosed by a type definition, instance initializer
+ * or static initializer, then <code>null</code> is returned.
+ *
+ * @return the immediate enclosing constructor if this class is
+ * declared within a constructor. Otherwise, <code>null</code>
+ * is returned.
+ * @since 1.5
+ */
+ /* FIXME[GENERICS]: Should return Constructor<?> */
+ public Constructor getEnclosingConstructor()
+ {
+ return VMClass.getEnclosingConstructor(this);
+ }
+
+ /**
+ * Returns the method which immediately encloses this class. If
+ * this class is a top-level class, or a local or anonymous class
+ * immediately enclosed by a type definition, instance initializer
+ * or static initializer, then <code>null</code> is returned.
+ *
+ * @return the immediate enclosing method if this class is
+ * declared within a method. Otherwise, <code>null</code>
+ * is returned.
+ * @since 1.5
+ */
+ public Method getEnclosingMethod()
+ {
+ return VMClass.getEnclosingMethod(this);
+ }
+
+ /**
+ * <p>
+ * Returns an array of <code>Type</code> objects which represent the
+ * interfaces directly implemented by this class or extended by this
+ * interface.
+ * </p>
+ * <p>
+ * If one of the superinterfaces is a parameterized type, then the
+ * object returned for this interface reflects the actual type
+ * parameters used in the source code. Type parameters are created
+ * using the semantics specified by the <code>ParameterizedType</code>
+ * interface, and only if an instance has not already been created.
+ * </p>
+ * <p>
+ * The order of the interfaces in the array matches the order in which
+ * the interfaces are declared. For classes which represent an array,
+ * an array of two interfaces, <code>Cloneable</code> and
+ * <code>Serializable</code>, is always returned, with the objects in
+ * that order. A class representing a primitive type or void always
+ * returns an array of zero size.
+ * </p>
+ *
+ * @return an array of interfaces implemented or extended by this class.
+ * @throws GenericSignatureFormatError if the generic signature of one
+ * of the interfaces does not comply with that specified by the Java
+ * Virtual Machine specification, 3rd edition.
+ * @throws TypeNotPresentException if any of the superinterfaces refers
+ * to a non-existant type.
+ * @throws MalformedParameterizedTypeException if any of the interfaces
+ * refer to a parameterized type that can not be instantiated for
+ * some reason.
+ * @since 1.5
+ * @see java.lang.reflect.ParameterizedType
+ */
+ public Type[] getGenericInterfaces()
+ {
+ if (isPrimitive())
+ return new Type[0];
+
+ String sig = VMClass.getClassSignature(this);
+ if (sig == null)
+ return getInterfaces();
+
+ ClassSignatureParser p = new ClassSignatureParser(this, sig);
+ return p.getInterfaceTypes();
+ }
+
+ /**
+ * <p>
+ * Returns a <code>Type</code> object representing the direct superclass,
+ * whether class, interface, primitive type or void, of this class.
+ * If this class is an array class, then a class instance representing
+ * the <code>Object</code> class is returned. If this class is primitive,
+ * an interface, or a representation of either the <code>Object</code>
+ * class or void, then <code>null</code> is returned.
+ * </p>
+ * <p>
+ * If the superclass is a parameterized type, then the
+ * object returned for this interface reflects the actual type
+ * parameters used in the source code. Type parameters are created
+ * using the semantics specified by the <code>ParameterizedType</code>
+ * interface, and only if an instance has not already been created.
+ * </p>
+ *
+ * @return the superclass of this class.
+ * @throws GenericSignatureFormatError if the generic signature of the
+ * class does not comply with that specified by the Java
+ * Virtual Machine specification, 3rd edition.
+ * @throws TypeNotPresentException if the superclass refers
+ * to a non-existant type.
+ * @throws MalformedParameterizedTypeException if the superclass
+ * refers to a parameterized type that can not be instantiated for
+ * some reason.
+ * @since 1.5
+ * @see java.lang.reflect.ParameterizedType
+ */
+ public Type getGenericSuperclass()
+ {
+ if (isArray())
+ return Object.class;
+
+ if (isPrimitive() || isInterface() || this == Object.class)
+ return null;
+
+ String sig = VMClass.getClassSignature(this);
+ if (sig == null)
+ return getSuperclass();
+
+ ClassSignatureParser p = new ClassSignatureParser(this, sig);
+ return p.getSuperclassType();
+ }
+
+ /**
+ * Returns an array of <code>TypeVariable</code> objects that represents
+ * the type variables declared by this class, in declaration order.
+ * An array of size zero is returned if this class has no type
+ * variables.
+ *
+ * @return the type variables associated with this class.
+ * @throws GenericSignatureFormatError if the generic signature does
+ * not conform to the format specified in the Virtual Machine
+ * specification, version 3.
+ * @since 1.5
+ */
+ /* FIXME[GENERICS]: Should return TypeVariable<Class<T>> */
+ public TypeVariable[] getTypeParameters()
+ {
+ String sig = VMClass.getClassSignature(this);
+ if (sig == null)
+ return new TypeVariable[0];
+
+ ClassSignatureParser p = new ClassSignatureParser(this, sig);
+ return p.getTypeParameters();
+ }
+
+ /**
+ * Returns true if an annotation for the specified type is associated
+ * with this class. This is primarily a short-hand for using marker
+ * annotations.
+ *
+ * @param annotationClass the type of annotation to look for.
+ * @return true if an annotation exists for the specified type.
+ * @since 1.5
+ */
+ /* FIXME[GENERICS]: Should be Class<? extends Annotation> */
+ public boolean isAnnotationPresent(Class
+ annotationClass)
+ {
+ return getAnnotation(annotationClass) != null;
+ }
+
+ /**
+ * Returns true if this object represents an anonymous class.
+ *
+ * @return true if this object represents an anonymous class.
+ * @since 1.5
+ */
+ public boolean isAnonymousClass()
+ {
+ return VMClass.isAnonymousClass(this);
+ }
+
+ /**
+ * Returns true if this object represents an local class.
+ *
+ * @return true if this object represents an local class.
+ * @since 1.5
+ */
+ public boolean isLocalClass()
+ {
+ return VMClass.isLocalClass(this);
+ }
+
+ /**
+ * Returns true if this object represents an member class.
+ *
+ * @return true if this object represents an member class.
+ * @since 1.5
+ */
+ public boolean isMemberClass()
+ {
+ return VMClass.isMemberClass(this);
+ }
+
+
}
diff --git a/libjava/classpath/java/lang/ClassLoader.java b/libjava/classpath/java/lang/ClassLoader.java
index 9f586c4cffc..83ef98da342 100644
--- a/libjava/classpath/java/lang/ClassLoader.java
+++ b/libjava/classpath/java/lang/ClassLoader.java
@@ -469,7 +469,8 @@ public abstract class ClassLoader
if (domain == null)
domain = StaticData.defaultProtectionDomain;
- return VMClassLoader.defineClass(this, name, data, offset, len, domain);
+ return VMClassLoader.defineClassWithTransformers(this, name, data, offset,
+ len, domain);
}
/**
@@ -628,8 +629,9 @@ public abstract class ClassLoader
* @return an enumaration of all resources found
* @throws IOException if I/O errors occur in the process
* @since 1.2
+ * @specnote this was <code>final</code> prior to 1.5
*/
- public final Enumeration getResources(String name) throws IOException
+ public Enumeration getResources(String name) throws IOException
{
Enumeration parentResources;
if (parent == null)
@@ -834,7 +836,7 @@ public abstract class ClassLoader
throw new IllegalArgumentException("Package " + name
+ " already defined");
Package p = new Package(name, specTitle, specVendor, specVersion,
- implTitle, implVendor, implVersion, sealed);
+ implTitle, implVendor, implVersion, sealed, this);
synchronized (definedPackages)
{
definedPackages.put(name, p);
diff --git a/libjava/classpath/java/lang/Enum.java b/libjava/classpath/java/lang/Enum.java
new file mode 100644
index 00000000000..5344d5c7201
--- /dev/null
+++ b/libjava/classpath/java/lang/Enum.java
@@ -0,0 +1,248 @@
+/* Enum.java - Base class for all enums
+ Copyright (C) 2004, 2005 Free Software Foundation
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath 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 for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+package java.lang;
+
+import java.io.Serializable;
+import java.lang.reflect.Field;
+
+/**
+ * This class represents a Java enumeration. All enumerations are
+ * subclasses of this class.
+ *
+ * @author Tom Tromey (tromey@redhat.com)
+ * @author Andrew John Hughes (gnu_andrew@member.fsf.org)
+ * @since 1.5
+ */
+/* FIXME[GENERICS]: Should be Enum<T extends Enum<T>>
+ and Comparable<T> */
+public abstract class Enum
+ implements Comparable, Serializable
+{
+
+ /**
+ * For compatability with Sun's JDK
+ */
+ private static final long serialVersionUID = -4300926546619394005L;
+
+ /**
+ * The name of this enum constant.
+ */
+ String name;
+
+ /**
+ * The number of this enum constant. Each constant is given a number
+ * which matches the order in which it was declared, starting with zero.
+ */
+ int ordinal;
+
+ /**
+ * This constructor is used by the compiler to create enumeration constants.
+ *
+ * @param name the name of the enumeration constant.
+ * @param ordinal the number of the enumeration constant, based on the
+ * declaration order of the constants and starting from zero.
+ */
+ protected Enum(String name, int ordinal)
+ {
+ this.name = name;
+ this.ordinal = ordinal;
+ }
+
+ /**
+ * Returns an Enum for a enum class given a description string of
+ * the enum constant.
+ *
+ * @exception NullPointerException when etype or s are null.
+ * @exception IllegalArgumentException when there is no value s in
+ * the enum etype.
+ */
+ /* FIXME[GENERICS]: Should be <S extends Enum<S>> S valueOf(Class<S>) */
+ public static Enum valueOf(Class etype, String s)
+ {
+ if (etype == null || s == null)
+ throw new NullPointerException();
+
+ try
+ {
+ Field f = etype.getDeclaredField(s);
+ if (! f.isEnumConstant())
+ throw new IllegalArgumentException(s);
+ /* FIXME[GENERICS]: Should cast to S */
+ return (Enum) f.get(null);
+ }
+ catch (NoSuchFieldException exception)
+ {
+ throw new IllegalArgumentException(s);
+ }
+ catch (IllegalAccessException exception)
+ {
+ throw new Error("Unable to access Enum class");
+ }
+ }
+
+ /**
+ * Returns true if this enumeration is equivalent to the supplied object,
+ * <code>o</code>. Only one instance of an enumeration constant exists,
+ * so the comparison is simply done using <code>==</code>.
+ *
+ * @param o the object to compare to this.
+ * @return true if <code>this == o</code>.
+ */
+ public final boolean equals(Object o)
+ {
+ // Enum constants are singular, so we need only compare `=='.
+ return this == o;
+ }
+
+ /**
+ * Returns the hash code of this constant. This is simply the ordinal.
+ *
+ * @return the hash code of this enumeration constant.
+ */
+ public final int hashCode()
+ {
+ return ordinal;
+ }
+
+ /**
+ * Returns a textual representation of this enumeration constant.
+ * By default, this is simply the declared name of the constant, but
+ * specific enumeration types may provide an implementation more suited
+ * to the data being stored.
+ *
+ * @return a textual representation of this constant.
+ */
+ public String toString()
+ {
+ return name;
+ }
+
+ /**
+ * Returns an integer which represents the relative ordering of this
+ * enumeration constant. Enumeration constants are ordered by their
+ * ordinals, which represents their declaration order. So, comparing
+ * two identical constants yields zero, while one declared prior to
+ * this returns a positive integer and one declared after yields a
+ * negative integer.
+ *
+ * @param e the enumeration constant to compare.
+ * @return a negative integer if <code>e.ordinal < this.ordinal</code>,
+ * zero if <code>e.ordinal == this.ordinal</code> and a positive
+ * integer if <code>e.ordinal > this.ordinal</code>.
+ * @throws ClassCastException if <code>e</code> is not an enumeration
+ * constant of the same class.
+ */
+ public final int compareTo(Enum e)
+ {
+ if (getDeclaringClass() != e.getDeclaringClass())
+ throw new ClassCastException();
+ return ordinal - e.ordinal;
+ }
+
+ /**
+ * Returns an integer which represents the relative ordering of this
+ * enumeration constant. Enumeration constants are ordered by their
+ * ordinals, which represents their declaration order. So, comparing
+ * two identical constants yields zero, while one declared prior to
+ * this returns a positive integer and one declared after yields a
+ * negative integer.
+ *
+ * @param o the enumeration constant to compare.
+ * @return a negative integer if <code>e.ordinal < this.ordinal</code>,
+ * zero if <code>e.ordinal == this.ordinal</code> and a positive
+ * integer if <code>e.ordinal > this.ordinal</code>.
+ * @throws ClassCastException if <code>e</code> is not an enumeration
+ * constant of the same class.
+ */
+ /* FIXME[GENERICS]: Remove this method */
+ public final int compareTo(Object o)
+ {
+ return compareTo((Enum)o);
+ }
+
+ /**
+ * Cloning of enumeration constants is prevented, to maintain their
+ * singleton status.
+ *
+ * @return the cloned object.
+ * @throws CloneNotSupportedException as enumeration constants can't be
+ * cloned.
+ */
+ protected final Object clone() throws CloneNotSupportedException
+ {
+ throw new CloneNotSupportedException("can't clone an enum constant");
+ }
+
+ /**
+ * Returns the name of this enumeration constant.
+ *
+ * @return the name of the constant.
+ */
+ public final String name()
+ {
+ return name;
+ }
+
+ /**
+ * Returns the number of this enumeration constant, which represents
+ * the order in which it was originally declared, starting from zero.
+ *
+ * @return the number of this constant.
+ */
+ public final int ordinal()
+ {
+ return ordinal;
+ }
+
+ /**
+ * Returns the type of this enumeration constant. This is the class
+ * corresponding to the declaration of the enumeration.
+ *
+ * @return the type of this enumeration constant.
+ */
+ /* FIXME[GENERICS]: Should return Class<T> */
+ public final Class getDeclaringClass()
+ {
+ Class k = getClass();
+ // We might be in an anonymous subclass of the enum class, so go
+ // up one more level.
+ if (k.getSuperclass() != Enum.class)
+ k = k.getSuperclass();
+ return k;
+ }
+}
diff --git a/libjava/classpath/java/lang/EnumConstantNotPresentException.java b/libjava/classpath/java/lang/EnumConstantNotPresentException.java
index dbec9d658ef..12b30fda599 100644
--- a/libjava/classpath/java/lang/EnumConstantNotPresentException.java
+++ b/libjava/classpath/java/lang/EnumConstantNotPresentException.java
@@ -48,6 +48,8 @@ package java.lang;
*/
public class EnumConstantNotPresentException extends RuntimeException
{
+ private static final long serialVersionUID = -6046998521960521108L;
+
/**
* The enum's type. Note that the name is fixed by the
* serialization spec.
diff --git a/libjava/classpath/java/lang/Iterable.java b/libjava/classpath/java/lang/Iterable.java
new file mode 100644
index 00000000000..8223bcf8c93
--- /dev/null
+++ b/libjava/classpath/java/lang/Iterable.java
@@ -0,0 +1,59 @@
+/* Iterable.java -- Notes collection over which one may iterate
+ Copyright (C) 2004 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath 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 for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package java.lang;
+
+import java.util.Iterator;
+
+/**
+ * This interface is used to indicate that a given class can be
+ * iterated over. The compiler uses this interface to determine which
+ * classes are suitable targets of the <code>foreach</code> construct.
+ *
+ * @author Tom Tromey <tromey@redhat.com>
+ * @since 1.5
+ */
+public interface Iterable
+{
+ /**
+ * Returns an iterator for the collection.
+ *
+ * @return an iterator.
+ */
+ Iterator iterator ();
+}
diff --git a/libjava/classpath/java/lang/Math.java b/libjava/classpath/java/lang/Math.java
index d7c8aa1c433..90574d52fc8 100644
--- a/libjava/classpath/java/lang/Math.java
+++ b/libjava/classpath/java/lang/Math.java
@@ -948,4 +948,105 @@ public final class Math
return VMMath.tanh(a);
}
+ /**
+ * Return the ulp for the given double argument. The ulp is the
+ * difference between the argument and the next larger double. Note
+ * that the sign of the double argument is ignored, that is,
+ * ulp(x) == ulp(-x). If the argument is a NaN, then NaN is returned.
+ * If the argument is an infinity, then +Inf is returned. If the
+ * argument is zero (either positive or negative), then
+ * {@link Double#MIN_VALUE} is returned.
+ * @param d the double whose ulp should be returned
+ * @return the difference between the argument and the next larger double
+ * @since 1.5
+ */
+ public static double ulp(double d)
+ {
+ if (Double.isNaN(d))
+ return d;
+ if (Double.isInfinite(d))
+ return Double.POSITIVE_INFINITY;
+ // This handles both +0.0 and -0.0.
+ if (d == 0.0)
+ return Double.MIN_VALUE;
+ long bits = Double.doubleToLongBits(d);
+ final int mantissaBits = 52;
+ final int exponentBits = 11;
+ final long mantMask = (1L << mantissaBits) - 1;
+ long mantissa = bits & mantMask;
+ final long expMask = (1L << exponentBits) - 1;
+ long exponent = (bits >>> mantissaBits) & expMask;
+
+ // Denormal number, so the answer is easy.
+ if (exponent == 0)
+ {
+ long result = (exponent << mantissaBits) | 1L;
+ return Double.longBitsToDouble(result);
+ }
+
+ // Conceptually we want to have '1' as the mantissa. Then we would
+ // shift the mantissa over to make a normal number. If this underflows
+ // the exponent, we will make a denormal result.
+ long newExponent = exponent - mantissaBits;
+ long newMantissa;
+ if (newExponent > 0)
+ newMantissa = 0;
+ else
+ {
+ newMantissa = 1L << -(newExponent - 1);
+ newExponent = 0;
+ }
+ return Double.longBitsToDouble((newExponent << mantissaBits) | newMantissa);
+ }
+
+ /**
+ * Return the ulp for the given float argument. The ulp is the
+ * difference between the argument and the next larger float. Note
+ * that the sign of the float argument is ignored, that is,
+ * ulp(x) == ulp(-x). If the argument is a NaN, then NaN is returned.
+ * If the argument is an infinity, then +Inf is returned. If the
+ * argument is zero (either positive or negative), then
+ * {@link Float#MIN_VALUE} is returned.
+ * @param f the float whose ulp should be returned
+ * @return the difference between the argument and the next larger float
+ * @since 1.5
+ */
+ public static float ulp(float f)
+ {
+ if (Float.isNaN(f))
+ return f;
+ if (Float.isInfinite(f))
+ return Float.POSITIVE_INFINITY;
+ // This handles both +0.0 and -0.0.
+ if (f == 0.0)
+ return Float.MIN_VALUE;
+ int bits = Float.floatToIntBits(f);
+ final int mantissaBits = 23;
+ final int exponentBits = 8;
+ final int mantMask = (1 << mantissaBits) - 1;
+ int mantissa = bits & mantMask;
+ final int expMask = (1 << exponentBits) - 1;
+ int exponent = (bits >>> mantissaBits) & expMask;
+
+ // Denormal number, so the answer is easy.
+ if (exponent == 0)
+ {
+ int result = (exponent << mantissaBits) | 1;
+ return Float.intBitsToFloat(result);
+ }
+
+ // Conceptually we want to have '1' as the mantissa. Then we would
+ // shift the mantissa over to make a normal number. If this underflows
+ // the exponent, we will make a denormal result.
+ int newExponent = exponent - mantissaBits;
+ int newMantissa;
+ if (newExponent > 0)
+ newMantissa = 0;
+ else
+ {
+ newMantissa = 1 << -(newExponent - 1);
+ newExponent = 0;
+ }
+ return Float.intBitsToFloat((newExponent << mantissaBits) | newMantissa);
+ }
}
diff --git a/libjava/classpath/java/lang/Package.java b/libjava/classpath/java/lang/Package.java
index 4cded0af304..38bb3240de4 100644
--- a/libjava/classpath/java/lang/Package.java
+++ b/libjava/classpath/java/lang/Package.java
@@ -1,5 +1,6 @@
/* Package.java -- information about a package
- Copyright (C) 2000, 2001, 2002, 2003, 2005 Free Software Foundation, Inc.
+ Copyright (C) 2000, 2001, 2002, 2003, 2005, 2006
+ Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -39,6 +40,8 @@ package java.lang;
import gnu.classpath.VMStackWalker;
+import java.lang.annotation.Annotation;
+import java.lang.reflect.AnnotatedElement;
import java.net.URL;
import java.util.NoSuchElementException;
import java.util.StringTokenizer;
@@ -70,9 +73,10 @@ import java.util.StringTokenizer;
* @see ClassLoader#definePackage(String, String, String, String, String,
* String, String, URL)
* @since 1.2
- * @status updated to 1.4
+ * @status updated to 1.5
*/
public class Package
+ implements AnnotatedElement
{
/** The name of the Package */
private final String name;
@@ -98,6 +102,20 @@ public class Package
/** If sealed the origin of the package classes, otherwise null */
private final URL sealed;
+ /** The class loader that defined this package */
+ private ClassLoader loader;
+
+ /** @deprecated Please use the other constructor that takes the class loader
+ * that defines the Package.
+ */
+ Package(String name,
+ String specTitle, String specVendor, String specVersion,
+ String implTitle, String implVendor, String implVersion, URL sealed)
+ {
+ this(name, specTitle, specVendor, specVersion, implTitle, implVendor,
+ implVersion, sealed, null);
+ }
+
/**
* A package local constructor for the Package class. All parameters except
* the <code>name</code> of the package may be <code>null</code>.
@@ -115,7 +133,8 @@ public class Package
*/
Package(String name,
String specTitle, String specVendor, String specVersion,
- String implTitle, String implVendor, String implVersion, URL sealed)
+ String implTitle, String implVendor, String implVersion, URL sealed,
+ ClassLoader loader)
{
if (name == null)
throw new IllegalArgumentException("null Package name");
@@ -128,6 +147,7 @@ public class Package
this.specVendor = specVendor;
this.specVersion = specVersion;
this.sealed = sealed;
+ this.loader = loader;
}
/**
@@ -233,7 +253,7 @@ public class Package
*
* @return true if the version is compatible, false otherwise
*
- * @Throws NumberFormatException if either version string is invalid
+ * @throws NumberFormatException if either version string is invalid
* @throws NullPointerException if either version string is null
*/
public boolean isCompatibleWith(String version)
@@ -315,4 +335,82 @@ public class Package
return ("package " + name + (specTitle == null ? "" : ", " + specTitle)
+ (specVersion == null ? "" : ", version " + specVersion));
}
+
+ /**
+ * Returns this package's annotation for the specified annotation type,
+ * or <code>null</code> if no such annotation exists.
+ *
+ * @param annotationClass the type of annotation to look for.
+ * @return this package's annotation for the specified type, or
+ * <code>null</code> if no such annotation exists.
+ * @since 1.5
+ */
+ /* FIXME[GENERICS]: <T extends Annotation> T getAnnotation(Class <T>) */
+ public Annotation getAnnotation(Class annotationClass)
+ {
+ Annotation foundAnnotation = null;
+ Annotation[] annotations = getAnnotations();
+ for (int i = 0; i < annotations.length; i++)
+ if (annotations[i].annotationType() == annotationClass)
+ foundAnnotation = annotations[i];
+ return foundAnnotation;
+ }
+
+ /**
+ * Returns all annotations associated with this package. If there are
+ * no annotations associated with this package, then a zero-length array
+ * will be returned. The returned array may be modified by the client
+ * code, but this will have no effect on the annotation content of this
+ * package, and hence no effect on the return value of this method for
+ * future callers.
+ *
+ * @return this package' annotations.
+ * @since 1.5
+ */
+ public Annotation[] getAnnotations()
+ {
+ /** All a package's annotations are declared within it. */
+ return getDeclaredAnnotations();
+ }
+
+ /**
+ * Returns all annotations directly defined by this package. If there are
+ * no annotations associated with this package, then a zero-length array
+ * will be returned. The returned array may be modified by the client
+ * code, but this will have no effect on the annotation content of this
+ * package, and hence no effect on the return value of this method for
+ * future callers.
+ *
+ * @return the annotations directly defined by this package.
+ * @since 1.5
+ */
+ public Annotation[] getDeclaredAnnotations()
+ {
+ try
+ {
+ Class pkgInfo = Class.forName(name + ".package-info", false, loader);
+ return pkgInfo.getDeclaredAnnotations();
+ }
+ catch (ClassNotFoundException _)
+ {
+ return new Annotation[0];
+ }
+ }
+
+ /**
+ * Returns true if an annotation for the specified type is associated
+ * with this package. This is primarily a short-hand for using marker
+ * annotations.
+ *
+ * @param annotationClass the type of annotation to look for.
+ * @return true if an annotation exists for the specified type.
+ * @since 1.5
+ */
+ /* FIXME[GENERICS]: Signature is Class<? extends Annotation> */
+ public boolean isAnnotationPresent(Class
+ annotationClass)
+ {
+ return getAnnotation(annotationClass) != null;
+ }
+
} // class Package
diff --git a/libjava/classpath/java/lang/StackTraceElement.java b/libjava/classpath/java/lang/StackTraceElement.java
index cf4d1c76f4d..746dd63db49 100644
--- a/libjava/classpath/java/lang/StackTraceElement.java
+++ b/libjava/classpath/java/lang/StackTraceElement.java
@@ -1,5 +1,5 @@
/* StackTraceElement.java -- One function call or call stack element
- Copyright (C) 2001, 2002, 2004, 2005 Free Software Foundation, Inc.
+ Copyright (C) 2001, 2002, 2004, 2005, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -211,7 +211,7 @@ public final class StackTraceElement implements Serializable
}
if (methodName != null)
sb.append(methodName);
- sb.append(" (");
+ sb.append("(");
if (fileName != null)
sb.append(fileName);
else
diff --git a/libjava/classpath/java/lang/StrictMath.java b/libjava/classpath/java/lang/StrictMath.java
index 2079cc11e41..548a6f1c16e 100644
--- a/libjava/classpath/java/lang/StrictMath.java
+++ b/libjava/classpath/java/lang/StrictMath.java
@@ -1841,4 +1841,84 @@ public final strictfp class StrictMath
double t = (float) a;
return t + a * (1 + t * z + t * v);
}
+
+ /**
+ * <p>
+ * Returns the sign of the argument as follows:
+ * </p>
+ * <ul>
+ * <li>If <code>a</code> is greater than zero, the result is 1.0.</li>
+ * <li>If <code>a</code> is less than zero, the result is -1.0.</li>
+ * <li>If <code>a</code> is <code>NaN</code>, the result is <code>NaN</code>.
+ * <li>If <code>a</code> is positive or negative zero, the result is the
+ * same.</li>
+ * </ul>
+ *
+ * @param a the numeric argument.
+ * @return the sign of the argument.
+ * @since 1.5.
+ */
+ public static double signum(double a)
+ {
+ // There's no difference.
+ return Math.signum(a);
+ }
+
+ /**
+ * <p>
+ * Returns the sign of the argument as follows:
+ * </p>
+ * <ul>
+ * <li>If <code>a</code> is greater than zero, the result is 1.0f.</li>
+ * <li>If <code>a</code> is less than zero, the result is -1.0f.</li>
+ * <li>If <code>a</code> is <code>NaN</code>, the result is <code>NaN</code>.
+ * <li>If <code>a</code> is positive or negative zero, the result is the
+ * same.</li>
+ * </ul>
+ *
+ * @param a the numeric argument.
+ * @return the sign of the argument.
+ * @since 1.5.
+ */
+ public static float signum(float a)
+ {
+ // There's no difference.
+ return Math.signum(a);
+ }
+
+ /**
+ * Return the ulp for the given double argument. The ulp is the
+ * difference between the argument and the next larger double. Note
+ * that the sign of the double argument is ignored, that is,
+ * ulp(x) == ulp(-x). If the argument is a NaN, then NaN is returned.
+ * If the argument is an infinity, then +Inf is returned. If the
+ * argument is zero (either positive or negative), then
+ * {@link Double#MIN_VALUE} is returned.
+ * @param d the double whose ulp should be returned
+ * @return the difference between the argument and the next larger double
+ * @since 1.5
+ */
+ public static double ulp(double d)
+ {
+ // There's no difference.
+ return Math.ulp(d);
+ }
+
+ /**
+ * Return the ulp for the given float argument. The ulp is the
+ * difference between the argument and the next larger float. Note
+ * that the sign of the float argument is ignored, that is,
+ * ulp(x) == ulp(-x). If the argument is a NaN, then NaN is returned.
+ * If the argument is an infinity, then +Inf is returned. If the
+ * argument is zero (either positive or negative), then
+ * {@link Float#MIN_VALUE} is returned.
+ * @param f the float whose ulp should be returned
+ * @return the difference between the argument and the next larger float
+ * @since 1.5
+ */
+ public static float ulp(float f)
+ {
+ // There's no difference.
+ return Math.ulp(f);
+ }
}
diff --git a/libjava/classpath/java/lang/StringBuilder.java b/libjava/classpath/java/lang/StringBuilder.java
index 01a83ca707b..98af48f8fb0 100644
--- a/libjava/classpath/java/lang/StringBuilder.java
+++ b/libjava/classpath/java/lang/StringBuilder.java
@@ -206,7 +206,7 @@ public final class StringBuilder
int max = value.length * 2 + 2;
minimumCapacity = (minimumCapacity < max ? max : minimumCapacity);
char[] nb = new char[minimumCapacity];
- System.arraycopy(value, 0, nb, 0, count);
+ VMSystem.arraycopy(value, 0, nb, 0, count);
value = nb;
}
}
@@ -285,7 +285,7 @@ public final class StringBuilder
{
if (srcOffset < 0 || srcEnd > count || srcEnd < srcOffset)
throw new StringIndexOutOfBoundsException();
- System.arraycopy(value, srcOffset, dst, dstOffset, srcEnd - srcOffset);
+ VMSystem.arraycopy(value, srcOffset, dst, dstOffset, srcEnd - srcOffset);
}
/**
@@ -355,7 +355,7 @@ public final class StringBuilder
{
int len = stringBuffer.count;
ensureCapacity(count + len);
- System.arraycopy(stringBuffer.value, 0, value, count, len);
+ VMSystem.arraycopy(stringBuffer.value, 0, value, count, len);
count += len;
}
return this;
@@ -395,7 +395,7 @@ public final class StringBuilder
if (offset < 0 || count < 0 || offset > data.length - count)
throw new StringIndexOutOfBoundsException();
ensureCapacity(this.count + count);
- System.arraycopy(data, offset, value, this.count, count);
+ VMSystem.arraycopy(data, offset, value, this.count, count);
this.count += count;
return this;
}
@@ -558,7 +558,7 @@ public final class StringBuilder
// This will unshare if required.
ensureCapacity(count);
if (count - end != 0)
- System.arraycopy(value, end, value, start, count - end);
+ VMSystem.arraycopy(value, end, value, start, count - end);
count -= end - start;
return this;
}
@@ -599,7 +599,7 @@ public final class StringBuilder
ensureCapacity(count + delta);
if (delta != 0 && end < count)
- System.arraycopy(value, end, value, end + delta, count - end);
+ VMSystem.arraycopy(value, end, value, end + delta, count - end);
str.getChars(0, len, value, start);
count += delta;
@@ -677,8 +677,8 @@ public final class StringBuilder
|| str_offset < 0 || str_offset > str.length - len)
throw new StringIndexOutOfBoundsException();
ensureCapacity(count + len);
- System.arraycopy(value, offset, value, offset + len, count - offset);
- System.arraycopy(str, str_offset, value, offset, len);
+ VMSystem.arraycopy(value, offset, value, offset + len, count - offset);
+ VMSystem.arraycopy(str, str_offset, value, offset, len);
count += len;
return this;
}
@@ -717,7 +717,7 @@ public final class StringBuilder
str = "null";
int len = str.count;
ensureCapacity(count + len);
- System.arraycopy(value, offset, value, offset + len, count - offset);
+ VMSystem.arraycopy(value, offset, value, offset + len, count - offset);
str.getChars(0, len, value, offset);
count += len;
return this;
@@ -814,7 +814,7 @@ public final class StringBuilder
if (offset < 0 || offset > count)
throw new StringIndexOutOfBoundsException(offset);
ensureCapacity(count + 1);
- System.arraycopy(value, offset, value, offset + 1, count - offset);
+ VMSystem.arraycopy(value, offset, value, offset + 1, count - offset);
value[offset] = ch;
count++;
return this;
@@ -1063,7 +1063,7 @@ public final class StringBuilder
if (count < value.length)
{
char[] newValue = new char[count];
- System.arraycopy(value, 0, newValue, 0, count);
+ VMSystem.arraycopy(value, 0, newValue, 0, count);
value = newValue;
}
}
diff --git a/libjava/classpath/java/lang/System.java b/libjava/classpath/java/lang/System.java
index 34bbfddc672..b538b795b95 100644
--- a/libjava/classpath/java/lang/System.java
+++ b/libjava/classpath/java/lang/System.java
@@ -364,7 +364,7 @@ public final class System
SecurityManager sm = SecurityManager.current; // Be thread-safe.
if (sm != null)
sm.checkPropertyAccess(key);
- else if (key.length() == 0)
+ if (key.length() == 0)
throw new IllegalArgumentException("key can't be empty");
return SystemProperties.getProperty(key);
}
@@ -385,6 +385,10 @@ public final class System
SecurityManager sm = SecurityManager.current; // Be thread-safe.
if (sm != null)
sm.checkPropertyAccess(key);
+ // This handles both the null pointer exception and the illegal
+ // argument exception.
+ if (key.length() == 0)
+ throw new IllegalArgumentException("key can't be empty");
return SystemProperties.getProperty(key, def);
}
@@ -405,10 +409,37 @@ public final class System
SecurityManager sm = SecurityManager.current; // Be thread-safe.
if (sm != null)
sm.checkPermission(new PropertyPermission(key, "write"));
+ // This handles both the null pointer exception and the illegal
+ // argument exception.
+ if (key.length() == 0)
+ throw new IllegalArgumentException("key can't be empty");
return SystemProperties.setProperty(key, value);
}
/**
+ * Remove a single system property by name. A security check may be
+ * performed, <code>checkPropertyAccess(key, "write")</code>.
+ *
+ * @param key the name of the system property to remove
+ * @return the previous value, or null
+ * @throws SecurityException if permission is denied
+ * @throws NullPointerException if key is null
+ * @throws IllegalArgumentException if key is ""
+ * @since 1.5
+ */
+ public static String clearProperty(String key)
+ {
+ SecurityManager sm = SecurityManager.current; // Be thread-safe.
+ if (sm != null)
+ sm.checkPermission(new PropertyPermission(key, "write"));
+ // This handles both the null pointer exception and the illegal
+ // argument exception.
+ if (key.length() == 0)
+ throw new IllegalArgumentException("key can't be empty");
+ return SystemProperties.remove(key);
+ }
+
+ /**
* Gets the value of an environment variable.
*
* @param name the name of the environment variable
diff --git a/libjava/classpath/java/lang/Thread.java b/libjava/classpath/java/lang/Thread.java
index 76df1037bb5..23620543aef 100644
--- a/libjava/classpath/java/lang/Thread.java
+++ b/libjava/classpath/java/lang/Thread.java
@@ -1,5 +1,5 @@
/* Thread -- an independent thread of executable code
- Copyright (C) 1998, 1999, 2000, 2001, 2002, 2003, 2004
+ Copyright (C) 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006
Free Software Foundation
This file is part of GNU Classpath.
@@ -81,6 +81,7 @@ import java.util.Map;
* @author Tom Tromey
* @author John Keiser
* @author Eric Blake (ebb9@email.byu.edu)
+ * @author Andrew John Hughes (gnu_andrew@member.fsf.org)
* @see Runnable
* @see Runtime#exit(int)
* @see #run()
@@ -130,15 +131,27 @@ public class Thread implements Runnable
/** The context classloader for this Thread. */
private ClassLoader contextClassLoader;
+
+ /** This thread's ID. */
+ private final long threadId;
/** The next thread number to use. */
private static int numAnonymousThreadsCreated;
+
+ /** The next thread ID to use. */
+ private static long nextThreadId;
+
+ /** The default exception handler. */
+ private static UncaughtExceptionHandler defaultHandler;
/** Thread local storage. Package accessible for use by
* InheritableThreadLocal.
*/
WeakIdentityHashMap locals;
+ /** The uncaught exception handler. */
+ UncaughtExceptionHandler exceptionHandler;
+
/**
* Allocates a new <code>Thread</code> object. This constructor has
* the same effect as <code>Thread(null, null,</code>
@@ -342,6 +355,11 @@ public class Thread implements Runnable
this.name = name.toString();
this.runnable = target;
this.stacksize = size;
+
+ synchronized (Thread.class)
+ {
+ this.threadId = nextThreadId++;
+ }
priority = current.priority;
daemon = current.daemon;
@@ -371,6 +389,11 @@ public class Thread implements Runnable
this.priority = priority;
this.daemon = daemon;
this.contextClassLoader = ClassLoader.getSystemClassLoader();
+ synchronized (Thread.class)
+ {
+ this.threadId = nextThreadId++;
+ }
+
}
/**
@@ -434,6 +457,19 @@ public class Thread implements Runnable
/**
* Originally intended to destroy this thread, this method was never
* implemented by Sun, and is hence a no-op.
+ *
+ * @deprecated This method was originally intended to simply destroy
+ * the thread without performing any form of cleanup operation.
+ * However, it was never implemented. It is now deprecated
+ * for the same reason as <code>suspend()</code>,
+ * <code>stop()</code> and <code>resume()</code>; namely,
+ * it is prone to deadlocks. If a thread is destroyed while
+ * it still maintains a lock on a resource, then this resource
+ * will remain locked and any attempts by other threads to
+ * access the resource will result in a deadlock. Thus, even
+ * an implemented version of this method would be still be
+ * deprecated, due to its unsafe nature.
+ * @throws NoSuchMethodError as this method was never implemented.
*/
public void destroy()
{
@@ -1000,4 +1036,159 @@ public class Thread implements Runnable
}
return locals;
}
+
+ /**
+ * Assigns the given <code>UncaughtExceptionHandler</code> to this
+ * thread. This will then be called if the thread terminates due
+ * to an uncaught exception, pre-empting that of the
+ * <code>ThreadGroup</code>.
+ *
+ * @param h the handler to use for this thread.
+ * @throws SecurityException if the current thread can't modify this thread.
+ * @since 1.5
+ */
+ public void setUncaughtExceptionHandler(UncaughtExceptionHandler h)
+ {
+ SecurityManager sm = SecurityManager.current; // Be thread-safe.
+ if (sm != null)
+ sm.checkAccess(this);
+ exceptionHandler = h;
+ }
+
+ /**
+ * <p>
+ * Returns the handler used when this thread terminates due to an
+ * uncaught exception. The handler used is determined by the following:
+ * </p>
+ * <ul>
+ * <li>If this thread has its own handler, this is returned.</li>
+ * <li>If not, then the handler of the thread's <code>ThreadGroup</code>
+ * object is returned.</li>
+ * <li>If both are unavailable, then <code>null</code> is returned
+ * (which can only happen when the thread was terminated since
+ * then it won't have an associated thread group anymore).</li>
+ * </ul>
+ *
+ * @return the appropriate <code>UncaughtExceptionHandler</code> or
+ * <code>null</code> if one can't be obtained.
+ * @since 1.5
+ */
+ public UncaughtExceptionHandler getUncaughtExceptionHandler()
+ {
+ return exceptionHandler != null ? exceptionHandler : group;
+ }
+
+ /**
+ * <p>
+ * Sets the default uncaught exception handler used when one isn't
+ * provided by the thread or its associated <code>ThreadGroup</code>.
+ * This exception handler is used when the thread itself does not
+ * have an exception handler, and the thread's <code>ThreadGroup</code>
+ * does not override this default mechanism with its own. As the group
+ * calls this handler by default, this exception handler should not defer
+ * to that of the group, as it may lead to infinite recursion.
+ * </p>
+ * <p>
+ * Uncaught exception handlers are used when a thread terminates due to
+ * an uncaught exception. Replacing this handler allows default code to
+ * be put in place for all threads in order to handle this eventuality.
+ * </p>
+ *
+ * @param h the new default uncaught exception handler to use.
+ * @throws SecurityException if a security manager is present and
+ * disallows the runtime permission
+ * "setDefaultUncaughtExceptionHandler".
+ * @since 1.5
+ */
+ public static void
+ setDefaultUncaughtExceptionHandler(UncaughtExceptionHandler h)
+ {
+ SecurityManager sm = SecurityManager.current; // Be thread-safe.
+ if (sm != null)
+ sm.checkPermission(new RuntimePermission("setDefaultUncaughtExceptionHandler"));
+ defaultHandler = h;
+ }
+
+ /**
+ * Returns the handler used by default when a thread terminates
+ * unexpectedly due to an exception, or <code>null</code> if one doesn't
+ * exist.
+ *
+ * @return the default uncaught exception handler.
+ * @since 1.5
+ */
+ public static UncaughtExceptionHandler getDefaultUncaughtExceptionHandler()
+ {
+ return defaultHandler;
+ }
+
+ /**
+ * Returns the unique identifier for this thread. This ID is generated
+ * on thread creation, and may be re-used on its death.
+ *
+ * @return a positive long number representing the thread's ID.
+ * @since 1.5
+ */
+ public long getId()
+ {
+ return threadId;
+ }
+
+ /**
+ * <p>
+ * This interface is used to handle uncaught exceptions
+ * which cause a <code>Thread</code> to terminate. When
+ * a thread, t, is about to terminate due to an uncaught
+ * exception, the virtual machine looks for a class which
+ * implements this interface, in order to supply it with
+ * the dying thread and its uncaught exception.
+ * </p>
+ * <p>
+ * The virtual machine makes two attempts to find an
+ * appropriate handler for the uncaught exception, in
+ * the following order:
+ * </p>
+ * <ol>
+ * <li>
+ * <code>t.getUncaughtExceptionHandler()</code> --
+ * the dying thread is queried first for a handler
+ * specific to that thread.
+ * </li>
+ * <li>
+ * <code>t.getThreadGroup()</code> --
+ * the thread group of the dying thread is used to
+ * handle the exception. If the thread group has
+ * no special requirements for handling the exception,
+ * it may simply forward it on to
+ * <code>Thread.getDefaultUncaughtExceptionHandler()</code>,
+ * the default handler, which is used as a last resort.
+ * </li>
+ * </ol>
+ * <p>
+ * The first handler found is the one used to handle
+ * the uncaught exception.
+ * </p>
+ *
+ * @author Tom Tromey <tromey@redhat.com>
+ * @author Andrew John Hughes <gnu_andrew@member.fsf.org>
+ * @since 1.5
+ * @see Thread#getUncaughtExceptionHandler()
+ * @see Thread#setUncaughtExceptionHander(java.lang.Thread.UncaughtExceptionHandler)
+ * @see Thread#getDefaultUncaughtExceptionHandler()
+ * @see
+ * Thread#setDefaultUncaughtExceptionHandler(java.lang.Thread.UncaughtExceptionHandler)
+ */
+ public interface UncaughtExceptionHandler
+ {
+ /**
+ * Invoked by the virtual machine with the dying thread
+ * and the uncaught exception. Any exceptions thrown
+ * by this method are simply ignored by the virtual
+ * machine.
+ *
+ * @param thr the dying thread.
+ * @param exc the uncaught exception.
+ */
+ void uncaughtException(Thread thr, Throwable exc);
+ }
}
diff --git a/libjava/classpath/java/lang/ThreadGroup.java b/libjava/classpath/java/lang/ThreadGroup.java
index 6e4c27a7135..7fbef88f4d6 100644
--- a/libjava/classpath/java/lang/ThreadGroup.java
+++ b/libjava/classpath/java/lang/ThreadGroup.java
@@ -37,6 +37,7 @@ exception statement from your version. */
package java.lang;
+import java.lang.Thread.UncaughtExceptionHandler;
import java.util.Vector;
/**
@@ -53,7 +54,7 @@ import java.util.Vector;
* @since 1.0
* @status updated to 1.4
*/
-public class ThreadGroup
+public class ThreadGroup implements UncaughtExceptionHandler
{
/** The Initial, top-level ThreadGroup. */
static ThreadGroup root = new ThreadGroup();
@@ -545,6 +546,8 @@ public class ThreadGroup
{
if (parent != null)
parent.uncaughtException(thread, t);
+ else if (Thread.getDefaultUncaughtExceptionHandler() != null)
+ Thread.getDefaultUncaughtExceptionHandler().uncaughtException(thread, t);
else if (! (t instanceof ThreadDeath))
{
if (t == null)
diff --git a/libjava/classpath/java/lang/ThreadLocal.java b/libjava/classpath/java/lang/ThreadLocal.java
index aceb2557a54..64df8c3dd26 100644
--- a/libjava/classpath/java/lang/ThreadLocal.java
+++ b/libjava/classpath/java/lang/ThreadLocal.java
@@ -152,4 +152,15 @@ public class ThreadLocal
// ever modify the map.
map.put(this, value == null ? NULL : value);
}
+
+ /**
+ * Removes the value associated with the ThreadLocal object for the
+ * currently executing Thread.
+ * @since 1.5
+ */
+ public void remove()
+ {
+ Map map = Thread.getThreadLocals();
+ map.remove(this);
+ }
}
diff --git a/libjava/classpath/java/lang/TypeNotPresentException.java b/libjava/classpath/java/lang/TypeNotPresentException.java
index 3010c968b6d..65d98457ec8 100644
--- a/libjava/classpath/java/lang/TypeNotPresentException.java
+++ b/libjava/classpath/java/lang/TypeNotPresentException.java
@@ -58,7 +58,8 @@ package java.lang;
public class TypeNotPresentException
extends RuntimeException
{
-
+ private static final long serialVersionUID = -5101214195716534496L;
+
/**
* Constructs a <code>TypeNotPresentException</code> for
* the supplied type. The specified cause <code>Throwable</code>
diff --git a/libjava/classpath/java/lang/annotation/Annotation.java b/libjava/classpath/java/lang/annotation/Annotation.java
new file mode 100644
index 00000000000..01e23930eea
--- /dev/null
+++ b/libjava/classpath/java/lang/annotation/Annotation.java
@@ -0,0 +1,136 @@
+/* Annotation.java - Base interface for all annotations
+ Copyright (C) 2004 Free Software Foundation
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath 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 for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+package java.lang.annotation;
+
+/**
+ * This is the common interface for all annotations. Note that classes
+ * that implement this class manually are not classed as annotations, and
+ * that this interface does not define an annotation type in itself.
+ *
+ * @author Tom Tromey (tromey@redhat.com)
+ * @author Andrew John Hughes (gnu_andrew@member.fsf.org)
+ * @since 1.5
+ */
+public interface Annotation
+{
+
+ /**
+ * Returns the type of this annotation.
+ *
+ * @return the class of which this annotation is an instance.
+ */
+ /* FIXME[GENERICS]: Should return Class<? extends Annotation> */
+ Class annotationType();
+
+ /**
+ * <p>
+ * Returns true if the supplied object is equivalent to this annotation.
+ * For this property to hold, the following must be true of <code>o</code>:
+ * </p>
+ * <ul>
+ * <li>The object is also an instance of the same annotation type.</li>
+ * <li>The members of the supplied annotation are equal to those of this
+ * annotation, according to the following:
+ * <ul>
+ * <li>If the members are <code>float</code>s, then, for floats
+ * <code>x</code> and <code>y</code>,
+ * <code>Float.valueOf(x).equals(Float.valueOf(y)</code> must return
+ * true. This differs from the usual (<code>==</code>) comparison
+ * in that <code>NaN</code> is considered equal to itself and positive
+ * and negative zero are seen as different.</li>
+ * <li>Likewise, if the members are <code>double</code>s, then, for doubles
+ * <code>x</code> and <code>y</code>,
+ * <code>Double.valueOf(x).equals(Double.valueOf(y)</code> must return
+ * true. This differs from the usual (<code>==</code>) comparison
+ * in that <code>NaN</code> is considered equal to itself and positive
+ * and negative zero are seen as different.</li>
+ * <li>Strings, classes, enumerations and annotations are considered
+ * equal according to the <code>equals()</code> implementation for these
+ * types.</li>
+ * <li>Arrays are considered equal according to <code>Arrays.equals()</code>
+ * </li>
+ * <li>Any remaining types are considered equal using <code>==</code>.</li>
+ * </li>
+ * </ul>
+ *
+ * @param o the object to compare with this annotation.
+ * @return true if the supplied object is an annotation with equivalent
+ * members.
+ */
+ boolean equals(Object o);
+
+ /**
+ * <p>
+ * Returns the hash code of the annotation. This is computed as the
+ * sum of the hash codes of the annotation's members.
+ * </p>
+ * <p>
+ * The hash code of a member of the annotation is the result of XORing
+ * the hash code of its value with the result of multiplying the hash code
+ * of its name by 127. Formally, if the value is <code>v</code> and the
+ * name is <code>n</code>, the hash code of the member is
+ * v.hashCode() XOR (127 * String.hashCode(n)). <code>v.hashCode()</code>
+ * is defined as follows:
+ * </p>
+ * <ul>
+ * <li>The hash code of a primitive value (i.e. <code>byte</code>,
+ * <code>char</code>, <code>double</code>, <code>float</code>,
+ * <code>int</code>, <code>long</code>, <code>short</code> and
+ * <code>boolean</code>) is the hash code obtained from its corresponding
+ * wrapper class using <code>valueOf(v).hashCode()</code>, where
+ * <code>v</code> is the primitive value.</li>
+ * <li>The hash code of an enumeration, string, class or other annotation
+ * is obtained using <code>v.hashCode()</code>.</li>
+ * <li>The hash code of an array is computed using
+ * <code>Arrays.hashCode(v)</code>.</li>
+ * </ul>
+ *
+ * @return the hash code of the annotation, computed as the sum of its
+ * member hashcodes.
+ */
+ int hashCode();
+
+ /**
+ * Returns a textual representation of the annotation. This is
+ * implementation-dependent, but is expected to include the classname
+ * and the names and values of each member.
+ *
+ * @return a textual representation of the annotation.
+ */
+ String toString();
+}
diff --git a/libjava/classpath/java/lang/annotation/AnnotationFormatError.java b/libjava/classpath/java/lang/annotation/AnnotationFormatError.java
index 40ce3ca10f7..36f60063274 100644
--- a/libjava/classpath/java/lang/annotation/AnnotationFormatError.java
+++ b/libjava/classpath/java/lang/annotation/AnnotationFormatError.java
@@ -49,6 +49,7 @@ package java.lang.annotation;
*/
public class AnnotationFormatError extends Error
{
+ private static final long serialVersionUID = -4256701562333669892L;
/**
* Constructs a new <code>AnnotationFormatError</code>
diff --git a/libjava/classpath/java/lang/class-dependencies.conf b/libjava/classpath/java/lang/class-dependencies.conf
deleted file mode 100644
index 4fbf75eb1ce..00000000000
--- a/libjava/classpath/java/lang/class-dependencies.conf
+++ /dev/null
@@ -1,58 +0,0 @@
-# This property file contains dependencies of classes, methods, and
-# field on other methods or classes.
-#
-# Syntax:
-#
-# <used>: <needed 1> [... <needed N>]
-#
-# means that when <used> is included, <needed 1> (... <needed N>) must
-# be included as well.
-#
-# <needed X> and <used> are of the form
-#
-# <class.methodOrField(signature)>
-#
-# or just
-#
-# <class>
-#
-# Within dependencies, variables can be used. A variable is defined as
-# follows:
-#
-# {variable}: value1 value2 ... value<n>
-#
-# variables can be used on the right side of dependencies as follows:
-#
-# <used>: com.bla.blu.{variable}.Class.m()V
-#
-# The use of the variable will expand to <n> dependencies of the form
-#
-# <used>: com.bla.blu.value1.Class.m()V
-# <used>: com.bla.blu.value2.Class.m()V
-# ...
-# <used>: com.bla.blu.value<n>.Class.m()V
-#
-# Variables can be redefined when building a system to select the
-# required support for features like encodings, protocols, etc.
-#
-# Hints:
-#
-# - For methods and fields, the signature is mandatory. For
-# specification, please see the Java Virtual Machine Specification by
-# SUN. Unlike in the spec, field signatures (types) are in brackets.
-#
-# - Package names must be separated by '/' (and not '.'). E.g.,
-# java/lang/Class (this is necessary, because the '.' is used to
-# separate method or field names from classes)
-#
-# - In case <needed> refers to a class, only the class itself will be
-# included in the resulting binary, NOT necessarily all its methods
-# and fields. If you want to refer to all methods and fields, you can
-# write class.* as an abbreviation.
-#
-# - Abbreviations for packages are also possible: my/package/* means all
-# methods and fields of all classes in my/package.
-#
-# - A line with a trailing '\' continues in the next line.
-
-# end of file
diff --git a/libjava/classpath/java/lang/instrument/ClassDefinition.java b/libjava/classpath/java/lang/instrument/ClassDefinition.java
new file mode 100644
index 00000000000..841597c31ed
--- /dev/null
+++ b/libjava/classpath/java/lang/instrument/ClassDefinition.java
@@ -0,0 +1,88 @@
+/* ClassDefinition.java -- Class that binds a class with a new class file
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath 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 for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package java.lang.instrument;
+
+/**
+ * This class binds a class that will be redefined with a new
+ * class file.
+ *
+ * @author Nicolas Geoffray (nicolas.geoffray@menlina.com)
+ * @see Instrumentation#redefineClasses(java.lang.instrument.ClassDefinition[])
+ * @since 1.5
+ */
+public final class ClassDefinition
+{
+
+ /* The class it's related */
+ private Class theClass;
+
+ /* The new bytecode of theClass */
+ private byte[] theClassFile;
+
+ /**
+ * @param theClass the Class that will be redefined
+ * @param theClassFile the new class file
+ * @throws NullPointerException if one of the argument is null
+ */
+ /* FIXME[GENERICS]: Signature should be (Class<?>, byte[]) */
+ public ClassDefinition(Class theClass, byte[] theClassFile)
+ {
+ if (theClass == null || theClassFile == null)
+ throw new NullPointerException();
+ this.theClass = theClass;
+ this.theClassFile = theClassFile;
+ }
+
+ /**
+ * @return the Class
+ */
+ /* FIXME[GENERICS]: Should return Class<?> */
+ public Class getDefinitionClass()
+ {
+ return theClass;
+ }
+
+ /**
+ * @return the bytes
+ */
+ public byte[] getDefinitionClassFile()
+ {
+ return theClassFile;
+ }
+}
diff --git a/libjava/classpath/java/lang/instrument/ClassFileTransformer.java b/libjava/classpath/java/lang/instrument/ClassFileTransformer.java
new file mode 100644
index 00000000000..68638d71971
--- /dev/null
+++ b/libjava/classpath/java/lang/instrument/ClassFileTransformer.java
@@ -0,0 +1,86 @@
+/* ClassFileTransformer.java -- Implementation of this interface is used by an agent to
+ transform class files.
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath 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 for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package java.lang.instrument;
+
+import java.security.ProtectionDomain;
+
+/**
+ * This interface should be implemented by classes wishing to transform
+ * classes bytecode when defining or redefining classes.
+ *
+ * @author Nicolas Geoffray (nicolas.geoffray@menlina.com)
+ * @see Instrumentation
+ * @see Instrumentation#addTransformer(java.lang.instrument.ClassFileTransformer)
+ * @see Instrumentation#removeTransformer(java.lang.instrument.ClassFileTransformer)
+ * @since 1.5
+ */
+public interface ClassFileTransformer
+{
+
+ /**
+ * Implementation of this method transforms a class by redefining its
+ * bytecodes. Once a ClassFileTransformer object registers itself to the
+ * Instrumentation object, this method will be called each time a class is
+ * defined (<code>ClassLoader.defineClass</code>) or redefined
+ * (<code>Instrumentation.redefineClasses</code>)
+ * @param loader the loader of the class
+ * @param className the name of the class with packages separated with "/"
+ * @param classBeingRedefined the class being redefined if it's the case,
+ * null otherwise
+ * @param protectionDomain the protection domain of the class being defined or
+ * redefined
+ * @param classfileBuffer the input byte buffer in class file format
+ *
+ * @return a class file buffer or null when no transformation has been performed
+ *
+ * @throws IllegalClassFormatException if the byte buffer does not represent
+ * a well-formed class file
+ * @see Instrumentation#redefineClasses(java.lang.instrument.ClassDefinition[])
+ *
+ */
+ /* FIXME[GENERICS]: Class should be Class<?> */
+ byte[] transform(ClassLoader loader,
+ String className,
+ Class classBeingRedefined,
+ ProtectionDomain protectionDomain,
+ byte[] classfileBuffer)
+ throws IllegalClassFormatException;
+}
+
diff --git a/libjava/classpath/java/lang/instrument/IllegalClassFormatException.java b/libjava/classpath/java/lang/instrument/IllegalClassFormatException.java
new file mode 100644
index 00000000000..c75bde003de
--- /dev/null
+++ b/libjava/classpath/java/lang/instrument/IllegalClassFormatException.java
@@ -0,0 +1,70 @@
+/* IllegalClassFormatException.java -- thrown when an array of byte does
+ not represent a valid class file
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath 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 for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package java.lang.instrument;
+
+/**
+ * @author Nicolas Geoffray (nicolas.geoffray@menlina.com)
+ * @since 1.5
+ */
+public class IllegalClassFormatException extends Exception
+{
+
+ /**
+ * Compatible with JDK 1.5+.
+ */
+ private static final long serialVersionUID = -3841736710924794009L;
+
+ /**
+ * Create an exception without a message.
+ */
+ public IllegalClassFormatException()
+ {
+ }
+
+ /**
+ * Create an exception with a message.
+ *
+ * @param s the message
+ */
+ public IllegalClassFormatException(String s)
+ {
+ super(s);
+ }
+}
diff --git a/libjava/classpath/java/lang/instrument/Instrumentation.java b/libjava/classpath/java/lang/instrument/Instrumentation.java
new file mode 100644
index 00000000000..81aefa6d6b8
--- /dev/null
+++ b/libjava/classpath/java/lang/instrument/Instrumentation.java
@@ -0,0 +1,139 @@
+/* Instrumentation.java -- Implementation of this interface is used to
+ instrument Java bytecode.
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath 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 for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package java.lang.instrument;
+
+/**
+ * An Instrumentation object has transformers that will
+ * be called each time a class is defined or redefined.
+ * The object is given to a <code>premain</code> function
+ * that is called before the <code>main</code> function.
+ *
+ * @author Nicolas Geoffray (nicolas.geoffray@menlina.com)
+ * @since 1.5
+ */
+public interface Instrumentation
+{
+
+ /**
+ * Adds a <code>ClassFileTransformer</class> object
+ * to the instrumentation. Each time a class is defined
+ * or redefined, the <code>transform</code> method of the
+ * <code>transformer</code> object is called.
+ *
+ * @param transformer the transformer to add
+ * @throws NullPointerException if transformer is null
+ */
+ void addTransformer(ClassFileTransformer transformer);
+
+ /**
+ * Removes the given transformer from the set of transformers
+ * this Instrumentation object has.
+ *
+ * @param transformer the transformer to remove
+ * @return true if the transformer was found and removed, false if
+ * the transformer was not found
+ * @throws NullPointerException if transformer is null
+ */
+ boolean removeTransformer(ClassFileTransformer transformer);
+
+ /**
+ * Returns if the current JVM supports class redefinition
+ *
+ * @return true if the current JVM supports class redefinition
+ */
+ boolean isRedefineClassesSupported();
+
+ /**
+ * Redefine classes present in the definitions array, with
+ * the corresponding class files.
+ *
+ * @param definitions an array of classes to redefine
+ *
+ * @throws ClassNotFoundException if a class cannot be found
+ * @throws UnmodifiableClassException if a class cannot be modified
+ * @throws UnsupportedOperationException if the JVM does not support
+ * redefinition or the redefinition made unsupported changes
+ * @throws ClassFormatError if a class file is not valid
+ * @throws NoClassDefFoundError if a class name is not equal to the name
+ * in the class file specified
+ * @throws UnsupportedClassVersionError if the class file version numbers
+ * are unsupported
+ * @throws ClassCircularityError if circularity occured with the new
+ * classes
+ * @throws LinkageError if a linkage error occurs
+ * @throws NullPointerException if the definitions array is null, or any
+ * of its element
+ *
+ * @see #isRedefineClassesSupported()
+ * @see #addTransformer(java.lang.instrument.ClassFileTransformer)
+ * @see ClassFileTransformer
+ */
+ void redefineClasses(ClassDefinition[] definitions)
+ throws ClassNotFoundException,
+ UnmodifiableClassException;
+
+
+ /**
+ * Get all the classes loaded by the JVM.
+ *
+ * @return an array containing all the classes loaded by the JVM. The array
+ * is empty if no class is loaded.
+ */
+ Class[] getAllLoadedClasses();
+
+ /**
+ * Get all the classes loaded by a given class loader
+ *
+ * @param loader the loader
+ *
+ * @return an array containing all the classes loaded by the given loader.
+ * The array is empty if no class was loaded by the loader.
+ */
+ Class[] getInitiatedClasses(ClassLoader loader);
+
+ /**
+ * Get the size of an object. It contains the size of all fields.
+ *
+ * @param objectToSize the object
+ * @return the size of the object
+ * @throws NullPointerException if objectToSize is null.
+ */
+ long getObjectSize(Object objectToSize);
+}
diff --git a/libjava/classpath/java/lang/instrument/UnmodifiableClassException.java b/libjava/classpath/java/lang/instrument/UnmodifiableClassException.java
new file mode 100644
index 00000000000..a01bd701d9c
--- /dev/null
+++ b/libjava/classpath/java/lang/instrument/UnmodifiableClassException.java
@@ -0,0 +1,69 @@
+/* UnmodifiableClassException.java -- thrown when attempting to redefine
+ an unmodifiable class
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath 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 for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package java.lang.instrument;
+
+/**
+ * @author Nicolas Geoffray (nicolas.geoffray@menlina.com)
+ * @since 1.5
+ */
+public class UnmodifiableClassException extends Exception
+{
+ /**
+ * Compatible with JDK 1.5+.
+ */
+ private static final long serialVersionUID = 1716652643585309178L;
+
+ /**
+ * Create an exception without a message.
+ */
+ public UnmodifiableClassException()
+ {
+ }
+
+ /**
+ * Create an exception with a message.
+ *
+ * @param s the message
+ */
+ public UnmodifiableClassException(String s)
+ {
+ super(s);
+ }
+}
diff --git a/libjava/classpath/java/lang/reflect/AccessibleObject.java b/libjava/classpath/java/lang/reflect/AccessibleObject.java
index 24418c971c7..8f09eac1b0b 100644
--- a/libjava/classpath/java/lang/reflect/AccessibleObject.java
+++ b/libjava/classpath/java/lang/reflect/AccessibleObject.java
@@ -1,5 +1,5 @@
/* java.lang.reflect.AccessibleObject
- Copyright (C) 2001, 2005 Free Software Foundation, Inc.
+ Copyright (C) 2001, 2005, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -38,6 +38,8 @@ exception statement from your version. */
package java.lang.reflect;
+import java.lang.annotation.Annotation;
+
/**
* This class is the superclass of various reflection classes, and
* allows sufficiently trusted code to bypass normal restrictions to
@@ -53,9 +55,10 @@ package java.lang.reflect;
* @see Method
* @see ReflectPermission
* @since 1.2
- * @status updated to 1.4
+ * @status updated to 1.5
*/
public class AccessibleObject
+ implements AnnotatedElement
{
/**
* True if this object is marked accessible, which means the reflected
@@ -156,4 +159,26 @@ public class AccessibleObject
throw new SecurityException("Cannot make object accessible: " + this);
this.flag = flag;
}
+
+ /* FIXME[GENERICS]: <T extends Annotation> T getAnnotation(Class <T>) */
+ public Annotation getAnnotation(Class annotationClass)
+ {
+ throw new AssertionError("Subclass must override this method");
+ }
+
+ public Annotation[] getAnnotations()
+ {
+ return getDeclaredAnnotations();
+ }
+
+ public Annotation[] getDeclaredAnnotations()
+ {
+ throw new AssertionError("Subclass must override this method");
+ }
+
+ /* FIXME[GENERICS]: Signature is Class<? extends Annotation> */
+ public boolean isAnnotationPresent(Class annotationClass)
+ {
+ return getAnnotation(annotationClass) != null;
+ }
}
diff --git a/libjava/classpath/java/lang/reflect/AnnotatedElement.java b/libjava/classpath/java/lang/reflect/AnnotatedElement.java
new file mode 100644
index 00000000000..69a64a02827
--- /dev/null
+++ b/libjava/classpath/java/lang/reflect/AnnotatedElement.java
@@ -0,0 +1,117 @@
+/* AnnotatedElement.java
+ Copyright (C) 2004, 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath 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 for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package java.lang.reflect;
+
+import java.lang.annotation.Annotation;
+
+/**
+ * <p>
+ * Represents an element that can be annotated. The methods of this interface
+ * provide reflection-based access to the annotations associated with a
+ * particular element, such as a class, field, method or package. Each
+ * annotation returned by these methods is both immutable and serializable.
+ * The returned arrays may be freely modified, without any effect on the
+ * arrays returned to future callers.
+ * </p>
+ * <p>
+ * If an annotation refers to a type or enumeration constant that is
+ * inaccessible, then a <code>TypeNotPresentException</code> or
+ * <code>EnumConstantNotPresentException</code> will be thrown. Likewise,
+ * invalid annotations will produce either a
+ * <code>AnnotationTypeMismatchException</code> or
+ * <code>IncompleteAnnotationException</code>.
+ * </p>
+ *
+ * @author Tom Tromey (tromey@redhat.com)
+ * @author Andrew John Hughes (gnu_andrew@member.fsf.org)
+ * @since 1.5
+ */
+public interface AnnotatedElement
+{
+
+ /**
+ * Returns the element's annotation for the specified annotation type,
+ * or <code>null</code> if no such annotation exists.
+ *
+ * @param annotationClass the type of annotation to look for.
+ * @return this element's annotation for the specified type, or
+ * <code>null</code> if no such annotation exists.
+ * @throws NullPointerException if the annotation class is <code>null</code>.
+ */
+ /* FIXME[GENERICS]: <T extends Annotation> T getAnnotation(Class <T>) */
+ Annotation getAnnotation(Class annotationClass);
+
+ /**
+ * Returns all annotations associated with the element. If there are
+ * no annotations associated with the element, then a zero-length array
+ * will be returned. The returned array may be modified by the client
+ * code, but this will have no effect on the annotation content of the
+ * element, and hence no effect on the return value of this method for
+ * future callers.
+ *
+ * @return this element's annotations.
+ */
+ Annotation[] getAnnotations();
+
+ /**
+ * Returns all annotations directly defined by the element. If there are
+ * no annotations directly associated with the element, then a zero-length
+ * array will be returned. The returned array may be modified by the client
+ * code, but this will have no effect on the annotation content of this
+ * class, and hence no effect on the return value of this method for
+ * future callers.
+ *
+ * @return the annotations directly defined by the element.
+ * @since 1.5
+ */
+ Annotation[] getDeclaredAnnotations();
+
+ /**
+ * Returns true if an annotation for the specified type is associated
+ * with the element. This is primarily a short-hand for using marker
+ * annotations.
+ *
+ * @param annotationClass the type of annotation to look for.
+ * @return true if an annotation exists for the specified type.
+ * @since 1.5
+ */
+ /* FIXME[GENERICS]: Signature is Class<? extends Annotation> */
+ boolean isAnnotationPresent(Class annotationClass);
+
+}
diff --git a/libjava/classpath/java/lang/reflect/Array.java b/libjava/classpath/java/lang/reflect/Array.java
index 35c77da369a..ae65ffbf240 100644
--- a/libjava/classpath/java/lang/reflect/Array.java
+++ b/libjava/classpath/java/lang/reflect/Array.java
@@ -38,8 +38,6 @@ exception statement from your version. */
package java.lang.reflect;
-import gnu.classpath.Configuration;
-
/**
* Array holds static helper functions that allow you to create and
* manipulate arrays by reflection. Operations know how to perform widening
@@ -78,13 +76,6 @@ import gnu.classpath.Configuration;
*/
public final class Array
{
- static
- {
- if (Configuration.INIT_LOAD_LIBRARY)
- {
- System.loadLibrary("javalangreflect");
- }
- }
/**
* This class is uninstantiable.
@@ -107,7 +98,7 @@ public final class Array
public static Object newInstance(Class componentType, int length)
{
if (! componentType.isPrimitive())
- return createObjectArray(componentType, length);
+ return VMArray.createObjectArray(componentType, length);
if (componentType == boolean.class)
return new boolean[length];
if (componentType == byte.class)
@@ -653,7 +644,7 @@ public final class Array
Object toAdd = createMultiArray(type, dimensions, index - 1);
Class thisType = toAdd.getClass();
Object[] retval
- = (Object[]) createObjectArray(thisType, dimensions[index]);
+ = (Object[]) VMArray.createObjectArray(thisType, dimensions[index]);
if (dimensions[index] > 0)
retval[0] = toAdd;
int i = dimensions[index];
@@ -662,14 +653,4 @@ public final class Array
return retval;
}
- /**
- * Dynamically create an array of objects.
- *
- * @param type guaranteed to be a valid object type
- * @param dim the length of the array
- * @return the new array
- * @throws NegativeArraySizeException if dim is negative
- * @throws OutOfMemoryError if memory allocation fails
- */
- private static native Object createObjectArray(Class type, int dim);
}
diff --git a/libjava/classpath/java/lang/reflect/GenericDeclaration.java b/libjava/classpath/java/lang/reflect/GenericDeclaration.java
new file mode 100644
index 00000000000..14f5ba8326b
--- /dev/null
+++ b/libjava/classpath/java/lang/reflect/GenericDeclaration.java
@@ -0,0 +1,63 @@
+/* GenericDeclaration.java
+ Copyright (C) 2004 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath 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 for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package java.lang.reflect;
+
+/**
+ * Represents an entity that declares one or more type parameters.
+ * This includes classes and methods (including constructors).
+ *
+ * @author Tom Tromey (tromey@redhat.com)
+ * @author Andrew John Hughes (gnu_andrew@member.fsf.org)
+ * @since 1.5
+ */
+public interface GenericDeclaration
+{
+ /**
+ * Returns a <code>TypeVariable</code> object for each type variable
+ * declared by this entity, in order of declaration. An empty array
+ * is returned if no type variables are declared.
+ *
+ * @return an array of <code>TypeVariable</code> objects.
+ * @throws GenericSignatureFormatError if the signature format within the
+ * class file does not conform to that specified in the 3rd edition
+ * of the Java Virtual Machine Specification.
+ */
+ /* FIXME[GENERICS]: Should be TypeVariable<?>[] */
+ TypeVariable[] getTypeParameters();
+}
diff --git a/libjava/classpath/java/lang/reflect/GenericSignatureFormatError.java b/libjava/classpath/java/lang/reflect/GenericSignatureFormatError.java
index ab6928de6c0..0f09522bc6b 100644
--- a/libjava/classpath/java/lang/reflect/GenericSignatureFormatError.java
+++ b/libjava/classpath/java/lang/reflect/GenericSignatureFormatError.java
@@ -51,6 +51,7 @@ package java.lang.reflect;
public class GenericSignatureFormatError
extends ClassFormatError
{
+ private static final long serialVersionUID = 6709919147137911034L;
/**
* Constructs a new <code>GenericSignatureFormatError</code>.
diff --git a/libjava/classpath/java/lang/reflect/MalformedParameterizedTypeException.java b/libjava/classpath/java/lang/reflect/MalformedParameterizedTypeException.java
new file mode 100644
index 00000000000..50ae23000e7
--- /dev/null
+++ b/libjava/classpath/java/lang/reflect/MalformedParameterizedTypeException.java
@@ -0,0 +1,60 @@
+/* MalformedParameterizedTypeException.java
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath 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 for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package java.lang.reflect;
+
+/**
+ * This exception class is thrown when one of the reflection
+ * methods encountered an invalid parameterized type within
+ * the metadata of a class. One possible reason for this
+ * exception being thrown is the specification of too few or
+ * too many type variables.
+ *
+ * @author Tom Tromey (tromey@redhat.com)
+ * @author Andrew John Hughes (gnu_andrew@member.fsf.org)
+ * @since 1.5
+ */
+public class MalformedParameterizedTypeException
+ extends RuntimeException
+{
+ private static final long serialVersionUID = -5696557788586220964L;
+
+ public MalformedParameterizedTypeException()
+ {
+ }
+}
diff --git a/libjava/classpath/java/lang/reflect/Member.java b/libjava/classpath/java/lang/reflect/Member.java
index c39731f8487..fed962cf913 100644
--- a/libjava/classpath/java/lang/reflect/Member.java
+++ b/libjava/classpath/java/lang/reflect/Member.java
@@ -97,4 +97,13 @@ public interface Member
* @see Modifier
*/
int getModifiers();
+
+ /**
+ * Return true if this member is synthetic, meaning that it was
+ * created by the compiler and does not appear in the user's
+ * source code.
+ * @return true if the member is synthetic
+ * @since 1.5
+ */
+ boolean isSynthetic();
}
diff --git a/libjava/classpath/java/lang/reflect/Modifier.java b/libjava/classpath/java/lang/reflect/Modifier.java
index efc88c941db..45fc4e37e69 100644
--- a/libjava/classpath/java/lang/reflect/Modifier.java
+++ b/libjava/classpath/java/lang/reflect/Modifier.java
@@ -158,6 +158,26 @@ public class Modifier
static final int ALL_FLAGS = 0xfff;
/**
+ * Flag indicating a bridge method.
+ */
+ static final int BRIDGE = 0x40;
+
+ /**
+ * Flag indicating a varargs method.
+ */
+ static final int VARARGS = 0x80;
+
+ /**
+ * Flag indicating a synthetic member.
+ */
+ static final int SYNTHETIC = 0x1000;
+
+ /**
+ * Flag indicating an enum constant or an enum class.
+ */
+ static final int ENUM = 0x4000;
+
+ /**
* Check whether the given modifier is abstract.
* @param mod the modifier.
* @return <code>true</code> if abstract, <code>false</code> otherwise.
@@ -288,7 +308,19 @@ public class Modifier
*/
public static String toString(int mod)
{
- return toString(mod, new StringBuffer()).toString();
+ return toString(mod, new StringBuilder()).toString();
+ }
+
+ /**
+ * Package helper method that can take a StringBuilder.
+ * @param mod the modifier
+ * @param r the StringBuilder to which the String representation is appended
+ * @return r, with information appended
+ */
+ static StringBuilder toString(int mod, StringBuilder r)
+ {
+ r.append(toString(mod, new StringBuffer()));
+ return r;
}
/**
diff --git a/libjava/classpath/java/lang/reflect/ParameterizedType.java b/libjava/classpath/java/lang/reflect/ParameterizedType.java
index 61081c962db..7a8a7b4e721 100644
--- a/libjava/classpath/java/lang/reflect/ParameterizedType.java
+++ b/libjava/classpath/java/lang/reflect/ParameterizedType.java
@@ -63,7 +63,7 @@ package java.lang.reflect;
*
* @author Tom Tromey (tromey@redhat.com)
* @author Andrew John Hughes (gnu_andrew@member.fsf.org)
- * @see GenericTypeDeclaration
+ * @see GenericDeclaration
* @see TypeVariable
* @since 1.5
*/
diff --git a/libjava/classpath/java/lang/reflect/TypeVariable.java b/libjava/classpath/java/lang/reflect/TypeVariable.java
new file mode 100644
index 00000000000..4ecc20c9d9e
--- /dev/null
+++ b/libjava/classpath/java/lang/reflect/TypeVariable.java
@@ -0,0 +1,99 @@
+/* TypeVariable.java
+ Copyright (C) 2004 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath 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 for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package java.lang.reflect;
+
+/**
+ * <p>
+ * This is a common interface for all type variables provided by
+ * the Java language. Instances are created the first time a type
+ * variable is needed by one of the reflective methods declared in
+ * this package.
+ * </p>
+ * <p>
+ * Creating a type variable requires resolving the appropriate type.
+ * This may involve resolving other classes as a side effect (e.g.
+ * if the type is nested inside other classes). Creation should not
+ * involve resolving the bounds. Repeated creation has no effect; an
+ * equivalent instance is returned. Caching is not required, but all
+ * instances must be <code>equal()</code> to each other.
+ * </p>
+ *
+ * @author Tom Tromey (tromey@redhat.com)
+ * @author Andrew John Hughes (gnu_andrew@member.fsf.org)
+ * @since 1.5
+ */
+/* FIXME[GENERICS]: Should be TypeVariable<T extends GenericDeclaration> */
+public interface TypeVariable
+ extends Type
+{
+
+ /**
+ * Returns an array of <code>Type</code> objects which represent the upper
+ * bounds of this type variable. There is always a default bound of
+ * <code>Object</code>. Any <code>ParameterizedType</code>s will be
+ * created as necessary, and other types resolved.
+ *
+ * @return an array of <code>Type</code> objects representing the upper
+ * bounds.
+ * @throws TypeNotPresentException if any of the bounds refer to a
+ * non-existant type.
+ * @throws MalformedParameterizedTypeException if the creation of a
+ * <code>ParameterizedType</code> fails.
+ */
+ Type[] getBounds();
+
+
+ /**
+ * Returns a representation of the declaration used to declare this
+ * type variable.
+ *
+ * @return the <code>GenericDeclaration</code> object for this type
+ * variable.
+ */
+ /* FIXME[GENERICS]: Should return type T */
+ GenericDeclaration getGenericDeclaration();
+
+ /**
+ * Returns the name of the type variable, as written in the source
+ * code.
+ *
+ * @return the name of the type variable.
+ */
+ String getName();
+}
diff --git a/libjava/classpath/java/math/class-dependencies.conf b/libjava/classpath/java/math/class-dependencies.conf
deleted file mode 100644
index 4fbf75eb1ce..00000000000
--- a/libjava/classpath/java/math/class-dependencies.conf
+++ /dev/null
@@ -1,58 +0,0 @@
-# This property file contains dependencies of classes, methods, and
-# field on other methods or classes.
-#
-# Syntax:
-#
-# <used>: <needed 1> [... <needed N>]
-#
-# means that when <used> is included, <needed 1> (... <needed N>) must
-# be included as well.
-#
-# <needed X> and <used> are of the form
-#
-# <class.methodOrField(signature)>
-#
-# or just
-#
-# <class>
-#
-# Within dependencies, variables can be used. A variable is defined as
-# follows:
-#
-# {variable}: value1 value2 ... value<n>
-#
-# variables can be used on the right side of dependencies as follows:
-#
-# <used>: com.bla.blu.{variable}.Class.m()V
-#
-# The use of the variable will expand to <n> dependencies of the form
-#
-# <used>: com.bla.blu.value1.Class.m()V
-# <used>: com.bla.blu.value2.Class.m()V
-# ...
-# <used>: com.bla.blu.value<n>.Class.m()V
-#
-# Variables can be redefined when building a system to select the
-# required support for features like encodings, protocols, etc.
-#
-# Hints:
-#
-# - For methods and fields, the signature is mandatory. For
-# specification, please see the Java Virtual Machine Specification by
-# SUN. Unlike in the spec, field signatures (types) are in brackets.
-#
-# - Package names must be separated by '/' (and not '.'). E.g.,
-# java/lang/Class (this is necessary, because the '.' is used to
-# separate method or field names from classes)
-#
-# - In case <needed> refers to a class, only the class itself will be
-# included in the resulting binary, NOT necessarily all its methods
-# and fields. If you want to refer to all methods and fields, you can
-# write class.* as an abbreviation.
-#
-# - Abbreviations for packages are also possible: my/package/* means all
-# methods and fields of all classes in my/package.
-#
-# - A line with a trailing '\' continues in the next line.
-
-# end of file
diff --git a/libjava/classpath/java/net/InetSocketAddress.java b/libjava/classpath/java/net/InetSocketAddress.java
index edeaf27753c..91254575265 100644
--- a/libjava/classpath/java/net/InetSocketAddress.java
+++ b/libjava/classpath/java/net/InetSocketAddress.java
@@ -1,5 +1,5 @@
/* InetSocketAddress.java --
- Copyright (C) 2002 Free Software Foundation, Inc.
+ Copyright (C) 2002, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -107,10 +107,26 @@ public class InetSocketAddress extends SocketAddress
* @param hostname The hostname for the socket address
* @param port The port for the socket address
*
- * @exception IllegalArgumentException If the port number is illegal
+ * @exception IllegalArgumentException If the port number is illegal or
+ * the hostname argument is null
*/
public InetSocketAddress(String hostname, int port)
- throws IllegalArgumentException
+ {
+ this(hostname, port, true);
+ }
+
+ /**
+ * Constructs an InetSocketAddress instance.
+ *
+ * @param hostname The hostname for the socket address
+ * @param port The port for the socket address
+ * @param resolve <code>true</code> if the address has to be resolved,
+ * <code>false</code> otherwise
+ *
+ * @exception IllegalArgumentException If the port number is illegal or
+ * the hostname argument is null
+ */
+ private InetSocketAddress(String hostname, int port, boolean resolve)
{
if (hostname == null)
throw new IllegalArgumentException("Null host name value");
@@ -120,15 +136,36 @@ public class InetSocketAddress extends SocketAddress
this.port = port;
this.hostname = hostname;
+ this.addr = null;
- try
- {
- this.addr = InetAddress.getByName(hostname);
- }
- catch (Exception e) // UnknownHostException, SecurityException
- {
- this.addr = null;
- }
+ if (resolve)
+ {
+ try
+ {
+ this.addr = InetAddress.getByName(hostname);
+ }
+ catch (Exception e) // UnknownHostException, SecurityException
+ {
+ // Do nothing here. this.addr is already set to null.
+ }
+ }
+
+ }
+
+ /**
+ * Creates an unresolved <code>InetSocketAddress</code> object.
+ *
+ * @param hostname The hostname for the socket address
+ * @param port The port for the socket address
+ *
+ * @exception IllegalArgumentException If the port number is illegal or
+ * the hostname argument is null
+ *
+ * @since 1.5
+ */
+ public static InetSocketAddress createUnresolved(String hostname, int port)
+ {
+ return new InetSocketAddress(hostname, port, false);
}
/**
diff --git a/libjava/classpath/java/net/MimeTypeMapper.java b/libjava/classpath/java/net/MimeTypeMapper.java
index 1747f4d5685..8153694b483 100644
--- a/libjava/classpath/java/net/MimeTypeMapper.java
+++ b/libjava/classpath/java/net/MimeTypeMapper.java
@@ -37,7 +37,17 @@ exception statement from your version. */
package java.net;
+import gnu.classpath.SystemProperties;
+
+import java.io.FileReader;
+import java.io.IOException;
+import java.io.LineNumberReader;
import java.util.Hashtable;
+import java.util.Iterator;
+import java.util.Map;
+import java.util.NoSuchElementException;
+import java.util.StringTokenizer;
+import java.util.TreeMap;
/**
@@ -56,131 +66,230 @@ class MimeTypeMapper implements FileNameMap
*/
protected static final String[][] mime_strings =
{
- { "application/mac-binhex40", "hqx" },
- { "application/mac-compactpro", "cpt" },
- { "application/msword", "doc" },
- { "application/octet-stream", "bin" },
- { "application/octet-stream", "dms" },
- { "application/octet-stream", "lha" },
- { "application/octet-stream", "lzh" },
- { "application/octet-stream", "exe" },
- { "application/octet-stream", "class" },
- { "application/oda", "oda" },
- { "application/pdf", "pdf" },
- { "application/postscript", "ai" },
- { "application/postscript", "eps" },
- { "application/postscript", "ps" },
- { "application/powerpoint", "ppt" },
- { "application/rtf", "rtf" },
- { "application/x-bcpio", "bcpio" },
- { "application/x-cdlink", "vcd" },
- { "application/x-compress", "Z" },
- { "application/x-cpio", "cpio" },
- { "application/x-csh", "csh" },
- { "application/x-director", "dcr" },
- { "application/x-director", "dir" },
- { "application/x-director", "dxr" },
- { "application/x-dvi", "dvi" },
- { "application/x-gtar", "gtar" },
- { "application/x-gzip", "gz" },
- { "application/x-hdf", "hdf" },
- { "application/x-httpd-cgi", "cgi" },
- { "application/x-koan", "skp" },
- { "application/x-koan", "skd" },
- { "application/x-koan", "skt" },
- { "application/x-koan", "skm" },
- { "application/x-latex", "latex" },
- { "application/x-mif", "mif" },
- { "application/x-netcdf", "nc" },
- { "application/x-netcdf", "cdf" },
- { "application/x-sh", "sh" },
- { "application/x-shar", "shar" },
- { "application/x-stuffit", "sit" },
- { "application/x-sv4cpio", "sv4cpio" },
- { "application/x-sv4crc", "sv4crc" },
- { "application/x-tar", "tar" },
- { "application/x-tcl", "tcl" },
- { "application/x-tex", "tex" },
- { "application/x-texinfo", "texinfo" },
- { "application/x-texinfo", "texi" },
- { "application/x-troff", "t" },
- { "application/x-troff", "tr" },
- { "application/x-troff", "roff" },
- { "application/x-troff-man", "man" },
- { "application/x-troff-me", "me" },
- { "application/x-troff-ms", "ms" },
- { "application/x-ustar", "ustar" },
- { "application/x-wais-source", "src" },
- { "application/zip", "zip" },
- { "audio/basic", "au" },
- { "audio/basic", "snd" },
- { "audio/mpeg", "mpga" },
- { "audio/mpeg", "mp2" },
- { "audio/mpeg", "mp3" },
- { "audio/x-aiff", "aif" },
- { "audio/x-aiff", "aiff" },
- { "audio/x-aiff", "aifc" },
- { "audio/x-pn-realaudio", "ram" },
- { "audio/x-pn-realaudio-plugin", "rpm" },
- { "audio/x-realaudio", "ra" },
- { "audio/x-wav", "wav" },
- { "chemical/x-pdb", "pdb" },
- { "chemical/x-pdb", "xyz" },
- { "image/gif", "gif" },
- { "image/ief", "ief" },
- { "image/jpeg", "jpeg" },
- { "image/jpeg", "jpg" },
- { "image/jpeg", "jpe" },
- { "image/png", "png" },
- { "image/tiff", "tiff" },
- { "image/tiff", "tif" },
- { "image/x-cmu-raster", "ras" },
- { "image/x-portable-anymap", "pnm" },
- { "image/x-portable-bitmap", "pbm" },
- { "image/x-portable-graymap", "pgm" },
- { "image/x-portable-pixmap", "ppm" },
- { "image/x-rgb", "rgb" },
- { "image/x-xbitmap", "xbm" },
- { "image/x-xpixmap", "xpm" },
- { "image/x-xwindowdump", "xwd" },
- { "text/html", "html" },
- { "text/html", "htm" },
- { "text/plain", "txt" },
- { "text/richtext", "rtx" },
- { "text/tab-separated-values", "tsv" },
- { "text/x-setext", "etx" },
- { "text/x-sgml", "sgml" },
- { "text/x-sgml", "sgm" },
- { "video/mpeg", "mpeg" },
- { "video/mpeg", "mpg" },
- { "video/mpeg", "mpe" },
- { "video/quicktime", "qt" },
- { "video/quicktime", "mov" },
- { "video/x-msvideo", "avi" },
- { "video/x-sgi-movie", "movie" },
- { "x-conference/x-cooltalk", "ice" },
- { "x-world/x-vrml", "wrl" },
- { "x-world/x-vrml", "vrml" }
+ { "ai", "application/postscript" }
+ , { "aif", "audio/x-aiff" }
+ , { "aifc", "audio/x-aiff" }
+ , { "aiff", "audio/x-aiff" }
+ , { "asc", "text/plain" }
+ , { "au", "audio/basic" }
+ , { "avi", "video/x-msvideo" }
+ , { "bcpio", "application/x-bcpio" }
+ , { "bin", "application/octet-stream" }
+ , { "bmp", "image/bmp" }
+ , { "bz2", "application/x-bzip2" }
+ , { "cdf", "application/x-netcdf" }
+ , { "chrt", "application/x-kchart" }
+ , { "class", "application/octet-stream" }
+ , { "cpio", "application/x-cpio" }
+ , { "cpt", "application/mac-compactpro" }
+ , { "csh", "application/x-csh" }
+ , { "css", "text/css" }
+ , { "dcr", "application/x-director" }
+ , { "dir", "application/x-director" }
+ , { "djv", "image/vnd.djvu" }
+ , { "djvu", "image/vnd.djvu" }
+ , { "dll", "application/octet-stream" }
+ , { "dms", "application/octet-stream" }
+ , { "doc", "application/msword" }
+ , { "dvi", "application/x-dvi" }
+ , { "dxr", "application/x-director" }
+ , { "eps", "application/postscript" }
+ , { "etx", "text/x-setext" }
+ , { "exe", "application/octet-stream" }
+ , { "ez", "application/andrew-inset" }
+ , { "gif", "image/gif" }
+ , { "gtar", "application/x-gtar" }
+ , { "gz", "application/x-gzip" }
+ , { "hdf", "application/x-hdf" }
+ , { "hqx", "application/mac-binhex40" }
+ , { "htm", "text/html" }
+ , { "html", "text/html" }
+ , { "ice", "x-conference/x-cooltalk" }
+ , { "ief", "image/ief" }
+ , { "iges", "model/iges" }
+ , { "igs", "model/iges" }
+ , { "img", "application/octet-stream" }
+ , { "iso", "application/octet-stream" }
+ , { "jpe", "image/jpeg" }
+ , { "jpeg", "image/jpeg" }
+ , { "jpg", "image/jpeg" }
+ , { "js", "application/x-javascript" }
+ , { "kar", "audio/midi" }
+ , { "kil", "application/x-killustrator" }
+ , { "kpr", "application/x-kpresenter" }
+ , { "kpt", "application/x-kpresenter" }
+ , { "ksp", "application/x-kspread" }
+ , { "kwd", "application/x-kword" }
+ , { "kwt", "application/x-kword" }
+ , { "latex", "application/x-latex" }
+ , { "lha", "application/octet-stream" }
+ , { "lzh", "application/octet-stream" }
+ , { "m3u", "audio/x-mpegurl" }
+ , { "man", "application/x-troff-man" }
+ , { "me", "application/x-troff-me" }
+ , { "mesh", "model/mesh" }
+ , { "mid", "audio/midi" }
+ , { "midi", "audio/midi" }
+ , { "mif", "application/vnd.mif" }
+ , { "mov", "video/quicktime" }
+ , { "movie", "video/x-sgi-movie" }
+ , { "mp2", "audio/mpeg" }
+ , { "mp3", "audio/mpeg" }
+ , { "mpe", "video/mpeg" }
+ , { "mpeg", "video/mpeg" }
+ , { "mpg", "video/mpeg" }
+ , { "mpga", "audio/mpeg" }
+ , { "ms", "application/x-troff-ms" }
+ , { "msh", "model/mesh" }
+ , { "mxu", "video/vnd.mpegurl" }
+ , { "nc", "application/x-netcdf" }
+ , { "ogg", "application/ogg" }
+ , { "pbm", "image/x-portable-bitmap" }
+ , { "pdb", "chemical/x-pdb" }
+ , { "pdf", "application/pdf" }
+ , { "pgm", "image/x-portable-graymap" }
+ , { "pgn", "application/x-chess-pgn" }
+ , { "png", "image/png" }
+ , { "pnm", "image/x-portable-anymap" }
+ , { "ppm", "image/x-portable-pixmap" }
+ , { "ppt", "application/vnd.ms-powerpoint" }
+ , { "ps", "application/postscript" }
+ , { "qt", "video/quicktime" }
+ , { "ra", "audio/x-realaudio" }
+ , { "ram", "audio/x-pn-realaudio" }
+ , { "ras", "image/x-cmu-raster" }
+ , { "rgb", "image/x-rgb" }
+ , { "rm", "audio/x-pn-realaudio" }
+ , { "roff", "application/x-troff" }
+ , { "rpm", "application/x-rpm" }
+ , { "rtf", "text/rtf" }
+ , { "rtx", "text/richtext" }
+ , { "sgm", "text/sgml" }
+ , { "sgml", "text/sgml" }
+ , { "sh", "application/x-sh" }
+ , { "shar", "application/x-shar" }
+ , { "silo", "model/mesh" }
+ , { "sit", "application/x-stuffit" }
+ , { "skd", "application/x-koan" }
+ , { "skm", "application/x-koan" }
+ , { "skp", "application/x-koan" }
+ , { "skt", "application/x-koan" }
+ , { "smi", "application/smil" }
+ , { "smil", "application/smil" }
+ , { "snd", "audio/basic" }
+ , { "so", "application/octet-stream" }
+ , { "spl", "application/x-futuresplash" }
+ , { "src", "application/x-wais-source" }
+ , { "stc", "application/vnd.sun.xml.calc.template" }
+ , { "std", "application/vnd.sun.xml.draw.template" }
+ , { "sti", "application/vnd.sun.xml.impress.template" }
+ , { "stw", "application/vnd.sun.xml.writer.template" }
+ , { "sv4cpio", "application/x-sv4cpio" }
+ , { "sv4crc", "application/x-sv4crc" }
+ , { "swf", "application/x-shockwave-flash" }
+ , { "sxc", "application/vnd.sun.xml.calc" }
+ , { "sxd", "application/vnd.sun.xml.draw" }
+ , { "sxg", "application/vnd.sun.xml.writer.global" }
+ , { "sxi", "application/vnd.sun.xml.impress" }
+ , { "sxm", "application/vnd.sun.xml.math" }
+ , { "sxw", "application/vnd.sun.xml.writer" }
+ , { "t", "application/x-troff" }
+ , { "tar", "application/x-tar" }
+ , { "tcl", "application/x-tcl" }
+ , { "tex", "application/x-tex" }
+ , { "texi", "application/x-texinfo" }
+ , { "texinfo", "application/x-texinfo" }
+ , { "tgz", "application/x-gzip" }
+ , { "tif", "image/tiff" }
+ , { "tiff", "image/tiff" }
+ , { "torrent", "application/x-bittorrent" }
+ , { "tr", "application/x-troff" }
+ , { "tsv", "text/tab-separated-values" }
+ , { "txt", "text/plain" }
+ , { "ustar", "application/x-ustar" }
+ , { "vcd", "application/x-cdlink" }
+ , { "vrml", "model/vrml" }
+ , { "wav", "audio/x-wav" }
+ , { "wbmp", "image/vnd.wap.wbmp" }
+ , { "wbxml", "application/vnd.wap.wbxml" }
+ , { "wml", "text/vnd.wap.wml" }
+ , { "wmlc", "application/vnd.wap.wmlc" }
+ , { "wmls", "text/vnd.wap.wmlscript" }
+ , { "wmlsc", "application/vnd.wap.wmlscriptc" }
+ , { "wrl", "model/vrml" }
+ , { "xbm", "image/x-xbitmap" }
+ , { "xht", "application/xhtml+xml" }
+ , { "xhtml", "application/xhtml+xml" }
+ , { "xls", "application/vnd.ms-excel" }
+ , { "xml", "text/xml" }
+ , { "xpm", "image/x-xpixmap" }
+ , { "xsl", "text/xml" }
+ , { "xwd", "image/x-xwindowdump" }
+ , { "xyz", "chemical/x-xyz" }
+ , { "zip", "application/zip" }
};
/**
* The MIME types above are put into this Hashtable for faster lookup.
*/
- private static Hashtable mime_types = new Hashtable(150);
-
- // Static initializer to load MIME types into Hashtable
- static
- {
- for (int i = 0; i < mime_strings.length; i++)
- mime_types.put(mime_strings[i][1], mime_strings[i][0]);
- }
+ private Hashtable mime_types = new Hashtable(150);
/**
* Create a new <code>MimeTypeMapper</code> object.
*/
public MimeTypeMapper()
{
- // Do nothing here.
+ for (int i = 0; i < mime_strings.length; i++)
+ mime_types.put(mime_strings[i][0], mime_strings[i][1]);
+
+ // Now read from the system mime database, if it exists. Entries found
+ // here override our internal ones.
+ try
+ {
+ // On Linux this usually means /etc/mime.types.
+ String file
+ = SystemProperties.getProperty("gnu.classpath.mime.types.file");
+ if (file != null)
+ fillFromFile(mime_types, file);
+ }
+ catch (IOException ignore)
+ {
+ }
+ }
+
+ public static void fillFromFile (Map table, String fname)
+ throws IOException
+ {
+ LineNumberReader reader =
+ new LineNumberReader (new FileReader (fname));
+
+ while (reader.ready ())
+ {
+ StringTokenizer tokenizer =
+ new StringTokenizer (reader.readLine ());
+
+ try
+ {
+ String t = tokenizer.nextToken ();
+
+ if (! t.startsWith ("#"))
+ {
+ while (true)
+ {
+ // Read the next extension
+ String e = tokenizer.nextToken ();
+ if ((e != null) && (! e.startsWith ("#")))
+ table.put (e, t);
+ else
+ break;
+ }
+ }
+ }
+ catch (NoSuchElementException ex)
+ {
+ // Do nothing.
+ }
+ }
}
/**
@@ -210,4 +319,27 @@ class MimeTypeMapper implements FileNameMap
else
return type;
}
+
+ /**
+ * Run this class as a program to create a new mime_strings table.
+ */
+ public static void main(String[] args) throws IOException
+ {
+ TreeMap map = new TreeMap();
+ // It is fine to hard-code the name here. This is only ever
+ // used by maintainers, who can hack it if they need to re-run
+ // it.
+ fillFromFile(map, "/etc/mime.types");
+ Iterator it = map.keySet().iterator();
+ boolean first = true;
+ while (it.hasNext())
+ {
+ String key = (String) it.next();
+ String value = (String) map.get(key);
+ // Put the "," first since it is easier to make correct syntax this way.
+ System.out.println(" " + (first ? " " : ", ")
+ + "{ \"" + key + "\", \"" + value + "\" }");
+ first = false;
+ }
+ }
}
diff --git a/libjava/classpath/java/net/URI.java b/libjava/classpath/java/net/URI.java
index 39e8dadfc10..401352fcf3c 100644
--- a/libjava/classpath/java/net/URI.java
+++ b/libjava/classpath/java/net/URI.java
@@ -487,16 +487,14 @@ public final class URI
for (int i = 0; i < str.length(); i++)
{
char c = str.charAt(i);
- if (legalCharacters.indexOf(c) == -1)
+ if ((legalCharacters.indexOf(c) == -1)
+ && (c <= 127))
{
- if (c <= 127)
- {
- sb.append('%');
- sb.append(HEX.charAt(c / 16));
- sb.append(HEX.charAt(c % 16));
- }
+ sb.append('%');
+ sb.append(HEX.charAt(c / 16));
+ sb.append(HEX.charAt(c % 16));
}
- else
+ else
sb.append(c);
}
return sb.toString();
diff --git a/libjava/classpath/java/net/URLClassLoader.java b/libjava/classpath/java/net/URLClassLoader.java
index 9e489db533f..183e645c85f 100644
--- a/libjava/classpath/java/net/URLClassLoader.java
+++ b/libjava/classpath/java/net/URLClassLoader.java
@@ -39,6 +39,7 @@ exception statement from your version. */
package java.net;
+import java.io.BufferedReader;
import java.io.ByteArrayOutputStream;
import java.io.EOFException;
import java.io.File;
@@ -46,6 +47,7 @@ import java.io.FileInputStream;
import java.io.FilePermission;
import java.io.IOException;
import java.io.InputStream;
+import java.io.InputStreamReader;
import java.security.AccessControlContext;
import java.security.AccessController;
import java.security.CodeSource;
@@ -315,27 +317,51 @@ public class URLClassLoader extends SecureClassLoader
jarfile =
((JarURLConnection) baseJarURL.openConnection()).getJarFile();
-
+
Manifest manifest;
Attributes attributes;
String classPathString;
- if ((manifest = jarfile.getManifest()) != null
+ this.classPath = new Vector();
+
+ // This goes through the cached jar files listed
+ // in the INDEX.LIST file. All the jars found are added
+ // to the classPath vector so they can be loaded.
+ String dir = "META-INF/INDEX.LIST";
+ if (jarfile.getEntry(dir) != null)
+ {
+ BufferedReader br = new BufferedReader(new InputStreamReader(new URL(baseJarURL,
+ dir).openStream()));
+ String line = br.readLine();
+ while (line != null)
+ {
+ if (line.endsWith(".jar"))
+ {
+ try
+ {
+ this.classPath.add(new URL(baseURL, line));
+ }
+ catch (java.net.MalformedURLException xx)
+ {
+ // Give up
+ }
+ }
+ line = br.readLine();
+ }
+ }
+ else if ((manifest = jarfile.getManifest()) != null
&& (attributes = manifest.getMainAttributes()) != null
&& ((classPathString
= attributes.getValue(Attributes.Name.CLASS_PATH))
!= null))
- {
- this.classPath = new Vector();
-
+ {
StringTokenizer st = new StringTokenizer(classPathString, " ");
while (st.hasMoreElements ())
{
String e = st.nextToken ();
try
{
- URL url = new URL(baseURL, e);
- this.classPath.add(url);
+ this.classPath.add(new URL(baseURL, e));
}
catch (java.net.MalformedURLException xx)
{
@@ -538,9 +564,14 @@ public class URLClassLoader extends SecureClassLoader
{
try
{
- File file = new File(dir, name).getCanonicalFile();
- if (file.exists() && !file.isDirectory())
- return new FileResource(this, file);
+ // Make sure that all components in name are valid by walking through
+ // them
+ File file = walkPathComponents(name);
+
+ if (file == null)
+ return null;
+
+ return new FileResource(this, file);
}
catch (IOException e)
{
@@ -548,6 +579,65 @@ public class URLClassLoader extends SecureClassLoader
}
return null;
}
+
+ /**
+ * Walk all path tokens and check them for validity. At no moment, we are
+ * allowed to reach a directory located "above" the root directory, stored
+ * in "dir" property. We are also not allowed to enter a non existing
+ * directory or a non directory component (plain file, symbolic link, ...).
+ * An empty or null path is valid. Pathnames components are separated by
+ * <code>File.separatorChar</code>
+ *
+ * @param resourceFileName the name to be checked for validity.
+ * @return the canonical file pointed by the resourceFileName or null if the
+ * walking failed
+ * @throws IOException in case of issue when creating the canonical
+ * resulting file
+ * @see File#separatorChar
+ */
+ private File walkPathComponents(String resourceFileName) throws IOException
+ {
+ StringTokenizer stringTokenizer = new StringTokenizer(resourceFileName, File.separator);
+ File currentFile = dir;
+ int tokenCount = stringTokenizer.countTokens();
+
+ for (int i = 0; i < tokenCount - 1; i++)
+ {
+ String currentToken = stringTokenizer.nextToken();
+
+ // If we are at the root directory and trying to go up, the walking is
+ // finished with an error
+ if ("..".equals(currentToken) && currentFile.equals(dir))
+ return null;
+
+ currentFile = new File(currentFile, currentToken);
+
+ // If the current file doesn't exist or is not a directory, the walking is
+ // finished with an error
+ if (! (currentFile.exists() && currentFile.isDirectory()))
+ return null;
+
+ }
+
+ // Treat the last token differently, if it exists, because it does not need
+ // to be a directory
+ if (tokenCount > 0)
+ {
+ String currentToken = stringTokenizer.nextToken();
+
+ if ("..".equals(currentToken) && currentFile.equals(dir))
+ return null;
+
+ currentFile = new File(currentFile, currentToken);
+
+ // If the current file doesn't exist, the walking is
+ // finished with an error
+ if (! currentFile.exists())
+ return null;
+ }
+
+ return currentFile.getCanonicalFile();
+ }
}
static final class FileResource extends Resource
diff --git a/libjava/classpath/java/net/URLConnection.java b/libjava/classpath/java/net/URLConnection.java
index b4a55a01a34..1f78dd8e8dd 100644
--- a/libjava/classpath/java/net/URLConnection.java
+++ b/libjava/classpath/java/net/URLConnection.java
@@ -1,5 +1,5 @@
/* URLConnection.java -- Abstract superclass for reading from URL's
- Copyright (C) 1998, 2002, 2003, 2004 Free Software Foundation, Inc.
+ Copyright (C) 1998, 2002, 2003, 2004, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -38,6 +38,9 @@ exception statement from your version. */
package java.net;
+import gnu.classpath.NotImplementedException;
+import gnu.classpath.SystemProperties;
+
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
@@ -49,6 +52,7 @@ import java.util.Collections;
import java.util.Date;
import java.util.Locale;
import java.util.Map;
+import java.util.StringTokenizer;
/**
* Written using on-line Java Platform 1.2 API Specification, as well
@@ -114,6 +118,12 @@ public abstract class URLConnection
private static boolean defaultUseCaches = true;
/**
+ * Default internal content handler factory.
+ */
+ private static ContentHandlerFactory defaultFactory
+ = new gnu.java.net.DefaultContentHandlerFactory();
+
+ /**
* This variable determines whether or not interaction is allowed with
* the user. For example, to prompt for a username and password.
*/
@@ -160,6 +170,7 @@ public abstract class URLConnection
* This is the URL associated with this connection
*/
protected URL url;
+
private static SimpleDateFormat[] dateFormats;
private static boolean dateformats_initialized;
@@ -168,7 +179,7 @@ public abstract class URLConnection
/**
* Creates a URL connection to a given URL. A real connection is not made.
- * Use #connect to do this.
+ * Use <code>connect()</code> to do this.
*
* @param url The Object to create the URL connection to
*
@@ -277,8 +288,8 @@ public abstract class URLConnection
/**
* Return a String representing the header value at the specified index.
* This allows the caller to walk the list of header fields. The analogous
- * getHeaderFieldKey(int) method allows access to the corresponding key
- * for this header field
+ * {@link #getHeaderField(int)} method allows access to the corresponding
+ * key for this header field
*
* @param index The index into the header field list to retrieve the value for
*
@@ -305,9 +316,10 @@ public abstract class URLConnection
}
/**
- * Returns a map of all sent header fields
- *
- * @return all header fields
+ * Returns an unmodifiable Map containing all sent header fields.
+ *
+ * @return The map of header fields. The map consists of String keys with
+ * an unmodifiable List of String objects as value.
*
* @since 1.4
*/
@@ -355,7 +367,7 @@ public abstract class URLConnection
* @param defaultValue The default date if the header field is not found
* or can't be converted.
*
- * @return Returns the date value of the header filed or the default value
+ * @return The date value of the header filed or the default value
* if the field is missing or malformed
*/
public long getHeaderFieldDate(String name, long defaultValue)
@@ -388,8 +400,8 @@ public abstract class URLConnection
/**
* Returns a String representing the header key at the specified index.
* This allows the caller to walk the list of header fields. The analogous
- * getHeaderField(int) method allows access to the corresponding value for
- * this tag.
+ * {@link #getHeaderField(int)} method allows access to the corresponding
+ * value for this tag.
*
* @param index The index into the header field list to retrieve the key for.
*
@@ -458,10 +470,16 @@ public abstract class URLConnection
* @exception UnknownServiceException If the protocol does not support the
* content type
*/
- public Object getContent(Class[] classes) throws IOException
+ public Object getContent(Class[] classes)
+ throws IOException
{
- // FIXME: implement this
- return getContent();
+ if (! connected)
+ connect();
+ String type = getContentType();
+ ContentHandler ch = getContentHandler(type);
+ if (ch != null)
+ return ch.getContent(this, classes);
+ throw new UnknownServiceException("protocol does not support the content type");
}
/**
@@ -722,7 +740,9 @@ public abstract class URLConnection
}
/**
- * Sets the value of the named request property
+ * Sets the value of the named request property.
+ * This method does overwrite the value of existing properties with
+ * the new value.
*
* @param key The name of the property
* @param value The value of the property
@@ -757,8 +777,8 @@ public abstract class URLConnection
* @exception IllegalStateException If already connected
* @exception NullPointerException If key is null
*
- * @see URLConnection#getRequestProperty(String key)
- * @see URLConnection#setRequestProperty(String key, String value)
+ * @see URLConnection#getRequestProperty(String)
+ * @see URLConnection#setRequestProperty(String, String)
*
* @since 1.4
*/
@@ -783,8 +803,8 @@ public abstract class URLConnection
*
* @exception IllegalStateException If already connected
*
- * @see URLConnection#setRequestProperty(String key, String value)
- * @see URLConnection#addRequestProperty(String key, String value)
+ * @see URLConnection#setRequestProperty(String, String)
+ * @see URLConnection#addRequestProperty(String, String)
*/
public String getRequestProperty(String key)
{
@@ -798,8 +818,9 @@ public abstract class URLConnection
/**
* Returns an unmodifiable Map containing the request properties.
- *
- * @return The map of properties
+ *
+ * @return The map of properties. The map consists of String keys with an
+ * unmodifiable List of String objects as value.
*
* @exception IllegalStateException If already connected
*
@@ -826,7 +847,7 @@ public abstract class URLConnection
* @deprecated 1.3 The method setRequestProperty should be used instead.
* This method does nothing now.
*
- * @see URLConnection#setRequestProperty(String key, String value)
+ * @see URLConnection#setRequestProperty(String, String)
*/
public static void setDefaultRequestProperty(String key, String value)
{
@@ -845,7 +866,7 @@ public abstract class URLConnection
* @deprecated 1.3 The method getRequestProperty should be used instead.
* This method does nothing now.
*
- * @see URLConnection#getRequestProperty(String key)
+ * @see URLConnection#getRequestProperty(String)
*/
public static String getDefaultRequestProperty(String key)
{
@@ -913,8 +934,10 @@ public abstract class URLConnection
* @exception IOException If an error occurs
*/
public static String guessContentTypeFromStream(InputStream is)
- throws IOException
+ throws IOException, NotImplementedException
{
+ // See /etc/gnome-vfs-mime-magic or /etc/mime-magic for a reasonable
+ // idea of how to handle this.
return "application/octet-stream";
}
@@ -969,44 +992,66 @@ public abstract class URLConnection
if (factory != null)
handler = factory.createContentHandler(contentType);
- // Then try our default class.
- try
- {
- String typeClass = contentType.replace('/', '.');
+ // Now try default factory. Using this factory to instantiate built-in
+ // content handlers is preferable
+ if (handler == null)
+ handler = defaultFactory.createContentHandler(contentType);
- // Deal with "Content-Type: text/html; charset=ISO-8859-1".
- int parameterBegin = typeClass.indexOf(';');
- if (parameterBegin >= 1)
- typeClass = typeClass.substring(0, parameterBegin);
-
- Class cls = Class.forName("gnu.java.net.content." + typeClass);
- Object obj = cls.newInstance();
-
- if (obj instanceof ContentHandler)
- {
- handler = (ContentHandler) obj;
- return handler;
- }
- }
- catch (ClassNotFoundException e)
- {
- // Ignore.
- }
- catch (InstantiationException e)
- {
- // Ignore.
- }
- catch (IllegalAccessException e)
+ // User-set factory has not returned a handler. Use the default search
+ // algorithm.
+ if (handler == null)
{
- // Ignore.
+ // Get the list of packages to check and append our default handler
+ // to it, along with the JDK specified default as a last resort.
+ // Except in very unusual environments the JDK specified one shouldn't
+ // ever be needed (or available).
+ String propVal = SystemProperties.getProperty("java.content.handler.pkgs");
+ propVal = (((propVal == null) ? "" : (propVal + "|"))
+ + "gnu.java.net.content|sun.net.www.content");
+
+ // Deal with "Content-Type: text/html; charset=ISO-8859-1".
+ int parameterBegin = contentType.indexOf(';');
+ if (parameterBegin >= 1)
+ contentType = contentType.substring(0, parameterBegin);
+ contentType = contentType.trim();
+
+ // Replace the '/' character in the content type with '.' and
+ // all other non-alphabetic, non-numeric characters with '_'.
+ char[] cArray = contentType.toCharArray();
+ for (int i = 0; i < cArray.length; i++)
+ {
+ if (cArray[i] == '/')
+ cArray[i] = '.';
+ else if (! ((cArray[i] >= 'A' && cArray[i] <= 'Z') ||
+ (cArray[i] >= 'a' && cArray[i] <= 'z') ||
+ (cArray[i] >= '0' && cArray[i] <= '9')))
+ cArray[i] = '_';
+ }
+ String contentClass = new String(cArray);
+
+ // See if a class of this content type exists in any of the packages.
+ StringTokenizer pkgPrefix = new StringTokenizer(propVal, "|");
+ do
+ {
+ String facName = pkgPrefix.nextToken() + "." + contentClass;
+ try
+ {
+ handler =
+ (ContentHandler) Class.forName(facName).newInstance();
+ }
+ catch (Exception e)
+ {
+ // Can't instantiate; handler still null, go on to next element.
+ }
+ } while (handler == null && pkgPrefix.hasMoreTokens());
}
return handler;
}
// We don't put these in a static initializer, because it creates problems
- // with initializer co-dependency: SimpleDateFormat's constructors eventually
- // depend on URLConnection (via the java.text.*Symbols classes).
+ // with initializer co-dependency: SimpleDateFormat's constructors
+ // eventually depend on URLConnection (via the java.text.*Symbols classes).
private static synchronized void initializeDateFormats()
{
if (dateformats_initialized)
diff --git a/libjava/classpath/java/net/class-dependencies.conf b/libjava/classpath/java/net/class-dependencies.conf
deleted file mode 100644
index 8b130f53684..00000000000
--- a/libjava/classpath/java/net/class-dependencies.conf
+++ /dev/null
@@ -1,122 +0,0 @@
-# This property file contains dependencies of classes, methods, and
-# field on other methods or classes.
-#
-# Syntax:
-#
-# <used>: <needed 1> [... <needed N>]
-#
-# means that when <used> is included, <needed 1> (... <needed N>) must
-# be included as well.
-#
-# <needed X> and <used> are of the form
-#
-# <class.methodOrField(signature)>
-#
-# or just
-#
-# <class>
-#
-# Within dependencies, variables can be used. A variable is defined as
-# follows:
-#
-# {variable}: value1 value2 ... value<n>
-#
-# variables can be used on the right side of dependencies as follows:
-#
-# <used>: com.bla.blu.{variable}.Class.m()V
-#
-# The use of the variable will expand to <n> dependencies of the form
-#
-# <used>: com.bla.blu.value1.Class.m()V
-# <used>: com.bla.blu.value2.Class.m()V
-# ...
-# <used>: com.bla.blu.value<n>.Class.m()V
-#
-# Variables can be redefined when building a system to select the
-# required support for features like encodings, protocols, etc.
-#
-# Hints:
-#
-# - For methods and fields, the signature is mandatory. For
-# specification, please see the Java Virtual Machine Specification by
-# SUN. Unlike in the spec, field signatures (types) are in brackets.
-#
-# - Package names must be separated by '/' (and not '.'). E.g.,
-# java/lang/Class (this is necessary, because the '.' is used to
-# separate method or field names from classes)
-#
-# - In case <needed> refers to a class, only the class itself will be
-# included in the resulting binary, NOT necessarily all its methods
-# and fields. If you want to refer to all methods and fields, you can
-# write class.* as an abbreviation.
-#
-# - Abbreviations for packages are also possible: my/package/* means all
-# methods and fields of all classes in my/package.
-#
-# - A line with a trailing '\' continues in the next line.
-
-java/net/InetAddress: \
- java/lang/ClassNotFoundException.<init>(Ljava/lang/String;)V \
- java/lang/InternalError.<init>(Ljava/lang/String;)V \
- java/net/UnknownHostException.<init>(Ljava/lang/String;)V
-
-java/net/DatagramSocketImpl: \
- java/net/DatagramSocketImpl.fd(Ljava/io/FileDescriptor;) \
- java/net/DatagramSocketImpl.localPort(I)
-
-java/net/PlainDatagramSocketImpl: \
- java/lang/ClassNotFoundException.<init>(Ljava/lang/String;)V \
- java/lang/InternalError.<init>(Ljava/lang/String;)V \
- java/io/IOException.<init>(Ljava/lang/String;)V \
- java/io/FileDescriptor.<init>()V \
- java/lang/Boolean.<init>(Z)V \
- java/lang/Integer.<init>(I)V \
- java/net/InetAddress.getByName(Ljava/lang/String;)Ljava/net/InetAddress; \
- java/net/InetAddress.getAddress()[B \
- java/lang/Boolean.booleanValue()Z \
- java/lang/Integer.intValue()I \
- java/net/SocketException.<init>(Ljava/lang/String;)V \
- java/net/DatagramPacket.getData()[B \
- java/net/SocketImpl.address(Ljava/net/InetAddress;) \
- java/net/PlainSocketImpl.native_fd(I) \
- java/net/SocketImpl.fd(Ljava/io/FileDescriptor;) \
- java/net/SocketImpl.address(Ljava/net/InetAddress;) \
- java/net/PlainDatagramSocketImpl.native_fd(I) \
- java/net/SocketImpl.localport(I) \
- java/net/SocketImpl.port(I)
-
-java/net/PlainSocketImpl: \
- java/lang/ClassNotFoundException.<init>(Ljava/lang/String;)V \
- java/lang/InternalError.<init>(Ljava/lang/String;)V \
- java/io/IOException.<init>(Ljava/lang/String;)V \
- java/io/FileDescriptor.<init>()V \
- java/lang/Boolean.<init>(Z)V \
- java/lang/Integer.<init>(I)V \
- java/net/InetAddress.getByName(Ljava/lang/String;)Ljava/net/InetAddress; \
- java/net/InetAddress.getAddress()[B \
- java/lang/Boolean.booleanValue()Z \
- java/lang/Integer.intValue()I \
- java/net/SocketException.<init>(Ljava/lang/String;)V \
- java/net/DatagramPacket.getData()[B \
- java/net/SocketImpl.address(Ljava/net/InetAddress;) \
- java/net/PlainSocketImpl.native_fd(I) \
- java/net/SocketImpl.fd(Ljava/io/FileDescriptor;) \
- java/net/SocketImpl.address(Ljava/net/InetAddress;) \
- java/net/PlainDatagramSocketImpl.native_fd(I) \
- java/net/SocketImpl.localport(I) \
- java/net/SocketImpl.port(I)
-
-# All protocols supported are loaded via URL.getURLStreamHandler from
-# class gnu.java.net.protocol.<protocol>.Handler.
-#
-# This introduces a dependency for all protocols. To allow an easy selection
-# and addition of protocols, the library variable {protocols} can be set to
-# the set of supported protocols.
-#
-{protocols}: http file jar
-
-java/net/URL.getURLStreamHandler(Ljava/lang/String;)Ljava/net/URLStreamHandler;: \
- gnu/java/net/protocol/{protocols}/Handler.* \
- com/aicas/java/net/protocol/rom/Handler.*
-
-# end of file
diff --git a/libjava/classpath/java/nio/ByteBufferImpl.java b/libjava/classpath/java/nio/ByteBufferImpl.java
index 48d7152000b..aa51a65bdd5 100644
--- a/libjava/classpath/java/nio/ByteBufferImpl.java
+++ b/libjava/classpath/java/nio/ByteBufferImpl.java
@@ -115,18 +115,11 @@ final class ByteBufferImpl extends ByteBuffer
checkIfReadOnly();
mark = -1;
int pos = position();
- if (pos > 0)
- {
- int count = remaining();
- shiftDown(0, pos, count);
- position(count);
- limit(capacity());
- }
- else
- {
- position(limit());
- limit(capacity());
- }
+ int n = limit() - pos;
+ if (n > 0)
+ shiftDown(0, pos, n);
+ position(n);
+ limit(capacity());
return this;
}
diff --git a/libjava/classpath/java/nio/CharBufferImpl.java b/libjava/classpath/java/nio/CharBufferImpl.java
index 33f8dab983f..e6097cb7516 100644
--- a/libjava/classpath/java/nio/CharBufferImpl.java
+++ b/libjava/classpath/java/nio/CharBufferImpl.java
@@ -90,15 +90,14 @@ final class CharBufferImpl extends CharBuffer
{
checkIfReadOnly();
mark = -1;
- int copied = 0;
-
- while (remaining () > 0)
+ int p = position();
+ int n = limit() - p;
+ if (n > 0)
{
- put (copied, get ());
- copied++;
+ System.arraycopy(backing_buffer, array_offset + p,
+ backing_buffer, array_offset, n);
}
-
- position (copied);
+ position(n);
limit(capacity());
return this;
}
diff --git a/libjava/classpath/java/nio/DoubleBufferImpl.java b/libjava/classpath/java/nio/DoubleBufferImpl.java
index 248ab45e7c2..98e8e974fff 100644
--- a/libjava/classpath/java/nio/DoubleBufferImpl.java
+++ b/libjava/classpath/java/nio/DoubleBufferImpl.java
@@ -82,15 +82,14 @@ final class DoubleBufferImpl extends DoubleBuffer
{
checkIfReadOnly();
mark = -1;
- int copied = 0;
-
- while (remaining () > 0)
+ int p = position();
+ int n = limit() - p;
+ if (n > 0)
{
- put (copied, get ());
- copied++;
+ System.arraycopy(backing_buffer, array_offset + p,
+ backing_buffer, array_offset, n);
}
-
- position (copied);
+ position(n);
limit(capacity());
return this;
}
diff --git a/libjava/classpath/java/nio/FloatBufferImpl.java b/libjava/classpath/java/nio/FloatBufferImpl.java
index b4868780c42..f1182ba38f3 100644
--- a/libjava/classpath/java/nio/FloatBufferImpl.java
+++ b/libjava/classpath/java/nio/FloatBufferImpl.java
@@ -82,15 +82,14 @@ final class FloatBufferImpl extends FloatBuffer
{
checkIfReadOnly();
mark = -1;
- int copied = 0;
-
- while (remaining () > 0)
+ int p = position();
+ int n = limit() - p;
+ if (n > 0)
{
- put (copied, get ());
- copied++;
+ System.arraycopy(backing_buffer, array_offset + p,
+ backing_buffer, array_offset, n);
}
-
- position (copied);
+ position(n);
limit(capacity());
return this;
}
diff --git a/libjava/classpath/java/nio/IntBufferImpl.java b/libjava/classpath/java/nio/IntBufferImpl.java
index 22657482b42..2bd1842440e 100644
--- a/libjava/classpath/java/nio/IntBufferImpl.java
+++ b/libjava/classpath/java/nio/IntBufferImpl.java
@@ -82,15 +82,14 @@ final class IntBufferImpl extends IntBuffer
{
checkIfReadOnly();
mark = -1;
- int copied = 0;
-
- while (remaining () > 0)
+ int p = position();
+ int n = limit() - p;
+ if (n > 0)
{
- put (copied, get ());
- copied++;
+ System.arraycopy(backing_buffer, array_offset + p,
+ backing_buffer, array_offset, n);
}
-
- position (copied);
+ position(n);
limit(capacity());
return this;
}
diff --git a/libjava/classpath/java/nio/LongBufferImpl.java b/libjava/classpath/java/nio/LongBufferImpl.java
index 8772f618c19..c04c41775a9 100644
--- a/libjava/classpath/java/nio/LongBufferImpl.java
+++ b/libjava/classpath/java/nio/LongBufferImpl.java
@@ -82,15 +82,14 @@ final class LongBufferImpl extends LongBuffer
{
checkIfReadOnly();
mark = -1;
- int copied = 0;
-
- while (remaining () > 0)
+ int p = position();
+ int n = limit() - p;
+ if (n > 0)
{
- put (copied, get ());
- copied++;
+ System.arraycopy(backing_buffer, array_offset + p,
+ backing_buffer, array_offset, n);
}
-
- position (copied);
+ position(n);
limit(capacity());
return this;
}
diff --git a/libjava/classpath/java/nio/MappedByteBuffer.java b/libjava/classpath/java/nio/MappedByteBuffer.java
index fa25bb7f1e7..25b0993079a 100644
--- a/libjava/classpath/java/nio/MappedByteBuffer.java
+++ b/libjava/classpath/java/nio/MappedByteBuffer.java
@@ -85,7 +85,7 @@ public abstract class MappedByteBuffer extends ByteBuffer
forceImpl();
}
- public void finalize()
+ protected void finalize()
throws Throwable
{
unmapImpl();
diff --git a/libjava/classpath/java/nio/ShortBufferImpl.java b/libjava/classpath/java/nio/ShortBufferImpl.java
index ee5bff2f95b..50f65ecbfc0 100644
--- a/libjava/classpath/java/nio/ShortBufferImpl.java
+++ b/libjava/classpath/java/nio/ShortBufferImpl.java
@@ -82,15 +82,14 @@ final class ShortBufferImpl extends ShortBuffer
{
checkIfReadOnly();
mark = -1;
- int copied = 0;
-
- while (remaining () > 0)
+ int p = position();
+ int n = limit() - p;
+ if (n > 0)
{
- put (copied, get ());
- copied++;
+ System.arraycopy(backing_buffer, array_offset + p,
+ backing_buffer, array_offset, n);
}
-
- position (copied);
+ position(n);
limit(capacity());
return this;
}
diff --git a/libjava/classpath/java/nio/channels/Channels.java b/libjava/classpath/java/nio/channels/Channels.java
index cfd8605c3b3..382a3d70538 100644
--- a/libjava/classpath/java/nio/channels/Channels.java
+++ b/libjava/classpath/java/nio/channels/Channels.java
@@ -39,6 +39,7 @@ exception statement from your version. */
package java.nio.channels;
import gnu.java.nio.ChannelReader;
+import gnu.java.nio.ChannelWriter;
import gnu.java.nio.InputStreamChannel;
import gnu.java.nio.OutputStreamChannel;
@@ -126,8 +127,7 @@ public final class Channels
public static Writer newWriter(WritableByteChannel ch, CharsetEncoder enc,
int minBufferCap)
{
- // FIXME: implement java.nio.channels.Channel.newWriter(WritableByteChannel, CharsetEncoder, int)
- throw new Error("not implemented");
+ return new ChannelWriter(ch, enc, minBufferCap);
}
/**
diff --git a/libjava/classpath/java/nio/class-dependencies.conf b/libjava/classpath/java/nio/class-dependencies.conf
deleted file mode 100644
index 4fbf75eb1ce..00000000000
--- a/libjava/classpath/java/nio/class-dependencies.conf
+++ /dev/null
@@ -1,58 +0,0 @@
-# This property file contains dependencies of classes, methods, and
-# field on other methods or classes.
-#
-# Syntax:
-#
-# <used>: <needed 1> [... <needed N>]
-#
-# means that when <used> is included, <needed 1> (... <needed N>) must
-# be included as well.
-#
-# <needed X> and <used> are of the form
-#
-# <class.methodOrField(signature)>
-#
-# or just
-#
-# <class>
-#
-# Within dependencies, variables can be used. A variable is defined as
-# follows:
-#
-# {variable}: value1 value2 ... value<n>
-#
-# variables can be used on the right side of dependencies as follows:
-#
-# <used>: com.bla.blu.{variable}.Class.m()V
-#
-# The use of the variable will expand to <n> dependencies of the form
-#
-# <used>: com.bla.blu.value1.Class.m()V
-# <used>: com.bla.blu.value2.Class.m()V
-# ...
-# <used>: com.bla.blu.value<n>.Class.m()V
-#
-# Variables can be redefined when building a system to select the
-# required support for features like encodings, protocols, etc.
-#
-# Hints:
-#
-# - For methods and fields, the signature is mandatory. For
-# specification, please see the Java Virtual Machine Specification by
-# SUN. Unlike in the spec, field signatures (types) are in brackets.
-#
-# - Package names must be separated by '/' (and not '.'). E.g.,
-# java/lang/Class (this is necessary, because the '.' is used to
-# separate method or field names from classes)
-#
-# - In case <needed> refers to a class, only the class itself will be
-# included in the resulting binary, NOT necessarily all its methods
-# and fields. If you want to refer to all methods and fields, you can
-# write class.* as an abbreviation.
-#
-# - Abbreviations for packages are also possible: my/package/* means all
-# methods and fields of all classes in my/package.
-#
-# - A line with a trailing '\' continues in the next line.
-
-# end of file
diff --git a/libjava/classpath/java/rmi/activation/Activatable.java b/libjava/classpath/java/rmi/activation/Activatable.java
index b4c38bf61a8..472c65c1110 100644
--- a/libjava/classpath/java/rmi/activation/Activatable.java
+++ b/libjava/classpath/java/rmi/activation/Activatable.java
@@ -1,5 +1,6 @@
-/* Activatable.java --
- Copyright (c) 1996, 1997, 1998, 1999, 2004 Free Software Foundation, Inc.
+/* Activatable.java -- A common ancestor for the activatable objects.
+ Copyright (c) 1996, 1997, 1998, 1999, 2004, 2006
+ Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -38,68 +39,493 @@ exception statement from your version. */
package java.rmi.activation;
+import gnu.java.rmi.server.ActivatableServerRef;
+import gnu.java.rmi.server.UnicastServer;
+import gnu.java.rmi.server.UnicastServerRef;
+
+import java.lang.reflect.Field;
import java.rmi.MarshalledObject;
import java.rmi.NoSuchObjectException;
import java.rmi.Remote;
import java.rmi.RemoteException;
+import java.rmi.server.ObjID;
import java.rmi.server.RMIClientSocketFactory;
import java.rmi.server.RMIServerSocketFactory;
+import java.rmi.server.RemoteObject;
import java.rmi.server.RemoteServer;
+import java.rmi.server.UnicastRemoteObject;
-public abstract class Activatable extends RemoteServer
+/**
+ * A common ancestor for the implementations of the activatable objects. Such
+ * objects require persistent access over time and can be activated by the
+ * system. The derived classes also implements the needed interface of some
+ * remote object and usually have the two parameter constructor, the first
+ * parameter being the {@link ActivationID} and the second the
+ * {@link MarshalledObject}. Activatable is the main class that developers need
+ * to use to implement and manage activatable objects. It also contains methods
+ * for making activatable remote objects that are not derived from the
+ * Activatable class.
+ *
+ * @author Audrius Meskauskas (audriusa@bioinformatics.org) (from stub)
+ */
+public abstract class Activatable
+ extends RemoteServer
{
-static final long serialVersionUID = -3120617863591563455L;
-protected Activatable(String location, MarshalledObject data, boolean restart, int port) throws ActivationException, RemoteException {
- throw new Error("Not implemented");
-}
+ /**
+ * Use SVUID for interoperability.
+ */
+ static final long serialVersionUID = - 3120617863591563455L;
+
+ /**
+ * The object activation id.
+ */
+ final ActivationID id;
+
+ /**
+ * This constructor is used to register export the object on the given port. A
+ * subclass of the Activatable class calls this constructor to register and
+ * export the object during initial construction. As a side-effect of
+ * activatable object construction, the remote object is both "registered"
+ * with the activation system and "exported" (on an anonymous port, if port is
+ * zero) to the RMI runtime so that it is available to accept incoming calls
+ * from clients.
+ *
+ * @param codebase the object code base url
+ * @param data the data, needed to activate the object.
+ * @param restart specifies reactivation mode after crash. If true, the object
+ * is activated when activator is restarted or the activation group
+ * is restarted. If false, the object is only activated on demand.
+ * This flag does has no effect during the normal operation (the
+ * object is normally activated on demand).
+ * @param port the port, on which the object will become available. The value
+ * 0 means anonymous port.
+ * @throws ActivationException if the activation failed
+ * @throws RemoteException if the remote call failed.
+ */
+ protected Activatable(String codebase, MarshalledObject data,
+ boolean restart, int port) throws ActivationException,
+ RemoteException
+ {
+ ActivationDesc descriptor = new ActivationDesc(getClass().getName(),
+ codebase, data, restart);
+ id = obtainId(descriptor);
+ exportObject(this, id, port);
+ }
-protected Activatable(String location, MarshalledObject data, boolean restart, int port, RMIClientSocketFactory csf, RMIServerSocketFactory ssf) throws ActivationException, RemoteException {
- throw new Error("Not implemented");
-}
+ /**
+ * This constructor is used to register export the object on the given port,
+ * additionally specifying the socket factories. A subclass of the Activatable
+ * class calls this constructor to register and export the object during
+ * initial construction.
+ *
+ * @param codebase the object code base url
+ * @param data the data, needed to activate the object.
+ * @param restart specifies reactivation mode after crash. If true, the object
+ * is activated when activator is restarted or the activation group
+ * is restarted. If false, the object is only activated on demand.
+ * This flag does has no effect during the normal operation (the
+ * object is normally activated on demand).
+ * @param port the port, on which the object will become available. The value
+ * 0 means anonymous port.
+ * @param csf the client socket factory
+ * @param ssf the server socket factory
+ * @throws ActivationException if the activation failed
+ * @throws RemoteException if the remote call failed.
+ */
+ protected Activatable(String codebase, MarshalledObject data,
+ boolean restart, int port, RMIClientSocketFactory csf,
+ RMIServerSocketFactory ssf) throws ActivationException,
+ RemoteException
+ {
+ ActivationDesc descriptor = new ActivationDesc(getClass().getName(),
+ codebase, data, restart);
+ id = obtainId(descriptor);
+ exportObject(this, id, port);
+ }
-protected Activatable(ActivationID id, int port) throws RemoteException {
- throw new Error("Not implemented");
-}
+ /**
+ * Creates the new instance of activatable with the given activation id and is
+ * listening at the given port. A subclass of the Activatable class calls this
+ * constructor when the object itself is activated via its special
+ * "activation" constructor with the two parameters ({@link ActivationID},
+ * {@link MarshalledObject}). As a side effect, the object is exported and is
+ * available to accept incomming calls.
+ *
+ * @param anId the activation id
+ * @param port the port, on which the activatable will be listening
+ * @throws RemoteException if the activation failed.
+ */
+ protected Activatable(ActivationID anId, int port) throws RemoteException
+ {
+ id = anId;
+ try
+ {
+ exportObject(this, anId, port);
+ }
+ catch (Exception e)
+ {
+ e.printStackTrace();
+ RemoteException acex =
+ new RemoteException("cannot export Activatable", e);
+ throw acex;
+ }
+ }
-protected Activatable(ActivationID id, int port, RMIClientSocketFactory csf, RMIServerSocketFactory ssf) throws RemoteException {
- throw new Error("Not implemented");
-}
+ /**
+ * Creates the new instance of activatable with the given activation id and is
+ * listening at the given port, using the specified client and server sockets
+ * factories. A subclass of the Activatable class calls this
+ * constructor when the object itself is activated via its special
+ * "activation" constructor with the two parameters ({@link ActivationID},
+ * {@link MarshalledObject}). As a side effect, the object is exported and is
+ * available to accept incomming calls.
+ *
+ * @param anId the activation id
+ * @param port the port, on which the activatable will be listening
+ * @param csf the client socket factory
+ * @param ssf the server socket factory
+ *
+ * @throws RemoteException if the remote call failed
+ */
+ protected Activatable(ActivationID anId, int port, RMIClientSocketFactory csf,
+ RMIServerSocketFactory ssf) throws RemoteException
+ {
+ id = anId;
+ try
+ {
+ exportObject(this, anId, port, csf, ssf);
+ }
+ catch (Exception e)
+ {
+ RemoteException acex = new RemoteException();
+ acex.initCause(e);
+ throw acex;
+ }
+ }
+
+ /**
+ * Get the objects activation identifier.
+ *
+ * @return the object activation identifier
+ */
+ protected ActivationID getID()
+ {
+ return id;
+ }
+
+ /**
+ * Obtain the activation Id from the activation descriptor by registering
+ * within the current group.
+ */
+ static ActivationID obtainId(ActivationDesc descriptor)
+ throws RemoteException, UnknownGroupException, ActivationException
+ {
+ ActivationGroupID id = descriptor.getGroupID();
+ ActivationSystem system;
-protected ActivationID getID() {
- throw new Error("Not implemented");
-}
+ if (id != null)
+ system = id.getSystem();
+ else
+ system = ActivationGroup.currentGroupID().getSystem();
+ return system.registerObject(descriptor);
+ }
+
+ /**
+ * This method registers an activatable object. The object is expected to be
+ * on the anonymous port (null client and server socket factories).
+ *
+ * @param desc the object description.
+ * @return the remote stub for the activatable object (the first call on this
+ * stub will activate the object).
+ * @throws UnknownGroupException if the object group identifier is unknown
+ * @throws ActivationException if the activation system is not running
+ * @throws RemoteException if the remote call fails
+ */
+ public static Remote register(ActivationDesc desc)
+ throws UnknownGroupException, ActivationException, RemoteException
+ {
+ ActivationID id = obtainId(desc);
+ try
+ {
+ return toStub(
+ id,
+ Thread.currentThread().getContextClassLoader().loadClass(
+ desc.getClassName()));
+ }
+ catch (ClassNotFoundException e)
+ {
+ throw new ActivationException("Class not found: "+desc.getClassName());
+ }
+ }
+
+ /**
+ * Inactivates and unexports the object. The subsequent calls will activate
+ * the object again. The object is not inactivated if it is currently
+ * executing calls.
+ *
+ * @param id the id of the object being inactivated
+ * @return true if the object has been inactivated, false if it has not been
+ * inactivated because of the running or pending calls.
+ * @throws UnknownObjectException if the object is unknown.
+ * @throws ActivationException if the object group is not active
+ * @throws RemoteException if the remote call fails
+ */
+ public static boolean inactive(ActivationID id)
+ throws UnknownObjectException, ActivationException, RemoteException
+ {
+ if (id.group!=null)
+ id.group.inactiveObject(id);
+ return UnicastRemoteObject.unexportObject(id.activate(false), false);
+ }
+
+ /**
+ * Unregister the object (the object will no longer be activable with that id)
+ *
+ * @param id the object id
+ * @throws UnknownObjectException if the id is unknown
+ * @throws ActivationException if the activation system is not running
+ * @throws RemoteException if the remote call fails.
+ */
+ public static void unregister(ActivationID id) throws UnknownObjectException,
+ ActivationException, RemoteException
+ {
+ ActivationGroup.currentGroupId.getSystem().unregisterObject(id);
+ UnicastServer.unregisterActivatable(id);
+ }
+
+ /**
+ * Register and export the object that activatable object that is not derived
+ * from the Activatable super class. It creates and registers the object
+ * activation descriptor. There is no need to call this method if the object
+ * extends Activable, as its work is done in the constructor
+ * {@link #Activatable(String, MarshalledObject, boolean, int)}.
+ *
+ * @param obj the object, that is exported, becoming available at the given
+ * port.
+ * @param location the object code location (codebase).
+ * @param data the data, needed to activate the object
+ * @param restart the restart mode
+ * @param port the port, where the object will be available
+ *
+ * @return the created object activation ID.
+ *
+ * @throws ActivationException if the activation group is not active
+ * @throws RemoteException if the registration or export fails
+ */
+ public static ActivationID exportObject(Remote obj, String location,
+ MarshalledObject data,
+ boolean restart, int port)
+ throws ActivationException, RemoteException
+ {
+ ActivationDesc descriptor = new ActivationDesc(obj.getClass().getName(),
+ location, data, restart);
+ ActivationID id = obtainId(descriptor);
+ Remote stub = exportObject(obj, id, port);
+ return id;
+ }
-public static Remote register(ActivationDesc desc) throws UnknownGroupException, ActivationException, RemoteException {
- throw new Error("Not implemented");
-}
+ /**
+ * Register and export the object that activatable object that is not derived
+ * from the Activatable super class. It creates and registers the object
+ * activation descriptor. There is no need to call this method if the object
+ * extends Activable, as its work is done in the constructor
+ * {@link #Activatable(String, MarshalledObject, boolean, int, RMIClientSocketFactory, RMIServerSocketFactory)}
+ *
+ * @param obj the object, that is exported, becoming available at the given
+ * port.
+ * @param location the object code location (codebase).
+ * @param data the data, needed to activate the object
+ * @param restart the restart mode
+ * @param port the port, where the object will be available
+ * @param csf the client socket factory
+ * @param ssf the server socket factory
+ *
+ * @return the created object activation ID.
+ *
+ * @throws ActivationException if the activation group is not active
+ * @throws RemoteException if the registration or export fails
+ */
+ public static ActivationID exportObject(Remote obj, String location,
+ MarshalledObject data,
+ boolean restart, int port,
+ RMIClientSocketFactory csf,
+ RMIServerSocketFactory ssf)
+ throws ActivationException, RemoteException
+ {
+ ActivationDesc descriptor = new ActivationDesc(obj.getClass().getName(),
+ location, data, restart);
+ ActivationID id = obtainId(descriptor);
+ Remote stub = exportObject(obj, id, port, csf, ssf);
+ return id;
-public static boolean inactive(ActivationID id) throws UnknownObjectException, ActivationException, RemoteException {
- throw new Error("Not implemented");
-}
+ }
-public static void unregister(ActivationID id) throws UnknownObjectException, ActivationException, RemoteException {
- throw new Error("Not implemented");
-}
+ /**
+ * During activation, this exportObject method should be invoked explicitly by
+ * the activatable object, that does is not derived from the Activatable
+ * class. There is no need to call this method if the object extends
+ * Activable, as its work is done in the constructor
+ * {@link #Activatable(ActivationID, int)}
+ *
+ * @param obj the object
+ * @param id the known activation id
+ * @param port the object port
+ *
+ * @return the remote stub of the activatable object
+ *
+ * @throws RemoteException if the object export fails
+ */
+ public static Remote exportObject(Remote obj, ActivationID id, int port)
+ throws RemoteException
+ {
+ Remote stub = export(id, obj, port, null);
+ return stub;
+ }
-public static ActivationID exportObject(Remote obj, String location, MarshalledObject data, boolean restart, int port) throws ActivationException, RemoteException {
- throw new Error("Not implemented");
-}
+ /**
+ * During activation, this exportObject method should be invoked explicitly by
+ * the activatable object, that does is not derived from the Activatable
+ * class. There is no need to call this method if the object extends
+ * Activable, as its work is done in the constructor
+ * {@link #Activatable(ActivationID, int)}
+ *
+ * @param obj the object
+ * @param id the known activation id
+ * @param port the object port
+ * @param csf the client socket factory
+ * @param ssf the server socket factory
+ *
+ * @return the remote stub of the activatable object
+ *
+ * @throws RemoteException if the object export fails
+ */
+ public static Remote exportObject(Remote obj, ActivationID id, int port,
+ RMIClientSocketFactory csf,
+ RMIServerSocketFactory ssf)
+ throws RemoteException
+ {
+ Remote stub = export(id, obj, port, ssf);
+ return stub;
-public static ActivationID exportObject(Remote obj, String location, MarshalledObject data, boolean restart, int port, RMIClientSocketFactory csf, RMIServerSocketFactory ssf) throws ActivationException, RemoteException {
- throw new Error("Not implemented");
-}
+ }
-public static Remote exportObject(Remote obj, ActivationID id, int port) throws RemoteException {
- throw new Error("Not implemented");
-}
+ /**
+ * Make the remote object unavailable for incoming calls. This method also
+ * unregisters the object, so it cannot be activated again by incomming call
+ * (unless registered).
+ *
+ * @param obj the object to unexport
+ * @param force if true, cancel all pending or running calls to that object
+ * (if false, the object with such calls is not unexported and false
+ * is returned by this method).
+ * @return if the object was successfully unexported, false otherwise
+ * @throws NoSuchObjectException if such object is not known
+ */
+ public static boolean unexportObject(Remote obj, boolean force)
+ throws NoSuchObjectException
+ {
+ Object aref = UnicastServer.getExportedRef(obj);
+
+ // Unregister it also (otherwise will be activated during the subsequent
+ // call.
+ if (aref instanceof ActivatableServerRef)
+ {
+ ActivatableServerRef aar = (ActivatableServerRef) aref;
+ UnicastServer.unregisterActivatable(aar.actId);
+ }
+ return UnicastRemoteObject.unexportObject(obj, force);
+ }
+
+ static Remote exportObject(Remote obj, int port,
+ RMIServerSocketFactory serverSocketFactory)
+ throws RemoteException
+ {
+ UnicastServerRef sref = null;
+ if (obj instanceof RemoteObject)
+ sref = (UnicastServerRef) ((RemoteObject) obj).getRef();
-public static Remote exportObject(Remote obj, ActivationID id, int port, RMIClientSocketFactory csf, RMIServerSocketFactory ssf) throws RemoteException {
- throw new Error("Not implemented");
-}
-
-public static boolean unexportObject(Remote obj, boolean force) throws NoSuchObjectException {
- throw new Error("Not implemented");
-}
+ if (sref == null)
+ sref = new UnicastServerRef(new ObjID(), port, serverSocketFactory);
+ Remote stub = sref.exportObject(obj);
+ // addStub(obj, stub);
+ // TODO Need to change the place of the stub repository
+ return stub;
+ }
+
+ /**
+ * Create and export the new remote object, making it available at the given
+ * port, using sockets, produced by the specified factories.
+ *
+ * @param port the port, on that the object should become available. Zero
+ * means anonymous port.
+ * @param serverSocketFactory the server socket factory
+ */
+ public static Remote export(ActivationID id, Remote obj, int port,
+ RMIServerSocketFactory serverSocketFactory)
+ throws RemoteException
+ {
+ ActivatableServerRef sref = null;
+ sref = new ActivatableServerRef(makeId(id), id, port, serverSocketFactory);
+ return sref.exportObject(obj);
+ }
+
+ /**
+ * Make the object ID from the activation ID. The same activation ID always
+ * produces the identical object id.
+ *
+ * @param aid the activation id
+ *
+ * @return the object id
+ */
+ public static ObjID makeId(ActivationID aid)
+ {
+ ObjID id = new ObjID(0);
+
+ // The fields of both ObjID and ActivationID must be package private,
+ // so we need to use the reflection to access them anyway.
+ // Probably other implementations use some very different approach.
+
+ try
+ {
+ Field idUid = ObjID.class.getDeclaredField("space");
+ Field aidUid = ActivationID.class.getDeclaredField("uid");
+
+ aidUid.setAccessible(true);
+ idUid.setAccessible(true);
+
+ idUid.set(id, aidUid.get(aid));
+ }
+ catch (Exception e)
+ {
+ InternalError ierr = new InternalError("Unable to set UID field");
+ ierr.initCause(e);
+ throw ierr;
+ }
+
+ return id;
+ }
+
+ /**
+ * Connect the object to the UnicastServer (export), but not activate it.
+ * The object will be activated on the first call.
+ */
+ static Remote toStub(ActivationID anId, Class stubFor)
+ {
+ try
+ {
+ ActivatableServerRef asr =
+ new ActivatableServerRef(makeId(anId), anId, 0, null);
+ UnicastServer.exportActivatableObject(asr);
+ return asr.exportClass(stubFor);
+ }
+ catch (RemoteException e)
+ {
+ InternalError ierr = new InternalError(
+ "Failed to obtain activatable stub");
+ ierr.initCause(e);
+ throw ierr;
+ }
+ }
}
diff --git a/libjava/classpath/java/rmi/activation/ActivationDesc.java b/libjava/classpath/java/rmi/activation/ActivationDesc.java
index 65894f808d2..b8616562fa5 100644
--- a/libjava/classpath/java/rmi/activation/ActivationDesc.java
+++ b/libjava/classpath/java/rmi/activation/ActivationDesc.java
@@ -1,6 +1,6 @@
-/* ActivationDecc.java --
+/* ActivationDesc.java -- record with info to activate an object
Copyright (c) 1996, 1997, 1998, 1999 Free Software Foundation, Inc.
-
+
This file is part of GNU Classpath.
GNU Classpath is free software; you can redistribute it and/or modify
@@ -40,74 +40,215 @@ package java.rmi.activation;
import java.io.Serializable;
import java.rmi.MarshalledObject;
-public final class ActivationDesc implements Serializable
+/**
+ * Contains the information, necessary to activate the object. This information
+ * includes:
+ * <ul>
+ * <li>the object class name</li>
+ * <li>the object group identifier</li>
+ * <li>the code location (codebase URL) that can be used to load the class
+ * remotely</li>
+ * <li>the object restart mode</li>
+ * <li>the object specific intialization information</li>
+ * </ul>
+ *
+ * @author Audrius Meskauskas (audriusa@bioinformatics.org) (from stub)
+ */
+public final class ActivationDesc
+ implements Serializable
{
+ /**
+ * Use SVUID for interoperability.
+ */
static final long serialVersionUID = 7455834104417690957L;
-private ActivationGroupID groupid;
-private String classname;
-private String location;
-private MarshalledObject data;
-private boolean restart;
-
-public ActivationDesc(String className, String location, MarshalledObject data) throws ActivationException {
- this(ActivationGroup.currentGroupID(), className, location, data, false);
-}
-
-public ActivationDesc(String className, String location, MarshalledObject data, boolean restart) throws ActivationException {
- this(ActivationGroup.currentGroupID(), className, location, data, restart);
-}
-
-public ActivationDesc(ActivationGroupID groupID, String className, String location, MarshalledObject data) {
- this(groupID, className, location, data, false);
-}
-
-public ActivationDesc(ActivationGroupID groupID, String className, String location, MarshalledObject data, boolean restart) {
- this.groupid = groupID;
- this.classname = className;
- this.location = location;
- this.data = data;
- this.restart = restart;
-}
-
-public ActivationGroupID getGroupID() {
- return (groupid);
-}
-
-public String getClassName() {
- return (classname);
-}
-
-public String getLocation() {
- return (location);
-}
-
-public MarshalledObject getData() {
- return (data);
-}
-
-public boolean getRestartMode() {
- return (restart);
-}
-
-public boolean equals(Object obj) {
- if (!(obj instanceof ActivationDesc)) {
- return (false);
- }
- ActivationDesc that = (ActivationDesc)obj;
-
- if (this.groupid.equals(that.groupid) &&
- this.classname.equals(that.classname) &&
- this.location.equals(that.location) &&
- this.data.equals(that.data) &&
- this.restart == that.restart) {
- return (true);
- }
- return (false);
-}
-
-public int hashCode() {
- return (groupid.hashCode() ^ classname.hashCode() ^ location.hashCode() ^ data.hashCode());
-}
-
+ /**
+ * The group id.
+ */
+ private ActivationGroupID groupid;
+
+ /**
+ * The class name.
+ */
+ private String classname;
+
+ /**
+ * The code location URL.
+ */
+ private String location;
+
+ /**
+ * The object specific intitalization data.
+ */
+ private MarshalledObject data;
+
+ /**
+ * The start mode.
+ */
+ private boolean restart;
+
+ /**
+ * Create the new activation description, assuming the object group is the
+ * {@link ActivationGroup#currentGroupID()}.
+ *
+ * @param className the object fully qualified class name
+ * @param location the code base URL
+ * @param data the object initialization data, contained in a marshalled form
+ */
+ public ActivationDesc(String className, String location, MarshalledObject data)
+ throws ActivationException
+ {
+ this(ActivationGroup.currentGroupID(), className, location, data, false);
+ }
+
+ /**
+ * Create the new activation description, assuming the object group is the
+ * {@link ActivationGroup#currentGroupID()}.
+ *
+ * @param className the object fully qualified class name
+ * @param location the code base URL
+ * @param data the object initialization data, contained in a marshalled form
+ * @param restart specifies reactivation mode after crash. If true, the object
+ * is activated when activator is restarted or the activation group
+ * is restarted. If false, the object is only activated on demand.
+ * This flag does has no effect during the normal operation (the
+ * object is normally activated on demand).
+ */
+ public ActivationDesc(String className, String location,
+ MarshalledObject data, boolean restart)
+ throws ActivationException
+ {
+ this(ActivationGroup.currentGroupID(), className, location, data, restart);
+ }
+
+ /**
+ * Create the new activation description. Under crash, the object will only
+ * be reactivated on demand.
+ *
+ * @param groupID the object group id.
+ * @param className the object fully qualified class name
+ * @param location the code base URL
+ * @param data the object initialization data, contained in a marshalled form
+ */
+ public ActivationDesc(ActivationGroupID groupID, String className,
+ String location, MarshalledObject data)
+ {
+ this(groupID, className, location, data, false);
+ }
+
+ /**
+ * Create the new activation description, providing full information.
+ *
+ * @param groupID the object group id.
+ * @param className the object fully qualified class name
+ * @param location the code base URL
+ * @param data the object initialization data, contained in a marshalled form
+ * @param restart specifies reactivation mode after crash. If true, the object
+ * is activated when activator is restarted or the activation group
+ * is restarted. If false, the object is only activated on demand.
+ * This flag does has no effect during the normal operation (the
+ * object is normally activated on demand).
+ */
+ public ActivationDesc(ActivationGroupID groupID, String className,
+ String location, MarshalledObject data, boolean restart)
+ {
+ this.groupid = groupID;
+ this.classname = className;
+ this.location = location;
+ this.data = data;
+ this.restart = restart;
+ }
+
+ public ActivationGroupID getGroupID()
+ {
+ return groupid;
+ }
+
+ /**
+ * Get the class name of the object being activated
+ *
+ * @return the fully qualified class name of the object being activated
+ */
+ public String getClassName()
+ {
+ return classname;
+ }
+
+ /**
+ * Get the code location URL ("codebase") of the object being activated.
+ *
+ * @return the codebase of the object being activated.
+ */
+ public String getLocation()
+ {
+ return location;
+ }
+
+ public MarshalledObject getData()
+ {
+ return data;
+ }
+
+ /**
+ * Get the object reactivation strategy after crash.
+ *
+ * @return true ir the object is activated when activator is restarted or the
+ * activation group is restarted. False if the object is only
+ * activated on demand. This flag does has no effect during the normal
+ * operation (the object is normally activated on demand).
+ */
+ public boolean getRestartMode()
+ {
+ return restart;
+ }
+
+ /**
+ * Compare this object with another activation description for equality.
+ *
+ * @return true if all fields have the equal values, false otherwise.
+ */
+ public boolean equals(Object obj)
+ {
+ if (obj instanceof ActivationDesc)
+ {
+ ActivationDesc that = (ActivationDesc) obj;
+ return eq(groupid, that.groupid) &&
+ eq(classname, that.classname) &&
+ eq(location, that.location) &&
+ eq(data, that.data)
+ && restart == that.restart;
+ }
+ else
+ return false;
+ }
+
+ /**
+ * Get the hash code of this object (overridden to make the returned value
+ * consistent with .equals(..).
+ */
+ public int hashCode()
+ {
+ return hash(groupid) ^ hash(classname) ^
+ hash(location) ^ hash(data);
+ }
+
+ /**
+ * Get the hashcode of x or 0 if x == null.
+ */
+ static final int hash(Object x)
+ {
+ return x == null ? 0 : x.hashCode();
+ }
+
+ /**
+ * Compare by .equals if both a and b are not null, compare directly if at
+ * least one of them is null.
+ */
+ static final boolean eq(Object a, Object b)
+ {
+ if (a == null || b == null)
+ return a == b;
+ else
+ return a.equals(b);
+ }
}
diff --git a/libjava/classpath/java/rmi/activation/ActivationGroup.java b/libjava/classpath/java/rmi/activation/ActivationGroup.java
index e5774a1b961..5e7bbd20998 100644
--- a/libjava/classpath/java/rmi/activation/ActivationGroup.java
+++ b/libjava/classpath/java/rmi/activation/ActivationGroup.java
@@ -1,5 +1,5 @@
-/* ActivationGroup.java --
- Copyright (c) 1996, 1997, 1998, 1999 Free Software Foundation, Inc.
+/* ActivationGroup.java -- the RMI activation group.
+ Copyright (c) 1996, 1997, 1998, 1999, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -38,48 +38,302 @@ exception statement from your version. */
package java.rmi.activation;
+import gnu.java.rmi.activation.DefaultActivationGroup;
+import gnu.java.rmi.activation.DefaultActivationSystem;
+
+import java.lang.reflect.Constructor;
import java.rmi.MarshalledObject;
import java.rmi.Remote;
import java.rmi.RemoteException;
import java.rmi.server.UnicastRemoteObject;
-public abstract class ActivationGroup extends UnicastRemoteObject
- implements ActivationInstantiator
+/**
+ * The entity that receives the request to activate object and activates it.
+ * Frequently there is one activation group per virtual machine.
+ *
+ * @author Audrius Meskauskas (audriusa@Bioinformatics.org) (from stub)
+ */
+public abstract class ActivationGroup
+ extends UnicastRemoteObject
+ implements ActivationInstantiator
{
-static final long serialVersionUID = -7696947875314805420L;
-protected ActivationGroup(ActivationGroupID groupID) throws RemoteException {
- throw new Error("Not implemented");
-}
+ /**
+ * Use the SVUID for interoperability.
+ */
+ static final long serialVersionUID = - 7696947875314805420L;
+
+ /**
+ * The Id of the current group on this VM (null if none).
+ */
+ static ActivationGroupID currentGroupId = null;
+
+ /**
+ * The groups identifier.
+ */
+ final ActivationGroupID groupId;
-public boolean inactiveObject(ActivationID id) throws ActivationException, UnknownObjectException, RemoteException {
- throw new Error("Not implemented");
-}
+ /**
+ * The groups activation monitor.
+ */
+ ActivationMonitor monitor;
+
+ /**
+ * The groups incarnation number.
+ */
+ long incarnation;
+
+ /**
+ * The groups activation system.
+ */
+ static ActivationSystem system;
+
+ /**
+ * Used during the group creation (required constructor).
+ */
+ static final Class[] cConstructorTypes = new Class[]
+ {
+ ActivationGroupID.class,
+ MarshalledObject.class
+ };
-public abstract void activeObject(ActivationID id, Remote obj) throws ActivationException, UnknownObjectException, RemoteException;
+ /**
+ * Create the new activation group with the given group id.
+ *
+ * @param aGroupId the group Id.
+ *
+ * @throws RemoteException if the group export fails.
+ */
+ protected ActivationGroup(ActivationGroupID aGroupId) throws RemoteException
+ {
+ groupId = aGroupId;
+ }
+
+ /**
+ * The method is called when the object is exported. The group must notify
+ * the activation monitor, if this was not already done before.
+ *
+ * @param id the object activation id
+ * @param obj the remote object implementation
+ *
+ * @throws ActivationException if the group is inactive
+ * @throws UnknownObjectException if such object is not known
+ * @throws RemoteException if the call to monitor fails
+ */
+ public abstract void activeObject(ActivationID id, Remote obj)
+ throws ActivationException, UnknownObjectException, RemoteException;
+
+ /**
+ * Notifies the monitor about the object being inactivated.
+ *
+ * @param id the object being inactivated.
+ * @return true always (must be overridden to return other values).
+ * @throws ActivationException never
+ * @throws UnknownObjectException if the object is not known
+ * @throws RemoteException if the remote call to monitor fails
+ */
+ public boolean inactiveObject(ActivationID id) throws ActivationException,
+ UnknownObjectException, RemoteException
+ {
+ if (monitor != null)
+ monitor.inactiveObject(id);
+ return true;
+ }
-public static ActivationGroup createGroup(ActivationGroupID id, ActivationGroupDesc desc, long incarnation) throws ActivationException {
- throw new Error("Not implemented");
-}
+ /**
+ * Create the new instance of the activation group, using the class name and
+ * location information, stored in the passed descriptor. The method expects
+ * the group class to have the two parameter constructor, the first parameter
+ * being the {@link ActivationGroupID} and the second the
+ * {@link MarshalledObject}. The group must be first be registered with the
+ * ActivationSystem. Once a group is created, the currentGroupID method
+ * returns the identifier for this group until the group becomes inactive.
+ *
+ * @param id the activation group id
+ * @param desc the group descriptor, providing the information, necessary to
+ * create the group
+ * @param incarnation the incarnation number
+ * @return the created group instance
+ * @throws ActivationException if the activation fails due any reason
+ */
+ public static ActivationGroup createGroup(ActivationGroupID id,
+ ActivationGroupDesc desc,
+ long incarnation)
+ throws ActivationException
+ {
+ // If the activation system is not yet set, set it to the system.
+ // passed in the group id.
+ if (system == null)
+ system = id.system;
+
+ ActivationGroup group = null;
-public static ActivationGroupID currentGroupID() {
- throw new Error("Not implemented");
-}
+ // TODO at the moment all groups are created on the current jre and the
+ // group class must be reachable via thread context class loader.
+ Class groupClass;
-public static void setSystem(ActivationSystem system) throws ActivationException {
- throw new Error("Not implemented");
-}
+ if (desc.className != null)
+ {
+ try
+ {
+ ClassLoader loader = Thread.currentThread().getContextClassLoader();
+ groupClass = loader.loadClass(desc.className);
+ }
+ catch (ClassNotFoundException e)
+ {
+ ActivationException acex = new ActivationException(
+ "Cannot load " + desc.className);
+ acex.detail = e;
+ throw acex;
+ }
+ }
+ else
+ groupClass = DefaultActivationGroup.class;
-public static ActivationSystem getSystem() throws ActivationException {
- throw new Error("Not implemented");
-}
+ try
+ {
+ Constructor constructor = groupClass.getConstructor(cConstructorTypes);
+ group = (ActivationGroup) constructor.newInstance(
+ new Object[] { id, desc.data });
+ }
+ catch (Exception e)
+ {
+ ActivationException acex = new ActivationException(
+ "Cannot instantiate " + desc.className);
+ acex.detail = e;
+ throw acex;
+ }
-protected void activeObject(ActivationID id, MarshalledObject mobj) throws ActivationException, UnknownObjectException, RemoteException {
- throw new Error("Not implemented");
-}
+ currentGroupId = id;
+ try
+ {
+ group.monitor = getSystem().activeGroup(id, group, incarnation);
+ return group;
+ }
+ catch (RemoteException e)
+ {
+ ActivationException acex = new ActivationException("createGroup");
+ acex.detail = e;
+ throw acex;
+ }
+ }
-protected void inactiveGroup() throws UnknownGroupException, RemoteException {
- throw new Error("Not implemented");
-}
+ /**
+ * Get the id of current activation group.
+ *
+ * @return the id of the current activation group or null if none exists.
+ */
+ public static ActivationGroupID currentGroupID()
+ {
+ try
+ {
+ if (currentGroupId==null)
+ {
+ // This will also assing the currentGroupId to the current
+ // (default) group of the default system.
+ setSystem(DefaultActivationSystem.get());
+ }
+ }
+ catch (ActivationException e)
+ {
+ InternalError ierr = new InternalError("Unable to activate AS");
+ ierr.initCause(e);
+ throw ierr;
+ }
+
+ return currentGroupId;
+ }
+
+ /**
+ * Set the activation system for this virtual machine. The system can only
+ * be set if no group is active.
+ *
+ * @param aSystem the system to set
+ *
+ * @throws ActivationException if some group is active now.
+ */
+ public static void setSystem(ActivationSystem aSystem)
+ throws ActivationException
+ {
+ if (currentGroupId!=null)
+ throw new ActivationException("Group active");
+ else
+ {
+ try
+ {
+ // Register the default transient activation system and group.
+ system = aSystem;
+ ActivationGroupDesc def = new ActivationGroupDesc(
+ DefaultActivationGroup.class.getName(),
+ "",
+ null,
+ null,
+ null);
+ currentGroupId = system.registerGroup(def);
+ }
+ catch (Exception ex)
+ {
+ InternalError ierr = new InternalError("Unable to start default AG");
+ ierr.initCause(ex);
+ throw ierr;
+ }
+ }
+ }
+
+ /**
+ * Get the current activation system. If the system is not set via
+ * {@link #setSystem} method, the default system for this virtual machine is
+ * returned. The default system is first searched by name
+ * "java.rmi.activation.ActivationSystem" on the activation registry port. The
+ * default value of the activation registry port is
+ * {@link ActivationSystem#SYSTEM_PORT}, but it can be changed by putting the
+ * system property java.rmi.activation.port. Both activation system and
+ * activation registry are provided by the RMI daemon tool, RMID, if it is
+ * running on the local host. If the RMID is not running, the internal
+ * transient activation system will be created and returned. This internal
+ * system is highly limited in in capabilities and is not intended to be used
+ * anywhere apart automated testing.
+ *
+ * @return the activation system for this virtual machine
+ * @throws ActivationException
+ */
+ public static ActivationSystem getSystem() throws ActivationException
+ {
+ if (system == null)
+ system = DefaultActivationSystem.get();
+ return system;
+ }
+
+ /**
+ * Makes the call back to the groups {@link ActivationMonitor}.
+ *
+ * @param id the id obj the object being activated
+ * @param mObject the marshalled object, contains the activated remote object
+ * stub.
+ * @throws ActivationException on activation error
+ * @throws UnknownObjectException if such object is not registered
+ * @throws RemoteException on remote call (to monitor) error
+ */
+ protected void activeObject(ActivationID id, MarshalledObject mObject)
+ throws ActivationException, UnknownObjectException, RemoteException
+ {
+ if (monitor!=null)
+ monitor.activeObject(id, mObject);
+
+ id.group = this;
+ }
+
+ /**
+ * Makes the call back to the groups {@link ActivationMonitor} and sets
+ * the current group to null.
+ */
+ protected void inactiveGroup() throws UnknownGroupException, RemoteException
+ {
+ if (monitor!=null)
+ monitor.inactiveGroup(groupId, incarnation);
+
+ if (currentGroupId!=null && currentGroupId.equals(groupId))
+ currentGroupId = null;
+ }
}
diff --git a/libjava/classpath/java/rmi/activation/ActivationGroupDesc.java b/libjava/classpath/java/rmi/activation/ActivationGroupDesc.java
index 35b546e3294..76ac63b6391 100644
--- a/libjava/classpath/java/rmi/activation/ActivationGroupDesc.java
+++ b/libjava/classpath/java/rmi/activation/ActivationGroupDesc.java
@@ -1,5 +1,6 @@
-/* ActivationGroupDesc.java --
- Copyright (c) 1996, 1997, 1998, 1999, 2004 Free Software Foundation, Inc.
+/* ActivationGroupDesc.java -- the RMI activation group descriptor
+ Copyright (c) 1996, 1997, 1998, 1999, 2004, 2006
+ Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -38,97 +39,395 @@ exception statement from your version. */
package java.rmi.activation;
+import gnu.java.rmi.activation.DefaultActivationGroup;
+
import java.io.Serializable;
import java.rmi.MarshalledObject;
+import java.util.Arrays;
+import java.util.Enumeration;
+import java.util.Iterator;
import java.util.Properties;
+import java.util.TreeSet;
+import java.util.zip.Adler32;
-public final class ActivationGroupDesc implements Serializable
+/**
+ * Contains information, necessary to create of recreate the activation objects.
+ * The group descriptor contains:
+ * <ul>
+ * <li>The name of the group's class. This class is derived from the
+ * {@link ActivationGroup}.</li>
+ * <li>The group class code location.</li>
+ * <li>The marshalled object that contains the group specific initialization
+ * information</li>
+ * </ul>
+ * The groups are created by the {@link ActivationGroup#createGroup} method that
+ * expectes the group class to have the two parameter constructor, the first
+ * parameter being the {@link ActivationGroupID} and the second the
+ * {@link MarshalledObject}.
+ *
+ * @author Audrius Meskauskas (audriusa@bioinformatics.org) (from stub)
+ */
+public final class ActivationGroupDesc
+ implements Serializable
{
- static final long serialVersionUID = -4936225423168276595L;
+ /**
+ * Contains the startup options for the {@link ActivationGroup}
+ * implementations. Allows to override system properties and specify other
+ * options for the implementation groups.
+ *
+ * @author Audrius Meskauskas (audriusa@bioinformatics.org) (from stub)
+ */
+ public static class CommandEnvironment
+ implements Serializable
+ {
-public static class CommandEnvironment
- implements Serializable {
+ /**
+ * Use the SVUID for interoperability.
+ */
+ static final long serialVersionUID = 6165754737887770191L;
+
+ /**
+ * The zero size string array used as argv value when null is passed.
+ */
+ private static final String[] NO_ARGS = new String[0];
-static final long serialVersionUID = 6165754737887770191L;
-
-private String cmdpath;
-private String[] argv;
+ /**
+ * The path to the java executable (or null for using default jre).
+ */
+ final String command;
+
+ /**
+ * The extra parameters (may be empty array but never null).
+ */
+ final String[] options;
+
+ /**
+ * Create the new command environment.
+ *
+ * @param commandPatch the full path (and name) to the java executable of
+ * null for using the default executable.
+ * @param args extra options that will be used when creating the activation
+ * group. Null has the same effect as the empty list.
+ */
+ public CommandEnvironment(String commandPatch, String[] args)
+ {
+ command = commandPatch;
+ if (args != null)
+ options = args;
+ else
+ options = NO_ARGS;
+ }
+
+ /**
+ * Get the path to the java executable.
+ *
+ * @return the path to the java executable or null for using the default
+ * jre.
+ */
+ public String getCommandPath()
+ {
+ return command;
+ }
+
+ /**
+ * Get the additional command options.
+ *
+ * @return the command options array, may be empty string
+ */
+ public String[] getCommandOptions()
+ {
+ return options;
+ }
+
+ /**
+ * Compare for content equality.
+ */
+ public boolean equals(Object obj)
+ {
+ if (obj instanceof CommandEnvironment)
+ {
+ CommandEnvironment that = (CommandEnvironment) obj;
-public CommandEnvironment(String cmdpath, String[] argv) {
- this.cmdpath = cmdpath;
- this.argv = argv;
-}
-
-public String getCommandPath() {
- return (cmdpath);
-}
-
-public String[] getCommandOptions() {
- return (argv);
-}
-
-public boolean equals(Object obj) {
- if (!(obj instanceof CommandEnvironment)) {
- return (false);
- }
- CommandEnvironment that = (CommandEnvironment)obj;
-
- if (!this.cmdpath.equals(that.cmdpath)) {
- return (false);
- }
-
- int len = this.argv.length;
- if (len != that.argv.length) {
- return (false);
- }
- for (int i = 0; i < len; i++) {
- if (!this.argv[i].equals(that.argv[i])) {
- return (false);
- }
- }
- return (true);
-}
+ if (command == null || that.command == null)
+ {
+ // Use direct comparison if null is involved.
+ if (command != that.command)
+ return false;
+ }
+ else
+ {
+ // Use .equals if null is not involved.
+ if (! this.command.equals(that.command))
+ return false;
+ }
-public int hashCode() {
- return (cmdpath.hashCode()); // Not a very good hash code.
-}
+ return Arrays.equals(options, that.options);
+ }
+ else
+ return false;
+ }
-}
+ /**
+ * Get the hash code.
+ */
+ public int hashCode()
+ {
+ int h = command == null ? 0 : command.hashCode();
+ for (int i = 0; i < options.length; i++)
+ h ^= options[i].hashCode();
-public ActivationGroupDesc(Properties overrides, ActivationGroupDesc.CommandEnvironment cmd) {
- throw new Error("Not implemented");
-}
+ return h;
+ }
+ }
+
+ /**
+ * Use the SVUID for interoperability.
+ */
+ static final long serialVersionUID = - 4936225423168276595L;
+
+ /**
+ * The group class name or null for the default group class implementation.
+ */
+ final String className;
+
+ /**
+ * The group class download location URL (codebase), ignored by the
+ * default implementation.
+ */
+ final String location;
+
+ /**
+ * The group initialization data.
+ */
+ final MarshalledObject data;
+
+ /**
+ * The path to the group jre and the parameters of this jre, may be
+ * null for the default jre.
+ */
+ final ActivationGroupDesc.CommandEnvironment env;
+
+ /**
+ * The properties that override the system properties.
+ */
+ final Properties props;
+
+ /**
+ * The cached hash code.
+ */
+ transient long hash;
+
+ /**
+ * Create the new activation group descriptor that will use the default
+ * activation group implementation with the given properties and
+ * environment.
+ *
+ * @param aProperties the properties that override the system properties
+ * @param environment the command line (and parameters), indicating, where to
+ * find the jre executable and with that parameters to call it. May
+ * be null if the default executable should be used. In this case,
+ * the activation group with the null name (the system default group)
+ * will be created.
+ */
+ public ActivationGroupDesc(Properties aProperties,
+ ActivationGroupDesc.CommandEnvironment environment)
+ {
+ this(DefaultActivationGroup.class.getName(), null, null, aProperties,
+ environment);
+ }
+
+ /**
+ * Create the new activation group descriptor.
+ *
+ * @param aClassName the name of the group implementation class. The null
+ * value indicates the default implementation.
+ * @param aLocation the location, from where the group implementation class
+ * should be loaded (ignored for the system default implementation).
+ * @param aData the group intialization data
+ * @param aProperties the properties that will override the system properties
+ * of the new group. These properties will be translated into -D
+ * options.
+ * @param environment the record, containing path to the jre executable and
+ * start options for the jre or null for using the default jre and
+ * options.
+ */
+ public ActivationGroupDesc(String aClassName, String aLocation,
+ MarshalledObject aData, Properties aProperties,
+ ActivationGroupDesc.CommandEnvironment environment)
+ {
+ className = aClassName;
+ location = aLocation;
+ data = aData;
+ props = aProperties;
+ env = environment;
+ }
+
+ /**
+ * Get the activation group class name.
+ *
+ * @return the activation group class name (null for default implementation)
+ */
+ public String getClassName()
+ {
+ return className;
+ }
+
+ /**
+ * Get the location, from where the group class will be loaded
+ *
+ * @return the location, from where the implementation should be loaded (null
+ * for the default implementation)
+ */
+ public String getLocation()
+ {
+ return location;
+ }
+
+ /**
+ * Get the group intialization data.
+ *
+ * @return the group intialization data in the marshalled form.
+ */
+ public MarshalledObject getData()
+ {
+ return data;
+ }
-public ActivationGroupDesc(String className, String location, MarshalledObject data, Properties overrides, ActivationGroupDesc.CommandEnvironment cmd) {
- throw new Error("Not implemented");
-}
+ /**
+ * Get the overridded system properties.
+ *
+ * @return the overridden group system properties.
+ */
+ public Properties getPropertyOverrides()
+ {
+ return props;
+ }
+
+ /**
+ * Get the group command environment, containing path to the jre executable
+ * and startup options.
+ *
+ * @return the command environment or null if the default environment should
+ * be used.
+ */
+ public ActivationGroupDesc.CommandEnvironment getCommandEnvironment()
+ {
+ return env;
+ }
+
+ /**
+ * Compare for the content equality.
+ */
+ public boolean equals(Object obj)
+ {
+ if (obj instanceof ActivationGroupDesc)
+ {
+ ActivationGroupDesc that = (ActivationGroupDesc) obj;
-public String getClassName() {
- throw new Error("Not implemented");
-}
+ // Ensure the hashcodes are computed.
+ if (hash == 0)
+ hashCode();
+ if (that.hash == 0)
+ that.hashCode();
-public String getLocation() {
- throw new Error("Not implemented");
-}
+ // We compare the hash fields as they are type long rather than int.
+ if (hash != that.hash)
+ return false;
-public MarshalledObject getData() {
- throw new Error("Not implemented");
-}
+ if (! eq(className, that.className))
+ return false;
+ if (! eq(data, that.data))
+ return false;
+ if (! eq(env, that.env))
+ return false;
+ if (! eq(location, that.location))
+ return false;
-public Properties getPropertyOverrides() {
- throw new Error("Not implemented");
-}
+ // Compare the properties.
+ if (eq(props, that.props))
+ return true;
-public ActivationGroupDesc.CommandEnvironment getCommandEnvironment() {
- throw new Error("Not implemented");
-}
+ if (props.size() != that.props.size())
+ return false;
-public boolean equals(Object obj) {
- throw new Error("Not implemented");
-}
+ Enumeration en = props.propertyNames();
+ Object key, value;
-public int hashCode() {
- throw new Error("Not implemented");
-}
+ while (en.hasMoreElements())
+ {
+ key = en.nextElement();
+ if (! that.props.containsKey(key))
+ return false;
+ if (! eq(props.get(key), that.props.get(key)))
+ return false;
+ }
+ return true;
+ }
+ else
+ return false;
+ }
+
+ /**
+ * Compare for direct equality if one or both parameters are null, otherwise
+ * call .equals.
+ */
+ static boolean eq(Object a, Object b)
+ {
+ if (a == null || b == null)
+ return a == b;
+ else
+ return a.equals(b);
+ }
+
+ /**
+ * Return the hashcode.
+ */
+ public int hashCode()
+ {
+ if (hash==0)
+ {
+ // Using Adler32 - the hashcode is cached, will be computed only
+ // once and due need to scan properties is the expensive operation
+ // anyway. Reliability is more important.
+ Adler32 adler = new Adler32();
+ if (className!=null)
+ adler.update(className.getBytes());
+ if (data!=null)
+ adler.update(data.hashCode());
+ if (env!=null)
+ adler.update(env.hashCode());
+ if (location!=null)
+ adler.update(location.getBytes());
+ if (props!=null)
+ {
+ Enumeration en = props.propertyNames();
+
+ // Using the intermediate sorted set to ensure that the
+ // properties are sorted.
+ TreeSet pr = new TreeSet();
+
+ Object key;
+ Object value;
+ while (en.hasMoreElements())
+ {
+ key = en.nextElement();
+ if (key!=null)
+ pr.add(key);
+ }
+
+ Iterator it = pr.iterator();
+ while (it.hasNext())
+ {
+ key = it.next();
+ value = props.get(key);
+ adler.update(key.hashCode());
+ if (value!=null)
+ adler.update(value.hashCode());
+ }
+ }
+ hash = adler.getValue();
+ }
+ return (int) hash;
+ }
}
diff --git a/libjava/classpath/java/rmi/activation/ActivationGroupID.java b/libjava/classpath/java/rmi/activation/ActivationGroupID.java
index 5e0b96442e8..e54b2a05d8d 100644
--- a/libjava/classpath/java/rmi/activation/ActivationGroupID.java
+++ b/libjava/classpath/java/rmi/activation/ActivationGroupID.java
@@ -1,5 +1,5 @@
/* ActivationGroupID.java --
- Copyright (c) 1996, 1997, 1998, 1999 Free Software Foundation, Inc.
+ Copyright (c) 1996, 1997, 1998, 1999, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -35,36 +35,88 @@ this exception to your version of the library, but you are not
obligated to do so. If you do not wish to do so, delete this
exception statement from your version. */
+
package java.rmi.activation;
import java.io.Serializable;
+import java.rmi.server.UID;
-public class ActivationGroupID implements Serializable
+/**
+ * This identifier identifies the activation group inside the scope of its
+ * activation system. It also contains (and can provide) the reference to the
+ * groups activation system.
+ *
+ * @see ActivationSystem#registerGroup(ActivationGroupDesc)
+ */
+public class ActivationGroupID
+ implements Serializable
{
- static final long serialVersionUID = -1648432278909740833L;
+ /**
+ * Use SVUID for interoperability.
+ */
+ static final long serialVersionUID = - 1648432278909740833L;
-private ActivationSystem system;
+ /**
+ * The associated activation system.
+ */
+ final ActivationSystem system;
+
+ /**
+ * The object identifier, making the ID unique.
+ */
+ final UID uid;
-public ActivationGroupID(ActivationSystem system) {
- this.system = system;
-}
+ /**
+ * Create the new activation group id in the scope of the given activation
+ * system
+ *
+ * @param aSystem the activation system
+ */
+ public ActivationGroupID(ActivationSystem aSystem)
+ {
+ system = aSystem;
+ uid = new UID();
+ }
-public ActivationSystem getSystem() {
- return (system);
-}
+ /**
+ * Get the associated activation system
+ *
+ * @return the associated activation system
+ */
+ public ActivationSystem getSystem()
+ {
+ return system;
+ }
-public int hashCode() {
- return (system.hashCode());
-}
+ /**
+ * Get the hash code of the associated activation system.
+ */
+ public int hashCode()
+ {
+ return uid.hashCode();
+ }
-public boolean equals(Object obj) {
- if (obj instanceof ActivationGroupID) {
- ActivationGroupID that = (ActivationGroupID)obj;
- if (this.system.equals(that.system)) {
- return (true);
- }
- }
- return (false);
-}
+ /**
+ * Copmare for equality, returns true if the passed object is also the
+ * activation group id and its activation system is the same.
+ */
+ public boolean equals(Object obj)
+ {
+ if (obj instanceof ActivationGroupID)
+ {
+ ActivationGroupID that = (ActivationGroupID) obj;
+ return uid.equals(that.uid);
+ }
+ else
+ return false;
+ }
+
+ /**
+ * Get the string representation
+ */
+ public String toString()
+ {
+ return uid.toString();
+ }
}
diff --git a/libjava/classpath/java/rmi/activation/ActivationGroup_Stub.java b/libjava/classpath/java/rmi/activation/ActivationGroup_Stub.java
index 249137b0863..fb55e5fd95f 100644
--- a/libjava/classpath/java/rmi/activation/ActivationGroup_Stub.java
+++ b/libjava/classpath/java/rmi/activation/ActivationGroup_Stub.java
@@ -51,7 +51,7 @@ import java.rmi.server.RemoteStub;
*
* @author Roman Kennke (kennke@aicas.com)
*/
-public class ActivationGroup_Stub extends RemoteStub
+public final class ActivationGroup_Stub extends RemoteStub
implements ActivationInstantiator, Remote
{
private static final long serialVersionUID = 2L;
diff --git a/libjava/classpath/java/rmi/activation/ActivationID.java b/libjava/classpath/java/rmi/activation/ActivationID.java
index 23ed853a478..c4bbcd285c5 100644
--- a/libjava/classpath/java/rmi/activation/ActivationID.java
+++ b/libjava/classpath/java/rmi/activation/ActivationID.java
@@ -1,5 +1,5 @@
-/* ActivationID.java --
- Copyright (c) 1996, 1997, 1998, 1999 Free Software Foundation, Inc.
+/* ActivationID.java -- the object activation identifier
+ Copyright (c) 1996, 1997, 1998, 1999, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -35,38 +35,165 @@ this exception to your version of the library, but you are not
obligated to do so. If you do not wish to do so, delete this
exception statement from your version. */
+
package java.rmi.activation;
+import java.io.IOException;
+import java.io.ObjectInputStream;
+import java.io.ObjectOutputStream;
import java.io.Serializable;
import java.rmi.Remote;
import java.rmi.RemoteException;
+import java.rmi.server.UID;
-public class ActivationID implements Serializable
+/**
+ * Denotes the object that can be activated over time. The instance of the
+ * ActivationID for the given object can be obtained in the following ways:
+ * <ul>
+ * <li>via {@link Activatable#register(ActivationDesc)}</li>
+ * <li>via Activatable constructor</li>
+ * <li>via Activatable.exportObject
+ * <li>
+ * </ul>
+ * An instance of the ActivationID has the {@link UID} as its component and
+ * hence is globally unique.
+ *
+ * @author Audrius Meskauskas (audriusa@bioinformatics.org) (from stub)
+ */
+public class ActivationID
+ implements Serializable
{
- static final long serialVersionUID = -4608673054848209235L;
-
-private Activator activator;
-
-public ActivationID(Activator activator) {
- this.activator = activator;
-}
+ /**
+ * Use SVUID for interoperability.
+ */
+ static final long serialVersionUID = - 4608673054848209235L;
-public Remote activate(boolean force) throws ActivationException, UnknownObjectException, RemoteException {
- throw new Error("Not implemented");
-}
-
-public int hashCode() {
- return (activator.hashCode());
-}
+ /**
+ * The activator.
+ */
+ transient Activator activator;
+
+ /**
+ * The UID, making this instance unique.
+ */
+ transient UID uid;
+
+ /**
+ * The activation group that has activated the object with this
+ * activation id. The field is filled in inside the group and is used
+ * to notify the group about the request to inactivated the object.
+ */
+ transient ActivationGroup group;
-public boolean equals(Object obj) {
- if (obj instanceof ActivationID) {
- ActivationID that = (ActivationID)obj;
- if (this.activator.equals(that.activator)) {
- return (true);
- }
- }
- return (false);
-}
+ /**
+ * Create a new instance with the given activator.
+ *
+ * @param an_activator tha activator that should activate the object.
+ */
+ public ActivationID(Activator an_activator)
+ {
+ activator = an_activator;
+ uid = new UID();
+ }
+
+ /**
+ * Activate the object.
+ *
+ * @param force if true, always contact the group. Otherwise, the cached value
+ * may be returned.
+ * @return the activated object
+ * @throws UnknownObjectException if the object is unknown
+ * @throws ActivationException if the activation has failed
+ * @throws RemoteException if the remote call has failed
+ */
+ public Remote activate(boolean force) throws ActivationException,
+ UnknownObjectException, RemoteException
+ {
+ try
+ {
+ return (Remote) activator.activate(this, force).get();
+ }
+ catch (IOException e)
+ {
+ ActivationException acex = new ActivationException("id "+uid, e);
+ throw acex;
+ }
+ catch (ClassNotFoundException e)
+ {
+ ActivationException acex = new ActivationException("id "+uid, e);
+ throw acex;
+ }
+ }
+
+ /**
+ * Returns the hash code of the activator.
+ */
+ public int hashCode()
+ {
+ return uid == null ? 0 : uid.hashCode();
+ }
+
+ /**
+ * Compares the activators for equality.
+ */
+ public boolean equals(Object obj)
+ {
+ if (obj instanceof ActivationID)
+ {
+ ActivationID that = (ActivationID) obj;
+ return eq(uid, that.uid);
+ }
+ else
+ return false;
+ }
+
+ /**
+ * Read the object from the input stream.
+ *
+ * @param in the stream to read from
+ *
+ * @throws IOException if thrown by the stream
+ * @throws ClassNotFoundException
+ */
+ private void readObject(ObjectInputStream in) throws IOException,
+ ClassNotFoundException
+ {
+ uid = (UID) in.readObject();
+ activator = (Activator) in.readObject();
+ }
+
+ /**
+ * Write the object to the output stream.
+ *
+ * @param out the stream to write int
+ * @throws IOException if thrown by the stream
+ * @throws ClassNotFoundException
+ */
+ private void writeObject(ObjectOutputStream out) throws IOException,
+ ClassNotFoundException
+ {
+ out.writeObject(uid);
+ out.writeObject(activator);
+ };
+
+ /**
+ * Compare by .equals if both a and b are not null, compare directly if at
+ * least one of them is null.
+ */
+ static final boolean eq(Object a, Object b)
+ {
+ if (a == null || b == null)
+ return a == b;
+ else
+ return a.equals(b);
+ }
+ /**
+ * Return the content based string representation.
+ */
+ public String toString()
+ {
+ return uid.toString();
+ }
+
}
diff --git a/libjava/classpath/java/rmi/activation/ActivationInstantiator.java b/libjava/classpath/java/rmi/activation/ActivationInstantiator.java
index 0aceb7a4ad6..a0f04ed36cd 100644
--- a/libjava/classpath/java/rmi/activation/ActivationInstantiator.java
+++ b/libjava/classpath/java/rmi/activation/ActivationInstantiator.java
@@ -42,9 +42,32 @@ import java.rmi.MarshalledObject;
import java.rmi.Remote;
import java.rmi.RemoteException;
+/**
+ * The implementation of this interface creates (instantiates) the new remote
+ * objects in response to the activation request. The instantiator is returned
+ * by the {@link ActivationGroup} that calls
+ * {@link ActivationSystem#activeGroup(ActivationGroupID, ActivationInstantiator, long)}.
+ */
public interface ActivationInstantiator
extends Remote
{
+ /**
+ * Creates and instantiate a new remote object. This method performs the
+ * following tasks:
+ * <ul>
+ * <li>Finds and loads (if not already loaded) the class of the object being
+ * instantiated</li>
+ * <li>Creates an instance of the object using its special two parameter
+ * activation constructor, the first parameter being the {@link ActivationID}
+ * and the second the {@link MarshalledObject}.</li>
+ *
+ * @param id the id of the object being instantiated
+ * @param desc the activation descriptor being instantiated
+ * @return the MarshalledObject, containing the stub to the newly created
+ * object.
+ * @throws ActivationException if the activation fails
+ * @throws RemoteException if the remote call fails
+ */
MarshalledObject newInstance (ActivationID id, ActivationDesc desc)
throws ActivationException, RemoteException;
}
diff --git a/libjava/classpath/java/rmi/activation/ActivationMonitor.java b/libjava/classpath/java/rmi/activation/ActivationMonitor.java
index 1e64257edd1..e9f43ae1a94 100644
--- a/libjava/classpath/java/rmi/activation/ActivationMonitor.java
+++ b/libjava/classpath/java/rmi/activation/ActivationMonitor.java
@@ -1,5 +1,6 @@
-/* ActivationMonitor.java --
- Copyright (c) 1996, 1997, 1998, 1999, 2004 Free Software Foundation, Inc.
+/* ActivationMonitor.java -- the RMI activation/inactivation event listener
+ Copyright (c) 1996, 1997, 1998, 1999, 2004, 2006
+ Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -42,14 +43,45 @@ import java.rmi.MarshalledObject;
import java.rmi.Remote;
import java.rmi.RemoteException;
+/**
+ * The activation and inactivation event listener. The group obtains this
+ * listener via {@link ActivationSystem#activeGroup} and must notify it
+ * when the group objects are activated or inactivated and also when the
+ * whole group becomes inactive.
+ * @author root.
+ */
public interface ActivationMonitor extends Remote
{
- void inactiveObject (ActivationID id)
+ /**
+ * Informs that the object is now active.
+ *
+ * @param id the activation id of the object that is now active
+ * @throws UnknownObjectException is such object is not known in this group
+ * @throws RemoteException if remote call fails
+ */
+ void activeObject (ActivationID id, MarshalledObject obj)
throws UnknownObjectException, RemoteException;
- void activeObject (ActivationID id, MarshalledObject obj)
+ /**
+ * Informs that the object is not inactive.
+ *
+ * @param id the activation id of the object that is now inactive
+ * @throws UnknownObjectException is such object is not known in this group
+ * @throws RemoteException if remote call fails
+ */
+ void inactiveObject (ActivationID id)
throws UnknownObjectException, RemoteException;
- void inactiveGroup (ActivationGroupID id, long incarnation)
+ /**
+ * Informs that the whole group is now inactive because all group objects are
+ * inactive. The group will be recreated upon the later request to activate
+ * any object, belonging to the group.
+ *
+ * @param groupId the group id
+ * @param incarnation the group incarnation number
+ * @throws UnknownGroupException if the group id is not known
+ * @throws RemoteException if the remote call fails
+ */
+ void inactiveGroup (ActivationGroupID groupId, long incarnation)
throws UnknownGroupException, RemoteException;
}
diff --git a/libjava/classpath/java/rmi/activation/ActivationSystem.java b/libjava/classpath/java/rmi/activation/ActivationSystem.java
index 4b92d40cb44..719676445f8 100644
--- a/libjava/classpath/java/rmi/activation/ActivationSystem.java
+++ b/libjava/classpath/java/rmi/activation/ActivationSystem.java
@@ -1,5 +1,6 @@
-/* ActivationSystem.java --
- Copyright (c) 1996, 1997, 1998, 1999, 2004 Free Software Foundation, Inc.
+/* ActivationSystem.java -- registers groups and objects to be activated.
+ Copyright (c) 1996, 1997, 1998, 1999, 2004, 2006
+ Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -41,38 +42,165 @@ package java.rmi.activation;
import java.rmi.Remote;
import java.rmi.RemoteException;
-public interface ActivationSystem extends Remote
+/**
+ * <p>
+ * The ActivationSystem registers groups and activatable objects to be activated
+ * within those groups. The ActivationSystem cooperates with both the Activator,
+ * which activates objects registered via the ActivationSystem, and the
+ * ActivationMonitor, which obtains information about active and inactive
+ * objects and inactive groups.
+ * </p>
+ * <p>
+ * The activation system if frequently a remote object. As a security mean, all
+ * methods in this interface throw {@link java.rmi.AccessException} if called
+ * from the client that is not reside on the same host as the activation system.
+ * </p>
+ * @see ActivationGroup#getSystem()
+ */
+public interface ActivationSystem
+ extends Remote
{
+ /**
+ * The port, used by the activation system. The value is equal to 1098 by
+ * default, but it can be changed by putting the system property
+ * .
+ */
int SYSTEM_PORT = 1098;
-
- ActivationID registerObject (ActivationDesc desc)
- throws ActivationException, UnknownGroupException, RemoteException;
-
- void unregisterObject (ActivationID id)
- throws ActivationException, UnknownObjectException, RemoteException;
-
- ActivationGroupID registerGroup (ActivationGroupDesc desc)
- throws ActivationException, RemoteException;
-
- ActivationMonitor activeGroup (ActivationGroupID id,
- ActivationInstantiator group, long incarnation)
- throws UnknownGroupException, ActivationException, RemoteException;
-
- void unregisterGroup (ActivationGroupID id)
- throws ActivationException, UnknownGroupException, RemoteException;
-
- void shutdown()
- throws RemoteException;
-
- ActivationDesc setActivationDesc (ActivationID id, ActivationDesc desc)
- throws ActivationException, UnknownObjectException, UnknownGroupException,
- RemoteException;
-
- ActivationGroupDesc setActivationGroupDesc (ActivationGroupID id,
- ActivationGroupDesc desc)
- throws ActivationException, UnknownGroupException, RemoteException;
-
- ActivationDesc getActivationDesc (ActivationID id) throws ActivationException, UnknownObjectException, RemoteException;
-
- ActivationGroupDesc getActivationGroupDesc (ActivationGroupID id) throws ActivationException, UnknownGroupException, RemoteException;
+
+ /**
+ * Registers the activation descriptor and creates (and returns) its
+ * activation identifier. The map entry (identifier to descriptor) is stored
+ * in the stable map and used when the {@link Activator} receives the request
+ * to activate the object.
+ *
+ * @param desc the activation descriptor to register.
+ * @return the created activation identifier that is mapped to the passed
+ * descriptor.
+ * @throws ActivationException if the registration fails (database update
+ * problems, etc).
+ * @throws UnknownGroupException the if group, specified in decriptor, is
+ * unknown.
+ * @throws RemoteException if the remote call fails.
+ */
+ ActivationID registerObject(ActivationDesc desc) throws ActivationException,
+ UnknownGroupException, RemoteException;
+
+ /**
+ * Removes the stored identifier-description map entry. The object will no
+ * longer be activable using the passed activation id
+ *
+ * @param id the activation id to remove
+ * @throws ActivationException if the entry removing operation failed
+ * (database update problems, etc)
+ * @throws UnknownObjectException if the passed id is not known to the system
+ * @throws RemoteException if the remote call fails
+ */
+ void unregisterObject(ActivationID id) throws ActivationException,
+ UnknownObjectException, RemoteException;
+
+ /**
+ * Register the new activation group. For instance, it can be one activation
+ * group per virtual machine.
+ *
+ * @param groupDesc the activation group descriptor.
+ * @return the created activation group ID for the activation group
+ * @throws ActivationException if the group registration fails
+ * @throws RemoteException if the remote call fails
+ */
+ ActivationGroupID registerGroup(ActivationGroupDesc groupDesc)
+ throws ActivationException, RemoteException;
+
+ /**
+ * This method is called from the {@link ActivationGroup} to inform the
+ * ActivatinSystem that the group is now active and there is the
+ * {@link ActivationInstantiator} for that group. This call is made internally
+ * from the {@link ActivationGroup#createGroup}.
+ *
+ * @param id the group id
+ * @param group the group activation instantiator
+ * @param incarnation the groups incarnatin number.
+ * @return the activation monitor that should be informed about the group
+ * state changes
+ * @throws UnknownGroupException if this group has not been registered
+ * @throws ActivationException if this group is already active
+ * @throws RemoteException if the remote call fails
+ */
+ ActivationMonitor activeGroup(ActivationGroupID id,
+ ActivationInstantiator group, long incarnation)
+ throws UnknownGroupException, ActivationException, RemoteException;
+
+ /**
+ * Removes the activation group with the given identifier. The group calls
+ * back, informing the activator about the shutdown.
+ *
+ * @param id the group activation id.
+ * @throws ActivationException if the database update fails
+ * @throws UnknownGroupException if such group is not registered
+ * @throws RemoteException if the remote call fails
+ */
+ void unregisterGroup(ActivationGroupID id) throws ActivationException,
+ UnknownGroupException, RemoteException;
+
+ /**
+ * Shutdown the activation system and all associated activation groups
+ *
+ * @throws RemoteException if the remote call fails
+ */
+ void shutdown() throws RemoteException;
+
+ /**
+ * Replace the activation descriptor for the object with the given activation
+ * id.
+ *
+ * @param id the activation id
+ * @param desc the new activation descriptor
+ * @return the previous activation descriptor for that object.
+ * @throws ActivationException if the database update fails
+ * @throws UnknownObjectException if the object with such id is not known
+ * @throws UnknownGroupException if the activation group (in desc) is not
+ * known.
+ * @throws RemoteException if the remote call fails
+ */
+ ActivationDesc setActivationDesc(ActivationID id, ActivationDesc desc)
+ throws ActivationException, UnknownObjectException,
+ UnknownGroupException, RemoteException;
+
+ /**
+ * Replaces the group descriptor for the group with the given group activation
+ * id.
+ *
+ * @param groupId the group id
+ * @param groupDesc the new group descriptor
+ * @return the previous group descriptor
+ * @throws ActivationException if the database update fails
+ * @throws UnknownGroupException if such group is not known
+ * @throws RemoteException if the remote call fails
+ */
+ ActivationGroupDesc setActivationGroupDesc(ActivationGroupID groupId,
+ ActivationGroupDesc groupDesc)
+ throws ActivationException, UnknownGroupException, RemoteException;
+
+ /**
+ * Get the activation descriptor for the object with the given activation id.
+ *
+ * @param id the object activation id
+ * @return the activation descriptor for that object
+ * @throws ActivationException if the database access fails
+ * @throws UnknownObjectException if this object is not known
+ * @throws RemoteException if the remote call fails
+ */
+ ActivationDesc getActivationDesc(ActivationID id) throws ActivationException,
+ UnknownObjectException, RemoteException;
+
+ /**
+ * Get the group descriptor for the group with the given id.
+ *
+ * @param groupId the group id
+ * @return the group descriptor
+ * @throws ActivationException if the database access fails
+ * @throws UnknownGroupException if the group with such id is not known
+ * @throws RemoteException if the remote call fails
+ */
+ ActivationGroupDesc getActivationGroupDesc(ActivationGroupID groupId)
+ throws ActivationException, UnknownGroupException, RemoteException;
}
diff --git a/libjava/classpath/java/rmi/activation/Activator.java b/libjava/classpath/java/rmi/activation/Activator.java
index 2fb5a581002..57a4d16a723 100644
--- a/libjava/classpath/java/rmi/activation/Activator.java
+++ b/libjava/classpath/java/rmi/activation/Activator.java
@@ -42,9 +42,31 @@ import java.rmi.MarshalledObject;
import java.rmi.Remote;
import java.rmi.RemoteException;
+/**
+ * Activates remote object, providing the live reference to the activable remote
+ * object. Usually there is only one activator per host.
+ *
+ * @see ActivationSystem
+ * @see ActivationMonitor
+ */
public interface Activator
extends Remote
{
+ /**
+ * Activate the object, associated with the given activation identifier. The
+ * activator looks for the {@link ActivationDesc}riptor for the passed
+ * identifier, determines the object activation group and initiates object
+ * recreation either via {@link ActivationInstantiator} or via
+ * {@link Class#newInstance()}.
+ *
+ * @param id the identifier of the object to activate.
+ * @param force if true, the activator always contacts the group to obtain the
+ * reference. If false, it may return the cached value.
+ * @return the activated remote object (its stub).
+ * @throws UnknownObjectException if the object with this id is unknown
+ * @throws ActivationException if the activation has failed due other reason
+ * @throws RemoteException if the remote call has failed.
+ */
MarshalledObject activate (ActivationID id, boolean force)
throws ActivationException, UnknownObjectException, RemoteException;
}
diff --git a/libjava/classpath/java/rmi/activation/package.html b/libjava/classpath/java/rmi/activation/package.html
index 444782dd721..9df518fede2 100644
--- a/libjava/classpath/java/rmi/activation/package.html
+++ b/libjava/classpath/java/rmi/activation/package.html
@@ -1,6 +1,6 @@
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 3.2 Final//EN">
<!-- package.html - describes classes in java.rmi.activation package.
- Copyright (C) 2002 Free Software Foundation, Inc.
+ Copyright (C) 2002, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -40,7 +40,34 @@ exception statement from your version. -->
<head><title>GNU Classpath - java.rmi.activation</title></head>
<body>
-<p></p>
-
+In the previous Classpath releases, an instance of a UnicastRemoteObject
+could be accessed from a server that:
+<ul>
+<li>has created an instance of that object<li>
+<li>has been running <i>all<i> the time</li>
+</ul>
+<p>The the activation system allows to activate and execute the object
+implementation on demand rather than running all time. If the activation
+system is persistent, the server can be terminated and then restarted.
+The clients, still holding remote references to the server side
+activatable objects, will activate those objects again. The server side
+objects will be reinstantiated (activated) during the first call of any
+remote method of such object.
+</p><p>
+The RMI client code for activatable objects is no different than the code for
+accessing non-activatable remote objects. Activation is a server-side feature.
+</p><p>
+In order for an object to be activated, the "activatable" object class
+(independently if it extends the {@link Activatable} class or not) defines a
+special public constructor that takes two arguments, its activation identifier
+({@link ActivationID}) and its activation data ({@link java.rmi.MarshalledObject}),
+supplied in the activation descriptor used during registration. When an
+activation group activates a remote object, it constructs the object via
+this special constructor. The remote object implementation may use the
+activation data to initialize itself in a needed manner. The remote object may
+also retain its activation identifier, so that it can inform the activation
+group when it becomes inactive (via a call to the Activatable.inactive method).
+</p>
+@author Audrius Meskauskas (audriusa@bioinformatics.org) (from empty)
</body>
</html>
diff --git a/libjava/classpath/java/rmi/dgc/VMID.java b/libjava/classpath/java/rmi/dgc/VMID.java
index f960d9ccd79..dc989c265d8 100644
--- a/libjava/classpath/java/rmi/dgc/VMID.java
+++ b/libjava/classpath/java/rmi/dgc/VMID.java
@@ -1,5 +1,5 @@
-/* VMID.java
- Copyright (c) 1996, 1997, 1998, 1999 Free Software Foundation, Inc.
+/* VMID.java -- The object ID, unique between all virtual machines.
+ Copyright (c) 1996, 1997, 1998, 1999, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -41,37 +41,72 @@ import java.io.Serializable;
import java.net.InetAddress;
import java.net.UnknownHostException;
import java.rmi.server.UID;
-
+import java.util.Arrays;
+
+/**
+ * An identifier that is unique accross the all virtual machines. This class is
+ * used by distributed garbage collector to identify the virtual machine of
+ * the client, but may also be used in various other cases, when such identifier
+ * is required. This class separately stores and transfers the host IP
+ * address, but will try to do its best also for the case if it failed to
+ * determine it. The alternative algorithms are used in {@link UID} that is
+ * part of this class. The VMID's, created on the same host, but in the two
+ * separately (parallely) running virtual machines are different.
+ */
public final class VMID implements Serializable
{
+ /**
+ * Use SVUID for interoperability.
+ */
static final long serialVersionUID = -538642295484486218L;
- static final boolean areWeUnique;
+ /**
+ * If true, the IP of this host can ve reliably determined.
+ */
+ static boolean areWeUnique;
+ /**
+ * The IP address of the local host.
+ */
static byte[] localAddr;
+ /**
+ * The IP address of the local host.
+ */
private byte[] addr;
+ /**
+ * The cached hash code.
+ */
+ transient int hash;
+
+ /**
+ * The UID of this VMID.
+ */
private UID uid;
static
- {
- byte[] addr;
- boolean awu = true;
- try {
- addr = InetAddress.getLocalHost().getAddress();
- if (addr[0] == 127 && addr[1] == 0 && addr[2] == 0 && addr[3] == 1) {
- awu = false;
- }
- }
- catch (UnknownHostException _) {
- addr = new byte[]{ 127, 0, 0, 1 };
- awu = false;
+ {
+ // This "local host" value usually indicates that the local
+ // IP address cannot be reliably determined.
+ byte[] localHost = new byte[] { 127, 0, 0, 1 };
+
+ try
+ {
+ localAddr = InetAddress.getLocalHost().getAddress();
+ areWeUnique = !Arrays.equals(localHost, localAddr);
+ }
+ catch (UnknownHostException uhex)
+ {
+ localAddr = localHost;
+ areWeUnique = false;
+ }
}
- localAddr = addr;
- areWeUnique = awu;
- }
-
+
+ /**
+ * Create the new VMID. All VMID's are unique accross tha all virtual
+ * machines.
+ */
public VMID()
{
addr = localAddr;
@@ -79,42 +114,58 @@ public final class VMID implements Serializable
}
/**
- * @deprecated
+ * Return true if it is possible to get the accurate address of this host.
+ * If false is returned, the created VMID's are less reliable, but the
+ * starting time and possibly the memory allocation are also taken into
+ * consideration in the incorporated UID. Hence the VMID's, created on the
+ * different virtual machines, still should be different.
+ *
+ * @deprecated VMID's are more or less always reliable.
+ *
+ * @return false if the local host ip address is 127.0.0.1 or unknown,
+ * true otherwise.
*/
public static boolean isUnique ()
{
return areWeUnique;
}
-
+
+ /**
+ * Get the hash code of this VMID.
+ */
public int hashCode ()
{
- return super.hashCode();
- }
-
- public boolean equals (Object obj)
- {
- if (!(obj instanceof VMID))
- {
- return false;
- }
-
- VMID other = (VMID) obj;
- if (addr.length != other.addr.length)
+ if (hash==0)
{
- return false;
+ for (int i = 0; i < localAddr.length; i++)
+ hash += addr[i];
+ hash = hash ^ uid.hashCode();
}
-
- for (int i = addr.length - 1; i >= 0; i--)
+ return hash;
+ }
+
+ /**
+ * Returns true if the passed parameter is also VMID and it is equal to this
+ * VMID. The VMID should only be equal to itself (also if the passed value is
+ * another instance, cloned by serialization).
+ */
+ public boolean equals(Object obj)
+ {
+ if (obj instanceof VMID)
{
- if (addr[i] != other.addr[i])
- {
- return false;
- }
+ VMID other = (VMID) obj;
+
+ // The UID's are compared faster than arrays.
+ return uid.equals(other.uid) && Arrays.equals(addr, other.addr);
}
-
- return uid.equals(other.uid);
- }
+ else
+ return false;
+ }
+
+ /**
+ * Get the string representation of this VMID.
+ */
public String toString ()
{
StringBuffer buf = new StringBuffer ("[VMID: ");
diff --git a/libjava/classpath/java/rmi/dgc/package.html b/libjava/classpath/java/rmi/dgc/package.html
index 9458d4c25f9..7f0a2081c72 100644
--- a/libjava/classpath/java/rmi/dgc/package.html
+++ b/libjava/classpath/java/rmi/dgc/package.html
@@ -1,6 +1,6 @@
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 3.2 Final//EN">
<!-- package.html - describes classes in java.rmi.dgc package.
- Copyright (C) 2002 Free Software Foundation, Inc.
+ Copyright (C) 2002, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -40,7 +40,13 @@ exception statement from your version. -->
<head><title>GNU Classpath - java.rmi.dgc</title></head>
<body>
-<p></p>
-
+The Distributed Garbage Collector (DGC). The DGC is reponsible for keeping all
+locally created and exported remote objects as long as they are referenced
+by some remote clients. The client must periodically notify the server that
+it still wants to keep the remote object on the server side. The client
+notifies the server by calling methods, defined in the DGC interface.
+Other classes in this package define the parameters that are used in this
+interface. The DGC object of some host can be found and accessed by its
+object identifier (ObjID.DGC_ID), without involving the name service.
</body>
</html>
diff --git a/libjava/classpath/java/rmi/server/ObjID.java b/libjava/classpath/java/rmi/server/ObjID.java
index 07cbbde3a62..1aaa223602c 100644
--- a/libjava/classpath/java/rmi/server/ObjID.java
+++ b/libjava/classpath/java/rmi/server/ObjID.java
@@ -1,5 +1,6 @@
-/* ObjID.java --
- Copyright (c) 1996, 1997, 1998, 1999, 2004 Free Software Foundation, Inc.
+/* ObjID.java -- Unique object id with respect to the given host.
+ Copyright (c) 1996, 1997, 1998, 1999, 2004, 2006
+ Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -45,59 +46,152 @@ import java.io.ObjectInput;
import java.io.ObjectOutput;
import java.io.Serializable;
-public final class ObjID implements Serializable
+/**
+ * Represents the object identifier, unique for the host that generated it.
+ * The ObjID contains inside the integer object identifier that, if needed,
+ * may indicated that this is a reference to one of the well known objects
+ * on that host (registry, activator or dgc) and the {@link UID} that
+ * ensures uniqueness.
+ */
+public final class ObjID
+ implements Serializable
{
-static final long serialVersionUID = -6386392263968365220L;
-private static long next = 0x8000000000000000L;
-private static final Object lock = ObjID.class;
-
-public static final int REGISTRY_ID = 0;
-public static final int ACTIVATOR_ID = 1;
-public static final int DGC_ID = 2;
-
-private long objNum;
-private UID space;
-
-public ObjID() {
- synchronized (lock) {
- objNum = next++;
- }
- space = new UID();
-}
-
-public ObjID(int num) {
- objNum = (long)num;
- space = new UID((short)0);
-}
-
-public void write(ObjectOutput out) throws IOException {
- DataOutput dout = (DataOutput)out;
- dout.writeLong(objNum);
- space.write(dout);
-}
-
-public static ObjID read(ObjectInput in) throws IOException {
- DataInput din = (DataInput)in;
- ObjID id = new ObjID();
- id.objNum = din.readLong();
- id.space = UID.read(din);
- return (id);
-}
-
-public int hashCode() {
- return ((int)objNum);
-}
-
-public boolean equals(Object obj) {
- if (obj instanceof ObjID && this.objNum == ((ObjID)obj).objNum) {
- return (true);
- }
- return (false);
-}
-
-public String toString() {
- return ("[objNum: " + objNum + ", " + space + "]");
-}
+ /**
+ * Use serial version uid for interoperability.
+ */
+ static final long serialVersionUID = - 6386392263968365220L;
+
+ /**
+ * The object counter, which value is assigned when creating the ordinary
+ * objects without the known object id. The counter is incremented each time
+ * the new ObjID is constructed.
+ */
+ private static long next = 0x8000000000000000L;
+
+ /**
+ * The object to put the lock on when incrementing {@link #next}
+ */
+ private static final Object lock = ObjID.class;
+
+ /**
+ * Defines the ID of the naming service.
+ */
+ public static final int REGISTRY_ID = 0;
+
+ /**
+ * Defines the ID of the activator.
+ */
+ public static final int ACTIVATOR_ID = 1;
+
+ /**
+ * Defines the ID of the distributed garbage collector.
+ */
+ public static final int DGC_ID = 2;
+
+ /**
+ * The object Id (either well-known value or the value of the incrementing
+ * object counter.
+ */
+ long objNum;
+
+ /**
+ * The object unique identifier, generated individually for each object.
+ */
+ UID space;
+
+ /**
+ * Create the new object id, unique for this host.
+ */
+ public ObjID()
+ {
+ synchronized (lock)
+ {
+ objNum = next++;
+ }
+ space = new UID();
+ }
+
+ /**
+ * Create the new object id defining the well known remotely accessible
+ * object, present in this host. The well - known objects are:
+ * <ul>
+ * <li>{@link #REGISTRY_ID} - RMI naming service.</li>
+ * <li>{@link #ACTIVATOR_ID} - activator</li>
+ * <li>{@link #DGC_ID} - distributed garbage collector (grants lease
+ * durations to keep the object before it is garbage collected.</li>
+ * </ul>
+ *
+ * @param id the well known object id, one of the above.
+ */
+ public ObjID(int id)
+ {
+ objNum = (long) id;
+ space = new UID((short) 0);
+ }
+
+ /**
+ * Write object id as long, then the object {@link UID}.
+ */
+ public void write(ObjectOutput out) throws IOException
+ {
+ DataOutput dout = (DataOutput) out;
+ dout.writeLong(objNum);
+ space.write(dout);
+ }
+
+ /**
+ * Read object id (as long), then the object {@link UID}.
+ */
+ public static ObjID read(ObjectInput in) throws IOException
+ {
+ DataInput din = (DataInput) in;
+ ObjID id = new ObjID();
+ id.objNum = din.readLong();
+ id.space = UID.read(din);
+ return (id);
+ }
+
+ /**
+ * Get the hashcode.
+ */
+ public int hashCode()
+ {
+ return space == null ? (int) objNum : space.hashCode() ^ (int) objNum;
+ }
+
+ /**
+ * Compare for equality.
+ */
+ public boolean equals(Object obj)
+ {
+ if (obj instanceof ObjID)
+ {
+ ObjID that = (ObjID) obj;
+ return that.objNum == objNum && eq(that.space, space);
+ }
+ else
+ return false;
+ }
+
+ /**
+ * Compare by .equals if both a and b are not null, compare directly if at
+ * least one of them is null.
+ */
+ static final boolean eq(Object a, Object b)
+ {
+ if (a == null || b == null)
+ return a == b;
+ else
+ return a.equals(b);
+ }
+
+ /**
+ * Get the string representation.
+ */
+ public String toString()
+ {
+ return (objNum + ":" + space);
+ }
}
diff --git a/libjava/classpath/java/rmi/server/Operation.java b/libjava/classpath/java/rmi/server/Operation.java
index 64faf66e2f8..f7b5f02cc0b 100644
--- a/libjava/classpath/java/rmi/server/Operation.java
+++ b/libjava/classpath/java/rmi/server/Operation.java
@@ -38,6 +38,9 @@ exception statement from your version. */
package java.rmi.server;
/**
+ * This class was used with jdk 1.1 stubs and skeletons. It is no longer
+ * needed since jdk 1.2 and higher.
+ *
* @deprecated
*/
public class Operation
@@ -45,6 +48,7 @@ public class Operation
private String operation;
/**
+ * Create operation with the given name.
* @deprecated
*/
public Operation (String op)
@@ -53,6 +57,8 @@ public class Operation
}
/**
+ * Get the name of the operation.
+ *
* @deprecated
*/
public String getOperation ()
@@ -61,6 +67,8 @@ public class Operation
}
/**
+ * Return the name of the operation.
+ *
* @deprecated
*/
public String toString ()
diff --git a/libjava/classpath/java/rmi/server/RemoteObject.java b/libjava/classpath/java/rmi/server/RemoteObject.java
index 60e57dc2428..5b926bfc34e 100644
--- a/libjava/classpath/java/rmi/server/RemoteObject.java
+++ b/libjava/classpath/java/rmi/server/RemoteObject.java
@@ -39,6 +39,7 @@ package java.rmi.server;
import java.io.IOException;
import java.io.ObjectInputStream;
+import java.io.ObjectOutput;
import java.io.ObjectOutputStream;
import java.io.Serializable;
import java.rmi.NoSuchObjectException;
@@ -101,6 +102,9 @@ public boolean equals(Object obj) {
return (this == obj);
}
+/**
+ * Get the string representation of this remote object.
+ */
public String toString()
{
if (ref == null)
@@ -108,55 +112,91 @@ public boolean equals(Object obj) {
return (ref.toString ());
}
- private void readObject(ObjectInputStream in) throws IOException, ClassNotFoundException
+ /**
+ * Read the remote object from the input stream. Expects the class name
+ * without package first. Then the method creates and assigns the {@link #ref}
+ * an instance of this class and calls its .readExternal method. The standard
+ * packageless class names are UnicastRef, UnicastRef2, UnicastServerRef,
+ * UnicastServerRef2, ActivatableRef or ActivatableServerRef.
+ *
+ * @param in the stream to read from
+ * @throws IOException if the IO exception occurs
+ * @throws ClassNotFoundException if the class with the given name is not
+ * present in the package gnu.java.rmi.server (for the case of the
+ * GNU Classpath.
+ */
+ private void readObject(ObjectInputStream in) throws IOException,
+ ClassNotFoundException
{
String cname = in.readUTF();
- if (!cname.equals(""))
+ if (! cname.equals(""))
{
- if (cname.equals ("UnicastRef2"))
- {
- // hack for interoperating with JDK
- cname = "UnicastRef";
- in.read (); //some unknown UnicastRef2 field
- }
-
- // It would be nice to use RemoteRef.packagePrefix here, but for binary
- // compatibility with the JDK that has to contain "sun.rmi.server"...
- cname = "gnu.java.rmi.server." + cname;
- try
- {
- Class cls = Class.forName(cname);
- ref = (RemoteRef)cls.newInstance();
- }
- catch (InstantiationException e1)
- {
- throw new UnmarshalException("failed to create ref", e1);
- }
- catch (IllegalAccessException e2)
- {
- throw new UnmarshalException("failed to create ref", e2);
- }
- ref.readExternal(in);
+ if (cname.equals("UnicastRef2"))
+ {
+ // hack for interoperating with JDK
+ cname = "UnicastRef";
+ in.read(); // some unknown UnicastRef2 field
+ }
+
+ // It would be nice to use RemoteRef.packagePrefix here, but for binary
+ // compatibility with the JDK that has to contain "sun.rmi.server"...
+ cname = "gnu.java.rmi.server." + cname;
+ try
+ {
+ Class cls = Class.forName(cname);
+ ref = (RemoteRef) cls.newInstance();
+ }
+ catch (InstantiationException e1)
+ {
+ throw new UnmarshalException("failed to create ref", e1);
+ }
+ catch (IllegalAccessException e2)
+ {
+ throw new UnmarshalException("failed to create ref", e2);
+ }
+ ref.readExternal(in);
}
- else
+ else
{
- ref = (RemoteRef)in.readObject();
+ ref = (RemoteRef) in.readObject();
}
}
-private void writeObject(ObjectOutputStream out) throws IOException, ClassNotFoundException {
- if (ref == null) {
- throw new UnmarshalException("no ref to serialize");
- }
- String cname = ref.getRefClass(out);
- if (cname != null && cname.length() > 0) {
- out.writeUTF(cname);
- ref.writeExternal(out);
- }
- else {
- out.writeUTF("");
- out.writeObject(ref);
- }
-}
+ /**
+ * Write the remote object to the output stream. This method first calls
+ * {@link RemoteRef#getRefClass(ObjectOutput)} on the {@link #ref} to get the
+ * class name without package, writes this name and then calls the
+ * ref.writeObject to write the data. The standard packageless class names are
+ * UnicastRef, UnicastRef2, UnicastServerRef, UnicastServerRef2,
+ * ActivatableRef or ActivatableServerRef. The empty string with the
+ * subsequently following serialized ref instance be written if the
+ * ref.getRefClass returns null.
+ *
+ * @param out the stream to write to
+ * @throws IOException if one occurs during writing
+ * @throws ClassNotFoundException never in this implementation (specified as
+ * part of the API standard)
+ * @throws UnmarshalException if the remote reference of this remote object is
+ * null.
+ */
+ private void writeObject(ObjectOutputStream out) throws IOException,
+ ClassNotFoundException
+ {
+ if (ref == null)
+ {
+ throw new UnmarshalException("no ref to serialize");
+ }
+ String cname = ref.getRefClass(out);
+ if (cname != null && cname.length() > 0)
+ {
+ out.writeUTF(cname);
+ ref.writeExternal(out);
+ }
+ else
+ {
+ out.writeUTF("");
+ out.writeObject(ref);
+ }
+ }
}
diff --git a/libjava/classpath/java/rmi/server/RemoteObjectInvocationHandler.java b/libjava/classpath/java/rmi/server/RemoteObjectInvocationHandler.java
index afd1d592715..2c19cd5afc4 100644
--- a/libjava/classpath/java/rmi/server/RemoteObjectInvocationHandler.java
+++ b/libjava/classpath/java/rmi/server/RemoteObjectInvocationHandler.java
@@ -90,6 +90,11 @@ public class RemoteObjectInvocationHandler extends RemoteObject implements
static final Class[] anObjectC = new Class[] { Object.class };
/**
+ * The empty object array to replace null when no args are passed.
+ */
+ static final Object[] noArgs = new Object[0];
+
+ /**
* Construct the remote invocation handler that forwards calls to the given
* remote object.
*
@@ -143,6 +148,9 @@ public class RemoteObjectInvocationHandler extends RemoteObject implements
throw new IllegalAccessException(name + " does not implement "
+ Remote.class.getName());
}
+
+ if (parameters == null)
+ parameters = noArgs;
String name = method.getName();
switch (name.charAt(0))
@@ -172,7 +180,7 @@ public class RemoteObjectInvocationHandler extends RemoteObject implements
break;
case 't':
if (parameters.length == 0 && name.equals("toString"))
- return proxyInstance.toString();
+ return "Proxy stub:"+ref.remoteToString();
break;
default:
break;
diff --git a/libjava/classpath/java/rmi/server/RemoteServer.java b/libjava/classpath/java/rmi/server/RemoteServer.java
index 9efb12a782d..f022b732604 100644
--- a/libjava/classpath/java/rmi/server/RemoteServer.java
+++ b/libjava/classpath/java/rmi/server/RemoteServer.java
@@ -1,5 +1,6 @@
/* RemoteServer.java --
- Copyright (c) 1996, 1997, 1998, 1999, 2004 Free Software Foundation, Inc.
+ Copyright (c) 1996, 1997, 1998, 1999, 2004, 2006
+ Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -35,6 +36,7 @@ this exception to your version of the library, but you are not
obligated to do so. If you do not wish to do so, delete this
exception statement from your version. */
+
package java.rmi.server;
import gnu.java.rmi.server.RMIIncomingThread;
@@ -42,35 +44,72 @@ import gnu.java.rmi.server.RMIIncomingThread;
import java.io.OutputStream;
import java.io.PrintStream;
-public abstract class RemoteServer extends RemoteObject
+/**
+ * A common superclass for the server implementations.
+ */
+public abstract class RemoteServer
+ extends RemoteObject
{
-private static final long serialVersionUID = -4100238210092549637L;
-
-protected RemoteServer() {
- super();
-}
-
-protected RemoteServer(RemoteRef ref) {
- super(ref);
-}
-
-public static String getClientHost() throws ServerNotActiveException {
- Thread currThread = Thread.currentThread();
- if (currThread instanceof RMIIncomingThread) {
- RMIIncomingThread incomingThread = (RMIIncomingThread) currThread;
- return incomingThread.getClientHost();
- } else {
- throw new ServerNotActiveException(
- "Unknown client host - current thread not instance of 'RMIIncomingThread'");
- }
-}
-
-public static void setLog(OutputStream out) {
- throw new Error("Not implemented");
-}
-
-public static PrintStream getLog() {
- throw new Error("Not implemented");
-}
+ private static final long serialVersionUID = - 4100238210092549637L;
+
+ /**
+ * Does nothing, delegates to super().
+ */
+ protected RemoteServer()
+ {
+ super();
+ }
+
+ /**
+ * Does nothing, delegates to super(ref).
+ */
+ protected RemoteServer(RemoteRef ref)
+ {
+ super(ref);
+ }
+
+ /**
+ * Get the host of the calling client. The current thread must be an instance
+ * of the {@link RMIIncomingThread}.
+ *
+ * @return the client host address
+ *
+ * @throws ServerNotActiveException if the current thread is not an instance
+ * of the RMIIncomingThread.
+ */
+ public static String getClientHost() throws ServerNotActiveException
+ {
+ Thread currThread = Thread.currentThread();
+ if (currThread instanceof RMIIncomingThread)
+ {
+ RMIIncomingThread incomingThread = (RMIIncomingThread) currThread;
+ return incomingThread.getClientHost();
+ }
+ else
+ {
+ throw new ServerNotActiveException(
+ "Unknown client host - current thread not instance of 'RMIIncomingThread'");
+ }
+ }
+
+ /**
+ * Set the stream for logging RMI calls.
+ *
+ * @param out the stream to set or null to turn the logging off.
+ */
+ public static void setLog(OutputStream out)
+ {
+ throw new Error("Not implemented");
+ }
+
+ /**
+ * Get the stream for logging RMI calls.
+ *
+ * @return the associated stream.
+ */
+ public static PrintStream getLog()
+ {
+ throw new Error("Not implemented");
+ }
}
diff --git a/libjava/classpath/java/rmi/server/UID.java b/libjava/classpath/java/rmi/server/UID.java
index 0f492bae77a..35963042211 100644
--- a/libjava/classpath/java/rmi/server/UID.java
+++ b/libjava/classpath/java/rmi/server/UID.java
@@ -1,5 +1,5 @@
-/* UID.java --
- Copyright (c) 1996, 1997, 1998, 1999, 2004 Free Software Foundation, Inc.
+/* UID.java -- The unique object Id
+ Copyright (c) 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -42,86 +42,186 @@ import java.io.DataInput;
import java.io.DataOutput;
import java.io.IOException;
import java.io.Serializable;
-
-public final class UID implements Serializable
-{
-private static final long serialVersionUID = 1086053664494604050L;
-
-private static final Object lock = UID.class;
-private static long baseTime = System.currentTimeMillis();
-private static short nextCount = Short.MIN_VALUE;
-// This is sun's algorithm - don't ask me why ...
-private static final int uniqueNr = (new Object()).hashCode();
-
-private int unique;
-private long time;
-private short count;
+import java.net.InetAddress;
/**
- * This is sun's algorithm - don't ask me why ...
+ * Represents the unique identifier over time for the host which has generated
+ * it. It contains time (when created), counter (the number of the UID
+ * creation order) and virtual machine id components. The UID can also be
+ * constructed specifying a "well known" identifier in the for of short:
+ * this identifier defines the UID uniqueness alone.
+ *
+ * @author Audrius Meskauskas (audriusa@bioinformatics.org)
*/
-public UID() {
- synchronized (lock) {
- if (nextCount == Short.MAX_VALUE) {
- long newtime;
- for (;;) {
- newtime = System.currentTimeMillis();
- if (newtime - baseTime > 1000) {
- break;
- }
- try {
- Thread.sleep(1000);
- }
- catch (InterruptedException _) {
- }
- }
- baseTime = newtime;
- nextCount = Short.MIN_VALUE;
- }
- count = nextCount++;
- unique = uniqueNr;
- time = baseTime;
- }
-}
-
-public UID(short num) {
- unique = (int)num;
- time = 0;
- count = 0;
-}
-
-public int hashCode() {
- return (unique);
-}
-
-public boolean equals(Object obj) {
- if (obj instanceof UID) {
- UID uid = (UID)obj;
- if (this.unique == uid.unique &&
- this.time == uid.time &&
- this.count == uid.count) {
- return (true);
- }
- }
- return (false);
-}
-
-public String toString() {
- return ("[UID: " + unique + "," + time + "," + count + "]");
-}
-
-public void write(DataOutput out) throws IOException {
- out.writeInt(unique);
- out.writeLong(time);
- out.writeShort(count);
-}
-
-public static UID read(DataInput in) throws IOException {
- UID id = new UID();
- id.unique = in.readInt();
- id.time = in.readLong();
- id.count = in.readShort();
- return (id);
-}
-
+public final class UID
+ implements Serializable
+{
+ /**
+ * Use the serial version uid for interoperability.
+ */
+ private static final long serialVersionUID = 1086053664494604050L;
+
+ /**
+ * The UID counter (the ordinary number in the sequence of number of UID's,
+ * created during the recent millisecond). In the next millisecond, it
+ * starts from the minimal value again. In the unlikely case of creating
+ * more than 65536 uids per millisecond the process pauses till the next
+ * ms.
+ */
+ private static short uidCounter = Short.MIN_VALUE;
+
+ /**
+ * The time, when the last UID has been created.
+ */
+ private static long last;
+
+ /**
+ * This constant tries to be the unique identifier of the virtual machine.
+ */
+ private static final int machineId = getMachineId();
+
+ /**
+ * The UID number in the UID creation sequence.
+ */
+ private short count;
+
+ /**
+ * Always gets the uniqueNr value.
+ */
+ private int unique;
+
+ /**
+ * The time stamp, when the UID was created.
+ */
+ private long time;
+
+ /**
+ * Create the new UID that would have the described features of the
+ * uniqueness.
+ */
+ public UID()
+ {
+ time = System.currentTimeMillis();
+ unique = machineId;
+ if (time > last)
+ {
+ last = time;
+ count = uidCounter = Short.MIN_VALUE;
+ }
+ else
+ {
+ synchronized (UID.class)
+ {
+ if (uidCounter == Short.MAX_VALUE)
+ {
+ // Make a 2 ms pause if the counter has reached the maximal
+ // value. This should seldom happen.
+ try
+ {
+ Thread.sleep(2);
+ }
+ catch (InterruptedException e)
+ {
+ }
+ uidCounter = Short.MIN_VALUE;
+ time = last = System.currentTimeMillis();
+ }
+
+ count = uidCounter++;
+ }
+ }
+ }
+
+ /**
+ * Create the new UID with the well known id (number). All UIDs, creates
+ * with the this constructor having the same parameter are equal to each
+ * other (regardless to the host and time where they were created.
+ *
+ * @param wellKnownId the well known UID.
+ */
+ public UID(short wellKnownId)
+ {
+ unique = wellKnownId;
+ }
+
+ /**
+ * Get the hashCode of this UID.
+ */
+ public int hashCode()
+ {
+ return (int) (unique ^ time ^ count);
+ }
+
+ /**
+ * Compare this UID with another UID for equality (not equal to other types of
+ * objects).
+ */
+ public boolean equals(Object other)
+ {
+ if (other instanceof UID)
+ {
+ UID ui = (UID) other;
+ return unique == ui.unique && time == ui.time && count == ui.count;
+ }
+ else
+ return false;
+ }
+
+ public static UID read(DataInput in) throws IOException
+ {
+ UID uid = new UID();
+ uid.unique = in.readInt();
+ uid.time = in.readLong();
+ uid.count = in.readShort();
+ return (uid);
+ }
+
+ public void write(DataOutput out) throws IOException
+ {
+ out.writeInt(unique);
+ out.writeLong(time);
+ out.writeShort(count);
+ }
+
+ /**
+ * Do our best to get the Id of this virtual machine.
+ */
+ static int getMachineId()
+ {
+ int hostIpHash;
+
+ try
+ {
+ // Try to get the host IP.
+ String host = InetAddress.getLocalHost().toString();
+ // This hash is content - based, not the address based.
+ hostIpHash = host.hashCode();
+ }
+ catch (Exception e)
+ {
+ // Failed due some reason.
+ hostIpHash = 0;
+ }
+
+ // Should be the unque address if hashcodes are addresses.
+ // Additionally, add the time when the RMI system was probably started
+ // (this class was first instantiated).
+ return new Object().hashCode() ^ (int) System.currentTimeMillis()
+ ^ hostIpHash;
+ }
+
+ /**
+ * Get the string representation of this UID.
+ *
+ * @return a string, uniquely identifying this id.
+ */
+ public String toString()
+ {
+ int max = Character.MAX_RADIX;
+ // Translate into object count, counting from 0.
+ long lc = (count + Short.MIN_VALUE) & 0xFFFF;
+ return Long.toString(time, max) + ":"
+ + Long.toString(unique, max) + ":"
+ + Long.toString(lc, max);
+ }
}
diff --git a/libjava/classpath/java/security/BasicPermission.java b/libjava/classpath/java/security/BasicPermission.java
index 267a6e292ab..ef2cc4df094 100644
--- a/libjava/classpath/java/security/BasicPermission.java
+++ b/libjava/classpath/java/security/BasicPermission.java
@@ -1,5 +1,6 @@
/* BasicPermission.java -- implements a simple named permission
- Copyright (C) 1998, 1999, 2002, 2003, 2004, 2005 Free Software Foundation, Inc.
+ Copyright (C) 1998, 1999, 2002, 2003, 2004, 2005, 2006
+ Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -97,7 +98,7 @@ public abstract class BasicPermission extends java.security.Permission
// requirement exists in the specification and Sun's runtime
// doesn't appear to do it.
- if ("".equals(name))
+ if (name.equals(""))
throw new IllegalArgumentException("Empty name");
}
diff --git a/libjava/classpath/java/security/KeyStore.java b/libjava/classpath/java/security/KeyStore.java
index 696448728ff..8681d826590 100644
--- a/libjava/classpath/java/security/KeyStore.java
+++ b/libjava/classpath/java/security/KeyStore.java
@@ -212,7 +212,7 @@ public class KeyStore
/**
* Returns the default KeyStore type. This method looks up the
* type in &lt;JAVA_HOME&gt;/lib/security/java.security with the
- * property "keystore.type" or if that fails then "jks" .
+ * property "keystore.type" or if that fails then "gkr" .
*/
public static final String getDefaultType()
{
@@ -221,7 +221,7 @@ public class KeyStore
String tmp = Security.getProperty("keystore.type");
if (tmp == null)
- tmp = "jks";
+ tmp = "gkr";
return tmp;
}
diff --git a/libjava/classpath/java/security/SecureRandom.java b/libjava/classpath/java/security/SecureRandom.java
index 0d892253c03..d403d496428 100644
--- a/libjava/classpath/java/security/SecureRandom.java
+++ b/libjava/classpath/java/security/SecureRandom.java
@@ -1,5 +1,6 @@
/* SecureRandom.java --- Secure Random class implementation
- Copyright (C) 1999, 2001, 2002, 2003, 2005 Free Software Foundation, Inc.
+ Copyright (C) 1999, 2001, 2002, 2003, 2005, 2006
+ Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -37,11 +38,19 @@ exception statement from your version. */
package java.security;
+import gnu.classpath.SystemProperties;
import gnu.java.security.Engine;
+import gnu.java.security.action.GetSecurityPropertyAction;
import gnu.java.security.jce.prng.Sha160RandomSpi;
+import java.io.IOException;
+import java.io.InputStream;
+import java.net.MalformedURLException;
+import java.net.URL;
import java.util.Enumeration;
import java.util.Random;
+import java.util.logging.Level;
+import java.util.logging.Logger;
/**
* An interface to a cryptographically secure pseudo-random number
@@ -71,6 +80,9 @@ public class SecureRandom extends Random
int randomBytesUsed = 0;
SecureRandomSpi secureRandomSpi = null;
byte[] state = null;
+ private String algorithm;
+
+ private boolean isSeeded = false;
// Constructors.
// ------------------------------------------------------------------------
@@ -111,6 +123,7 @@ public class SecureRandom extends Random
secureRandomSpi = (SecureRandomSpi) Class.
forName(classname).newInstance();
provider = p[i];
+ algorithm = key.substring(13); // Minus SecureRandom.
return;
}
catch (ThreadDeath death)
@@ -128,6 +141,7 @@ public class SecureRandom extends Random
// Nothing found. Fall back to SHA1PRNG
secureRandomSpi = new Sha160RandomSpi();
+ algorithm = "Sha160";
}
/**
@@ -159,8 +173,18 @@ public class SecureRandom extends Random
*/
protected SecureRandom(SecureRandomSpi secureRandomSpi, Provider provider)
{
+ this(secureRandomSpi, provider, "unknown");
+ }
+
+ /**
+ * Private constructor called from the getInstance() method.
+ */
+ private SecureRandom(SecureRandomSpi secureRandomSpi, Provider provider,
+ String algorithm)
+ {
this.secureRandomSpi = secureRandomSpi;
this.provider = provider;
+ this.algorithm = algorithm;
}
// Class methods.
@@ -243,7 +267,7 @@ public class SecureRandom extends Random
{
return new SecureRandom((SecureRandomSpi)
Engine.getInstance(SECURE_RANDOM, algorithm, provider),
- provider);
+ provider, algorithm);
}
catch (java.lang.reflect.InvocationTargetException ite)
{
@@ -269,6 +293,18 @@ public class SecureRandom extends Random
}
/**
+ * Returns the algorithm name used or "unknown" when the algorithm
+ * used couldn't be determined (as when constructed by the protected
+ * 2 argument constructor).
+ *
+ * @since 1.5
+ */
+ public String getAlgorithm()
+ {
+ return algorithm;
+ }
+
+ /**
Seeds the SecureRandom. The class is re-seeded for each call and
each seed builds on the previous seed so as not to weaken security.
@@ -277,6 +313,7 @@ public class SecureRandom extends Random
public void setSeed(byte[] seed)
{
secureRandomSpi.engineSetSeed(seed);
+ isSeeded = true;
}
/**
@@ -304,6 +341,7 @@ public class SecureRandom extends Random
(byte) (0xff & seed)
};
secureRandomSpi.engineSetSeed(tmp);
+ isSeeded = true;
}
}
@@ -315,6 +353,8 @@ public class SecureRandom extends Random
*/
public void nextBytes(byte[] bytes)
{
+ if (!isSeeded)
+ setSeed(getSeed(32));
randomBytesUsed += bytes.length;
counter++;
secureRandomSpi.engineNextBytes(bytes);
@@ -360,10 +400,8 @@ public class SecureRandom extends Random
public static byte[] getSeed(int numBytes)
{
byte[] tmp = new byte[numBytes];
-
- new Random().nextBytes(tmp);
+ generateSeed(tmp);
return tmp;
- //return secureRandomSpi.engineGenerateSeed( numBytes );
}
/**
@@ -378,4 +416,64 @@ public class SecureRandom extends Random
return secureRandomSpi.engineGenerateSeed(numBytes);
}
+ // Seed methods.
+
+ private static final String SECURERANDOM_SOURCE = "securerandom.source";
+ private static final String JAVA_SECURITY_EGD = "java.security.egd";
+ private static final Logger logger = Logger.getLogger(SecureRandom.class.getName());
+
+ private static int generateSeed(byte[] buffer)
+ {
+ return generateSeed(buffer, 0, buffer.length);
+ }
+
+ private static int generateSeed(byte[] buffer, int offset, int length)
+ {
+ URL sourceUrl = null;
+ String urlStr = null;
+
+ GetSecurityPropertyAction action = new GetSecurityPropertyAction(SECURERANDOM_SOURCE);
+ try
+ {
+ urlStr = (String) AccessController.doPrivileged(action);
+ if (urlStr != null)
+ sourceUrl = new URL(urlStr);
+ }
+ catch (MalformedURLException ignored)
+ {
+ logger.log(Level.WARNING, SECURERANDOM_SOURCE + " property is malformed: {0}",
+ urlStr);
+ }
+
+ if (sourceUrl == null)
+ {
+ try
+ {
+ urlStr = SystemProperties.getProperty(JAVA_SECURITY_EGD);
+ if (urlStr != null)
+ sourceUrl = new URL(urlStr);
+ }
+ catch (MalformedURLException mue)
+ {
+ logger.log(Level.WARNING, JAVA_SECURITY_EGD + " property is malformed: {0}",
+ urlStr);
+ }
+ }
+
+ if (sourceUrl != null)
+ {
+ try
+ {
+ InputStream in = sourceUrl.openStream();
+ return in.read(buffer, offset, length);
+ }
+ catch (IOException ioe)
+ {
+ logger.log(Level.FINE, "error reading random bytes", ioe);
+ }
+ }
+
+ // If we get here, we did not get any seed from a property URL.
+ return VMSecureRandom.generateSeed(buffer, offset, length);
+ }
}
diff --git a/libjava/classpath/java/security/Security.java b/libjava/classpath/java/security/Security.java
index 4e31dab75e9..d99c451499a 100644
--- a/libjava/classpath/java/security/Security.java
+++ b/libjava/classpath/java/security/Security.java
@@ -101,7 +101,12 @@ public final class Security
System.err.println
(" Falling back to standard GNU security provider");
}
+ // Note that this matches our classpath.security file.
providers.addElement (new gnu.java.security.provider.Gnu());
+ providers.addElement(new gnu.javax.crypto.jce.GnuCrypto());
+ providers.addElement(new gnu.javax.crypto.jce.GnuSasl());
+ providers.addElement(new gnu.javax.net.ssl.provider.Jessie());
+ providers.addElement(new gnu.javax.security.auth.callback.GnuCallbacks());
}
}
// This class can't be instantiated.
diff --git a/libjava/classpath/java/security/cert/CertPathValidatorSpi.java b/libjava/classpath/java/security/cert/CertPathValidatorSpi.java
index 8d18b49dac4..282b7a695b9 100644
--- a/libjava/classpath/java/security/cert/CertPathValidatorSpi.java
+++ b/libjava/classpath/java/security/cert/CertPathValidatorSpi.java
@@ -38,6 +38,8 @@ exception statement from your version. */
package java.security.cert;
+import java.security.InvalidAlgorithmParameterException;
+
/**
* The <i>service provider interface</i> (<b>SPI</b>) for the {@link
* CertPathValidator} class. Providers implementing certificate path
@@ -75,5 +77,5 @@ public abstract class CertPathValidatorSpi
public abstract CertPathValidatorResult
engineValidate(CertPath certPath, CertPathParameters params)
throws CertPathValidatorException,
- java.security.InvalidAlgorithmParameterException;
+ InvalidAlgorithmParameterException;
}
diff --git a/libjava/classpath/java/security/cert/CertStoreSpi.java b/libjava/classpath/java/security/cert/CertStoreSpi.java
index eca0e866ca1..a69545f0d32 100644
--- a/libjava/classpath/java/security/cert/CertStoreSpi.java
+++ b/libjava/classpath/java/security/cert/CertStoreSpi.java
@@ -38,6 +38,7 @@ exception statement from your version. */
package java.security.cert;
+import java.security.InvalidAlgorithmParameterException;
import java.util.Collection;
/**
@@ -69,7 +70,7 @@ public abstract class CertStoreSpi
* parameters are inappropriate for this class.
*/
public CertStoreSpi(CertStoreParameters params)
- throws java.security.InvalidAlgorithmParameterException
+ throws InvalidAlgorithmParameterException
{
super();
}
diff --git a/libjava/classpath/java/security/cert/Certificate.java b/libjava/classpath/java/security/cert/Certificate.java
index f8456f97ae5..33a14a43983 100644
--- a/libjava/classpath/java/security/cert/Certificate.java
+++ b/libjava/classpath/java/security/cert/Certificate.java
@@ -73,7 +73,7 @@ import java.security.SignatureException;
*/
public abstract class Certificate implements Serializable
{
- private static final long serialVersionUID = -6751606818319535583L;
+ private static final long serialVersionUID = -3585440601605666277L;
private String type;
diff --git a/libjava/classpath/java/security/cert/PKIXCertPathChecker.java b/libjava/classpath/java/security/cert/PKIXCertPathChecker.java
index 7a33576e1bb..a6eef41a298 100644
--- a/libjava/classpath/java/security/cert/PKIXCertPathChecker.java
+++ b/libjava/classpath/java/security/cert/PKIXCertPathChecker.java
@@ -46,7 +46,7 @@ import java.util.Set;
*
* <p>Concrete subclasses can be passed to the {@link
* PKIXParameters#setCertPathCheckers(java.util.List)} and {@link
- * PKIXParameters#addCertPathChecker(java.security.cert.PKIXCertPathChecker}
+ * PKIXParameters#addCertPathChecker(java.security.cert.PKIXCertPathChecker)}
* methods, which are then used to set up PKIX certificate chain
* builders or validators. These classes then call the {@link
* #check(java.security.cert.Certificate,java.util.Collection)} method
diff --git a/libjava/classpath/java/security/cert/PKIXParameters.java b/libjava/classpath/java/security/cert/PKIXParameters.java
index 4a987115a29..16ef07f8870 100644
--- a/libjava/classpath/java/security/cert/PKIXParameters.java
+++ b/libjava/classpath/java/security/cert/PKIXParameters.java
@@ -55,7 +55,7 @@ import java.util.Set;
* Parameters for verifying certificate paths using the PKIX
* (Public-Key Infrastructure (X.509)) algorithm.
*
- * @see CertPathBulider
+ * @see CertPathBuilder
*/
public class PKIXParameters implements CertPathParameters
{
diff --git a/libjava/classpath/java/security/cert/X509CertSelector.java b/libjava/classpath/java/security/cert/X509CertSelector.java
index e3b8c0eb2ca..a46d2288b8d 100644
--- a/libjava/classpath/java/security/cert/X509CertSelector.java
+++ b/libjava/classpath/java/security/cert/X509CertSelector.java
@@ -367,7 +367,7 @@ public class X509CertSelector implements CertSelector, Cloneable
* Sets the authority key identifier criterion, or <code>null</code> to clear
* this criterion. Note that the byte array is cloned to prevent modification.
*
- * @param subjectKeyId The subject key identifier.
+ * @param authKeyId The authority key identifier.
*/
public void setAuthorityKeyIdentifier(byte[] authKeyId)
{
diff --git a/libjava/classpath/java/sql/Array.java b/libjava/classpath/java/sql/Array.java
index 51628757885..c3c42d9cb57 100644
--- a/libjava/classpath/java/sql/Array.java
+++ b/libjava/classpath/java/sql/Array.java
@@ -1,5 +1,5 @@
/* Array.java -- Interface for accessing SQL array object
- Copyright (C) 1999, 2000, 2002 Free Software Foundation, Inc.
+ Copyright (C) 1999, 2000, 2002, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -50,7 +50,7 @@ public interface Array
* Returns the name of the SQL type of the elements in this
* array. This name is database specific.
*
- * @param The name of the SQL type of the elements in this array.
+ * @return The name of the SQL type of the elements in this array.
* @exception SQLException If an error occurs.
*/
String getBaseTypeName() throws SQLException;
@@ -87,22 +87,22 @@ public interface Array
Object getArray(Map map) throws SQLException;
/**
- * Returns a portion of this array starting at <code>index</code>
+ * Returns a portion of this array starting at <code>start</code>
* into the array and continuing for <code>count</code>
* elements. Fewer than the requested number of elements will be
* returned if the array does not contain the requested number of elements.
* The object returned will be an array of Java objects of
* the appropriate types.
*
- * @param offset The offset into this array to start returning elements from.
+ * @param start The index into this array to start returning elements from.
* @param count The requested number of elements to return.
* @return The requested portion of the array.
* @exception SQLException If an error occurs.
*/
- Object getArray(long index, int count) throws SQLException;
+ Object getArray(long start, int count) throws SQLException;
/**
- * This method returns a portion of this array starting at <code>index</code>
+ * This method returns a portion of this array starting at <code>start</code>
* into the array and continuing for <code>count</code>
* elements. Fewer than the requested number of elements will be
* returned if the array does not contain the requested number of elements.
@@ -110,13 +110,13 @@ public interface Array
* <code>Map</code> will be used for overriding selected SQL type to
* Java class mappings.
*
- * @param offset The offset into this array to start returning elements from.
+ * @param start The index into this array to start returning elements from.
* @param count The requested number of elements to return.
* @param map A mapping of SQL types to Java classes.
* @return The requested portion of the array.
* @exception SQLException If an error occurs.
*/
- Object getArray(long index, int count, Map map) throws SQLException;
+ Object getArray(long start, int count, Map map) throws SQLException;
/**
* Returns the elements in the array as a <code>ResultSet</code>.
@@ -147,24 +147,24 @@ public interface Array
/**
* This method returns a portion of the array as a <code>ResultSet</code>.
- * The returned portion will start at <code>index</code> into the
+ * The returned portion will start at <code>start</code> into the
* array and up to <code>count</code> elements will be returned.
* <p>
* Each row of the result set will have two columns. The first will be
* the index into the array of that row's contents. The second will be
* the actual value of that array element.
*
- * @param offset The index into the array to start returning elements from.
- * @param length The requested number of elements to return.
+ * @param start The index into the array to start returning elements from.
+ * @param count The requested number of elements to return.
* @return The requested elements of this array as a <code>ResultSet</code>.
* @exception SQLException If an error occurs.
* @see ResultSet
*/
- ResultSet getResultSet(long index, int count) throws SQLException;
+ ResultSet getResultSet(long start, int count) throws SQLException;
/**
* This method returns a portion of the array as a <code>ResultSet</code>.
- * The returned portion will start at <code>index</code> into the
+ * The returned portion will start at <code>start</code> into the
* array and up to <code>count</code> elements will be returned.
*
* <p> Each row of the result set will have two columns. The first will be
@@ -173,13 +173,13 @@ public interface Array
* will be used to override selected default mappings of SQL types to
* Java classes.</p>
*
- * @param offset The index into the array to start returning elements from.
- * @param length The requested number of elements to return.
+ * @param start The index into the array to start returning elements from.
+ * @param count The requested number of elements to return.
* @param map A mapping of SQL types to Java classes.
* @return The requested elements of this array as a <code>ResultSet</code>.
* @exception SQLException If an error occurs.
* @see ResultSet
*/
- ResultSet getResultSet(long index, int count, Map map)
+ ResultSet getResultSet(long start, int count, Map map)
throws SQLException;
}
diff --git a/libjava/classpath/java/sql/Blob.java b/libjava/classpath/java/sql/Blob.java
index 616839d01be..c662aad5f2f 100644
--- a/libjava/classpath/java/sql/Blob.java
+++ b/libjava/classpath/java/sql/Blob.java
@@ -1,5 +1,5 @@
/* Blob.java -- Access a SQL Binary Large OBject.
- Copyright (C) 1999, 2000, 2002 Free Software Foundation, Inc.
+ Copyright (C) 1999, 2000, 2002, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -41,48 +41,51 @@ import java.io.InputStream;
import java.io.OutputStream;
/**
- * This interface specified methods for accessing a SQL BLOB (Binary
- * Large OBject) type.
- *
+ * This interface specified methods for accessing a SQL BLOB (Binary Large
+ * OBject) type.
+ *
* @author Aaron M. Renn (arenn@urbanophile.com)
* @since 1.2
*/
-public interface Blob
+public interface Blob
{
/**
- * This method returns the number of bytes in the BLOB.
- *
- * @return The number of bytes in the BLOB.
+ * This method returns the number of bytes in this <code>Blob</code>.
+ *
+ * @return The number of bytes in this <code>Blob</code>.
* @exception SQLException If an error occurs.
*/
long length() throws SQLException;
/**
- * This method returns up to the requested bytes of this BLOB as a
- * <code>byte</code> array.
- *
- * @param pos The index into the BLOB to start returning bytes from.
- * @param length The requested number of bytes to return.
- * @return The requested bytes from the BLOB.
+ * This method returns up to the requested bytes of this <code>Blob</code>
+ * as a <code>byte</code> array.
+ *
+ * @param start The index into this <code>Blob</code> to start returning
+ * bytes from.
+ * @param count The requested number of bytes to return.
+ * @return The requested bytes from this <code>Blob</code>.
* @exception SQLException If an error occurs.
*/
- byte[] getBytes(long pos, int length) throws SQLException;
+ byte[] getBytes(long start, int count) throws SQLException;
/**
- * This method returns a stream that will read the bytes of the BLOB.
- *
- * @return A stream that will read the bytes of the BLOB.
+ * This method returns a stream that will read the bytes of this
+ * <code>Blob</code>.
+ *
+ * @return A stream that will read the bytes of this <code>Blob</code>.
* @exception SQLException If an error occurs.
*/
InputStream getBinaryStream() throws SQLException;
/**
- * This method returns the index into the BLOB at which the first instance
- * of the specified bytes occur. The searching starts at the specified
- * index into the BLOB.
- *
+ * This method returns the index into this <code>Blob</code> at which the
+ * first instance of the specified bytes occur. The searching starts at the
+ * specified index into this <code>Blob</code>.
+ *
* @param pattern The byte pattern to search for.
- * @param offset The index into the BLOB to starting searching for the pattern.
+ * @param start The index into this <code>Blob</code> to start searching for
+ * the pattern.
* @return The offset at which the pattern is first found, or -1 if the
* pattern is not found.
* @exception SQLException If an error occurs.
@@ -90,14 +93,15 @@ public interface Blob
long position(byte[] pattern, long start) throws SQLException;
/**
- * This method returns the index into the BLOB at which the first instance
- * of the specified pattern occurs. The searching starts at the specified
- * index into this BLOB. The bytes in the specified <code>Blob</code> are
- * used as the search pattern.
- *
+ * This method returns the index into this <code>Blob</code> at which the
+ * first instance of the specified pattern occurs. The searching starts at the
+ * specified index into this <code>Blob</code>. The bytes in the specified
+ * <code>Blob</code> are used as the search pattern.
+ *
* @param pattern The <code>Blob</code> containing the byte pattern to
- * search for.
- * @param offset The index into the BLOB to starting searching for the pattern.
+ * search for.
+ * @param start The index into this <code>Blob</code> to start searching for
+ * the pattern.
* @return The offset at which the pattern is first found, or -1 if the
* pattern is not found.
* @exception SQLException If an error occurs.
@@ -105,27 +109,49 @@ public interface Blob
long position(Blob pattern, long start) throws SQLException;
/**
+ * Writes the specified data into this <code>Blob</code>, starting at the
+ * specified index.
+ *
+ * @param start The index at which the writing starts.
+ * @param bytes The data to write.
* @exception SQLException If an error occurs.
* @since 1.4
*/
- int setBytes(long pos, byte[] bytes) throws SQLException;
+ int setBytes(long start, byte[] bytes) throws SQLException;
/**
+ * Writes a portion of the specified data into this <code>Blob</code>,
+ * starting at the specified index.
+ *
+ * @param startWrite The index into this <code>Blob</code> at which writing
+ * starts.
+ * @param bytes The data to write a portion of.
+ * @param startRead The offset into the data where the portion to copy starts.
+ * @param count The number of bytes to write.
* @exception SQLException If an error occurs.
* @since 1.4
*/
- int setBytes(long pos, byte[] bytes, int offset, int len)
- throws SQLException;
+ int setBytes(long startWrite, byte[] bytes, int startRead, int count)
+ throws SQLException;
/**
+ * Returns a binary stream that writes into this <code>Blob</code>,
+ * starting at the specified index.
+ *
+ * @param start The index at which the writing starts.
+ * @return A binary stream to write into this <code>Blob</code>.
* @exception SQLException If an error occurs.
* @since 1.4
*/
- OutputStream setBinaryStream(long pos) throws SQLException;
+ OutputStream setBinaryStream(long start) throws SQLException;
/**
+ * Truncates this <code>Blob</code> to be at most the specified number of
+ * bytes long.
+ *
+ * @param count The length this <code>Blob</code> is truncated to.
* @exception SQLException If an error occurs.
* @since 1.4
*/
- void truncate(long len) throws SQLException;
+ void truncate(long count) throws SQLException;
}
diff --git a/libjava/classpath/java/sql/CallableStatement.java b/libjava/classpath/java/sql/CallableStatement.java
index 452294144a0..75eade77480 100644
--- a/libjava/classpath/java/sql/CallableStatement.java
+++ b/libjava/classpath/java/sql/CallableStatement.java
@@ -1,5 +1,5 @@
/* CallableStatement.java -- A statement for calling stored procedures.
- Copyright (C) 1999, 2000, 2002 Free Software Foundation, Inc.
+ Copyright (C) 1999, 2000, 2002, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -56,10 +56,10 @@ public interface CallableStatement extends PreparedStatement
* of the specified SQL type.
*
* @param index The index of the parameter to register as output.
- * @param type The SQL type value from <code>Types</code>.
+ * @param sqlType The SQL type value from <code>Types</code>.
* @exception SQLException If an error occurs.
*/
- void registerOutParameter(int parameterIndex, int sqlType)
+ void registerOutParameter(int index, int sqlType)
throws SQLException;
/**
@@ -67,11 +67,11 @@ public interface CallableStatement extends PreparedStatement
* of the specified SQL type and scale.
*
* @param index The index of the parameter to register as output.
- * @param type The SQL type value from <code>Types</code>.
+ * @param sqlType The SQL type value from <code>Types</code>.
* @param scale The scale of the value that will be returned.
* @exception SQLException If an error occurs.
*/
- void registerOutParameter(int parameterIndex, int sqlType, int scale)
+ void registerOutParameter(int index, int sqlType, int scale)
throws SQLException;
/**
@@ -92,7 +92,7 @@ public interface CallableStatement extends PreparedStatement
* @return The parameter value as a <code>String</code>.
* @exception SQLException If an error occurs.
*/
- String getString(int parameterIndex) throws SQLException;
+ String getString(int index) throws SQLException;
/**
* This method returns the value of the specified parameter as a Java
@@ -102,7 +102,7 @@ public interface CallableStatement extends PreparedStatement
* @return The parameter value as a <code>boolean</code>.
* @exception SQLException If an error occurs.
*/
- boolean getBoolean(int parameterIndex) throws SQLException;
+ boolean getBoolean(int index) throws SQLException;
/**
* This method returns the value of the specified parameter as a Java
@@ -112,7 +112,7 @@ public interface CallableStatement extends PreparedStatement
* @return The parameter value as a <code>byte</code>.
* @exception SQLException If an error occurs.
*/
- byte getByte(int parameterIndex) throws SQLException;
+ byte getByte(int index) throws SQLException;
/**
* This method returns the value of the specified parameter as a Java
@@ -122,7 +122,7 @@ public interface CallableStatement extends PreparedStatement
* @return The parameter value as a <code>short</code>.
* @exception SQLException If an error occurs.
*/
- short getShort(int parameterIndex) throws SQLException;
+ short getShort(int index) throws SQLException;
/**
* This method returns the value of the specified parameter as a Java
@@ -132,7 +132,7 @@ public interface CallableStatement extends PreparedStatement
* @return The parameter value as a <code>int</code>.
* @exception SQLException If an error occurs.
*/
- int getInt(int parameterIndex) throws SQLException;
+ int getInt(int index) throws SQLException;
/**
* This method returns the value of the specified parameter as a Java
@@ -142,7 +142,7 @@ public interface CallableStatement extends PreparedStatement
* @return The parameter value as a <code>long</code>.
* @exception SQLException If an error occurs.
*/
- long getLong(int parameterIndex) throws SQLException;
+ long getLong(int index) throws SQLException;
/**
* This method returns the value of the specified parameter as a Java
@@ -152,7 +152,7 @@ public interface CallableStatement extends PreparedStatement
* @return The parameter value as a <code>float</code>.
* @exception SQLException If an error occurs.
*/
- float getFloat(int parameterIndex) throws SQLException;
+ float getFloat(int index) throws SQLException;
/**
* This method returns the value of the specified parameter as a Java
@@ -162,31 +162,31 @@ public interface CallableStatement extends PreparedStatement
* @return The parameter value as a <code>double</code>.
* @exception SQLException If an error occurs.
*/
- double getDouble(int parameterIndex) throws SQLException;
+ double getDouble(int index) throws SQLException;
/**
* This method returns the value of the specified parameter as a Java
* <code>BigDecimal</code>.
*
- * @param parameterIndex The index of the parameter to return.
+ * @param index The index of the parameter to return.
* @param scale The number of digits to the right of the decimal to return.
* @return The parameter value as a <code>BigDecimal</code>.
* @exception SQLException If an error occurs.
- * @deprecated Use getBigDecimal(int parameterIndex)
- * or getBigDecimal(String parameterName) instead.
+ * @deprecated Use getBigDecimal(int index)
+ * or getBigDecimal(String name) instead.
*/
- BigDecimal getBigDecimal(int parameterIndex, int scale)
+ BigDecimal getBigDecimal(int index, int scale)
throws SQLException;
/**
* This method returns the value of the specified parameter as a Java
* byte array.
*
- * @param parameterIndex The index of the parameter to return.
+ * @param index The index of the parameter to return.
* @return The parameter value as a byte array
* @exception SQLException If an error occurs.
*/
- byte[] getBytes(int parameterIndex) throws SQLException;
+ byte[] getBytes(int index) throws SQLException;
/**
* This method returns the value of the specified parameter as a Java
@@ -196,7 +196,7 @@ public interface CallableStatement extends PreparedStatement
* @return The parameter value as a <code>java.sql.Date</code>.
* @exception SQLException If an error occurs.
*/
- Date getDate(int parameterIndex) throws SQLException;
+ Date getDate(int index) throws SQLException;
/**
* This method returns the value of the specified parameter as a Java
@@ -206,7 +206,7 @@ public interface CallableStatement extends PreparedStatement
* @return The parameter value as a <code>java.sql.Time</code>.
* @exception SQLException If an error occurs.
*/
- Time getTime(int parameterIndex) throws SQLException;
+ Time getTime(int index) throws SQLException;
/**
* This method returns the value of the specified parameter as a Java
@@ -216,29 +216,29 @@ public interface CallableStatement extends PreparedStatement
* @return The parameter value as a <code>java.sql.Timestamp</code>.
* @exception SQLException If an error occurs.
*/
- Timestamp getTimestamp(int parameterIndex) throws SQLException;
+ Timestamp getTimestamp(int index) throws SQLException;
/**
* This method returns the value of the specified parameter as a Java
* <code>Object</code>.
*
- * @param parameterIndex The index of the parameter to return.
+ * @param index The index of the parameter to return.
* @return The parameter value as an <code>Object</code>.
* @exception SQLException If an error occurs.
* @since 1.2
*/
- Object getObject(int parameterIndex) throws SQLException;
+ Object getObject(int index) throws SQLException;
/**
* This method returns the value of the specified parameter as a Java
* <code>BigDecimal</code>.
*
- * @param parameterIndex The index of the parameter to return.
+ * @param index The index of the parameter to return.
* @return The parameter value as a <code>BigDecimal</code>.
* @exception SQLException If an error occurs.
* @since 1.2
*/
- BigDecimal getBigDecimal(int parameterIndex) throws SQLException;
+ BigDecimal getBigDecimal(int index) throws SQLException;
/**
* This method returns the value of the specified parameter as a Java
@@ -289,7 +289,7 @@ public interface CallableStatement extends PreparedStatement
* This method returns the value of the specified parameter as a Java
* <code>Array</code>.
*
- * @param parameterIndex The index of the parameter to return.
+ * @param index The index of the parameter to return.
* @return The parameter value as a <code>Array</code>.
* @exception SQLException If an error occurs.
* @since 1.2
@@ -300,25 +300,25 @@ public interface CallableStatement extends PreparedStatement
* This method returns the value of the specified parameter as a Java
* <code>java.sql.Date</code>.
*
- * @param parameterIndex The index of the parameter to return.
+ * @param index The index of the parameter to return.
* @param cal The <code>Calendar</code> to use for timezone and locale.
* @return The parameter value as a <code>java.sql.Date</code>.
* @exception SQLException If an error occurs.
* @since 1.2
*/
- Date getDate(int parameterIndex, Calendar cal) throws SQLException;
+ Date getDate(int index, Calendar cal) throws SQLException;
/**
* This method returns the value of the specified parameter as a Java
* <code>java.sql.Time</code>.
*
- * @param parameterIndex The index of the parameter to return.
+ * @param index The index of the parameter to return.
* @param cal The <code>Calendar</code> to use for timezone and locale.
* @return The parameter value as a <code>java.sql.Time</code>.
* @exception SQLException If an error occurs.
* @since 1.2
*/
- Time getTime(int parameterIndex, Calendar cal) throws SQLException;
+ Time getTime(int index, Calendar cal) throws SQLException;
/**
* This method returns the value of the specified parameter as a Java
@@ -329,7 +329,7 @@ public interface CallableStatement extends PreparedStatement
* @exception SQLException If an error occurs.
* @since 1.2
*/
- Timestamp getTimestamp(int parameterIndex, Calendar cal)
+ Timestamp getTimestamp(int index, Calendar cal)
throws SQLException;
/**
@@ -337,25 +337,24 @@ public interface CallableStatement extends PreparedStatement
* of the specified SQL type.
*
* @param index The index of the parameter to register as output.
- * @param type The SQL type value from <code>Types</code>.
- * @param name The user defined data type name.
+ * @param sqlType The SQL type value from <code>Types</code>.
+ * @param typeName The user defined data type name.
* @exception SQLException If an error occurs.
* @since 1.2
*/
- void registerOutParameter(int paramIndex, int sqlType,
- String typeName)
+ void registerOutParameter(int index, int sqlType, String typeName)
throws SQLException;
/**
* This method registers the specified parameter as an output parameter
* of the specified SQL type.
*
- * @param parameterName The name of the parameter to register as output.
+ * @param name The name of the parameter to register as output.
* @param sqlType The SQL type value from <code>Types</code>.
* @exception SQLException If an error occurs.
* @since 1.4
*/
- void registerOutParameter(String parameterName, int sqlType)
+ void registerOutParameter(String name, int sqlType)
throws SQLException;
/**
@@ -363,14 +362,13 @@ public interface CallableStatement extends PreparedStatement
* of the specified SQL type. This version of registerOutParameter is used
* for NUMERIC or DECIMAL types.
*
- * @param parameterName The name of the parameter to register as output.
+ * @param name The name of the parameter to register as output.
* @param sqlType The SQL type value from <code>Types</code>.
* @param scale Number of digits to the right of the decimal point.
* @exception SQLException If an error occurs.
* @since 1.4
*/
- void registerOutParameter(String parameterName, int sqlType,
- int scale)
+ void registerOutParameter(String name, int sqlType, int scale)
throws SQLException;
@@ -380,272 +378,584 @@ public interface CallableStatement extends PreparedStatement
* for user-named or REF types. If the type of the output parameter does
* not have such a type, the typeName argument is ignored.
*
- * @param parameterName The name of the parameter to register as output.
+ * @param name The name of the parameter to register as output.
* @param sqlType The SQL type value from <code>Types</code>.
* @param typeName The SQL structured type name.
* @exception SQLException If an error occurs.
* @since 1.4
*/
- void registerOutParameter(String parameterName, int sqlType,
- String typeName)
+ void registerOutParameter(String name, int sqlType, String typeName)
throws SQLException;
/**
+ * This method returns the value of the specified parameter as a Java
+ * <code>java.net.URL</code>.
+ *
+ * @param index The index of the parameter to return.
+ * @return The parameter value as a <code>URL</code>.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- URL getURL(int parameterIndex) throws SQLException;
+ URL getURL(int index) throws SQLException;
/**
+ * This method sets the value of the specified parameter to the specified
+ * <code>java.net.URL</code>
+ *
+ * @param name The name of the parameter to set.
+ * @param value The value the parameter.
* @since 1.4
*/
- void setURL(String parameterName, URL val) throws SQLException;
+ void setURL(String name, URL value) throws SQLException;
/**
+ * This method populates the specified parameter with a SQL NULL value
+ * for the specified type.
+ *
+ * @param name The name of the parameter to set.
+ * @param sqlType The SQL type identifier of the parameter from
+ * <code>Types</code>
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void setNull(String parameterName, int sqlType) throws SQLException;
+ void setNull(String name, int sqlType) throws SQLException;
/**
+ * This method sets the specified parameter from the given Java
+ * <code>boolean</code> value.
+ *
+ * @param name The name of the parameter value to set.
+ * @param value The value of the parameter.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void setBoolean(String parameterName, boolean x) throws SQLException;
+ void setBoolean(String name, boolean value) throws SQLException;
/**
+ * This method sets the specified parameter from the given Java
+ * <code>byte</code> value.
+ *
+ * @param name The name of the parameter value to set.
+ * @param value The value of the parameter.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void setByte(String parameterName, byte x) throws SQLException;
+ void setByte(String name, byte value) throws SQLException;
/**
+ * This method sets the specified parameter from the given Java
+ * <code>short</code> value.
+ *
+ * @param name The name of the parameter value to set.
+ * @param value The value of the parameter.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void setShort(String parameterName, short x) throws SQLException;
+ void setShort(String name, short value) throws SQLException;
/**
+ * This method sets the specified parameter from the given Java
+ * <code>int</code> value.
+ *
+ * @param name The name of the parameter value to set.
+ * @param value The value of the parameter.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void setInt(String parameterName, int x) throws SQLException;
+ void setInt(String name, int value) throws SQLException;
/**
+ * This method sets the specified parameter from the given Java
+ * <code>long</code> value.
+ *
+ * @param name The name of the parameter value to set.
+ * @param value The value of the parameter.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void setLong(String parameterName, long x) throws SQLException;
+ void setLong(String name, long value) throws SQLException;
/**
+ * This method sets the specified parameter from the given Java
+ * <code>float</code> value.
+ *
+ * @param name The name of the parameter value to set.
+ * @param value The value of the parameter.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void setFloat(String parameterName, float x) throws SQLException;
+ void setFloat(String name, float value) throws SQLException;
/**
+ * This method sets the specified parameter from the given Java
+ * <code>double</code> value.
+ *
+ * @param name The name of the parameter value to set.
+ * @param value The value of the parameter.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void setDouble(String parameterName, double x) throws SQLException;
+ void setDouble(String name, double value) throws SQLException;
/**
+ * This method sets the specified parameter from the given Java
+ * <code>BigDecimal</code> value.
+ *
+ * @param name The name of the parameter value to set.
+ * @param value The value of the parameter.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void setBigDecimal(String parameterName, BigDecimal x)
+ void setBigDecimal(String name, BigDecimal value)
throws SQLException;
/**
+ * This method sets the specified parameter from the given Java
+ * <code>String</code> value.
+ *
+ * @param name The name of the parameter value to set.
+ * @param value The value of the parameter.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void setString(String parameterName, String x) throws SQLException;
+ void setString(String name, String value) throws SQLException;
/**
+ * This method sets the specified parameter from the given Java
+ * <code>byte</code> array value.
+ *
+ * @param name The name of the parameter value to set.
+ * @param value The value of the parameter.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void setBytes(String parameterName, byte[] x) throws SQLException;
+ void setBytes(String name, byte[] value) throws SQLException;
/**
+ * This method sets the specified parameter from the given Java
+ * <code>java.sql.Date</code> value.
+ *
+ * @param name The name of the parameter value to set.
+ * @param value The value of the parameter.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void setDate(String parameterName, Date x) throws SQLException;
+ void setDate(String name, Date value) throws SQLException;
/**
+ * This method sets the specified parameter from the given Java
+ * <code>java.sql.Time</code> value.
+ *
+ * @param name The name of the parameter value to set.
+ * @param value The value of the parameter.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void setTime(String parameterName, Time x) throws SQLException;
+ void setTime(String name, Time value) throws SQLException;
/**
+ * This method sets the specified parameter from the given Java
+ * <code>java.sql.Timestamp</code> value.
+ *
+ * @param name The name of the parameter value to set.
+ * @param value The value of the parameter.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void setTimestamp(String parameterName, Timestamp x)
+ void setTimestamp(String name, Timestamp value)
throws SQLException;
/**
+ * This method sets the specified parameter from the given Java
+ * ASCII <code>InputStream</code> value.
+ *
+ * @param name The name of the parameter value to set.
+ * @param stream The stream from which the parameter value is read.
+ * @param count The number of bytes in the stream.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void setAsciiStream(String parameterName, InputStream x, int length)
+ void setAsciiStream(String name, InputStream stream, int count)
throws SQLException;
/**
+ * This method sets the specified parameter from the given Java
+ * binary <code>InputStream</code> value.
+ *
+ * @param name The name of the parameter value to set.
+ * @param stream The stream from which the parameter value is read.
+ * @param count The number of bytes in the stream.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void setBinaryStream(String parameterName, InputStream x, int length)
+ void setBinaryStream(String name, InputStream stream, int count)
throws SQLException;
/**
+ * This method sets the specified parameter from the given Java
+ * <code>Object</code> value. The specified SQL object type will be used.
+ *
+ * @param name The name of the parameter value to set.
+ * @param value The value of the parameter.
+ * @param sqlType The SQL type to use for the parameter, from
+ * <code>Types</code>
+ * @param scale The scale of the value, for numeric values only.
+ * @exception SQLException If an error occurs.
+ * @see Types
* @since 1.4
*/
- void setObject(String parameterName, Object x, int targetSqlType,
- int scale)
+ void setObject(String name, Object value, int sqlType, int scale)
throws SQLException;
/**
+ * This method sets the specified parameter from the given Java
+ * <code>Object</code> value. The specified SQL object type will be used.
+ *
+ * @param name The name of the parameter value to set.
+ * @param value The value of the parameter.
+ * @param sqlType The SQL type to use for the parameter, from
+ * <code>Types</code>
+ * @exception SQLException If an error occurs.
+ * @see Types
* @since 1.4
*/
- void setObject(String parameterName, Object x, int targetSqlType)
+ void setObject(String name, Object value, int sqlType)
throws SQLException;
/**
+ * This method sets the specified parameter from the given Java
+ * <code>Object</code> value. The default object type to SQL type mapping
+ * will be used.
+ *
+ * @param name The name of the parameter value to set.
+ * @param value The value of the parameter.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void setObject(String parameterName, Object x) throws SQLException;
+ void setObject(String name, Object value) throws SQLException;
/**
+ * This method sets the specified parameter from the given Java
+ * character <code>Reader</code> value.
+ *
+ * @param name The name of the parameter value to set.
+ * @param reader The reader from which the parameter value is read.
+ * @param count The number of characters in the stream.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void setCharacterStream(String parameterName, Reader reader,
- int length)
+ void setCharacterStream(String name, Reader reader, int count)
throws SQLException;
/**
+ * This method sets the specified parameter from the given Java
+ * <code>java.sql.Date</code> value.
+ *
+ * @param name The name of the parameter value to set.
+ * @param value The value of the parameter.
+ * @param cal The <code>Calendar</code> to use for timezone and locale.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void setDate(String parameterName, Date x, Calendar cal)
+ void setDate(String name, Date value, Calendar cal)
throws SQLException;
/**
+ * This method sets the specified parameter from the given Java
+ * <code>java.sql.Time</code> value.
+ *
+ * @param name The name of the parameter value to set.
+ * @param value The value of the parameter.
+ * @param cal The <code>Calendar</code> to use for timezone and locale.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void setTime(String parameterName, Time x, Calendar cal)
+ void setTime(String name, Time value, Calendar cal)
throws SQLException;
/**
+ * This method sets the specified parameter from the given Java
+ * <code>java.sql.Timestamp</code> value.
+ *
+ * @param name The name of the parameter value to set.
+ * @param value The value of the parameter.
+ * @param cal The <code>Calendar</code> to use for timezone and locale.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void setTimestamp(String parameterName, Timestamp x, Calendar cal)
+ void setTimestamp(String name, Timestamp value, Calendar cal)
throws SQLException;
/**
+ * This method populates the specified parameter with a SQL NULL value
+ * for the specified type.
+ *
+ * @param name The name of the parameter to set.
+ * @param sqlType The SQL type identifier of the parameter from
+ * <code>Types</code>
+ * @param typeName The name of the data type, for user defined types.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void setNull(String parameterName, int sqlType, String typeName)
+ void setNull(String name, int sqlType, String typeName)
throws SQLException;
/**
+ * This method returns the value of the specified parameter as a Java
+ * <code>String</code>.
+ *
+ * @param name The name of the parameter to return.
+ * @return The parameter value as a <code>String</code>.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- String getString(String parameterName) throws SQLException;
+ String getString(String name) throws SQLException;
/**
+ * This method returns the value of the specified parameter as a Java
+ * <code>boolean</code>.
+ *
+ * @param name The name of the parameter to return.
+ * @return The parameter value as a <code>boolean</code>.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- boolean getBoolean(String parameterName) throws SQLException;
+ boolean getBoolean(String name) throws SQLException;
/**
+ * This method returns the value of the specified parameter as a Java
+ * <code>byte</code>.
+ *
+ * @param name The name of the parameter to return.
+ * @return The parameter value as a <code>byte</code>.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- byte getByte(String parameterName) throws SQLException;
+ byte getByte(String name) throws SQLException;
/**
+ * This method returns the value of the specified parameter as a Java
+ * <code>short</code>.
+ *
+ * @param name The name of the parameter to return.
+ * @return The parameter value as a <code>short</code>.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- short getShort(String parameterName) throws SQLException;
+ short getShort(String name) throws SQLException;
/**
+ * This method returns the value of the specified parameter as a Java
+ * <code>int</code>.
+ *
+ * @param name The name of the parameter to return.
+ * @return The parameter value as a <code>int</code>.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- int getInt(String parameterName) throws SQLException;
+ int getInt(String name) throws SQLException;
/**
+ * This method returns the value of the specified parameter as a Java
+ * <code>long</code>.
+ *
+ * @param name The name of the parameter to return.
+ * @return The parameter value as a <code>long</code>.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- long getLong(String parameterName) throws SQLException;
+ long getLong(String name) throws SQLException;
/**
+ * This method returns the value of the specified parameter as a Java
+ * <code>float</code>.
+ *
+ * @param name The name of the parameter to return.
+ * @return The parameter value as a <code>float</code>.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- float getFloat(String parameterName) throws SQLException;
+ float getFloat(String name) throws SQLException;
/**
+ * This method returns the value of the specified parameter as a Java
+ * <code>double</code>.
+ *
+ * @param name The name of the parameter to return.
+ * @return The parameter value as a <code>double</code>.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- double getDouble(String parameterName) throws SQLException;
+ double getDouble(String name) throws SQLException;
/**
+ * This method returns the value of the specified parameter as a Java
+ * <code>byte</code> array.
+ *
+ * @param name The name of the parameter to return.
+ * @return The parameter value as a <code>byte[]</code>.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- byte[] getBytes(String parameterName) throws SQLException;
+ byte[] getBytes(String name) throws SQLException;
/**
+ * This method returns the value of the specified parameter as a Java
+ * <code>java.sql.Date</code>.
+ *
+ * @param name The name of the parameter to return.
+ * @return The parameter value as a <code>java.sql.Date</code>.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- Date getDate(String parameterName) throws SQLException;
+ Date getDate(String name) throws SQLException;
/**
+ * This method returns the value of the specified parameter as a Java
+ * <code>java.sql.Time</code>.
+ *
+ * @param name The name of the parameter to return.
+ * @return The parameter value as a <code>java.sql.Time</code>.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- Time getTime(String parameterName) throws SQLException;
+ Time getTime(String name) throws SQLException;
/**
+ * This method returns the value of the specified parameter as a Java
+ * <code>java.sql.Timestamp</code>.
+ *
+ * @param name The name of the parameter to return.
+ * @return The parameter value as a <code>java.sql.Timestamp</code>.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- Timestamp getTimestamp(String parameterName) throws SQLException;
+ Timestamp getTimestamp(String name) throws SQLException;
/**
+ * This method returns the value of the specified parameter as a Java
+ * <code>Object</code>.
+ *
+ * @param name The name of the parameter to return.
+ * @return The parameter value as a <code>Object</code>.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- Object getObject(String parameterName) throws SQLException;
+ Object getObject(String name) throws SQLException;
/**
+ * This method returns the value of the specified parameter as a Java
+ * <code>BigDecimal</code>.
+ *
+ * @param name The name of the parameter to return.
+ * @return The parameter value as a <code>BigDecimal</code>.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- BigDecimal getBigDecimal(String parameterName) throws SQLException;
+ BigDecimal getBigDecimal(String name) throws SQLException;
/**
+ * This method returns the value of the specified parameter as a Java
+ * <code>Object</code> using the specified mapping for conversion from
+ * SQL to Java types.
+ *
+ * @param name The name of the parameter to return.
+ * @param map The mapping to use for conversion from SQL to Java types.
+ * @return The parameter value as an <code>Object</code>.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- Object getObject(String parameterName, Map map) throws SQLException;
+ Object getObject(String name, Map map) throws SQLException;
/**
+ * This method returns the value of the specified parameter as a Java
+ * <code>Ref</code>.
+ *
+ * @param name The name of the parameter to return.
+ * @return The parameter value as a <code>Ref</code>.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- Ref getRef(String parameterName) throws SQLException;
+ Ref getRef(String name) throws SQLException;
/**
+ * This method returns the value of the specified parameter as a Java
+ * <code>Blob</code>.
+ *
+ * @param name The name of the parameter to return.
+ * @return The parameter value as a <code>Blob</code>.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- Blob getBlob(String parameterName) throws SQLException;
+ Blob getBlob(String name) throws SQLException;
/**
+ * This method returns the value of the specified parameter as a Java
+ * <code>Clob</code>.
+ *
+ * @param name The name of the parameter to return.
+ * @return The parameter value as a <code>Clob</code>.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- Clob getClob(String parameterName) throws SQLException;
+ Clob getClob(String name) throws SQLException;
/**
+ * This method returns the value of the specified parameter as a Java
+ * <code>Array</code>.
+ *
+ * @param name The name of the parameter to return.
+ * @return The parameter value as a <code>Array</code>.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- Array getArray(String parameterName) throws SQLException;
+ Array getArray(String name) throws SQLException;
/**
+ * This method returns the value of the specified parameter as a Java
+ * <code>java.sql.Date</code>.
+ *
+ * @param name The name of the parameter to return.
+ * @param cal The <code>Calendar</code> to use for timezone and locale.
+ * @return The parameter value as a <code>java.sql.Date</code>.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- Date getDate(String parameterName, Calendar cal) throws SQLException;
+ Date getDate(String name, Calendar cal) throws SQLException;
/**
+ * This method returns the value of the specified parameter as a Java
+ * <code>java.sql.Time</code>.
+ *
+ * @param name The name of the parameter to return.
+ * @param cal The <code>Calendar</code> to use for timezone and locale.
+ * @return The parameter value as a <code>java.sql.Time</code>.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- Time getTime(String parameterName, Calendar cal) throws SQLException;
+ Time getTime(String name, Calendar cal) throws SQLException;
/**
+ * This method returns the value of the specified parameter as a Java
+ * <code>java.sql.Timestamp</code>.
+ *
+ * @param name The name of the parameter to return.
+ * @param cal The <code>Calendar</code> to use for timezone and locale.
+ * @return The parameter value as a <code>java.sql.Timestamp</code>.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- Timestamp getTimestamp(String parameterName, Calendar cal)
+ Timestamp getTimestamp(String name, Calendar cal)
throws SQLException;
/**
+ * This method returns the value of the specified parameter as a Java
+ * <code>java.net.URL</code>.
+ *
+ * @param name The name of the parameter to return.
+ * @return The parameter value as a <code>java.net.URL</code>.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- URL getURL(String parameterName) throws SQLException;
+ URL getURL(String name) throws SQLException;
}
diff --git a/libjava/classpath/java/sql/Clob.java b/libjava/classpath/java/sql/Clob.java
index 8789da5967a..53bf6393cde 100644
--- a/libjava/classpath/java/sql/Clob.java
+++ b/libjava/classpath/java/sql/Clob.java
@@ -1,5 +1,5 @@
/* Clob.java -- Access Character Large OBjects
- Copyright (C) 1999, 2000, 2002 Free Software Foundation, Inc.
+ Copyright (C) 1999, 2000, 2002, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -35,6 +35,7 @@ this exception to your version of the library, but you are not
obligated to do so. If you do not wish to do so, delete this
exception statement from your version. */
+
package java.sql;
import java.io.InputStream;
@@ -43,110 +44,144 @@ import java.io.Reader;
import java.io.Writer;
/**
- * This interface contains methods for accessing a SQL CLOB (Character
- * Large OBject) type.
- *
+ * This interface contains methods for accessing a SQL CLOB (Character Large
+ * OBject) type.
+ *
* @author Aaron M. Renn (arenn@urbanophile.com)
*/
-public interface Clob
+public interface Clob
{
- /**
- * This method returns the number of characters in the CLOB.
- *
- * @return The number of characters in the CLOB.
- * @exception SQLException If an error occurs.
- * @since 1.2
- */
+ /**
+ * This method returns the number of characters in this <code>Clob</code>.
+ *
+ * @return The number of characters in this <code>Clob</code>.
+ * @exception SQLException If an error occurs.
+ * @since 1.2
+ */
long length() throws SQLException;
/**
- * This method returns the specified portion of the CLOB as a
- * <code>String</code>.
- *
- * @param offset The index into the CLOB (index values start at 1) to
- * start returning characters from.
- * @param length The requested number of characters to return.
- * @return The requested CLOB section, as a <code>String</code>.
+ * This method returns the specified portion of this <code>Clob</code> as a
+ * <code>String</code>.
+ *
+ * @param start The index into this <code>Clob</code> (index values
+ * start at 1) to start returning characters from.
+ * @param count The requested number of characters to return.
+ * @return The requested <code>Clob</code> section, as a <code>String</code>.
* @exception SQLException If an error occurs.
* @since 1.2
*/
- String getSubString(long pos, int length) throws SQLException;
+ String getSubString(long start, int count) throws SQLException;
/**
- * This method returns a character stream that reads the contents of the
- * CLOB.
- *
- * @return A character stream to read the CLOB's contents.
+ * This method returns a character stream that reads the contents of this
+ * <code>Clob</code>.
+ *
+ * @return A character stream to read this <code>Clob</code>'s contents.
* @exception SQLException If an error occurs.
* @since 1.2
*/
Reader getCharacterStream() throws SQLException;
/**
- * This method returns a byte stream that reads the contents of the
- * CLOB as a series of ASCII bytes.
- *
- * @return A stream to read the CLOB's contents.
+ * This method returns a byte stream that reads the contents of this
+ * <code>Clob</code> as a series of ASCII bytes.
+ *
+ * @return A stream to read this <code>Clob</code>'s contents.
* @exception SQLException If an error occurs.
* @since 1.2
*/
InputStream getAsciiStream() throws SQLException;
/**
- * This method returns the index into the CLOB of the first occurrence of
- * the specified character pattern (supplied by the caller as a
- * <code>String</code>). The search begins at the specified index.
- *
- * @param searchstr The character pattern to search for, passed as a
- * <code>String</code>.
- * @param start. The index into the CLOB to start search (indexes start
- * at 1).
- * @return The index at which the pattern was found (indexes start at 1),
- * or -1 if the pattern was not found.
+ * This method returns the index into this <code>Clob</code> of the first
+ * occurrence of the specified character pattern (supplied by the caller as a
+ * <code>String</code>). The search begins at the specified index.
+ *
+ * @param pattern The character pattern to search for, passed as a
+ * <code>String</code>.
+ * @param start The index into this <code>Clob</code> to start searching
+ * (indices start at 1).
+ * @return The index at which the pattern was found (indices start at 1), or
+ * -1 if the pattern was not found.
* @exception SQLException If an error occurs.
* @since 1.2
*/
- long position(String searchstr, long start) throws SQLException;
+ long position(String pattern, long start) throws SQLException;
/**
- * This method returns the index into the CLOB of the first occurrence of
- * the specified character pattern (supplied by the caller as a
- * <code>Clob</code>). The search begins at the specified index.
- *
- * @param searchstr The character pattern to search for, passed as a
- * <code>Clob</code>.
- * @param start. The index into the CLOB to start search (indexes start
- * at 1).
- * @return The index at which the pattern was found (indexes start at 1),
- * or -1 if the pattern was not found.
+ * This method returns the index into this <code>Clob</code> of the first
+ * occurrence of the specified character pattern (supplied by the caller as a
+ * <code>Clob</code>). The search begins at the specified index.
+ *
+ * @param pattern The character pattern to search for, passed as a
+ * <code>Clob</code>.
+ * @param start The index into this <code>Clob</code> to start searching
+ * (indices start at 1).
+ * @return The index at which the pattern was found (indices start at 1), or
+ * -1 if the pattern was not found.
* @exception SQLException If an error occurs.
* @since 1.2
*/
- long position(Clob searchstr, long start) throws SQLException;
+ long position(Clob pattern, long start) throws SQLException;
/**
+ * Writes the specified string into this <code>Clob</code>, starting at the
+ * specified index.
+ *
+ * @param start The index at which the writing starts.
+ * @param value The string to write.
+ * @return The number of characters written.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- int setString(long pos, String str) throws SQLException;
+ int setString(long start, String value) throws SQLException;
/**
+ * Writes the specified portion of a string into this <code>Clob</code>,
+ * starting at the specified index.
+ *
+ * @param startWrite The index at which the writing starts.
+ * @param value The string to write a portion of.
+ * @param startRead The offset into the string where the portion to copy
+ * starts.
+ * @param count The number of characters to write.
+ * @return The number of characters written.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- int setString(long pos, String str, int offset, int len)
- throws SQLException;
+ int setString(long startWrite, String value, int startRead, int count)
+ throws SQLException;
/**
+ * Returns an ASCII text stream that writes into this <code>Clob</code>,
+ * starting at the specified index.
+ *
+ * @param start The index at which the writing starts.
+ * @return An ASCII text stream to write into this <code>Clob</code>.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- OutputStream setAsciiStream(long pos) throws SQLException;
+ OutputStream setAsciiStream(long start) throws SQLException;
/**
+ * Returns a character stream that writes into this <code>Clob</code>,
+ * starting at the specified index.
+ *
+ * @param start The index at which the writing starts.
+ * @return A character stream to write into this <code>Clob</code>.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- Writer setCharacterStream(long pos) throws SQLException;
+ Writer setCharacterStream(long start) throws SQLException;
/**
+ * Truncates this <code>Clob</code> to be at most the specified number of
+ * characters long.
+ *
+ * @param count The length this <code>Clob</code> is truncated to.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void truncate(long len) throws SQLException;
+ void truncate(long count) throws SQLException;
}
diff --git a/libjava/classpath/java/sql/Connection.java b/libjava/classpath/java/sql/Connection.java
index 48ec12dd09f..d827e75b089 100644
--- a/libjava/classpath/java/sql/Connection.java
+++ b/libjava/classpath/java/sql/Connection.java
@@ -1,5 +1,5 @@
/* Connection.java -- Manage a database connection.
- Copyright (C) 1999, 2000, 2002 Free Software Foundation, Inc.
+ Copyright (C) 1999, 2000, 2002, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -61,7 +61,7 @@ public interface Connection
int TRANSACTION_READ_UNCOMMITTED = 1;
/**
- * This transaction isolation leve indicates that only committed data from
+ * This transaction isolation level indicates that only committed data from
* other transactions will be read. If a transaction reads a row, then
* another transaction commits a change to that row, the first transaction
* would retrieve the changed row on subsequent reads of the same row.
@@ -101,8 +101,8 @@ public interface Connection
* SQL string. This method is designed for use with parameterized
* statements. The default result set type and concurrency will be used.
*
- * @param The SQL statement to use in creating this
- * <code>PreparedStatement</code>.
+ * @param sql The SQL statement to use in creating this
+ * <code>PreparedStatement</code>.
* @return A new <code>PreparedStatement</code>.
* @exception SQLException If an error occurs.
* @see PreparedStatement
@@ -115,8 +115,8 @@ public interface Connection
* stored procedures. The default result set type and concurrency
* will be used.
*
- * @param The SQL statement to use in creating this
- * <code>CallableStatement</code>.
+ * @param sql The SQL statement to use in creating this
+ * <code>CallableStatement</code>.
* @return A new <code>CallableStatement</code>.
* @exception SQLException If an error occurs.
* @see CallableStatement
@@ -127,7 +127,7 @@ public interface Connection
* This method converts the specified generic SQL statement into the
* native grammer of the database this object is connected to.
*
- * @param The JDBC generic SQL statement.
+ * @param sql The JDBC generic SQL statement.
* @return The native SQL statement.
* @exception SQLException If an error occurs.
*/
@@ -139,10 +139,10 @@ public interface Connection
* transaction must be explicitly committed or rolled back.
*
* @param autoCommit <code>true</code> to enable auto commit mode,
- * <code>false</code> to disable it.
+ * <code>false</code> to disable it.
* @exception SQLException If an error occurs.
- * @see commit
- * @see rollback
+ * @see #commit()
+ * @see #rollback()
*/
void setAutoCommit(boolean autoCommit) throws SQLException;
@@ -152,12 +152,10 @@ public interface Connection
* Otherwise a transaction must be explicitly committed or rolled back.
*
* @return <code>true</code> if auto commit mode is enabled,
- * <code>false</code> otherwise.
- *
+ * <code>false</code> otherwise.
* @exception SQLException If an error occurs.
- *
- * @see commit
- * @see rollback
+ * @see #commit()
+ * @see #rollback()
*/
boolean getAutoCommit() throws SQLException;
@@ -207,7 +205,7 @@ public interface Connection
* a transaction is in progress.
*
* @param readOnly <code>true</code> if this connection is read only,
- * <code>false</code> otherwise.
+ * <code>false</code> otherwise.
* @exception SQLException If an error occurs.
*/
void setReadOnly(boolean readOnly) throws SQLException;
@@ -235,8 +233,8 @@ public interface Connection
* This method returns the name of the catalog in use by this connection,
* if any.
*
- * @return The name of the catalog, or <code>null</code> if one does not
- * exist or catalogs are not supported by this database.
+ * @return The name of the catalog, or <code>null</code> if none
+ * exists or catalogs are not supported by this database.
* @exception SQLException If an error occurs.
*/
String getCatalog() throws SQLException;
@@ -283,8 +281,8 @@ public interface Connection
* <code>ResultSet</code> class.
*
* @param resultSetType The type of result set to use for this statement.
- * @param resultSetConcurrency. The type of concurrency to be used in
- * the result set for this statement.
+ * @param resultSetConcurrency The type of concurrency to be used in
+ * the result set for this statement.
* @return A new <code>Statement</code> object.
* @exception SQLException If an error occurs.
* @see Statement
@@ -300,11 +298,11 @@ public interface Connection
* Valid values for these parameters are specified in the
* <code>ResultSet</code> class.
*
- * @param The SQL statement to use in creating this
- * <code>PreparedStatement</code>.
+ * @param sql The SQL statement to use in creating this
+ * <code>PreparedStatement</code>.
* @param resultSetType The type of result set to use for this statement.
- * @param resultSetConcurrency. The type of concurrency to be used in
- * the result set for this statement.
+ * @param resultSetConcurrency The type of concurrency to be used in
+ * the result set for this statement.
* @return A new <code>PreparedStatement</code>.
* @exception SQLException If an error occurs.
* @see PreparedStatement
@@ -320,11 +318,11 @@ public interface Connection
* will be used. Valid values for these parameters are specified in the
* <code>ResultSet</code> class.
*
- * @param The SQL statement to use in creating this
- * <code>PreparedStatement</code>.
+ * @param sql The SQL statement to use in creating this
+ * <code>PreparedStatement</code>.
* @param resultSetType The type of result set to use for this statement.
- * @param resultSetConcurrency. The type of concurrency to be used in
- * the result set for this statement.
+ * @param resultSetConcurrency The type of concurrency to be used in
+ * the result set for this statement.
* @return A new <code>CallableStatement</code>.
* @exception SQLException If an error occurs.
* @see CallableStatement
@@ -353,48 +351,130 @@ public interface Connection
void setTypeMap(Map map) throws SQLException;
/**
+ * Sets the default holdability of <code>ResultSet</code>S that are created
+ * from <code>Statement</code>S using this <code>Connection</code>.
+ *
+ * @param holdability The default holdability value to set, this must be one
+ * of <code>ResultSet.HOLD_CURSORS_OVER_COMMIT</code> or
+ * <code>ResultSet.CLOSE_CURSORS_AT_COMMIT</code>.
+ * @exception SQLException If an error occurs.
+ * @see ResultSet
* @since 1.4
*/
void setHoldability(int holdability) throws SQLException;
/**
+ * Gets the default holdability of <code>ResultSet</code>S that are created
+ * from <code>Statement</code>S using this <code>Connection</code>.
+ *
+ * @return The current default holdability value, this must be one of
+ * <code>ResultSet.HOLD_CURSORS_OVER_COMMIT</code> or
+ * <code>ResultSet.CLOSE_CURSORS_AT_COMMIT</code>.
+ * @exception SQLException If an error occurs.
+ * @see ResultSet
* @since 1.4
*/
int getHoldability() throws SQLException;
/**
+ * Creates a new unnamed savepoint for this <code>Connection</code>
+ *
+ * @return The <code>Savepoint</code> object representing the savepoint.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
Savepoint setSavepoint() throws SQLException;
/**
+ * Creates a new savepoint with the specifiend name for this
+ * <code>Connection</code>.
+ *
+ * @param name The name of the savepoint.
+ * @return The <code>Savepoint</code> object representing the savepoint.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
Savepoint setSavepoint(String name) throws SQLException;
/**
+ * Undoes all changes made after the specified savepoint was set.
+ *
+ * @param savepoint The safepoint to roll back to.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
void rollback(Savepoint savepoint) throws SQLException;
/**
+ * Removes the specified savepoint from this <code>Connection</code>.
+ * Refering to a savepoint after it was removed is an error and will throw an
+ * SQLException.
+ *
+ * @param savepoint The savepoint to release.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
void releaseSavepoint(Savepoint savepoint) throws SQLException;
/**
+ * This method creates a new SQL statement with the specified type,
+ * concurrency and holdability, instead of using the defaults. Valid values
+ * for these parameters are specified in the <code>ResultSet</code> class.
+ *
+ * @param resultSetType The type of result set to use for this statement.
+ * @param resultSetConcurrency The type of concurrency to be used in
+ * the result set for this statement.
+ * @param resultSetHoldability The type of holdability to be usd in the
+ * result set for this statement.
+ * @return A new <code>Statement</code>
+ * @exception SQLException If an error occurs.
+ * @see ResultSet
* @since 1.4
*/
Statement createStatement(int resultSetType, int
resultSetConcurrency, int resultSetHoldability) throws SQLException;
/**
+ * This method creates a new <code>PreparedStatement</code> for the specified
+ * SQL string. This method is designed for use with parameterized
+ * statements. The specified result set type, concurrency and holdability
+ * will be used. Valid values for these parameters are specified in the
+ * <code>ResultSet</code> class.
+ *
+ * @param sql The SQL statement to use in creating this
+ * <code>PreparedStatement</code>.
+ * @param resultSetType The type of result set to use for this statement.
+ * @param resultSetConcurrency The type of concurrency to be used in
+ * the result set for this statement.
+ * @param resultSetHoldability The type of holdability to be usd in the
+ * result set for this statement.
+ * @return A new <code>PreparedStatement</code>.
+ * @exception SQLException If an error occurs.
+ * @see PreparedStatement
+ * @see ResultSet
* @since 1.4
*/
PreparedStatement prepareStatement(String sql, int resultSetType, int
resultSetConcurrency, int resultSetHoldability) throws SQLException;
/**
+ * This method creates a new <code>CallableStatement</code> for the
+ * specified SQL string. Thie method is designed to be used with
+ * stored procedures. The specified result set type, concurrency and
+ * holdability will be used. Valid values for these parameters are specified
+ * in the <code>ResultSet</code> class.
+ *
+ * @param sql The SQL statement to use in creating this
+ * <code>PreparedStatement</code>.
+ * @param resultSetType The type of result set to use for this statement.
+ * @param resultSetConcurrency The type of concurrency to be used in
+ * the result set for this statement.
+ * @param resultSetHoldability The type of holdability to be used in the
+ * result set for this statement.
+ * @return A new <code>CallableStatement</code>.
+ * @exception SQLException If an error occurs.
+ * @see CallableStatement
+ * @see ResultSet
* @since 1.4
*/
CallableStatement prepareCall(String sql, int resultSetType, int
diff --git a/libjava/classpath/java/sql/DatabaseMetaData.java b/libjava/classpath/java/sql/DatabaseMetaData.java
index d34c4e2f927..48c2d9afcd8 100644
--- a/libjava/classpath/java/sql/DatabaseMetaData.java
+++ b/libjava/classpath/java/sql/DatabaseMetaData.java
@@ -1,5 +1,5 @@
/* DatabaseMetaData.java -- Information about the database itself.
- Copyright (C) 1999, 2000, 2001, 2002 Free Software Foundation, Inc.
+ Copyright (C) 1999, 2000, 2001, 2002, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -256,10 +256,19 @@ public interface DatabaseMetaData
*/
short tableIndexOther = 3;
+ /**
+ * A NULL value is not allowed for this attribute.
+ */
short attributeNoNulls = 0;
+ /**
+ * A NULL value is allowed for this attribute.
+ */
short attributeNullable = 1;
+ /**
+ * It is unknown whether or not NULL values are allowed for this attribute.
+ */
short attributeNullableUnknown = 2;
int sqlStateXOpen = 1;
@@ -1395,12 +1404,12 @@ public interface DatabaseMetaData
* or "" to return procedures from all catalogs.
* @param schemaPattern A schema pattern for the schemas to return stored
* procedures from, or "" to return procedures from all schemas.
- * @param namePattern The pattern of procedures names to return.
+ * @param procedurePattern The pattern of procedure names to return.
* @returns A <code>ResultSet</code> with all the requested procedures.
* @exception SQLException If an error occurs.
*/
ResultSet getProcedures(String catalog, String schemaPattern, String
- procedureNamePattern) throws SQLException;
+ procedurePattern) throws SQLException;
/**
* This method returns a list of the parameter and result columns for
@@ -1436,13 +1445,13 @@ public interface DatabaseMetaData
* or "" to return procedures from all catalogs.
* @param schemaPattern A schema pattern for the schemas to return stored
* procedures from, or "" to return procedures from all schemas.
- * @param namePattern The pattern of procedures names to return.
+ * @param procedurePattern The pattern of procedures names to return.
* @param columnPattern The pattern of column names to return.
* @returns A <code>ResultSet</code> with all the requested procedures.
* @exception SQLException If an error occurs.
*/
ResultSet getProcedureColumns(String catalog, String schemaPattern,
- String procedureNamePattern, String columnNamePattern) throws
+ String procedurePattern, String columnPattern) throws
SQLException;
/**
@@ -1462,13 +1471,13 @@ public interface DatabaseMetaData
* or "" to return tables from all catalogs.
* @param schemaPattern A schema pattern for the schemas to return tables
* from, or "" to return tables from all schemas.
- * @param namePattern The pattern of table names to return.
+ * @param tablePattern The pattern of table names to return.
* @param types The list of table types to include; null returns all types.
* @returns A <code>ResultSet</code> with all the requested tables.
* @exception SQLException If an error occurs.
*/
ResultSet getTables(String catalog, String schemaPattern, String
- tableNamePattern, String[] types) throws SQLException;
+ tablePattern, String[] types) throws SQLException;
/**
* This method returns the list of database schemas as a
@@ -1536,13 +1545,13 @@ public interface DatabaseMetaData
* or "" to return tables from all catalogs.
* @param schemaPattern A schema pattern for the schemas to return
* tables from, or "" to return tables from all schemas.
- * @param namePattern The pattern of tables names to return.
+ * @param tablePattern The pattern of table names to return.
* @param columnPattern The pattern of column names to return.
* @returns A <code>ResultSet</code> with all the requested tables.
* @exception SQLException If an error occurs.
*/
ResultSet getColumns(String catalog, String schemaPattern, String
- tableNamePattern, String columnNamePattern) throws SQLException;
+ tablePattern, String columnPattern) throws SQLException;
/**
* This method returns the access rights that have been granted to the
@@ -1568,13 +1577,13 @@ public interface DatabaseMetaData
* to return information from all catalogs.
* @param schema The schema to retrieve information from, or the empty string
* to return entities not associated with a schema.
- * @param table The table name to return information for.
+ * @param tableName The table name to return information for.
* @param columnPattern A pattern of column names to return information for.
* @return A <code>ResultSet</code> with all the requested privileges.
* @exception SQLException If an error occurs.
*/
ResultSet getColumnPrivileges(String catalog, String schema, String
- table, String columnNamePattern) throws SQLException;
+ tableName, String columnPattern) throws SQLException;
/**
* This method returns the access rights that have been granted to the
@@ -1597,7 +1606,7 @@ public interface DatabaseMetaData
* @param catalog The catalog to retrieve information from, or the empty string
* to return entities not associated with a catalog, or <code>null</code>
* to return information from all catalogs.
- * @param schema The schema to retrieve information from, or the empty string
+ * @param schemaPattern The schema to retrieve information from, or the empty string
* to return entities not associated with a schema.
* @param tablePattern The table name pattern of tables to return
* information for.
@@ -1605,7 +1614,7 @@ public interface DatabaseMetaData
* @exception SQLException If an error occurs.
*/
ResultSet getTablePrivileges(String catalog, String schemaPattern,
- String tableNamePattern) throws SQLException;
+ String tablePattern) throws SQLException;
/**
* This method returns the best set of columns for uniquely identifying
@@ -1634,8 +1643,7 @@ public interface DatabaseMetaData
* to return information from all catalogs.
* @param schema The schema to retrieve information from, or the empty string
* to return entities not associated with a schema.
- * @param table The table name to return information for.
- * @param columnPattern A pattern of column names to return information for.
+ * @param tableName The table name to return information for.
* @param scope One of the best row id scope constants from this class.
* @param nullable <code>true</code> to include columns that are nullable,
* <code>false</code> otherwise.
@@ -1643,7 +1651,7 @@ public interface DatabaseMetaData
* @exception SQLException If an error occurs.
*/
ResultSet getBestRowIdentifier(String catalog, String schema,
- String table, int scope, boolean nullable) throws SQLException;
+ String tableName, int scope, boolean nullable) throws SQLException;
/**
* This method returns the set of columns that are automatically updated
@@ -1670,13 +1678,12 @@ public interface DatabaseMetaData
* to return information from all catalogs.
* @param schema The schema to retrieve information from, or the empty string
* to return entities not associated with a schema.
- * @param table The table name to return information for.
- * @param columnPattern A pattern of column names to return information for.
+ * @param tableName The table name to return information for
* @return A <code>ResultSet</code> with the version columns.
* @exception SQLException If an error occurs.
*/
ResultSet getVersionColumns(String catalog, String schema,
- String table) throws SQLException;
+ String tableName) throws SQLException;
/**
* This method returns a list of a table's primary key columns. These
@@ -1696,12 +1703,11 @@ public interface DatabaseMetaData
* to return information from all catalogs.
* @param schema The schema to retrieve information from, or the empty string
* to return entities not associated with a schema.
- * @param table The table name to return information for.
- * @param columnPattern A pattern of column names to return information for.
+ * @param tableName The table name to return information for.
* @return A <code>ResultSet</code> with the primary key columns.
* @exception SQLException If an error occurs.
*/
- ResultSet getPrimaryKeys(String catalog, String schema, String table)
+ ResultSet getPrimaryKeys(String catalog, String schema, String tableName)
throws SQLException;
/**
@@ -1740,14 +1746,12 @@ public interface DatabaseMetaData
* to return information from all catalogs.
* @param schema The schema to retrieve information from, or the empty string
* to return entities not associated with a schema.
- * @param table The table name to return information for.
- *
+ * @param tableName The table name to return information for.
* @return A <code>ResultSet</code> with the foreign key columns.
- *
* @exception SQLException If an error occurs.
*/
ResultSet getImportedKeys(String catalog, String schema,
- String table) throws SQLException;
+ String tableName) throws SQLException;
/**
* This method returns a list of the table's which use this table's
@@ -1786,12 +1790,12 @@ public interface DatabaseMetaData
* to return information from all catalogs.
* @param schema The schema to retrieve information from, or the empty string
* to return entities not associated with a schema.
- * @param table The table name to return information for.
+ * @param tableName The table name to return information for.
* @return A <code>ResultSet</code> with the requested information
* @exception SQLException If an error occurs.
*/
ResultSet getExportedKeys(String catalog, String schema,
- String table) throws SQLException;
+ String tableName) throws SQLException;
/**
* This method returns a description of how one table imports another
@@ -1825,26 +1829,30 @@ public interface DatabaseMetaData
* <code>importedKeyNotDeferrable</code>).</li>
* </ol>
*
- * @param primCatalog The catalog to retrieve information from, or the empty string
- * to return entities not associated with a catalog, or <code>null</code>
- * to return information from all catalogs, on the exporting side.
- * @param primSchema The schema to retrieve information from, or the empty string
- * to return entities not associated with a schema, on the exporting side.
- * @param primTable The table name to return information for, on the exporting
- * side.
- * @param forCatalog The catalog to retrieve information from, or the empty string
- * to return entities not associated with a catalog, or <code>null</code>
- * to return information from all catalogs, on the importing side.
- * @param forSchema The schema to retrieve information from, or the empty string
- * to return entities not associated with a schema on the importing side.
- * @param forTable The table name to return information for on the importing
- * side.
+ * @param primaryCatalog The catalog to retrieve information from, or the
+ * empty string to return entities not associated with a catalog, or
+ * <code>null</code> to return information from all catalogs, on the
+ * exporting side.
+ * @param primarySchema The schema to retrieve information from, or the empty
+ * string to return entities not associated with a schema, on the
+ * exporting side.
+ * @param primaryTableName The table name to return information for, on the
+ * exporting side.
+ * @param foreignCatalog The catalog to retrieve information from, or the
+ * empty string to return entities not associated with a catalog,
+ * or <code>null</code> to return information from all catalogs, on
+ * the importing side.
+ * @param foreignSchema The schema to retrieve information from, or the
+ * empty string to return entities not associated with a schema on
+ * the importing side.
+ * @param foreignTableName The table name to return information for on the
+ * importing side.
* @return A <code>ResultSet</code> with the requested information
* @exception SQLException If an error occurs.
*/
ResultSet getCrossReference(String primaryCatalog, String
- primarySchema, String primaryTable, String foreignCatalog, String
- foreignSchema, String foreignTable) throws SQLException;
+ primarySchema, String primaryTableName, String foreignCatalog, String
+ foreignSchema, String foreignTableName) throws SQLException;
/**
* This method returns a list of the SQL types supported by this
@@ -1921,15 +1929,15 @@ public interface DatabaseMetaData
* <code>null</code> to return information from all catalogs.
* @param schema The schema to retrieve information from, or the empty string
* to return entities not associated with a schema.
- * @param table The table name to return information for.
+ * @param tableName The table name to return information for.
* @param unique <code>true</code> to return only unique indexes,
* <code>false</code> otherwise.
- * @param approx <code>true</code> if data values can be approximations,
+ * @param approximate <code>true</code> if data values can be approximations,
* <code>false</code> otherwise.
* @return A <code>ResultSet</code> with the requested index information
* @exception SQLException If an error occurs.
*/
- ResultSet getIndexInfo(String catalog, String schema, String table,
+ ResultSet getIndexInfo(String catalog, String schema, String tableName,
boolean unique, boolean approximate) throws SQLException;
/**
@@ -1954,8 +1962,8 @@ public interface DatabaseMetaData
*
* @param type The desired result type, which is one of the constants
* defined in <code>ResultSet</code>.
- * @param concur The desired concurrency type, which is one of the constants
- * defined in <code>ResultSet</code>.
+ * @param concurrency The desired concurrency type, which is one of the
+ * constants defined in <code>ResultSet</code>.
* @return <code>true</code> if the result set type is supported,
* <code>false</code> otherwise.
* @exception SQLException If an error occurs.
@@ -2108,8 +2116,8 @@ public interface DatabaseMetaData
* @param catalog The catalog to retrieve information from, or the empty string
* to return entities not associated with a catalog, or <code>null</code>
* to return information from all catalogs.
- * @param schema The schema to retrieve information from, or the empty string
- * to return entities not associated with a schema.
+ * @param schemaPattern The schema to retrieve information from, or the
+ * empty string to return entities not associated with a schema.
* @param typePattern The type name pattern to match.
* @param types The type identifier patterns (from <code>Types</code>) to
* match.
@@ -2117,7 +2125,7 @@ public interface DatabaseMetaData
* @exception SQLException If an error occurs.
*/
ResultSet getUDTs(String catalog, String schemaPattern, String
- typeNamePattern, int[] types) throws SQLException;
+ typePattern, int[] types) throws SQLException;
/**
* This method returns the <code>Connection</code> object that was used
@@ -2129,16 +2137,33 @@ public interface DatabaseMetaData
Connection getConnection() throws SQLException;
/**
+ * This method tests whether the databse supports savepoints.
+ *
+ * @return <code>true</code> if the database supports savepoints,
+ * <code>false</code> if it does not.
+ * @exception SQLException If an error occurs.
+ * @see Savepoint
* @since 1.4
*/
boolean supportsSavepoints() throws SQLException;
/**
+ * This method tests whether the database supports named parameters.
+ *
+ * @return <code>true</code> if the database supports named parameters,
+ * <code>false</code> if it does not.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
boolean supportsNamedParameters() throws SQLException;
/**
+ * This method tests whether the database supports returning multiple
+ * <code>ResultSet</code>S from a <code>CallableStatement</code> at once.
+ *
+ * @return <code>true</code> if the database supports returnig multiple
+ * results at once, <code>false</code> if it does not.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
boolean supportsMultipleOpenResults() throws SQLException;
@@ -2152,47 +2177,78 @@ public interface DatabaseMetaData
* @since 1.4
*/
ResultSet getSuperTypes(String catalog, String schemaPattern,
- String typeNamePattern) throws SQLException;
+ String typePattern) throws SQLException;
/**
* @since 1.4
*/
ResultSet getSuperTables(String catalog, String schemaPattern,
- String tableNamePattern) throws SQLException;
+ String tablePattern) throws SQLException;
/**
* @since 1.4
*/
ResultSet getAttributes(String catalog, String schemaPattern, String
- typeNamePattern, String attributeNamePattern) throws SQLException;
+ typePattern, String attributePattern) throws SQLException;
/**
+ * This method tests if the database supports the specified holdability type.
+ * Valid values for this parameter are specified in the
+ * <code>ResultSet</code> class.
+ *
+ * @param holdability The holdability type to test.
+ * @return <code>true</code> if the database supports the holdability type,
+ * <code>false</code> if it does not.
+ * @exception SQLException If an error occurs.
+ * @see ResultSet
* @since 1.4
*/
boolean supportsResultSetHoldability(int holdability)
throws SQLException;
/**
+ * This method returns the default holdability type of <code>ResultSet</code>S
+ * retrieved from this database. The possible values are specified in the
+ * <code>ResultSet</code> class.
+ *
+ * @return The default holdability type.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
int getResultSetHoldability() throws SQLException;
/**
+ * This method returns the major version number of the database.
+ *
+ * @return The major version number of the database.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
int getDatabaseMajorVersion() throws SQLException;
/**
+ * This method returns the minor version number of the database.
+ *
+ * @return The minor version number of the database.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
int getDatabaseMinorVersion() throws SQLException;
/**
+ * This method returns the major version number of the JDBC driver.
+ *
+ * @return The major version number of the JDBC driver.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
int getJDBCMajorVersion() throws SQLException;
/**
+ * This method returns the minor version number of the JDBC driver.
+ *
+ * @return The minor version number of the database.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
int getJDBCMinorVersion() throws SQLException;
diff --git a/libjava/classpath/java/sql/Date.java b/libjava/classpath/java/sql/Date.java
index d429cc8267d..f4c3307092e 100644
--- a/libjava/classpath/java/sql/Date.java
+++ b/libjava/classpath/java/sql/Date.java
@@ -1,5 +1,5 @@
/* Date.java -- Wrapper around java.util.Date
- Copyright (C) 1999, 2000, 2003, 2005 Free Software Foundation, Inc.
+ Copyright (C) 1999, 2000, 2003, 2005, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -72,10 +72,10 @@ public class Date extends java.util.Date
/**
* This method initializes a new instance of this class with the
- * specified time value representing the number of seconds since
+ * specified time value representing the number of milliseconds since
* Jan 1, 1970 at 12:00 midnight GMT.
*
- * @param time The time value to intialize this date to.
+ * @param date The time value to intialize this date to.
*/
public Date(long date)
{
diff --git a/libjava/classpath/java/sql/Driver.java b/libjava/classpath/java/sql/Driver.java
index 10f83ef2f8b..277dd171360 100644
--- a/libjava/classpath/java/sql/Driver.java
+++ b/libjava/classpath/java/sql/Driver.java
@@ -1,5 +1,5 @@
/* Driver.java -- A JDBC driver
- Copyright (C) 1999, 2000 Free Software Foundation, Inc.
+ Copyright (C) 1999, 2000, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -68,7 +68,7 @@ public interface Driver
* connection, or <code>null</code> if the URL is not understood.
* @exception SQLException If an error occurs.
*/
- Connection connect(String url, Properties info) throws SQLException;
+ Connection connect(String url, Properties properties) throws SQLException;
/**
* This method tests whether or not the driver believes it can connect to
@@ -76,7 +76,7 @@ public interface Driver
* understands and accepts the URL. It should not necessarily attempt to
* probe the database for a connection.
*
- * @param The database URL string.
+ * @param url The database URL string.
* @return <code>true</code> if the drivers can connect to the database,
* <code>false</code> otherwise.
* @exception SQLException If an error occurs.
diff --git a/libjava/classpath/java/sql/DriverManager.java b/libjava/classpath/java/sql/DriverManager.java
index 9e252abcc60..94f743b92da 100644
--- a/libjava/classpath/java/sql/DriverManager.java
+++ b/libjava/classpath/java/sql/DriverManager.java
@@ -1,5 +1,6 @@
/* DriverManager.java -- Manage JDBC drivers
- Copyright (C) 1999, 2000, 2001, 2003, 2004 Free Software Foundation, Inc.
+ Copyright (C) 1999, 2000, 2001, 2003, 2004, 2006
+ Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -292,11 +293,11 @@ public class DriverManager
* This method set the login timeout used by JDBC drivers. This is a
* system-wide parameter that applies to all drivers.
*
- * @param login_timeout The new login timeout value.
+ * @param seconds The new login timeout value.
*/
public static void setLoginTimeout(int seconds)
{
- DriverManager.login_timeout = login_timeout;
+ DriverManager.login_timeout = seconds;
}
/**
@@ -312,20 +313,18 @@ public class DriverManager
/**
* This method sets the log stream in use by JDBC.
*
- * @param log_stream The log stream in use by JDBC.
- *
+ * @param stream The log stream in use by JDBC.
* @deprecated Use <code>setLogWriter</code> instead.
*/
- public static void setLogStream(PrintStream out)
+ public static void setLogStream(PrintStream stream)
{
- DriverManager.log_stream = log_stream;
+ DriverManager.log_stream = stream;
}
/**
* This method returns the log stream in use by JDBC.
*
* @return The log stream in use by JDBC.
- *
* @deprecated Use <code>getLogWriter()</code> instead.
*/
public static PrintStream getLogStream()
@@ -336,7 +335,7 @@ public class DriverManager
/**
* This method prints the specified line to the log stream.
*
- * @param str The string to write to the log stream.
+ * @param message The string to write to the log stream.
*/
public static void println(String message)
{
diff --git a/libjava/classpath/java/sql/PreparedStatement.java b/libjava/classpath/java/sql/PreparedStatement.java
index 3aedbc59300..ca7eb2c5d79 100644
--- a/libjava/classpath/java/sql/PreparedStatement.java
+++ b/libjava/classpath/java/sql/PreparedStatement.java
@@ -1,5 +1,5 @@
/* PreparedStatement.java -- Interface for pre-compiled statements.
- Copyright (C) 1999, 2000 Free Software Foundation, Inc.
+ Copyright (C) 1999, 2000, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -48,6 +48,8 @@ import java.util.Calendar;
* statements. This provides greater efficiency when calling the same
* statement multiple times. Parameters are allowed in a statement,
* providings for maximum reusability.
+ *
+ * <p> Note that in this class parameter indices start at 1, not 0.</p>
*
* @author Aaron M. Renn (arenn@urbanophile.com)
*/
@@ -76,11 +78,12 @@ public interface PreparedStatement extends Statement
* for the specified type.
*
* @param index The index of the parameter to set.
- * @param type The SQL type identifier of the parameter from <code>Types</code>
+ * @param sqlType The SQL type identifier of the parameter from
+ * <code>Types</code>
*
* @exception SQLException If an error occurs.
*/
- void setNull(int parameterIndex, int sqlType) throws SQLException;
+ void setNull(int index, int sqlType) throws SQLException;
/**
* This method sets the specified parameter from the given Java
@@ -90,7 +93,7 @@ public interface PreparedStatement extends Statement
* @param value The value of the parameter.
* @exception SQLException If an error occurs.
*/
- void setBoolean(int parameterIndex, boolean x) throws SQLException;
+ void setBoolean(int index, boolean value) throws SQLException;
/**
* This method sets the specified parameter from the given Java
@@ -100,7 +103,7 @@ public interface PreparedStatement extends Statement
* @param value The value of the parameter.
* @exception SQLException If an error occurs.
*/
- void setByte(int parameterIndex, byte x) throws SQLException;
+ void setByte(int index, byte value) throws SQLException;
/**
* This method sets the specified parameter from the given Java
@@ -110,7 +113,7 @@ public interface PreparedStatement extends Statement
* @param value The value of the parameter.
* @exception SQLException If an error occurs.
*/
- void setShort(int parameterIndex, short x) throws SQLException;
+ void setShort(int index, short value) throws SQLException;
/**
* This method sets the specified parameter from the given Java
@@ -120,7 +123,7 @@ public interface PreparedStatement extends Statement
* @param value The value of the parameter.
* @exception SQLException If an error occurs.
*/
- void setInt(int parameterIndex, int x) throws SQLException;
+ void setInt(int index, int value) throws SQLException;
/**
* This method sets the specified parameter from the given Java
@@ -130,7 +133,7 @@ public interface PreparedStatement extends Statement
* @param value The value of the parameter.
* @exception SQLException If an error occurs.
*/
- void setLong(int parameterIndex, long x) throws SQLException;
+ void setLong(int index, long value) throws SQLException;
/**
* This method sets the specified parameter from the given Java
@@ -140,7 +143,7 @@ public interface PreparedStatement extends Statement
* @param value The value of the parameter.
* @exception SQLException If an error occurs.
*/
- void setFloat(int parameterIndex, float x) throws SQLException;
+ void setFloat(int index, float value) throws SQLException;
/**
* This method sets the specified parameter from the given Java
@@ -150,7 +153,7 @@ public interface PreparedStatement extends Statement
* @param value The value of the parameter.
* @exception SQLException If an error occurs.
*/
- void setDouble(int parameterIndex, double x) throws SQLException;
+ void setDouble(int index, double value) throws SQLException;
/**
* This method sets the specified parameter from the given Java
@@ -160,7 +163,7 @@ public interface PreparedStatement extends Statement
* @param value The value of the parameter.
* @exception SQLException If an error occurs.
*/
- void setBigDecimal(int parameterIndex, BigDecimal x) throws
+ void setBigDecimal(int index, BigDecimal value) throws
SQLException;
/**
@@ -171,7 +174,7 @@ public interface PreparedStatement extends Statement
* @param value The value of the parameter.
* @exception SQLException If an error occurs.
*/
- void setString(int parameterIndex, String x) throws SQLException;
+ void setString(int index, String value) throws SQLException;
/**
* This method sets the specified parameter from the given Java
@@ -181,7 +184,7 @@ public interface PreparedStatement extends Statement
* @param value The value of the parameter.
* @exception SQLException If an error occurs.
*/
- void setBytes(int parameterIndex, byte[] x) throws SQLException;
+ void setBytes(int index, byte[] value) throws SQLException;
/**
* This method sets the specified parameter from the given Java
@@ -191,7 +194,7 @@ public interface PreparedStatement extends Statement
* @param value The value of the parameter.
* @exception SQLException If an error occurs.
*/
- void setDate(int parameterIndex, Date x) throws SQLException;
+ void setDate(int index, Date value) throws SQLException;
/**
* This method sets the specified parameter from the given Java
@@ -201,7 +204,7 @@ public interface PreparedStatement extends Statement
* @param value The value of the parameter.
* @exception SQLException If an error occurs.
*/
- void setTime(int parameterIndex, Time x) throws SQLException;
+ void setTime(int index, Time value) throws SQLException;
/**
* This method sets the specified parameter from the given Java
@@ -211,7 +214,7 @@ public interface PreparedStatement extends Statement
* @param value The value of the parameter.
* @exception SQLException If an error occurs.
*/
- void setTimestamp(int parameterIndex, Timestamp x)
+ void setTimestamp(int index, Timestamp value)
throws SQLException;
/**
@@ -219,11 +222,11 @@ public interface PreparedStatement extends Statement
* ASCII <code>InputStream</code> value.
*
* @param index The index of the parameter value to set.
- * @param value The value of the parameter.
- * @param length The number of bytes in the stream.
+ * @param stream The stream from which the parameter value is read.
+ * @param count The number of bytes in the stream.
* @exception SQLException If an error occurs.
*/
- void setAsciiStream(int parameterIndex, InputStream x, int length)
+ void setAsciiStream(int index, InputStream stream, int count)
throws SQLException;
/**
@@ -231,12 +234,12 @@ public interface PreparedStatement extends Statement
* Unicode UTF-8 <code>InputStream</code> value.
*
* @param index The index of the parameter value to set.
- * @param value The value of the parameter.
- * @param length The number of bytes in the stream.
+ * @param stream The stream from which the parameter value is read.
+ * @param count The number of bytes in the stream.
* @exception SQLException If an error occurs.
* @deprecated
*/
- void setUnicodeStream(int parameterIndex, InputStream x, int length)
+ void setUnicodeStream(int index, InputStream stream, int count)
throws SQLException;
/**
@@ -244,11 +247,11 @@ public interface PreparedStatement extends Statement
* binary <code>InputStream</code> value.
*
* @param index The index of the parameter value to set.
- * @param value The value of the parameter.
- * @param length The number of bytes in the stream.
+ * @param stream The stream from which the parameter value is read.
+ * @param count The number of bytes in the stream.
* @exception SQLException If an error occurs.
*/
- void setBinaryStream(int parameterIndex, InputStream x, int length)
+ void setBinaryStream(int index, InputStream stream, int count)
throws SQLException;
/**
@@ -265,13 +268,14 @@ public interface PreparedStatement extends Statement
*
* @param index The index of the parameter value to set.
* @param value The value of the parameter.
- * @param type The SQL type to use for the parameter, from <code>Types</code>
+ * @param sqlType The SQL type to use for the parameter, from
+ * <code>Types</code>
* @param scale The scale of the value, for numeric values only.
* @exception SQLException If an error occurs.
* @see Types
*/
- void setObject(int parameterIndex, Object x, int targetSqlType,
- int scale) throws SQLException;
+ void setObject(int index, Object value, int sqlType, int scale)
+ throws SQLException;
/**
* This method sets the specified parameter from the given Java
@@ -279,11 +283,12 @@ public interface PreparedStatement extends Statement
*
* @param index The index of the parameter value to set.
* @param value The value of the parameter.
- * @param type The SQL type to use for the parameter, from <code>Types</code>
+ * @param sqlType The SQL type to use for the parameter, from
+ * <code>Types</code>
* @exception SQLException If an error occurs.
* @see Types
*/
- void setObject(int parameterIndex, Object x, int targetSqlType)
+ void setObject(int index, Object value, int sqlType)
throws SQLException;
/**
@@ -295,7 +300,7 @@ public interface PreparedStatement extends Statement
* @param value The value of the parameter.
* @exception SQLException If an error occurs.
*/
- void setObject(int parameterIndex, Object x) throws SQLException;
+ void setObject(int index, Object value) throws SQLException;
/**
* This method executes a prepared SQL query.
@@ -319,12 +324,12 @@ public interface PreparedStatement extends Statement
* character <code>Reader</code> value.
*
* @param index The index of the parameter value to set.
- * @param value The value of the parameter.
- * @param length The number of bytes in the stream.
+ * @param reader The reader from which the parameter value is read.
+ * @param count The number of characters in the stream.
* @exception SQLException If an error occurs.
*/
- void setCharacterStream(int parameterIndex, Reader reader,
- int length) throws SQLException;
+ void setCharacterStream(int index, Reader reader, int count)
+ throws SQLException;
/**
* This method sets the specified parameter from the given Java
@@ -332,10 +337,10 @@ public interface PreparedStatement extends Statement
* will be used.
*
* @param index The index of the parameter value to set.
- * @param value The value of the parameter.
+ * @param value The <code>Ref</code> used to set the value of the parameter.
* @exception SQLException If an error occurs.
*/
- void setRef(int i, Ref x) throws SQLException;
+ void setRef(int index, Ref value) throws SQLException;
/**
* This method sets the specified parameter from the given Java
@@ -343,10 +348,11 @@ public interface PreparedStatement extends Statement
* will be used.
*
* @param index The index of the parameter value to set.
- * @param value The value of the parameter.
+ * @param value The <code>Blob</code> used to set the
+ * value of the parameter.
* @exception SQLException If an error occurs.
*/
- void setBlob(int i, Blob x) throws SQLException;
+ void setBlob(int index, Blob value) throws SQLException;
/**
* This method sets the specified parameter from the given Java
@@ -354,10 +360,11 @@ public interface PreparedStatement extends Statement
* will be used.
*
* @param index The index of the parameter value to set.
- * @param value The value of the parameter.
+ * @param value The <code>Clob</code> used to set the
+ * value of the parameter.
* @exception SQLException If an error occurs.
*/
- void setClob(int i, Clob x) throws SQLException;
+ void setClob(int index, Clob value) throws SQLException;
/**
* This method sets the specified parameter from the given Java
@@ -368,7 +375,7 @@ public interface PreparedStatement extends Statement
* @param value The value of the parameter.
* @exception SQLException If an error occurs.
*/
- void setArray(int i, Array x) throws SQLException;
+ void setArray(int index, Array value) throws SQLException;
/**
* This method returns meta data for the result set from this statement.
@@ -384,10 +391,10 @@ public interface PreparedStatement extends Statement
*
* @param index The index of the parameter value to set.
* @param value The value of the parameter.
- * @param calendar The <code>Calendar</code> to use for timezone and locale.
+ * @param cal The <code>Calendar</code> to use for timezone and locale.
* @exception SQLException If an error occurs.
*/
- void setDate(int parameterIndex, Date x, Calendar cal)
+ void setDate(int index, Date value, Calendar cal)
throws SQLException;
/**
@@ -396,10 +403,10 @@ public interface PreparedStatement extends Statement
*
* @param index The index of the parameter value to set.
* @param value The value of the parameter.
- * @param calendar The <code>Calendar</code> to use for timezone and locale.
+ * @param cal The <code>Calendar</code> to use for timezone and locale.
* @exception SQLException If an error occurs.
*/
- void setTime(int parameterIndex, Time x, Calendar cal)
+ void setTime(int index, Time value, Calendar cal)
throws SQLException;
/**
@@ -408,10 +415,10 @@ public interface PreparedStatement extends Statement
*
* @param index The index of the parameter value to set.
* @param value The value of the parameter.
- * @param calendar The <code>Calendar</code> to use for timezone and locale.
+ * @param cal The <code>Calendar</code> to use for timezone and locale.
* @exception SQLException If an error occurs.
*/
- void setTimestamp(int parameterIndex, Timestamp x, Calendar cal)
+ void setTimestamp(int index, Timestamp value, Calendar cal)
throws SQLException;
/**
@@ -419,19 +426,32 @@ public interface PreparedStatement extends Statement
* for the specified type.
*
* @param index The index of the parameter to set.
- * @param type The SQL type identifier of the parameter from <code>Types</code>
- * @param name The name of the data type, for user defined types.
+ * @param sqlType The SQL type identifier of the parameter from
+ * <code>Types</code>
+ * @param typeName The name of the data type, for user defined types.
* @exception SQLException If an error occurs.
*/
- void setNull(int paramIndex, int sqlType, String typeName)
+ void setNull(int index, int sqlType, String typeName)
throws SQLException;
/**
+ * This method sets the specified parameter from the given Java
+ * <code>java.net.URL</code> value.
+ *
+ * @param index The index of the parameter to set.
+ * @param value The value of the parameter.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void setURL(int parameterIndex, URL x) throws SQLException;
+ void setURL(int index, URL value) throws SQLException;
/**
+ * Returns information about the parameters set on this
+ * <code>PreparedStatement</code> (see {@link ParameterMetaData} for a
+ * detailed description of the provided information).
+ *
+ * @return Meta data for the parameters of this statement.
+ * @see ParameterMetaData
* @since 1.4
*/
ParameterMetaData getParameterMetaData() throws SQLException;
diff --git a/libjava/classpath/java/sql/ResultSet.java b/libjava/classpath/java/sql/ResultSet.java
index 97f2897d423..79cba63d419 100644
--- a/libjava/classpath/java/sql/ResultSet.java
+++ b/libjava/classpath/java/sql/ResultSet.java
@@ -1,5 +1,5 @@
/* ResultSet.java -- A SQL statement result set.
- Copyright (C) 1999, 2000, 2002 Free Software Foundation, Inc.
+ Copyright (C) 1999, 2000, 2002, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -138,7 +138,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>String</code>.
*
- * @param index The index of the column to return.
+ * @param columnIndex The index of the column to return.
* @return The column value as a <code>String</code>.
* @exception SQLException If an error occurs.
*/
@@ -148,7 +148,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>boolean</code>.
*
- * @param index The index of the column to return.
+ * @param columnIndex The index of the column to return.
* @return The column value as a <code>boolean</code>.
* @exception SQLException If an error occurs.
*/
@@ -158,7 +158,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>byte</code>.
*
- * @param index The index of the column to return.
+ * @param columnIndex The index of the column to return.
* @return The column value as a <code>byte</code>.
* @exception SQLException If an error occurs.
*/
@@ -168,7 +168,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>short</code>.
*
- * @param index The index of the column to return.
+ * @param columnIndex The index of the column to return.
* @return The column value as a <code>short</code>.
* @exception SQLException If an error occurs.
*/
@@ -178,7 +178,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>int</code>.
*
- * @param index The index of the column to return.
+ * @param columnIndex The index of the column to return.
* @return The column value as a <code>int</code>.
* @exception SQLException If an error occurs.
*/
@@ -188,7 +188,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>long</code>.
*
- * @param index The index of the column to return.
+ * @param columnIndex The index of the column to return.
* @return The column value as a <code>long</code>.
* @exception SQLException If an error occurs.
*/
@@ -198,7 +198,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>float</code>.
*
- * @param index The index of the column to return.
+ * @param columnIndex The index of the column to return.
* @return The column value as a <code>float</code>.
* @exception SQLException If an error occurs.
*/
@@ -208,7 +208,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>double</code>.
*
- * @param index The index of the column to return.
+ * @param columnIndex The index of the column to return.
* @return The column value as a <code>double</code>.
* @exception SQLException If an error occurs.
*/
@@ -218,7 +218,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>BigDecimal</code>.
*
- * @param index The index of the column to return.
+ * @param columnIndex The index of the column to return.
* @param scale The number of digits to the right of the decimal to return.
* @return The column value as a <code>BigDecimal</code>.
* @exception SQLException If an error occurs.
@@ -231,7 +231,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* byte array.
*
- * @param index The index of the column to return.
+ * @param columnIndex The index of the column to return.
* @return The column value as a byte array
* @exception SQLException If an error occurs.
*/
@@ -241,7 +241,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>java.sql.Date</code>.
*
- * @param index The index of the column to return.
+ * @param columnIndex The index of the column to return.
* @return The column value as a <code>java.sql.Date</code>.
* @exception SQLException If an error occurs.
*/
@@ -251,7 +251,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>java.sql.Time</code>.
*
- * @param index The index of the column to return.
+ * @param columnIndex The index of the column to return.
* @return The column value as a <code>java.sql.Time</code>.
* @exception SQLException If an error occurs.
*/
@@ -261,7 +261,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>java.sql.Timestamp</code>.
*
- * @param index The index of the column to return.
+ * @param columnIndex The index of the column to return.
* @return The column value as a <code>java.sql.Timestamp</code>.
* @exception SQLException If an error occurs.
*/
@@ -274,7 +274,7 @@ public interface ResultSet
* calling <code>next()</code> or <code>close()</code> on this result set
* will close this stream as well.
*
- * @param index The index of the column to return.
+ * @param columnIndex The index of the column to return.
* @return The column value as an ASCII <code>InputStream</code>.
* @exception SQLException If an error occurs.
*/
@@ -287,7 +287,7 @@ public interface ResultSet
* calling <code>next()</code> or <code>close()</code> on this result set
* will close this stream as well.
*
- * @param index The index of the column to return.
+ * @param columnIndex The index of the column to return.
* @return The column value as a Unicode UTF-8 <code>InputStream</code>.
* @exception SQLException If an error occurs.
* @deprecated Use getCharacterStream instead.
@@ -301,7 +301,7 @@ public interface ResultSet
* calling <code>next()</code> or <code>close()</code> on this result set
* will close this stream as well.
*
- * @param index The index of the column to return.
+ * @param columnIndex The index of the column to return.
* @return The column value as a raw byte <code>InputStream</code>.
* @exception SQLException If an error occurs.
*/
@@ -311,7 +311,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>String</code>.
*
- * @param column The name of the column to return.
+ * @param columnName The name of the column to return.
* @return The column value as a <code>String</code>.
* @exception SQLException If an error occurs.
*/
@@ -321,7 +321,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>boolean</code>.
*
- * @param column The name of the column to return.
+ * @param columnName The name of the column to return.
* @return The column value as a <code>boolean</code>.
* @exception SQLException If an error occurs.
*/
@@ -331,7 +331,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>byte</code>.
*
- * @param column The name of the column to return.
+ * @param columnName The name of the column to return.
* @return The column value as a <code>byte</code>.
* @exception SQLException If an error occurs.
*/
@@ -341,7 +341,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>short</code>.
*
- * @param column The name of the column to return.
+ * @param columnName The name of the column to return.
* @return The column value as a <code>short</code>.
* @exception SQLException If an error occurs.
*/
@@ -351,7 +351,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>int</code>.
*
- * @param column The name of the column to return.
+ * @param columnName The name of the column to return.
* @return The column value as a <code>int</code>.
* @exception SQLException If an error occurs.
*/
@@ -361,7 +361,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>long</code>.
*
- * @param column The name of the column to return.
+ * @param columnName The name of the column to return.
* @return The column value as a <code>long</code>.
* @exception SQLException If an error occurs.
*/
@@ -371,7 +371,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>float</code>.
*
- * @param column The name of the column to return.
+ * @param columnName The name of the column to return.
* @return The column value as a <code>float</code>.
* @exception SQLException If an error occurs.
*/
@@ -381,7 +381,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>double</code>.
*
- * @param column The name of the column to return.
+ * @param columnName The name of the column to return.
* @return The column value as a <code>double</code>.
* @exception SQLException If an error occurs.
*/
@@ -391,7 +391,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>BigDecimal</code>.
*
- * @param index The index of the column to return.
+ * @param columnName The name of the column to return.
* @return The column value as a <code>BigDecimal</code>.
* @exception SQLException If an error occurs.
* @deprecated
@@ -403,7 +403,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* byte array.
*
- * @param column The name of the column to return.
+ * @param columnName The name of the column to return.
* @return The column value as a byte array
* @exception SQLException If an error occurs.
*/
@@ -413,7 +413,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>java.sql.Date</code>.
*
- * @param column The name of the column to return.
+ * @param columnName The name of the column to return.
* @return The column value as a <code>java.sql.Date</code>.
* @exception SQLException If an error occurs.
*/
@@ -423,7 +423,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>java.sql.Time</code>.
*
- * @param column The name of the column to return.
+ * @param columnName The name of the column to return.
* @return The column value as a <code>java.sql.Time</code>.
* @exception SQLException If an error occurs.
*/
@@ -433,7 +433,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>java.sql.Timestamp</code>.
*
- * @param column The name of the column to return.
+ * @param columnName The name of the column to return.
* @return The column value as a <code>java.sql.Timestamp</code>.
* @exception SQLException If an error occurs.
*/
@@ -446,7 +446,7 @@ public interface ResultSet
* calling <code>next()</code> or <code>close()</code> on this result set
* will close this stream as well.
*
- * @param column The name of the column to return.
+ * @param columnName The name of the column to return.
* @return The column value as an ASCII <code>InputStream</code>.
* @exception SQLException If an error occurs.
*/
@@ -459,7 +459,7 @@ public interface ResultSet
* calling <code>next()</code> or <code>close()</code> on this result set
* will close this stream as well.
*
- * @param column The name of the column to return.
+ * @param columnName The name of the column to return.
* @return The column value as a Unicode UTF-8 <code>InputStream</code>.
* @exception SQLException If an error occurs.
* @deprecated Use getCharacterStream instead.
@@ -473,7 +473,7 @@ public interface ResultSet
* calling <code>next()</code> or <code>close()</code> on this result set
* will close this stream as well.
*
- * @param column The name of the column to return.
+ * @param columnName The name of the column to return.
* @return The column value as a raw byte <code>InputStream</code>.
* @exception SQLException If an error occurs.
*/
@@ -518,7 +518,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>Object</code>.
*
- * @param index The index of the column to return.
+ * @param columnIndex The index of the column to return.
* @return The column value as an <code>Object</code>.
* @exception SQLException If an error occurs.
*/
@@ -528,7 +528,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>Object</code>.
*
- * @param column The name of the column to return.
+ * @param columnName The name of the column to return.
* @return The column value as an <code>Object</code>.
* @exception SQLException If an error occurs.
*/
@@ -537,7 +537,7 @@ public interface ResultSet
/**
* This method returns the column index of the specified named column.
*
- * @param column The name of the column.
+ * @param columnName The name of the column.
* @return The index of the column.
* @exception SQLException If an error occurs.
*/
@@ -550,7 +550,7 @@ public interface ResultSet
* calling <code>next()</code> or <code>close()</code> on this result set
* will close this stream as well.
*
- * @param index The index of the column to return.
+ * @param columnIndex The index of the column to return.
* @return The column value as an character <code>Reader</code>.
* @exception SQLException If an error occurs.
*/
@@ -563,7 +563,7 @@ public interface ResultSet
* calling <code>next()</code> or <code>close()</code> on this result set
* will close this stream as well.
*
- * @param column The name of the column to return.
+ * @param columnName The name of the column to return.
* @return The column value as an character <code>Reader</code>.
* @exception SQLException If an error occurs.
*/
@@ -573,7 +573,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>BigDecimal</code>.
*
- * @param index The index of the column to return.
+ * @param columnIndex The index of the column to return.
* @return The column value as a <code>BigDecimal</code>.
* @exception SQLException If an error occurs.
*/
@@ -583,7 +583,7 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>BigDecimal</code>.
*
- * @param column The name of the column to return.
+ * @param columnName The name of the column to return.
* @return The column value as a <code>BigDecimal</code>.
* @exception SQLException If an error occurs.
*/
@@ -692,7 +692,7 @@ public interface ResultSet
* This method moves the result set position relative to the current row.
* The offset can be positive or negative.
*
- * @param row The relative row position to move to.
+ * @param rows The number of row positions to move.
* @return <code>true</code> if the current position was changed,
* <code>false</code> otherwise.
* @exception SQLException If an error occurs.
@@ -713,7 +713,9 @@ public interface ResultSet
* This method provides a hint to the driver about which direction the
* result set will be processed in.
*
- * @param direction The direction in which rows will be processed. (Values?)
+ * @param direction The direction in which rows will be processed. The
+ * allowed values are the <code>FETCH_*</code> constants
+ * defined in this interface.
* @exception SQLException If an error occurs.
*/
void setFetchDirection(int direction) throws SQLException;
@@ -746,7 +748,7 @@ public interface ResultSet
/**
* This method returns the result set type of this result set. This will
- * be one of the TYPE_* constants defined in this interface.
+ * be one of the <code>TYPE_*</code> constants defined in this interface.
*
* @return The result set type.
* @exception SQLException If an error occurs.
@@ -755,7 +757,7 @@ public interface ResultSet
/**
* This method returns the concurrency type of this result set. This will
- * be one of the CONCUR_* constants defined in this interface.
+ * be one of the <code>CONCUR_*</code> constants defined in this interface.
*
* @return The result set concurrency type.
* @exception SQLException If an error occurs.
@@ -800,7 +802,7 @@ public interface ResultSet
* does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @return index The index of the column to update.
+ * @param columnIndex The index of the column to update.
* @exception SQLException If an error occurs.
*/
void updateNull(int columnIndex) throws SQLException;
@@ -810,88 +812,88 @@ public interface ResultSet
* does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param index The index of the column to update.
+ * @param columnIndex The index of the column to update.
* @param value The new value of the column.
* @exception SQLException If an error occurs.
*/
- void updateBoolean(int columnIndex, boolean x) throws SQLException;
+ void updateBoolean(int columnIndex, boolean value) throws SQLException;
/**
* This method updates the specified column to have a byte value. This
* does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param index The index of the column to update.
+ * @param columnIndex The index of the column to update.
* @param value The new value of the column.
* @exception SQLException If an error occurs.
*/
- void updateByte(int columnIndex, byte x) throws SQLException;
+ void updateByte(int columnIndex, byte value) throws SQLException;
/**
* This method updates the specified column to have a short value. This
* does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param index The index of the column to update.
+ * @param columnIndex The index of the column to update.
* @param value The new value of the column.
* @exception SQLException If an error occurs.
*/
- void updateShort(int columnIndex, short x) throws SQLException;
+ void updateShort(int columnIndex, short value) throws SQLException;
/**
* This method updates the specified column to have an int value. This
* does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param index The index of the column to update.
+ * @param columnIndex The index of the column to update.
* @param value The new value of the column.
* @exception SQLException If an error occurs.
*/
- void updateInt(int columnIndex, int x) throws SQLException;
+ void updateInt(int columnIndex, int value) throws SQLException;
/**
* This method updates the specified column to have a long value. This
* does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param index The index of the column to update.
+ * @param columnIndex The index of the column to update.
* @param value The new value of the column.
* @exception SQLException If an error occurs.
*/
- void updateLong(int columnIndex, long x) throws SQLException;
+ void updateLong(int columnIndex, long value) throws SQLException;
/**
* This method updates the specified column to have a float value. This
* does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param index The index of the column to update.
+ * @param columnIndex The index of the column to update.
* @param value The new value of the column.
* @exception SQLException If an error occurs.
*/
- void updateFloat(int columnIndex, float x) throws SQLException;
+ void updateFloat(int columnIndex, float value) throws SQLException;
/**
* This method updates the specified column to have a double value. This
* does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param index The index of the column to update.
+ * @param columnIndex The index of the column to update.
* @param value The new value of the column.
* @exception SQLException If an error occurs.
*/
- void updateDouble(int columnIndex, double x) throws SQLException;
+ void updateDouble(int columnIndex, double value) throws SQLException;
/**
* This method updates the specified column to have a BigDecimal value. This
* does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param index The index of the column to update.
+ * @param columnIndex The index of the column to update.
* @param value The new value of the column.
* @exception SQLException If an error occurs.
*/
- void updateBigDecimal(int columnIndex, BigDecimal x)
+ void updateBigDecimal(int columnIndex, BigDecimal value)
throws SQLException;
/**
@@ -899,55 +901,55 @@ public interface ResultSet
* does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param index The index of the column to update.
+ * @param columnIndex The index of the column to update.
* @param value The new value of the column.
* @exception SQLException If an error occurs.
*/
- void updateString(int columnIndex, String x) throws SQLException;
+ void updateString(int columnIndex, String value) throws SQLException;
/**
* This method updates the specified column to have a byte array value. This
* does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param index The index of the column to update.
+ * @param columnIndex The index of the column to update.
* @param value The new value of the column.
* @exception SQLException If an error occurs.
*/
- void updateBytes(int columnIndex, byte[] x) throws SQLException;
+ void updateBytes(int columnIndex, byte[] value) throws SQLException;
/**
* This method updates the specified column to have a java.sql.Date value. This
* does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param index The index of the column to update.
+ * @param columnIndex The index of the column to update.
* @param value The new value of the column.
* @exception SQLException If an error occurs.
*/
- void updateDate(int columnIndex, Date x) throws SQLException;
+ void updateDate(int columnIndex, Date value) throws SQLException;
/**
* This method updates the specified column to have a java.sql.Time value. This
* does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param index The index of the column to update.
+ * @param columnIndex The index of the column to update.
* @param value The new value of the column.
* @exception SQLException If an error occurs.
*/
- void updateTime(int columnIndex, Time x) throws SQLException;
+ void updateTime(int columnIndex, Time value) throws SQLException;
/**
* This method updates the specified column to have a java.sql.Timestamp value.
* This does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param index The index of the column to update.
+ * @param columnIndex The index of the column to update.
* @param value The new value of the column.
* @exception SQLException If an error occurs.
*/
- void updateTimestamp(int columnIndex, Timestamp x)
+ void updateTimestamp(int columnIndex, Timestamp value)
throws SQLException;
/**
@@ -955,12 +957,12 @@ public interface ResultSet
* This does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param index The index of the column to update.
- * @param value The new value of the column.
- * @param length The length of the stream.
+ * @param columnIndex The index of the column to update.
+ * @param stream The stream from which the column value is updated.
+ * @param count The length of the stream.
* @exception SQLException If an error occurs.
*/
- void updateAsciiStream(int columnIndex, InputStream x, int length)
+ void updateAsciiStream(int columnIndex, InputStream stream, int count)
throws SQLException;
/**
@@ -968,12 +970,12 @@ public interface ResultSet
* This does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param index The index of the column to update.
- * @param value The new value of the column.
- * @param length The length of the stream.
+ * @param columnIndex The index of the column to update.
+ * @param stream The stream from which the column value is updated.
+ * @param count The length of the stream.
* @exception SQLException If an error occurs.
*/
- void updateBinaryStream(int columnIndex, InputStream x, int length)
+ void updateBinaryStream(int columnIndex, InputStream stream, int count)
throws SQLException;
/**
@@ -981,12 +983,12 @@ public interface ResultSet
* This does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param index The index of the column to update.
- * @param value The new value of the column.
- * @param length The length of the stream.
+ * @param columnIndex The index of the column to update.
+ * @param reader The reader from which the column value is updated.
+ * @param count The length of the stream.
* @exception SQLException If an error occurs.
*/
- void updateCharacterStream(int columnIndex, Reader x, int length)
+ void updateCharacterStream(int columnIndex, Reader reader, int count)
throws SQLException;
/**
@@ -994,12 +996,13 @@ public interface ResultSet
* This does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param index The index of the column to update.
+ * @param columnIndex The index of the column to update.
* @param value The new value of the column.
- *
+ * @param scale The scale of the object in question, which is used only
+ * for numeric type objects.
* @exception SQLException If an error occurs.
*/
- void updateObject(int columnIndex, Object x, int scale)
+ void updateObject(int columnIndex, Object value, int scale)
throws SQLException;
/**
@@ -1007,20 +1010,18 @@ public interface ResultSet
* This does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param index The index of the column to update.
+ * @param columnIndex The index of the column to update.
* @param value The new value of the column.
- * @param scale The scale of the object in question, which is used only
- * for numeric type objects.
* @exception SQLException If an error occurs.
*/
- void updateObject(int columnIndex, Object x) throws SQLException;
+ void updateObject(int columnIndex, Object value) throws SQLException;
/**
* This method updates the specified column to have a NULL value. This
* does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @return name The name of the column to update.
+ * @param columnName The name of the column to update.
* @exception SQLException If an error occurs.
*/
void updateNull(String columnName) throws SQLException;
@@ -1030,88 +1031,88 @@ public interface ResultSet
* does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param name The name of the column to update.
+ * @param columnName The name of the column to update.
* @param value The new value of the column.
* @exception SQLException If an error occurs.
*/
- void updateBoolean(String columnName, boolean x) throws SQLException;
+ void updateBoolean(String columnName, boolean value) throws SQLException;
/**
* This method updates the specified column to have a byte value. This
* does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param name The name of the column to update.
+ * @param columnName The name of the column to update.
* @param value The new value of the column.
* @exception SQLException If an error occurs.
*/
- void updateByte(String columnName, byte x) throws SQLException;
+ void updateByte(String columnName, byte value) throws SQLException;
/**
* This method updates the specified column to have a short value. This
* does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param name The name of the column to update.
+ * @param columnName The name of the column to update.
* @param value The new value of the column.
* @exception SQLException If an error occurs.
*/
- void updateShort(String columnName, short x) throws SQLException;
+ void updateShort(String columnName, short value) throws SQLException;
/**
* This method updates the specified column to have an int value. This
* does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param name The name of the column to update.
+ * @param columnName The name of the column to update.
* @param value The new value of the column.
* @exception SQLException If an error occurs.
*/
- void updateInt(String columnName, int x) throws SQLException;
+ void updateInt(String columnName, int value) throws SQLException;
/**
* This method updates the specified column to have a long value. This
* does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param name The name of the column to update.
+ * @param columnName The name of the column to update.
* @param value The new value of the column.
* @exception SQLException If an error occurs.
*/
- void updateLong(String columnName, long x) throws SQLException;
+ void updateLong(String columnName, long value) throws SQLException;
/**
* This method updates the specified column to have a float value. This
* does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param name The name of the column to update.
+ * @param columnName The name of the column to update.
* @param value The new value of the column.
* @exception SQLException If an error occurs.
*/
- void updateFloat(String columnName, float x) throws SQLException;
+ void updateFloat(String columnName, float value) throws SQLException;
/**
* This method updates the specified column to have a double value. This
* does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param name The name of the column to update.
+ * @param columnName The name of the column to update.
* @param value The new value of the column.
* @exception SQLException If an error occurs.
*/
- void updateDouble(String columnName, double x) throws SQLException;
+ void updateDouble(String columnName, double value) throws SQLException;
/**
* This method updates the specified column to have a BigDecimal value. This
* does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param name The name of the column to update.
+ * @param columnName The name of the column to update.
* @param value The new value of the column.
* @exception SQLException If an error occurs.
*/
- void updateBigDecimal(String columnName, BigDecimal x)
+ void updateBigDecimal(String columnName, BigDecimal value)
throws SQLException;
/**
@@ -1119,55 +1120,55 @@ public interface ResultSet
* does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param name The name of the column to update.
+ * @param columnName The name of the column to update.
* @param value The new value of the column.
* @exception SQLException If an error occurs.
*/
- void updateString(String columnName, String x) throws SQLException;
+ void updateString(String columnName, String value) throws SQLException;
/**
* This method updates the specified column to have a byte array value. This
* does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param name The name of the column to update.
+ * @param columnName The name of the column to update.
* @param value The new value of the column.
* @exception SQLException If an error occurs.
*/
- void updateBytes(String columnName, byte[] x) throws SQLException;
+ void updateBytes(String columnName, byte[] value) throws SQLException;
/**
* This method updates the specified column to have a java.sql.Date value. This
* does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param name The name of the column to update.
+ * @param columnName The name of the column to update.
* @param value The new value of the column.
* @exception SQLException If an error occurs.
*/
- void updateDate(String columnName, Date x) throws SQLException;
+ void updateDate(String columnName, Date value) throws SQLException;
/**
* This method updates the specified column to have a java.sql.Time value. This
* does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param name The name of the column to update.
+ * @param columnName The name of the column to update.
* @param value The new value of the column.
* @exception SQLException If an error occurs.
*/
- void updateTime(String columnName, Time x) throws SQLException;
+ void updateTime(String columnName, Time value) throws SQLException;
/**
* This method updates the specified column to have a java.sql.Timestamp value.
* This does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param name The name of the column to update.
+ * @param columnName The name of the column to update.
* @param value The new value of the column.
* @exception SQLException If an error occurs.
*/
- void updateTimestamp(String columnName, Timestamp x)
+ void updateTimestamp(String columnName, Timestamp value)
throws SQLException;
/**
@@ -1175,12 +1176,12 @@ public interface ResultSet
* This does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param name The name of the column to update.
- * @param value The new value of the column.
- * @param length The length of the stream.
+ * @param columnName The name of the column to update.
+ * @param stream The stream from which the column value is updated.
+ * @param count The length of the stream.
* @exception SQLException If an error occurs.
*/
- void updateAsciiStream(String columnName, InputStream x, int length)
+ void updateAsciiStream(String columnName, InputStream stream, int count)
throws SQLException;
/**
@@ -1188,12 +1189,12 @@ public interface ResultSet
* This does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param name The name of the column to update.
- * @param value The new value of the column.
- * @param length The length of the stream.
+ * @param columnName The name of the column to update.
+ * @param stream The stream from which the column value is updated.
+ * @param count The length of the stream.
* @exception SQLException If an error occurs.
*/
- void updateBinaryStream(String columnName, InputStream x, int length)
+ void updateBinaryStream(String columnName, InputStream stream, int count)
throws SQLException;
/**
@@ -1201,25 +1202,26 @@ public interface ResultSet
* This does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param name The name of the column to update.
- * @param value The new value of the column.
- * @param length The length of the stream.
- *
+ * @param columnName The name of the column to update.
+ * @param reader The reader from which the column value is updated.
+ * @param count The length of the stream.
* @exception SQLException If an error occurs.
*/
- void updateCharacterStream(String columnName, Reader reader,
- int length) throws SQLException;
+ void updateCharacterStream(String columnName, Reader reader, int count)
+ throws SQLException;
/**
* This method updates the specified column to have an Object value.
* This does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param name The name of the column to update.
+ * @param columnName The name of the column to update.
* @param value The new value of the column.
+ * @param scale The scale of the object in question, which is used only
+ * for numeric type objects.
* @exception SQLException If an error occurs.
*/
- void updateObject(String columnName, Object x, int scale)
+ void updateObject(String columnName, Object value, int scale)
throws SQLException;
/**
@@ -1227,13 +1229,11 @@ public interface ResultSet
* This does not update the actual database. <code>updateRow</code> must be
* called in order to do that.
*
- * @param name The name of the column to update.
+ * @param columnName The name of the column to update.
* @param value The new value of the column.
- * @param scale The scale of the object in question, which is used only
- * for numeric type objects.
* @exception SQLException If an error occurs.
*/
- void updateObject(String columnName, Object x) throws SQLException;
+ void updateObject(String columnName, Object value) throws SQLException;
/**
* This method inserts the current row into the database. The result set
@@ -1304,97 +1304,97 @@ public interface ResultSet
* This method returns the value of the specified column as a Java
* <code>Object</code> using the specified SQL type to Java type map.
*
- * @param index The index of the column to return.
+ * @param columnIndex The index of the column to return.
* @param map The SQL type to Java type map to use.
* @return The value of the column as an <code>Object</code>.
* @exception SQLException If an error occurs.
*/
- Object getObject(int i, Map map) throws SQLException;
+ Object getObject(int columnIndex, Map map) throws SQLException;
/**
* This method returns a <code>Ref</code> for the specified column which
* represents the structured type for the column.
*
- * @param index The index of the column to return.
+ * @param columnIndex The index of the column to return.
* @return A <code>Ref</code> object for the column
* @exception SQLException If an error occurs.
*/
- Ref getRef(int i) throws SQLException;
+ Ref getRef(int columnIndex) throws SQLException;
/**
* This method returns the specified column value as a BLOB.
*
- * @param index The index of the column value to return.
+ * @param columnIndex The index of the column value to return.
* @return The value of the column as a BLOB.
* @exception SQLException If an error occurs.
*/
- Blob getBlob(int i) throws SQLException;
+ Blob getBlob(int columnIndex) throws SQLException;
/**
* This method returns the specified column value as a CLOB.
*
- * @param index The index of the column value to return.
+ * @param columnIndex The index of the column value to return.
* @return The value of the column as a CLOB.
* @exception SQLException If an error occurs.
*/
- Clob getClob(int i) throws SQLException;
+ Clob getClob(int columnIndex) throws SQLException;
/**
* This method returns the specified column value as an <code>Array</code>.
*
- * @param index The index of the column value to return.
+ * @param columnIndex The index of the column value to return.
* @return The value of the column as an <code>Array</code>.
* @exception SQLException If an error occurs.
*/
- Array getArray(int i) throws SQLException;
+ Array getArray(int columnIndex) throws SQLException;
/**
* This method returns the value of the specified column as a Java
* <code>Object</code> using the specified SQL type to Java type map.
*
- * @param name The name of the column to return.
+ * @param columnName The name of the column to return.
* @param map The SQL type to Java type map to use.
* @return The value of the column as an <code>Object</code>.
* @exception SQLException If an error occurs.
*/
- Object getObject(String colName, Map map) throws SQLException;
+ Object getObject(String columnName, Map map) throws SQLException;
/**
* This method returns a <code>Ref</code> for the specified column which
* represents the structured type for the column.
*
- * @param index The index of the column to return.
+ * @param columnName The name of the column to return.
* @return A <code>Ref</code> object for the column
* @exception SQLException If an error occurs.
*/
- Ref getRef(String colName) throws SQLException;
+ Ref getRef(String columnName) throws SQLException;
/**
* This method returns the specified column value as a BLOB.
*
- * @param name The name of the column value to return.
+ * @param columnName The name of the column value to return.
* @return The value of the column as a BLOB.
* @exception SQLException If an error occurs.
*/
- Blob getBlob(String colName) throws SQLException;
+ Blob getBlob(String columnName) throws SQLException;
/**
* This method returns the specified column value as a CLOB.
*
- * @param name The name of the column value to return.
+ * @param columnName The name of the column value to return.
* @return The value of the column as a CLOB.
* @exception SQLException If an error occurs.
*/
- Clob getClob(String colName) throws SQLException;
+ Clob getClob(String columnName) throws SQLException;
/**
* This method returns the specified column value as an <code>Array</code>.
*
- * @param name The name of the column value to return.
+ * @param columnName The name of the column value to return.
* @return The value of the column as an <code>Array</code>.
* @exception SQLException If an error occurs.
*/
- Array getArray(String colName) throws SQLException;
+ Array getArray(String columnName) throws SQLException;
/**
* This method returns the specified column value as a
@@ -1402,7 +1402,7 @@ public interface ResultSet
* to generate a value for the date if the database does not support
* timezones.
*
- * @param index The index of the column value to return.
+ * @param columnIndex The index of the column value to return.
* @param cal The <code>Calendar</code> to use for calculating timezones.
* @return The value of the column as a <code>java.sql.Date</code>.
* @exception SQLException If an error occurs.
@@ -1415,7 +1415,7 @@ public interface ResultSet
* to generate a value for the date if the database does not support
* timezones.
*
- * @param name The name of the column value to return.
+ * @param columnName The name of the column value to return.
* @param cal The <code>Calendar</code> to use for calculating timezones.
* @return The value of the column as a <code>java.sql.Date</code>.
* @exception SQLException If an error occurs.
@@ -1428,7 +1428,7 @@ public interface ResultSet
* to generate a value for the time if the database does not support
* timezones.
*
- * @param index The index of the column value to return.
+ * @param columnIndex The index of the column value to return.
* @param cal The <code>Calendar</code> to use for calculating timezones.
* @return The value of the column as a <code>java.sql.Time</code>.
* @exception SQLException If an error occurs.
@@ -1441,7 +1441,7 @@ public interface ResultSet
* to generate a value for the time if the database does not support
* timezones.
*
- * @param name The name of the column value to return.
+ * @param columnName The name of the column value to return.
* @param cal The <code>Calendar</code> to use for calculating timezones.
* @return The value of the column as a <code>java.sql.Time</code>.
* @exception SQLException If an error occurs.
@@ -1454,7 +1454,7 @@ public interface ResultSet
* to generate a value for the timestamp if the database does not support
* timezones.
*
- * @param index The index of the column value to return.
+ * @param columnIndex The index of the column value to return.
* @param cal The <code>Calendar</code> to use for calculating timezones.
* @return The value of the column as a <code>java.sql.Timestamp</code>.
* @exception SQLException If an error occurs.
@@ -1468,7 +1468,7 @@ public interface ResultSet
* to generate a value for the timestamp if the database does not support
* timezones.
*
- * @param name The name of the column value to return.
+ * @param columnName The name of the column value to return.
* @param cal The <code>Calendar</code> to use for calculating timezones.
*
* @return The value of the column as a <code>java.sql.Timestamp</code>.
@@ -1479,52 +1479,132 @@ public interface ResultSet
throws SQLException;
/**
+ * This method returns the specified column value as a
+ * <code>java.net.URL</code>.
+ *
+ * @param columnIndex The index of the column value to return.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
URL getURL(int columnIndex) throws SQLException;
/**
+ * This method returns the specified column value as a
+ * <code>java.net.URL</code>.
+ *
+ * @param columnName The name of the column value to return.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
URL getURL(String columnName) throws SQLException;
/**
+ * This method updates the specified column to have a
+ * <code>java.sql.Ref</code> value.
+ * This does not update the actual database. <code>updateRow</code> must be
+ * called in order to do that.
+ *
+ * @parm columnIndex The index of the column value to update.
+ * @parm value The <code>java.sql.Ref</code> used to set the new value
+ * of the column.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void updateRef(int columnIndex, Ref x) throws SQLException;
+ void updateRef(int columnIndex, Ref value) throws SQLException;
/**
+ * This method updates the specified column to have a
+ * <code>java.sql.Ref</code> value.
+ * This does not update the actual database. <code>updateRow</code> must be
+ * called in order to do that.
+ *
+ * @parm columnName The name of the column value to update.
+ * @parm value The <code>java.sql.Ref</code> used to set the new value
+ * of the column.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void updateRef(String columnName, Ref x) throws SQLException;
+ void updateRef(String columnName, Ref value) throws SQLException;
/**
+ * This method updates the specified column to have a
+ * <code>java.sql.Blob</code> value.
+ * This does not update the actual database. <code>updateRow</code> must be
+ * called in order to do that.
+ *
+ * @parm columnIndex The index of the column value to update.
+ * @parm value The <code>java.sql.Blob</code> used to set the new value
+ * of the column.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void updateBlob(int columnIndex, Blob x) throws SQLException;
+ void updateBlob(int columnIndex, Blob value) throws SQLException;
/**
+ * This method updates the specified column to have a
+ * <code>java.sql.Blob</code> value.
+ * This does not update the actual database. <code>updateRow</code> must be
+ * called in order to do that.
+ *
+ * @parm columnName The name of the column value to update.
+ * @parm value The <code>java.sql.Blob</code> used to set the new value
+ * of the column.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void updateBlob(String columnName, Blob x) throws SQLException;
+ void updateBlob(String columnName, Blob value) throws SQLException;
/**
+ * This method updates the specified column to have a
+ * <code>java.sql.Clob</code> value.
+ * This does not update the actual database. <code>updateRow</code> must be
+ * called in order to do that.
+ *
+ * @parm columnIndex The index of the column value to update.
+ * @parm value The <code>java.sql.Clob</code> used to set the new value
+ * of the column.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void updateClob(int columnIndex, Clob x) throws SQLException;
+ void updateClob(int columnIndex, Clob value) throws SQLException;
/**
+ * This method updates the specified column to have a
+ * <code>java.sql.Clob</code> value.
+ * This does not update the actual database. <code>updateRow</code> must be
+ * called in order to do that.
+ *
+ * @parm columnName The name of the column value to update.
+ * @parm value The <code>java.sql.Clob</code> used to set the new value
+ * of the column.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void updateClob(String columnName, Clob x) throws SQLException;
+ void updateClob(String columnName, Clob value) throws SQLException;
/**
+ * This method updates the specified column to have a
+ * <code>java.sqlArray</code> value.
+ * This does not update the actual database. <code>updateRow</code> must be
+ * called in order to do that.
+ *
+ * @parm columnIndex The index of the column value to update.
+ * @parm value The new value of the column.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void updateArray(int columnIndex, Array x) throws SQLException;
+ void updateArray(int columnIndex, Array value) throws SQLException;
/**
+ * This method updates the specified column to have a
+ * <code>java.sqlArray</code> value.
+ * This does not update the actual database. <code>updateRow</code> must be
+ * called in order to do that.
+ *
+ * @parm columnName The name of the column value to update.
+ * @parm value The new value of the column.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void updateArray(String columnName, Array x) throws SQLException;
+ void updateArray(String columnName, Array value) throws SQLException;
}
diff --git a/libjava/classpath/java/sql/ResultSetMetaData.java b/libjava/classpath/java/sql/ResultSetMetaData.java
index 0086677ee60..5a62c549e1e 100644
--- a/libjava/classpath/java/sql/ResultSetMetaData.java
+++ b/libjava/classpath/java/sql/ResultSetMetaData.java
@@ -1,5 +1,5 @@
/* ResultSetMetaData.java -- Returns information about the ResultSet
- Copyright (C) 1999, 2000, 2002 Free Software Foundation, Inc.
+ Copyright (C) 1999, 2000, 2002, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -41,8 +41,8 @@ package java.sql;
/**
* This interface provides a mechanism for obtaining information about
* the columns that are present in a <code>ResultSet</code>.
- * <p>
- * Note that in this class column indexes start at 1, not 0.
+ *
+ * <p> Note that in this class column indices start at 1, not 0.</p>
*
* @author Aaron M. Renn (arenn@urbanophile.com)
*/
@@ -75,207 +75,207 @@ public interface ResultSetMetaData
* This method test whether or not the column is an auto-increment column.
* Auto-increment columns are read-only.
*
- * @param index The index of the column to test.
+ * @param columnIndex The index of the column to test.
* @return <code>true</code> if the column is auto-increment, <code>false</code>
* otherwise.
* @exception SQLException If an error occurs.
*/
- boolean isAutoIncrement(int column) throws SQLException;
+ boolean isAutoIncrement(int columnIndex) throws SQLException;
/**
* This method tests whether or not a column is case sensitive in its values.
*
- * @param index The index of the column to test.
+ * @param columnIndex The index of the column to test.
* @return <code>true</code> if the column value is case sensitive,
* <code>false</code> otherwise.
* @exception SQLException If an error occurs.
*/
- boolean isCaseSensitive(int column) throws SQLException;
+ boolean isCaseSensitive(int columnIndex) throws SQLException;
/**
* This method tests whether not the specified column can be used in
* a WHERE clause.
*
- * @param index The index of the column to test.
+ * @param columnIndex The index of the column to test.
* @return <code>true</code> if the column may be used in a WHERE clause,
* <code>false</code> otherwise.
* @exception SQLException If an error occurs.
*/
- boolean isSearchable(int column) throws SQLException;
+ boolean isSearchable(int columnIndex) throws SQLException;
/**
* This method tests whether or not the column stores a monetary value.
*
- * @param index The index of the column to test.
+ * @param columnIndex The index of the column to test.
* @return <code>true</code> if the column contains a monetary value,
* <code>false</code> otherwise.
* @exception SQLException If an error occurs.
*/
- boolean isCurrency(int column) throws SQLException;
+ boolean isCurrency(int columnIndex) throws SQLException;
/**
* This method returns a value indicating whether or not the specified
* column may contain a NULL value.
*
- * @param index The index of the column to test.
+ * @param columnIndex The index of the column to test.
* @return A constant indicating whether or not the column can contain NULL,
* which will be one of <code>columnNoNulls</code>,
* <code>columnNullable</code>, or <code>columnNullableUnknown</code>.
* @exception SQLException If an error occurs.
*/
- int isNullable(int column) throws SQLException;
+ int isNullable(int columnIndex) throws SQLException;
/**
* This method tests whether or not the value of the specified column
* is signed or unsigned.
*
- * @param index The index of the column to test.
+ * @param columnIndex The index of the column to test.
* @return <code>true</code> if the column value is signed, <code>false</code>
* otherwise.
* @exception SQLException If an error occurs.
*/
- boolean isSigned(int column) throws SQLException;
+ boolean isSigned(int columnIndex) throws SQLException;
/**
* This method returns the maximum number of characters that can be used
* to display a value in this column.
*
- * @param index The index of the column to check.
+ * @param columnIndex The index of the column to check.
* @return The maximum number of characters that can be used to display a
* value for this column.
* @exception SQLException If an error occurs.
*/
- int getColumnDisplaySize(int column) throws SQLException;
+ int getColumnDisplaySize(int columnIndex) throws SQLException;
/**
* This method returns a string that should be used as a caption for this
* column for user display purposes.
*
- * @param index The index of the column to check.
+ * @param columnIndex The index of the column to check.
* @return A display string for the column.
* @exception SQLException If an error occurs.
*/
- String getColumnLabel(int column) throws SQLException;
+ String getColumnLabel(int columnIndex) throws SQLException;
/**
* This method returns the name of the specified column.
*
- * @param index The index of the column to return the name of.
+ * @param columnIndex The index of the column to return the name of.
* @return The name of the column.
* @exception SQLException If an error occurs.
*/
- String getColumnName(int column) throws SQLException;
+ String getColumnName(int columnIndex) throws SQLException;
/**
* This method returns the name of the schema that contains the specified
* column.
*
- * @param index The index of the column to check the schema name for.
+ * @param columnIndex The index of the column to check the schema name for.
* @return The name of the schema that contains the column.
* @exception SQLException If an error occurs.
*/
- String getSchemaName(int column) throws SQLException;
+ String getSchemaName(int columnIndex) throws SQLException;
/**
* This method returns the precision of the specified column, which is the
* number of decimal digits it contains.
*
- * @param index The index of the column to check the precision on.
+ * @param columnIndex The index of the column to check the precision on.
* @return The precision of the specified column.
* @exception SQLException If an error occurs.
*/
- int getPrecision(int column) throws SQLException;
+ int getPrecision(int columnIndex) throws SQLException;
/**
* This method returns the scale of the specified column, which is the
* number of digits to the right of the decimal point.
*
- * @param index The index column to check the scale of.
+ * @param columnIndex The index column to check the scale of.
* @return The scale of the column.
* @exception SQLException If an error occurs.
*/
- int getScale(int column) throws SQLException;
+ int getScale(int columnIndex) throws SQLException;
/**
* This method returns the name of the table containing the specified
* column.
*
- * @param index The index of the column to check the table name for.
+ * @param columnIndex The index of the column to check the table name for.
* @return The name of the table containing the column.
* @exception SQLException If an error occurs.
*/
- String getTableName(int column) throws SQLException;
+ String getTableName(int columnIndex) throws SQLException;
/**
* This method returns the name of the catalog containing the specified
* column.
*
- * @param index The index of the column to check the catalog name for.
+ * @param columnIndex The index of the column to check the catalog name for.
* @return The name of the catalog containing the column.
* @exception SQLException If an error occurs.
*/
- String getCatalogName(int column) throws SQLException;
+ String getCatalogName(int columnIndex) throws SQLException;
/**
* This method returns the SQL type of the specified column. This will
* be one of the constants from <code>Types</code>.
*
- * @param index The index of the column to check the SQL type of.
+ * @param columnIndex The index of the column to check the SQL type of.
* @return The SQL type for this column.
* @exception SQLException If an error occurs.
* @see Types
*/
- int getColumnType(int column) throws SQLException;
+ int getColumnType(int columnIndex) throws SQLException;
/**
* This method returns the name of the SQL type for this column.
*
- * @param index The index of the column to check the SQL type name for.
+ * @param columnIndex The index of the column to check the SQL type name for.
* @return The name of the SQL type for this column.
* @exception SQLException If an error occurs.
*/
- String getColumnTypeName(int column) throws SQLException;
+ String getColumnTypeName(int columnIndex) throws SQLException;
/**
* This method tests whether or not the specified column is read only.
*
- * @param index The index of the column to check.
+ * @param columnIndex The index of the column to check.
* @return <code>true</code> if the column is read only, <code>false</code>
* otherwise.
* @exception SQLException If an error occurs.
*/
- boolean isReadOnly(int column) throws SQLException;
+ boolean isReadOnly(int columnIndex) throws SQLException;
/**
* This method tests whether or not the column may be writable. This
* does not guarantee that a write will be successful.
*
- * @param index The index of the column to check for writability.
+ * @param columnIndex The index of the column to check for writability.
* @return <code>true</code> if the column may be writable,
* <code>false</code> otherwise.
* @exception SQLException If an error occurs.
*/
- boolean isWritable(int column) throws SQLException;
+ boolean isWritable(int columnIndex) throws SQLException;
/**
* This method tests whether or not the column is writable. This
* does guarantee that a write will be successful.
*
- * @param index The index of the column to check for writability.
+ * @param columnIndex The index of the column to check for writability.
* @return <code>true</code> if the column is writable,
* <code>false</code> otherwise.
* @exception SQLException If an error occurs.
*/
- boolean isDefinitelyWritable(int column) throws SQLException;
+ boolean isDefinitelyWritable(int columnIndex) throws SQLException;
/**
* This method returns the name of the Java class which will be used to
* create objects representing the data in this column.
*
- * @param index The index of the column to check.
+ * @param columnIndex The index of the column to check.
* @return The name of the Java class that will be used for values in
* this column.
* @exception SQLException If an error occurs.
*/
- String getColumnClassName(int column) throws SQLException;
+ String getColumnClassName(int columnIndex) throws SQLException;
}
diff --git a/libjava/classpath/java/sql/SQLData.java b/libjava/classpath/java/sql/SQLData.java
index 2ba1fb18d05..cf006e15a0d 100644
--- a/libjava/classpath/java/sql/SQLData.java
+++ b/libjava/classpath/java/sql/SQLData.java
@@ -1,5 +1,5 @@
/* SQLData.java -- Custom mapping for a user defined datatype
- Copyright (C) 1999, 2000 Free Software Foundation, Inc.
+ Copyright (C) 1999, 2000, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -57,7 +57,7 @@ public interface SQLData
* This method populates the data in the object from the specified stream.
*
* @param stream The stream to read the data from.
- * @param name The data type name of the data on the stream.
+ * @param typeName The data type name of the data on the stream.
* @exception SQLException If an error occurs.
*/
void readSQL(SQLInput stream, String typeName) throws SQLException;
diff --git a/libjava/classpath/java/sql/SQLOutput.java b/libjava/classpath/java/sql/SQLOutput.java
index 8e6c88f8cf6..e210258fa0a 100644
--- a/libjava/classpath/java/sql/SQLOutput.java
+++ b/libjava/classpath/java/sql/SQLOutput.java
@@ -1,5 +1,5 @@
/* SQLOutput.java -- Write SQL values to a stream
- Copyright (C) 1999, 2000, 2002 Free Software Foundation, Inc.
+ Copyright (C) 1999, 2000, 2002, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -59,7 +59,7 @@ public interface SQLOutput
* @param value The value to write to the stream.
* @exception SQLException If an error occurs.
*/
- void writeString(String x) throws SQLException;
+ void writeString(String value) throws SQLException;
/**
* This method writes the specified Java <code>boolean</code>
@@ -68,7 +68,7 @@ public interface SQLOutput
* @param value The value to write to the stream.
* @exception SQLException If an error occurs.
*/
- void writeBoolean(boolean x) throws SQLException;
+ void writeBoolean(boolean value) throws SQLException;
/**
* This method writes the specified Java <code>byte</code>
@@ -77,7 +77,7 @@ public interface SQLOutput
* @param value The value to write to the stream.
* @exception SQLException If an error occurs.
*/
- void writeByte(byte x) throws SQLException;
+ void writeByte(byte value) throws SQLException;
/**
* This method writes the specified Java <code>short</code>
@@ -86,7 +86,7 @@ public interface SQLOutput
* @param value The value to write to the stream.
* @exception SQLException If an error occurs.
*/
- void writeShort(short x) throws SQLException;
+ void writeShort(short value) throws SQLException;
/**
* This method writes the specified Java <code>int</code>
@@ -95,7 +95,7 @@ public interface SQLOutput
* @param value The value to write to the stream.
* @exception SQLException If an error occurs.
*/
- void writeInt(int x) throws SQLException;
+ void writeInt(int value) throws SQLException;
/**
* This method writes the specified Java <code>long</code>
@@ -104,7 +104,7 @@ public interface SQLOutput
* @param value The value to write to the stream.
* @exception SQLException If an error occurs.
*/
- void writeLong(long x) throws SQLException;
+ void writeLong(long value) throws SQLException;
/**
* This method writes the specified Java <code>float</code>
@@ -113,7 +113,7 @@ public interface SQLOutput
* @param value The value to write to the stream.
* @exception SQLException If an error occurs.
*/
- void writeFloat(float x) throws SQLException;
+ void writeFloat(float value) throws SQLException;
/**
* This method writes the specified Java <code>double</code>
@@ -122,7 +122,7 @@ public interface SQLOutput
* @param value The value to write to the stream.
* @exception SQLException If an error occurs.
*/
- void writeDouble(double x) throws SQLException;
+ void writeDouble(double value) throws SQLException;
/**
* This method writes the specified Java <code>BigDecimal</code>
@@ -131,7 +131,7 @@ public interface SQLOutput
* @param value The value to write to the stream.
* @exception SQLException If an error occurs.
*/
- void writeBigDecimal(BigDecimal x) throws SQLException;
+ void writeBigDecimal(BigDecimal value) throws SQLException;
/**
* This method writes the specified Java <code>byte</code> array
@@ -140,7 +140,7 @@ public interface SQLOutput
* @param value The value to write to the stream.
* @exception SQLException If an error occurs.
*/
- void writeBytes(byte[] x) throws SQLException;
+ void writeBytes(byte[] value) throws SQLException;
/**
* This method writes the specified Java <code>java.sql.Date</code>
@@ -149,7 +149,7 @@ public interface SQLOutput
* @param value The value to write to the stream.
* @exception SQLException If an error occurs.
*/
- void writeDate(Date x) throws SQLException;
+ void writeDate(Date value) throws SQLException;
/**
* This method writes the specified Java <code>java.sql.Time</code>
@@ -158,7 +158,7 @@ public interface SQLOutput
* @param value The value to write to the stream.
* @exception SQLException If an error occurs.
*/
- void writeTime(Time x) throws SQLException;
+ void writeTime(Time value) throws SQLException;
/**
* This method writes the specified Java <code>java.sql.Timestamp</code>
@@ -167,34 +167,34 @@ public interface SQLOutput
* @param value The value to write to the stream.
* @exception SQLException If an error occurs.
*/
- void writeTimestamp(Timestamp x) throws SQLException;
+ void writeTimestamp(Timestamp value) throws SQLException;
/**
* This method writes the specified Java character stream
* to the SQL stream.
*
- * @param value The value to write to the stream.
+ * @param stream The stream that holds the character data to write.
* @exception SQLException If an error occurs.
*/
- void writeCharacterStream(Reader x) throws SQLException;
+ void writeCharacterStream(Reader stream) throws SQLException;
/**
* This method writes the specified ASCII text stream
* to the SQL stream.
*
- * @param value The value to write to the stream.
+ * @param stream The stream that holds the ASCII data to write.
* @exception SQLException If an error occurs.
*/
- void writeAsciiStream(InputStream x) throws SQLException;
+ void writeAsciiStream(InputStream stream) throws SQLException;
/**
* This method writes the specified uninterpreted binary byte stream
* to the SQL stream.
*
- * @param value The value to write to the stream.
+ * @param stream The stream that holds the binary data to write.
* @exception SQLException If an error occurs.
*/
- void writeBinaryStream(InputStream x) throws SQLException;
+ void writeBinaryStream(InputStream stream) throws SQLException;
/**
* This method writes the specified Java <code>SQLData</code> object
@@ -203,43 +203,48 @@ public interface SQLOutput
* @param value The value to write to the stream.
* @exception SQLException If an error occurs.
*/
- void writeObject(SQLData x) throws SQLException;
+ void writeObject(SQLData value) throws SQLException;
/**
* This method writes the specified Java SQL <code>Ref</code> object
* to the SQL stream.
*
- * @param value The value to write to the stream.
+ * @param value The <code>Ref</code> object to write to the stream.
* @exception SQLException If an error occurs.
+ * @see Ref
*/
- void writeRef(Ref x) throws SQLException;
+ void writeRef(Ref value) throws SQLException;
+
/**
* This method writes the specified Java SQL <code>Blob</code> object
* to the SQL stream.
*
- * @param value The value to write to the stream.
+ * @param value The <code>Blob</code> object to write to the stream.
* @exception SQLException If an error occurs.
+ * @see Blob
*/
- void writeBlob(Blob x) throws SQLException;
+ void writeBlob(Blob value) throws SQLException;
/**
* This method writes the specified Java SQL <code>Clob</code> object
* to the SQL stream.
*
- * @param value The value to write to the stream.
+ * @param value The <code>Clob</code> object to write to the stream.
* @exception SQLException If an error occurs.
+ * @see Clob
*/
- void writeClob(Clob x) throws SQLException;
+ void writeClob(Clob value) throws SQLException;
/**
* This method writes the specified Java SQL <code>Struct</code> object
* to the SQL stream.
*
- * @param value The value to write to the stream.
+ * @param value The <code>Struct</code> object to write to the stream.
* @exception SQLException If an error occurs.
+ * @see Struct
*/
- void writeStruct(Struct x) throws SQLException;
+ void writeStruct(Struct value) throws SQLException;
/**
* This method writes the specified Java SQL <code>Array</code> object
@@ -248,10 +253,15 @@ public interface SQLOutput
* @param value The value to write to the stream.
* @exception SQLException If an error occurs.
*/
- void writeArray(Array x) throws SQLException;
+ void writeArray(Array value) throws SQLException;
/**
+ * This method writes the specified <code>java.net.URL</code> object to the
+ * SQL stream.
+ *
+ * @param value The value to write to the stream.
+ * @exception SQLException If an error occurs.
* @since 1.4
*/
- void writeURL(URL x) throws SQLException;
+ void writeURL(URL value) throws SQLException;
}
diff --git a/libjava/classpath/java/sql/SQLWarning.java b/libjava/classpath/java/sql/SQLWarning.java
index 841d137e13a..d9c7e354ed6 100644
--- a/libjava/classpath/java/sql/SQLWarning.java
+++ b/libjava/classpath/java/sql/SQLWarning.java
@@ -1,5 +1,5 @@
/* SQLWarning.java -- Database access warnings.
- Copyright (C) 1999, 2000, 2002 Free Software Foundation, Inc.
+ Copyright (C) 1999, 2000, 2002, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -56,9 +56,9 @@ public class SQLWarning extends SQLException
* @param SQLState A string containing the SQL state of the error.
* @param vendorCode The vendor error code associated with this error.
*/
- public SQLWarning(String reason, String SQLState, int vendorCode)
+ public SQLWarning(String message, String SQLState, int vendorCode)
{
- super(reason, SQLState, vendorCode);
+ super(message, SQLState, vendorCode);
}
/**
diff --git a/libjava/classpath/java/sql/Statement.java b/libjava/classpath/java/sql/Statement.java
index 42e8e8e8816..195600eaa2c 100644
--- a/libjava/classpath/java/sql/Statement.java
+++ b/libjava/classpath/java/sql/Statement.java
@@ -1,5 +1,5 @@
/* Statement.java -- Interface for executing SQL statements.
- Copyright (C) 1999, 2000, 2002 Free Software Foundation, Inc.
+ Copyright (C) 1999, 2000, 2002, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -91,10 +91,10 @@ public interface Statement
/**
* This method sets the limit for the maximum length of any column in bytes.
*
- * @param maxsize The new maximum length of any column in bytes.
+ * @param maxSize The new maximum length of any column in bytes.
* @exception SQLException If an error occurs.
*/
- void setMaxFieldSize(int max) throws SQLException;
+ void setMaxFieldSize(int maxSize) throws SQLException;
/**
* This method returns the maximum possible number of rows in a result set.
@@ -108,20 +108,20 @@ public interface Statement
* This method sets the maximum number of rows that can be present in a
* result set.
*
- * @param maxrows The maximum possible number of rows in a result set.
+ * @param maxRows The maximum possible number of rows in a result set.
* @exception SQLException If an error occurs.
*/
- void setMaxRows(int max) throws SQLException;
+ void setMaxRows(int maxRows) throws SQLException;
/**
* This method sets the local escape processing mode on or off. The
* default value is on.
*
* @param escape <code>true</code> to enable local escape processing,
- * <code>false</code> to disable it.
+ * <code>false</code> to disable it.
* @exception SQLException If an error occurs.
*/
- void setEscapeProcessing(boolean enable) throws SQLException;
+ void setEscapeProcessing(boolean escape) throws SQLException;
/**
* The method returns the number of seconds a statement may be in process
@@ -136,7 +136,7 @@ public interface Statement
* This method sets the number of seconds a statement may be in process
* before timing out. A value of 0 means there is no timeout.
*
- * @param timeout The new SQL statement timeout value.
+ * @param seconds The new SQL statement timeout value.
* @exception SQLException If an error occurs.
*/
void setQueryTimeout(int seconds) throws SQLException;
@@ -192,7 +192,10 @@ public interface Statement
* @return The result set of the query, or <code>null</code> if there was
* no result set (for example, if the statement was an UPDATE).
* @exception SQLException If an error occurs.
- * @see execute
+ * @see #execute(String)
+ * @see #execute(String, int)
+ * @see #execute(String, int[])
+ * @see #execute(String, String[])
*/
ResultSet getResultSet() throws SQLException;
@@ -203,7 +206,10 @@ public interface Statement
* @return The update count of the query, or -1 if there was no update
* count (for example, if the statement was a SELECT).
* @exception SQLException If an error occurs.
- * @see execute
+ * @see #execute(String)
+ * @see #execute(String, int)
+ * @see #execute(String, int[])
+ * @see #execute(String, String[])
*/
int getUpdateCount() throws SQLException;
@@ -215,7 +221,10 @@ public interface Statement
* <code>false</code> otherwise (for example, the next result is an
* update count).
* @exception SQLException If an error occurs.
- * @see execute
+ * @see #execute(String)
+ * @see #execute(String, int)
+ * @see #execute(String, int[])
+ * @see #execute(String, String[])
*/
boolean getMoreResults() throws SQLException;
@@ -241,11 +250,11 @@ public interface Statement
* This method informs the driver how many rows it should fetch from the
* database at a time.
*
- * @param numrows The number of rows the driver should fetch at a time
- * to populate the result set.
+ * @param numRows The number of rows the driver should fetch at a time
+ * to populate the result set.
* @exception SQLException If an error occurs.
*/
- void setFetchSize(int rows) throws SQLException;
+ void setFetchSize(int numRows) throws SQLException;
/**
* This method returns the number of rows the driver believes should be
diff --git a/libjava/classpath/java/sql/Time.java b/libjava/classpath/java/sql/Time.java
index 57551528b43..2d1a433fa41 100644
--- a/libjava/classpath/java/sql/Time.java
+++ b/libjava/classpath/java/sql/Time.java
@@ -1,5 +1,6 @@
/* Time.java -- Wrapper around java.util.Date
- Copyright (C) 1999, 2000, 2002, 2003, 2005 Free Software Foundation, Inc.
+ Copyright (C) 1999, 2000, 2002, 2003, 2005, 2006
+ Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -177,10 +178,10 @@ public class Time extends java.util.Date
/**
* This method initializes a new instance of this class with the
- * specified time value representing the number of seconds since
+ * specified time value representing the number of milliseconds since
* Jan 1, 1970 at 12:00 midnight GMT.
*
- * @param time The time value to intialize this <code>Time</code> to.
+ * @param date The time value to intialize this <code>Time</code> to.
*/
public Time(long date)
{
diff --git a/libjava/classpath/java/sql/Timestamp.java b/libjava/classpath/java/sql/Timestamp.java
index f3459b22f3e..66a57641a02 100644
--- a/libjava/classpath/java/sql/Timestamp.java
+++ b/libjava/classpath/java/sql/Timestamp.java
@@ -1,5 +1,5 @@
/* Time.java -- Wrapper around java.util.Date
- Copyright (C) 1999, 2000, 2003, 2004 Free Software Foundation, Inc.
+ Copyright (C) 1999, 2000, 2003, 2004, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -143,7 +143,7 @@ public class Timestamp extends java.util.Date
* specified time value representing the number of milliseconds since
* Jan 1, 1970 at 12:00 midnight GMT.
*
- * @param time The time value to intialize this <code>Time</code> to.
+ * @param date The time value to intialize this <code>Time</code> to.
*/
public Timestamp(long date)
{
@@ -279,12 +279,13 @@ public class Timestamp extends java.util.Date
}
/**
- * Compare two Timestamp
- * @param when the other Timestamp.
- * @return 0, if the date represented
- * by obj is exactly the same as the time represented by this
- * object, a negative if this Timestamp is before the other Timestamp, and
- * a positive value otherwise.
+ * Compares this <code>Timestamp</code> to another one.
+ *
+ * @param ts The other Timestamp.
+ * @return <code>0</code>, if both <code>Timestamp</code>'s represent exactly
+ * the same date, a negative value if this <code>Timestamp</code> is
+ * before the specified <code>Timestamp</code> and a positive value
+ * otherwise.
* @since 1.2
*/
public int compareTo(Timestamp ts)
@@ -297,15 +298,18 @@ public class Timestamp extends java.util.Date
}
/**
- * Compares this Timestamp to another. This behaves like
+ * Compares this <code>Timestamp</code> to another one. This behaves like
* <code>compareTo(Timestamp)</code>, but it may throw a
- * <code>ClassCastException</code>
- * @param obj the other Timestamp.
- * @return 0, if the Timestamp represented
- * by obj is exactly the same as the time represented by this
- * object, a negative if this Timestamp is before the other Timestamp, and
- * a positive value otherwise.
+ * <code>ClassCastException</code>, if the specified object is not of type
+ * <code>Timestamp</code>.
+ *
+ * @param obj The object to compare with.
+ * @return <code>0</code>, if both <code>Timestamp</code>'s represent exactly
+ * the same date, a negative value if this <code>Timestamp</code> is
+ * before the specified <code>Timestamp</code> and a positive value
+ * otherwise.
* @exception ClassCastException if obj is not of type Timestamp.
+ * @see #compareTo(Timestamp)
* @since 1.2
*/
public int compareTo(Object obj)
diff --git a/libjava/classpath/java/text/AttributedCharacterIterator.java b/libjava/classpath/java/text/AttributedCharacterIterator.java
index 8413c203130..37c7450b2c8 100644
--- a/libjava/classpath/java/text/AttributedCharacterIterator.java
+++ b/libjava/classpath/java/text/AttributedCharacterIterator.java
@@ -127,13 +127,13 @@ public interface AttributedCharacterIterator extends CharacterIterator
*/
protected Object readResolve() throws InvalidObjectException
{
- if (this.equals (READING))
+ if (getName().equals(READING.getName()))
return READING;
- if (this.equals (LANGUAGE))
+ if (getName().equals(LANGUAGE.getName()))
return LANGUAGE;
- if (this.equals (INPUT_METHOD_SEGMENT))
+ if (getName().equals(INPUT_METHOD_SEGMENT.getName()))
return INPUT_METHOD_SEGMENT;
throw new InvalidObjectException ("Can't resolve Attribute: "
diff --git a/libjava/classpath/java/text/Bidi.java b/libjava/classpath/java/text/Bidi.java
index 57b9a88dfa7..43743604570 100644
--- a/libjava/classpath/java/text/Bidi.java
+++ b/libjava/classpath/java/text/Bidi.java
@@ -1,5 +1,5 @@
/* Bidi.java -- Bidirectional Algorithm implementation
- Copyright (C) 2005 Free Software Foundation, Inc.
+ Copyright (C) 2005, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -38,18 +38,939 @@ exception statement from your version. */
package java.text;
+import java.awt.font.NumericShaper;
+import java.awt.font.TextAttribute;
+import java.util.ArrayList;
+
+
/**
* Bidirectional Algorithm implementation.
*
- * TODO/FIXME Only one method <code>requiresBidi</code> is implemented
- * for now by using <code>Character</code>. The full algorithm is <a
- * href="http://www.unicode.org/unicode/reports/tr9/">Unicode Standard
- * Annex #9: The Bidirectional Algorithm</a>. A full implementation is
- * <a href="http://fribidi.org/">GNU FriBidi</a>.
+ * The full algorithm is
+ * <a href="http://www.unicode.org/unicode/reports/tr9/">Unicode Standard
+ * Annex #9: The Bidirectional Algorithm</a>.
+ *
+ * @since 1.4
*/
-public class Bidi
+public final class Bidi
{
/**
+ * This indicates that a strongly directional character in the text should
+ * set the initial direction, but if no such character is found, then the
+ * initial direction will be left-to-right.
+ */
+ public static final int DIRECTION_DEFAULT_LEFT_TO_RIGHT = -2;
+
+ /**
+ * This indicates that a strongly directional character in the text should
+ * set the initial direction, but if no such character is found, then the
+ * initial direction will be right-to-left.
+ */
+ public static final int DIRECTION_DEFAULT_RIGHT_TO_LEFT = -1;
+
+ /**
+ * This indicates that the initial direction should be left-to-right.
+ */
+ public static final int DIRECTION_LEFT_TO_RIGHT = 0;
+
+ /**
+ * This indicates that the initial direction should be right-to-left.
+ */
+ public static final int DIRECTION_RIGHT_TO_LEFT = 1;
+
+ // Flags used when computing the result.
+ private static final int LTOR = 1 << DIRECTION_LEFT_TO_RIGHT;
+ private static final int RTOL = 1 << DIRECTION_RIGHT_TO_LEFT;
+
+ // The text we are examining, and the starting offset.
+ // If we had a better way to handle createLineBidi, we wouldn't
+ // need this at all -- which for the String case would be an
+ // efficiency win.
+ private char[] text;
+ private int textOffset;
+ // The embeddings corresponding to the text, and the starting offset.
+ private byte[] embeddings;
+ private int embeddingOffset;
+ // The length of the text (and embeddings) to use.
+ private int length;
+ // The flags.
+ private int flags;
+
+ // All instance fields following this point are initialized
+ // during analysis. Fields before this must be set by the constructor.
+
+ // The initial embedding level.
+ private int baseEmbedding;
+ // The type of each character in the text.
+ private byte[] types;
+ // The levels we compute.
+ private byte[] levels;
+
+ // A list of indices where a formatting code was found. These
+ // are indicies into the original text -- not into the text after
+ // the codes have been removed.
+ private ArrayList formatterIndices;
+
+ // Indices of the starts of runs in the text.
+ private int[] runs;
+
+ // A convenience field where we keep track of what kinds of runs
+ // we've seen.
+ private int resultFlags;
+
+ /**
+ * Create a new Bidi object given an attributed character iterator.
+ * This constructor will examine various attributes of the text:
+ * <ul>
+ * <li> {@link TextAttribute#RUN_DIRECTION} is used to determine the
+ * paragraph's base embedding level. This constructor will recognize
+ * either {@link TextAttribute#RUN_DIRECTION_LTR} or
+ * {@link TextAttribute#RUN_DIRECTION_RTL}. If neither is given,
+ * {@link #DIRECTION_DEFAULT_LEFT_TO_RIGHT} is assumed.
+ * </li>
+ *
+ * <li> If {@link TextAttribute#NUMERIC_SHAPING} is seen, then numeric
+ * shaping will be done before the Bidi algorithm is run.
+ * </li>
+ *
+ * <li> If {@link TextAttribute#BIDI_EMBEDDING} is seen on a given
+ * character, then the value of this attribute will be used as an
+ * embedding level override.
+ * </li>
+ * </ul>
+ * @param iter the attributed character iterator to use
+ */
+ public Bidi(AttributedCharacterIterator iter)
+ {
+ // If set, this attribute should be set on all characters.
+ // We don't check this (should we?) but we do assume that we
+ // can simply examine the first character.
+ Object val = iter.getAttribute(TextAttribute.RUN_DIRECTION);
+ if (val == TextAttribute.RUN_DIRECTION_LTR)
+ this.flags = DIRECTION_LEFT_TO_RIGHT;
+ else if (val == TextAttribute.RUN_DIRECTION_RTL)
+ this.flags = DIRECTION_RIGHT_TO_LEFT;
+ else
+ this.flags = DIRECTION_DEFAULT_LEFT_TO_RIGHT;
+
+ // Likewise this attribute should be specified on the whole text.
+ // We read it here and then, if it is set, we apply the numeric shaper
+ // to the text before processing it.
+ NumericShaper shaper = null;
+ val = iter.getAttribute(TextAttribute.NUMERIC_SHAPING);
+ if (val instanceof NumericShaper)
+ shaper = (NumericShaper) val;
+
+ char[] text = new char[iter.getEndIndex() - iter.getBeginIndex()];
+ this.embeddings = new byte[this.text.length];
+ this.embeddingOffset = 0;
+ this.length = text.length;
+ for (int i = 0; i < this.text.length; ++i)
+ {
+ this.text[i] = iter.current();
+
+ val = iter.getAttribute(TextAttribute.BIDI_EMBEDDING);
+ if (val instanceof Integer)
+ {
+ int ival = ((Integer) val).intValue();
+ byte bval;
+ if (ival < -62 || ival > 62)
+ bval = 0;
+ else
+ bval = (byte) ival;
+ this.embeddings[i] = bval;
+ }
+ }
+
+ // Invoke the numeric shaper, if specified.
+ if (shaper != null)
+ shaper.shape(this.text, 0, this.length);
+
+ runBidi();
+ }
+
+ /**
+ * Create a new Bidi object with the indicated text and, possibly, explicit
+ * embedding settings.
+ *
+ * If the embeddings array is null, it is ignored. Otherwise it is taken to
+ * be explicit embedding settings corresponding to the text. Positive values
+ * from 1 to 61 are embedding levels, and negative values from -1 to -61 are
+ * embedding overrides. (FIXME: not at all clear what this really means.)
+ *
+ * @param text the text to use
+ * @param offset the offset of the first character of the text
+ * @param embeddings the explicit embeddings, or null if there are none
+ * @param embedOffset the offset of the first embedding value to use
+ * @param length the length of both the text and the embeddings
+ * @param flags a flag indicating the base embedding direction
+ */
+ public Bidi(char[] text, int offset, byte[] embeddings, int embedOffset,
+ int length, int flags)
+ {
+ if (flags != DIRECTION_DEFAULT_LEFT_TO_RIGHT
+ && flags != DIRECTION_DEFAULT_RIGHT_TO_LEFT
+ && flags != DIRECTION_LEFT_TO_RIGHT
+ && flags != DIRECTION_RIGHT_TO_LEFT)
+ throw new IllegalArgumentException("unrecognized 'flags' argument: "
+ + flags);
+ this.text = text;
+ this.textOffset = offset;
+ this.embeddings = embeddings;
+ this.embeddingOffset = embedOffset;
+ this.length = length;
+ this.flags = flags;
+
+ runBidi();
+ }
+
+ /**
+ * Create a new Bidi object using the contents of the given String
+ * as the text.
+ * @param text the text to use
+ * @param flags a flag indicating the base embedding direction
+ */
+ public Bidi(String text, int flags)
+ {
+ if (flags != DIRECTION_DEFAULT_LEFT_TO_RIGHT
+ && flags != DIRECTION_DEFAULT_RIGHT_TO_LEFT
+ && flags != DIRECTION_LEFT_TO_RIGHT
+ && flags != DIRECTION_RIGHT_TO_LEFT)
+ throw new IllegalArgumentException("unrecognized 'flags' argument: "
+ + flags);
+
+ // This is inefficient, but it isn't clear whether it matters.
+ // If it does we can change our implementation a bit to allow either
+ // a String or a char[].
+ this.text = text.toCharArray();
+ this.textOffset = 0;
+ this.embeddings = null;
+ this.embeddingOffset = 0;
+ this.length = text.length();
+ this.flags = flags;
+
+ runBidi();
+ }
+
+ /**
+ * Implementation function which computes the initial type of
+ * each character in the input.
+ */
+ private void computeTypes()
+ {
+ types = new byte[length];
+ for (int i = 0; i < length; ++i)
+ types[i] = Character.getDirectionality(text[textOffset + i]);
+ }
+
+ /**
+ * An internal function which implements rules P2 and P3.
+ * This computes the base embedding level.
+ * @return the paragraph's base embedding level
+ */
+ private int computeParagraphEmbeddingLevel()
+ {
+ // First check to see if the user supplied a directionality override.
+ if (flags == DIRECTION_LEFT_TO_RIGHT
+ || flags == DIRECTION_RIGHT_TO_LEFT)
+ return flags;
+
+ // This implements rules P2 and P3.
+ // (Note that we don't need P1, as the user supplies
+ // a paragraph.)
+ for (int i = 0; i < length; ++i)
+ {
+ int dir = types[i];
+ if (dir == Character.DIRECTIONALITY_LEFT_TO_RIGHT)
+ return DIRECTION_LEFT_TO_RIGHT;
+ if (dir == Character.DIRECTIONALITY_RIGHT_TO_LEFT
+ || dir == Character.DIRECTIONALITY_RIGHT_TO_LEFT)
+ return DIRECTION_RIGHT_TO_LEFT;
+ }
+ return (flags == DIRECTION_DEFAULT_LEFT_TO_RIGHT
+ ? DIRECTION_LEFT_TO_RIGHT
+ : DIRECTION_RIGHT_TO_LEFT);
+ }
+
+ /**
+ * An internal function which implements rules X1 through X9.
+ * This computes the initial levels for the text, handling
+ * explicit overrides and embeddings.
+ */
+ private void computeExplicitLevels()
+ {
+ levels = new byte[length];
+ byte currentEmbedding = (byte) baseEmbedding;
+ // The directional override is a Character directionality
+ // constant. -1 means there is no override.
+ byte directionalOverride = -1;
+ // The stack of pushed embeddings, and the stack pointer.
+ // Note that because the direction is inherent in the depth,
+ // and because we have a bit left over in a byte, we can encode
+ // the override, if any, directly in this value on the stack.
+ final int MAX_DEPTH = 62;
+ byte[] embeddingStack = new byte[MAX_DEPTH];
+ int sp = 0;
+
+ for (int i = 0; i < length; ++i)
+ {
+ // If we see an explicit embedding, we use that, even if
+ // the current character is itself a directional override.
+ if (embeddings != null && embeddings[embeddingOffset + i] != 0)
+ {
+ // It isn't at all clear what we're supposed to do here.
+ // What does a negative value really mean?
+ // Should we push on the embedding stack here?
+ currentEmbedding = embeddings[embeddingOffset + i];
+ if (currentEmbedding < 0)
+ {
+ currentEmbedding = (byte) -currentEmbedding;
+ directionalOverride
+ = (((currentEmbedding % 2) == 0)
+ ? Character.DIRECTIONALITY_LEFT_TO_RIGHT
+ : Character.DIRECTIONALITY_RIGHT_TO_LEFT);
+ }
+ else
+ directionalOverride = -1;
+ continue;
+ }
+ // No explicit embedding.
+ boolean isLtoR = false;
+ boolean isSpecial = true;
+ switch (types[i])
+ {
+ case Character.DIRECTIONALITY_LEFT_TO_RIGHT_EMBEDDING:
+ case Character.DIRECTIONALITY_LEFT_TO_RIGHT_OVERRIDE:
+ isLtoR = true;
+ // Fall through.
+ case Character.DIRECTIONALITY_RIGHT_TO_LEFT_EMBEDDING:
+ case Character.DIRECTIONALITY_RIGHT_TO_LEFT_OVERRIDE:
+ {
+ byte newEmbedding;
+ if (isLtoR)
+ {
+ // Least greater even.
+ newEmbedding = (byte) ((currentEmbedding & ~1) + 2);
+ }
+ else
+ {
+ // Least greater odd.
+ newEmbedding = (byte) ((currentEmbedding + 1) | 1);
+ }
+ // FIXME: we don't properly handle invalid pushes.
+ if (newEmbedding < MAX_DEPTH)
+ {
+ // The new level is valid. Push the old value.
+ // See above for a comment on the encoding here.
+ if (directionalOverride != -1)
+ currentEmbedding |= Byte.MIN_VALUE;
+ embeddingStack[sp++] = currentEmbedding;
+ currentEmbedding = newEmbedding;
+ if (types[i] == Character.DIRECTIONALITY_LEFT_TO_RIGHT_OVERRIDE)
+ directionalOverride = Character.DIRECTIONALITY_LEFT_TO_RIGHT;
+ else if (types[i] == Character.DIRECTIONALITY_RIGHT_TO_LEFT_OVERRIDE)
+ directionalOverride = Character.DIRECTIONALITY_RIGHT_TO_LEFT;
+ else
+ directionalOverride = -1;
+ }
+ }
+ break;
+ case Character.DIRECTIONALITY_POP_DIRECTIONAL_FORMAT:
+ {
+ // FIXME: we don't properly handle a pop with a corresponding
+ // invalid push.
+ if (sp == 0)
+ {
+ // We saw a pop without a push. Just ignore it.
+ break;
+ }
+ byte newEmbedding = embeddingStack[--sp];
+ currentEmbedding = (byte) (newEmbedding & 0x7f);
+ if (newEmbedding < 0)
+ directionalOverride
+ = (((newEmbedding & 1) == 0)
+ ? Character.DIRECTIONALITY_LEFT_TO_RIGHT
+ : Character.DIRECTIONALITY_RIGHT_TO_LEFT);
+ else
+ directionalOverride = -1;
+ }
+ break;
+ default:
+ isSpecial = false;
+ break;
+ }
+ levels[i] = currentEmbedding;
+ if (isSpecial)
+ {
+ // Mark this character for removal.
+ if (formatterIndices == null)
+ formatterIndices = new ArrayList();
+ formatterIndices.add(Integer.valueOf(i));
+ }
+ else if (directionalOverride != -1)
+ types[i] = directionalOverride;
+ }
+
+ // Remove the formatting codes and update both the arrays
+ // and 'length'. It would be more efficient not to remove
+ // these codes, but it is also more complicated. Also, the
+ // Unicode algorithm reference does not properly describe
+ // how this is to be done -- from what I can tell, their suggestions
+ // in this area will not yield the correct results.
+ if (formatterIndices == null)
+ return;
+ int output = 0, input = 0;
+ final int size = formatterIndices.size();
+ for (int i = 0; i <= size; ++i)
+ {
+ int nextFmt;
+ if (i == size)
+ nextFmt = length;
+ else
+ nextFmt = ((Integer) formatterIndices.get(i)).intValue();
+ // Non-formatter codes are from 'input' to 'nextFmt'.
+ int len = nextFmt - input;
+ System.arraycopy(levels, input, levels, output, len);
+ System.arraycopy(types, input, types, output, len);
+ output += len;
+ input = nextFmt + 1;
+ }
+ length -= formatterIndices.size();
+ }
+
+ /**
+ * An internal function to compute the boundaries of runs
+ * in the text. It isn't strictly necessary to do this, but
+ * it lets us write some following passes in a less complicated
+ * way. Also it lets us efficiently implement some of the public
+ * methods. A run is simply a sequence of characters at the
+ * same level.
+ */
+ private void computeRuns()
+ {
+ int runCount = 0;
+ int currentEmbedding = baseEmbedding;
+ for (int i = 0; i < length; ++i)
+ {
+ if (levels[i] != currentEmbedding)
+ {
+ currentEmbedding = levels[i];
+ ++runCount;
+ }
+ }
+
+ // This may be called multiple times. If so, and if
+ // the number of runs has not changed, then don't bother
+ // allocating a new array.
+ if (runs == null || runs.length != runCount + 1)
+ runs = new int[runCount + 1];
+ int where = 0;
+ int lastRunStart = 0;
+ currentEmbedding = baseEmbedding;
+ for (int i = 0; i < length; ++i)
+ {
+ if (levels[i] != currentEmbedding)
+ {
+ runs[where++] = lastRunStart;
+ lastRunStart = i;
+ currentEmbedding = levels[i];
+ }
+ }
+ runs[where++] = lastRunStart;
+ }
+
+ /**
+ * An internal method to resolve weak types. This implements
+ * rules W1 through W7.
+ */
+ private void resolveWeakTypes()
+ {
+ final int runCount = getRunCount();
+
+ int previousLevel = baseEmbedding;
+ for (int run = 0; run < runCount; ++run)
+ {
+ int start = getRunStart(run);
+ int end = getRunLimit(run);
+ int level = getRunLevel(run);
+
+ // These are the names used in the Bidi algorithm.
+ byte sor = (((Math.max(previousLevel, level) % 2) == 0)
+ ? Character.DIRECTIONALITY_LEFT_TO_RIGHT
+ : Character.DIRECTIONALITY_RIGHT_TO_LEFT);
+ int nextLevel;
+ if (run == runCount - 1)
+ nextLevel = baseEmbedding;
+ else
+ nextLevel = getRunLevel(run + 1);
+ byte eor = (((Math.max(level, nextLevel) % 2) == 0)
+ ? Character.DIRECTIONALITY_LEFT_TO_RIGHT
+ : Character.DIRECTIONALITY_RIGHT_TO_LEFT);
+
+ byte prevType = sor;
+ byte prevStrongType = sor;
+ for (int i = start; i < end; ++i)
+ {
+ final byte nextType = (i == end - 1) ? eor : types[i + 1];
+
+ // Rule W1: change NSM to the prevailing direction.
+ if (types[i] == Character.DIRECTIONALITY_NONSPACING_MARK)
+ types[i] = prevType;
+ else
+ prevType = types[i];
+
+ // Rule W2: change EN to AN in some cases.
+ if (types[i] == Character.DIRECTIONALITY_EUROPEAN_NUMBER)
+ {
+ if (prevStrongType == Character.DIRECTIONALITY_RIGHT_TO_LEFT_ARABIC)
+ types[i] = Character.DIRECTIONALITY_ARABIC_NUMBER;
+ }
+ else if (types[i] == Character.DIRECTIONALITY_LEFT_TO_RIGHT
+ || types[i] == Character.DIRECTIONALITY_RIGHT_TO_LEFT
+ || types[i] == Character.DIRECTIONALITY_RIGHT_TO_LEFT_ARABIC)
+ prevStrongType = types[i];
+
+ // Rule W3: change AL to R.
+ if (types[i] == Character.DIRECTIONALITY_RIGHT_TO_LEFT_ARABIC)
+ types[i] = Character.DIRECTIONALITY_RIGHT_TO_LEFT;
+
+ // Rule W4: handle separators between two numbers.
+ if (prevType == Character.DIRECTIONALITY_EUROPEAN_NUMBER
+ && nextType == Character.DIRECTIONALITY_EUROPEAN_NUMBER)
+ {
+ if (types[i] == Character.DIRECTIONALITY_EUROPEAN_NUMBER_SEPARATOR
+ || types[i] == Character.DIRECTIONALITY_COMMON_NUMBER_SEPARATOR)
+ types[i] = nextType;
+ }
+ else if (prevType == Character.DIRECTIONALITY_ARABIC_NUMBER
+ && nextType == Character.DIRECTIONALITY_ARABIC_NUMBER
+ && types[i] == Character.DIRECTIONALITY_COMMON_NUMBER_SEPARATOR)
+ types[i] = nextType;
+
+ // Rule W5: change a sequence of european terminators to
+ // european numbers, if they are adjacent to european numbers.
+ // We also include BN characters in this.
+ if (types[i] == Character.DIRECTIONALITY_EUROPEAN_NUMBER_TERMINATOR
+ || types[i] == Character.DIRECTIONALITY_BOUNDARY_NEUTRAL)
+ {
+ if (prevType == Character.DIRECTIONALITY_EUROPEAN_NUMBER)
+ types[i] = prevType;
+ else
+ {
+ // Look ahead to see if there is an EN terminating this
+ // sequence of ETs.
+ int j = i + 1;
+ while (j < end
+ && (types[j] == Character.DIRECTIONALITY_EUROPEAN_NUMBER_TERMINATOR
+ || types[j] == Character.DIRECTIONALITY_BOUNDARY_NEUTRAL))
+ ++j;
+ if (j < end
+ && types[j] == Character.DIRECTIONALITY_EUROPEAN_NUMBER)
+ {
+ // Change them all to EN now.
+ for (int k = i; k < j; ++k)
+ types[k] = Character.DIRECTIONALITY_EUROPEAN_NUMBER;
+ }
+ }
+ }
+
+ // Rule W6: separators and terminators change to ON.
+ // Again we include BN.
+ if (types[i] == Character.DIRECTIONALITY_EUROPEAN_NUMBER_TERMINATOR
+ || types[i] == Character.DIRECTIONALITY_EUROPEAN_NUMBER_TERMINATOR
+ || types[i] == Character.DIRECTIONALITY_COMMON_NUMBER_SEPARATOR
+ || types[i] == Character.DIRECTIONALITY_BOUNDARY_NEUTRAL)
+ types[i] = Character.DIRECTIONALITY_OTHER_NEUTRALS;
+
+ // Rule W7: change european number types.
+ if (prevStrongType == Character.DIRECTIONALITY_LEFT_TO_RIGHT
+ && types[i] == Character.DIRECTIONALITY_EUROPEAN_NUMBER)
+ types[i] = prevStrongType;
+ }
+
+ previousLevel = level;
+ }
+ }
+
+ /**
+ * An internal method to resolve neutral types. This implements
+ * rules N1 and N2.
+ */
+ private void resolveNeutralTypes()
+ {
+ // This implements rules N1 and N2.
+ final int runCount = getRunCount();
+
+ int previousLevel = baseEmbedding;
+ for (int run = 0; run < runCount; ++run)
+ {
+ int start = getRunStart(run);
+ int end = getRunLimit(run);
+ int level = getRunLevel(run);
+
+ byte embeddingDirection
+ = (((level % 2) == 0) ? Character.DIRECTIONALITY_LEFT_TO_RIGHT
+ : Character.DIRECTIONALITY_RIGHT_TO_LEFT);
+ // These are the names used in the Bidi algorithm.
+ byte sor = (((Math.max(previousLevel, level) % 2) == 0)
+ ? Character.DIRECTIONALITY_LEFT_TO_RIGHT
+ : Character.DIRECTIONALITY_RIGHT_TO_LEFT);
+ int nextLevel;
+ if (run == runCount - 1)
+ nextLevel = baseEmbedding;
+ else
+ nextLevel = getRunLevel(run + 1);
+ byte eor = (((Math.max(level, nextLevel) % 2) == 0)
+ ? Character.DIRECTIONALITY_LEFT_TO_RIGHT
+ : Character.DIRECTIONALITY_RIGHT_TO_LEFT);
+
+ byte prevStrong = sor;
+ int neutralStart = -1;
+ for (int i = start; i <= end; ++i)
+ {
+ byte newStrong = -1;
+ byte thisType = i == end ? eor : types[i];
+ switch (thisType)
+ {
+ case Character.DIRECTIONALITY_LEFT_TO_RIGHT:
+ newStrong = Character.DIRECTIONALITY_LEFT_TO_RIGHT;
+ break;
+ case Character.DIRECTIONALITY_RIGHT_TO_LEFT:
+ case Character.DIRECTIONALITY_ARABIC_NUMBER:
+ case Character.DIRECTIONALITY_EUROPEAN_NUMBER:
+ newStrong = Character.DIRECTIONALITY_RIGHT_TO_LEFT;
+ break;
+ case Character.DIRECTIONALITY_BOUNDARY_NEUTRAL:
+ case Character.DIRECTIONALITY_OTHER_NEUTRALS:
+ case Character.DIRECTIONALITY_SEGMENT_SEPARATOR:
+ case Character.DIRECTIONALITY_PARAGRAPH_SEPARATOR:
+ if (neutralStart == -1)
+ neutralStart = i;
+ break;
+ }
+ // If we see a strong character, update all the neutrals.
+ if (newStrong != -1)
+ {
+ if (neutralStart != -1)
+ {
+ byte override = (prevStrong == newStrong
+ ? prevStrong
+ : embeddingDirection);
+ for (int j = neutralStart; j < i; ++j)
+ types[i] = override;
+ }
+ prevStrong = newStrong;
+ neutralStart = -1;
+ }
+ }
+
+ previousLevel = level;
+ }
+ }
+
+ /**
+ * An internal method to resolve implicit levels.
+ * This implements rules I1 and I2.
+ */
+ private void resolveImplicitLevels()
+ {
+ // This implements rules I1 and I2.
+ for (int i = 0; i < length; ++i)
+ {
+ if ((levels[i] & 1) == 0)
+ {
+ if (types[i] == Character.DIRECTIONALITY_RIGHT_TO_LEFT)
+ ++levels[i];
+ else if (types[i] == Character.DIRECTIONALITY_ARABIC_NUMBER
+ || types[i] == Character.DIRECTIONALITY_EUROPEAN_NUMBER)
+ levels[i] += 2;
+ }
+ else
+ {
+ if (types[i] == Character.DIRECTIONALITY_LEFT_TO_RIGHT
+ || types[i] == Character.DIRECTIONALITY_ARABIC_NUMBER
+ || types[i] == Character.DIRECTIONALITY_EUROPEAN_NUMBER)
+ ++levels[i];
+ }
+
+ // Update the result flags.
+ resultFlags |= 1 << (levels[i] & 1);
+ }
+ // One final update of the result flags, using the base level.
+ resultFlags |= 1 << baseEmbedding;
+ }
+
+ /**
+ * This reinserts the formatting codes that we removed early on.
+ * Actually it does not insert formatting codes per se, but rather
+ * simply inserts new levels at the appropriate locations in the
+ * 'levels' array.
+ */
+ private void reinsertFormattingCodes()
+ {
+ if (formatterIndices == null)
+ return;
+ int input = length;
+ int output = levels.length;
+ // Process from the end as we are copying the array over itself here.
+ for (int index = formatterIndices.size() - 1; index >= 0; --index)
+ {
+ int nextFmt = ((Integer) formatterIndices.get(index)).intValue();
+
+ // nextFmt points to a location in the original array. So,
+ // nextFmt+1 is the target of our copying. output is the location
+ // to which we last copied, thus we can derive the length of the
+ // copy from it.
+ int len = output - nextFmt - 1;
+ output = nextFmt;
+ input -= len;
+ // Note that we no longer need 'types' at this point, so we
+ // only edit 'levels'.
+ if (nextFmt + 1 < levels.length)
+ System.arraycopy(levels, input, levels, nextFmt + 1, len);
+
+ // Now set the level at the reinsertion point.
+ int rightLevel;
+ if (output == levels.length - 1)
+ rightLevel = baseEmbedding;
+ else
+ rightLevel = levels[output + 1];
+ int leftLevel;
+ if (input == 0)
+ leftLevel = baseEmbedding;
+ else
+ leftLevel = levels[input];
+ levels[output] = (byte) Math.max(leftLevel, rightLevel);
+ }
+ length = levels.length;
+ }
+
+ /**
+ * This is the main internal entry point. After a constructor
+ * has initialized the appropriate local state, it will call
+ * this method to do all the work.
+ */
+ private void runBidi()
+ {
+ computeTypes();
+ baseEmbedding = computeParagraphEmbeddingLevel();
+ computeExplicitLevels();
+ computeRuns();
+ resolveWeakTypes();
+ resolveNeutralTypes();
+ resolveImplicitLevels();
+ // We're done with the types. Let the GC clean up.
+ types = null;
+ reinsertFormattingCodes();
+ // After resolving the implicit levels, the number
+ // of runs may have changed.
+ computeRuns();
+ }
+
+ /**
+ * Return true if the paragraph base embedding is left-to-right,
+ * false otherwise.
+ */
+ public boolean baseIsLeftToRight()
+ {
+ return baseEmbedding == DIRECTION_LEFT_TO_RIGHT;
+ }
+
+ /**
+ * Create a new Bidi object for a single line of text, taken
+ * from the text used when creating the current Bidi object.
+ * @param start the index of the first character of the line
+ * @param end the index of the final character of the line
+ * @return a new Bidi object for the indicated line of text
+ */
+ public Bidi createLineBidi(int start, int end)
+ {
+ // This isn't the most efficient implementation possible.
+ // This probably does not matter, so we choose simplicity instead.
+ int level = getLevelAt(start);
+ int flag = (((level % 2) == 0)
+ ? DIRECTION_LEFT_TO_RIGHT
+ : DIRECTION_RIGHT_TO_LEFT);
+ return new Bidi(text, textOffset + start,
+ embeddings, embeddingOffset + start,
+ end - start, flag);
+ }
+
+ /**
+ * Return the base embedding level of the paragraph.
+ */
+ public int getBaseLevel()
+ {
+ return baseEmbedding;
+ }
+
+ /**
+ * Return the length of the paragraph, in characters.
+ */
+ public int getLength()
+ {
+ return length;
+ }
+
+ /**
+ * Return the level at the indicated character. If the
+ * supplied index is less than zero or greater than the length
+ * of the text, then the paragraph's base embedding level will
+ * be returned.
+ * @param offset the character to examine
+ * @return the level of that character
+ */
+ public int getLevelAt(int offset)
+ {
+ if (offset < 0 || offset >= length)
+ return getBaseLevel();
+ return levels[offset];
+ }
+
+ /**
+ * Return the number of runs in the result. A run is
+ * a sequence of characters at the same embedding level.
+ */
+ public int getRunCount()
+ {
+ return runs.length;
+ }
+
+ /**
+ * Return the level of the indicated run.
+ * @param which the run to examine
+ * @return the level of that run
+ */
+ public int getRunLevel(int which)
+ {
+ return levels[runs[which]];
+ }
+
+ /**
+ * Return the index of the character just following the end
+ * of the indicated run.
+ * @param which the run to examine
+ * @return the index of the character after the final character
+ * of the run
+ */
+ public int getRunLimit(int which)
+ {
+ if (which == runs.length - 1)
+ return length;
+ return runs[which + 1];
+ }
+
+ /**
+ * Return the index of the first character in the indicated run.
+ * @param which the run to examine
+ * @return the index of the first character of the run
+ */
+ public int getRunStart(int which)
+ {
+ return runs[which];
+ }
+
+ /**
+ * Return true if the text is entirely left-to-right, and the
+ * base embedding is also left-to-right.
+ */
+ public boolean isLeftToRight()
+ {
+ return resultFlags == LTOR;
+ }
+
+ /**
+ * Return true if the text consists of mixed left-to-right and
+ * right-to-left runs, or if the text consists of one kind of run
+ * which differs from the base embedding direction.
+ */
+ public boolean isMixed()
+ {
+ return resultFlags == (LTOR | RTOL);
+ }
+
+ /**
+ * Return true if the text is entirely right-to-left, and the
+ * base embedding is also right-to-left.
+ */
+ public boolean isRightToLeft()
+ {
+ return resultFlags == RTOL;
+ }
+
+ /**
+ * Return a String describing the internal state of this object.
+ * This is only useful for debugging.
+ */
+ public String toString()
+ {
+ return "Bidi Bidi Bidi I like you, Buck!";
+ }
+
+ /**
+ * Reorder objects according to the levels passed in. This implements
+ * reordering as defined by the Unicode bidirectional layout specification.
+ * The levels are integers from 0 to 62; even numbers represent left-to-right
+ * runs, and odd numbers represent right-to-left runs.
+ *
+ * @param levels the levels associated with each object
+ * @param levelOffset the index of the first level to use
+ * @param objs the objects to reorder according to the levels
+ * @param objOffset the index of the first object to use
+ * @param count the number of objects (and levels) to manipulate
+ */
+ public static void reorderVisually(byte[] levels, int levelOffset,
+ Object[] objs, int objOffset, int count)
+ {
+ // We need a copy of the 'levels' array, as we are going to modify it.
+ // This is unfortunate but difficult to avoid.
+ byte[] levelCopy = new byte[count];
+ // Do this explicitly so we can also find the maximum depth at the
+ // same time.
+ int max = 0;
+ int lowestOdd = 63;
+ for (int i = 0; i < count; ++i)
+ {
+ levelCopy[i] = levels[levelOffset + i];
+ max = Math.max(levelCopy[i], max);
+ if (levelCopy[i] % 2 != 0)
+ lowestOdd = Math.min(lowestOdd, levelCopy[i]);
+ }
+
+ // Reverse the runs starting with the deepest.
+ for (int depth = max; depth >= lowestOdd; --depth)
+ {
+ int start = 0;
+ while (start < count)
+ {
+ // Find the start of a run >= DEPTH.
+ while (start < count && levelCopy[start] < depth)
+ ++start;
+ if (start == count)
+ break;
+ // Find the end of the run.
+ int end = start + 1;
+ while (end < count && levelCopy[end] >= depth)
+ ++end;
+
+ // Reverse this run.
+ for (int i = 0; i < (end - start) / 2; ++i)
+ {
+ byte tmpb = levelCopy[end - i - 1];
+ levelCopy[end - i - 1] = levelCopy[start + i];
+ levelCopy[start + i] = tmpb;
+ Object tmpo = objs[objOffset + end - i - 1];
+ objs[objOffset + end - i - 1] = objs[objOffset + start + i];
+ objs[objOffset + start + i] = tmpo;
+ }
+
+ // Handle the next run.
+ start = end + 1;
+ }
+ }
+ }
+
+ /**
* Returns false if all characters in the text between start and end
* are all left-to-right text. This implementation is just calls
* <code>Character.getDirectionality(char)</code> on all characters
diff --git a/libjava/classpath/java/text/Collator.java b/libjava/classpath/java/text/Collator.java
index 7dea83f0a5a..08739163a64 100644
--- a/libjava/classpath/java/text/Collator.java
+++ b/libjava/classpath/java/text/Collator.java
@@ -38,6 +38,8 @@ exception statement from your version. */
package java.text;
+import gnu.java.locale.LocaleHelper;
+
import java.util.Comparator;
import java.util.Locale;
import java.util.MissingResourceException;
@@ -68,10 +70,6 @@ import java.util.ResourceBundle;
* @author Aaron M. Renn (arenn@urbanophile.com)
* @date March 18, 1999
*/
-/* Written using "Java Class Libraries", 2nd edition, plus online
- * API docs for JDK 1.2 from http://www.javasoft.com.
- * Status: Mostly complete, but parts stubbed out. Look for FIXME.
- */
public abstract class Collator implements Comparator, Cloneable
{
/**
@@ -244,10 +242,7 @@ public abstract class Collator implements Comparator, Cloneable
*/
public static synchronized Locale[] getAvailableLocales ()
{
- // FIXME
- Locale[] l = new Locale[1];
- l[0] = Locale.US;
- return l;
+ return LocaleHelper.getCollatorLocales();
}
/**
@@ -292,7 +287,7 @@ public abstract class Collator implements Comparator, Cloneable
* specified locale. If no <code>Collator</code> exists for the desired
* locale, a <code>Collator</code> for the default locale will be returned.
*
- * @param loc The desired localed to load a <code>Collator</code> for.
+ * @param loc The desired locale to load a <code>Collator</code> for.
*
* @return A <code>Collator</code> for the requested locale
*/
diff --git a/libjava/classpath/java/text/DateFormatSymbols.java b/libjava/classpath/java/text/DateFormatSymbols.java
index 6a20b4c2a36..bffd31fb6a7 100644
--- a/libjava/classpath/java/text/DateFormatSymbols.java
+++ b/libjava/classpath/java/text/DateFormatSymbols.java
@@ -292,6 +292,8 @@ public class DateFormatSymbols implements java.io.Serializable, Cloneable
*/
public void setAmPmStrings (String[] value)
{
+ if(value==null)
+ throw new NullPointerException();
ampms = value;
}
@@ -305,6 +307,8 @@ public class DateFormatSymbols implements java.io.Serializable, Cloneable
*/
public void setEras (String[] labels)
{
+ if(labels==null)
+ throw new NullPointerException();
eras = labels;
}
@@ -343,6 +347,8 @@ public class DateFormatSymbols implements java.io.Serializable, Cloneable
*/
public void setLocalPatternChars (String chars)
{
+ if(chars==null)
+ throw new NullPointerException();
localPatternChars = chars;
}
@@ -357,6 +363,8 @@ public class DateFormatSymbols implements java.io.Serializable, Cloneable
*/
public void setMonths (String[] labels)
{
+ if(labels==null)
+ throw new NullPointerException();
months = labels;
}
@@ -372,6 +380,8 @@ public class DateFormatSymbols implements java.io.Serializable, Cloneable
*/
public void setShortMonths (String[] labels)
{
+ if(labels==null)
+ throw new NullPointerException();
shortMonths = labels;
}
@@ -387,6 +397,8 @@ public class DateFormatSymbols implements java.io.Serializable, Cloneable
*/
public void setShortWeekdays (String[] labels)
{
+ if(labels==null)
+ throw new NullPointerException();
shortWeekdays = labels;
}
@@ -401,6 +413,8 @@ public class DateFormatSymbols implements java.io.Serializable, Cloneable
*/
public void setWeekdays (String[] labels)
{
+ if(labels==null)
+ throw new NullPointerException();
weekdays = labels;
}
@@ -421,6 +435,8 @@ public class DateFormatSymbols implements java.io.Serializable, Cloneable
*/
public void setZoneStrings (String[][] zones)
{
+ if(zones==null)
+ throw new NullPointerException();
zoneStrings = zones;
}
diff --git a/libjava/classpath/java/text/DecimalFormat.java b/libjava/classpath/java/text/DecimalFormat.java
index a9ec7767f94..f64249b6755 100644
--- a/libjava/classpath/java/text/DecimalFormat.java
+++ b/libjava/classpath/java/text/DecimalFormat.java
@@ -542,9 +542,9 @@ public class DecimalFormat extends NumberFormat
// Compute exponent.
long exponent = 0;
double baseNumber;
- if (useExponentialNotation)
+ if (useExponentialNotation && number > 0)
{
- exponent = (long) Math.floor (Math.log(number) / Math.log(10));
+ exponent = (long) Math.floor (Math.log10(number));
exponent = exponent - (exponent % exponentRound);
if (minimumIntegerDigits > 0)
exponent -= minimumIntegerDigits - 1;
@@ -654,7 +654,7 @@ public class DecimalFormat extends NumberFormat
index = dest.length();
dest.setDefaultAttribute(NumberFormat.Field.EXPONENT);
String exponentString = Long.toString ((long) exponent);
-
+
for (count = 0; count < minExponentDigits-exponentString.length();
count++)
dest.append((char) symbols.getZeroDigit());
diff --git a/libjava/classpath/java/text/RuleBasedCollator.java b/libjava/classpath/java/text/RuleBasedCollator.java
index 5756e9aa791..4bffcaf2905 100644
--- a/libjava/classpath/java/text/RuleBasedCollator.java
+++ b/libjava/classpath/java/text/RuleBasedCollator.java
@@ -38,6 +38,8 @@ exception statement from your version. */
package java.text;
+import gnu.classpath.NotImplementedException;
+
import java.util.ArrayList;
import java.util.HashMap;
@@ -921,6 +923,7 @@ element_loop:
* @return A <code>CollationElementIterator</code> for the specified <code>String</code>.
*/
public CollationElementIterator getCollationElementIterator(CharacterIterator source)
+ throws NotImplementedException // Because decomposeCharacter does not work
{
StringBuffer expand = new StringBuffer("");
diff --git a/libjava/classpath/java/text/SimpleDateFormat.java b/libjava/classpath/java/text/SimpleDateFormat.java
index c0c4cf68cea..00c08507e81 100644
--- a/libjava/classpath/java/text/SimpleDateFormat.java
+++ b/libjava/classpath/java/text/SimpleDateFormat.java
@@ -805,7 +805,8 @@ public class SimpleDateFormat extends DateFormat
buffer.setDefaultAttribute(DateFormat.Field.RFC822_TIME_ZONE);
int pureMinutes = (calendar.get(Calendar.ZONE_OFFSET) +
calendar.get(Calendar.DST_OFFSET)) / (1000 * 60);
- String sign = (pureMinutes < 0) ? "-" : "+";
+ String sign = (pureMinutes < 0) ? "-" : "+";
+ pureMinutes = Math.abs(pureMinutes);
int hours = pureMinutes / 60;
int minutes = pureMinutes % 60;
buffer.append(sign);
diff --git a/libjava/classpath/java/text/class-dependencies.conf b/libjava/classpath/java/text/class-dependencies.conf
deleted file mode 100644
index 011b146ce10..00000000000
--- a/libjava/classpath/java/text/class-dependencies.conf
+++ /dev/null
@@ -1,220 +0,0 @@
-# This property file contains dependencies of classes, methods, and
-# field on other methods or classes.
-#
-# Syntax:
-#
-# <used>: <needed 1> [... <needed N>]
-#
-# means that when <used> is included, <needed 1> (... <needed N>) must
-# be included as well.
-#
-# <needed X> and <used> are of the form
-#
-# <class.methodOrField(signature)>
-#
-# or just
-#
-# <class>
-#
-# Within dependencies, variables can be used. A variable is defined as
-# follows:
-#
-# {variable}: value1 value2 ... value<n>
-#
-# variables can be used on the right side of dependencies as follows:
-#
-# <used>: com.bla.blu.{variable}.Class.m()V
-#
-# The use of the variable will expand to <n> dependencies of the form
-#
-# <used>: com.bla.blu.value1.Class.m()V
-# <used>: com.bla.blu.value2.Class.m()V
-# ...
-# <used>: com.bla.blu.value<n>.Class.m()V
-#
-# Variables can be redefined when building a system to select the
-# required support for features like encodings, protocols, etc.
-#
-# Hints:
-#
-# - For methods and fields, the signature is mandatory. For
-# specification, please see the Java Virtual Machine Specification by
-# SUN. Unlike in the spec, field signatures (types) are in brackets.
-#
-# - Package names must be separated by '/' (and not '.'). E.g.,
-# java/lang/Class (this is necessary, because the '.' is used to
-# separate method or field names from classes)
-#
-# - In case <needed> refers to a class, only the class itself will be
-# included in the resulting binary, NOT necessarily all its methods
-# and fields. If you want to refer to all methods and fields, you can
-# write class.* as an abbreviation.
-#
-# - Abbreviations for packages are also possible: my/package/* means all
-# methods and fields of all classes in my/package.
-#
-# - A line with a trailing '\' continues in the next line.
-
-# end of file
-
-# All locales supported are loaded via classes from java.text (see below)
-# from class gnu/java/locale/LocaleInformation_<locale_id>
-#
-# This introduces a dependency for all locales. To allow an easy selection
-# and addition of locales, the library variable {text_locales} can be set to
-# the set of supported locales.
-#
-
-{text_locales}: \
- af_ZA \
- ar_AE \
- ar_BH \
- ar_DZ \
- ar_EG \
- ar_IN \
- ar_IQ \
- ar_JO \
- ar_KW \
- ar_LB \
- ar_LY \
- ar_MA \
- ar_OM \
- ar_QA \
- ar_SD \
- ar_SY \
- ar_TN \
- ar_YE \
- be_BY \
- bn_IN \
- br_FR \
- bs_BA \
- ca_ES \
- cs_CZ \
- cy_GB \
- da_DK \
- de \
- de_AT \
- de_BE \
- de_CH \
- de_DE \
- de_LU \
- el_GR \
- en \
- en_AU \
- en_BW \
- en_CA \
- en_DK \
- en_GB \
- en_HK \
- en_IE \
- en_IN \
- en_NZ \
- en_PH \
- en_SG \
- en_US \
- en_ZA \
- en_ZW \
- es_AR \
- es_BO \
- es_CL \
- es_CO \
- es_CR \
- es_DO \
- es_EC \
- es_ES \
- es_GT \
- es_HN \
- es_MX \
- es_NI \
- es_PA \
- es_PE \
- es_PR \
- es_PY \
- es_SV \
- es_US \
- es_UY \
- es_VE \
- et_EE \
- eu_ES \
- fa_IR \
- fi_FI \
- fo_FO \
- fr_BE \
- fr_CA \
- fr_CH \
- fr_FR \
- fr_LU \
- ga_IE \
- gd_GB \
- gl_ES \
- gv_GB \
- he_IL \
- hi_IN \
- hr_HR \
- hu_HU \
- id_ID \
- it_CH \
- it_IT \
- iw_IL \
- ja_JP \
- ka_GE \
- kl_GL \
- ko_KR \
- kw_GB \
- lt_LT \
- lv_LV \
- mi_NZ \
- mk_MK \
- mr_IN \
- mt_MT \
- nl \
- nl_BE \
- nl_NL \
- nn_NO \
- no_NO \
- oc_FR \
- pl_PL \
- pt_BR \
- pt_PT \
- ro_RO \
- ru_RU \
- ru_UA \
- se_NO \
- sk_SK \
- sl_SI \
- sq_AL \
- sr_YU \
- sv_FI \
- sv_SE \
- ta_IN \
- te_IN \
- tg_TJ \
- tl_PH \
- tr_TR \
- uk_UA \
- ur_PK \
- uz_UZ \
- vi_VN \
- yi_US \
- zh_CN \
- zh_HK \
- zh_SG \
- zh_TW
-
-java/text/Collator.getInstance(Ljava/util/Locale;)Ljava/text/Collator;: \
- gnu/java/locale/LocaleInformation_{text_locales}.*
-
-java/text/DateFormatSymbols.<init>(Ljava/util/Locale;)V: \
- gnu/java/locale/LocaleInformation_{text_locales}.*
-
-java/text/DecimalFormatSymbols.<init>(Ljava/util/Locale;)V: \
- gnu/java/locale/LocaleInformation_{text_locales}.*
-
-java/text/BreakIterator.getInstance(Ljava/lang/String;Ljava/util/Locale;)Ljava/text/BreakIterator;: \
- gnu/java/locale/LocaleInformation_{text_locales}.*
-
-java/text/NumberFormat.computeInstance(Ljava/util/Locale;Ljava/lang/String;Ljava/lang/String;)Ljava/text/NumberFormat;: \
- gnu/java/locale/LocaleInformation_{text_locales}.*
-
-java/text/DateFormat.computeInstance(IILjava/util/Locale;ZZ)Ljava/text/DateFormat;: \
- gnu/java/locale/LocaleInformation_{text_locales}.*
diff --git a/libjava/classpath/java/util/AbstractList.java b/libjava/classpath/java/util/AbstractList.java
index 8a9b6f10d7a..114712eeeaf 100644
--- a/libjava/classpath/java/util/AbstractList.java
+++ b/libjava/classpath/java/util/AbstractList.java
@@ -327,12 +327,9 @@ while (i.hasNext())
*
* @return True if the end of the list has not yet been
* reached.
- * @throws ConcurrentModificationException if the
- * list has been modified elsewhere.
*/
public boolean hasNext()
{
- checkMod();
return pos < size;
}
@@ -461,12 +458,9 @@ while (i.hasNext())
*
* @return True if the end of the list has not yet been
* reached.
- * @throws ConcurrentModificationException if the
- * list has been modified elsewhere.
*/
public boolean hasNext()
{
- checkMod();
return position < size;
}
@@ -476,12 +470,9 @@ while (i.hasNext())
*
* @return True if objects exist prior to the current
* position of the iterator.
- * @throws ConcurrentModificationException if the
- * list has been modified elsewhere.
*/
public boolean hasPrevious()
{
- checkMod();
return position > 0;
}
@@ -526,12 +517,9 @@ while (i.hasNext())
* list, which will be retrieved by <code>next()</code>
*
* @return The index of the next element.
- * @throws ConcurrentModificationException if the list
- * has been modified elsewhere.
*/
public int nextIndex()
{
- checkMod();
return position;
}
@@ -540,12 +528,9 @@ while (i.hasNext())
* list, which will be retrieved by <code>previous()</code>
*
* @return The index of the previous element.
- * @throws ConcurrentModificationException if the list
- * has been modified elsewhere.
*/
public int previousIndex()
{
- checkMod();
return position - 1;
}
@@ -1030,12 +1015,9 @@ while (i.hasNext())
*
* @return True if the end of the list has not yet been
* reached.
- * @throws ConcurrentModificationException if the
- * list has been modified elsewhere.
*/
public boolean hasNext()
{
- checkMod();
return position < size;
}
@@ -1045,12 +1027,9 @@ while (i.hasNext())
*
* @return True if objects exist prior to the current
* position of the iterator.
- * @throws ConcurrentModificationException if the
- * list has been modified elsewhere.
*/
public boolean hasPrevious()
{
- checkMod();
return position > 0;
}
@@ -1093,8 +1072,6 @@ while (i.hasNext())
* list, which will be retrieved by <code>next()</code>
*
* @return The index of the next element.
- * @throws ConcurrentModificationException if the
- * list has been modified elsewhere.
*/
public int nextIndex()
{
@@ -1106,8 +1083,6 @@ while (i.hasNext())
* list, which will be retrieved by <code>previous()</code>
*
* @return The index of the previous element.
- * @throws ConcurrentModificationException if the
- * list has been modified elsewhere.
*/
public int previousIndex()
{
diff --git a/libjava/classpath/java/util/Arrays.java b/libjava/classpath/java/util/Arrays.java
index b28c156b46e..29134467b2b 100644
--- a/libjava/classpath/java/util/Arrays.java
+++ b/libjava/classpath/java/util/Arrays.java
@@ -2352,185 +2352,556 @@ public class Arrays
return new Arrays.ArrayList(a);
}
+ /**
+ * Returns the hashcode of an array of long numbers. If two arrays
+ * are equal, according to <code>equals()</code>, they should have the
+ * same hashcode. The hashcode returned by the method is equal to that
+ * obtained by the corresponding <code>List</code> object. This has the same
+ * data, but represents longs in their wrapper class, <code>Long</code>.
+ * For <code>null</code>, 0 is returned.
+ *
+ * @param v an array of long numbers for which the hash code should be
+ * computed.
+ * @return the hash code of the array, or 0 if null was given.
+ * @since 1.5
+ */
+ public static int hashCode(long[] v)
+ {
+ if (v == null)
+ return 0;
+ int result = 1;
+ for (int i = 0; i < v.length; ++i)
+ {
+ int elt = (int) (v[i] ^ (v[i] >>> 32));
+ result = 31 * result + elt;
+ }
+ return result;
+ }
+
+ /**
+ * Returns the hashcode of an array of integer numbers. If two arrays
+ * are equal, according to <code>equals()</code>, they should have the
+ * same hashcode. The hashcode returned by the method is equal to that
+ * obtained by the corresponding <code>List</code> object. This has the same
+ * data, but represents ints in their wrapper class, <code>Integer</code>.
+ * For <code>null</code>, 0 is returned.
+ *
+ * @param v an array of integer numbers for which the hash code should be
+ * computed.
+ * @return the hash code of the array, or 0 if null was given.
+ * @since 1.5
+ */
+ public static int hashCode(int[] v)
+ {
+ if (v == null)
+ return 0;
+ int result = 1;
+ for (int i = 0; i < v.length; ++i)
+ result = 31 * result + v[i];
+ return result;
+ }
+
+ /**
+ * Returns the hashcode of an array of short numbers. If two arrays
+ * are equal, according to <code>equals()</code>, they should have the
+ * same hashcode. The hashcode returned by the method is equal to that
+ * obtained by the corresponding <code>List</code> object. This has the same
+ * data, but represents shorts in their wrapper class, <code>Short</code>.
+ * For <code>null</code>, 0 is returned.
+ *
+ * @param v an array of short numbers for which the hash code should be
+ * computed.
+ * @return the hash code of the array, or 0 if null was given.
+ * @since 1.5
+ */
+ public static int hashCode(short[] v)
+ {
+ if (v == null)
+ return 0;
+ int result = 1;
+ for (int i = 0; i < v.length; ++i)
+ result = 31 * result + v[i];
+ return result;
+ }
+
+ /**
+ * Returns the hashcode of an array of characters. If two arrays
+ * are equal, according to <code>equals()</code>, they should have the
+ * same hashcode. The hashcode returned by the method is equal to that
+ * obtained by the corresponding <code>List</code> object. This has the same
+ * data, but represents chars in their wrapper class, <code>Character</code>.
+ * For <code>null</code>, 0 is returned.
+ *
+ * @param v an array of characters for which the hash code should be
+ * computed.
+ * @return the hash code of the array, or 0 if null was given.
+ * @since 1.5
+ */
+ public static int hashCode(char[] v)
+ {
+ if (v == null)
+ return 0;
+ int result = 1;
+ for (int i = 0; i < v.length; ++i)
+ result = 31 * result + v[i];
+ return result;
+ }
+
+ /**
+ * Returns the hashcode of an array of bytes. If two arrays
+ * are equal, according to <code>equals()</code>, they should have the
+ * same hashcode. The hashcode returned by the method is equal to that
+ * obtained by the corresponding <code>List</code> object. This has the same
+ * data, but represents bytes in their wrapper class, <code>Byte</code>.
+ * For <code>null</code>, 0 is returned.
+ *
+ * @param v an array of bytes for which the hash code should be
+ * computed.
+ * @return the hash code of the array, or 0 if null was given.
+ * @since 1.5
+ */
+ public static int hashCode(byte[] v)
+ {
+ if (v == null)
+ return 0;
+ int result = 1;
+ for (int i = 0; i < v.length; ++i)
+ result = 31 * result + v[i];
+ return result;
+ }
+
+ /**
+ * Returns the hashcode of an array of booleans. If two arrays
+ * are equal, according to <code>equals()</code>, they should have the
+ * same hashcode. The hashcode returned by the method is equal to that
+ * obtained by the corresponding <code>List</code> object. This has the same
+ * data, but represents booleans in their wrapper class,
+ * <code>Boolean</code>. For <code>null</code>, 0 is returned.
+ *
+ * @param v an array of booleans for which the hash code should be
+ * computed.
+ * @return the hash code of the array, or 0 if null was given.
+ * @since 1.5
+ */
+ public static int hashCode(boolean[] v)
+ {
+ if (v == null)
+ return 0;
+ int result = 1;
+ for (int i = 0; i < v.length; ++i)
+ result = 31 * result + (v[i] ? 1231 : 1237);
+ return result;
+ }
+
+ /**
+ * Returns the hashcode of an array of floats. If two arrays
+ * are equal, according to <code>equals()</code>, they should have the
+ * same hashcode. The hashcode returned by the method is equal to that
+ * obtained by the corresponding <code>List</code> object. This has the same
+ * data, but represents floats in their wrapper class, <code>Float</code>.
+ * For <code>null</code>, 0 is returned.
+ *
+ * @param v an array of floats for which the hash code should be
+ * computed.
+ * @return the hash code of the array, or 0 if null was given.
+ * @since 1.5
+ */
+ public static int hashCode(float[] v)
+ {
+ if (v == null)
+ return 0;
+ int result = 1;
+ for (int i = 0; i < v.length; ++i)
+ result = 31 * result + Float.floatToIntBits(v[i]);
+ return result;
+ }
+
+ /**
+ * Returns the hashcode of an array of doubles. If two arrays
+ * are equal, according to <code>equals()</code>, they should have the
+ * same hashcode. The hashcode returned by the method is equal to that
+ * obtained by the corresponding <code>List</code> object. This has the same
+ * data, but represents doubles in their wrapper class, <code>Double</code>.
+ * For <code>null</code>, 0 is returned.
+ *
+ * @param v an array of doubles for which the hash code should be
+ * computed.
+ * @return the hash code of the array, or 0 if null was given.
+ * @since 1.5
+ */
+ public static int hashCode(double[] v)
+ {
+ if (v == null)
+ return 0;
+ int result = 1;
+ for (int i = 0; i < v.length; ++i)
+ {
+ long l = Double.doubleToLongBits(v[i]);
+ int elt = (int) (l ^ (l >>> 32));
+ result = 31 * result + elt;
+ }
+ return result;
+ }
+
+ /**
+ * Returns the hashcode of an array of integer numbers. If two arrays
+ * are equal, according to <code>equals()</code>, they should have the
+ * same hashcode. The hashcode returned by the method is equal to that
+ * obtained by the corresponding <code>List</code> object. This has the same
+ * data, but represents ints in their wrapper class, <code>Integer</code>.
+ * For <code>null</code>, 0 is returned.
+ *
+ * @param v an array of integer numbers for which the hash code should be
+ * computed.
+ * @return the hash code of the array, or 0 if null was given.
+ * @since 1.5
+ */
+ public static int hashCode(Object[] v)
+ {
+ if (v == null)
+ return 0;
+ int result = 1;
+ for (int i = 0; i < v.length; ++i)
+ {
+ int elt = v[i] == null ? 0 : v[i].hashCode();
+ result = 31 * result + elt;
+ }
+ return result;
+ }
+
+ /** @since 1.5 */
+ public static int deepHashCode(Object[] v)
+ {
+ if (v == null)
+ return 0;
+ int result = 1;
+ for (int i = 0; i < v.length; ++i)
+ {
+ int elt;
+ if (v[i] == null)
+ elt = 0;
+ else if (v[i] instanceof boolean[])
+ elt = hashCode((boolean[]) v[i]);
+ else if (v[i] instanceof byte[])
+ elt = hashCode((byte[]) v[i]);
+ else if (v[i] instanceof char[])
+ elt = hashCode((char[]) v[i]);
+ else if (v[i] instanceof short[])
+ elt = hashCode((short[]) v[i]);
+ else if (v[i] instanceof int[])
+ elt = hashCode((int[]) v[i]);
+ else if (v[i] instanceof long[])
+ elt = hashCode((long[]) v[i]);
+ else if (v[i] instanceof float[])
+ elt = hashCode((float[]) v[i]);
+ else if (v[i] instanceof double[])
+ elt = hashCode((double[]) v[i]);
+ else if (v[i] instanceof Object[])
+ elt = hashCode((Object[]) v[i]);
+ else
+ elt = v[i].hashCode();
+ result = 31 * result + elt;
+ }
+ return result;
+ }
+
+ /** @since 1.5 */
+ public static boolean deepEquals(Object[] v1, Object[] v2)
+ {
+ if (v1 == null)
+ return v2 == null;
+ if (v2 == null || v1.length != v2.length)
+ return false;
+
+ for (int i = 0; i < v1.length; ++i)
+ {
+ Object e1 = v1[i];
+ Object e2 = v2[i];
+
+ if (e1 == e2)
+ continue;
+ if (e1 == null || e2 == null)
+ return false;
+
+ boolean check;
+ if (e1 instanceof boolean[] && e2 instanceof boolean[])
+ check = equals((boolean[]) e1, (boolean[]) e2);
+ else if (e1 instanceof byte[] && e2 instanceof byte[])
+ check = equals((byte[]) e1, (byte[]) e2);
+ else if (e1 instanceof char[] && e2 instanceof char[])
+ check = equals((char[]) e1, (char[]) e2);
+ else if (e1 instanceof short[] && e2 instanceof short[])
+ check = equals((short[]) e1, (short[]) e2);
+ else if (e1 instanceof int[] && e2 instanceof int[])
+ check = equals((int[]) e1, (int[]) e2);
+ else if (e1 instanceof long[] && e2 instanceof long[])
+ check = equals((long[]) e1, (long[]) e2);
+ else if (e1 instanceof float[] && e2 instanceof float[])
+ check = equals((float[]) e1, (float[]) e2);
+ else if (e1 instanceof double[] && e2 instanceof double[])
+ check = equals((double[]) e1, (double[]) e2);
+ else if (e1 instanceof Object[] && e2 instanceof Object[])
+ check = equals((Object[]) e1, (Object[]) e2);
+ else
+ check = e1.equals(e2);
+ if (! check)
+ return false;
+ }
+
+ return true;
+ }
+
/**
* Returns a String representation of the argument array. Returns "null"
* if <code>a</code> is null.
- * @param a the array to represent
+ * @param v the array to represent
* @return a String representing this array
* @since 1.5
*/
- public static String toString (long[] a)
+ public static String toString(boolean[] v)
{
- if (a == null)
+ if (v == null)
return "null";
- if (a.length == 0)
- return "[]";
- String result = "[";
- for (int i = 0; i < a.length - 1; i++)
- result += String.valueOf(a[i]) + ", ";
- result += String.valueOf(a[a.length - 1]) + "]";
- return result;
- }
-
+ StringBuilder b = new StringBuilder("[");
+ for (int i = 0; i < v.length; ++i)
+ {
+ if (i > 0)
+ b.append(", ");
+ b.append(v[i]);
+ }
+ b.append("]");
+ return b.toString();
+ }
+
/**
* Returns a String representation of the argument array. Returns "null"
* if <code>a</code> is null.
- * @param a the array to represent
+ * @param v the array to represent
* @return a String representing this array
* @since 1.5
*/
- public static String toString (int[] a)
+ public static String toString(byte[] v)
{
- if (a == null)
+ if (v == null)
return "null";
- if (a.length == 0)
- return "[]";
- String result = "[";
- for (int i = 0; i < a.length - 1; i++)
- result += String.valueOf(a[i]) + ", ";
- result += String.valueOf(a[a.length - 1]) + "]";
- return result;
- }
-
+ StringBuilder b = new StringBuilder("[");
+ for (int i = 0; i < v.length; ++i)
+ {
+ if (i > 0)
+ b.append(", ");
+ b.append(v[i]);
+ }
+ b.append("]");
+ return b.toString();
+ }
+
/**
* Returns a String representation of the argument array. Returns "null"
* if <code>a</code> is null.
- * @param a the array to represent
+ * @param v the array to represent
* @return a String representing this array
* @since 1.5
*/
- public static String toString (short[] a)
+ public static String toString(char[] v)
{
- if (a == null)
+ if (v == null)
return "null";
- if (a.length == 0)
- return "[]";
- String result = "[";
- for (int i = 0; i < a.length - 1; i++)
- result += String.valueOf(a[i]) + ", ";
- result += String.valueOf(a[a.length - 1]) + "]";
- return result;
- }
+ StringBuilder b = new StringBuilder("[");
+ for (int i = 0; i < v.length; ++i)
+ {
+ if (i > 0)
+ b.append(", ");
+ b.append(v[i]);
+ }
+ b.append("]");
+ return b.toString();
+ }
/**
* Returns a String representation of the argument array. Returns "null"
* if <code>a</code> is null.
- * @param a the array to represent
+ * @param v the array to represent
* @return a String representing this array
* @since 1.5
*/
- public static String toString (char[] a)
+ public static String toString(short[] v)
{
- if (a == null)
+ if (v == null)
return "null";
- if (a.length == 0)
- return "[]";
- String result = "[";
- for (int i = 0; i < a.length - 1; i++)
- result += String.valueOf(a[i]) + ", ";
- result += String.valueOf(a[a.length - 1]) + "]";
- return result;
- }
+ StringBuilder b = new StringBuilder("[");
+ for (int i = 0; i < v.length; ++i)
+ {
+ if (i > 0)
+ b.append(", ");
+ b.append(v[i]);
+ }
+ b.append("]");
+ return b.toString();
+ }
/**
* Returns a String representation of the argument array. Returns "null"
* if <code>a</code> is null.
- * @param a the array to represent
+ * @param v the array to represent
* @return a String representing this array
* @since 1.5
*/
- public static String toString (byte[] a)
+ public static String toString(int[] v)
{
- if (a == null)
+ if (v == null)
return "null";
- if (a.length == 0)
- return "[]";
- String result = "[";
- for (int i = 0; i < a.length - 1; i++)
- result += String.valueOf(a[i]) + ", ";
- result += String.valueOf(a[a.length - 1]) + "]";
- return result;
- }
+ StringBuilder b = new StringBuilder("[");
+ for (int i = 0; i < v.length; ++i)
+ {
+ if (i > 0)
+ b.append(", ");
+ b.append(v[i]);
+ }
+ b.append("]");
+ return b.toString();
+ }
/**
* Returns a String representation of the argument array. Returns "null"
* if <code>a</code> is null.
- * @param a the array to represent
+ * @param v the array to represent
* @return a String representing this array
* @since 1.5
*/
- public static String toString (boolean[] a)
+ public static String toString(long[] v)
{
- if (a == null)
+ if (v == null)
return "null";
- if (a.length == 0)
- return "[]";
- String result = "[";
- for (int i = 0; i < a.length - 1; i++)
- result += String.valueOf(a[i]) + ", ";
- result += String.valueOf(a[a.length - 1]) + "]";
- return result;
- }
+ StringBuilder b = new StringBuilder("[");
+ for (int i = 0; i < v.length; ++i)
+ {
+ if (i > 0)
+ b.append(", ");
+ b.append(v[i]);
+ }
+ b.append("]");
+ return b.toString();
+ }
/**
* Returns a String representation of the argument array. Returns "null"
* if <code>a</code> is null.
- * @param a the array to represent
+ * @param v the array to represent
* @return a String representing this array
* @since 1.5
*/
- public static String toString (float[] a)
+ public static String toString(float[] v)
{
- if (a == null)
+ if (v == null)
return "null";
- if (a.length == 0)
- return "[]";
- String result = "[";
- for (int i = 0; i < a.length - 1; i++)
- result += String.valueOf(a[i]) + ", ";
- result += String.valueOf(a[a.length - 1]) + "]";
- return result;
- }
-
+ StringBuilder b = new StringBuilder("[");
+ for (int i = 0; i < v.length; ++i)
+ {
+ if (i > 0)
+ b.append(", ");
+ b.append(v[i]);
+ }
+ b.append("]");
+ return b.toString();
+ }
+
/**
* Returns a String representation of the argument array. Returns "null"
* if <code>a</code> is null.
- * @param a the array to represent
+ * @param v the array to represent
* @return a String representing this array
* @since 1.5
*/
- public static String toString (double[] a)
+ public static String toString(double[] v)
{
- if (a == null)
+ if (v == null)
return "null";
- if (a.length == 0)
- return "[]";
- String result = "[";
- for (int i = 0; i < a.length - 1; i++)
- result += String.valueOf(a[i]) + ", ";
- result += String.valueOf(a[a.length - 1]) + "]";
- return result;
- }
+ StringBuilder b = new StringBuilder("[");
+ for (int i = 0; i < v.length; ++i)
+ {
+ if (i > 0)
+ b.append(", ");
+ b.append(v[i]);
+ }
+ b.append("]");
+ return b.toString();
+ }
/**
* Returns a String representation of the argument array. Returns "null"
* if <code>a</code> is null.
- * @param a the array to represent
+ * @param v the array to represent
* @return a String representing this array
* @since 1.5
*/
- public static String toString (Object[] a)
+ public static String toString(Object[] v)
{
- if (a == null)
+ if (v == null)
return "null";
- if (a.length == 0)
- return "[]";
- String result = "[";
- for (int i = 0; i < a.length - 1; i++)
- result += String.valueOf(a[i]) + ", ";
- result += String.valueOf(a[a.length - 1]) + "]";
- return result;
- }
+ StringBuilder b = new StringBuilder("[");
+ for (int i = 0; i < v.length; ++i)
+ {
+ if (i > 0)
+ b.append(", ");
+ b.append(v[i]);
+ }
+ b.append("]");
+ return b.toString();
+ }
+
+ private static void deepToString(Object[] v, StringBuilder b, HashSet seen)
+ {
+ b.append("[");
+ for (int i = 0; i < v.length; ++i)
+ {
+ if (i > 0)
+ b.append(", ");
+ Object elt = v[i];
+ if (elt == null)
+ b.append("null");
+ else if (elt instanceof boolean[])
+ b.append(toString((boolean[]) elt));
+ else if (elt instanceof byte[])
+ b.append(toString((byte[]) elt));
+ else if (elt instanceof char[])
+ b.append(toString((char[]) elt));
+ else if (elt instanceof short[])
+ b.append(toString((short[]) elt));
+ else if (elt instanceof int[])
+ b.append(toString((int[]) elt));
+ else if (elt instanceof long[])
+ b.append(toString((long[]) elt));
+ else if (elt instanceof float[])
+ b.append(toString((float[]) elt));
+ else if (elt instanceof double[])
+ b.append(toString((double[]) elt));
+ else if (elt instanceof Object[])
+ {
+ Object[] os = (Object[]) elt;
+ if (seen.contains(os))
+ b.append("[...]");
+ else
+ {
+ seen.add(os);
+ deepToString(os, b, seen);
+ }
+ }
+ else
+ b.append(elt);
+ }
+ b.append("]");
+ }
+
+ /** @since 1.5 */
+ public static String deepToString(Object[] v)
+ {
+ if (v == null)
+ return "null";
+ HashSet seen = new HashSet();
+ StringBuilder b = new StringBuilder();
+ deepToString(v, b, seen);
+ return b.toString();
+ }
/**
* Inner class used by {@link #asList(Object[])} to provide a list interface
diff --git a/libjava/classpath/java/util/BitSet.java b/libjava/classpath/java/util/BitSet.java
index ce88794f52b..f1b5aaa06ee 100644
--- a/libjava/classpath/java/util/BitSet.java
+++ b/libjava/classpath/java/util/BitSet.java
@@ -365,7 +365,7 @@ public class BitSet implements Cloneable, Serializable
throw new IndexOutOfBoundsException();
BitSet bs = new BitSet(to - from);
int lo_offset = from >>> 6;
- if (lo_offset >= bits.length)
+ if (lo_offset >= bits.length || to == from)
return bs;
int lo_bit = from & LONG_MASK;
diff --git a/libjava/classpath/java/util/Calendar.java b/libjava/classpath/java/util/Calendar.java
index f94bed40dad..a324f5adabf 100644
--- a/libjava/classpath/java/util/Calendar.java
+++ b/libjava/classpath/java/util/Calendar.java
@@ -1037,6 +1037,8 @@ public abstract class Calendar implements Serializable, Cloneable
public void setTimeZone(TimeZone zone)
{
this.zone = zone;
+ computeTime();
+ computeFields();
}
/**
diff --git a/libjava/classpath/java/util/Collection.java b/libjava/classpath/java/util/Collection.java
index 29e1b3786b4..f7db708c16d 100644
--- a/libjava/classpath/java/util/Collection.java
+++ b/libjava/classpath/java/util/Collection.java
@@ -81,9 +81,9 @@ package java.util;
* @see Arrays
* @see AbstractCollection
* @since 1.2
- * @status updated to 1.4
+ * @status updated to 1.5 (minus generics)
*/
-public interface Collection
+public interface Collection extends Iterable
{
/**
* Add an element to this collection.
diff --git a/libjava/classpath/java/util/GregorianCalendar.java b/libjava/classpath/java/util/GregorianCalendar.java
index 89b7c4dbd02..5ce053a3705 100644
--- a/libjava/classpath/java/util/GregorianCalendar.java
+++ b/libjava/classpath/java/util/GregorianCalendar.java
@@ -588,7 +588,7 @@ public class GregorianCalendar extends Calendar
day = offs + 7 * (fields[WEEK_OF_MONTH] - 1);
offs = fields[DAY_OF_WEEK] - getFirstDayOfWeek();
- if (offs <= 0)
+ if (offs < 0)
offs += 7;
day += offs;
}
diff --git a/libjava/classpath/java/util/HashMap.java b/libjava/classpath/java/util/HashMap.java
index 7176db0d58e..a734af48405 100644
--- a/libjava/classpath/java/util/HashMap.java
+++ b/libjava/classpath/java/util/HashMap.java
@@ -849,12 +849,9 @@ public class HashMap extends AbstractMap
/**
* Returns true if the Iterator has more elements.
* @return true if there are more elements
- * @throws ConcurrentModificationException if the HashMap was modified
*/
public boolean hasNext()
{
- if (knownMod != modCount)
- throw new ConcurrentModificationException();
return count > 0;
}
diff --git a/libjava/classpath/java/util/Hashtable.java b/libjava/classpath/java/util/Hashtable.java
index 76b0d5c15bd..4c00d18a8e2 100644
--- a/libjava/classpath/java/util/Hashtable.java
+++ b/libjava/classpath/java/util/Hashtable.java
@@ -1017,12 +1017,9 @@ public class Hashtable extends Dictionary
/**
* Returns true if the Iterator has more elements.
* @return true if there are more elements
- * @throws ConcurrentModificationException if the hashtable was modified
*/
public boolean hasNext()
{
- if (knownMod != modCount)
- throw new ConcurrentModificationException();
return count > 0;
}
diff --git a/libjava/classpath/java/util/IdentityHashMap.java b/libjava/classpath/java/util/IdentityHashMap.java
index 6369fac691b..89ef034159b 100644
--- a/libjava/classpath/java/util/IdentityHashMap.java
+++ b/libjava/classpath/java/util/IdentityHashMap.java
@@ -705,12 +705,9 @@ public class IdentityHashMap extends AbstractMap
/**
* Returns true if the Iterator has more elements.
* @return true if there are more elements
- * @throws ConcurrentModificationException if the Map was modified
*/
public boolean hasNext()
{
- if (knownMod != modCount)
- throw new ConcurrentModificationException();
return count > 0;
}
diff --git a/libjava/classpath/java/util/InvalidPropertiesFormatException.java b/libjava/classpath/java/util/InvalidPropertiesFormatException.java
index 6540c2313f3..aaa6c4eb463 100644
--- a/libjava/classpath/java/util/InvalidPropertiesFormatException.java
+++ b/libjava/classpath/java/util/InvalidPropertiesFormatException.java
@@ -39,11 +39,16 @@ exception statement from your version. */
package java.util;
import java.io.IOException;
+import java.io.NotSerializableException;
+import java.io.ObjectInputStream;
+import java.io.ObjectOutputStream;
-// FIXME: serialization methods should throw NotSerializableException
/** @since 1.5 */
public class InvalidPropertiesFormatException extends IOException
{
+ // This class won't serialize, but we have a UID to placate the compiler.
+ private static final long serialVersionUID = 7763056076009360219L;
+
public InvalidPropertiesFormatException(String message)
{
super(message);
@@ -54,4 +59,14 @@ public class InvalidPropertiesFormatException extends IOException
super();
initCause(cause);
}
+
+ private void writeObject(ObjectOutputStream out) throws IOException
+ {
+ throw new NotSerializableException("objects of this type are not serializable");
+ }
+
+ private void readObject(ObjectInputStream in) throws IOException
+ {
+ throw new NotSerializableException("objects of this type are not serializable");
+ }
}
diff --git a/libjava/classpath/java/util/LinkedHashMap.java b/libjava/classpath/java/util/LinkedHashMap.java
index 8e895a9e0d8..2b002b27296 100644
--- a/libjava/classpath/java/util/LinkedHashMap.java
+++ b/libjava/classpath/java/util/LinkedHashMap.java
@@ -452,12 +452,9 @@ public class LinkedHashMap extends HashMap
* Returns true if the Iterator has more elements.
*
* @return true if there are more elements
- * @throws ConcurrentModificationException if the HashMap was modified
*/
public boolean hasNext()
{
- if (knownMod != modCount)
- throw new ConcurrentModificationException();
return current != null;
}
diff --git a/libjava/classpath/java/util/LinkedList.java b/libjava/classpath/java/util/LinkedList.java
index 2a35425fa24..e77ae536b64 100644
--- a/libjava/classpath/java/util/LinkedList.java
+++ b/libjava/classpath/java/util/LinkedList.java
@@ -804,11 +804,9 @@ public class LinkedList extends AbstractSequentialList
* Returns the index of the next element.
*
* @return the next index
- * @throws ConcurrentModificationException if the list was modified
*/
public int nextIndex()
{
- checkMod();
return position;
}
@@ -816,11 +814,9 @@ public class LinkedList extends AbstractSequentialList
* Returns the index of the previous element.
*
* @return the previous index
- * @throws ConcurrentModificationException if the list was modified
*/
public int previousIndex()
{
- checkMod();
return position - 1;
}
@@ -828,11 +824,9 @@ public class LinkedList extends AbstractSequentialList
* Returns true if more elements exist via next.
*
* @return true if next will succeed
- * @throws ConcurrentModificationException if the list was modified
*/
public boolean hasNext()
{
- checkMod();
return (next != null);
}
@@ -840,11 +834,9 @@ public class LinkedList extends AbstractSequentialList
* Returns true if more elements exist via previous.
*
* @return true if previous will succeed
- * @throws ConcurrentModificationException if the list was modified
*/
public boolean hasPrevious()
{
- checkMod();
return (previous != null);
}
diff --git a/libjava/classpath/java/util/Locale.java b/libjava/classpath/java/util/Locale.java
index 9e7bbfea2b3..d2aead43c68 100644
--- a/libjava/classpath/java/util/Locale.java
+++ b/libjava/classpath/java/util/Locale.java
@@ -39,6 +39,7 @@ exception statement from your version. */
package java.util;
import gnu.classpath.SystemProperties;
+import gnu.java.locale.LocaleHelper;
import java.io.IOException;
import java.io.ObjectInputStream;
@@ -65,11 +66,12 @@ import java.io.Serializable;
* be separated by an underscore (U+005F).
*
* <p>The default locale is determined by the values of the system properties
- * user.language, user.region, and user.variant, defaulting to "en". Note that
- * the locale does NOT contain the conversion and formatting capabilities (for
- * that, use ResourceBundle and java.text). Rather, it is an immutable tag
- * object for identifying a given locale, which is referenced by these other
- * classes when they must make locale-dependent decisions.
+ * user.language, user.country (or user.region), and user.variant, defaulting
+ * to "en_US". Note that the locale does NOT contain the conversion and
+ * formatting capabilities (for that, use ResourceBundle and java.text).
+ * Rather, it is an immutable tag object for identifying a given locale, which
+ * is referenced by these other classes when they must make locale-dependent
+ * decisions.
*
* @see ResourceBundle
* @see java.text.Format
@@ -209,10 +211,18 @@ public final class Locale implements Serializable, Cloneable
* null. Note the logic in the main constructor, to detect when
* bootstrapping has completed.
*/
- private static Locale defaultLocale =
- getLocale(SystemProperties.getProperty("user.language", "en"),
- SystemProperties.getProperty("user.region", ""),
- SystemProperties.getProperty("user.variant", ""));
+ private static Locale defaultLocale;
+
+ static {
+ String language = SystemProperties.getProperty("user.language", "en");
+ String country = SystemProperties.getProperty("user.country", "US");
+ String region = SystemProperties.getProperty("user.region", null);
+ String variant = SystemProperties.getProperty("user.variant", "");
+
+ defaultLocale = getLocale(language,
+ (region != null) ? region : country,
+ variant);
+ }
/**
* Array storing all the available two-letter ISO639 languages.
@@ -236,38 +246,38 @@ public final class Locale implements Serializable, Cloneable
}
/**
- * Retrieves the locale with the specified language and region
+ * Retrieves the locale with the specified language and country
* from the cache.
*
* @param language the language of the locale to retrieve.
- * @param region the region of the locale to retrieve.
+ * @param country the country of the locale to retrieve.
* @return the locale.
*/
- private static Locale getLocale(String language, String region)
+ private static Locale getLocale(String language, String country)
{
- return getLocale(language, region, "");
+ return getLocale(language, country, "");
}
/**
- * Retrieves the locale with the specified language, region
+ * Retrieves the locale with the specified language, country
* and variant from the cache.
*
* @param language the language of the locale to retrieve.
- * @param region the region of the locale to retrieve.
+ * @param country the country of the locale to retrieve.
* @param variant the variant of the locale to retrieve.
* @return the locale.
*/
- private static Locale getLocale(String language, String region, String variant)
+ private static Locale getLocale(String language, String country, String variant)
{
if (localeMap == null)
localeMap = new HashMap(256);
- String name = language + "_" + region + "_" + variant;
+ String name = language + "_" + country + "_" + variant;
Locale locale = (Locale) localeMap.get(name);
if (locale == null)
{
- locale = new Locale(language, region, variant);
+ locale = new Locale(language, country, variant);
localeMap.put(name, locale);
}
@@ -384,33 +394,33 @@ public final class Locale implements Serializable, Cloneable
{
if (availableLocales == null)
{
- String[] localeNames = LocaleData.localeNames;
- availableLocales = new Locale[localeNames.length];
+ int len = LocaleHelper.getLocaleCount();
+ availableLocales = new Locale[len];
- for (int i = 0; i < localeNames.length; i++)
+ for (int i = 0; i < len; i++)
{
String language;
- String region = "";
+ String country = "";
String variant = "";
- String name = localeNames[i];
+ String name = LocaleHelper.getLocaleName(i);
language = name.substring(0, 2);
if (name.length() > 2)
- region = name.substring(3);
+ country = name.substring(3);
- int index = region.indexOf("_");
+ int index = country.indexOf("_");
if (index > 0)
{
- variant = region.substring(index + 1);
- region = region.substring(0, index - 1);
+ variant = country.substring(index + 1);
+ country = country.substring(0, index - 1);
}
- availableLocales[i] = getLocale(language, region, variant);
+ availableLocales[i] = getLocale(language, country, variant);
}
}
- return availableLocales;
+ return (Locale[]) availableLocales.clone();
}
/**
@@ -426,7 +436,7 @@ public final class Locale implements Serializable, Cloneable
countryCache = getISOStrings("territories");
}
- return countryCache;
+ return (String[]) countryCache.clone();
}
/**
@@ -441,7 +451,7 @@ public final class Locale implements Serializable, Cloneable
{
languageCache = getISOStrings("languages");
}
- return languageCache;
+ return (String[]) languageCache.clone();
}
/**
diff --git a/libjava/classpath/java/util/SimpleTimeZone.java b/libjava/classpath/java/util/SimpleTimeZone.java
index 0bda44c3327..d94f89ad3f9 100644
--- a/libjava/classpath/java/util/SimpleTimeZone.java
+++ b/libjava/classpath/java/util/SimpleTimeZone.java
@@ -774,7 +774,7 @@ public class SimpleTimeZone extends TimeZone
* @param year The year.
*/
private int getDaysInMonth(int month, int year)
- {
+ {
if (month == Calendar.FEBRUARY)
{
if ((year & 3) != 0)
diff --git a/libjava/classpath/java/util/TreeMap.java b/libjava/classpath/java/util/TreeMap.java
index a00f257aa8b..60d0a4d50a1 100644
--- a/libjava/classpath/java/util/TreeMap.java
+++ b/libjava/classpath/java/util/TreeMap.java
@@ -1434,12 +1434,9 @@ public class TreeMap extends AbstractMap
/**
* Returns true if the Iterator has more elements.
* @return true if there are more elements
- * @throws ConcurrentModificationException if the TreeMap was modified
*/
public boolean hasNext()
{
- if (knownMod != modCount)
- throw new ConcurrentModificationException();
return next != max;
}
diff --git a/libjava/classpath/java/util/WeakHashMap.java b/libjava/classpath/java/util/WeakHashMap.java
index 2ed982ac32d..ef2444c0409 100644
--- a/libjava/classpath/java/util/WeakHashMap.java
+++ b/libjava/classpath/java/util/WeakHashMap.java
@@ -292,12 +292,9 @@ public class WeakHashMap extends AbstractMap implements Map
/**
* Checks if there are more entries.
* @return true, iff there are more elements.
- * @throws ConcurrentModificationException if the hash map was
- * modified.
*/
public boolean hasNext()
{
- checkMod();
return nextEntry != null;
}
diff --git a/libjava/classpath/java/util/class-dependencies.conf b/libjava/classpath/java/util/class-dependencies.conf
deleted file mode 100644
index 39f96062744..00000000000
--- a/libjava/classpath/java/util/class-dependencies.conf
+++ /dev/null
@@ -1,78 +0,0 @@
-# This property file contains dependencies of classes, methods, and
-# field on other methods or classes.
-#
-# Syntax:
-#
-# <used>: <needed 1> [... <needed N>]
-#
-# means that when <used> is included, <needed 1> (... <needed N>) must
-# be included as well.
-#
-# <needed X> and <used> are of the form
-#
-# <class.methodOrField(signature)>
-#
-# or just
-#
-# <class>
-#
-# Within dependencies, variables can be used. A variable is defined as
-# follows:
-#
-# {variable}: value1 value2 ... value<n>
-#
-# variables can be used on the right side of dependencies as follows:
-#
-# <used>: com.bla.blu.{variable}.Class.m()V
-#
-# The use of the variable will expand to <n> dependencies of the form
-#
-# <used>: com.bla.blu.value1.Class.m()V
-# <used>: com.bla.blu.value2.Class.m()V
-# ...
-# <used>: com.bla.blu.value<n>.Class.m()V
-#
-# Variables can be redefined when building a system to select the
-# required support for features like encodings, protocols, etc.
-#
-# Hints:
-#
-# - For methods and fields, the signature is mandatory. For
-# specification, please see the Java Virtual Machine Specification by
-# SUN. Unlike in the spec, field signatures (types) are in brackets.
-#
-# - Package names must be separated by '/' (and not '.'). E.g.,
-# java/lang/Class (this is necessary, because the '.' is used to
-# separate method or field names from classes)
-#
-# - In case <needed> refers to a class, only the class itself will be
-# included in the resulting binary, NOT necessarily all its methods
-# and fields. If you want to refer to all methods and fields, you can
-# write class.* as an abbreviation.
-#
-# - Abbreviations for packages are also possible: my/package/* means all
-# methods and fields of all classes in my/package.
-#
-# - A line with a trailing '\' continues in the next line.
-
-
-# All calendars supported are loaded via java/util/Calendar.getBundle or
-# java/util/GregorianCalendar.getBundle from class
-# gnu/java/locale/Calendar_{locale_id}
-#
-# This introduces a dependency for the localized calendars. To allow an easy
-# selection and addition of locales, the library variable {calendar_locales}
-# can be set to the set of supported calendar locales.
-#
-
-{calendar_locales}: de en nl
-
-java/util/Calendar.getBundle(Ljava/util/Locale;)Ljava/util/ResourceBundle;: \
- gnu/java/locale/Calendar.* \
- gnu/java/locale/Calendar_{calendar_locales}.*
-
-java/util/GregorianCalendar.getBundle(Ljava/util/Locale;)Ljava/util/ResourceBundle;: \
- gnu/java/locale/Calendar.* \
- gnu/java/locale/Calendar_{calendar_locales}.*
-
-# end of file
diff --git a/libjava/classpath/java/util/jar/Attributes.java b/libjava/classpath/java/util/jar/Attributes.java
index c8babddab37..92d29cf49b9 100644
--- a/libjava/classpath/java/util/jar/Attributes.java
+++ b/libjava/classpath/java/util/jar/Attributes.java
@@ -37,6 +37,8 @@ exception statement from your version. */
package java.util.jar;
+import gnu.java.util.jar.JarUtils;
+
import java.util.Collection;
import java.util.Hashtable;
import java.util.Map;
@@ -65,7 +67,8 @@ import java.util.Set;
* @see java.util.jar.Attributes.Name
* @author Mark Wielaard (mark@klomp.org)
*/
-public class Attributes implements Cloneable, Map
+public class Attributes
+ implements Cloneable, java.util.Map // Fully qualified for jikes 1.22
{
// Fields
@@ -121,14 +124,13 @@ public class Attributes implements Cloneable, Map
* General main attribute -
* the version of this Manifest file.
*/
- public static final Name MANIFEST_VERSION = new Name("Manifest-Version");
+ public static final Name MANIFEST_VERSION = new Name(JarUtils.MANIFEST_VERSION);
/**
* General main attribute -
* the version of the jar file signature.
*/
- public static final Name SIGNATURE_VERSION
- = new Name("Signature-Version");
+ public static final Name SIGNATURE_VERSION = new Name(JarUtils.SIGNATURE_VERSION);
/**
* General main attribute -
@@ -433,7 +435,7 @@ public class Attributes implements Cloneable, Map
* @returns the old value of the attribute name or null if it didn't exist
* yet
*/
- public String putValue(Name name, String value)
+ private String putValue(Name name, String value)
{
return (String) put(name, value);
}
diff --git a/libjava/classpath/java/util/jar/JarFile.java b/libjava/classpath/java/util/jar/JarFile.java
index 7ccbc60af87..88814f1d6bf 100644
--- a/libjava/classpath/java/util/jar/JarFile.java
+++ b/libjava/classpath/java/util/jar/JarFile.java
@@ -1,5 +1,5 @@
/* JarFile.java - Representation of a jar file
- Copyright (C) 2000, 2003, 2004, 2005 Free Software Foundation, Inc.
+ Copyright (C) 2000, 2003, 2004, 2005, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -42,6 +42,7 @@ import gnu.java.io.Base64InputStream;
import gnu.java.security.OID;
import gnu.java.security.pkcs.PKCS7SignedData;
import gnu.java.security.pkcs.SignerInfo;
+import gnu.java.security.provider.Gnu;
import java.io.ByteArrayOutputStream;
import java.io.File;
@@ -105,6 +106,14 @@ public class JarFile extends ZipFile
/** The suffix for signature files. */
private static final String SF_SUFFIX = ".SF";
+ /**
+ * The security provider to use for signature verification.
+ * We need a known fallback to be able to read any signed jar file
+ * (which might contain the user selected security provider).
+ * This is package-private to avoid accessor methods for inner classes.
+ */
+ static final Gnu provider = new Gnu();
+
// Signature OIDs.
private static final OID MD2_OID = new OID("1.2.840.113549.2.2");
private static final OID MD4_OID = new OID("1.2.840.113549.2.4");
@@ -636,19 +645,19 @@ public class JarFile extends ZipFile
{
if (!signerInfo.getDigestAlgorithmId().equals(SHA1_OID))
return;
- sig = Signature.getInstance("SHA1withDSA");
+ sig = Signature.getInstance("SHA1withDSA", provider);
}
else if (alg.equals(RSA_ENCRYPTION_OID))
{
OID hash = signerInfo.getDigestAlgorithmId();
if (hash.equals(MD2_OID))
- sig = Signature.getInstance("md2WithRsaEncryption");
+ sig = Signature.getInstance("md2WithRsaEncryption", provider);
else if (hash.equals(MD4_OID))
- sig = Signature.getInstance("md4WithRsaEncryption");
+ sig = Signature.getInstance("md4WithRsaEncryption", provider);
else if (hash.equals(MD5_OID))
- sig = Signature.getInstance("md5WithRsaEncryption");
+ sig = Signature.getInstance("md5WithRsaEncryption", provider);
else if (hash.equals(SHA1_OID))
- sig = Signature.getInstance("sha1WithRsaEncryption");
+ sig = Signature.getInstance("sha1WithRsaEncryption", provider);
else
return;
}
@@ -756,7 +765,7 @@ public class JarFile extends ZipFile
try
{
byte[] hash = Base64InputStream.decode((String) e.getValue());
- MessageDigest md = MessageDigest.getInstance(alg);
+ MessageDigest md = MessageDigest.getInstance(alg, provider);
md.update(entryBytes);
byte[] hash2 = md.digest();
if (DEBUG)
@@ -939,8 +948,9 @@ public class JarFile extends ZipFile
hashes.add(Base64InputStream.decode((String) e.getValue()));
try
{
- md.add(MessageDigest.getInstance
- (key.substring(0, key.length() - DIGEST_KEY_SUFFIX.length())));
+ int length = key.length() - DIGEST_KEY_SUFFIX.length();
+ String alg = key.substring(0, length);
+ md.add(MessageDigest.getInstance(alg, provider));
}
catch (NoSuchAlgorithmException nsae)
{
diff --git a/libjava/classpath/java/util/jar/Manifest.java b/libjava/classpath/java/util/jar/Manifest.java
index ff82aa2db96..aa869f4c4b0 100644
--- a/libjava/classpath/java/util/jar/Manifest.java
+++ b/libjava/classpath/java/util/jar/Manifest.java
@@ -37,16 +37,12 @@ exception statement from your version. */
package java.util.jar;
-import java.io.BufferedReader;
-import java.io.BufferedWriter;
+import gnu.java.util.jar.JarUtils;
+
import java.io.IOException;
import java.io.InputStream;
-import java.io.InputStreamReader;
import java.io.OutputStream;
-import java.io.OutputStreamWriter;
-import java.io.PrintWriter;
import java.util.Hashtable;
-import java.util.Iterator;
import java.util.Map;
/**
@@ -156,282 +152,27 @@ public class Manifest implements Cloneable
}
/**
- * XXX
+ * Read and merge a <code>Mainfest</code> from the designated input stream.
+ *
+ * @param in the input stream to read from.
+ * @throws IOException if an I/O related exception occurs during the process.
*/
public void read(InputStream in) throws IOException
{
- BufferedReader br =
- new BufferedReader(new InputStreamReader(in, "8859_1"));
- read_main_section(getMainAttributes(), br);
- read_individual_sections(getEntries(), br);
- }
-
- // Private Static methods for reading the Manifest file from BufferedReader
-
- private static void read_main_section(Attributes attr,
- BufferedReader br) throws IOException
- {
- // According to the spec we should actually call read_version_info() here.
- read_attributes(attr, br);
- // Explicitly set Manifest-Version attribute if not set in Main
- // attributes of Manifest.
- if (attr.getValue(Attributes.Name.MANIFEST_VERSION) == null)
- attr.putValue(Attributes.Name.MANIFEST_VERSION, "0.0");
- }
-
- /**
- * Pedantic method that requires the next attribute in the Manifest to be
- * the "Manifest-Version". This follows the Manifest spec closely but
- * reject some jar Manifest files out in the wild.
- */
- private static void read_version_info(Attributes attr,
- BufferedReader br) throws IOException
- {
- String version_header = Attributes.Name.MANIFEST_VERSION.toString();
- try
- {
- String value = expect_header(version_header, br);
- attr.putValue(Attributes.Name.MANIFEST_VERSION, value);
- }
- catch (IOException ioe)
- {
- throw new JarException("Manifest should start with a " +
- version_header + ": " + ioe.getMessage());
- }
- }
-
- private static String expect_header(String header, BufferedReader br)
- throws IOException
- {
- String s = br.readLine();
- if (s == null)
- {
- throw new JarException("unexpected end of file");
- }
- return expect_header(header, br, s);
- }
-
- private static String expect_header(String header, BufferedReader br,
- String s) throws IOException
- {
- try
- {
- String name = s.substring(0, header.length() + 1);
- if (name.equalsIgnoreCase(header + ":"))
- {
- String value_start = s.substring(header.length() + 2);
- return read_header_value(value_start, br);
- }
- }
- catch (IndexOutOfBoundsException iobe)
- {
- }
- // If we arrive here, something went wrong
- throw new JarException("unexpected '" + s + "'");
- }
-
- private static String read_header_value(String s, BufferedReader br)
- throws IOException
- {
- boolean try_next = true;
- while (try_next)
- {
- // Lets see if there is something on the next line
- br.mark(1);
- if (br.read() == ' ')
- {
- s += br.readLine();
- }
- else
- {
- br.reset();
- try_next = false;
- }
- }
- return s;
- }
-
- private static void read_attributes(Attributes attr,
- BufferedReader br) throws IOException
- {
- String s = br.readLine();
- while (s != null && (!s.equals("")))
- {
- read_attribute(attr, s, br);
- s = br.readLine();
- }
- }
-
- private static void read_attribute(Attributes attr, String s,
- BufferedReader br) throws IOException
- {
- try
- {
- int colon = s.indexOf(": ");
- String name = s.substring(0, colon);
- String value_start = s.substring(colon + 2);
- String value = read_header_value(value_start, br);
- attr.putValue(name, value);
- }
- catch (IndexOutOfBoundsException iobe)
- {
- throw new JarException("Manifest contains a bad header: " + s);
- }
- }
-
- private static void read_individual_sections(Map entries,
- BufferedReader br) throws
- IOException
- {
- String s = br.readLine();
- while (s != null && (!s.equals("")))
- {
- Attributes attr = read_section_name(s, br, entries);
- read_attributes(attr, br);
- s = br.readLine();
- }
- }
-
- private static Attributes read_section_name(String s, BufferedReader br,
- Map entries) throws JarException
- {
- try
- {
- String name = expect_header("Name", br, s);
- Attributes attr = new Attributes();
- entries.put(name, attr);
- return attr;
- }
- catch (IOException ioe)
- {
- throw new JarException
- ("Section should start with a Name header: " + ioe.getMessage());
- }
+ JarUtils.readMFManifest(getMainAttributes(), getEntries(), in);
}
/**
- * XXX
+ * Writes the contents of this <code>Manifest</code> to the designated
+ * output stream. Line-endings are platform-independent and consist of the
+ * 2-codepoint sequence <code>0x0D</code> and <code>0x0A</code>.
+ *
+ * @param out the output stream to write this <code>Manifest</code> to.
+ * @throws IOException if an I/O related exception occurs during the process.
*/
public void write(OutputStream out) throws IOException
{
- PrintWriter pw =
- new PrintWriter(new
- BufferedWriter(new OutputStreamWriter(out, "8859_1")));
- write_main_section(getMainAttributes(), pw);
- pw.println();
- write_individual_sections(getEntries(), pw);
- if (pw.checkError())
- {
- throw new JarException("Error while writing manifest");
- }
- }
-
- // Private Static functions for writing the Manifest file to a PrintWriter
-
- private static void write_main_section(Attributes attr,
- PrintWriter pw) throws JarException
- {
- write_version_info(attr, pw);
- write_main_attributes(attr, pw);
- }
-
- private static void write_version_info(Attributes attr, PrintWriter pw)
- {
- // First check if there is already a version attribute set
- String version = attr.getValue(Attributes.Name.MANIFEST_VERSION);
- if (version == null)
- {
- version = "1.0";
- }
- write_header(Attributes.Name.MANIFEST_VERSION.toString(), version, pw);
- }
-
- private static void write_header(String name, String value, PrintWriter pw)
- {
- pw.print(name + ": ");
-
- int last = 68 - name.length();
- if (last > value.length())
- {
- pw.println(value);
- }
- else
- {
- pw.println(value.substring(0, last));
- }
- while (last < value.length())
- {
- pw.print(" ");
- int end = (last + 69);
- if (end > value.length())
- {
- pw.println(value.substring(last));
- }
- else
- {
- pw.println(value.substring(last, end));
- }
- last = end;
- }
- }
-
- private static void write_main_attributes(Attributes attr, PrintWriter pw)
- throws JarException
- {
- Iterator it = attr.entrySet().iterator();
- while (it.hasNext())
- {
- Map.Entry entry = (Map.Entry) it.next();
- // Don't print the manifest version again
- if (!Attributes.Name.MANIFEST_VERSION.equals(entry.getKey()))
- {
- write_attribute_entry(entry, pw);
- }
- }
- }
-
- private static void write_attribute_entry(Map.Entry entry, PrintWriter pw)
- throws JarException
- {
- String name = entry.getKey().toString();
- String value = entry.getValue().toString();
-
- if (name.equalsIgnoreCase("Name"))
- {
- throw new JarException("Attributes cannot be called 'Name'");
- }
- if (name.startsWith("From"))
- {
- throw new
- JarException("Header cannot start with the four letters 'From'" +
- name);
- }
- write_header(name, value, pw);
- }
-
- private static void write_individual_sections(Map entries, PrintWriter pw)
- throws JarException
- {
-
- Iterator it = entries.entrySet().iterator();
- while (it.hasNext())
- {
- Map.Entry entry = (Map.Entry) it.next();
- write_header("Name", entry.getKey().toString(), pw);
- write_entry_attributes((Attributes) entry.getValue(), pw);
- pw.println();
- }
- }
-
- private static void write_entry_attributes(Attributes attr, PrintWriter pw)
- throws JarException
- {
- Iterator it = attr.entrySet().iterator();
- while (it.hasNext())
- {
- Map.Entry entry = (Map.Entry) it.next();
- write_attribute_entry(entry, pw);
- }
+ JarUtils.writeMFManifest(getMainAttributes(), getEntries(), out);
}
/**
diff --git a/libjava/classpath/java/util/logging/Level.java b/libjava/classpath/java/util/logging/Level.java
index 2c400dc3a90..48ff318a464 100644
--- a/libjava/classpath/java/util/logging/Level.java
+++ b/libjava/classpath/java/util/logging/Level.java
@@ -1,5 +1,5 @@
/* Level.java -- a class for indicating logging levels
- Copyright (C) 2002, 2005 Free Software Foundation, Inc.
+ Copyright (C) 2002, 2005, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -341,6 +341,9 @@ public class Level implements Serializable
for (int i = 0; i < knownLevels.length; i++)
{
+ // It's safe to use == instead of .equals here because only the
+ // standard logging levels will be returned by this method, and
+ // they are all created using string literals.
if (name == knownLevels[i].name)
return knownLevels[i];
}
diff --git a/libjava/classpath/java/util/logging/LogManager.java b/libjava/classpath/java/util/logging/LogManager.java
index 73eb9bcdd21..e2604815b0c 100644
--- a/libjava/classpath/java/util/logging/LogManager.java
+++ b/libjava/classpath/java/util/logging/LogManager.java
@@ -1,6 +1,6 @@
/* LogManager.java -- a class for maintaining Loggers and managing
configuration properties
- Copyright (C) 2002,2005 Free Software Foundation, Inc.
+ Copyright (C) 2002, 2005, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -48,11 +48,14 @@ import java.lang.ref.WeakReference;
import java.net.URL;
import java.util.Collections;
import java.util.Enumeration;
+import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import java.util.Properties;
import java.util.StringTokenizer;
+import gnu.classpath.SystemProperties;
+
/**
* The <code>LogManager</code> maintains a hierarchical namespace
* of Logger objects and manages properties for configuring the logging
@@ -114,7 +117,6 @@ public class LogManager
* a WeakReference to it.
*/
private Map loggers;
- final Logger rootLogger;
/**
* The properties for the logging framework which have been
@@ -135,83 +137,62 @@ public class LogManager
* this case.
*/
private final PropertyChangeSupport pcs = new PropertyChangeSupport( /* source bean */
- LogManager.class);
+ LogManager.class);
protected LogManager()
{
- if (logManager != null)
- throw new IllegalStateException("there can be only one LogManager; use LogManager.getLogManager()");
-
- logManager = this;
- loggers = new java.util.HashMap();
- rootLogger = new Logger("", null);
- rootLogger.setLevel(Level.INFO);
- addLogger(rootLogger);
-
- /* Make sure that Logger.global has the rootLogger as its parent.
- *
- * Logger.global is set during class initialization of Logger,
- * which may or may not be before this code is being executed.
- * For example, on the Sun 1.3.1 and 1.4.0 JVMs, Logger.global
- * has been set before this code is being executed. In contrast,
- * Logger.global still is null on GCJ 3.2. Since the LogManager
- * and Logger classes are mutually dependent, both behaviors are
- * correct.
- *
- * This means that we cannot depend on Logger.global to have its
- * value when this code executes, although that variable is final.
- * Since Logger.getLogger will always return the same logger for
- * the same name, the subsequent line works fine irrespective of
- * the order in which classes are initialized.
- */
- Logger.getLogger("global").setParent(rootLogger);
- Logger.getLogger("global").setUseParentHandlers(true);
+ loggers = new HashMap();
}
/**
* Returns the globally shared LogManager instance.
*/
- public static LogManager getLogManager()
+ public static synchronized LogManager getLogManager()
{
+ if (logManager == null)
+ {
+ logManager = makeLogManager();
+ initLogManager();
+ }
return logManager;
}
- static
- {
- makeLogManager();
-
- /* The Javadoc description of the class explains
- * what is going on here.
- */
- Object configurator = createInstance(System.getProperty("java.util.logging.config.class"),
- /* must be instance of */ Object.class);
-
- try
- {
- if (configurator == null)
- getLogManager().readConfiguration();
- }
- catch (IOException ex)
- {
- /* FIXME: Is it ok to ignore exceptions here? */
- }
- }
+ private static final String MANAGER_PROPERTY = "java.util.logging.manager";
private static LogManager makeLogManager()
{
- String managerClassName;
- LogManager manager;
+ String managerClassName = SystemProperties.getProperty(MANAGER_PROPERTY);
+ LogManager manager = (LogManager) createInstance
+ (managerClassName, LogManager.class, MANAGER_PROPERTY);
+ if (manager == null)
+ manager = new LogManager();
+ return manager;
+ }
- managerClassName = System.getProperty("java.util.logging.manager");
- manager = (LogManager) createInstance(managerClassName, LogManager.class);
- if (manager != null)
- return manager;
+ private static final String CONFIG_PROPERTY = "java.util.logging.config.class";
- if (managerClassName != null)
- System.err.println("WARNING: System property \"java.util.logging.manager\""
- + " should be the name of a subclass of java.util.logging.LogManager");
+ private static void initLogManager()
+ {
+ LogManager manager = getLogManager();
+ Logger.root.setLevel(Level.INFO);
+ manager.addLogger(Logger.root);
+
+ /* The Javadoc description of the class explains
+ * what is going on here.
+ */
+ Object configurator = createInstance(System.getProperty(CONFIG_PROPERTY),
+ /* must be instance of */ Object.class,
+ CONFIG_PROPERTY);
- return new LogManager();
+ try
+ {
+ if (configurator == null)
+ manager.readConfiguration();
+ }
+ catch (IOException ex)
+ {
+ /* FIXME: Is it ok to ignore exceptions here? */
+ }
}
/**
@@ -314,7 +295,7 @@ public class LogManager
if(index > -1)
searchName = searchName.substring(0,index);
else
- searchName = "";
+ searchName = "";
}
logger.setLevel(logLevel);
@@ -324,12 +305,12 @@ public class LogManager
* When adding "foo.bar", the logger "foo.bar.baz" should change
* its parent to "foo.bar".
*/
- if (parent != rootLogger)
+ if (parent != Logger.root)
{
for (Iterator iter = loggers.keySet().iterator(); iter.hasNext();)
{
Logger possChild = (Logger) ((WeakReference) loggers.get(iter.next()))
- .get();
+ .get();
if ((possChild == null) || (possChild == logger)
|| (possChild.getParent() != parent))
continue;
@@ -367,14 +348,14 @@ public class LogManager
{
String childName = child.getName();
int childNameLength = childName.length();
- Logger best = rootLogger;
+ Logger best = Logger.root;
int bestNameLength = 0;
Logger cand;
String candName;
int candNameLength;
- if (child == rootLogger)
+ if (child == Logger.root)
return null;
for (Iterator iter = loggers.keySet().iterator(); iter.hasNext();)
@@ -468,7 +449,7 @@ public class LogManager
if (logger == null)
iter.remove();
- else if (logger != rootLogger)
+ else if (logger != Logger.root)
{
logger.resetLogger();
logger.setLevel(null);
@@ -476,8 +457,8 @@ public class LogManager
}
}
- rootLogger.setLevel(Level.INFO);
- rootLogger.resetLogger();
+ Logger.root.setLevel(Level.INFO);
+ Logger.root.resetLogger();
}
/**
@@ -524,11 +505,11 @@ public class LogManager
// If no config file could be found use a default configuration.
if(inputStream == null)
- {
- String defaultConfig = "handlers = java.util.logging.ConsoleHandler \n"
+ {
+ String defaultConfig = "handlers = java.util.logging.ConsoleHandler \n"
+ ".level=INFO \n";
- inputStream = new ByteArrayInputStream(defaultConfig.getBytes());
- }
+ inputStream = new ByteArrayInputStream(defaultConfig.getBytes());
+ }
}
else
inputStream = new java.io.FileInputStream(path);
@@ -574,21 +555,9 @@ public class LogManager
while (tokenizer.hasMoreTokens())
{
String handlerName = tokenizer.nextToken();
- try
- {
- Class handlerClass = ClassLoader.getSystemClassLoader().loadClass(handlerName);
- getLogger("").addHandler((Handler) handlerClass
- .newInstance());
- }
- catch (ClassCastException ex)
- {
- System.err.println("[LogManager] class " + handlerName
- + " is not subclass of java.util.logging.Handler");
- }
- catch (Exception ex)
- {
- //System.out.println("[LogManager.readConfiguration]"+ex);
- }
+ Handler handler = (Handler)
+ createInstance(handlerName, Handler.class, key);
+ Logger.root.addHandler(handler);
}
}
@@ -602,14 +571,19 @@ public class LogManager
logger = Logger.getLogger(loggerName);
addLogger(logger);
}
+ Level level = null;
try
- {
- logger.setLevel(Level.parse(value));
- }
- catch (Exception _)
- {
- //System.out.println("[LogManager.readConfiguration] "+_);
- }
+ {
+ level = Level.parse(value);
+ }
+ catch (IllegalArgumentException e)
+ {
+ warn("bad level \'" + value + "\'", e);
+ }
+ if (level != null)
+ {
+ logger.setLevel(level);
+ }
continue;
}
}
@@ -748,19 +722,17 @@ public class LogManager
*/
static final Class getClassProperty(String propertyName, Class defaultValue)
{
- Class usingClass = null;
+ String propertyValue = logManager.getProperty(propertyName);
- try
- {
- String propertyValue = logManager.getProperty(propertyName);
- if (propertyValue != null)
- usingClass = Class.forName(propertyValue);
- if (usingClass != null)
- return usingClass;
- }
- catch (Exception _)
- {
- }
+ if (propertyValue != null)
+ try
+ {
+ return locateClass(propertyValue);
+ }
+ catch (ClassNotFoundException e)
+ {
+ warn(propertyName + " = " + propertyValue, e);
+ }
return defaultValue;
}
@@ -774,12 +746,17 @@ public class LogManager
try
{
- Object obj = klass.newInstance();
- if (ofClass.isInstance(obj))
- return obj;
+ Object obj = klass.newInstance();
+ if (ofClass.isInstance(obj))
+ return obj;
}
- catch (Exception _)
+ catch (InstantiationException e)
{
+ warn(propertyName + " = " + klass.getName(), e);
+ }
+ catch (IllegalAccessException e)
+ {
+ warn(propertyName + " = " + klass.getName(), e);
}
if (defaultClass == null)
@@ -824,14 +801,17 @@ public class LogManager
}
/**
- * Creates a new instance of a class specified by name.
+ * Creates a new instance of a class specified by name and verifies
+ * that it is an instance (or subclass of) a given type.
*
* @param className the name of the class of which a new instance
* should be created.
*
- * @param ofClass the class to which the new instance should
- * be either an instance or an instance of a subclass.
- * FIXME: This description is just terrible.
+ * @param type the object created must be an instance of
+ * <code>type</code> or any subclass of <code>type</code>
+ *
+ * @param property the system property to reference in error
+ * messages
*
* @return the new instance, or <code>null</code> if
* <code>className</code> is <code>null</code>, if no class
@@ -839,28 +819,89 @@ public class LogManager
* loading that class, or if the constructor of the class
* has thrown an exception.
*/
- static final Object createInstance(String className, Class ofClass)
+ private static final Object createInstance(String className, Class type,
+ String property)
{
- Class klass;
+ Class klass = null;
if ((className == null) || (className.length() == 0))
return null;
try
{
- klass = Class.forName(className);
- if (! ofClass.isAssignableFrom(klass))
- return null;
-
- return klass.newInstance();
+ klass = locateClass(className);
+ if (type.isAssignableFrom(klass))
+ return klass.newInstance();
+ warn(property, className, "not an instance of " + type.getName());
+ }
+ catch (ClassNotFoundException e)
+ {
+ warn(property, className, "class not found");
+ }
+ catch (IllegalAccessException e)
+ {
+ warn(property, className, "illegal access");
}
- catch (Exception _)
+ catch (InstantiationException e)
{
- return null;
+ warn(property, className, e);
}
- catch (java.lang.LinkageError _)
+ catch (java.lang.LinkageError e)
{
- return null;
+ warn(property, className, "linkage error");
}
+
+ return null;
}
+
+ private static final void warn(String property, String klass, Throwable t)
+ {
+ warn(property, klass, null, t);
+ }
+
+ private static final void warn(String property, String klass, String msg)
+ {
+ warn(property, klass, msg, null);
+ }
+
+ private static final void warn(String property, String klass, String msg,
+ Throwable t)
+ {
+ warn("error instantiating '" + klass + "' referenced by " + property +
+ (msg == null ? "" : ", " + msg), t);
+ }
+
+ /**
+ * All debug warnings go through this method.
+ */
+
+ private static final void warn(String msg, Throwable t)
+ {
+ System.err.println("WARNING: " + msg);
+ if (t != null)
+ t.printStackTrace(System.err);
+ }
+
+ /**
+ * Locates a class by first checking the system class loader and
+ * then checking the context class loader.
+ *
+ * @param name the fully qualified name of the Class to locate
+ * @return Class the located Class
+ */
+
+ private static Class locateClass(String name) throws ClassNotFoundException
+ {
+ ClassLoader loader = Thread.currentThread().getContextClassLoader();
+ try
+ {
+ return Class.forName(name, true, loader);
+ }
+ catch (ClassNotFoundException e)
+ {
+ loader = ClassLoader.getSystemClassLoader();
+ return Class.forName(name, true, loader);
+ }
+ }
+
}
diff --git a/libjava/classpath/java/util/logging/Logger.java b/libjava/classpath/java/util/logging/Logger.java
index 367faad9707..29f19e440ca 100644
--- a/libjava/classpath/java/util/logging/Logger.java
+++ b/libjava/classpath/java/util/logging/Logger.java
@@ -1,5 +1,5 @@
/* Logger.java -- a class for logging messages
- Copyright (C) 2002, 2004 Free Software Foundation, Inc.
+ Copyright (C) 2002, 2004, 2006 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -41,6 +41,8 @@ package java.util.logging;
import java.util.List;
import java.util.MissingResourceException;
import java.util.ResourceBundle;
+import java.security.AccessController;
+import java.security.PrivilegedAction;
/**
* A Logger is used for logging information about events. Usually, there
@@ -67,13 +69,29 @@ import java.util.ResourceBundle;
*/
public class Logger
{
+
+ static final Logger root = new Logger("", null);
+
/**
* A logger provided to applications that make only occasional use
* of the logging framework, typically early prototypes. Serious
* products are supposed to create and use their own Loggers, so
* they can be controlled individually.
*/
- public static final Logger global = getLogger("global");
+ public static final Logger global;
+
+ static
+ {
+ // Our class might be initialized from an unprivileged context
+ global = (Logger) AccessController.doPrivileged
+ (new PrivilegedAction()
+ {
+ public Object run()
+ {
+ return getLogger("global");
+ }
+ });
+ }
/**
@@ -175,7 +193,7 @@ public class Logger
/* This is null when the root logger is being constructed,
* and the root logger afterwards.
*/
- parent = LogManager.getLogManager().rootLogger;
+ parent = root;
useParentHandlers = (parent != null);
}
@@ -1148,16 +1166,12 @@ public class Logger
*/
public synchronized void setParent(Logger parent)
{
- LogManager lm;
-
/* Throw a new NullPointerException if parent is null. */
parent.getClass();
- lm = LogManager.getLogManager();
-
- if (this == lm.rootLogger)
+ if (this == root)
throw new IllegalArgumentException(
- "only the root logger can have a null parent");
+ "the root logger can only have a null parent");
/* An application is allowed to control an anonymous logger
* without having the permission to control the logging
diff --git a/libjava/classpath/java/util/regex/Matcher.java b/libjava/classpath/java/util/regex/Matcher.java
index 98086bfdbe7..e86be25fc41 100644
--- a/libjava/classpath/java/util/regex/Matcher.java
+++ b/libjava/classpath/java/util/regex/Matcher.java
@@ -40,6 +40,7 @@ package java.util.regex;
import gnu.regexp.RE;
import gnu.regexp.REMatch;
+import gnu.regexp.CharIndexed;
/**
* Instance of a regular expression applied to a char sequence.
@@ -50,6 +51,10 @@ public final class Matcher implements MatchResult
{
private Pattern pattern;
private CharSequence input;
+ // We use CharIndexed as an input object to the getMatch method in order
+ // that /\G/ (the end of the previous match) may work. The information
+ // of the previous match is stored in the CharIndexed object.
+ private CharIndexed inputCharIndexed;
private int position;
private int appendPosition;
private REMatch match;
@@ -58,6 +63,7 @@ public final class Matcher implements MatchResult
{
this.pattern = pattern;
this.input = input;
+ this.inputCharIndexed = RE.makeCharIndexed(input, 0);
}
/**
@@ -119,7 +125,7 @@ public final class Matcher implements MatchResult
public boolean find ()
{
boolean first = (match == null);
- match = pattern.getRE().getMatch(input, position);
+ match = pattern.getRE().getMatch(inputCharIndexed, position);
if (match != null)
{
int endIndex = match.getEndIndex();
@@ -150,7 +156,7 @@ public final class Matcher implements MatchResult
*/
public boolean find (int start)
{
- match = pattern.getRE().getMatch(input, start);
+ match = pattern.getRE().getMatch(inputCharIndexed, start);
if (match != null)
{
position = match.getEndIndex();
@@ -212,7 +218,7 @@ public final class Matcher implements MatchResult
public boolean lookingAt ()
{
- match = pattern.getRE().getMatch(input, 0);
+ match = pattern.getRE().getMatch(inputCharIndexed, 0);
if (match != null)
{
if (match.getStartIndex() == 0)
@@ -237,7 +243,7 @@ public final class Matcher implements MatchResult
*/
public boolean matches ()
{
- match = pattern.getRE().getMatch(input, 0, RE.REG_TRY_ENTIRE_MATCH);
+ match = pattern.getRE().getMatch(inputCharIndexed, 0, RE.REG_TRY_ENTIRE_MATCH);
if (match != null)
{
if (match.getStartIndex() == 0)
diff --git a/libjava/classpath/java/util/regex/Pattern.java b/libjava/classpath/java/util/regex/Pattern.java
index d39f1cfb04d..8c1998343a6 100644
--- a/libjava/classpath/java/util/regex/Pattern.java
+++ b/libjava/classpath/java/util/regex/Pattern.java
@@ -74,14 +74,16 @@ public final class Pattern implements Serializable
this.flags = flags;
int gnuFlags = 0;
+ gnuFlags |= RE.REG_ICASE_USASCII;
if ((flags & CASE_INSENSITIVE) != 0)
gnuFlags |= RE.REG_ICASE;
if ((flags & MULTILINE) != 0)
gnuFlags |= RE.REG_MULTILINE;
if ((flags & DOTALL) != 0)
gnuFlags |= RE.REG_DOT_NEWLINE;
+ if ((flags & UNICODE_CASE) != 0)
+ gnuFlags &= ~RE.REG_ICASE_USASCII;
// not yet supported:
- // if ((flags & UNICODE_CASE) != 0) gnuFlags =
// if ((flags & CANON_EQ) != 0) gnuFlags =
RESyntax syntax = RESyntax.RE_SYNTAX_JAVA_1_4;
@@ -94,7 +96,7 @@ public final class Pattern implements Serializable
if ((flags & COMMENTS) != 0)
{
- // Use a syntax with support for comments?
+ gnuFlags |= RE.REG_X_COMMENTS;
}
try
diff --git a/libjava/classpath/java/util/zip/Deflater.java b/libjava/classpath/java/util/zip/Deflater.java
index 7bc1a1911eb..a4ec0e64303 100644
--- a/libjava/classpath/java/util/zip/Deflater.java
+++ b/libjava/classpath/java/util/zip/Deflater.java
@@ -221,7 +221,6 @@ public class Deflater
* where the compressor allocates native memory.
* If you call any method (even reset) afterwards the behaviour is
* <i>undefined</i>.
- * @deprecated Just clear all references to deflater instead.
*/
public void end()
{
diff --git a/libjava/classpath/java/util/zip/DeflaterEngine.java b/libjava/classpath/java/util/zip/DeflaterEngine.java
index 3eea7c250fc..f79e47742bb 100644
--- a/libjava/classpath/java/util/zip/DeflaterEngine.java
+++ b/libjava/classpath/java/util/zip/DeflaterEngine.java
@@ -497,7 +497,7 @@ class DeflaterEngine implements DeflaterConstants
throw new InternalError();
}
}
- huffman.tallyDist(strstart - matchStart, matchLen);
+ boolean full = huffman.tallyDist(strstart - matchStart, matchLen);
lookahead -= matchLen;
if (matchLen <= max_lazy && lookahead >= MIN_MATCH)
@@ -516,7 +516,8 @@ class DeflaterEngine implements DeflaterConstants
updateHash();
}
matchLen = MIN_MATCH - 1;
- continue;
+ if (!full)
+ continue;
}
else
{
diff --git a/libjava/classpath/java/util/zip/GZIPInputStream.java b/libjava/classpath/java/util/zip/GZIPInputStream.java
index 2cea755b3cc..f244810e787 100644
--- a/libjava/classpath/java/util/zip/GZIPInputStream.java
+++ b/libjava/classpath/java/util/zip/GZIPInputStream.java
@@ -207,7 +207,7 @@ public class GZIPInputStream
/* 2. Check the compression type (must be 8) */
int CM = in.read();
- if (CM != 8)
+ if (CM != Deflater.DEFLATED)
throw new IOException("Error in GZIP header, data not in deflate format");
headCRC.update(CM);
diff --git a/libjava/classpath/java/util/zip/Inflater.java b/libjava/classpath/java/util/zip/Inflater.java
index 76de891faa5..f1616d60199 100644
--- a/libjava/classpath/java/util/zip/Inflater.java
+++ b/libjava/classpath/java/util/zip/Inflater.java
@@ -199,7 +199,6 @@ public class Inflater
* with Sun's JDK, where the compressor allocates native memory.
* If you call any method (even reset) afterwards the behaviour is
* <i>undefined</i>.
- * @deprecated Just clear all references to inflater instead.
*/
public void end ()
{
diff --git a/libjava/classpath/java/util/zip/ZipConstants.java b/libjava/classpath/java/util/zip/ZipConstants.java
index 6d664196a53..bdf94506ba2 100644
--- a/libjava/classpath/java/util/zip/ZipConstants.java
+++ b/libjava/classpath/java/util/zip/ZipConstants.java
@@ -85,9 +85,6 @@ interface ZipConstants
long ENDSIG = 'P'|('K'<<8)|(5<<16)|(6<<24);
int ENDHDR = 22;
- /* The following two fields are missing in SUN JDK */
- int ENDNRD = 4;
- int ENDDCD = 6;
int ENDSUB = 8;
int ENDTOT = 10;
int ENDSIZ = 12;
diff --git a/libjava/classpath/java/util/zip/ZipFile.java b/libjava/classpath/java/util/zip/ZipFile.java
index 7307ee9a422..b8495516f16 100644
--- a/libjava/classpath/java/util/zip/ZipFile.java
+++ b/libjava/classpath/java/util/zip/ZipFile.java
@@ -43,6 +43,7 @@ import gnu.java.util.EmptyEnumeration;
import java.io.EOFException;
import java.io.File;
+import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.InputStream;
import java.io.RandomAccessFile;
@@ -75,6 +76,11 @@ public class ZipFile implements ZipConstants
*/
public static final int OPEN_DELETE = 0x4;
+ /**
+ * This field isn't defined in the JDK's ZipConstants, but should be.
+ */
+ static final int ENDNRD = 4;
+
// Name of this zip file.
private final String name;
@@ -86,6 +92,37 @@ public class ZipFile implements ZipConstants
private boolean closed = false;
+
+ /**
+ * Helper function to open RandomAccessFile and throw the proper
+ * ZipException in case opening the file fails.
+ *
+ * @param name the file name, or null if file is provided
+ *
+ * @param file the file, or null if name is provided
+ *
+ * @return the newly open RandomAccessFile, never null
+ */
+ private RandomAccessFile openFile(String name,
+ File file)
+ throws ZipException, IOException
+ {
+ try
+ {
+ return
+ (name != null)
+ ? new RandomAccessFile(name, "r")
+ : new RandomAccessFile(file, "r");
+ }
+ catch (FileNotFoundException f)
+ {
+ ZipException ze = new ZipException(f.getMessage());
+ ze.initCause(f);
+ throw ze;
+ }
+ }
+
+
/**
* Opens a Zip file with the given name for reading.
* @exception IOException if a i/o error occured.
@@ -94,7 +131,7 @@ public class ZipFile implements ZipConstants
*/
public ZipFile(String name) throws ZipException, IOException
{
- this.raf = new RandomAccessFile(name, "r");
+ this.raf = openFile(name,null);
this.name = name;
checkZipFile();
}
@@ -107,7 +144,7 @@ public class ZipFile implements ZipConstants
*/
public ZipFile(File file) throws ZipException, IOException
{
- this.raf = new RandomAccessFile(file, "r");
+ this.raf = openFile(null,file);
this.name = file.getPath();
checkZipFile();
}
@@ -134,7 +171,7 @@ public class ZipFile implements ZipConstants
throw new IllegalArgumentException("invalid mode");
if ((mode & OPEN_DELETE) != 0)
file.deleteOnExit();
- this.raf = new RandomAccessFile(file, "r");
+ this.raf = openFile(null,file);
this.name = file.getPath();
checkZipFile();
}
@@ -408,7 +445,19 @@ public class ZipFile implements ZipConstants
case ZipOutputStream.STORED:
return inp;
case ZipOutputStream.DEFLATED:
- return new InflaterInputStream(inp, new Inflater(true));
+ final Inflater inf = new Inflater(true);
+ final int sz = (int) entry.getSize();
+ return new InflaterInputStream(inp, inf)
+ {
+ public int available() throws IOException
+ {
+ if (sz == -1)
+ return super.available();
+ if (super.available() != 0)
+ return sz - inf.getTotalOut();
+ return 0;
+ }
+ };
default:
throw new ZipException("Unknown compression method " + method);
}
@@ -514,6 +563,7 @@ public class ZipFile implements ZipConstants
pos = 0;
fillBuffer();
}
+
return buffer[pos++] & 0xFF;
}
@@ -544,7 +594,7 @@ public class ZipFile implements ZipConstants
len -= remain;
totalBytesRead += remain;
}
-
+
return totalBytesRead;
}