1157 lines · 50.0 KB · Java
RawDownload
/* * Copyright (c) 2000, 2011, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License version 2 only, as * published by the Free Software Foundation.  Oracle designates this * particular file as subject to the "Classpath" exception as provided * by Oracle in the LICENSE file that accompanied this code. * * This code is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License * version 2 for more details (a copy is included in the LICENSE file that * accompanied this code). * * You should have received a copy of the GNU General Public License version * 2 along with this work; if not, write to the Free Software Foundation, * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. * * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA * or visit www.oracle.com if you need additional information or have any * questions. */ package java.nio.channels; import java.io.*;import java.nio.ByteBuffer;import java.nio.MappedByteBuffer;import java.nio.channels.spi.AbstractInterruptibleChannel;import java.nio.file.*;import java.nio.file.attribute.FileAttribute;import java.nio.file.spi.*;import java.util.Set;import java.util.HashSet;import java.util.Collections; /** * A channel for reading, writing, mapping, and manipulating a file. * * <p> A file channel is a {@link SeekableByteChannel} that is connected to * a file. It has a current <i>position</i> within its file which can * be both {@link #position() <i>queried</i>} and {@link #position(long) * <i>modified</i>}.  The file itself contains a variable-length sequence * of bytes that can be read and written and whose current {@link #size * <i>size</i>} can be queried.  The size of the file increases * when bytes are written beyond its current size; the size of the file * decreases when it is {@link #truncate </code><i>truncated</i><code>}.  The * file may also have some associated <i>metadata</i> such as access * permissions, content type, and last-modification time; this class does not * define methods for metadata access. * * <p> In addition to the familiar read, write, and close operations of byte * channels, this class defines the following file-specific operations: </p> * * <ul> * *   <li><p> Bytes may be {@link #read(ByteBuffer, long) read} or *   {@link #write(ByteBuffer, long) <i>written</i>} at an absolute *   position in a file in a way that does not affect the channel's current *   position.  </p></li> * *   <li><p> A region of a file may be {@link #map <i>mapped</i>} *   directly into memory; for large files this is often much more efficient *   than invoking the usual <tt>read</tt> or <tt>write</tt> methods. *   </p></li> * *   <li><p> Updates made to a file may be {@link #force <i>forced *   out</i>} to the underlying storage device, ensuring that data are not *   lost in the event of a system crash.  </p></li> * *   <li><p> Bytes can be transferred from a file {@link #transferTo <i>to *   some other channel</i>}, and {@link #transferFrom <i>vice *   versa</i>}, in a way that can be optimized by many operating systems *   into a very fast transfer directly to or from the filesystem cache. *   </p></li> * *   <li><p> A region of a file may be {@link FileLock <i>locked</i>} *   against access by other programs.  </p></li> * * </ul> * * <p> File channels are safe for use by multiple concurrent threads.  The * {@link Channel#close close} method may be invoked at any time, as specified * by the {@link Channel} interface.  Only one operation that involves the * channel's position or can change its file's size may be in progress at any * given time; attempts to initiate a second such operation while the first is * still in progress will block until the first operation completes.  Other * operations, in particular those that take an explicit position, may proceed * concurrently; whether they in fact do so is dependent upon the underlying * implementation and is therefore unspecified. * * <p> The view of a file provided by an instance of this class is guaranteed * to be consistent with other views of the same file provided by other * instances in the same program.  The view provided by an instance of this * class may or may not, however, be consistent with the views seen by other * concurrently-running programs due to caching performed by the underlying * operating system and delays induced by network-filesystem protocols.  This * is true regardless of the language in which these other programs are * written, and whether they are running on the same machine or on some other * machine.  The exact nature of any such inconsistencies are system-dependent * and are therefore unspecified. * * <p> A file channel is created by invoking one of the {@link #open open} * methods defined by this class. A file channel can also be obtained from an * existing {@link java.io.FileInputStream#getChannel FileInputStream}, {@link * java.io.FileOutputStream#getChannel FileOutputStream}, or {@link * java.io.RandomAccessFile#getChannel RandomAccessFile} object by invoking * that object's <tt>getChannel</tt> method, which returns a file channel that * is connected to the same underlying file. Where the file channel is obtained * from an existing stream or random access file then the state of the file * channel is intimately connected to that of the object whose <tt>getChannel</tt> * method returned the channel.  Changing the channel's position, whether * explicitly or by reading or writing bytes, will change the file position of * the originating object, and vice versa. Changing the file's length via the * file channel will change the length seen via the originating object, and vice * versa.  Changing the file's content by writing bytes will change the content * seen by the originating object, and vice versa. * * <a name="open-mode"></a> <p> At various points this class specifies that an * instance that is "open for reading," "open for writing," or "open for * reading and writing" is required.  A channel obtained via the {@link * java.io.FileInputStream#getChannel getChannel} method of a {@link * java.io.FileInputStream} instance will be open for reading.  A channel * obtained via the {@link java.io.FileOutputStream#getChannel getChannel} * method of a {@link java.io.FileOutputStream} instance will be open for * writing.  Finally, a channel obtained via the {@link * java.io.RandomAccessFile#getChannel getChannel} method of a {@link * java.io.RandomAccessFile} instance will be open for reading if the instance * was created with mode <tt>"r"</tt> and will be open for reading and writing * if the instance was created with mode <tt>"rw"</tt>. * * <a name="append-mode"></a><p> A file channel that is open for writing may be in * <i>append mode</i>, for example if it was obtained from a file-output stream * that was created by invoking the {@link * java.io.FileOutputStream#FileOutputStream(java.io.File,boolean) * FileOutputStream(File,boolean)} constructor and passing <tt>true</tt> for * the second parameter.  In this mode each invocation of a relative write * operation first advances the position to the end of the file and then writes * the requested data.  Whether the advancement of the position and the writing * of the data are done in a single atomic operation is system-dependent and * therefore unspecified. * * @see java.io.FileInputStream#getChannel() * @see java.io.FileOutputStream#getChannel() * @see java.io.RandomAccessFile#getChannel() * * @author Mark Reinhold * @author Mike McCloskey * @author JSR-51 Expert Group * @since 1.4 */ public abstract class FileChannel    extends AbstractInterruptibleChannel    implements SeekableByteChannel, GatheringByteChannel, ScatteringByteChannel{    /**     * Initializes a new instance of this class.     */    protected FileChannel() { }     /**     * Opens or creates a file, returning a file channel to access the file.     *     * <p> The {@code options} parameter determines how the file is opened.     * The {@link StandardOpenOption#READ READ} and {@link StandardOpenOption#WRITE     * WRITE} options determine if the file should be opened for reading and/or     * writing. If neither option (or the {@link StandardOpenOption#APPEND APPEND}     * option) is contained in the array then the file is opened for reading.     * By default reading or writing commences at the beginning of the file.     *     * <p> In the addition to {@code READ} and {@code WRITE}, the following     * options may be present:     *     * <table border=1 cellpadding=5 summary="">     * <tr> <th>Option</th> <th>Description</th> </tr>     * <tr>     *   <td> {@link StandardOpenOption#APPEND APPEND} </td>     *   <td> If this option is present then the file is opened for writing and     *     each invocation of the channel's {@code write} method first advances     *     the position to the end of the file and then writes the requested     *     data. Whether the advancement of the position and the writing of the     *     data are done in a single atomic operation is system-dependent and     *     therefore unspecified. This option may not be used in conjunction     *     with the {@code READ} or {@code TRUNCATE_EXISTING} options. </td>     * </tr>     * <tr>     *   <td> {@link StandardOpenOption#TRUNCATE_EXISTING TRUNCATE_EXISTING} </td>     *   <td> If this option is present then the existing file is truncated to     *   a size of 0 bytes. This option is ignored when the file is opened only     *   for reading. </td>     * </tr>     * <tr>     *   <td> {@link StandardOpenOption#CREATE_NEW CREATE_NEW} </td>     *   <td> If this option is present then a new file is created, failing if     *   the file already exists. When creating a file the check for the     *   existence of the file and the creation of the file if it does not exist     *   is atomic with respect to other file system operations. This option is     *   ignored when the file is opened only for reading. </td>     * </tr>     * <tr>     *   <td > {@link StandardOpenOption#CREATE CREATE} </td>     *   <td> If this option is present then an existing file is opened if it     *   exists, otherwise a new file is created. When creating a file the check     *   for the existence of the file and the creation of the file if it does     *   not exist is atomic with respect to other file system operations. This     *   option is ignored if the {@code CREATE_NEW} option is also present or     *   the file is opened only for reading. </td>     * </tr>     * <tr>     *   <td > {@link StandardOpenOption#DELETE_ON_CLOSE DELETE_ON_CLOSE} </td>     *   <td> When this option is present then the implementation makes a     *   <em>best effort</em> attempt to delete the file when closed by the     *   the {@link #close close} method. If the {@code close} method is not     *   invoked then a <em>best effort</em> attempt is made to delete the file     *   when the Java virtual machine terminates. </td>     * </tr>     * <tr>     *   <td>{@link StandardOpenOption#SPARSE SPARSE} </td>     *   <td> When creating a new file this option is a <em>hint</em> that the     *   new file will be sparse. This option is ignored when not creating     *   a new file. </td>     * </tr>     * <tr>     *   <td> {@link StandardOpenOption#SYNC SYNC} </td>     *   <td> Requires that every update to the file's content or metadata be     *   written synchronously to the underlying storage device. (see <a     *   href="../file/package-summary.html#integrity"> Synchronized I/O file     *   integrity</a>). </td>     * <tr>     * <tr>     *   <td> {@link StandardOpenOption#DSYNC DSYNC} </td>     *   <td> Requires that every update to the file's content be written     *   synchronously to the underlying storage device. (see <a     *   href="../file/package-summary.html#integrity"> Synchronized I/O file     *   integrity</a>). </td>     * </tr>     * </table>     *     * <p> An implementation may also support additional options.     *     * <p> The {@code attrs} parameter is an optional array of file {@link     * FileAttribute file-attributes} to set atomically when creating the file.     *     * <p> The new channel is created by invoking the {@link     * FileSystemProvider#newFileChannel newFileChannel} method on the     * provider that created the {@code Path}.     *     * @param   path     *          The path of the file to open or create     * @param   options     *          Options specifying how the file is opened     * @param   attrs     *          An optional list of file attributes to set atomically when     *          creating the file     *     * @return  A new file channel     *     * @throws  IllegalArgumentException     *          If the set contains an invalid combination of options     * @throws  UnsupportedOperationException     *          If the {@code path} is associated with a provider that does not     *          support creating file channels, or an unsupported open option is     *          specified, or the array contains an attribute that cannot be set     *          atomically when creating the file     * @throws  IOException     *          If an I/O error occurs     * @throws  SecurityException     *          If a security manager is installed and it denies an     *          unspecified permission required by the implementation.     *          In the case of the default provider, the {@link     *          SecurityManager#checkRead(String)} method is invoked to check     *          read access if the file is opened for reading. The {@link     *          SecurityManager#checkWrite(String)} method is invoked to check     *          write access if the file is opened for writing     *     * @since   1.7     */    public static FileChannel open(Path path,                                   Set<? extends OpenOption> options,                                   FileAttribute<?>... attrs)        throws IOException    {        FileSystemProvider provider = path.getFileSystem().provider();        return provider.newFileChannel(path, options, attrs);    }     private static final FileAttribute<?>[] NO_ATTRIBUTES = new FileAttribute[0];     /**     * Opens or creates a file, returning a file channel to access the file.     *     * <p> An invocation of this method behaves in exactly the same way as the     * invocation     * <pre>     *     fc.{@link #open(Path,Set,FileAttribute[]) open}(file, opts, new FileAttribute&lt;?&gt;[0]);     * </pre>     * where {@code opts} is a set of the options specified in the {@code     * options} array.     *     * @param   path     *          The path of the file to open or create     * @param   options     *          Options specifying how the file is opened     *     * @return  A new file channel     *     * @throws  IllegalArgumentException     *          If the set contains an invalid combination of options     * @throws  UnsupportedOperationException     *          If the {@code path} is associated with a provider that does not     *          support creating file channels, or an unsupported open option is     *          specified     * @throws  IOException     *          If an I/O error occurs     * @throws  SecurityException     *          If a security manager is installed and it denies an     *          unspecified permission required by the implementation.     *          In the case of the default provider, the {@link     *          SecurityManager#checkRead(String)} method is invoked to check     *          read access if the file is opened for reading. The {@link     *          SecurityManager#checkWrite(String)} method is invoked to check     *          write access if the file is opened for writing     *     * @since   1.7     */    public static FileChannel open(Path path, OpenOption... options)        throws IOException    {        Set<OpenOption> set = new HashSet<OpenOption>(options.length);        Collections.addAll(set, options);        return open(path, set, NO_ATTRIBUTES);    }     // -- Channel operations --     /**     * Reads a sequence of bytes from this channel into the given buffer.     *     * <p> Bytes are read starting at this channel's current file position, and     * then the file position is updated with the number of bytes actually     * read.  Otherwise this method behaves exactly as specified in the {@link     * ReadableByteChannel} interface. </p>     */    public abstract int read(ByteBuffer dst) throws IOException;     /**     * Reads a sequence of bytes from this channel into a subsequence of the     * given buffers.     *     * <p> Bytes are read starting at this channel's current file position, and     * then the file position is updated with the number of bytes actually     * read.  Otherwise this method behaves exactly as specified in the {@link     * ScatteringByteChannel} interface.  </p>     */    public abstract long read(ByteBuffer[] dsts, int offset, int length)        throws IOException;     /**     * Reads a sequence of bytes from this channel into the given buffers.     *     * <p> Bytes are read starting at this channel's current file position, and     * then the file position is updated with the number of bytes actually     * read.  Otherwise this method behaves exactly as specified in the {@link     * ScatteringByteChannel} interface.  </p>     */    public final long read(ByteBuffer[] dsts) throws IOException {        return read(dsts, 0, dsts.length);    }     /**     * Writes a sequence of bytes to this channel from the given buffer.     *     * <p> Bytes are written starting at this channel's current file position     * unless the channel is in append mode, in which case the position is     * first advanced to the end of the file.  The file is grown, if necessary,     * to accommodate the written bytes, and then the file position is updated     * with the number of bytes actually written.  Otherwise this method     * behaves exactly as specified by the {@link WritableByteChannel}     * interface. </p>     */    public abstract int write(ByteBuffer src) throws IOException;     /**     * Writes a sequence of bytes to this channel from a subsequence of the     * given buffers.     *     * <p> Bytes are written starting at this channel's current file position     * unless the channel is in append mode, in which case the position is     * first advanced to the end of the file.  The file is grown, if necessary,     * to accommodate the written bytes, and then the file position is updated     * with the number of bytes actually written.  Otherwise this method     * behaves exactly as specified in the {@link GatheringByteChannel}     * interface.  </p>     */    public abstract long write(ByteBuffer[] srcs, int offset, int length)        throws IOException;     /**     * Writes a sequence of bytes to this channel from the given buffers.     *     * <p> Bytes are written starting at this channel's current file position     * unless the channel is in append mode, in which case the position is     * first advanced to the end of the file.  The file is grown, if necessary,     * to accommodate the written bytes, and then the file position is updated     * with the number of bytes actually written.  Otherwise this method     * behaves exactly as specified in the {@link GatheringByteChannel}     * interface.  </p>     */    public final long write(ByteBuffer[] srcs) throws IOException {        return write(srcs, 0, srcs.length);    }      // -- Other operations --     /**     * Returns this channel's file position.  </p>     *     * @return  This channel's file position,     *          a non-negative integer counting the number of bytes     *          from the beginning of the file to the current position     *     * @throws  ClosedChannelException     *          If this channel is closed     *     * @throws  IOException     *          If some other I/O error occurs     */    public abstract long position() throws IOException;     /**     * Sets this channel's file position.     *     * <p> Setting the position to a value that is greater than the file's     * current size is legal but does not change the size of the file.  A later     * attempt to read bytes at such a position will immediately return an     * end-of-file indication.  A later attempt to write bytes at such a     * position will cause the file to be grown to accommodate the new bytes;     * the values of any bytes between the previous end-of-file and the     * newly-written bytes are unspecified.  </p>     *     * @param  newPosition     *         The new position, a non-negative integer counting     *         the number of bytes from the beginning of the file     *     * @return  This file channel     *     * @throws  ClosedChannelException     *          If this channel is closed     *     * @throws  IllegalArgumentException     *          If the new position is negative     *     * @throws  IOException     *          If some other I/O error occurs     */    public abstract FileChannel position(long newPosition) throws IOException;     /**     * Returns the current size of this channel's file.  </p>     *     * @return  The current size of this channel's file,     *          measured in bytes     *     * @throws  ClosedChannelException     *          If this channel is closed     *     * @throws  IOException     *          If some other I/O error occurs     */    public abstract long size() throws IOException;     /**     * Truncates this channel's file to the given size.     *     * <p> If the given size is less than the file's current size then the file     * is truncated, discarding any bytes beyond the new end of the file.  If     * the given size is greater than or equal to the file's current size then     * the file is not modified.  In either case, if this channel's file     * position is greater than the given size then it is set to that size.     * </p>     *     * @param  size     *         The new size, a non-negative byte count     *     * @return  This file channel     *     * @throws  NonWritableChannelException     *          If this channel was not opened for writing     *     * @throws  ClosedChannelException     *          If this channel is closed     *     * @throws  IllegalArgumentException     *          If the new size is negative     *     * @throws  IOException

Lines 1–500 of 1157.