1   /*
2    * %W% %E%
3    *
4    * Copyright (c) 2006, Oracle and/or its affiliates. All rights reserved.
5    * ORACLE PROPRIETARY/CONFIDENTIAL. Use is subject to license terms.
6    */
7   
8   package java.util.zip;
9   
10  import java.io.FilterInputStream;
11  import java.io.InputStream;
12  import java.io.IOException;
13  
14  /**
15   * An input stream that also maintains a checksum of the data being read.
16   * The checksum can then be used to verify the integrity of the input data.
17   *
18   * @see     Checksum
19   * @version     %I%, %G%
20   * @author  David Connelly
21   */
22  public
23  class CheckedInputStream extends FilterInputStream {
24      private Checksum cksum;
25  
26      /**
27       * Creates an input stream using the specified Checksum.
28       * @param in the input stream
29       * @param cksum the Checksum
30       */
31      public CheckedInputStream(InputStream in, Checksum cksum) {
32      super(in);
33      this.cksum = cksum;
34      }
35  
36      /**
37       * Reads a byte. Will block if no input is available.
38       * @return the byte read, or -1 if the end of the stream is reached.
39       * @exception IOException if an I/O error has occurred
40       */
41      public int read() throws IOException {
42      int b = in.read();
43      if (b != -1) {
44          cksum.update(b);
45      }
46      return b;
47      }
48  
49      /**
50       * Reads into an array of bytes. If <code>len</code> is not zero, the method
51       * blocks until some input is available; otherwise, no
52       * bytes are read and <code>0</code> is returned.
53       * @param buf the buffer into which the data is read
54       * @param off the start offset in the destination array <code>b</code>
55       * @param len the maximum number of bytes read
56       * @return    the actual number of bytes read, or -1 if the end
57       *        of the stream is reached.
58       * @exception  NullPointerException If <code>buf</code> is <code>null</code>.
59       * @exception  IndexOutOfBoundsException If <code>off</code> is negative, 
60       * <code>len</code> is negative, or <code>len</code> is greater than 
61       * <code>buf.length - off</code>
62       * @exception IOException if an I/O error has occurred
63       */
64      public int read(byte[] buf, int off, int len) throws IOException {
65      len = in.read(buf, off, len);
66      if (len != -1) {
67          cksum.update(buf, off, len);
68      }
69      return len;
70      }
71  
72      /**
73       * Skips specified number of bytes of input.
74       * @param n the number of bytes to skip
75       * @return the actual number of bytes skipped
76       * @exception IOException if an I/O error has occurred
77       */
78      public long skip(long n) throws IOException {
79      byte[] buf = new byte[512];
80      long total = 0;
81      while (total < n) {
82          long len = n - total;
83          len = read(buf, 0, len < buf.length ? (int)len : buf.length);
84          if (len == -1) {
85          return total;
86          }
87          total += len;
88      }
89      return total;
90      }
91  
92      /**
93       * Returns the Checksum for this input stream.
94       * @return the Checksum value
95       */
96      public Checksum getChecksum() {
97      return cksum;
98      }
99  }
100