java.io thinks that a read at EOF is an error and should return -1, contrary to traditional
Unix practice where you'd read until you got 0 bytes (and any future read would return -1).
494354
public static int read(FileDescriptor fd, byte[] bytes, int byteOffset, int byteCount) throws IOException {
        Arrays.checkOffsetAndCount(bytes.length, byteOffset, byteCount);
        if (byteCount == 0) {
            return 0;
        }
        try {
            int readCount = Libcore.os.read(fd, bytes, byteOffset, byteCount);
            if (readCount == 0) {
                return -1;
            }
            return readCount;
        } catch (ErrnoException errnoException) {
            if (errnoException.errno == EAGAIN) {
                // We return 0 rather than throw if we try to read from an empty non-blocking pipe.
                return 0;
            }
            throw errnoException.rethrowAsIOException();
        }
    }
7776
@Override
    public int read(byte[] buffer, int offset, int length) throws IOException {
        abortIfNeeded();
        int numBytesRead;
        // If no more bytes are available, do not read any bytes into the buffer
        if(this.virtualAvailable <= 0) {
            numBytesRead = -1;
        } else {
            // If the desired read length is greater than the number of available bytes,
            // shorten the read length to the number of available bytes.
            if(length > this.virtualAvailable) {
                // If the number of available bytes is greater than the maximum value of a 32 bit int, then
                // read as many bytes as an int can.
                length = (this.virtualAvailable < Integer.MAX_VALUE) ? (int)this.virtualAvailable : Integer.MAX_VALUE;
            }
            // Read bytes into the buffer.
            numBytesRead = this.decryptedContents.read(buffer, offset, length);
        }
        // If we were able to read bytes, decrement the number of bytes available to be read.
        if(numBytesRead != -1) {
            this.virtualAvailable -= numBytesRead;
        } else {
            // If we've reached the end of the stream, close it
            this.virtualAvailable = 0;
            close();
        }
        return numBytesRead;
    }
1255785
public synchronized int read() throws IOException
    {
        int b;
        if (_pos >=_avail)
            fill();
        if (_pos >=_avail)
            b=-1;
        else
            b=_buf[_pos++]&255;
        
        return b;
    }
825956
public int read(byte []buf, int offset, int length) throws IOException
  {
    if (_is == null)
      return -1;

    int len = _is.read(buf, offset, length);

    return len;
  }
977617
public int read()
    throws IOException
  {
    if (_peek >= 0) {
      int peek = _peek;
      _peek = -1;
      return peek;
    }

    InputStream is = _is;
    
    int ch1 = is.read();
    
    if (ch1 < 0x80) {
      return ch1;
    }
    else if ((ch1 & 0xe0) == 0xc0) {
      int ch2 = is.read();
      
      if (ch2 < 0) {
        return error("unexpected end of file in utf8 character");
      }
      else if ((ch2 & 0xc0) != 0x80) {
        return error("utf-8 character conversion error for '{0}' because second byte is invalid at "
                     + String.format("0x%02x 0x%02x", ch1, ch2));
      }
      
      return ((ch1 & 0x1f) << 6) + (ch2 & 0x3f);
    }
    else if ((ch1 & 0xf0) == 0xe0) {
      int ch2 = is.read();
      int ch3 = is.read();
      
      if (ch2 < 0)
        return error("unexpected end of file in utf8 character");
      else if ((ch2 & 0xc0) != 0x80) {
        return error("illegal utf8 encoding at "
                     + "\\x" + Integer.toHexString(ch1)
                     + "\\x" + Integer.toHexString(ch2)
                     + "\\x" + Integer.toHexString(ch3));
      }
      
      if (ch3 < 0)
        return error("unexpected end of file in utf8 character");
      else if ((ch3 & 0xc0) != 0x80)
        return error("illegal utf8 encoding at "
                     + "\\x" + Integer.toHexString(ch1)
                     + "\\x" + Integer.toHexString(ch2)
                     + "\\x" + Integer.toHexString(ch3));

      int ch = ((ch1 & 0x1f) << 12) + ((ch2 & 0x3f) << 6) + (ch3 & 0x3f);
    
      if (ch == 0xfeff) { // If byte-order-mark, read next character
        // server/1m00
        return read();
      }
      else
        return ch;
    }
    else if ((ch1 & 0xf0) == 0xf0) {
      int ch2 = is.read();
      int ch3 = is.read();
      int ch4 = is.read();

      if (ch2 < 0)
        return error("unexpected end of file in utf8 character");
      else if ((ch2 & 0xc0) != 0x80)
        return error("illegal utf8 encoding at 0x" +
                     Integer.toHexString(ch2));
      
      if (ch3 < 0)
        return error("unexpected end of file in utf8 character");
      else if ((ch3 & 0xc0) != 0x80)
        return error("illegal utf8 encoding at 0x" +
                                          Integer.toHexString(ch3));
      
      if (ch4 < 0)
        return error("unexpected end of file in utf8 character");
      else if ((ch4 & 0xc0) != 0x80)
        return error("illegal utf8 encoding at 0x"
                                          + Integer.toHexString(ch4));
      
      int ch = (((ch1 & 0xf) << 18) +
          ((ch2 & 0x3f) << 12) +
          ((ch3 & 0x3f) << 6) +
          ((ch4 & 0x3f)));

      _peek = 0xdc00 + (ch & 0x3ff);
      
      return 0xd800 + ((ch - 0x10000) / 0x400);
    }
    else {
      return error("illegal utf8 encoding at (0x"
                   + Integer.toHexString(ch1) + ")");
    }
  }
