Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
openanolis
dragonwell8_jdk
提交
d33bc88e
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看板
提交
d33bc88e
编写于
11月 15, 2010
作者:
C
chegar
浏览文件
操作
浏览文件
下载
电子邮件补丁
差异文件
6993789: LinkedBlockingDeque iterator/descendingIterator loops and owns lock forever
Reviewed-by: dl, dholmes
上级
fbe518a5
变更
2
隐藏空白更改
内联
并排
Showing
2 changed file
with
98 addition
and
50 deletion
+98
-50
src/share/classes/java/util/concurrent/LinkedBlockingDeque.java
...are/classes/java/util/concurrent/LinkedBlockingDeque.java
+61
-33
test/java/util/concurrent/ConcurrentQueues/IteratorWeakConsistency.java
.../concurrent/ConcurrentQueues/IteratorWeakConsistency.java
+37
-17
未找到文件。
src/share/classes/java/util/concurrent/LinkedBlockingDeque.java
浏览文件 @
d33bc88e
...
@@ -126,10 +126,8 @@ public class LinkedBlockingDeque<E>
...
@@ -126,10 +126,8 @@ public class LinkedBlockingDeque<E>
*/
*/
Node
<
E
>
next
;
Node
<
E
>
next
;
Node
(
E
x
,
Node
<
E
>
p
,
Node
<
E
>
n
)
{
Node
(
E
x
)
{
item
=
x
;
item
=
x
;
prev
=
p
;
next
=
n
;
}
}
}
}
...
@@ -199,7 +197,7 @@ public class LinkedBlockingDeque<E>
...
@@ -199,7 +197,7 @@ public class LinkedBlockingDeque<E>
for
(
E
e
:
c
)
{
for
(
E
e
:
c
)
{
if
(
e
==
null
)
if
(
e
==
null
)
throw
new
NullPointerException
();
throw
new
NullPointerException
();
if
(!
linkLast
(
e
))
if
(!
linkLast
(
new
Node
<
E
>(
e
)
))
throw
new
IllegalStateException
(
"Deque full"
);
throw
new
IllegalStateException
(
"Deque full"
);
}
}
}
finally
{
}
finally
{
...
@@ -211,38 +209,38 @@ public class LinkedBlockingDeque<E>
...
@@ -211,38 +209,38 @@ public class LinkedBlockingDeque<E>
// Basic linking and unlinking operations, called only while holding lock
// Basic linking and unlinking operations, called only while holding lock
/**
/**
* Links e as first element, or returns false if full.
* Links
nod
e as first element, or returns false if full.
*/
*/
private
boolean
linkFirst
(
E
e
)
{
private
boolean
linkFirst
(
Node
<
E
>
nod
e
)
{
// assert lock.isHeldByCurrentThread();
// assert lock.isHeldByCurrentThread();
if
(
count
>=
capacity
)
if
(
count
>=
capacity
)
return
false
;
return
false
;
Node
<
E
>
f
=
first
;
Node
<
E
>
f
=
first
;
Node
<
E
>
x
=
new
Node
<
E
>(
e
,
null
,
f
)
;
node
.
next
=
f
;
first
=
x
;
first
=
node
;
if
(
last
==
null
)
if
(
last
==
null
)
last
=
x
;
last
=
node
;
else
else
f
.
prev
=
x
;
f
.
prev
=
node
;
++
count
;
++
count
;
notEmpty
.
signal
();
notEmpty
.
signal
();
return
true
;
return
true
;
}
}
/**
/**
* Links e as last element, or returns false if full.
* Links
nod
e as last element, or returns false if full.
*/
*/
private
boolean
linkLast
(
E
e
)
{
private
boolean
linkLast
(
Node
<
E
>
nod
e
)
{
// assert lock.isHeldByCurrentThread();
// assert lock.isHeldByCurrentThread();
if
(
count
>=
capacity
)
if
(
count
>=
capacity
)
return
false
;
return
false
;
Node
<
E
>
l
=
last
;
Node
<
E
>
l
=
last
;
Node
<
E
>
x
=
new
Node
<
E
>(
e
,
l
,
null
)
;
node
.
prev
=
l
;
last
=
x
;
last
=
node
;
if
(
first
==
null
)
if
(
first
==
null
)
first
=
x
;
first
=
node
;
else
else
l
.
next
=
x
;
l
.
next
=
node
;
++
count
;
++
count
;
notEmpty
.
signal
();
notEmpty
.
signal
();
return
true
;
return
true
;
...
@@ -339,10 +337,11 @@ public class LinkedBlockingDeque<E>
...
@@ -339,10 +337,11 @@ public class LinkedBlockingDeque<E>
*/
*/
public
boolean
offerFirst
(
E
e
)
{
public
boolean
offerFirst
(
E
e
)
{
if
(
e
==
null
)
throw
new
NullPointerException
();
if
(
e
==
null
)
throw
new
NullPointerException
();
Node
<
E
>
node
=
new
Node
<
E
>(
e
);
final
ReentrantLock
lock
=
this
.
lock
;
final
ReentrantLock
lock
=
this
.
lock
;
lock
.
lock
();
lock
.
lock
();
try
{
try
{
return
linkFirst
(
e
);
return
linkFirst
(
nod
e
);
}
finally
{
}
finally
{
lock
.
unlock
();
lock
.
unlock
();
}
}
...
@@ -353,10 +352,11 @@ public class LinkedBlockingDeque<E>
...
@@ -353,10 +352,11 @@ public class LinkedBlockingDeque<E>
*/
*/
public
boolean
offerLast
(
E
e
)
{
public
boolean
offerLast
(
E
e
)
{
if
(
e
==
null
)
throw
new
NullPointerException
();
if
(
e
==
null
)
throw
new
NullPointerException
();
Node
<
E
>
node
=
new
Node
<
E
>(
e
);
final
ReentrantLock
lock
=
this
.
lock
;
final
ReentrantLock
lock
=
this
.
lock
;
lock
.
lock
();
lock
.
lock
();
try
{
try
{
return
linkLast
(
e
);
return
linkLast
(
nod
e
);
}
finally
{
}
finally
{
lock
.
unlock
();
lock
.
unlock
();
}
}
...
@@ -368,10 +368,11 @@ public class LinkedBlockingDeque<E>
...
@@ -368,10 +368,11 @@ public class LinkedBlockingDeque<E>
*/
*/
public
void
putFirst
(
E
e
)
throws
InterruptedException
{
public
void
putFirst
(
E
e
)
throws
InterruptedException
{
if
(
e
==
null
)
throw
new
NullPointerException
();
if
(
e
==
null
)
throw
new
NullPointerException
();
Node
<
E
>
node
=
new
Node
<
E
>(
e
);
final
ReentrantLock
lock
=
this
.
lock
;
final
ReentrantLock
lock
=
this
.
lock
;
lock
.
lock
();
lock
.
lock
();
try
{
try
{
while
(!
linkFirst
(
e
))
while
(!
linkFirst
(
nod
e
))
notFull
.
await
();
notFull
.
await
();
}
finally
{
}
finally
{
lock
.
unlock
();
lock
.
unlock
();
...
@@ -384,10 +385,11 @@ public class LinkedBlockingDeque<E>
...
@@ -384,10 +385,11 @@ public class LinkedBlockingDeque<E>
*/
*/
public
void
putLast
(
E
e
)
throws
InterruptedException
{
public
void
putLast
(
E
e
)
throws
InterruptedException
{
if
(
e
==
null
)
throw
new
NullPointerException
();
if
(
e
==
null
)
throw
new
NullPointerException
();
Node
<
E
>
node
=
new
Node
<
E
>(
e
);
final
ReentrantLock
lock
=
this
.
lock
;
final
ReentrantLock
lock
=
this
.
lock
;
lock
.
lock
();
lock
.
lock
();
try
{
try
{
while
(!
linkLast
(
e
))
while
(!
linkLast
(
nod
e
))
notFull
.
await
();
notFull
.
await
();
}
finally
{
}
finally
{
lock
.
unlock
();
lock
.
unlock
();
...
@@ -401,11 +403,12 @@ public class LinkedBlockingDeque<E>
...
@@ -401,11 +403,12 @@ public class LinkedBlockingDeque<E>
public
boolean
offerFirst
(
E
e
,
long
timeout
,
TimeUnit
unit
)
public
boolean
offerFirst
(
E
e
,
long
timeout
,
TimeUnit
unit
)
throws
InterruptedException
{
throws
InterruptedException
{
if
(
e
==
null
)
throw
new
NullPointerException
();
if
(
e
==
null
)
throw
new
NullPointerException
();
Node
<
E
>
node
=
new
Node
<
E
>(
e
);
long
nanos
=
unit
.
toNanos
(
timeout
);
long
nanos
=
unit
.
toNanos
(
timeout
);
final
ReentrantLock
lock
=
this
.
lock
;
final
ReentrantLock
lock
=
this
.
lock
;
lock
.
lockInterruptibly
();
lock
.
lockInterruptibly
();
try
{
try
{
while
(!
linkFirst
(
e
))
{
while
(!
linkFirst
(
nod
e
))
{
if
(
nanos
<=
0
)
if
(
nanos
<=
0
)
return
false
;
return
false
;
nanos
=
notFull
.
awaitNanos
(
nanos
);
nanos
=
notFull
.
awaitNanos
(
nanos
);
...
@@ -423,11 +426,12 @@ public class LinkedBlockingDeque<E>
...
@@ -423,11 +426,12 @@ public class LinkedBlockingDeque<E>
public
boolean
offerLast
(
E
e
,
long
timeout
,
TimeUnit
unit
)
public
boolean
offerLast
(
E
e
,
long
timeout
,
TimeUnit
unit
)
throws
InterruptedException
{
throws
InterruptedException
{
if
(
e
==
null
)
throw
new
NullPointerException
();
if
(
e
==
null
)
throw
new
NullPointerException
();
Node
<
E
>
node
=
new
Node
<
E
>(
e
);
long
nanos
=
unit
.
toNanos
(
timeout
);
long
nanos
=
unit
.
toNanos
(
timeout
);
final
ReentrantLock
lock
=
this
.
lock
;
final
ReentrantLock
lock
=
this
.
lock
;
lock
.
lockInterruptibly
();
lock
.
lockInterruptibly
();
try
{
try
{
while
(!
linkLast
(
e
))
{
while
(!
linkLast
(
nod
e
))
{
if
(
nanos
<=
0
)
if
(
nanos
<=
0
)
return
false
;
return
false
;
nanos
=
notFull
.
awaitNanos
(
nanos
);
nanos
=
notFull
.
awaitNanos
(
nanos
);
...
@@ -955,7 +959,20 @@ public class LinkedBlockingDeque<E>
...
@@ -955,7 +959,20 @@ public class LinkedBlockingDeque<E>
final
ReentrantLock
lock
=
this
.
lock
;
final
ReentrantLock
lock
=
this
.
lock
;
lock
.
lock
();
lock
.
lock
();
try
{
try
{
return
super
.
toString
();
Node
<
E
>
p
=
first
;
if
(
p
==
null
)
return
"[]"
;
StringBuilder
sb
=
new
StringBuilder
();
sb
.
append
(
'['
);
for
(;;)
{
E
e
=
p
.
item
;
sb
.
append
(
e
==
this
?
"(this Collection)"
:
e
);
p
=
p
.
next
;
if
(
p
==
null
)
return
sb
.
append
(
']'
).
toString
();
sb
.
append
(
','
).
append
(
' '
);
}
}
finally
{
}
finally
{
lock
.
unlock
();
lock
.
unlock
();
}
}
...
@@ -1053,6 +1070,26 @@ public class LinkedBlockingDeque<E>
...
@@ -1053,6 +1070,26 @@ public class LinkedBlockingDeque<E>
}
}
}
}
/**
* Returns the successor node of the given non-null, but
* possibly previously deleted, node.
*/
private
Node
<
E
>
succ
(
Node
<
E
>
n
)
{
// Chains of deleted nodes ending in null or self-links
// are possible if multiple interior nodes are removed.
for
(;;)
{
Node
<
E
>
s
=
nextNode
(
n
);
if
(
s
==
null
)
return
null
;
else
if
(
s
.
item
!=
null
)
return
s
;
else
if
(
s
==
n
)
return
firstNode
();
else
n
=
s
;
}
}
/**
/**
* Advances next.
* Advances next.
*/
*/
...
@@ -1061,16 +1098,7 @@ public class LinkedBlockingDeque<E>
...
@@ -1061,16 +1098,7 @@ public class LinkedBlockingDeque<E>
lock
.
lock
();
lock
.
lock
();
try
{
try
{
// assert next != null;
// assert next != null;
Node
<
E
>
s
=
nextNode
(
next
);
next
=
succ
(
next
);
if
(
s
==
next
)
{
next
=
firstNode
();
}
else
{
// Skip over removed nodes.
// May be necessary if multiple interior Nodes are removed.
while
(
s
!=
null
&&
s
.
item
==
null
)
s
=
nextNode
(
s
);
next
=
s
;
}
nextItem
=
(
next
==
null
)
?
null
:
next
.
item
;
nextItem
=
(
next
==
null
)
?
null
:
next
.
item
;
}
finally
{
}
finally
{
lock
.
unlock
();
lock
.
unlock
();
...
...
test/java/util/concurrent/ConcurrentQueues/IteratorWeakConsistency.java
浏览文件 @
d33bc88e
...
@@ -56,23 +56,44 @@ public class IteratorWeakConsistency {
...
@@ -56,23 +56,44 @@ public class IteratorWeakConsistency {
// test(new ArrayBlockingQueue(20));
// test(new ArrayBlockingQueue(20));
}
}
void
test
(
Queue
q
)
throws
Throwable
{
void
test
(
Queue
q
)
{
// TODO: make this more general
// TODO: make this more general
for
(
int
i
=
0
;
i
<
10
;
i
++)
try
{
q
.
add
(
i
);
for
(
int
i
=
0
;
i
<
10
;
i
++)
Iterator
it
=
q
.
iterator
();
q
.
add
(
i
);
q
.
poll
();
Iterator
it
=
q
.
iterator
();
q
.
poll
();
q
.
poll
();
q
.
poll
();
q
.
poll
();
q
.
remove
(
7
);
q
.
poll
();
List
list
=
new
ArrayList
();
q
.
remove
(
7
);
while
(
it
.
hasNext
())
List
list
=
new
ArrayList
();
list
.
add
(
it
.
next
());
while
(
it
.
hasNext
())
equal
(
list
,
Arrays
.
asList
(
0
,
3
,
4
,
5
,
6
,
8
,
9
));
list
.
add
(
it
.
next
());
check
(!
list
.
contains
(
null
));
equal
(
list
,
Arrays
.
asList
(
0
,
3
,
4
,
5
,
6
,
8
,
9
));
System
.
out
.
printf
(
"%s: %s%n"
,
check
(!
list
.
contains
(
null
));
q
.
getClass
().
getSimpleName
(),
System
.
out
.
printf
(
"%s: %s%n"
,
list
);
q
.
getClass
().
getSimpleName
(),
list
);
}
catch
(
Throwable
t
)
{
unexpected
(
t
);
}
try
{
q
.
clear
();
q
.
add
(
1
);
q
.
add
(
2
);
q
.
add
(
3
);
q
.
add
(
4
);
Iterator
it
=
q
.
iterator
();
it
.
next
();
q
.
remove
(
2
);
q
.
remove
(
1
);
q
.
remove
(
3
);
boolean
found4
=
false
;
while
(
it
.
hasNext
())
{
found4
|=
it
.
next
().
equals
(
4
);
}
check
(
found4
);
}
catch
(
Throwable
t
)
{
unexpected
(
t
);
}
}
}
//--------------------- Infrastructure ---------------------------
//--------------------- Infrastructure ---------------------------
...
@@ -85,7 +106,6 @@ public class IteratorWeakConsistency {
...
@@ -85,7 +106,6 @@ public class IteratorWeakConsistency {
void
equal
(
Object
x
,
Object
y
)
{
void
equal
(
Object
x
,
Object
y
)
{
if
(
x
==
null
?
y
==
null
:
x
.
equals
(
y
))
pass
();
if
(
x
==
null
?
y
==
null
:
x
.
equals
(
y
))
pass
();
else
fail
(
x
+
" not equal to "
+
y
);}
else
fail
(
x
+
" not equal to "
+
y
);}
static
Class
<?>
thisClass
=
new
Object
(){}.
getClass
().
getEnclosingClass
();
public
static
void
main
(
String
[]
args
)
throws
Throwable
{
public
static
void
main
(
String
[]
args
)
throws
Throwable
{
new
IteratorWeakConsistency
().
instanceMain
(
args
);}
new
IteratorWeakConsistency
().
instanceMain
(
args
);}
public
void
instanceMain
(
String
[]
args
)
throws
Throwable
{
public
void
instanceMain
(
String
[]
args
)
throws
Throwable
{
...
...
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录