View Javadoc

1   /*
2    * Copyright (c) 2004-2007 Creative Sphere Limited.
3    * All rights reserved. This program and the accompanying materials
4    * are made available under the terms of the Eclipse Public License v1.0
5    * which accompanies this distribution, and is available at
6    * http://www.eclipse.org/legal/epl-v10.html
7    *
8    * Contributors:
9    *
10   *   Creative Sphere - initial API and implementation
11   *
12   */
13  package org.abstracthorizon.mercury.imap.util.section;
14  
15  import java.io.IOException;
16  import java.io.InputStream;
17  
18  /**
19   * Input stream that counts number of bytes and let only
20   * specified number of bytes to be read
21   *
22   * @author Daniel Sendula
23   */
24  public class MeasuredInputStream extends InputStream {
25  
26      /** Wrapped input stream */
27      protected InputStream is;
28  
29      /** Maximum len */
30      protected long len;
31  
32      /** Amount of read bytes */
33      protected long read = 0;
34  
35      /** Mark */
36      protected long mark = -1;
37  
38      /**
39       * Constructor
40       * @param is input stream
41       * @param len expected len
42       */
43      public MeasuredInputStream(InputStream is, long len) {
44          this.is = is;
45          this.len = len;
46      }
47  
48      /**
49       * Returns measured size
50       * @return measured size
51       */
52      public long size() {
53          return len;
54      }
55  
56      @Override
57      public int available() throws IOException {
58          int a = is.available();
59          if (read >= len) {
60              return 0;
61          } else if (a > read - len) {
62              return (int)(read - len);
63          } else {
64              return a;
65          }
66      }
67  
68      @Override
69      public void close() throws IOException {
70           is.close();
71      }
72  
73      @Override
74      public void mark(int readlimit) {
75          is.mark(readlimit);
76          mark = read;
77      }
78  
79      @Override
80      public boolean markSupported() {
81          return is.markSupported();
82      }
83  
84      @Override
85      public int read() throws IOException {
86          if (read >= this.len) {
87              return -1;
88          } else {
89              int r = is.read();
90              if (r >= 0) {
91                  read = read + 1;
92              }
93              return r;
94          }
95      }
96  
97      @Override
98      public int read(byte[] b) throws IOException {
99          return is.read(b, 0, b.length);
100     }
101 
102     @Override
103     public int read(byte[] b, int off, int len) throws IOException {
104         if (read >= this.len) {
105             return -1;
106         } else if (len >= read - this.len) {
107             len = (int)(read - this.len);
108         }
109         int l = is.read(b, off, len);
110         if (l >= 0) {
111             read = read + l;
112         }
113         return l;
114     }
115 
116     @Override
117     public void reset() throws IOException {
118         is.reset();
119         read = mark;
120     }
121 
122     @Override
123     public long skip(long n) throws IOException {
124         if (read >= len) {
125             return 0;
126         } else if (n > (read - len)) {
127             n = (read - len);
128         }
129         long l = is.skip(n);
130         read = read + l;
131         return l;
132     }
133 }
134