Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
openanolis
dragonwell8_langtools
提交
da351bac
D
dragonwell8_langtools
项目概览
openanolis
/
dragonwell8_langtools
通知
0
Star
2
Fork
0
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
D
dragonwell8_langtools
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
提交
Issue看板
提交
da351bac
编写于
7月 01, 2015
作者:
A
asaha
浏览文件
操作
浏览文件
下载
差异文件
Merge
上级
8128757a
c09806f2
变更
4
隐藏空白更改
内联
并排
Showing
4 changed file
with
283 addition
and
431 deletion
+283
-431
.hgtags
.hgtags
+1
-0
THIRD_PARTY_README
THIRD_PARTY_README
+4
-35
src/share/classes/com/sun/tools/javac/comp/Flow.java
src/share/classes/com/sun/tools/javac/comp/Flow.java
+277
-381
src/share/classes/com/sun/tools/javac/util/Bits.java
src/share/classes/com/sun/tools/javac/util/Bits.java
+1
-15
未找到文件。
.hgtags
浏览文件 @
da351bac
...
@@ -440,3 +440,4 @@ e7e42c79861ea1ab7495de5f238c01f98035a8a8 jdk8u60-b18
...
@@ -440,3 +440,4 @@ e7e42c79861ea1ab7495de5f238c01f98035a8a8 jdk8u60-b18
0366d7f1faa12ed35694571c151524e0847f05ff jdk8u60-b19
0366d7f1faa12ed35694571c151524e0847f05ff jdk8u60-b19
976523f1d5626bdb6dd47883e2734614b64a5e61 jdk8u60-b20
976523f1d5626bdb6dd47883e2734614b64a5e61 jdk8u60-b20
97328f3e2aa2c713931edf471270a1208980b963 jdk8u60-b21
97328f3e2aa2c713931edf471270a1208980b963 jdk8u60-b21
d1febf79ce5ea41fb4b818ffd3589cf923e6de5f jdk8u60-b22
THIRD_PARTY_README
浏览文件 @
da351bac
...
@@ -1140,37 +1140,6 @@ included with JRE 8, JDK 8, and OpenJDK 8.
...
@@ -1140,37 +1140,6 @@ included with JRE 8, JDK 8, and OpenJDK 8.
--------------------------------------------------------------------------------
--------------------------------------------------------------------------------
%% This notice is provided with respect to JSON, which may be included
with JRE 8 & JDK 8.
--- begin of LICENSE ---
Copyright (c) 2002 JSON.org
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
The Software shall be used for Good, not Evil.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
--- end of LICENSE ---
-------------------------------------------------------------------------------
%% This notice is provided with respect to Kerberos functionality, which
%% This notice is provided with respect to Kerberos functionality, which
which may be included with JRE 8, JDK 8, and OpenJDK 8.
which may be included with JRE 8, JDK 8, and OpenJDK 8.
...
@@ -1250,7 +1219,7 @@ included with JDK 8 and OpenJDK 8 source distributions.
...
@@ -1250,7 +1219,7 @@ included with JDK 8 and OpenJDK 8 source distributions.
-------------------------------------------------------------------------------
-------------------------------------------------------------------------------
%% This notice is provided with respect to libpng 1.6.16, which may be
%% This notice is provided with respect to libpng 1.6.16, which may be
included with JRE 8, JDK 8, and OpenJDK 8.
included with JRE 8, JDK 8, and OpenJDK 8.
--- begin of LICENSE ---
--- begin of LICENSE ---
...
@@ -1370,7 +1339,7 @@ December 22, 2014
...
@@ -1370,7 +1339,7 @@ December 22, 2014
-------------------------------------------------------------------------------
-------------------------------------------------------------------------------
%% This notice is provided with respect to libungif 4.1.3, which may be
%% This notice is provided with respect to
GIFLIB 5.1.1 &
libungif 4.1.3, which may be
included with JRE 8, JDK 8, and OpenJDK 8.
included with JRE 8, JDK 8, and OpenJDK 8.
--- begin of LICENSE ---
--- begin of LICENSE ---
...
@@ -1399,13 +1368,13 @@ THE SOFTWARE.
...
@@ -1399,13 +1368,13 @@ THE SOFTWARE.
-------------------------------------------------------------------------------
-------------------------------------------------------------------------------
%% This notice is provided with respect to Little CMS 2.
5
, which may be
%% This notice is provided with respect to Little CMS 2.
7
, which may be
included with JRE 8, JDK 8, and OpenJDK 8.
included with JRE 8, JDK 8, and OpenJDK 8.
--- begin of LICENSE ---
--- begin of LICENSE ---
Little CMS
Little CMS
Copyright (c) 1998-201
1
Marti Maria Saguer
Copyright (c) 1998-201
5
Marti Maria Saguer
Permission is hereby granted, free of charge, to any person obtaining a copy
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
of this software and associated documentation files (the "Software"), to deal
...
...
src/share/classes/com/sun/tools/javac/comp/Flow.java
浏览文件 @
da351bac
/*
/*
* Copyright (c) 1999, 201
4
, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 1999, 201
5
, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
*
* This code is free software; you can redistribute it and/or modify it
* This code is free software; you can redistribute it and/or modify it
...
@@ -353,17 +353,17 @@ public class Flow {
...
@@ -353,17 +353,17 @@ public class Flow {
this
.
tree
=
tree
;
this
.
tree
=
tree
;
}
}
void
resolveJump
(
JCTree
tree
)
{
void
resolveJump
()
{
//do nothing
//do nothing
}
}
}
}
abstract
void
markDead
(
JCTree
tree
);
abstract
void
markDead
();
/** Record an outward transfer of control. */
/** Record an outward transfer of control. */
void
recordExit
(
JCTree
tree
,
P
pe
)
{
void
recordExit
(
P
pe
)
{
pendingExits
.
append
(
pe
);
pendingExits
.
append
(
pe
);
markDead
(
tree
);
markDead
();
}
}
/** Resolve all jumps of this statement. */
/** Resolve all jumps of this statement. */
...
@@ -377,7 +377,7 @@ public class Flow {
...
@@ -377,7 +377,7 @@ public class Flow {
P
exit
=
exits
.
head
;
P
exit
=
exits
.
head
;
if
(
exit
.
tree
.
hasTag
(
jk
.
treeTag
)
&&
if
(
exit
.
tree
.
hasTag
(
jk
.
treeTag
)
&&
jk
.
getTarget
(
exit
.
tree
)
==
tree
)
{
jk
.
getTarget
(
exit
.
tree
)
==
tree
)
{
exit
.
resolveJump
(
tree
);
exit
.
resolveJump
();
resolved
=
true
;
resolved
=
true
;
}
else
{
}
else
{
pendingExits
.
append
(
exit
);
pendingExits
.
append
(
exit
);
...
@@ -420,7 +420,7 @@ public class Flow {
...
@@ -420,7 +420,7 @@ public class Flow {
private
boolean
alive
;
private
boolean
alive
;
@Override
@Override
void
markDead
(
JCTree
tree
)
{
void
markDead
()
{
alive
=
false
;
alive
=
false
;
}
}
...
@@ -464,7 +464,7 @@ public class Flow {
...
@@ -464,7 +464,7 @@ public class Flow {
ListBuffer
<
PendingExit
>
pendingExitsPrev
=
pendingExits
;
ListBuffer
<
PendingExit
>
pendingExitsPrev
=
pendingExits
;
Lint
lintPrev
=
lint
;
Lint
lintPrev
=
lint
;
pendingExits
=
new
ListBuffer
<
PendingExit
>();
pendingExits
=
new
ListBuffer
<>();
lint
=
lint
.
augment
(
tree
.
sym
);
lint
=
lint
.
augment
(
tree
.
sym
);
try
{
try
{
...
@@ -513,7 +513,7 @@ public class Flow {
...
@@ -513,7 +513,7 @@ public class Flow {
log
.
error
(
TreeInfo
.
diagEndPos
(
tree
.
body
),
"missing.ret.stmt"
);
log
.
error
(
TreeInfo
.
diagEndPos
(
tree
.
body
),
"missing.ret.stmt"
);
List
<
PendingExit
>
exits
=
pendingExits
.
toList
();
List
<
PendingExit
>
exits
=
pendingExits
.
toList
();
pendingExits
=
new
ListBuffer
<
PendingExit
>();
pendingExits
=
new
ListBuffer
<>();
while
(
exits
.
nonEmpty
())
{
while
(
exits
.
nonEmpty
())
{
PendingExit
exit
=
exits
.
head
;
PendingExit
exit
=
exits
.
head
;
exits
=
exits
.
tail
;
exits
=
exits
.
tail
;
...
@@ -542,7 +542,7 @@ public class Flow {
...
@@ -542,7 +542,7 @@ public class Flow {
public
void
visitDoLoop
(
JCDoWhileLoop
tree
)
{
public
void
visitDoLoop
(
JCDoWhileLoop
tree
)
{
ListBuffer
<
PendingExit
>
prevPendingExits
=
pendingExits
;
ListBuffer
<
PendingExit
>
prevPendingExits
=
pendingExits
;
pendingExits
=
new
ListBuffer
<
PendingExit
>();
pendingExits
=
new
ListBuffer
<>();
scanStat
(
tree
.
body
);
scanStat
(
tree
.
body
);
alive
|=
resolveContinues
(
tree
);
alive
|=
resolveContinues
(
tree
);
scan
(
tree
.
cond
);
scan
(
tree
.
cond
);
...
@@ -552,7 +552,7 @@ public class Flow {
...
@@ -552,7 +552,7 @@ public class Flow {
public
void
visitWhileLoop
(
JCWhileLoop
tree
)
{
public
void
visitWhileLoop
(
JCWhileLoop
tree
)
{
ListBuffer
<
PendingExit
>
prevPendingExits
=
pendingExits
;
ListBuffer
<
PendingExit
>
prevPendingExits
=
pendingExits
;
pendingExits
=
new
ListBuffer
<
PendingExit
>();
pendingExits
=
new
ListBuffer
<>();
scan
(
tree
.
cond
);
scan
(
tree
.
cond
);
alive
=
!
tree
.
cond
.
type
.
isFalse
();
alive
=
!
tree
.
cond
.
type
.
isFalse
();
scanStat
(
tree
.
body
);
scanStat
(
tree
.
body
);
...
@@ -564,7 +564,7 @@ public class Flow {
...
@@ -564,7 +564,7 @@ public class Flow {
public
void
visitForLoop
(
JCForLoop
tree
)
{
public
void
visitForLoop
(
JCForLoop
tree
)
{
ListBuffer
<
PendingExit
>
prevPendingExits
=
pendingExits
;
ListBuffer
<
PendingExit
>
prevPendingExits
=
pendingExits
;
scanStats
(
tree
.
init
);
scanStats
(
tree
.
init
);
pendingExits
=
new
ListBuffer
<
PendingExit
>();
pendingExits
=
new
ListBuffer
<>();
if
(
tree
.
cond
!=
null
)
{
if
(
tree
.
cond
!=
null
)
{
scan
(
tree
.
cond
);
scan
(
tree
.
cond
);
alive
=
!
tree
.
cond
.
type
.
isFalse
();
alive
=
!
tree
.
cond
.
type
.
isFalse
();
...
@@ -582,7 +582,7 @@ public class Flow {
...
@@ -582,7 +582,7 @@ public class Flow {
visitVarDef
(
tree
.
var
);
visitVarDef
(
tree
.
var
);
ListBuffer
<
PendingExit
>
prevPendingExits
=
pendingExits
;
ListBuffer
<
PendingExit
>
prevPendingExits
=
pendingExits
;
scan
(
tree
.
expr
);
scan
(
tree
.
expr
);
pendingExits
=
new
ListBuffer
<
PendingExit
>();
pendingExits
=
new
ListBuffer
<>();
scanStat
(
tree
.
body
);
scanStat
(
tree
.
body
);
alive
|=
resolveContinues
(
tree
);
alive
|=
resolveContinues
(
tree
);
resolveBreaks
(
tree
,
prevPendingExits
);
resolveBreaks
(
tree
,
prevPendingExits
);
...
@@ -591,14 +591,14 @@ public class Flow {
...
@@ -591,14 +591,14 @@ public class Flow {
public
void
visitLabelled
(
JCLabeledStatement
tree
)
{
public
void
visitLabelled
(
JCLabeledStatement
tree
)
{
ListBuffer
<
PendingExit
>
prevPendingExits
=
pendingExits
;
ListBuffer
<
PendingExit
>
prevPendingExits
=
pendingExits
;
pendingExits
=
new
ListBuffer
<
PendingExit
>();
pendingExits
=
new
ListBuffer
<>();
scanStat
(
tree
.
body
);
scanStat
(
tree
.
body
);
alive
|=
resolveBreaks
(
tree
,
prevPendingExits
);
alive
|=
resolveBreaks
(
tree
,
prevPendingExits
);
}
}
public
void
visitSwitch
(
JCSwitch
tree
)
{
public
void
visitSwitch
(
JCSwitch
tree
)
{
ListBuffer
<
PendingExit
>
prevPendingExits
=
pendingExits
;
ListBuffer
<
PendingExit
>
prevPendingExits
=
pendingExits
;
pendingExits
=
new
ListBuffer
<
PendingExit
>();
pendingExits
=
new
ListBuffer
<>();
scan
(
tree
.
selector
);
scan
(
tree
.
selector
);
boolean
hasDefault
=
false
;
boolean
hasDefault
=
false
;
for
(
List
<
JCCase
>
l
=
tree
.
cases
;
l
.
nonEmpty
();
l
=
l
.
tail
)
{
for
(
List
<
JCCase
>
l
=
tree
.
cases
;
l
.
nonEmpty
();
l
=
l
.
tail
)
{
...
@@ -625,7 +625,7 @@ public class Flow {
...
@@ -625,7 +625,7 @@ public class Flow {
public
void
visitTry
(
JCTry
tree
)
{
public
void
visitTry
(
JCTry
tree
)
{
ListBuffer
<
PendingExit
>
prevPendingExits
=
pendingExits
;
ListBuffer
<
PendingExit
>
prevPendingExits
=
pendingExits
;
pendingExits
=
new
ListBuffer
<
PendingExit
>();
pendingExits
=
new
ListBuffer
<>();
for
(
JCTree
resource
:
tree
.
resources
)
{
for
(
JCTree
resource
:
tree
.
resources
)
{
if
(
resource
instanceof
JCVariableDecl
)
{
if
(
resource
instanceof
JCVariableDecl
)
{
JCVariableDecl
vdecl
=
(
JCVariableDecl
)
resource
;
JCVariableDecl
vdecl
=
(
JCVariableDecl
)
resource
;
...
@@ -688,21 +688,21 @@ public class Flow {
...
@@ -688,21 +688,21 @@ public class Flow {
}
}
public
void
visitBreak
(
JCBreak
tree
)
{
public
void
visitBreak
(
JCBreak
tree
)
{
recordExit
(
tree
,
new
PendingExit
(
tree
));
recordExit
(
new
PendingExit
(
tree
));
}
}
public
void
visitContinue
(
JCContinue
tree
)
{
public
void
visitContinue
(
JCContinue
tree
)
{
recordExit
(
tree
,
new
PendingExit
(
tree
));
recordExit
(
new
PendingExit
(
tree
));
}
}
public
void
visitReturn
(
JCReturn
tree
)
{
public
void
visitReturn
(
JCReturn
tree
)
{
scan
(
tree
.
expr
);
scan
(
tree
.
expr
);
recordExit
(
tree
,
new
PendingExit
(
tree
));
recordExit
(
new
PendingExit
(
tree
));
}
}
public
void
visitThrow
(
JCThrow
tree
)
{
public
void
visitThrow
(
JCThrow
tree
)
{
scan
(
tree
.
expr
);
scan
(
tree
.
expr
);
markDead
(
tree
);
markDead
();
}
}
public
void
visitApply
(
JCMethodInvocation
tree
)
{
public
void
visitApply
(
JCMethodInvocation
tree
)
{
...
@@ -756,7 +756,7 @@ public class Flow {
...
@@ -756,7 +756,7 @@ public class Flow {
try
{
try
{
attrEnv
=
env
;
attrEnv
=
env
;
Flow
.
this
.
make
=
make
;
Flow
.
this
.
make
=
make
;
pendingExits
=
new
ListBuffer
<
PendingExit
>();
pendingExits
=
new
ListBuffer
<>();
alive
=
true
;
alive
=
true
;
scan
(
tree
);
scan
(
tree
);
}
finally
{
}
finally
{
...
@@ -803,7 +803,7 @@ public class Flow {
...
@@ -803,7 +803,7 @@ public class Flow {
}
}
@Override
@Override
void
markDead
(
JCTree
tree
)
{
void
markDead
()
{
//do nothing
//do nothing
}
}
...
@@ -1201,16 +1201,16 @@ public class Flow {
...
@@ -1201,16 +1201,16 @@ public class Flow {
}
}
public
void
visitBreak
(
JCBreak
tree
)
{
public
void
visitBreak
(
JCBreak
tree
)
{
recordExit
(
tree
,
new
FlowPendingExit
(
tree
,
null
));
recordExit
(
new
FlowPendingExit
(
tree
,
null
));
}
}
public
void
visitContinue
(
JCContinue
tree
)
{
public
void
visitContinue
(
JCContinue
tree
)
{
recordExit
(
tree
,
new
FlowPendingExit
(
tree
,
null
));
recordExit
(
new
FlowPendingExit
(
tree
,
null
));
}
}
public
void
visitReturn
(
JCReturn
tree
)
{
public
void
visitReturn
(
JCReturn
tree
)
{
scan
(
tree
.
expr
);
scan
(
tree
.
expr
);
recordExit
(
tree
,
new
FlowPendingExit
(
tree
,
null
));
recordExit
(
new
FlowPendingExit
(
tree
,
null
));
}
}
public
void
visitThrow
(
JCThrow
tree
)
{
public
void
visitThrow
(
JCThrow
tree
)
{
...
@@ -1228,7 +1228,7 @@ public class Flow {
...
@@ -1228,7 +1228,7 @@ public class Flow {
else
{
else
{
markThrown
(
tree
,
tree
.
expr
.
type
);
markThrown
(
tree
,
tree
.
expr
.
type
);
}
}
markDead
(
tree
);
markDead
();
}
}
public
void
visitApply
(
JCMethodInvocation
tree
)
{
public
void
visitApply
(
JCMethodInvocation
tree
)
{
...
@@ -1379,12 +1379,10 @@ public class Flow {
...
@@ -1379,12 +1379,10 @@ public class Flow {
* effectively-final local variables/parameters.
* effectively-final local variables/parameters.
*/
*/
public
abstract
class
AbstractAssignAnalyzer
<
P
extends
AbstractAssignAnalyzer
<
P
>.
AbstractAssignPendingExit
>
public
class
AssignAnalyzer
extends
BaseAnalyzer
<
AssignAnalyzer
.
AssignPendingExit
>
{
extends
BaseAnalyzer
<
P
>
{
/** The set of definitely assigned variables.
/** The set of definitely assigned variables.
*/
*/
protected
Bits
inits
;
final
Bits
inits
;
/** The set of definitely unassigned variables.
/** The set of definitely unassigned variables.
*/
*/
...
@@ -1432,20 +1430,20 @@ public class Flow {
...
@@ -1432,20 +1430,20 @@ public class Flow {
*/
*/
Scope
unrefdResources
;
Scope
unrefdResources
;
/**
Set
when processing a loop body the second time for DU analysis. */
/**
Modified
when processing a loop body the second time for DU analysis. */
FlowKind
flowKind
=
FlowKind
.
NORMAL
;
FlowKind
flowKind
=
FlowKind
.
NORMAL
;
/** The starting position of the analy
s
ed tree */
/** The starting position of the analy
z
ed tree */
int
startPos
;
int
startPos
;
public
class
A
bstractA
ssignPendingExit
extends
BaseAnalyzer
.
PendingExit
{
public
class
AssignPendingExit
extends
BaseAnalyzer
.
PendingExit
{
final
Bits
inits
;
final
Bits
inits
;
final
Bits
uninits
;
final
Bits
uninits
;
final
Bits
exit_inits
=
new
Bits
(
true
);
final
Bits
exit_inits
=
new
Bits
(
true
);
final
Bits
exit_uninits
=
new
Bits
(
true
);
final
Bits
exit_uninits
=
new
Bits
(
true
);
public
A
bstractA
ssignPendingExit
(
JCTree
tree
,
final
Bits
inits
,
final
Bits
uninits
)
{
public
AssignPendingExit
(
JCTree
tree
,
final
Bits
inits
,
final
Bits
uninits
)
{
super
(
tree
);
super
(
tree
);
this
.
inits
=
inits
;
this
.
inits
=
inits
;
this
.
uninits
=
uninits
;
this
.
uninits
=
uninits
;
...
@@ -1454,13 +1452,13 @@ public class Flow {
...
@@ -1454,13 +1452,13 @@ public class Flow {
}
}
@Override
@Override
public
void
resolveJump
(
JCTree
tree
)
{
void
resolveJump
(
)
{
inits
.
andSet
(
exit_inits
);
inits
.
andSet
(
exit_inits
);
uninits
.
andSet
(
exit_uninits
);
uninits
.
andSet
(
exit_uninits
);
}
}
}
}
public
A
bstractA
ssignAnalyzer
()
{
public
AssignAnalyzer
()
{
this
.
inits
=
new
Bits
();
this
.
inits
=
new
Bits
();
uninits
=
new
Bits
();
uninits
=
new
Bits
();
uninitsTry
=
new
Bits
();
uninitsTry
=
new
Bits
();
...
@@ -1473,7 +1471,7 @@ public class Flow {
...
@@ -1473,7 +1471,7 @@ public class Flow {
private
boolean
isInitialConstructor
=
false
;
private
boolean
isInitialConstructor
=
false
;
@Override
@Override
protected
void
markDead
(
JCTree
tree
)
{
void
markDead
(
)
{
if
(!
isInitialConstructor
)
{
if
(!
isInitialConstructor
)
{
inits
.
inclRange
(
returnadr
,
nextadr
);
inits
.
inclRange
(
returnadr
,
nextadr
);
}
else
{
}
else
{
...
@@ -1520,35 +1518,41 @@ public class Flow {
...
@@ -1520,35 +1518,41 @@ public class Flow {
}
}
sym
.
adr
=
nextadr
;
sym
.
adr
=
nextadr
;
vardecls
[
nextadr
]
=
varDecl
;
vardecls
[
nextadr
]
=
varDecl
;
exclVarFromInits
(
varDecl
,
nextadr
);
inits
.
excl
(
nextadr
);
uninits
.
incl
(
nextadr
);
uninits
.
incl
(
nextadr
);
nextadr
++;
nextadr
++;
}
}
protected
void
exclVarFromInits
(
JCTree
tree
,
int
adr
)
{
inits
.
excl
(
adr
);
}
protected
void
assignToInits
(
JCTree
tree
,
Bits
bits
)
{
inits
.
assign
(
bits
);
}
protected
void
andSetInits
(
JCTree
tree
,
Bits
bits
)
{
inits
.
andSet
(
bits
);
}
protected
void
orSetInits
(
JCTree
tree
,
Bits
bits
)
{
inits
.
orSet
(
bits
);
}
/** Record an initialization of a trackable variable.
/** Record an initialization of a trackable variable.
*/
*/
void
letInit
(
DiagnosticPosition
pos
,
VarSymbol
sym
)
{
void
letInit
(
DiagnosticPosition
pos
,
VarSymbol
sym
)
{
if
(
sym
.
adr
>=
firstadr
&&
trackable
(
sym
))
{
if
(
sym
.
adr
>=
firstadr
&&
trackable
(
sym
))
{
if
(
uninits
.
isMember
(
sym
.
adr
))
{
if
((
sym
.
flags
()
&
EFFECTIVELY_FINAL
)
!=
0
)
{
uninit
(
sym
);
if
(!
uninits
.
isMember
(
sym
.
adr
))
{
//assignment targeting an effectively final variable
//makes the variable lose its status of effectively final
//if the variable is _not_ definitively unassigned
sym
.
flags_field
&=
~
EFFECTIVELY_FINAL
;
}
else
{
uninit
(
sym
);
}
}
else
if
((
sym
.
flags
()
&
FINAL
)
!=
0
)
{
if
((
sym
.
flags
()
&
PARAMETER
)
!=
0
)
{
if
((
sym
.
flags
()
&
UNION
)
!=
0
)
{
//multi-catch parameter
log
.
error
(
pos
,
"multicatch.parameter.may.not.be.assigned"
,
sym
);
}
else
{
log
.
error
(
pos
,
"final.parameter.may.not.be.assigned"
,
sym
);
}
}
else
if
(!
uninits
.
isMember
(
sym
.
adr
))
{
log
.
error
(
pos
,
flowKind
.
errKey
,
sym
);
}
else
{
uninit
(
sym
);
}
}
}
inits
.
incl
(
sym
.
adr
);
inits
.
incl
(
sym
.
adr
);
}
else
if
((
sym
.
flags
()
&
FINAL
)
!=
0
)
{
log
.
error
(
pos
,
"var.might.already.be.assigned"
,
sym
);
}
}
}
}
//where
//where
...
@@ -1583,7 +1587,14 @@ public class Flow {
...
@@ -1583,7 +1587,14 @@ public class Flow {
checkInit
(
pos
,
sym
,
"var.might.not.have.been.initialized"
);
checkInit
(
pos
,
sym
,
"var.might.not.have.been.initialized"
);
}
}
void
checkInit
(
DiagnosticPosition
pos
,
VarSymbol
sym
,
String
errkey
)
{}
void
checkInit
(
DiagnosticPosition
pos
,
VarSymbol
sym
,
String
errkey
)
{
if
((
sym
.
adr
>=
firstadr
||
sym
.
owner
.
kind
!=
TYP
)
&&
trackable
(
sym
)
&&
!
inits
.
isMember
(
sym
.
adr
))
{
log
.
error
(
pos
,
errkey
,
sym
);
inits
.
incl
(
sym
.
adr
);
}
}
/** Utility method to reset several Bits instances.
/** Utility method to reset several Bits instances.
*/
*/
...
@@ -1607,7 +1618,7 @@ public class Flow {
...
@@ -1607,7 +1618,7 @@ public class Flow {
/** Merge (intersect) inits/uninits from WhenTrue/WhenFalse sets.
/** Merge (intersect) inits/uninits from WhenTrue/WhenFalse sets.
*/
*/
protected
void
merge
(
JCTree
tree
)
{
protected
void
merge
()
{
inits
.
assign
(
initsWhenFalse
.
andSet
(
initsWhenTrue
));
inits
.
assign
(
initsWhenFalse
.
andSet
(
initsWhenTrue
));
uninits
.
assign
(
uninitsWhenFalse
.
andSet
(
uninitsWhenTrue
));
uninits
.
assign
(
uninitsWhenFalse
.
andSet
(
uninitsWhenTrue
));
}
}
...
@@ -1623,7 +1634,7 @@ public class Flow {
...
@@ -1623,7 +1634,7 @@ public class Flow {
if
(
tree
!=
null
)
{
if
(
tree
!=
null
)
{
scan
(
tree
);
scan
(
tree
);
if
(
inits
.
isReset
())
{
if
(
inits
.
isReset
())
{
merge
(
tree
);
merge
();
}
}
}
}
}
}
...
@@ -1641,7 +1652,7 @@ public class Flow {
...
@@ -1641,7 +1652,7 @@ public class Flow {
*/
*/
void
scanCond
(
JCTree
tree
)
{
void
scanCond
(
JCTree
tree
)
{
if
(
tree
.
type
.
isFalse
())
{
if
(
tree
.
type
.
isFalse
())
{
if
(
inits
.
isReset
())
merge
(
tree
);
if
(
inits
.
isReset
())
merge
();
initsWhenTrue
.
assign
(
inits
);
initsWhenTrue
.
assign
(
inits
);
initsWhenTrue
.
inclRange
(
firstadr
,
nextadr
);
initsWhenTrue
.
inclRange
(
firstadr
,
nextadr
);
uninitsWhenTrue
.
assign
(
uninits
);
uninitsWhenTrue
.
assign
(
uninits
);
...
@@ -1649,7 +1660,7 @@ public class Flow {
...
@@ -1649,7 +1660,7 @@ public class Flow {
initsWhenFalse
.
assign
(
inits
);
initsWhenFalse
.
assign
(
inits
);
uninitsWhenFalse
.
assign
(
uninits
);
uninitsWhenFalse
.
assign
(
uninits
);
}
else
if
(
tree
.
type
.
isTrue
())
{
}
else
if
(
tree
.
type
.
isTrue
())
{
if
(
inits
.
isReset
())
merge
(
tree
);
if
(
inits
.
isReset
())
merge
();
initsWhenFalse
.
assign
(
inits
);
initsWhenFalse
.
assign
(
inits
);
initsWhenFalse
.
inclRange
(
firstadr
,
nextadr
);
initsWhenFalse
.
inclRange
(
firstadr
,
nextadr
);
uninitsWhenFalse
.
assign
(
uninits
);
uninitsWhenFalse
.
assign
(
uninits
);
...
@@ -1668,173 +1679,202 @@ public class Flow {
...
@@ -1668,173 +1679,202 @@ public class Flow {
/* ------------ Visitor methods for various sorts of trees -------------*/
/* ------------ Visitor methods for various sorts of trees -------------*/
@Override
public
void
visitClassDef
(
JCClassDecl
tree
)
{
public
void
visitClassDef
(
JCClassDecl
tree
)
{
if
(
tree
.
sym
==
null
)
{
if
(
tree
.
sym
==
null
)
{
return
;
return
;
}
}
JCClassDecl
classDefPrev
=
classDef
;
Lint
lintPrev
=
lint
;
int
firstadrPrev
=
firstadr
;
lint
=
lint
.
augment
(
tree
.
sym
);
int
nextadrPrev
=
nextadr
;
ListBuffer
<
P
>
pendingExitsPrev
=
pendingExits
;
pendingExits
=
new
ListBuffer
<
P
>();
if
(
tree
.
name
!=
names
.
empty
)
{
firstadr
=
nextadr
;
}
classDef
=
tree
;
try
{
try
{
// define all the static fields
if
(
tree
.
sym
==
null
)
{
for
(
List
<
JCTree
>
l
=
tree
.
defs
;
l
.
nonEmpty
();
l
=
l
.
tail
)
{
return
;
if
(
l
.
head
.
hasTag
(
VARDEF
))
{
}
JCVariableDecl
def
=
(
JCVariableDecl
)
l
.
head
;
if
((
def
.
mods
.
flags
&
STATIC
)
!=
0
)
{
JCClassDecl
classDefPrev
=
classDef
;
VarSymbol
sym
=
def
.
sym
;
int
firstadrPrev
=
firstadr
;
if
(
trackable
(
sym
))
{
int
nextadrPrev
=
nextadr
;
newVar
(
def
);
ListBuffer
<
AssignPendingExit
>
pendingExitsPrev
=
pendingExits
;
pendingExits
=
new
ListBuffer
<>();
if
(
tree
.
name
!=
names
.
empty
)
{
firstadr
=
nextadr
;
}
classDef
=
tree
;
try
{
// define all the static fields
for
(
List
<
JCTree
>
l
=
tree
.
defs
;
l
.
nonEmpty
();
l
=
l
.
tail
)
{
if
(
l
.
head
.
hasTag
(
VARDEF
))
{
JCVariableDecl
def
=
(
JCVariableDecl
)
l
.
head
;
if
((
def
.
mods
.
flags
&
STATIC
)
!=
0
)
{
VarSymbol
sym
=
def
.
sym
;
if
(
trackable
(
sym
))
{
newVar
(
def
);
}
}
}
}
}
}
}
}
// process all the static initializers
// process all the static initializers
for
(
List
<
JCTree
>
l
=
tree
.
defs
;
l
.
nonEmpty
();
l
=
l
.
tail
)
{
for
(
List
<
JCTree
>
l
=
tree
.
defs
;
l
.
nonEmpty
();
l
=
l
.
tail
)
{
if
(!
l
.
head
.
hasTag
(
METHODDEF
)
&&
if
(!
l
.
head
.
hasTag
(
METHODDEF
)
&&
(
TreeInfo
.
flags
(
l
.
head
)
&
STATIC
)
!=
0
)
{
(
TreeInfo
.
flags
(
l
.
head
)
&
STATIC
)
!=
0
)
{
scan
(
l
.
head
);
scan
(
l
.
head
);
}
}
}
}
// define all the instance fields
// define all the instance fields
for
(
List
<
JCTree
>
l
=
tree
.
defs
;
l
.
nonEmpty
();
l
=
l
.
tail
)
{
for
(
List
<
JCTree
>
l
=
tree
.
defs
;
l
.
nonEmpty
();
l
=
l
.
tail
)
{
if
(
l
.
head
.
hasTag
(
VARDEF
))
{
if
(
l
.
head
.
hasTag
(
VARDEF
))
{
JCVariableDecl
def
=
(
JCVariableDecl
)
l
.
head
;
JCVariableDecl
def
=
(
JCVariableDecl
)
l
.
head
;
if
((
def
.
mods
.
flags
&
STATIC
)
==
0
)
{
if
((
def
.
mods
.
flags
&
STATIC
)
==
0
)
{
VarSymbol
sym
=
def
.
sym
;
VarSymbol
sym
=
def
.
sym
;
if
(
trackable
(
sym
))
{
if
(
trackable
(
sym
))
{
newVar
(
def
);
newVar
(
def
);
}
}
}
}
}
}
}
}
// process all the instance initializers
for
(
List
<
JCTree
>
l
=
tree
.
defs
;
l
.
nonEmpty
();
l
=
l
.
tail
)
{
// process all the instance initializers
if
(!
l
.
head
.
hasTag
(
METHODDEF
)
&&
for
(
List
<
JCTree
>
l
=
tree
.
defs
;
l
.
nonEmpty
();
l
=
l
.
tail
)
{
(
TreeInfo
.
flags
(
l
.
head
)
&
STATIC
)
==
0
)
{
if
(!
l
.
head
.
hasTag
(
METHODDEF
)
&&
scan
(
l
.
head
);
(
TreeInfo
.
flags
(
l
.
head
)
&
STATIC
)
==
0
)
{
}
scan
(
l
.
head
);
}
}
}
// process all the methods
// process all the methods
for
(
List
<
JCTree
>
l
=
tree
.
defs
;
l
.
nonEmpty
();
l
=
l
.
tail
)
{
for
(
List
<
JCTree
>
l
=
tree
.
defs
;
l
.
nonEmpty
();
l
=
l
.
tail
)
{
if
(
l
.
head
.
hasTag
(
METHODDEF
))
{
if
(
l
.
head
.
hasTag
(
METHODDEF
))
{
scan
(
l
.
head
);
scan
(
l
.
head
);
}
}
}
}
finally
{
pendingExits
=
pendingExitsPrev
;
nextadr
=
nextadrPrev
;
firstadr
=
firstadrPrev
;
classDef
=
classDefPrev
;
}
}
}
finally
{
}
finally
{
pendingExits
=
pendingExitsPrev
;
lint
=
lintPrev
;
nextadr
=
nextadrPrev
;
firstadr
=
firstadrPrev
;
classDef
=
classDefPrev
;
}
}
}
}
@Override
public
void
visitMethodDef
(
JCMethodDecl
tree
)
{
public
void
visitMethodDef
(
JCMethodDecl
tree
)
{
if
(
tree
.
body
==
null
)
{
if
(
tree
.
body
==
null
)
{
return
;
return
;
}
}
/* Ignore synthetic methods, except for translated lambda methods.
/* MemberEnter can generate synthetic methods ignore them
*/
*/
if
((
tree
.
sym
.
flags
()
&
(
SYNTHETIC
|
LAMBDA_METHOD
))
==
SYNTHETIC
)
{
if
((
tree
.
sym
.
flags
()
&
SYNTHETIC
)
!=
0
)
{
return
;
return
;
}
}
final
Bits
initsPrev
=
new
Bits
(
inits
);
Lint
lintPrev
=
lint
;
final
Bits
uninitsPrev
=
new
Bits
(
uninits
);
lint
=
lint
.
augment
(
tree
.
sym
);
int
nextadrPrev
=
nextadr
;
int
firstadrPrev
=
firstadr
;
int
returnadrPrev
=
returnadr
;
Assert
.
check
(
pendingExits
.
isEmpty
());
boolean
lastInitialConstructor
=
isInitialConstructor
;
try
{
try
{
isInitialConstructor
=
TreeInfo
.
isInitialConstructor
(
tree
);
if
(
tree
.
body
==
null
)
{
return
;
if
(!
isInitialConstructor
)
{
firstadr
=
nextadr
;
}
}
for
(
List
<
JCVariableDecl
>
l
=
tree
.
params
;
l
.
nonEmpty
();
l
=
l
.
tail
)
{
/* Ignore synthetic methods, except for translated lambda methods.
JCVariableDecl
def
=
l
.
head
;
*/
scan
(
def
);
if
((
tree
.
sym
.
flags
()
&
(
SYNTHETIC
|
LAMBDA_METHOD
))
==
SYNTHETIC
)
{
Assert
.
check
((
def
.
sym
.
flags
()
&
PARAMETER
)
!=
0
,
"Method parameter without PARAMETER flag"
);
return
;
/* If we are executing the code from Gen, then there can be
* synthetic or mandated variables, ignore them.
*/
initParam
(
def
);
}
}
// else we are in an instance initializer block;
// leave caught unchanged.
scan
(
tree
.
body
);
if
(
isInitialConstructor
)
{
final
Bits
initsPrev
=
new
Bits
(
inits
);
boolean
isSynthesized
=
(
tree
.
sym
.
flags
()
&
final
Bits
uninitsPrev
=
new
Bits
(
uninits
);
GENERATEDCONSTR
)
!=
0
;
int
nextadrPrev
=
nextadr
;
for
(
int
i
=
firstadr
;
i
<
nextadr
;
i
++)
{
int
firstadrPrev
=
firstadr
;
JCVariableDecl
vardecl
=
vardecls
[
i
];
int
returnadrPrev
=
returnadr
;
VarSymbol
var
=
vardecl
.
sym
;
if
(
var
.
owner
==
classDef
.
sym
)
{
Assert
.
check
(
pendingExits
.
isEmpty
());
// choose the diagnostic position based on whether
boolean
lastInitialConstructor
=
isInitialConstructor
;
// the ctor is default(synthesized) or not
try
{
if
(
isSynthesized
)
{
isInitialConstructor
=
TreeInfo
.
isInitialConstructor
(
tree
);
checkInit
(
TreeInfo
.
diagnosticPositionFor
(
var
,
vardecl
),
var
,
"var.not.initialized.in.default.constructor"
);
if
(!
isInitialConstructor
)
{
}
else
{
firstadr
=
nextadr
;
checkInit
(
TreeInfo
.
diagEndPos
(
tree
.
body
),
var
);
}
}
}
}
}
for
(
List
<
JCVariableDecl
>
l
=
tree
.
params
;
l
.
nonEmpty
();
l
=
l
.
tail
)
{
List
<
P
>
exits
=
pendingExits
.
toList
();
JCVariableDecl
def
=
l
.
head
;
pendingExits
=
new
ListBuffer
<>();
scan
(
def
);
while
(
exits
.
nonEmpty
())
{
Assert
.
check
((
def
.
sym
.
flags
()
&
PARAMETER
)
!=
0
,
"Method parameter without PARAMETER flag"
);
P
exit
=
exits
.
head
;
/* If we are executing the code from Gen, then there can be
exits
=
exits
.
tail
;
* synthetic or mandated variables, ignore them.
Assert
.
check
(
exit
.
tree
.
hasTag
(
RETURN
),
exit
.
tree
);
*/
initParam
(
def
);
}
// else we are in an instance initializer block;
// leave caught unchanged.
scan
(
tree
.
body
);
if
(
isInitialConstructor
)
{
if
(
isInitialConstructor
)
{
assignToInits
(
exit
.
tree
,
exit
.
exit_inits
);
boolean
isSynthesized
=
(
tree
.
sym
.
flags
()
&
GENERATEDCONSTR
)
!=
0
;
for
(
int
i
=
firstadr
;
i
<
nextadr
;
i
++)
{
for
(
int
i
=
firstadr
;
i
<
nextadr
;
i
++)
{
checkInit
(
exit
.
tree
.
pos
(),
vardecls
[
i
].
sym
);
JCVariableDecl
vardecl
=
vardecls
[
i
];
VarSymbol
var
=
vardecl
.
sym
;
if
(
var
.
owner
==
classDef
.
sym
)
{
// choose the diagnostic position based on whether
// the ctor is default(synthesized) or not
if
(
isSynthesized
)
{
checkInit
(
TreeInfo
.
diagnosticPositionFor
(
var
,
vardecl
),
var
,
"var.not.initialized.in.default.constructor"
);
}
else
{
checkInit
(
TreeInfo
.
diagEndPos
(
tree
.
body
),
var
);
}
}
}
}
List
<
AssignPendingExit
>
exits
=
pendingExits
.
toList
();
pendingExits
=
new
ListBuffer
<>();
while
(
exits
.
nonEmpty
())
{
AssignPendingExit
exit
=
exits
.
head
;
exits
=
exits
.
tail
;
Assert
.
check
(
exit
.
tree
.
hasTag
(
RETURN
),
exit
.
tree
);
if
(
isInitialConstructor
)
{
inits
.
assign
(
exit
.
exit_inits
);
for
(
int
i
=
firstadr
;
i
<
nextadr
;
i
++)
{
checkInit
(
exit
.
tree
.
pos
(),
vardecls
[
i
].
sym
);
}
}
}
}
}
}
finally
{
inits
.
assign
(
initsPrev
);
uninits
.
assign
(
uninitsPrev
);
nextadr
=
nextadrPrev
;
firstadr
=
firstadrPrev
;
returnadr
=
returnadrPrev
;
isInitialConstructor
=
lastInitialConstructor
;
}
}
}
finally
{
}
finally
{
assignToInits
(
tree
,
initsPrev
);
lint
=
lintPrev
;
uninits
.
assign
(
uninitsPrev
);
nextadr
=
nextadrPrev
;
firstadr
=
firstadrPrev
;
returnadr
=
returnadrPrev
;
isInitialConstructor
=
lastInitialConstructor
;
}
}
}
}
protected
void
initParam
(
JCVariableDecl
def
)
{
protected
void
initParam
(
JCVariableDecl
def
)
{
inits
.
incl
(
def
.
sym
.
adr
);
inits
.
incl
(
def
.
sym
.
adr
);
uninits
.
excl
(
def
.
sym
.
adr
);
uninits
.
excl
(
def
.
sym
.
adr
);
}
}
public
void
visitVarDef
(
JCVariableDecl
tree
)
{
public
void
visitVarDef
(
JCVariableDecl
tree
)
{
boolean
track
=
trackable
(
tree
.
sym
);
Lint
lintPrev
=
lint
;
if
(
track
&&
tree
.
sym
.
owner
.
kind
==
MTH
)
{
lint
=
lint
.
augment
(
tree
.
sym
);
newVar
(
tree
);
try
{
}
boolean
track
=
trackable
(
tree
.
sym
);
if
(
tree
.
init
!=
null
)
{
if
(
track
&&
tree
.
sym
.
owner
.
kind
==
MTH
)
{
scanExpr
(
tree
.
init
);
newVar
(
tree
);
if
(
track
)
{
}
letInit
(
tree
.
pos
(),
tree
.
sym
);
if
(
tree
.
init
!=
null
)
{
scanExpr
(
tree
.
init
);
if
(
track
)
{
letInit
(
tree
.
pos
(),
tree
.
sym
);
}
}
}
}
finally
{
lint
=
lintPrev
;
}
}
}
}
...
@@ -1844,18 +1884,14 @@ public class Flow {
...
@@ -1844,18 +1884,14 @@ public class Flow {
nextadr
=
nextadrPrev
;
nextadr
=
nextadrPrev
;
}
}
int
getLogNumberOfErrors
()
{
return
0
;
}
public
void
visitDoLoop
(
JCDoWhileLoop
tree
)
{
public
void
visitDoLoop
(
JCDoWhileLoop
tree
)
{
ListBuffer
<
P
>
prevPendingExits
=
pendingExits
;
ListBuffer
<
AssignPendingExit
>
prevPendingExits
=
pendingExits
;
FlowKind
prevFlowKind
=
flowKind
;
FlowKind
prevFlowKind
=
flowKind
;
flowKind
=
FlowKind
.
NORMAL
;
flowKind
=
FlowKind
.
NORMAL
;
final
Bits
initsSkip
=
new
Bits
(
true
);
final
Bits
initsSkip
=
new
Bits
(
true
);
final
Bits
uninitsSkip
=
new
Bits
(
true
);
final
Bits
uninitsSkip
=
new
Bits
(
true
);
pendingExits
=
new
ListBuffer
<
P
>();
pendingExits
=
new
ListBuffer
<>();
int
prevErrors
=
getLogNumberOfErrors
()
;
int
prevErrors
=
log
.
nerrors
;
do
{
do
{
final
Bits
uninitsEntry
=
new
Bits
(
uninits
);
final
Bits
uninitsEntry
=
new
Bits
(
uninits
);
uninitsEntry
.
excludeFrom
(
nextadr
);
uninitsEntry
.
excludeFrom
(
nextadr
);
...
@@ -1866,28 +1902,28 @@ public class Flow {
...
@@ -1866,28 +1902,28 @@ public class Flow {
initsSkip
.
assign
(
initsWhenFalse
);
initsSkip
.
assign
(
initsWhenFalse
);
uninitsSkip
.
assign
(
uninitsWhenFalse
);
uninitsSkip
.
assign
(
uninitsWhenFalse
);
}
}
if
(
getLogNumberOfErrors
()
!=
prevErrors
||
if
(
log
.
nerrors
!=
prevErrors
||
flowKind
.
isFinal
()
||
flowKind
.
isFinal
()
||
new
Bits
(
uninitsEntry
).
diffSet
(
uninitsWhenTrue
).
nextBit
(
firstadr
)==-
1
)
new
Bits
(
uninitsEntry
).
diffSet
(
uninitsWhenTrue
).
nextBit
(
firstadr
)==-
1
)
break
;
break
;
assignToInits
(
tree
.
cond
,
initsWhenTrue
);
inits
.
assign
(
initsWhenTrue
);
uninits
.
assign
(
uninitsEntry
.
andSet
(
uninitsWhenTrue
));
uninits
.
assign
(
uninitsEntry
.
andSet
(
uninitsWhenTrue
));
flowKind
=
FlowKind
.
SPECULATIVE_LOOP
;
flowKind
=
FlowKind
.
SPECULATIVE_LOOP
;
}
while
(
true
);
}
while
(
true
);
flowKind
=
prevFlowKind
;
flowKind
=
prevFlowKind
;
assignToInits
(
tree
,
initsSkip
);
inits
.
assign
(
initsSkip
);
uninits
.
assign
(
uninitsSkip
);
uninits
.
assign
(
uninitsSkip
);
resolveBreaks
(
tree
,
prevPendingExits
);
resolveBreaks
(
tree
,
prevPendingExits
);
}
}
public
void
visitWhileLoop
(
JCWhileLoop
tree
)
{
public
void
visitWhileLoop
(
JCWhileLoop
tree
)
{
ListBuffer
<
P
>
prevPendingExits
=
pendingExits
;
ListBuffer
<
AssignPendingExit
>
prevPendingExits
=
pendingExits
;
FlowKind
prevFlowKind
=
flowKind
;
FlowKind
prevFlowKind
=
flowKind
;
flowKind
=
FlowKind
.
NORMAL
;
flowKind
=
FlowKind
.
NORMAL
;
final
Bits
initsSkip
=
new
Bits
(
true
);
final
Bits
initsSkip
=
new
Bits
(
true
);
final
Bits
uninitsSkip
=
new
Bits
(
true
);
final
Bits
uninitsSkip
=
new
Bits
(
true
);
pendingExits
=
new
ListBuffer
<>();
pendingExits
=
new
ListBuffer
<>();
int
prevErrors
=
getLogNumberOfErrors
()
;
int
prevErrors
=
log
.
nerrors
;
final
Bits
uninitsEntry
=
new
Bits
(
uninits
);
final
Bits
uninitsEntry
=
new
Bits
(
uninits
);
uninitsEntry
.
excludeFrom
(
nextadr
);
uninitsEntry
.
excludeFrom
(
nextadr
);
do
{
do
{
...
@@ -1896,11 +1932,11 @@ public class Flow {
...
@@ -1896,11 +1932,11 @@ public class Flow {
initsSkip
.
assign
(
initsWhenFalse
)
;
initsSkip
.
assign
(
initsWhenFalse
)
;
uninitsSkip
.
assign
(
uninitsWhenFalse
);
uninitsSkip
.
assign
(
uninitsWhenFalse
);
}
}
assignToInits
(
tree
,
initsWhenTrue
);
inits
.
assign
(
initsWhenTrue
);
uninits
.
assign
(
uninitsWhenTrue
);
uninits
.
assign
(
uninitsWhenTrue
);
scan
(
tree
.
body
);
scan
(
tree
.
body
);
resolveContinues
(
tree
);
resolveContinues
(
tree
);
if
(
getLogNumberOfErrors
()
!=
prevErrors
||
if
(
log
.
nerrors
!=
prevErrors
||
flowKind
.
isFinal
()
||
flowKind
.
isFinal
()
||
new
Bits
(
uninitsEntry
).
diffSet
(
uninits
).
nextBit
(
firstadr
)
==
-
1
)
{
new
Bits
(
uninitsEntry
).
diffSet
(
uninits
).
nextBit
(
firstadr
)
==
-
1
)
{
break
;
break
;
...
@@ -1911,21 +1947,21 @@ public class Flow {
...
@@ -1911,21 +1947,21 @@ public class Flow {
flowKind
=
prevFlowKind
;
flowKind
=
prevFlowKind
;
//a variable is DA/DU after the while statement, if it's DA/DU assuming the
//a variable is DA/DU after the while statement, if it's DA/DU assuming the
//branch is not taken AND if it's DA/DU before any break statement
//branch is not taken AND if it's DA/DU before any break statement
assignToInits
(
tree
.
body
,
initsSkip
);
inits
.
assign
(
initsSkip
);
uninits
.
assign
(
uninitsSkip
);
uninits
.
assign
(
uninitsSkip
);
resolveBreaks
(
tree
,
prevPendingExits
);
resolveBreaks
(
tree
,
prevPendingExits
);
}
}
public
void
visitForLoop
(
JCForLoop
tree
)
{
public
void
visitForLoop
(
JCForLoop
tree
)
{
ListBuffer
<
P
>
prevPendingExits
=
pendingExits
;
ListBuffer
<
AssignPendingExit
>
prevPendingExits
=
pendingExits
;
FlowKind
prevFlowKind
=
flowKind
;
FlowKind
prevFlowKind
=
flowKind
;
flowKind
=
FlowKind
.
NORMAL
;
flowKind
=
FlowKind
.
NORMAL
;
int
nextadrPrev
=
nextadr
;
int
nextadrPrev
=
nextadr
;
scan
(
tree
.
init
);
scan
(
tree
.
init
);
final
Bits
initsSkip
=
new
Bits
(
true
);
final
Bits
initsSkip
=
new
Bits
(
true
);
final
Bits
uninitsSkip
=
new
Bits
(
true
);
final
Bits
uninitsSkip
=
new
Bits
(
true
);
pendingExits
=
new
ListBuffer
<
P
>();
pendingExits
=
new
ListBuffer
<>();
int
prevErrors
=
getLogNumberOfErrors
()
;
int
prevErrors
=
log
.
nerrors
;
do
{
do
{
final
Bits
uninitsEntry
=
new
Bits
(
uninits
);
final
Bits
uninitsEntry
=
new
Bits
(
uninits
);
uninitsEntry
.
excludeFrom
(
nextadr
);
uninitsEntry
.
excludeFrom
(
nextadr
);
...
@@ -1935,7 +1971,7 @@ public class Flow {
...
@@ -1935,7 +1971,7 @@ public class Flow {
initsSkip
.
assign
(
initsWhenFalse
);
initsSkip
.
assign
(
initsWhenFalse
);
uninitsSkip
.
assign
(
uninitsWhenFalse
);
uninitsSkip
.
assign
(
uninitsWhenFalse
);
}
}
assignToInits
(
tree
.
body
,
initsWhenTrue
);
inits
.
assign
(
initsWhenTrue
);
uninits
.
assign
(
uninitsWhenTrue
);
uninits
.
assign
(
uninitsWhenTrue
);
}
else
if
(!
flowKind
.
isFinal
())
{
}
else
if
(!
flowKind
.
isFinal
())
{
initsSkip
.
assign
(
inits
);
initsSkip
.
assign
(
inits
);
...
@@ -1946,7 +1982,7 @@ public class Flow {
...
@@ -1946,7 +1982,7 @@ public class Flow {
scan
(
tree
.
body
);
scan
(
tree
.
body
);
resolveContinues
(
tree
);
resolveContinues
(
tree
);
scan
(
tree
.
step
);
scan
(
tree
.
step
);
if
(
getLogNumberOfErrors
()
!=
prevErrors
||
if
(
log
.
nerrors
!=
prevErrors
||
flowKind
.
isFinal
()
||
flowKind
.
isFinal
()
||
new
Bits
(
uninitsEntry
).
diffSet
(
uninits
).
nextBit
(
firstadr
)
==
-
1
)
new
Bits
(
uninitsEntry
).
diffSet
(
uninits
).
nextBit
(
firstadr
)
==
-
1
)
break
;
break
;
...
@@ -1956,7 +1992,7 @@ public class Flow {
...
@@ -1956,7 +1992,7 @@ public class Flow {
flowKind
=
prevFlowKind
;
flowKind
=
prevFlowKind
;
//a variable is DA/DU after a for loop, if it's DA/DU assuming the
//a variable is DA/DU after a for loop, if it's DA/DU assuming the
//branch is not taken AND if it's DA/DU before any break statement
//branch is not taken AND if it's DA/DU before any break statement
assignToInits
(
tree
.
body
,
initsSkip
);
inits
.
assign
(
initsSkip
);
uninits
.
assign
(
uninitsSkip
);
uninits
.
assign
(
uninitsSkip
);
resolveBreaks
(
tree
,
prevPendingExits
);
resolveBreaks
(
tree
,
prevPendingExits
);
nextadr
=
nextadrPrev
;
nextadr
=
nextadrPrev
;
...
@@ -1965,7 +2001,7 @@ public class Flow {
...
@@ -1965,7 +2001,7 @@ public class Flow {
public
void
visitForeachLoop
(
JCEnhancedForLoop
tree
)
{
public
void
visitForeachLoop
(
JCEnhancedForLoop
tree
)
{
visitVarDef
(
tree
.
var
);
visitVarDef
(
tree
.
var
);
ListBuffer
<
P
>
prevPendingExits
=
pendingExits
;
ListBuffer
<
AssignPendingExit
>
prevPendingExits
=
pendingExits
;
FlowKind
prevFlowKind
=
flowKind
;
FlowKind
prevFlowKind
=
flowKind
;
flowKind
=
FlowKind
.
NORMAL
;
flowKind
=
FlowKind
.
NORMAL
;
int
nextadrPrev
=
nextadr
;
int
nextadrPrev
=
nextadr
;
...
@@ -1974,14 +2010,14 @@ public class Flow {
...
@@ -1974,14 +2010,14 @@ public class Flow {
final
Bits
uninitsStart
=
new
Bits
(
uninits
);
final
Bits
uninitsStart
=
new
Bits
(
uninits
);
letInit
(
tree
.
pos
(),
tree
.
var
.
sym
);
letInit
(
tree
.
pos
(),
tree
.
var
.
sym
);
pendingExits
=
new
ListBuffer
<
P
>();
pendingExits
=
new
ListBuffer
<>();
int
prevErrors
=
getLogNumberOfErrors
()
;
int
prevErrors
=
log
.
nerrors
;
do
{
do
{
final
Bits
uninitsEntry
=
new
Bits
(
uninits
);
final
Bits
uninitsEntry
=
new
Bits
(
uninits
);
uninitsEntry
.
excludeFrom
(
nextadr
);
uninitsEntry
.
excludeFrom
(
nextadr
);
scan
(
tree
.
body
);
scan
(
tree
.
body
);
resolveContinues
(
tree
);
resolveContinues
(
tree
);
if
(
getLogNumberOfErrors
()
!=
prevErrors
||
if
(
log
.
nerrors
!=
prevErrors
||
flowKind
.
isFinal
()
||
flowKind
.
isFinal
()
||
new
Bits
(
uninitsEntry
).
diffSet
(
uninits
).
nextBit
(
firstadr
)
==
-
1
)
new
Bits
(
uninitsEntry
).
diffSet
(
uninits
).
nextBit
(
firstadr
)
==
-
1
)
break
;
break
;
...
@@ -1989,21 +2025,21 @@ public class Flow {
...
@@ -1989,21 +2025,21 @@ public class Flow {
flowKind
=
FlowKind
.
SPECULATIVE_LOOP
;
flowKind
=
FlowKind
.
SPECULATIVE_LOOP
;
}
while
(
true
);
}
while
(
true
);
flowKind
=
prevFlowKind
;
flowKind
=
prevFlowKind
;
assignToInits
(
tree
.
body
,
initsStart
);
inits
.
assign
(
initsStart
);
uninits
.
assign
(
uninitsStart
.
andSet
(
uninits
));
uninits
.
assign
(
uninitsStart
.
andSet
(
uninits
));
resolveBreaks
(
tree
,
prevPendingExits
);
resolveBreaks
(
tree
,
prevPendingExits
);
nextadr
=
nextadrPrev
;
nextadr
=
nextadrPrev
;
}
}
public
void
visitLabelled
(
JCLabeledStatement
tree
)
{
public
void
visitLabelled
(
JCLabeledStatement
tree
)
{
ListBuffer
<
P
>
prevPendingExits
=
pendingExits
;
ListBuffer
<
AssignPendingExit
>
prevPendingExits
=
pendingExits
;
pendingExits
=
new
ListBuffer
<
P
>();
pendingExits
=
new
ListBuffer
<>();
scan
(
tree
.
body
);
scan
(
tree
.
body
);
resolveBreaks
(
tree
,
prevPendingExits
);
resolveBreaks
(
tree
,
prevPendingExits
);
}
}
public
void
visitSwitch
(
JCSwitch
tree
)
{
public
void
visitSwitch
(
JCSwitch
tree
)
{
ListBuffer
<
P
>
prevPendingExits
=
pendingExits
;
ListBuffer
<
AssignPendingExit
>
prevPendingExits
=
pendingExits
;
pendingExits
=
new
ListBuffer
<>();
pendingExits
=
new
ListBuffer
<>();
int
nextadrPrev
=
nextadr
;
int
nextadrPrev
=
nextadr
;
scanExpr
(
tree
.
selector
);
scanExpr
(
tree
.
selector
);
...
@@ -2011,7 +2047,7 @@ public class Flow {
...
@@ -2011,7 +2047,7 @@ public class Flow {
final
Bits
uninitsSwitch
=
new
Bits
(
uninits
);
final
Bits
uninitsSwitch
=
new
Bits
(
uninits
);
boolean
hasDefault
=
false
;
boolean
hasDefault
=
false
;
for
(
List
<
JCCase
>
l
=
tree
.
cases
;
l
.
nonEmpty
();
l
=
l
.
tail
)
{
for
(
List
<
JCCase
>
l
=
tree
.
cases
;
l
.
nonEmpty
();
l
=
l
.
tail
)
{
assignToInits
(
l
.
head
,
initsSwitch
);
inits
.
assign
(
initsSwitch
);
uninits
.
assign
(
uninits
.
andSet
(
uninitsSwitch
));
uninits
.
assign
(
uninits
.
andSet
(
uninitsSwitch
));
JCCase
c
=
l
.
head
;
JCCase
c
=
l
.
head
;
if
(
c
.
pat
==
null
)
{
if
(
c
.
pat
==
null
)
{
...
@@ -2020,19 +2056,19 @@ public class Flow {
...
@@ -2020,19 +2056,19 @@ public class Flow {
scanExpr
(
c
.
pat
);
scanExpr
(
c
.
pat
);
}
}
if
(
hasDefault
)
{
if
(
hasDefault
)
{
assignToInits
(
null
,
initsSwitch
);
inits
.
assign
(
initsSwitch
);
uninits
.
assign
(
uninits
.
andSet
(
uninitsSwitch
));
uninits
.
assign
(
uninits
.
andSet
(
uninitsSwitch
));
}
}
scan
(
c
.
stats
);
scan
(
c
.
stats
);
addVars
(
c
.
stats
,
initsSwitch
,
uninitsSwitch
);
addVars
(
c
.
stats
,
initsSwitch
,
uninitsSwitch
);
if
(!
hasDefault
)
{
if
(!
hasDefault
)
{
assignToInits
(
l
.
head
.
stats
.
last
(),
initsSwitch
);
inits
.
assign
(
initsSwitch
);
uninits
.
assign
(
uninits
.
andSet
(
uninitsSwitch
));
uninits
.
assign
(
uninits
.
andSet
(
uninitsSwitch
));
}
}
// Warn about fall-through if lint switch fallthrough enabled.
// Warn about fall-through if lint switch fallthrough enabled.
}
}
if
(!
hasDefault
)
{
if
(!
hasDefault
)
{
andSetInits
(
null
,
initsSwitch
);
inits
.
andSet
(
initsSwitch
);
}
}
resolveBreaks
(
tree
,
prevPendingExits
);
resolveBreaks
(
tree
,
prevPendingExits
);
nextadr
=
nextadrPrev
;
nextadr
=
nextadrPrev
;
...
@@ -2051,16 +2087,10 @@ public class Flow {
...
@@ -2051,16 +2087,10 @@ public class Flow {
}
}
}
}
boolean
isEnabled
(
Lint
.
LintCategory
lc
)
{
return
false
;
}
void
reportWarning
(
Lint
.
LintCategory
lc
,
DiagnosticPosition
pos
,
String
key
,
Object
...
args
)
{}
public
void
visitTry
(
JCTry
tree
)
{
public
void
visitTry
(
JCTry
tree
)
{
ListBuffer
<
JCVariableDecl
>
resourceVarDecls
=
new
ListBuffer
<>();
ListBuffer
<
JCVariableDecl
>
resourceVarDecls
=
new
ListBuffer
<>();
final
Bits
uninitsTryPrev
=
new
Bits
(
uninitsTry
);
final
Bits
uninitsTryPrev
=
new
Bits
(
uninitsTry
);
ListBuffer
<
P
>
prevPendingExits
=
pendingExits
;
ListBuffer
<
AssignPendingExit
>
prevPendingExits
=
pendingExits
;
pendingExits
=
new
ListBuffer
<>();
pendingExits
=
new
ListBuffer
<>();
final
Bits
initsTry
=
new
Bits
(
inits
);
final
Bits
initsTry
=
new
Bits
(
inits
);
uninitsTry
.
assign
(
uninits
);
uninitsTry
.
assign
(
uninits
);
...
@@ -2083,10 +2113,10 @@ public class Flow {
...
@@ -2083,10 +2113,10 @@ public class Flow {
int
nextadrCatch
=
nextadr
;
int
nextadrCatch
=
nextadr
;
if
(!
resourceVarDecls
.
isEmpty
()
&&
if
(!
resourceVarDecls
.
isEmpty
()
&&
isEnabled
(
Lint
.
LintCategory
.
TRY
))
{
lint
.
isEnabled
(
Lint
.
LintCategory
.
TRY
))
{
for
(
JCVariableDecl
resVar
:
resourceVarDecls
)
{
for
(
JCVariableDecl
resVar
:
resourceVarDecls
)
{
if
(
unrefdResources
.
includes
(
resVar
.
sym
))
{
if
(
unrefdResources
.
includes
(
resVar
.
sym
))
{
reportW
arning
(
Lint
.
LintCategory
.
TRY
,
resVar
.
pos
(),
log
.
w
arning
(
Lint
.
LintCategory
.
TRY
,
resVar
.
pos
(),
"try.resource.not.referenced"
,
resVar
.
sym
);
"try.resource.not.referenced"
,
resVar
.
sym
);
unrefdResources
.
remove
(
resVar
.
sym
);
unrefdResources
.
remove
(
resVar
.
sym
);
}
}
...
@@ -2102,7 +2132,7 @@ public class Flow {
...
@@ -2102,7 +2132,7 @@ public class Flow {
for
(
List
<
JCCatch
>
l
=
tree
.
catchers
;
l
.
nonEmpty
();
l
=
l
.
tail
)
{
for
(
List
<
JCCatch
>
l
=
tree
.
catchers
;
l
.
nonEmpty
();
l
=
l
.
tail
)
{
JCVariableDecl
param
=
l
.
head
.
param
;
JCVariableDecl
param
=
l
.
head
.
param
;
assignToInits
(
tree
.
body
,
initsCatchPrev
);
inits
.
assign
(
initsCatchPrev
);
uninits
.
assign
(
uninitsCatchPrev
);
uninits
.
assign
(
uninitsCatchPrev
);
scan
(
param
);
scan
(
param
);
/* If this is a TWR and we are executing the code from Gen,
/* If this is a TWR and we are executing the code from Gen,
...
@@ -2115,9 +2145,9 @@ public class Flow {
...
@@ -2115,9 +2145,9 @@ public class Flow {
nextadr
=
nextadrCatch
;
nextadr
=
nextadrCatch
;
}
}
if
(
tree
.
finalizer
!=
null
)
{
if
(
tree
.
finalizer
!=
null
)
{
assignToInits
(
tree
.
finalizer
,
initsTry
);
inits
.
assign
(
initsTry
);
uninits
.
assign
(
uninitsTry
);
uninits
.
assign
(
uninitsTry
);
ListBuffer
<
P
>
exits
=
pendingExits
;
ListBuffer
<
AssignPendingExit
>
exits
=
pendingExits
;
pendingExits
=
prevPendingExits
;
pendingExits
=
prevPendingExits
;
scan
(
tree
.
finalizer
);
scan
(
tree
.
finalizer
);
if
(!
tree
.
finallyCanCompleteNormally
)
{
if
(!
tree
.
finallyCanCompleteNormally
)
{
...
@@ -2127,19 +2157,19 @@ public class Flow {
...
@@ -2127,19 +2157,19 @@ public class Flow {
// FIX: this doesn't preserve source order of exits in catch
// FIX: this doesn't preserve source order of exits in catch
// versus finally!
// versus finally!
while
(
exits
.
nonEmpty
())
{
while
(
exits
.
nonEmpty
())
{
P
exit
=
exits
.
next
();
AssignPendingExit
exit
=
exits
.
next
();
if
(
exit
.
exit_inits
!=
null
)
{
if
(
exit
.
exit_inits
!=
null
)
{
exit
.
exit_inits
.
orSet
(
inits
);
exit
.
exit_inits
.
orSet
(
inits
);
exit
.
exit_uninits
.
andSet
(
uninits
);
exit
.
exit_uninits
.
andSet
(
uninits
);
}
}
pendingExits
.
append
(
exit
);
pendingExits
.
append
(
exit
);
}
}
orSetInits
(
tree
,
initsEnd
);
inits
.
orSet
(
initsEnd
);
}
}
}
else
{
}
else
{
assignToInits
(
tree
,
initsEnd
);
inits
.
assign
(
initsEnd
);
uninits
.
assign
(
uninitsEnd
);
uninits
.
assign
(
uninitsEnd
);
ListBuffer
<
P
>
exits
=
pendingExits
;
ListBuffer
<
AssignPendingExit
>
exits
=
pendingExits
;
pendingExits
=
prevPendingExits
;
pendingExits
=
prevPendingExits
;
while
(
exits
.
nonEmpty
())
pendingExits
.
append
(
exits
.
next
());
while
(
exits
.
nonEmpty
())
pendingExits
.
append
(
exits
.
next
());
}
}
...
@@ -2150,7 +2180,7 @@ public class Flow {
...
@@ -2150,7 +2180,7 @@ public class Flow {
scanCond
(
tree
.
cond
);
scanCond
(
tree
.
cond
);
final
Bits
initsBeforeElse
=
new
Bits
(
initsWhenFalse
);
final
Bits
initsBeforeElse
=
new
Bits
(
initsWhenFalse
);
final
Bits
uninitsBeforeElse
=
new
Bits
(
uninitsWhenFalse
);
final
Bits
uninitsBeforeElse
=
new
Bits
(
uninitsWhenFalse
);
assignToInits
(
tree
.
cond
,
initsWhenTrue
);
inits
.
assign
(
initsWhenTrue
);
uninits
.
assign
(
uninitsWhenTrue
);
uninits
.
assign
(
uninitsWhenTrue
);
if
(
tree
.
truepart
.
type
.
hasTag
(
BOOLEAN
)
&&
if
(
tree
.
truepart
.
type
.
hasTag
(
BOOLEAN
)
&&
tree
.
falsepart
.
type
.
hasTag
(
BOOLEAN
))
{
tree
.
falsepart
.
type
.
hasTag
(
BOOLEAN
))
{
...
@@ -2163,7 +2193,7 @@ public class Flow {
...
@@ -2163,7 +2193,7 @@ public class Flow {
final
Bits
initsAfterThenWhenFalse
=
new
Bits
(
initsWhenFalse
);
final
Bits
initsAfterThenWhenFalse
=
new
Bits
(
initsWhenFalse
);
final
Bits
uninitsAfterThenWhenTrue
=
new
Bits
(
uninitsWhenTrue
);
final
Bits
uninitsAfterThenWhenTrue
=
new
Bits
(
uninitsWhenTrue
);
final
Bits
uninitsAfterThenWhenFalse
=
new
Bits
(
uninitsWhenFalse
);
final
Bits
uninitsAfterThenWhenFalse
=
new
Bits
(
uninitsWhenFalse
);
assignToInits
(
tree
.
truepart
,
initsBeforeElse
);
inits
.
assign
(
initsBeforeElse
);
uninits
.
assign
(
uninitsBeforeElse
);
uninits
.
assign
(
uninitsBeforeElse
);
scanCond
(
tree
.
falsepart
);
scanCond
(
tree
.
falsepart
);
initsWhenTrue
.
andSet
(
initsAfterThenWhenTrue
);
initsWhenTrue
.
andSet
(
initsAfterThenWhenTrue
);
...
@@ -2174,10 +2204,10 @@ public class Flow {
...
@@ -2174,10 +2204,10 @@ public class Flow {
scanExpr
(
tree
.
truepart
);
scanExpr
(
tree
.
truepart
);
final
Bits
initsAfterThen
=
new
Bits
(
inits
);
final
Bits
initsAfterThen
=
new
Bits
(
inits
);
final
Bits
uninitsAfterThen
=
new
Bits
(
uninits
);
final
Bits
uninitsAfterThen
=
new
Bits
(
uninits
);
assignToInits
(
tree
.
truepart
,
initsBeforeElse
);
inits
.
assign
(
initsBeforeElse
);
uninits
.
assign
(
uninitsBeforeElse
);
uninits
.
assign
(
uninitsBeforeElse
);
scanExpr
(
tree
.
falsepart
);
scanExpr
(
tree
.
falsepart
);
andSetInits
(
tree
.
falsepart
,
initsAfterThen
);
inits
.
andSet
(
initsAfterThen
);
uninits
.
andSet
(
uninitsAfterThen
);
uninits
.
andSet
(
uninitsAfterThen
);
}
}
}
}
...
@@ -2186,46 +2216,42 @@ public class Flow {
...
@@ -2186,46 +2216,42 @@ public class Flow {
scanCond
(
tree
.
cond
);
scanCond
(
tree
.
cond
);
final
Bits
initsBeforeElse
=
new
Bits
(
initsWhenFalse
);
final
Bits
initsBeforeElse
=
new
Bits
(
initsWhenFalse
);
final
Bits
uninitsBeforeElse
=
new
Bits
(
uninitsWhenFalse
);
final
Bits
uninitsBeforeElse
=
new
Bits
(
uninitsWhenFalse
);
assignToInits
(
tree
.
cond
,
initsWhenTrue
);
inits
.
assign
(
initsWhenTrue
);
uninits
.
assign
(
uninitsWhenTrue
);
uninits
.
assign
(
uninitsWhenTrue
);
scan
(
tree
.
thenpart
);
scan
(
tree
.
thenpart
);
if
(
tree
.
elsepart
!=
null
)
{
if
(
tree
.
elsepart
!=
null
)
{
final
Bits
initsAfterThen
=
new
Bits
(
inits
);
final
Bits
initsAfterThen
=
new
Bits
(
inits
);
final
Bits
uninitsAfterThen
=
new
Bits
(
uninits
);
final
Bits
uninitsAfterThen
=
new
Bits
(
uninits
);
assignToInits
(
tree
.
thenpart
,
initsBeforeElse
);
inits
.
assign
(
initsBeforeElse
);
uninits
.
assign
(
uninitsBeforeElse
);
uninits
.
assign
(
uninitsBeforeElse
);
scan
(
tree
.
elsepart
);
scan
(
tree
.
elsepart
);
andSetInits
(
tree
.
elsepart
,
initsAfterThen
);
inits
.
andSet
(
initsAfterThen
);
uninits
.
andSet
(
uninitsAfterThen
);
uninits
.
andSet
(
uninitsAfterThen
);
}
else
{
}
else
{
andSetInits
(
tree
.
thenpart
,
initsBeforeElse
);
inits
.
andSet
(
initsBeforeElse
);
uninits
.
andSet
(
uninitsBeforeElse
);
uninits
.
andSet
(
uninitsBeforeElse
);
}
}
}
}
protected
P
createNewPendingExit
(
JCTree
tree
,
Bits
inits
,
Bits
uninits
)
{
return
null
;
}
@Override
@Override
public
void
visitBreak
(
JCBreak
tree
)
{
public
void
visitBreak
(
JCBreak
tree
)
{
recordExit
(
tree
,
createNew
PendingExit
(
tree
,
inits
,
uninits
));
recordExit
(
new
Assign
PendingExit
(
tree
,
inits
,
uninits
));
}
}
@Override
@Override
public
void
visitContinue
(
JCContinue
tree
)
{
public
void
visitContinue
(
JCContinue
tree
)
{
recordExit
(
tree
,
createNew
PendingExit
(
tree
,
inits
,
uninits
));
recordExit
(
new
Assign
PendingExit
(
tree
,
inits
,
uninits
));
}
}
@Override
@Override
public
void
visitReturn
(
JCReturn
tree
)
{
public
void
visitReturn
(
JCReturn
tree
)
{
scanExpr
(
tree
.
expr
);
scanExpr
(
tree
.
expr
);
recordExit
(
tree
,
createNew
PendingExit
(
tree
,
inits
,
uninits
));
recordExit
(
new
Assign
PendingExit
(
tree
,
inits
,
uninits
));
}
}
public
void
visitThrow
(
JCThrow
tree
)
{
public
void
visitThrow
(
JCThrow
tree
)
{
scanExpr
(
tree
.
expr
);
scanExpr
(
tree
.
expr
);
markDead
(
tree
.
expr
);
markDead
();
}
}
public
void
visitApply
(
JCMethodInvocation
tree
)
{
public
void
visitApply
(
JCMethodInvocation
tree
)
{
...
@@ -2244,10 +2270,10 @@ public class Flow {
...
@@ -2244,10 +2270,10 @@ public class Flow {
final
Bits
prevUninits
=
new
Bits
(
uninits
);
final
Bits
prevUninits
=
new
Bits
(
uninits
);
final
Bits
prevInits
=
new
Bits
(
inits
);
final
Bits
prevInits
=
new
Bits
(
inits
);
int
returnadrPrev
=
returnadr
;
int
returnadrPrev
=
returnadr
;
ListBuffer
<
P
>
prevPending
=
pendingExits
;
ListBuffer
<
AssignPendingExit
>
prevPending
=
pendingExits
;
try
{
try
{
returnadr
=
nextadr
;
returnadr
=
nextadr
;
pendingExits
=
new
ListBuffer
<
P
>();
pendingExits
=
new
ListBuffer
<>();
for
(
List
<
JCVariableDecl
>
l
=
tree
.
params
;
l
.
nonEmpty
();
l
=
l
.
tail
)
{
for
(
List
<
JCVariableDecl
>
l
=
tree
.
params
;
l
.
nonEmpty
();
l
=
l
.
tail
)
{
JCVariableDecl
def
=
l
.
head
;
JCVariableDecl
def
=
l
.
head
;
scan
(
def
);
scan
(
def
);
...
@@ -2263,7 +2289,7 @@ public class Flow {
...
@@ -2263,7 +2289,7 @@ public class Flow {
finally
{
finally
{
returnadr
=
returnadrPrev
;
returnadr
=
returnadrPrev
;
uninits
.
assign
(
prevUninits
);
uninits
.
assign
(
prevUninits
);
assignToInits
(
tree
,
prevInits
);
inits
.
assign
(
prevInits
);
pendingExits
=
prevPending
;
pendingExits
=
prevPending
;
}
}
}
}
...
@@ -2279,11 +2305,11 @@ public class Flow {
...
@@ -2279,11 +2305,11 @@ public class Flow {
scanCond
(
tree
.
cond
);
scanCond
(
tree
.
cond
);
uninitsExit
.
andSet
(
uninitsWhenTrue
);
uninitsExit
.
andSet
(
uninitsWhenTrue
);
if
(
tree
.
detail
!=
null
)
{
if
(
tree
.
detail
!=
null
)
{
assignToInits
(
tree
,
initsWhenFalse
);
inits
.
assign
(
initsWhenFalse
);
uninits
.
assign
(
uninitsWhenFalse
);
uninits
.
assign
(
uninitsWhenFalse
);
scanExpr
(
tree
.
detail
);
scanExpr
(
tree
.
detail
);
}
}
assignToInits
(
tree
,
initsExit
);
inits
.
assign
(
initsExit
);
uninits
.
assign
(
uninitsExit
);
uninits
.
assign
(
uninitsExit
);
}
}
...
@@ -2351,7 +2377,7 @@ public class Flow {
...
@@ -2351,7 +2377,7 @@ public class Flow {
scanCond
(
tree
.
lhs
);
scanCond
(
tree
.
lhs
);
final
Bits
initsWhenFalseLeft
=
new
Bits
(
initsWhenFalse
);
final
Bits
initsWhenFalseLeft
=
new
Bits
(
initsWhenFalse
);
final
Bits
uninitsWhenFalseLeft
=
new
Bits
(
uninitsWhenFalse
);
final
Bits
uninitsWhenFalseLeft
=
new
Bits
(
uninitsWhenFalse
);
assignToInits
(
tree
.
lhs
,
initsWhenTrue
);
inits
.
assign
(
initsWhenTrue
);
uninits
.
assign
(
uninitsWhenTrue
);
uninits
.
assign
(
uninitsWhenTrue
);
scanCond
(
tree
.
rhs
);
scanCond
(
tree
.
rhs
);
initsWhenFalse
.
andSet
(
initsWhenFalseLeft
);
initsWhenFalse
.
andSet
(
initsWhenFalseLeft
);
...
@@ -2361,7 +2387,7 @@ public class Flow {
...
@@ -2361,7 +2387,7 @@ public class Flow {
scanCond
(
tree
.
lhs
);
scanCond
(
tree
.
lhs
);
final
Bits
initsWhenTrueLeft
=
new
Bits
(
initsWhenTrue
);
final
Bits
initsWhenTrueLeft
=
new
Bits
(
initsWhenTrue
);
final
Bits
uninitsWhenTrueLeft
=
new
Bits
(
uninitsWhenTrue
);
final
Bits
uninitsWhenTrueLeft
=
new
Bits
(
uninitsWhenTrue
);
assignToInits
(
tree
.
lhs
,
initsWhenFalse
);
inits
.
assign
(
initsWhenFalse
);
uninits
.
assign
(
uninitsWhenFalse
);
uninits
.
assign
(
uninitsWhenFalse
);
scanCond
(
tree
.
rhs
);
scanCond
(
tree
.
rhs
);
initsWhenTrue
.
andSet
(
initsWhenTrueLeft
);
initsWhenTrue
.
andSet
(
initsWhenTrueLeft
);
...
@@ -2436,136 +2462,6 @@ public class Flow {
...
@@ -2436,136 +2462,6 @@ public class Flow {
}
}
}
}
public
class
AssignAnalyzer
extends
AbstractAssignAnalyzer
<
AssignAnalyzer
.
AssignPendingExit
>
{
public
class
AssignPendingExit
extends
AbstractAssignAnalyzer
<
AssignPendingExit
>.
AbstractAssignPendingExit
{
public
AssignPendingExit
(
JCTree
tree
,
final
Bits
inits
,
final
Bits
uninits
)
{
super
(
tree
,
inits
,
uninits
);
}
}
@Override
protected
AssignPendingExit
createNewPendingExit
(
JCTree
tree
,
Bits
inits
,
Bits
uninits
)
{
return
new
AssignPendingExit
(
tree
,
inits
,
uninits
);
}
/** Record an initialization of a trackable variable.
*/
@Override
void
letInit
(
DiagnosticPosition
pos
,
VarSymbol
sym
)
{
if
(
sym
.
adr
>=
firstadr
&&
trackable
(
sym
))
{
if
((
sym
.
flags
()
&
EFFECTIVELY_FINAL
)
!=
0
)
{
if
(!
uninits
.
isMember
(
sym
.
adr
))
{
//assignment targeting an effectively final variable
//makes the variable lose its status of effectively final
//if the variable is _not_ definitively unassigned
sym
.
flags_field
&=
~
EFFECTIVELY_FINAL
;
}
else
{
uninit
(
sym
);
}
}
else
if
((
sym
.
flags
()
&
FINAL
)
!=
0
)
{
if
((
sym
.
flags
()
&
PARAMETER
)
!=
0
)
{
if
((
sym
.
flags
()
&
UNION
)
!=
0
)
{
//multi-catch parameter
log
.
error
(
pos
,
"multicatch.parameter.may.not.be.assigned"
,
sym
);
}
else
{
log
.
error
(
pos
,
"final.parameter.may.not.be.assigned"
,
sym
);
}
}
else
if
(!
uninits
.
isMember
(
sym
.
adr
))
{
log
.
error
(
pos
,
flowKind
.
errKey
,
sym
);
}
else
{
uninit
(
sym
);
}
}
inits
.
incl
(
sym
.
adr
);
}
else
if
((
sym
.
flags
()
&
FINAL
)
!=
0
)
{
log
.
error
(
pos
,
"var.might.already.be.assigned"
,
sym
);
}
}
@Override
void
checkInit
(
DiagnosticPosition
pos
,
VarSymbol
sym
,
String
errkey
)
{
if
((
sym
.
adr
>=
firstadr
||
sym
.
owner
.
kind
!=
TYP
)
&&
trackable
(
sym
)
&&
!
inits
.
isMember
(
sym
.
adr
))
{
log
.
error
(
pos
,
errkey
,
sym
);
inits
.
incl
(
sym
.
adr
);
}
}
@Override
void
reportWarning
(
Lint
.
LintCategory
lc
,
DiagnosticPosition
pos
,
String
key
,
Object
...
args
)
{
log
.
warning
(
lc
,
pos
,
key
,
args
);
}
@Override
int
getLogNumberOfErrors
()
{
return
log
.
nerrors
;
}
@Override
boolean
isEnabled
(
Lint
.
LintCategory
lc
)
{
return
lint
.
isEnabled
(
lc
);
}
@Override
public
void
visitClassDef
(
JCClassDecl
tree
)
{
if
(
tree
.
sym
==
null
)
{
return
;
}
Lint
lintPrev
=
lint
;
lint
=
lint
.
augment
(
tree
.
sym
);
try
{
super
.
visitClassDef
(
tree
);
}
finally
{
lint
=
lintPrev
;
}
}
@Override
public
void
visitMethodDef
(
JCMethodDecl
tree
)
{
if
(
tree
.
body
==
null
)
{
return
;
}
/* MemberEnter can generate synthetic methods ignore them
*/
if
((
tree
.
sym
.
flags
()
&
SYNTHETIC
)
!=
0
)
{
return
;
}
Lint
lintPrev
=
lint
;
lint
=
lint
.
augment
(
tree
.
sym
);
try
{
super
.
visitMethodDef
(
tree
);
}
finally
{
lint
=
lintPrev
;
}
}
@Override
public
void
visitVarDef
(
JCVariableDecl
tree
)
{
if
(
tree
.
init
==
null
)
{
super
.
visitVarDef
(
tree
);
}
else
{
Lint
lintPrev
=
lint
;
lint
=
lint
.
augment
(
tree
.
sym
);
try
{
super
.
visitVarDef
(
tree
);
}
finally
{
lint
=
lintPrev
;
}
}
}
}
/**
/**
* This pass implements the last step of the dataflow analysis, namely
* This pass implements the last step of the dataflow analysis, namely
* the effectively-final analysis check. This checks that every local variable
* the effectively-final analysis check. This checks that every local variable
...
@@ -2578,7 +2474,7 @@ public class Flow {
...
@@ -2578,7 +2474,7 @@ public class Flow {
JCTree
currentTree
;
//local class or lambda
JCTree
currentTree
;
//local class or lambda
@Override
@Override
void
markDead
(
JCTree
tree
)
{
void
markDead
()
{
//do nothing
//do nothing
}
}
...
@@ -2715,7 +2611,7 @@ public class Flow {
...
@@ -2715,7 +2611,7 @@ public class Flow {
try
{
try
{
attrEnv
=
env
;
attrEnv
=
env
;
Flow
.
this
.
make
=
make
;
Flow
.
this
.
make
=
make
;
pendingExits
=
new
ListBuffer
<
PendingExit
>();
pendingExits
=
new
ListBuffer
<>();
scan
(
tree
);
scan
(
tree
);
}
finally
{
}
finally
{
pendingExits
=
null
;
pendingExits
=
null
;
...
...
src/share/classes/com/sun/tools/javac/util/Bits.java
浏览文件 @
da351bac
/*
/*
* Copyright (c) 1999, 201
3
, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 1999, 201
5
, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
*
* This code is free software; you can redistribute it and/or modify it
* This code is free software; you can redistribute it and/or modify it
...
@@ -84,20 +84,6 @@ public class Bits {
...
@@ -84,20 +84,6 @@ public class Bits {
}
}
public
enum
BitsOpKind
{
INIT
,
CLEAR
,
INCL_BIT
,
EXCL_BIT
,
ASSIGN
,
AND_SET
,
OR_SET
,
DIFF_SET
,
XOR_SET
,
INCL_RANGE
,
EXCL_RANGE
,
}
private
final
static
int
wordlen
=
32
;
private
final
static
int
wordlen
=
32
;
private
final
static
int
wordshift
=
5
;
private
final
static
int
wordshift
=
5
;
private
final
static
int
wordmask
=
wordlen
-
1
;
private
final
static
int
wordmask
=
wordlen
-
1
;
...
...
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录