Source Code Cross Referenced for Channels.java in  » 6.0-JDK-Core » io-nio » java » nio » channels » Java Source Code / Java DocumentationJava Source Code and Java Documentation

Home
Java Source Code / Java Documentation
1.6.0 JDK Core
2.6.0 JDK Modules
3.6.0 JDK Modules com.sun
4.6.0 JDK Modules com.sun.java
5.6.0 JDK Modules sun
6.6.0 JDK Platform
7.Ajax
8.Apache Harmony Java SE
9.Aspect oriented
10.Authentication Authorization
11.Blogger System
12.Build
13.Byte Code
14.Cache
15.Chart
16.Chat
17.Code Analyzer
18.Collaboration
19.Content Management System
20.Database Client
21.Database DBMS
22.Database JDBC Connection Pool
23.Database ORM
24.Development
25.EJB Server
26.ERP CRM Financial
27.ESB
28.Forum
29.Game
30.GIS
31.Graphic 3D
32.Graphic Library
33.Groupware
34.HTML Parser
35.IDE
36.IDE Eclipse
37.IDE Netbeans
38.Installer
39.Internationalization Localization
40.Inversion of Control
41.Issue Tracking
42.J2EE
43.J2ME
44.JBoss
45.JMS
46.JMX
47.Library
48.Mail Clients
49.Music
50.Net
51.Parser
52.PDF
53.Portal
54.Profiler
55.Project Management
56.Report
57.RSS RDF
58.Rule Engine
59.Science
60.Scripting
61.Search Engine
62.Security
63.Sevlet Container
64.Source Control
65.Swing Library
66.Template Engine
67.Test Coverage
68.Testing
69.UML
70.Web Crawler
71.Web Framework
72.Web Mail
73.Web Server
74.Web Services
75.Web Services apache cxf 2.2.6
76.Web Services AXIS2
77.Wiki Engine
78.Workflow Engines
79.XML
80.XML UI
Java Source Code / Java Documentation » 6.0 JDK Core » io nio » java.nio.channels 
Source Cross Referenced  Class Diagram Java Document (Java Doc) 


