Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
openanolis
dragonwell8_jdk
提交
3cea21b7
D
dragonwell8_jdk
项目概览
openanolis
/
dragonwell8_jdk
通知
4
Star
2
Fork
0
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
D
dragonwell8_jdk
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
提交
Issue看板
提交
3cea21b7
编写于
9月 10, 2010
作者:
A
alanb
浏览文件
操作
浏览文件
下载
电子邮件补丁
差异文件
6881498: (file) Re-examine DirectoryStream exception handling
Reviewed-by: forax
上级
edc01f8e
变更
12
隐藏空白更改
内联
并排
Showing
12 changed file
with
387 addition
and
221 deletion
+387
-221
make/java/nio/FILES_java.gmk
make/java/nio/FILES_java.gmk
+1
-0
src/share/classes/java/nio/file/DirectoryIteratorException.java
...are/classes/java/nio/file/DirectoryIteratorException.java
+87
-0
src/share/classes/java/nio/file/DirectoryStream.java
src/share/classes/java/nio/file/DirectoryStream.java
+55
-31
src/share/classes/java/nio/file/Path.java
src/share/classes/java/nio/file/Path.java
+4
-4
src/share/classes/java/nio/file/SecureDirectoryStream.java
src/share/classes/java/nio/file/SecureDirectoryStream.java
+0
-9
src/share/classes/java/util/ConcurrentModificationException.java
...re/classes/java/util/ConcurrentModificationException.java
+38
-3
src/solaris/classes/sun/nio/fs/UnixDirectoryStream.java
src/solaris/classes/sun/nio/fs/UnixDirectoryStream.java
+17
-64
src/solaris/classes/sun/nio/fs/UnixSecureDirectoryStream.java
...solaris/classes/sun/nio/fs/UnixSecureDirectoryStream.java
+1
-1
src/windows/classes/sun/nio/fs/WindowsDirectoryStream.java
src/windows/classes/sun/nio/fs/WindowsDirectoryStream.java
+22
-53
test/java/nio/file/DirectoryStream/Basic.java
test/java/nio/file/DirectoryStream/Basic.java
+31
-40
test/java/nio/file/DirectoryStream/SecureDS.java
test/java/nio/file/DirectoryStream/SecureDS.java
+0
-16
test/java/nio/file/etc/Exceptions.java
test/java/nio/file/etc/Exceptions.java
+131
-0
未找到文件。
make/java/nio/FILES_java.gmk
浏览文件 @
3cea21b7
...
@@ -83,6 +83,7 @@ FILES_src = \
...
@@ -83,6 +83,7 @@ FILES_src = \
java/nio/file/ClosedFileSystemException.java \
java/nio/file/ClosedFileSystemException.java \
java/nio/file/ClosedWatchServiceException.java \
java/nio/file/ClosedWatchServiceException.java \
java/nio/file/CopyOption.java \
java/nio/file/CopyOption.java \
java/nio/file/DirectoryIteratorException.java \
java/nio/file/DirectoryNotEmptyException.java \
java/nio/file/DirectoryNotEmptyException.java \
java/nio/file/DirectoryStream.java \
java/nio/file/DirectoryStream.java \
java/nio/file/FileAlreadyExistsException.java \
java/nio/file/FileAlreadyExistsException.java \
...
...
src/share/classes/java/nio/file/DirectoryIteratorException.java
0 → 100644
浏览文件 @
3cea21b7
/*
* Copyright (c) 2010, 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.file
;
import
java.util.ConcurrentModificationException
;
import
java.util.Objects
;
import
java.io.IOException
;
import
java.io.ObjectInputStream
;
import
java.io.InvalidObjectException
;
/**
* Runtime exception thrown if an I/O error is encountered when iterating over
* the entries in a directory. The I/O error is retrieved as an {@link
* IOException} using the {@link #getCause() getCause()} method.
*
* @since 1.7
* @see DirectoryStream
*/
public
final
class
DirectoryIteratorException
extends
ConcurrentModificationException
{
private
static
final
long
serialVersionUID
=
-
6012699886086212874L
;
/**
* Constructs an instance of this class.
*
* @param cause
* the {@code IOException} that caused the directory iteration
* to fail
*
* @throws NullPointerException
* if the cause is {@code null}
*/
public
DirectoryIteratorException
(
IOException
cause
)
{
super
(
Objects
.
nonNull
(
cause
));
}
/**
* Returns the cause of this exception.
*
* @return the cause
*/
@Override
public
IOException
getCause
()
{
return
(
IOException
)
super
.
getCause
();
}
/**
* Called to read the object from a stream.
*
* @throws InvalidObjectException
* if the object is invalid or has a cause that is not
* an {@code IOException}
*/
private
void
readObject
(
ObjectInputStream
s
)
throws
IOException
,
ClassNotFoundException
{
s
.
defaultReadObject
();
Throwable
cause
=
super
.
getCause
();
if
(!(
cause
instanceof
IOException
))
throw
new
InvalidObjectException
(
"Cause must be an IOException"
);
}
}
src/share/classes/java/nio/file/DirectoryStream.java
浏览文件 @
3cea21b7
...
@@ -31,60 +31,84 @@ import java.io.IOException;
...
@@ -31,60 +31,84 @@ import java.io.IOException;
/**
/**
* An object to iterate over the entries in a directory. A directory stream
* An object to iterate over the entries in a directory. A directory stream
* allows for convenient use of the for-each construct:
* allows for the convenient use of the for-each construct to iterate over a
* directory.
*
* <p> <b> While {@code DirectoryStream} extends {@code Iterable}, it is not a
* general-purpose {@code Iterable} as it supports only a single {@code
* Iterator}; invoking the {@link #iterator iterator} method to obtain a second
* or subsequent iterator throws {@code IllegalStateException}. </b>
*
* <p> An important property of the directory stream's {@code Iterator} is that
* its {@link Iterator#hasNext() hasNext} method is guaranteed to read-ahead by
* at least one element. If {@code hasNext} method returns {@code true}, and is
* followed by a call to the {@code next} method, it is guaranteed that the
* {@code next} method will not throw an exception due to an I/O error, or
* because the stream has been {@link #close closed}. The {@code Iterator} does
* not support the {@link Iterator#remove remove} operation.
*
* <p> A {@code DirectoryStream} is opened upon creation and is closed by
* invoking the {@code close} method. Closing a directory stream releases any
* resources associated with the stream. Failure to close the stream may result
* in a resource leak. The try-with-resources statement provides a useful
* construct to ensure that the stream is closed:
* <pre>
* <pre>
* Path dir = ...
* Path dir = ...
* DirectoryStream<Path> stream = dir.newDirectoryStream();
* try (DirectoryStream<Path> stream = dir.newDirectoryStream()) {
* try {
* for (Path entry: stream) {
* for (Path entry: stream) {
* ..
*
.
..
* }
* }
* } finally {
* stream.close();
* }
* }
* </pre>
* </pre>
*
*
* <p><b> A {@code DirectoryStream} is not a general-purpose {@code Iterable}.
* <p> Once a directory stream is closed, then further access to the directory,
* While this interface extends {@code Iterable}, the {@code iterator} method
* using the {@code Iterator}, behaves as if the end of stream has been reached.
* may only be invoked once to obtain the iterator; a second, or subsequent,
* Due to read-ahead, the {@code Iterator} may return one or more elements
* call to the {@code iterator} method throws {@code IllegalStateException}. </b>
* after the directory stream has been closed. Once these buffered elements
*
* have been read, then subsequent calls to the {@code hasNext} method returns
* <p> A {@code DirectoryStream} is opened upon creation and is closed by
* {@code false}, and subsequent calls to the {@code next} method will throw
* invoking the {@link #close close} method. Closing the directory stream
* {@code NoSuchElementException}.
* releases any resources associated with the stream. Once a directory stream
* is closed, all further method invocations on the iterator throw {@link
* java.util.ConcurrentModificationException} with cause {@link
* ClosedDirectoryStreamException}.
*
*
* <p> A directory stream is not required to be <i>asynchronously closeable</i>.
* <p> A directory stream is not required to be <i>asynchronously closeable</i>.
* If a thread is blocked on the directory stream's iterator reading from the
* If a thread is blocked on the directory stream's iterator reading from the
* directory, and another thread invokes the {@code close} method, then the
* directory, and another thread invokes the {@code close} method, then the
* second thread may block until the read operation is complete.
* second thread may block until the read operation is complete.
*
*
* <p>
The {@link Iterator#hasNext() hasNext} and {@link Iterator#next() next}
* <p>
If an I/O error is encountered when accessing the directory then it
*
methods can encounter an I/O error when iterating over the directory in which
*
causes the {@code Iterator}'s {@code hasNext} or {@code next} methods to
*
case {@code ConcurrentModificationException} is thrown with caus
e
*
throw {@link DirectoryIteratorException} with the {@link IOException} as th
e
*
{@link java.io.IOException}. T
he {@code hasNext} method is guaranteed to
*
cause. As stated above, t
he {@code hasNext} method is guaranteed to
* read-ahead by at least one element. This means that if
the {@code hasNext}
* read-ahead by at least one element. This means that if
{@code hasNext} method
*
method returns {@code true} and is followed by a call to the {@code next}
*
returns {@code true}, and is followed by a call to the {@code next} method,
*
method then it is guaranteed not to fail with a {@code
*
then it is guaranteed that the {@code next} method will not fail with a
*
ConcurrentModification
Exception}.
*
{@code DirectoryIterator
Exception}.
*
*
* <p> The elements returned by the iterator are in no specific order. Some file
* <p> The elements returned by the iterator are in no specific order. Some file
* systems maintain special links to the directory itself and the directory's
* systems maintain special links to the directory itself and the directory's
* parent directory. Entries representing these links are not returned by the
* parent directory. Entries representing these links are not returned by the
* iterator.
* iterator.
*
*
* <p> The iterator's {@link Iterator#remove() remove} method removes the
* directory entry for the last element returned by the iterator, as if by
* invoking the {@link Path#delete delete} method. If an I/O error or
* security exception occurs then {@code ConcurrentModificationException} is
* thrown with the cause.
*
* <p> The iterator is <i>weakly consistent</i>. It is thread safe but does not
* <p> The iterator is <i>weakly consistent</i>. It is thread safe but does not
* freeze the directory while iterating, so it may (or may not) reflect updates
* freeze the directory while iterating, so it may (or may not) reflect updates
* to the directory that occur after the {@code DirectoryStream} is created.
* to the directory that occur after the {@code DirectoryStream} is created.
*
*
* <p> <b>Usage Examples:</b>
* Suppose we want a list of the source files in a directory. This example uses
* both the for-each and try-with-resources constructs.
* <pre>
* List<Path> listSourceFiles(Path dir) throws IOException {
* List<Path> result = new ArrayList<Path>();
* try (DirectoryStream<Path> stream = dir.newDirectoryStream("*.{c,h,cpp,hpp,java}")) {
* for (Path entry: stream) {
* result.add(entry);
* }
* } catch (DirectoryIteratorException ex) {
* // I/O error encounted during the iteration, the cause is an IOException
* throw ex.getCause();
* }
* return result;
* }
* </pre>
* @param <T> The type of element returned by the iterator
* @param <T> The type of element returned by the iterator
*
*
* @since 1.7
* @since 1.7
...
...
src/share/classes/java/nio/file/Path.java
浏览文件 @
3cea21b7
...
@@ -984,11 +984,11 @@ public abstract class Path
...
@@ -984,11 +984,11 @@ public abstract class Path
* directory.
* directory.
*
*
* <p> Where the filter terminates due to an uncaught error or runtime
* <p> Where the filter terminates due to an uncaught error or runtime
* exception then it is prop
ogated to the iterator's
{@link Iterator#hasNext()
* exception then it is prop
agated to the
{@link Iterator#hasNext()
* hasNext} or {@link Iterator#next() next} method. Where an {@code
* hasNext} or {@link Iterator#next() next} method. Where an {@code
* IOException} is thrown, it
is propogated as a {@link
* IOException} is thrown, it
results in the {@code hasNext} or {@code
*
java.util.ConcurrentModificationException} with the {@cod
e
*
next} method throwing a {@link DirectoryIteratorException} with th
e
* IOException} as the cause.
*
{@code
IOException} as the cause.
*
*
* <p> When an implementation supports operations on entries in the
* <p> When an implementation supports operations on entries in the
* directory that execute in a race-free manner then the returned directory
* directory that execute in a race-free manner then the returned directory
...
...
src/share/classes/java/nio/file/SecureDirectoryStream.java
浏览文件 @
3cea21b7
...
@@ -47,15 +47,6 @@ import java.io.IOException;
...
@@ -47,15 +47,6 @@ import java.io.IOException;
* newDirectoryStream} method will be a {@code SecureDirectoryStream} and must
* newDirectoryStream} method will be a {@code SecureDirectoryStream} and must
* be cast to that type in order to invoke the methods defined by this interface.
* be cast to that type in order to invoke the methods defined by this interface.
*
*
* <p> As specified by {@code DirectoryStream}, the iterator's {@link
* java.util.Iterator#remove() remove} method removes the directory entry for
* the last element returned by the iterator. In the case of a {@code
* SecureDirectoryStream} the {@code remove} method behaves as if by invoking
* the {@link #deleteFile deleteFile} or {@link #deleteDirectory deleteDirectory}
* methods defined by this interface. The {@code remove} may require to examine
* the file to determine if the file is a directory, and consequently, it may
* not be atomic with respect to other file system operations.
*
* <p> In the case of the default {@link java.nio.file.spi.FileSystemProvider
* <p> In the case of the default {@link java.nio.file.spi.FileSystemProvider
* provider}, and a security manager is set, then the permission checks are
* provider}, and a security manager is set, then the permission checks are
* performed using the path obtained by resolving the given relative path
* performed using the path obtained by resolving the given relative path
...
...
src/share/classes/java/util/ConcurrentModificationException.java
浏览文件 @
3cea21b7
...
@@ -49,9 +49,9 @@ package java.util;
...
@@ -49,9 +49,9 @@ package java.util;
* <p>Note that fail-fast behavior cannot be guaranteed as it is, generally
* <p>Note that fail-fast behavior cannot be guaranteed as it is, generally
* speaking, impossible to make any hard guarantees in the presence of
* speaking, impossible to make any hard guarantees in the presence of
* unsynchronized concurrent modification. Fail-fast operations
* unsynchronized concurrent modification. Fail-fast operations
* throw
<tt>ConcurrentModificationException</tt>
on a best-effort basis.
* throw
{@code ConcurrentModificationException}
on a best-effort basis.
* Therefore, it would be wrong to write a program that depended on this
* Therefore, it would be wrong to write a program that depended on this
* exception for its correctness: <i>
<tt>ConcurrentModificationException</tt>
* exception for its correctness: <i>
{@code ConcurrentModificationException}
* should be used only to detect bugs.</i>
* should be used only to detect bugs.</i>
*
*
* @author Josh Bloch
* @author Josh Bloch
...
@@ -77,7 +77,7 @@ public class ConcurrentModificationException extends RuntimeException {
...
@@ -77,7 +77,7 @@ public class ConcurrentModificationException extends RuntimeException {
}
}
/**
/**
* Constructs a
<tt>ConcurrentModificationException</tt>
with the
* Constructs a
{@code ConcurrentModificationException}
with the
* specified detail message.
* specified detail message.
*
*
* @param message the detail message pertaining to this exception.
* @param message the detail message pertaining to this exception.
...
@@ -85,4 +85,39 @@ public class ConcurrentModificationException extends RuntimeException {
...
@@ -85,4 +85,39 @@ public class ConcurrentModificationException extends RuntimeException {
public
ConcurrentModificationException
(
String
message
)
{
public
ConcurrentModificationException
(
String
message
)
{
super
(
message
);
super
(
message
);
}
}
/**
* Constructs a new exception with the specified cause and a detail
* message of {@code (cause==null ? null : cause.toString())} (which
* typically contains the class and detail message of {@code cause}.
*
* @param cause the cause (which is saved for later retrieval by the
* {@link Throwable#getCause()} method). (A {@code null} value is
* permitted, and indicates that the cause is nonexistent or
* unknown.)
* @since 1.7
*/
public
ConcurrentModificationException
(
Throwable
cause
)
{
super
(
cause
);
}
/**
* Constructs a new exception with the specified detail message and
* cause.
*
* <p>Note that the detail message associated with <code>cause</code> is
* <i>not</i> automatically incorporated in this exception's detail
* message.
*
* @param message the detail message (which is saved for later retrieval
* by the {@link Throwable#getMessage()} method).
* @param cause the cause (which is saved for later retrieval by the
* {@link Throwable#getCause()} method). (A {@code null} value
* is permitted, and indicates that the cause is nonexistent or
* unknown.)
* @since 1.7
*/
public
ConcurrentModificationException
(
String
message
,
Throwable
cause
)
{
super
(
message
,
cause
);
}
}
}
src/solaris/classes/sun/nio/fs/UnixDirectoryStream.java
浏览文件 @
3cea21b7
...
@@ -27,7 +27,6 @@ package sun.nio.fs;
...
@@ -27,7 +27,6 @@ package sun.nio.fs;
import
java.nio.file.*
;
import
java.nio.file.*
;
import
java.util.Iterator
;
import
java.util.Iterator
;
import
java.util.ConcurrentModificationException
;
import
java.util.NoSuchElementException
;
import
java.util.NoSuchElementException
;
import
java.util.concurrent.locks.*
;
import
java.util.concurrent.locks.*
;
import
java.io.IOException
;
import
java.io.IOException
;
...
@@ -139,9 +138,6 @@ class UnixDirectoryStream
...
@@ -139,9 +138,6 @@ class UnixDirectoryStream
// next entry to return
// next entry to return
private
Path
nextEntry
;
private
Path
nextEntry
;
// previous entry returned by next method (needed by remove method)
private
Path
prevEntry
;
UnixDirectoryIterator
(
DirectoryStream
<
Path
>
stream
)
{
UnixDirectoryIterator
(
DirectoryStream
<
Path
>
stream
)
{
atEof
=
false
;
atEof
=
false
;
this
.
stream
=
stream
;
this
.
stream
=
stream
;
...
@@ -168,24 +164,19 @@ class UnixDirectoryStream
...
@@ -168,24 +164,19 @@ class UnixDirectoryStream
// prevent close while reading
// prevent close while reading
readLock
().
lock
();
readLock
().
lock
();
try
{
try
{
if
(
isClosed
)
if
(
isOpen
())
{
throwAsConcurrentModificationException
(
new
ClosedDirectoryStreamException
());
try
{
nameAsBytes
=
readdir
(
dp
);
nameAsBytes
=
readdir
(
dp
);
}
catch
(
UnixException
x
)
{
try
{
x
.
rethrowAsIOException
(
dir
);
}
catch
(
IOException
ioe
)
{
throwAsConcurrentModificationException
(
ioe
);
}
}
}
}
catch
(
UnixException
x
)
{
IOException
ioe
=
x
.
asIOException
(
dir
);
throw
new
DirectoryIteratorException
(
ioe
);
}
finally
{
}
finally
{
readLock
().
unlock
();
readLock
().
unlock
();
}
}
// EOF
// EOF
if
(
nameAsBytes
==
null
)
{
if
(
nameAsBytes
==
null
)
{
atEof
=
true
;
return
null
;
return
null
;
}
}
...
@@ -198,7 +189,7 @@ class UnixDirectoryStream
...
@@ -198,7 +189,7 @@ class UnixDirectoryStream
if
(
filter
==
null
||
filter
.
accept
(
entry
))
if
(
filter
==
null
||
filter
.
accept
(
entry
))
return
entry
;
return
entry
;
}
catch
(
IOException
ioe
)
{
}
catch
(
IOException
ioe
)
{
throw
AsConcurrentModification
Exception
(
ioe
);
throw
new
DirectoryIterator
Exception
(
ioe
);
}
}
}
}
}
}
...
@@ -206,66 +197,28 @@ class UnixDirectoryStream
...
@@ -206,66 +197,28 @@ class UnixDirectoryStream
@Override
@Override
public
synchronized
boolean
hasNext
()
{
public
synchronized
boolean
hasNext
()
{
if
(
nextEntry
==
null
&&
!
atEof
)
{
if
(
nextEntry
==
null
&&
!
atEof
)
nextEntry
=
readNextEntry
();
nextEntry
=
readNextEntry
();
// at EOF?
if
(
nextEntry
==
null
)
atEof
=
true
;
}
return
nextEntry
!=
null
;
return
nextEntry
!=
null
;
}
}
@Override
@Override
public
synchronized
Path
next
()
{
public
synchronized
Path
next
()
{
if
(
nextEntry
==
null
)
{
Path
result
;
if
(!
atEof
)
{
if
(
nextEntry
==
null
&&
!
atEof
)
{
nextEntry
=
readNextEntry
();
result
=
readNextEntry
();
}
}
else
{
if
(
nextEntry
==
null
)
{
result
=
nextEntry
;
atEof
=
true
;
nextEntry
=
null
;
throw
new
NoSuchElementException
();
}
}
}
prevEntry
=
nextEntry
;
if
(
result
==
null
)
nextEntry
=
null
;
throw
new
NoSuchElementException
()
;
return
prevEntry
;
return
result
;
}
}
@Override
@Override
public
void
remove
()
{
public
void
remove
()
{
if
(
isClosed
)
{
throw
new
UnsupportedOperationException
();
throwAsConcurrentModificationException
(
new
ClosedDirectoryStreamException
());
}
Path
entry
;
synchronized
(
this
)
{
if
(
prevEntry
==
null
)
throw
new
IllegalStateException
(
"No previous entry to remove"
);
entry
=
prevEntry
;
prevEntry
=
null
;
}
// use (race-free) unlinkat if available
try
{
if
(
stream
instanceof
UnixSecureDirectoryStream
)
{
((
UnixSecureDirectoryStream
)
stream
)
.
implDelete
(
entry
.
getName
(),
false
,
0
);
}
else
{
entry
.
delete
();
}
}
catch
(
IOException
ioe
)
{
throwAsConcurrentModificationException
(
ioe
);
}
catch
(
SecurityException
se
)
{
throwAsConcurrentModificationException
(
se
);
}
}
}
}
}
private
static
void
throwAsConcurrentModificationException
(
Throwable
t
)
{
ConcurrentModificationException
cme
=
new
ConcurrentModificationException
();
cme
.
initCause
(
t
);
throw
cme
;
}
}
}
src/solaris/classes/sun/nio/fs/UnixSecureDirectoryStream.java
浏览文件 @
3cea21b7
...
@@ -166,7 +166,7 @@ class UnixSecureDirectoryStream
...
@@ -166,7 +166,7 @@ class UnixSecureDirectoryStream
* Deletes file/directory in this directory. Works in a race-free manner
* Deletes file/directory in this directory. Works in a race-free manner
* when invoked with flags.
* when invoked with flags.
*/
*/
void
implDelete
(
Path
obj
,
boolean
haveFlags
,
int
flags
)
private
void
implDelete
(
Path
obj
,
boolean
haveFlags
,
int
flags
)
throws
IOException
throws
IOException
{
{
UnixPath
file
=
getName
(
obj
);
UnixPath
file
=
getName
(
obj
);
...
...
src/windows/classes/sun/nio/fs/WindowsDirectoryStream.java
浏览文件 @
3cea21b7
...
@@ -28,7 +28,6 @@ package sun.nio.fs;
...
@@ -28,7 +28,6 @@ package sun.nio.fs;
import
java.nio.file.*
;
import
java.nio.file.*
;
import
java.nio.file.attribute.BasicFileAttributes
;
import
java.nio.file.attribute.BasicFileAttributes
;
import
java.util.Iterator
;
import
java.util.Iterator
;
import
java.util.ConcurrentModificationException
;
import
java.util.NoSuchElementException
;
import
java.util.NoSuchElementException
;
import
java.io.IOException
;
import
java.io.IOException
;
...
@@ -121,17 +120,10 @@ class WindowsDirectoryStream
...
@@ -121,17 +120,10 @@ class WindowsDirectoryStream
}
}
}
}
private
static
void
throwAsConcurrentModificationException
(
Throwable
t
)
{
ConcurrentModificationException
cme
=
new
ConcurrentModificationException
();
cme
.
initCause
(
t
);
throw
cme
;
}
private
class
WindowsDirectoryIterator
implements
Iterator
<
Path
>
{
private
class
WindowsDirectoryIterator
implements
Iterator
<
Path
>
{
private
boolean
atEof
;
private
boolean
atEof
;
private
String
first
;
private
String
first
;
private
Path
nextEntry
;
private
Path
nextEntry
;
private
Path
prevEntry
;
WindowsDirectoryIterator
(
String
first
)
{
WindowsDirectoryIterator
(
String
first
)
{
atEof
=
false
;
atEof
=
false
;
...
@@ -156,7 +148,7 @@ class WindowsDirectoryStream
...
@@ -156,7 +148,7 @@ class WindowsDirectoryStream
if
(
filter
.
accept
(
entry
))
if
(
filter
.
accept
(
entry
))
return
entry
;
return
entry
;
}
catch
(
IOException
ioe
)
{
}
catch
(
IOException
ioe
)
{
throw
AsConcurrentModification
Exception
(
ioe
);
throw
new
DirectoryIterator
Exception
(
ioe
);
}
}
return
null
;
return
null
;
}
}
...
@@ -177,21 +169,19 @@ class WindowsDirectoryStream
...
@@ -177,21 +169,19 @@ class WindowsDirectoryStream
// synchronize on closeLock to prevent close while reading
// synchronize on closeLock to prevent close while reading
synchronized
(
closeLock
)
{
synchronized
(
closeLock
)
{
if
(!
isOpen
)
throwAsConcurrentModificationException
(
new
ClosedDirectoryStreamException
());
try
{
try
{
name
=
FindNextFile
(
handle
,
findDataBuffer
.
address
());
if
(
isOpen
)
{
if
(
name
==
null
)
{
name
=
FindNextFile
(
handle
,
findDataBuffer
.
address
());
// NO_MORE_FILES
return
null
;
}
}
}
catch
(
WindowsException
x
)
{
}
catch
(
WindowsException
x
)
{
try
{
IOException
ioe
=
x
.
asIOException
(
dir
);
x
.
rethrowAsIOException
(
dir
);
throw
new
DirectoryIteratorException
(
ioe
);
}
catch
(
IOException
ioe
)
{
}
throwAsConcurrentModificationException
(
ioe
);
}
// NO_MORE_FILES or stream closed
if
(
name
==
null
)
{
atEof
=
true
;
return
null
;
}
}
// grab the attributes from the WIN32_FIND_DATA structure
// grab the attributes from the WIN32_FIND_DATA structure
...
@@ -210,49 +200,28 @@ class WindowsDirectoryStream
...
@@ -210,49 +200,28 @@ class WindowsDirectoryStream
@Override
@Override
public
synchronized
boolean
hasNext
()
{
public
synchronized
boolean
hasNext
()
{
if
(
nextEntry
==
null
&&
!
atEof
)
{
if
(
nextEntry
==
null
&&
!
atEof
)
nextEntry
=
readNextEntry
();
nextEntry
=
readNextEntry
();
atEof
=
(
nextEntry
==
null
);
}
return
nextEntry
!=
null
;
return
nextEntry
!=
null
;
}
}
@Override
@Override
public
synchronized
Path
next
()
{
public
synchronized
Path
next
()
{
if
(
nextEntry
==
null
)
{
Path
result
=
null
;
if
(!
atEof
)
{
if
(
nextEntry
==
null
&&
!
atEof
)
{
nextEntry
=
readNextEntry
();
result
=
readNextEntry
();
}
}
else
{
if
(
nextEntry
==
null
)
{
result
=
nextEntry
;
atEof
=
true
;
nextEntry
=
null
;
throw
new
NoSuchElementException
();
}
}
}
prevEntry
=
nextEntry
;
if
(
result
==
null
)
nextEntry
=
null
;
throw
new
NoSuchElementException
()
;
return
prevEntry
;
return
result
;
}
}
@Override
@Override
public
void
remove
()
{
public
void
remove
()
{
if
(!
isOpen
)
{
throw
new
UnsupportedOperationException
();
throwAsConcurrentModificationException
(
new
ClosedDirectoryStreamException
());
}
Path
entry
;
synchronized
(
this
)
{
if
(
prevEntry
==
null
)
throw
new
IllegalStateException
(
"no last element"
);
entry
=
prevEntry
;
prevEntry
=
null
;
}
try
{
entry
.
delete
();
}
catch
(
IOException
ioe
)
{
throwAsConcurrentModificationException
(
ioe
);
}
catch
(
SecurityException
se
)
{
throwAsConcurrentModificationException
(
se
);
}
}
}
}
}
}
}
test/java/nio/file/DirectoryStream/Basic.java
浏览文件 @
3cea21b7
...
@@ -104,20 +104,20 @@ public class Basic {
...
@@ -104,20 +104,20 @@ public class Basic {
stream
.
close
();
stream
.
close
();
}
}
// check that
IOExceptions throws by filters are
propagated
// check that
an IOException thrown by a filter is
propagated
filter
=
new
DirectoryStream
.
Filter
<
Path
>()
{
filter
=
new
DirectoryStream
.
Filter
<
Path
>()
{
public
boolean
accept
(
Path
file
)
throws
IOException
{
public
boolean
accept
(
Path
file
)
throws
IOException
{
throw
new
IO
Exception
();
throw
new
java
.
util
.
zip
.
Zip
Exception
();
}
}
};
};
stream
=
dir
.
newDirectoryStream
(
filter
);
stream
=
dir
.
newDirectoryStream
(
filter
);
try
{
try
{
stream
.
iterator
().
hasNext
();
stream
.
iterator
().
hasNext
();
throw
new
RuntimeException
(
"
ConcurrentModification
Exception expected"
);
throw
new
RuntimeException
(
"
DirectoryIterator
Exception expected"
);
}
catch
(
ConcurrentModification
Exception
x
)
{
}
catch
(
DirectoryIterator
Exception
x
)
{
Throwable
t
=
x
.
getCause
();
IOException
cause
=
x
.
getCause
();
if
(!(
t
instanceof
IO
Exception
))
if
(!(
cause
instanceof
java
.
util
.
zip
.
Zip
Exception
))
throw
new
RuntimeException
(
"
Cause is not IOException as expec
ted"
);
throw
new
RuntimeException
(
"
Expected IOException not propaga
ted"
);
}
finally
{
}
finally
{
stream
.
close
();
stream
.
close
();
}
}
...
@@ -142,58 +142,49 @@ public class Basic {
...
@@ -142,58 +142,49 @@ public class Basic {
}
catch
(
NotDirectoryException
x
)
{
}
catch
(
NotDirectoryException
x
)
{
}
}
// test
iterator remove method
// test
UnsupportedOperationException
stream
=
dir
.
newDirectoryStream
();
stream
=
dir
.
newDirectoryStream
();
Iterator
<
Path
>
i
=
stream
.
iterator
();
Iterator
<
Path
>
i
=
stream
.
iterator
();
while
(
i
.
hasNext
())
{
i
.
next
();
Path
entry
=
i
.
next
();
try
{
if
(!
entry
.
getName
().
equals
(
foo
))
throw
new
RuntimeException
(
"entry not expected"
);
i
.
remove
();
i
.
remove
();
throw
new
RuntimeException
(
"UnsupportedOperationException expected"
);
}
catch
(
UnsupportedOperationException
uoe
)
{
}
}
stream
.
close
();
// test IllegalStateException
// test IllegalStateException
dir
.
resolve
(
foo
).
createFile
();
stream
=
dir
.
newDirectoryStream
();
stream
=
dir
.
newDirectoryStream
();
i
=
stream
.
iterator
();
stream
.
iterator
();
i
.
next
();
try
{
try
{
// attempt to obtain second iterator
stream
.
iterator
();
stream
.
iterator
();
throw
new
RuntimeException
(
"IllegalStateException not thrown as expected"
);
throw
new
RuntimeException
(
"IllegalStateException not thrown as expected"
);
}
catch
(
IllegalStateException
x
)
{
}
catch
(
IllegalStateException
x
)
{
}
}
stream
.
close
();
stream
.
close
();
stream
=
dir
.
newDirectoryStream
();
stream
.
close
();
try
{
try
{
// attempt to obtain iterator after stream is closed
stream
.
iterator
();
stream
.
iterator
();
throw
new
RuntimeException
(
"IllegalStateException not thrown as expected"
);
throw
new
RuntimeException
(
"IllegalStateException not thrown as expected"
);
}
catch
(
IllegalStateException
x
)
{
}
catch
(
IllegalStateException
x
)
{
}
}
try
{
i
.
hasNext
();
// test that iterator reads to end of stream when closed
throw
new
RuntimeException
(
"ConcurrentModificationException not thrown as expected"
);
stream
=
dir
.
newDirectoryStream
();
}
catch
(
ConcurrentModificationException
x
)
{
i
=
stream
.
iterator
();
Throwable
t
=
x
.
getCause
();
stream
.
close
();
if
(!(
t
instanceof
ClosedDirectoryStreamException
))
while
(
i
.
hasNext
())
throw
new
RuntimeException
(
"Cause is not ClosedDirectoryStreamException as expected"
);
}
try
{
i
.
next
();
i
.
next
();
throw
new
RuntimeException
(
"ConcurrentModificationException not thrown as expected"
);
}
catch
(
ConcurrentModificationException
x
)
{
Throwable
t
=
x
.
getCause
();
if
(!(
t
instanceof
ClosedDirectoryStreamException
))
throw
new
RuntimeException
(
"Cause is not ClosedDirectoryStreamException as expected"
);
}
try
{
i
.
remove
();
throw
new
RuntimeException
(
"ConcurrentModificationException not thrown as expected"
);
}
catch
(
ConcurrentModificationException
x
)
{
Throwable
t
=
x
.
getCause
();
if
(!(
t
instanceof
ClosedDirectoryStreamException
))
throw
new
RuntimeException
(
"Cause is not ClosedDirectoryStreamException as expected"
);
}
stream
=
dir
.
newDirectoryStream
();
i
=
stream
.
iterator
();
stream
.
close
();
try
{
for
(;;)
i
.
next
();
}
catch
(
NoSuchElementException
expected
)
{
}
}
}
public
static
void
main
(
String
[]
args
)
throws
IOException
{
public
static
void
main
(
String
[]
args
)
throws
IOException
{
...
...
test/java/nio/file/DirectoryStream/SecureDS.java
浏览文件 @
3cea21b7
...
@@ -166,22 +166,6 @@ public class SecureDS {
...
@@ -166,22 +166,6 @@ public class SecureDS {
stream
.
deleteDirectory
(
dirEntry
);
stream
.
deleteDirectory
(
dirEntry
);
stream
.
deleteFile
(
fileEntry
);
stream
.
deleteFile
(
fileEntry
);
// Test: remove
// (requires resetting environment to get new iterator)
stream
.
close
();
dir2
.
moveTo
(
dir1
);
dir1
.
resolve
(
fileEntry
).
createFile
();
stream
=
(
SecureDirectoryStream
<
Path
>)
dir1
.
newDirectoryStream
();
dir1
.
moveTo
(
dir2
);
Iterator
<
Path
>
iter
=
stream
.
iterator
();
int
removed
=
0
;
while
(
iter
.
hasNext
())
{
iter
.
next
();
iter
.
remove
();
removed
++;
}
assertTrue
(
removed
==
1
);
// clean-up
// clean-up
stream
.
close
();
stream
.
close
();
dir2
.
delete
();
dir2
.
delete
();
...
...
test/java/nio/file/etc/Exceptions.java
0 → 100644
浏览文件 @
3cea21b7
/*
* Copyright (c) 2010, 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.
*
* 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.
*/
/* @test
* @bug 4313887 6881498
* @summary Miscellenous tests on exceptions in java.nio.file
*/
import
java.nio.file.*
;
import
java.io.*
;
import
java.util.Objects
;
import
java.lang.reflect.*
;
public
class
Exceptions
{
public
static
void
main
(
String
[]
args
)
throws
Exception
{
testFileSystemException
();
testDirectoryIteratorException
();
}
static
void
testFileSystemException
()
throws
Exception
{
String
thisFile
=
"source"
;
String
otherFile
=
"target"
;
String
reason
=
"Access denied"
;
// getFile/getOtherFile
testFileSystemException
(
thisFile
,
otherFile
,
reason
);
testFileSystemException
(
null
,
otherFile
,
reason
);
testFileSystemException
(
thisFile
,
null
,
reason
);
testFileSystemException
(
thisFile
,
otherFile
,
null
);
// serialization
FileSystemException
exc
;
exc
=
new
FileSystemException
(
thisFile
,
otherFile
,
reason
);
exc
=
(
FileSystemException
)
deserialize
(
serialize
(
exc
));
if
(!
exc
.
getFile
().
equals
(
thisFile
)
||
!
exc
.
getOtherFile
().
equals
(
otherFile
))
throw
new
RuntimeException
(
"Exception not reconstituted completely"
);
}
static
void
testFileSystemException
(
String
thisFile
,
String
otherFile
,
String
reason
)
{
FileSystemException
exc
=
new
FileSystemException
(
thisFile
,
otherFile
,
reason
);
if
(!
Objects
.
equals
(
thisFile
,
exc
.
getFile
()))
throw
new
RuntimeException
(
"getFile returned unexpected result"
);
if
(!
Objects
.
equals
(
otherFile
,
exc
.
getOtherFile
()))
throw
new
RuntimeException
(
"getOtherFile returned unexpected result"
);
if
(!
Objects
.
equals
(
reason
,
exc
.
getReason
()))
throw
new
RuntimeException
(
"getReason returned unexpected result"
);
}
static
void
testDirectoryIteratorException
()
throws
Exception
{
// NullPointerException
try
{
new
DirectoryIteratorException
(
null
);
throw
new
RuntimeException
(
"NullPointerException expected"
);
}
catch
(
NullPointerException
expected
)
{
}
// serialization
DirectoryIteratorException
exc
;
exc
=
new
DirectoryIteratorException
(
new
IOException
());
exc
=
(
DirectoryIteratorException
)
deserialize
(
serialize
(
exc
));
IOException
ioe
=
exc
.
getCause
();
if
(
ioe
==
null
)
throw
new
RuntimeException
(
"Cause should not be null"
);
// when deserializing then the cause should be an IOException
hackCause
(
exc
,
null
);
try
{
deserialize
(
serialize
(
exc
));
throw
new
RuntimeException
(
"InvalidObjectException expected"
);
}
catch
(
InvalidObjectException
expected
)
{
}
hackCause
(
exc
,
new
RuntimeException
());
try
{
deserialize
(
serialize
(
exc
));
throw
new
RuntimeException
(
"InvalidObjectException expected"
);
}
catch
(
InvalidObjectException
expected
)
{
}
}
// Use reflection to set a Throwable's cause.
static
void
hackCause
(
Throwable
t
,
Throwable
cause
)
throws
NoSuchFieldException
,
IllegalAccessException
{
Field
f
=
Throwable
.
class
.
getDeclaredField
(
"cause"
);
f
.
setAccessible
(
true
);
f
.
set
(
t
,
cause
);
}
// Serialize the given object to a byte[]
static
byte
[]
serialize
(
Object
o
)
throws
IOException
{
ByteArrayOutputStream
baos
=
new
ByteArrayOutputStream
();
ObjectOutputStream
oos
=
new
ObjectOutputStream
(
baos
);
oos
.
writeObject
(
o
);
oos
.
close
();
return
baos
.
toByteArray
();
}
// Read an object from its serialized form
static
Object
deserialize
(
byte
[]
bytes
)
throws
IOException
,
ClassNotFoundException
{
ByteArrayInputStream
in
=
new
ByteArrayInputStream
(
bytes
);
ObjectInputStream
ois
=
new
ObjectInputStream
(
in
);
Object
result
=
ois
.
readObject
();
ois
.
close
();
return
result
;
}
}
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录