/** * Return the number of bytes available for reading without * blocking for a long period. * * @return For this stream, this is the number of bytes between the * current read position and the indicated end of the file. * @exception IOException */ public synchronized int available() throws IOException { checkOpen(); // this is backed by a file, which doesn't really block. We can return all the way to the // marked data end, if necessary long endMarker = start + datalen; return (int)(endMarker - (bufpos + pos)); }
/** * Reset the mark position. * * @exception IOException */ public synchronized void reset() throws IOException { checkOpen(); if (markpos < 0) { throw new IOException("Resetting to invalid mark position"); } // if we have a markpos, it will still be in the buffer bounds. pos = markpos; }
/** * Read a single byte of data from the input stream. * * @return The read byte. Returns -1 if an eof condition has been hit. * @exception IOException */ public synchronized int read() throws IOException { checkOpen(); // check to see if we can fill more data if (!checkFill()) { return -1; } // return the current byte...anded to prevent sign extension. return buf[pos++] & 0xff; }
/** * Skip the read pointer ahead a given number of bytes. * * @param n The number of bytes to skip. * * @return The number of bytes actually skipped. * @exception IOException */ public synchronized long skip(long n) throws IOException { checkOpen(); // nothing to skip, so don't skip if (n <= 0) { return 0; } // see if we need to fill more data, and potentially shift the mark positions if (!checkFill()) { return 0; } long available = count - pos; // the skipped contract allows skipping within the current buffer bounds, so cap it there. long skipped = available < n ? available : n; pos += skipped; return skipped; }