001        /*
002         * Copyright 2000-2005 Sun Microsystems, Inc.  All Rights Reserved.
003         * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
004         *
005         * This code is free software; you can redistribute it and/or modify it
006         * under the terms of the GNU General Public License version 2 only, as
007         * published by the Free Software Foundation.  Sun designates this
008         * particular file as subject to the "Classpath" exception as provided
009         * by Sun in the LICENSE file that accompanied this code.
010         *
011         * This code is distributed in the hope that it will be useful, but WITHOUT
012         * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
013         * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
014         * version 2 for more details (a copy is included in the LICENSE file that
015         * accompanied this code).
016         *
017         * You should have received a copy of the GNU General Public License version
018         * 2 along with this work; if not, write to the Free Software Foundation,
019         * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
020         *
021         * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
022         * CA 95054 USA or visit www.sun.com if you need additional information or
023         * have any questions.
024         */
025
026        package java.nio.channels;
027
028        import java.io.FileInputStream;
029        import java.io.FileOutputStream;
030        import java.io.InputStream;
031        import java.io.OutputStream;
032        import java.io.Reader;
033        import java.io.Writer;
034        import java.io.IOException;
035        import java.nio.ByteBuffer;
036        import java.nio.CharBuffer;
037        import java.nio.BufferOverflowException;
038        import java.nio.BufferUnderflowException;
039        import java.nio.charset.Charset;
040        import java.nio.charset.CharsetDecoder;
041        import java.nio.charset.CharsetEncoder;
042        import java.nio.charset.CoderResult;
043        import java.nio.charset.UnsupportedCharsetException;
044        import java.nio.channels.spi.AbstractInterruptibleChannel;
045        import sun.nio.ch.ChannelInputStream;
046        import sun.nio.cs.StreamDecoder;
047        import sun.nio.cs.StreamEncoder;
048
049        /**
050         * Utility methods for channels and streams.
051         *
052         * <p> This class defines static methods that support the interoperation of the
053         * stream classes of the <tt>{@link java.io}</tt> package with the channel
054         * classes of this package.  </p>
055         *
056         *
057         * @author Mark Reinhold
058         * @author Mike McCloskey
059         * @author JSR-51 Expert Group
060         * @version 1.31, 07/05/05
061         * @since 1.4
062         */
063
064        public final class Channels {
065
066            private Channels() {
067            } // No instantiation
068
069            private static int write(WritableByteChannel ch, ByteBuffer bb)
070                    throws IOException {
071                if (ch instanceof  SelectableChannel) {
072                    SelectableChannel sc = (SelectableChannel) ch;
073                    synchronized (sc.blockingLock()) {
074                        if (!sc.isBlocking())
075                            throw new IllegalBlockingModeException();
076                        return ch.write(bb);
077                    }
078                } else {
079                    return ch.write(bb);
080                }
081            }
082
083            // -- Byte streams from channels --
084
085            /**
086             * Constructs a stream that reads bytes from the given channel.
087             *
088             * <p> The <tt>read</tt> methods of the resulting stream will throw an
089             * {@link IllegalBlockingModeException} if invoked while the underlying
090             * channel is in non-blocking mode.  The stream will not be buffered, and
091             * it will not support the {@link InputStream#mark mark} or {@link
092             * InputStream#reset reset} methods.  The stream will be safe for access by
093             * multiple concurrent threads.  Closing the stream will in turn cause the
094             * channel to be closed.  </p>
095             *
096             * @param  ch
097             *         The channel from which bytes will be read
098             *
099             * @return  A new input stream
100             */
101            public static InputStream newInputStream(ReadableByteChannel ch) {
102                return new sun.nio.ch.ChannelInputStream(ch);
103            }
104
105            /**
106             * Constructs a stream that writes bytes to the given channel.
107             *
108             * <p> The <tt>write</tt> methods of the resulting stream will throw an
109             * {@link IllegalBlockingModeException} if invoked while the underlying
110             * channel is in non-blocking mode.  The stream will not be buffered.  The
111             * stream will be safe for access by multiple concurrent threads.  Closing
112             * the stream will in turn cause the channel to be closed.  </p>
113             *
114             * @param  ch
115             *         The channel to which bytes will be written
116             *
117             * @return  A new output stream
118             */
119            public static OutputStream newOutputStream(
120                    final WritableByteChannel ch) {
121                return new OutputStream() {
122
123                    private ByteBuffer bb = null;
124                    private byte[] bs = null; // Invoker's previous array
125                    private byte[] b1 = null;
126
127                    public synchronized void write(int b) throws IOException {
128                        if (b1 == null)
129                            b1 = new byte[1];
130                        b1[0] = (byte) b;
131                        this .write(b1);
132                    }
133
134                    public synchronized void write(byte[] bs, int off, int len)
135                            throws IOException {
136                        if ((off < 0) || (off > bs.length) || (len < 0)
137                                || ((off + len) > bs.length)
138                                || ((off + len) < 0)) {
139                            throw new IndexOutOfBoundsException();
140                        } else if (len == 0) {
141                            return;
142                        }
143                        ByteBuffer bb = ((this .bs == bs) ? this .bb : ByteBuffer
144                                .wrap(bs));
145                        bb.limit(Math.min(off + len, bb.capacity()));
146                        bb.position(off);
147                        this .bb = bb;
148                        this .bs = bs;
149                        Channels.write(ch, bb);
150                    }
151
152                    public void close() throws IOException {
153                        ch.close();
154                    }
155
156                };
157            }
158
159            // -- Channels from streams --
160
161            /**
162             * Constructs a channel that reads bytes from the given stream.
163             *
164             * <p> The resulting channel will not be buffered; it will simply redirect
165             * its I/O operations to the given stream.  Closing the channel will in
166             * turn cause the stream to be closed.  </p>
167             *
168             * @param  in
169             *         The stream from which bytes are to be read
170             *
171             * @return  A new readable byte channel
172             */
173            public static ReadableByteChannel newChannel(final InputStream in) {
174                if (in == null) {
175                    throw new NullPointerException();
176                }
177
178                if (in instanceof  FileInputStream
179                        && FileInputStream.class.equals(in.getClass())) {
180                    return ((FileInputStream) in).getChannel();
181                }
182
183                return new ReadableByteChannelImpl(in);
184            }
185
186            private static class ReadableByteChannelImpl extends
187                    AbstractInterruptibleChannel // Not really interruptible
188                    implements  ReadableByteChannel {
189                InputStream in;
190                private static final int TRANSFER_SIZE = 8192;
191                private byte buf[] = new byte[0];
192                private boolean open = true;
193                private Object readLock = new Object();
194
195                ReadableByteChannelImpl(InputStream in) {
196                    this .in = in;
197                }
198
199                public int read(ByteBuffer dst) throws IOException {
200                    int len = dst.remaining();
201                    int totalRead = 0;
202                    int bytesRead = 0;
203                    synchronized (readLock) {
204                        while (totalRead < len) {
205                            int bytesToRead = Math.min((len - totalRead),
206                                    TRANSFER_SIZE);
207                            if (buf.length < bytesToRead)
208                                buf = new byte[bytesToRead];
209                            if ((totalRead > 0) && !(in.available() > 0))
210                                break; // block at most once
211                            try {
212                                begin();
213                                bytesRead = in.read(buf, 0, bytesToRead);
214                            } finally {
215                                end(bytesRead > 0);
216                            }
217                            if (bytesRead < 0)
218                                break;
219                            else
220                                totalRead += bytesRead;
221                            dst.put(buf, 0, bytesRead);
222                        }
223                        if ((bytesRead < 0) && (totalRead == 0))
224                            return -1;
225
226                        return totalRead;
227                    }
228                }
229
230                protected void implCloseChannel() throws IOException {
231                    in.close();
232                    open = false;
233                }
234            }
235
236            /**
237             * Constructs a channel that writes bytes to the given stream.
238             *
239             * <p> The resulting channel will not be buffered; it will simply redirect
240             * its I/O operations to the given stream.  Closing the channel will in
241             * turn cause the stream to be closed.  </p>
242             *
243             * @param  out
244             *         The stream to which bytes are to be written
245             *
246             * @return  A new writable byte channel
247             */
248            public static WritableByteChannel newChannel(final OutputStream out) {
249                if (out == null) {
250                    throw new NullPointerException();
251                }
252
253                if (out instanceof  FileOutputStream
254                        && FileOutputStream.class.equals(out.getClass())) {
255                    return ((FileOutputStream) out).getChannel();
256                }
257
258                return new WritableByteChannelImpl(out);
259            }
260
261            private static class WritableByteChannelImpl extends
262                    AbstractInterruptibleChannel // Not really interruptible
263                    implements  WritableByteChannel {
264                OutputStream out;
265                private static final int TRANSFER_SIZE = 8192;
266                private byte buf[] = new byte[0];
267                private boolean open = true;
268                private Object writeLock = new Object();
269
270                WritableByteChannelImpl(OutputStream out) {
271                    this .out = out;
272                }
273
274                public int write(ByteBuffer src) throws IOException {
275                    int len = src.remaining();
276                    int totalWritten = 0;
277                    synchronized (writeLock) {
278                        while (totalWritten < len) {
279                            int bytesToWrite = Math.min((len - totalWritten),
280                                    TRANSFER_SIZE);
281                            if (buf.length < bytesToWrite)
282                                buf = new byte[bytesToWrite];
283                            src.get(buf, 0, bytesToWrite);
284                            try {
285                                begin();
286                                out.write(buf, 0, bytesToWrite);
287                            } finally {
288                                end(bytesToWrite > 0);
289                            }
290                            totalWritten += bytesToWrite;
291                        }
292                        return totalWritten;
293                    }
294                }
295
296                protected void implCloseChannel() throws IOException {
297                    out.close();
298                    open = false;
299                }
300            }
301
302            // -- Character streams from channels --
303
304            /**
305             * Constructs a reader that decodes bytes from the given channel using the
306             * given decoder.
307             *
308             * <p> The resulting stream will contain an internal input buffer of at
309             * least <tt>minBufferCap</tt> bytes.  The stream's <tt>read</tt> methods
310             * will, as needed, fill the buffer by reading bytes from the underlying
311             * channel; if the channel is in non-blocking mode when bytes are to be
312             * read then an {@link IllegalBlockingModeException} will be thrown.  The
313             * resulting stream will not otherwise be buffered, and it will not support
314             * the {@link Reader#mark mark} or {@link Reader#reset reset} methods.
315             * Closing the stream will in turn cause the channel to be closed.  </p>
316             *
317             * @param  ch
318             *         The channel from which bytes will be read
319             *
320             * @param  dec
321             *         The charset decoder to be used
322             *
323             * @param  minBufferCap
324             *         The minimum capacity of the internal byte buffer,
325             *         or <tt>-1</tt> if an implementation-dependent
326             *         default capacity is to be used
327             *
328             * @return  A new reader
329             */
330            public static Reader newReader(ReadableByteChannel ch,
331                    CharsetDecoder dec, int minBufferCap) {
332                dec.reset();
333                return StreamDecoder.forDecoder(ch, dec, minBufferCap);
334            }
335
336            /**
337             * Constructs a reader that decodes bytes from the given channel according
338             * to the named charset.
339             *
340             * <p> An invocation of this method of the form
341             *
342             * <blockquote><pre>
343             * Channels.newReader(ch, csname)</pre></blockquote>
344             *
345             * behaves in exactly the same way as the expression
346             *
347             * <blockquote><pre>
348             * Channels.newReader(ch,
349             *                    Charset.forName(csName)
350             *                        .newDecoder(),
351             *                    -1);</pre></blockquote>
352             *
353             * @param  ch
354             *         The channel from which bytes will be read
355             *
356             * @param  csName
357             *         The name of the charset to be used
358             *
359             * @return  A new reader
360             *
361             * @throws  UnsupportedCharsetException
362             *          If no support for the named charset is available
363             *          in this instance of the Java virtual machine
364             */
365            public static Reader newReader(ReadableByteChannel ch, String csName) {
366                return newReader(ch, Charset.forName(csName).newDecoder(), -1);
367            }
368
369            /**
370             * Constructs a writer that encodes characters using the given encoder and
371             * writes the resulting bytes to the given channel.
372             *
373             * <p> The resulting stream will contain an internal output buffer of at
374             * least <tt>minBufferCap</tt> bytes.  The stream's <tt>write</tt> methods
375             * will, as needed, flush the buffer by writing bytes to the underlying
376             * channel; if the channel is in non-blocking mode when bytes are to be
377             * written then an {@link IllegalBlockingModeException} will be thrown.
378             * The resulting stream will not otherwise be buffered.  Closing the stream
379             * will in turn cause the channel to be closed.  </p>
380             *
381             * @param  ch
382             *         The channel to which bytes will be written
383             *
384             * @param  enc
385             *         The charset encoder to be used
386             *
387             * @param  minBufferCap
388             *         The minimum capacity of the internal byte buffer,
389             *         or <tt>-1</tt> if an implementation-dependent
390             *         default capacity is to be used
391             *
392             * @return  A new writer
393             */
394            public static Writer newWriter(final WritableByteChannel ch,
395                    final CharsetEncoder enc, final int minBufferCap) {
396                enc.reset();
397                return StreamEncoder.forEncoder(ch, enc, minBufferCap);
398            }
399
400            /**
401             * Constructs a writer that encodes characters according to the named
402             * charset and writes the resulting bytes to the given channel.
403             *
404             * <p> An invocation of this method of the form
405             *
406             * <blockquote><pre>
407             * Channels.newWriter(ch, csname)</pre></blockquote>
408             *
409             * behaves in exactly the same way as the expression
410             *
411             * <blockquote><pre>
412             * Channels.newWriter(ch,
413             *                    Charset.forName(csName)
414             *                        .newEncoder(),
415             *                    -1);</pre></blockquote>
416             *
417             * @param  ch
418             *         The channel to which bytes will be written
419             *
420             * @param  csName
421             *         The name of the charset to be used
422             *
423             * @return  A new writer
424             *
425             * @throws  UnsupportedCharsetException
426             *          If no support for the named charset is available
427             *          in this instance of the Java virtual machine
428             */
429            public static Writer newWriter(WritableByteChannel ch, String csName) {
430                return newWriter(ch, Charset.forName(csName).newEncoder(), -1);
431            }
432
433        }
www.java2java.com | Contact Us
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.