1. /*
  2. * @(#)Reader.java 1.24 03/01/23
  3. *
  4. * Copyright 2003 Sun Microsystems, Inc. All rights reserved.
  5. * SUN PROPRIETARY/CONFIDENTIAL. Use is subject to license terms.
  6. */
  7. package java.io;
  8. /**
  9. * Abstract class for reading character streams. The only methods that a
  10. * subclass must implement are read(char[], int, int) and close(). Most
  11. * subclasses, however, will override some of the methods defined here in order
  12. * to provide higher efficiency, additional functionality, or both.
  13. *
  14. *
  15. * @see BufferedReader
  16. * @see LineNumberReader
  17. * @see CharArrayReader
  18. * @see InputStreamReader
  19. * @see FileReader
  20. * @see FilterReader
  21. * @see PushbackReader
  22. * @see PipedReader
  23. * @see StringReader
  24. * @see Writer
  25. *
  26. * @version 1.24, 03/01/23
  27. * @author Mark Reinhold
  28. * @since JDK1.1
  29. */
  30. public abstract class Reader {
  31. /**
  32. * The object used to synchronize operations on this stream. For
  33. * efficiency, a character-stream object may use an object other than
  34. * itself to protect critical sections. A subclass should therefore use
  35. * the object in this field rather than <tt>this</tt> or a synchronized
  36. * method.
  37. */
  38. protected Object lock;
  39. /**
  40. * Create a new character-stream reader whose critical sections will
  41. * synchronize on the reader itself.
  42. */
  43. protected Reader() {
  44. this.lock = this;
  45. }
  46. /**
  47. * Create a new character-stream reader whose critical sections will
  48. * synchronize on the given object.
  49. *
  50. * @param lock The Object to synchronize on.
  51. */
  52. protected Reader(Object lock) {
  53. if (lock == null) {
  54. throw new NullPointerException();
  55. }
  56. this.lock = lock;
  57. }
  58. /**
  59. * Read a single character. This method will block until a character is
  60. * available, an I/O error occurs, or the end of the stream is reached.
  61. *
  62. * <p> Subclasses that intend to support efficient single-character input
  63. * should override this method.
  64. *
  65. * @return The character read, as an integer in the range 0 to 65535
  66. * (<tt>0x00-0xffff</tt>), or -1 if the end of the stream has
  67. * been reached
  68. *
  69. * @exception IOException If an I/O error occurs
  70. */
  71. public int read() throws IOException {
  72. char cb[] = new char[1];
  73. if (read(cb, 0, 1) == -1)
  74. return -1;
  75. else
  76. return cb[0];
  77. }
  78. /**
  79. * Read characters into an array. This method will block until some input
  80. * is available, an I/O error occurs, or the end of the stream is reached.
  81. *
  82. * @param cbuf Destination buffer
  83. *
  84. * @return The number of characters read, or -1
  85. * if the end of the stream
  86. * has been reached
  87. *
  88. * @exception IOException If an I/O error occurs
  89. */
  90. public int read(char cbuf[]) throws IOException {
  91. return read(cbuf, 0, cbuf.length);
  92. }
  93. /**
  94. * Read characters into a portion of an array. This method will block
  95. * until some input is available, an I/O error occurs, or the end of the
  96. * stream is reached.
  97. *
  98. * @param cbuf Destination buffer
  99. * @param off Offset at which to start storing characters
  100. * @param len Maximum number of characters to read
  101. *
  102. * @return The number of characters read, or -1 if the end of the
  103. * stream has been reached
  104. *
  105. * @exception IOException If an I/O error occurs
  106. */
  107. abstract public int read(char cbuf[], int off, int len) throws IOException;
  108. /** Maximum skip-buffer size */
  109. private static final int maxSkipBufferSize = 8192;
  110. /** Skip buffer, null until allocated */
  111. private char skipBuffer[] = null;
  112. /**
  113. * Skip characters. This method will block until some characters are
  114. * available, an I/O error occurs, or the end of the stream is reached.
  115. *
  116. * @param n The number of characters to skip
  117. *
  118. * @return The number of characters actually skipped
  119. *
  120. * @exception IllegalArgumentException If <code>n</code> is negative.
  121. * @exception IOException If an I/O error occurs
  122. */
  123. public long skip(long n) throws IOException {
  124. if (n < 0L)
  125. throw new IllegalArgumentException("skip value is negative");
  126. int nn = (int) Math.min(n, maxSkipBufferSize);
  127. synchronized (lock) {
  128. if ((skipBuffer == null) || (skipBuffer.length < nn))
  129. skipBuffer = new char[nn];
  130. long r = n;
  131. while (r > 0) {
  132. int nc = read(skipBuffer, 0, (int)Math.min(r, nn));
  133. if (nc == -1)
  134. break;
  135. r -= nc;
  136. }
  137. return n - r;
  138. }
  139. }
  140. /**
  141. * Tell whether this stream is ready to be read.
  142. *
  143. * @return True if the next read() is guaranteed not to block for input,
  144. * false otherwise. Note that returning false does not guarantee that the
  145. * next read will block.
  146. *
  147. * @exception IOException If an I/O error occurs
  148. */
  149. public boolean ready() throws IOException {
  150. return false;
  151. }
  152. /**
  153. * Tell whether this stream supports the mark() operation. The default
  154. * implementation always returns false. Subclasses should override this
  155. * method.
  156. *
  157. * @return true if and only if this stream supports the mark operation.
  158. */
  159. public boolean markSupported() {
  160. return false;
  161. }
  162. /**
  163. * Mark the present position in the stream. Subsequent calls to reset()
  164. * will attempt to reposition the stream to this point. Not all
  165. * character-input streams support the mark() operation.
  166. *
  167. * @param readAheadLimit Limit on the number of characters that may be
  168. * read while still preserving the mark. After
  169. * reading this many characters, attempting to
  170. * reset the stream may fail.
  171. *
  172. * @exception IOException If the stream does not support mark(),
  173. * or if some other I/O error occurs
  174. */
  175. public void mark(int readAheadLimit) throws IOException {
  176. throw new IOException("mark() not supported");
  177. }
  178. /**
  179. * Reset the stream. If the stream has been marked, then attempt to
  180. * reposition it at the mark. If the stream has not been marked, then
  181. * attempt to reset it in some way appropriate to the particular stream,
  182. * for example by repositioning it to its starting point. Not all
  183. * character-input streams support the reset() operation, and some support
  184. * reset() without supporting mark().
  185. *
  186. * @exception IOException If the stream has not been marked,
  187. * or if the mark has been invalidated,
  188. * or if the stream does not support reset(),
  189. * or if some other I/O error occurs
  190. */
  191. public void reset() throws IOException {
  192. throw new IOException("reset() not supported");
  193. }
  194. /**
  195. * Close the stream. Once a stream has been closed, further read(),
  196. * ready(), mark(), or reset() invocations will throw an IOException.
  197. * Closing a previously-closed stream, however, has no effect.
  198. *
  199. * @exception IOException If an I/O error occurs
  200. */
  201. abstract public void close() throws IOException;
  202. }