예제 #1
0
  private int bufferedRead(ByteList dst, int number) throws IOException, BadDescriptorException {

    int bytesRead = 0;

    //
    // Copy what is in the buffer, if there is some buffered data
    //
    bytesRead += copyBufferedBytes(dst, number);

    boolean done = false;
    //
    // Avoid double-copying for reads that are larger than the buffer size
    //
    while ((number - bytesRead) >= BUFSIZE) {
      //
      // limit each iteration to a max of BULK_READ_SIZE to avoid over-size allocations
      //
      final int bytesToRead = Math.min(BULK_READ_SIZE, number - bytesRead);
      final int n = descriptor.read(bytesToRead, dst);
      if (n == -1) {
        eof = true;
        done = true;
        break;
      } else if (n == 0) {
        done = true;
        break;
      }
      bytesRead += n;
    }

    //
    // Complete the request by filling the read buffer first
    //
    while (!done && bytesRead < number) {
      int read = refillBuffer();

      if (read == -1) {
        eof = true;
        break;
      } else if (read == 0) {
        break;
      }

      // append what we read into our buffer and allow the loop to continue
      final int len = Math.min(buffer.remaining(), number - bytesRead);
      dst.append(buffer, len);
      bytesRead += len;
    }

    if (bytesRead == 0 && number != 0) {
      if (eof) {
        throw newEOFException();
      }
    }

    return bytesRead;
  }
예제 #2
0
  public synchronized ByteList read(int number) throws IOException, BadDescriptorException {
    checkReadable();
    ensureReadNonBuffered();

    ByteList byteList = new ByteList(number);

    // TODO this should entry into error handling somewhere
    int bytesRead = descriptor.read(number, byteList);

    if (bytesRead == -1) {
      eof = true;
    }

    return byteList;
  }
예제 #3
0
  private int bufferedRead(ByteBuffer dst, boolean partial)
      throws IOException, BadDescriptorException {
    checkReadable();
    ensureRead();

    boolean done = false;
    int bytesRead = 0;

    //
    // Copy what is in the buffer, if there is some buffered data
    //
    bytesRead += copyBufferedBytes(dst);

    //
    // Avoid double-copying for reads that are larger than the buffer size, or
    // the destination is a direct buffer.
    //
    while ((bytesRead < 1 || !partial) && (dst.remaining() >= BUFSIZE || dst.isDirect())) {
      ByteBuffer tmpDst = dst;
      if (!dst.isDirect()) {
        //
        // We limit reads to BULK_READ_SIZED chunks to avoid NIO allocating
        // a huge temporary native buffer, when doing reads into a heap buffer
        // If the dst buffer is direct, then no need to limit.
        //
        int bytesToRead = Math.min(BULK_READ_SIZE, dst.remaining());
        if (bytesToRead < dst.remaining()) {
          tmpDst = dst.duplicate();
          tmpDst.limit(tmpDst.position() + bytesToRead);
        }
      }
      int n = descriptor.read(tmpDst);
      if (n == -1) {
        eof = true;
        done = true;
        break;
      } else if (n == 0) {
        done = true;
        break;
      } else {
        bytesRead += n;
      }
    }

    //
    // Complete the request by filling the read buffer first
    //
    while (!done && dst.hasRemaining() && (bytesRead < 1 || !partial)) {
      int read = refillBuffer();

      if (read == -1) {
        eof = true;
        done = true;
        break;
      } else if (read == 0) {
        done = true;
        break;
      } else {
        // append what we read into our buffer and allow the loop to continue
        bytesRead += copyBufferedBytes(dst);
      }
    }

    if (eof && bytesRead == 0 && dst.remaining() != 0) {
      throw newEOFException();
    }

    return bytesRead;
  }