1050798
private boolean before() throws IOException {
        if (closed) {
            throw new IOException("Attempted read from closed stream.");
        }
        switch (length) {
            case EOF:
                return false;
            case UNKNOWN:
                length = readLength();
                pos = 0;
                if (length == EOF) {
                    HeaderList.parse(src); // result is ignored
                    return false;
                }
                return true;
            default:
                return true;
        }
    }
607277
@Override
	public int read() throws IOException {
		byte[] buf = new byte[1];

		int res = this.read(buf, 0, 1);

		if (res != -1) {
			return 0xFF & buf[0];
		}

		return res;
	}
40668
public int read()
    throws IOException
  {
    if (_byteHead == _byteTail) {
      return -1;
    }

    int b = _byteBuffer[_byteTail] & 0xff;
    _byteTail = (_byteTail + 1) % _byteBuffer.length;

    return b;
  }
898124
def read(self, length=-1):
        
        if length == -1 and self.at_eof():
            raise IOError(
                'Attempted to read from the buffer but already at the end')
        elif length > 0 and self.tell() + length > len(self):
            raise IOError('Attempted to read %d bytes from the buffer but '
                'only %d remain' % (length, len(self) - self.tell()))

        return StringIOProxy.read(self, length)
351135
private static int read(InputStream is) throws IOException {
        int b = is.read();
        if (b == -1) {
            throw new EOFException();
        }
        return b;
    }
333579
int read() throws IOException {
        int nextInt = -1;
        if (!hasSplit) {
            split();
        }
        if (beforeDoctype != null) {
            nextInt = beforeDoctype.read();
            if (nextInt == -1) {
                beforeDoctype = null;
            }
        }
        if (nextInt == -1 && decl != null) {
            nextInt = decl.read();
            if (nextInt == -1) {
                decl = null;
            }
        }
        if (nextInt == -1 && afterDoctype != null) {
            nextInt = afterDoctype.read();
            if (nextInt == -1) {
                afterDoctype = null;
            }
        }
        if (nextInt == -1) {
            nextInt = original.read();
        }
        return nextInt;
    }
699979
def read_from(io)
      nbytes = @limit - @position
      raise OverflowError, "buffer is full" if nbytes.zero?

      bytes_read = IO.try_convert(io).read_nonblock(nbytes, exception: false)
      return 0 if bytes_read == :wait_readable

      self << bytes_read
      bytes_read.length
    end
