OSDN Git Service

03a0c3e862e13a0b9ae7a55b4e522695e9a9ea13
[pf3gnuchains/gcc-fork.git] / libjava / java / io / InputStreamReader.java
1 /* Copyright (C) 1998, 1999, 2001  Free Software Foundation
2
3    This file is part of libgcj.
4
5 This software is copyrighted work licensed under the terms of the
6 Libgcj License.  Please consult the file "LIBGCJ_LICENSE" for
7 details.  */
8  
9 package java.io;
10 import gnu.gcj.convert.*;
11
12 /**
13  * @author Per Bothner <bothner@cygnus.com>
14  * @date April 22, 1998.  
15  */
16 /* Written using "Java Class Libraries", 2nd edition, plus online
17  * API docs for JDK 1.2 beta from http://www.javasoft.com.
18  * Status:  Believed complete and correct, but only supports 8859_1.
19  */
20
21 public class InputStreamReader extends Reader
22 {
23   BufferedInputStream in;
24
25   // Buffer of chars read from in and converted but not consumed.
26   char[] work;
27   // Next available character (in work buffer) to read.
28   int wpos;
29   // Last available character (in work buffer) to read.
30   int wcount;
31
32   BytesToUnicode converter;
33
34   public InputStreamReader(InputStream in)
35   {
36     this(in, BytesToUnicode.getDefaultDecoder());
37   }
38
39   public InputStreamReader(InputStream in, String enc)
40     throws UnsupportedEncodingException
41   {
42     this(in, BytesToUnicode.getDecoder(enc));
43   }
44
45   private InputStreamReader(InputStream in, BytesToUnicode decoder)
46   {
47     this.in = in instanceof BufferedInputStream
48               ? (BufferedInputStream) in
49               : new BufferedInputStream(in);
50     /* Don't need to call super(in) here as long as the lock gets set. */
51     this.lock = in;
52     converter = decoder;
53     converter.setInput(this.in.buf, 0, 0);
54   }
55
56   public void close() throws IOException
57   {
58     synchronized (lock)
59       {
60         if (in != null)
61           in.close();
62         in = null;
63         work = null;
64         wpos = wcount = 0;
65       }
66   }
67
68   public String getEncoding() { return converter.getName(); }
69
70   public boolean ready() throws IOException
71   {
72     synchronized (lock)
73       {
74         if (in == null)
75           throw new IOException("Stream closed");
76
77         if (wpos < wcount)
78           return true;
79         if (work == null)
80           {
81             work = new char[100];
82             wpos = 0;
83             wcount = 0;
84           }
85         for (;;)
86           {
87             if (in.available() <= 0)
88               return false;
89             in.mark(1);
90             int b = in.read();
91             if (b < 0)
92               return true;
93             in.reset();
94             converter.setInput(in.buf, in.pos, in.count);
95             wpos = 0;
96             wcount = converter.read(work, 0, work.length);
97             in.skip(converter.inpos - in.pos);
98             if (wcount > 0)
99               return true;
100           }
101       }
102   }
103
104   public int read(char buf[], int offset, int length) throws IOException
105   {
106     synchronized (lock)
107       {
108         if (in == null)
109           throw new IOException("Stream closed");
110
111         int wavail = wcount - wpos;
112         if (wavail > 0)
113           {
114             if (length > wavail)
115               length = wavail;
116             System.arraycopy(work, wpos, buf, offset, length);
117             wpos += length;
118             return length;
119           }
120         else
121           {
122             if (length == 0)
123               return 0;
124             for (;;)
125               {
126                 in.mark(1);
127                 int b = in.read();
128                 if (b < 0)
129                   return -1;
130                 in.reset();
131                 converter.setInput(in.buf, in.pos, in.count);
132                 int count = converter.read (buf, offset, length);
133                 in.skip(converter.inpos - in.pos);
134                 if (count > 0)
135                   return count;
136               }
137           }
138       }
139   }
140
141   public int read() throws IOException
142   {
143     synchronized (lock)
144       {
145         if (in == null)
146           throw new IOException("Stream closed");
147
148         int wavail = wcount - wpos;
149         if (wavail > 0)
150           return work[wpos++];
151         if (work == null)
152           {
153             work = new char[100];
154             wpos = 0;
155             wcount = 0;
156           }
157         else if (wavail == 0)
158           {
159             wpos = 0;
160             wcount = 0;
161           }
162         int count = read(work, wpos, work.length-wpos);
163         if (count <= 0)
164           return -1;
165         wcount = wpos + count;
166         return work[wpos++];
167       }
168   }
169 }