/* Copyright (C) 1998, 1999 Cygnus Solutions This file is part of libgcj. This software is copyrighted work licensed under the terms of the Libgcj License. Please consult the file "LIBGCJ_LICENSE" for details. */ package java.io; /** * @author Warren Levy * @date October 16, 1998. */ /* Written using "Java Class Libraries", 2nd edition, ISBN 0-201-31002-3 * "The Java Language Specification", ISBN 0-201-63451-1 * plus online API docs for JDK 1.2 beta from http://www.javasoft.com. * Status: Believed complete and correct */ public class CharArrayReader extends Reader { /* An array of chars provided by the creator of the stream. */ protected char[] buf; /* Position of the next char in buf to be read. */ protected int pos; /* The currently marked position in the stream. */ protected int markedPos; /* The index in buf one greater than the last valid character. */ protected int count; public CharArrayReader(char[] buffer) { this(buffer, 0, buffer.length); } public CharArrayReader(char[] buffer, int offset, int length) { super(); buf = buffer; count = offset + length; if (count > buf.length) count = buf.length; pos = offset; // TBD: What should we do if pos is neg. or > count? E.g. throw exc. or: // if (pos < 0 || pos > count) // pos = 0; markedPos = pos; } public void close() { synchronized (lock) { buf = null; } } public void mark(int readAheadLimit) { synchronized (lock) { // readAheadLimit is ignored per Java Class Lib. book, p. 318. markedPos = pos; } } public boolean markSupported() { return true; } public int read() throws IOException { synchronized (lock) { if (buf == null) throw new IOException(); if (pos < 0) throw new ArrayIndexOutOfBoundsException(pos); if (pos < count) return ((int) buf[pos++]) & 0xFFFF; return -1; } } public int read(char[] b, int off, int len) throws IOException { synchronized (lock) { if (buf == null) throw new IOException(); /* Don't need to check pos value, arraycopy will check it. */ if (off < 0 || len < 0 || off + len > b.length) throw new ArrayIndexOutOfBoundsException(); if (pos >= count) return -1; int numChars = Math.min(count - pos, len); System.arraycopy(buf, pos, b, off, numChars); pos += numChars; return numChars; } } public boolean ready() throws IOException { if (buf == null) throw new IOException(); return true; } public void reset() throws IOException { synchronized (lock) { if (buf == null) throw new IOException(); pos = markedPos; } } public long skip(long n) throws IOException { synchronized (lock) { if (buf == null) throw new IOException(); // Even though the var numChars is a long, in reality it can never // be larger than an int since the result of subtracting 2 positive // ints will always fit in an int. Since we have to return a long // anyway, numChars might as well just be a long. long numChars = Math.min((long) (count - pos), n < 0 ? 0L : n); pos += numChars; return numChars; } } }