1055961
@Override
  public int read(byte[] b, int off, int len) throws IOException {
    if (b == null) {
      throw new NullPointerException();
    } else if (off < 0 || len < 0 || len > b.length - off) {
      throw new IndexOutOfBoundsException();
    } else if (len == 0) {
      return 0;
    }
    if (endOfInput && !bbuf.hasRemaining()) {
      return -1;
    }

    int totalRead = 0;
    while (len > 0 && !endOfInput) {
      if (bbuf.hasRemaining()) {
        int remaining = Math.min(len, bbuf.remaining());
        bbuf.get(b, off, remaining);
        totalRead += remaining;
        off += remaining;
        len -= remaining;
        if (len == 0) {
          return totalRead;
        }
      }
      advance();
    }
    if (endOfInput && !bbuf.hasRemaining() && totalRead == 0) {
      return -1;
    }
    return totalRead;
  }
886105
@Override
	public int read() throws IOException {
		// Read from the queue
		synchronized(file) {
			while(true) {
				long len=file.getLength();
				if(len>=1) {
					long pos=file.getFirstIndex();
					file.file.seek(pos+16);
					int b=file.file.read();
					if(b==-1) throw new EOFException("Unexpected EOF");
					addStats(1);
					long newFirstIndex=pos+1;
					while(newFirstIndex>=file.maxFifoLength) newFirstIndex-=file.maxFifoLength;
					file.setFirstIndex(newFirstIndex);
					file.setLength(len-1);
					file.notify();
					return b;
				}
				try {
					file.wait();
				} catch(InterruptedException err) {
					InterruptedIOException ioErr=new InterruptedIOException();
					ioErr.initCause(err);
					throw ioErr;
				}
			}
		}
	}
1342504
def read_eof(self, echo=None):
        

        d = b''
        while True:
            try:
                d += self.read(1, echo)
            except EOFError:
                return d
857395
@Override
  public int read(byte[] buffer, int offset, int length) throws IOException
  {
    int b = -1;

    if (_isPartDone)
      return -1;

    int i = 0;
    // Need the last peek or would miss the initial '\n'
    while (_peekOffset + 1 < _peekLength && length > 0) {
      buffer[offset + i++] = _peek[_peekOffset++];
      length--;
    }

    while (i < length && (b = read()) >= 0) {
      boolean hasCr = false;

      if (b == '\r') {
        hasCr = true;
        b = read();

        // XXX: Macintosh?
        if (b != '\n') {
          buffer[offset + i++] = (byte) '\r';
          _peek[0] = (byte) b;
          _peekOffset = 0;
          _peekLength = 1;
          continue;
        }
      }
      else if (b != '\n') {
        buffer[offset + i++] = (byte) b;
        continue;
      }

      int j;
      for (j = 0;
           j < _boundaryLength && (b = read()) >= 0 && _boundaryBuffer[j] == b;
           j++) {
      }

      if (j == _boundaryLength) {
        _isPartDone = true;
        if ((b = read()) == '-') {
          if ((b = read()) == '-') {
            _isDone = true;
            _isComplete = true;
          }
        }

        for (; b > 0 && b != '\r' && b != '\n'; b = read()) {
        }
        if (b == '\r' && (b = read()) != '\n') {
          _peek[0] = (byte) b;
          _peekOffset = 0;
          _peekLength = 1;
        }

        return i > 0 ? i : -1;
      }

      _peekLength = 0;
      if (hasCr && i + 1 < length) {
        buffer[offset + i++] = (byte) '\r';
        buffer[offset + i++] = (byte) '\n';
      }
      else if (hasCr) {
        buffer[offset + i++] = (byte) '\r';
        _peek[_peekLength++] = (byte) '\n';
      }
      else {
        buffer[offset + i++] = (byte) '\n';
      }

      int k = 0;
      while (k < j && i + 1 < length)
        buffer[offset + i++] = _boundaryBuffer[k++];

      while (k < j)
        _peek[_peekLength++] = _boundaryBuffer[k++];

      _peek[_peekLength++] = (byte) b;
      _peekOffset = 0;
    }

    if (i <= 0) {
      _isPartDone = true;
      if (b < 0)
        _isDone = true;
      return -1;
    }
    else {
      return i;
    }
  }
973419
protected int readByte(InputStream is) throws IOException
   {
      byte[] data = new byte[1];
      if (is.read(data) != data.length)
      {
         throw new EOFException();
      }

      return (MPPUtility.getByte(data, 0));
   }