Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
openanolis
dragonwell8_hotspot
提交
f0bda8e5
D
dragonwell8_hotspot
项目概览
openanolis
/
dragonwell8_hotspot
通知
2
Star
2
Fork
0
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
D
dragonwell8_hotspot
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
提交
Issue看板
提交
f0bda8e5
编写于
7月 02, 2012
作者:
B
bdelsart
浏览文件
操作
浏览文件
下载
差异文件
Merge
上级
e13550bd
4fe5d370
变更
28
隐藏空白更改
内联
并排
Showing
28 changed file
with
566 addition
and
315 deletion
+566
-315
agent/src/share/classes/sun/jvm/hotspot/oops/ConstMethod.java
...t/src/share/classes/sun/jvm/hotspot/oops/ConstMethod.java
+56
-11
agent/src/share/classes/sun/jvm/hotspot/oops/ExceptionTableElement.java
...e/classes/sun/jvm/hotspot/oops/ExceptionTableElement.java
+81
-0
agent/src/share/classes/sun/jvm/hotspot/oops/GenerateOopMap.java
...rc/share/classes/sun/jvm/hotspot/oops/GenerateOopMap.java
+22
-20
agent/src/share/classes/sun/jvm/hotspot/oops/Method.java
agent/src/share/classes/sun/jvm/hotspot/oops/Method.java
+8
-1
agent/src/share/classes/sun/jvm/hotspot/tools/jcore/ClassWriter.java
...hare/classes/sun/jvm/hotspot/tools/jcore/ClassWriter.java
+15
-12
agent/src/share/classes/sun/jvm/hotspot/ui/classbrowser/HTMLGenerator.java
...lasses/sun/jvm/hotspot/ui/classbrowser/HTMLGenerator.java
+31
-29
src/share/vm/ci/ciMethod.cpp
src/share/vm/ci/ciMethod.cpp
+7
-8
src/share/vm/classfile/classFileParser.cpp
src/share/vm/classfile/classFileParser.cpp
+41
-33
src/share/vm/classfile/classFileParser.hpp
src/share/vm/classfile/classFileParser.hpp
+2
-2
src/share/vm/classfile/systemDictionary.cpp
src/share/vm/classfile/systemDictionary.cpp
+0
-1
src/share/vm/classfile/verifier.cpp
src/share/vm/classfile/verifier.cpp
+66
-64
src/share/vm/interpreter/interpreterRuntime.cpp
src/share/vm/interpreter/interpreterRuntime.cpp
+1
-2
src/share/vm/memory/dump.cpp
src/share/vm/memory/dump.cpp
+0
-3
src/share/vm/memory/oopFactory.cpp
src/share/vm/memory/oopFactory.cpp
+5
-2
src/share/vm/memory/oopFactory.hpp
src/share/vm/memory/oopFactory.hpp
+2
-0
src/share/vm/oops/constMethodKlass.cpp
src/share/vm/oops/constMethodKlass.cpp
+17
-20
src/share/vm/oops/constMethodKlass.hpp
src/share/vm/oops/constMethodKlass.hpp
+2
-1
src/share/vm/oops/constMethodOop.cpp
src/share/vm/oops/constMethodOop.cpp
+42
-4
src/share/vm/oops/constMethodOop.hpp
src/share/vm/oops/constMethodOop.hpp
+30
-18
src/share/vm/oops/generateOopMap.cpp
src/share/vm/oops/generateOopMap.cpp
+18
-19
src/share/vm/oops/methodOop.cpp
src/share/vm/oops/methodOop.cpp
+12
-15
src/share/vm/oops/methodOop.hpp
src/share/vm/oops/methodOop.hpp
+66
-4
src/share/vm/prims/jvm.cpp
src/share/vm/prims/jvm.cpp
+7
-6
src/share/vm/prims/jvmtiClassFileReconstituter.cpp
src/share/vm/prims/jvmtiClassFileReconstituter.cpp
+9
-10
src/share/vm/prims/jvmtiRedefineClasses.cpp
src/share/vm/prims/jvmtiRedefineClasses.cpp
+8
-14
src/share/vm/prims/methodHandleWalk.cpp
src/share/vm/prims/methodHandleWalk.cpp
+2
-5
src/share/vm/runtime/relocator.cpp
src/share/vm/runtime/relocator.cpp
+10
-10
src/share/vm/runtime/vmStructs.cpp
src/share/vm/runtime/vmStructs.cpp
+6
-1
未找到文件。
agent/src/share/classes/sun/jvm/hotspot/oops/ConstMethod.java
浏览文件 @
f0bda8e5
...
...
@@ -47,14 +47,11 @@ public class ConstMethod extends Oop {
private
static
int
HAS_LINENUMBER_TABLE
;
private
static
int
HAS_CHECKED_EXCEPTIONS
;
private
static
int
HAS_LOCALVARIABLE_TABLE
;
private
static
int
HAS_EXCEPTION_TABLE
;
private
static
synchronized
void
initialize
(
TypeDataBase
db
)
throws
WrongTypeException
{
Type
type
=
db
.
lookupType
(
"constMethodOopDesc"
);
constants
=
new
OopField
(
type
.
getOopField
(
"_constants"
),
0
);
// The exception handler table. 4-tuples of ints [start_pc, end_pc,
// handler_pc, catch_type index] For methods with no exceptions the
// table is pointing to Universe::the_empty_int_array
exceptionTable
=
new
OopField
(
type
.
getOopField
(
"_exception_table"
),
0
);
constMethodSize
=
new
CIntField
(
type
.
getCIntegerField
(
"_constMethod_size"
),
0
);
flags
=
new
ByteField
(
type
.
getJByteField
(
"_flags"
),
0
);
...
...
@@ -62,6 +59,7 @@ public class ConstMethod extends Oop {
HAS_LINENUMBER_TABLE
=
db
.
lookupIntConstant
(
"constMethodOopDesc::_has_linenumber_table"
).
intValue
();
HAS_CHECKED_EXCEPTIONS
=
db
.
lookupIntConstant
(
"constMethodOopDesc::_has_checked_exceptions"
).
intValue
();
HAS_LOCALVARIABLE_TABLE
=
db
.
lookupIntConstant
(
"constMethodOopDesc::_has_localvariable_table"
).
intValue
();
HAS_EXCEPTION_TABLE
=
db
.
lookupIntConstant
(
"constMethodOopDesc::_has_exception_table"
).
intValue
();
// Size of Java bytecodes allocated immediately after constMethodOop.
codeSize
=
new
CIntField
(
type
.
getCIntegerField
(
"_code_size"
),
0
);
...
...
@@ -78,6 +76,9 @@ public class ConstMethod extends Oop {
type
=
db
.
lookupType
(
"LocalVariableTableElement"
);
localVariableTableElementSize
=
type
.
getSize
();
type
=
db
.
lookupType
(
"ExceptionTableElement"
);
exceptionTableElementSize
=
type
.
getSize
();
}
ConstMethod
(
OopHandle
handle
,
ObjectHeap
heap
)
{
...
...
@@ -86,7 +87,6 @@ public class ConstMethod extends Oop {
// Fields
private
static
OopField
constants
;
private
static
OopField
exceptionTable
;
private
static
CIntField
constMethodSize
;
private
static
ByteField
flags
;
private
static
CIntField
codeSize
;
...
...
@@ -100,6 +100,7 @@ public class ConstMethod extends Oop {
private
static
long
checkedExceptionElementSize
;
private
static
long
localVariableTableElementSize
;
private
static
long
exceptionTableElementSize
;
public
Method
getMethod
()
{
InstanceKlass
ik
=
(
InstanceKlass
)
getConstants
().
getPoolHolder
();
...
...
@@ -112,10 +113,6 @@ public class ConstMethod extends Oop {
return
(
ConstantPool
)
constants
.
getValue
(
this
);
}
public
TypeArray
getExceptionTable
()
{
return
(
TypeArray
)
exceptionTable
.
getValue
(
this
);
}
public
long
getConstMethodSize
()
{
return
constMethodSize
.
getValue
(
this
);
}
...
...
@@ -235,7 +232,6 @@ public class ConstMethod extends Oop {
super
.
iterateFields
(
visitor
,
doVMFields
);
if
(
doVMFields
)
{
visitor
.
doOop
(
constants
,
true
);
visitor
.
doOop
(
exceptionTable
,
true
);
visitor
.
doCInt
(
constMethodSize
,
true
);
visitor
.
doByte
(
flags
,
true
);
visitor
.
doCInt
(
codeSize
,
true
);
...
...
@@ -326,6 +322,23 @@ public class ConstMethod extends Oop {
return
ret
;
}
public
boolean
hasExceptionTable
()
{
return
(
getFlags
()
&
HAS_EXCEPTION_TABLE
)
!=
0
;
}
public
ExceptionTableElement
[]
getExceptionTable
()
{
if
(
Assert
.
ASSERTS_ENABLED
)
{
Assert
.
that
(
hasExceptionTable
(),
"should only be called if table is present"
);
}
ExceptionTableElement
[]
ret
=
new
ExceptionTableElement
[
getExceptionTableLength
()];
long
offset
=
offsetOfExceptionTable
();
for
(
int
i
=
0
;
i
<
ret
.
length
;
i
++)
{
ret
[
i
]
=
new
ExceptionTableElement
(
getHandle
(),
offset
);
offset
+=
exceptionTableElementSize
;
}
return
ret
;
}
public
boolean
hasCheckedExceptions
()
{
return
(
getFlags
()
&
HAS_CHECKED_EXCEPTIONS
)
!=
0
;
}
...
...
@@ -415,7 +428,10 @@ public class ConstMethod extends Oop {
if
(
Assert
.
ASSERTS_ENABLED
)
{
Assert
.
that
(
hasLocalVariableTable
(),
"should only be called if table is present"
);
}
if
(
hasCheckedExceptions
())
{
if
(
hasExceptionTable
())
{
return
offsetOfExceptionTable
()
-
2
;
}
else
if
(
hasCheckedExceptions
())
{
return
offsetOfCheckedExceptions
()
-
2
;
}
else
{
return
offsetOfLastU2Element
();
...
...
@@ -432,4 +448,33 @@ public class ConstMethod extends Oop {
return
offset
;
}
private
int
getExceptionTableLength
()
{
if
(
hasExceptionTable
())
{
return
(
int
)
getHandle
().
getCIntegerAt
(
offsetOfExceptionTableLength
(),
2
,
true
);
}
else
{
return
0
;
}
}
private
long
offsetOfExceptionTableLength
()
{
if
(
Assert
.
ASSERTS_ENABLED
)
{
Assert
.
that
(
hasExceptionTable
(),
"should only be called if table is present"
);
}
if
(
hasCheckedExceptions
())
{
return
offsetOfCheckedExceptions
()
-
2
;
}
else
{
return
offsetOfLastU2Element
();
}
}
private
long
offsetOfExceptionTable
()
{
long
offset
=
offsetOfExceptionTableLength
();
long
length
=
getExceptionTableLength
();
if
(
Assert
.
ASSERTS_ENABLED
)
{
Assert
.
that
(
length
>
0
,
"should only be called if table is present"
);
}
offset
-=
length
*
exceptionTableElementSize
;
return
offset
;
}
}
agent/src/share/classes/sun/jvm/hotspot/oops/ExceptionTableElement.java
0 → 100644
浏览文件 @
f0bda8e5
/*
* Copyright (c) 2012, 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.
*
*/
package
sun.jvm.hotspot.oops
;
import
java.io.*
;
import
java.util.*
;
import
sun.jvm.hotspot.debugger.*
;
import
sun.jvm.hotspot.interpreter.*
;
import
sun.jvm.hotspot.runtime.*
;
import
sun.jvm.hotspot.types.*
;
import
sun.jvm.hotspot.utilities.*
;
public
class
ExceptionTableElement
{
static
{
VM
.
registerVMInitializedObserver
(
new
Observer
()
{
public
void
update
(
Observable
o
,
Object
data
)
{
initialize
(
VM
.
getVM
().
getTypeDataBase
());
}
});
}
private
static
synchronized
void
initialize
(
TypeDataBase
db
)
throws
WrongTypeException
{
Type
type
=
db
.
lookupType
(
"ExceptionTableElement"
);
offsetOfStartPC
=
type
.
getCIntegerField
(
"start_pc"
).
getOffset
();
offsetOfEndPC
=
type
.
getCIntegerField
(
"end_pc"
).
getOffset
();
offsetOfHandlerPC
=
type
.
getCIntegerField
(
"handler_pc"
).
getOffset
();
offsetOfCatchTypeIndex
=
type
.
getCIntegerField
(
"catch_type_index"
).
getOffset
();
}
private
static
long
offsetOfStartPC
;
private
static
long
offsetOfEndPC
;
private
static
long
offsetOfHandlerPC
;
private
static
long
offsetOfCatchTypeIndex
;
private
OopHandle
handle
;
private
long
offset
;
public
ExceptionTableElement
(
OopHandle
handle
,
long
offset
)
{
this
.
handle
=
handle
;
this
.
offset
=
offset
;
}
public
int
getStartPC
()
{
return
(
int
)
handle
.
getCIntegerAt
(
offset
+
offsetOfStartPC
,
2
,
true
);
}
public
int
getEndPC
()
{
return
(
int
)
handle
.
getCIntegerAt
(
offset
+
offsetOfEndPC
,
2
,
true
);
}
public
int
getHandlerPC
()
{
return
(
int
)
handle
.
getCIntegerAt
(
offset
+
offsetOfHandlerPC
,
2
,
true
);
}
public
int
getCatchTypeIndex
()
{
return
(
int
)
handle
.
getCIntegerAt
(
offset
+
offsetOfCatchTypeIndex
,
2
,
true
);
}
}
agent/src/share/classes/sun/jvm/hotspot/oops/GenerateOopMap.java
浏览文件 @
f0bda8e5
/*
* Copyright (c) 2001, 201
1
, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2001, 201
2
, 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
...
...
@@ -651,10 +651,11 @@ public class GenerateOopMap {
boolean
fellThrough
=
false
;
// False to get first BB marked.
// First mark all exception handlers as start of a basic-block
TypeArray
excps
=
method
().
getExceptionTable
();
for
(
int
i
=
0
;
i
<
excps
.
getLength
();
i
+=
4
)
{
int
handler_pc_idx
=
i
+
2
;
markBB
(
excps
.
getIntAt
(
handler_pc_idx
),
null
);
if
(
method
().
hasExceptionTable
())
{
ExceptionTableElement
[]
excps
=
method
().
getExceptionTable
();
for
(
int
i
=
0
;
i
<
excps
.
length
;
i
++)
{
markBB
(
excps
[
i
].
getHandlerPC
(),
null
);
}
}
// Then iterate through the code
...
...
@@ -891,14 +892,15 @@ public class GenerateOopMap {
// Mark entry basic block as alive and all exception handlers
_basic_blocks
[
0
].
markAsAlive
();
TypeArray
excps
=
method
().
getExceptionTable
();
for
(
int
i
=
0
;
i
<
excps
.
getLength
();
i
+=
4
)
{
int
handler_pc_idx
=
i
+
2
;
BasicBlock
bb
=
getBasicBlockAt
(
excps
.
getIntAt
(
handler_pc_idx
));
// If block is not already alive (due to multiple exception handlers to same bb), then
// make it alive
if
(
bb
.
isDead
())
bb
.
markAsAlive
();
if
(
method
().
hasExceptionTable
())
{
ExceptionTableElement
[]
excps
=
method
().
getExceptionTable
();
for
(
int
i
=
0
;
i
<
excps
.
length
;
i
++)
{
BasicBlock
bb
=
getBasicBlockAt
(
excps
[
i
].
getHandlerPC
());
// If block is not already alive (due to multiple exception handlers to same bb), then
// make it alive
if
(
bb
.
isDead
())
bb
.
markAsAlive
();
}
}
BytecodeStream
bcs
=
new
BytecodeStream
(
_method
);
...
...
@@ -1468,12 +1470,12 @@ public class GenerateOopMap {
if
(
_has_exceptions
)
{
int
bci
=
itr
.
bci
();
TypeArray
exct
=
method
().
getExceptionTable
();
for
(
int
i
=
0
;
i
<
exct
.
getLength
();
i
+=
4
)
{
int
start_pc
=
exct
.
getIntAt
(
i
);
int
end_pc
=
exct
.
getIntAt
(
i
+
1
);
int
handler_pc
=
exct
.
getIntAt
(
i
+
2
);
int
catch_type
=
exct
.
getIntAt
(
i
+
3
);
ExceptionTableElement
[]
exct
=
method
().
getExceptionTable
();
for
(
int
i
=
0
;
i
<
exct
.
length
;
i
++
)
{
int
start_pc
=
exct
[
i
].
getStartPC
(
);
int
end_pc
=
exct
[
i
].
getEndPC
(
);
int
handler_pc
=
exct
[
i
].
getHandlerPC
(
);
int
catch_type
=
exct
[
i
].
getCatchTypeIndex
(
);
if
(
start_pc
<=
bci
&&
bci
<
end_pc
)
{
BasicBlock
excBB
=
getBasicBlockAt
(
handler_pc
);
...
...
@@ -2151,7 +2153,7 @@ public class GenerateOopMap {
_conflict
=
false
;
_max_locals
=
(
int
)
method
().
getMaxLocals
();
_max_stack
=
(
int
)
method
().
getMaxStack
();
_has_exceptions
=
(
method
().
getExceptionTable
().
getLength
()
>
0
);
_has_exceptions
=
(
method
().
hasExceptionTable
()
);
_nof_refval_conflicts
=
0
;
_init_vars
=
new
ArrayList
(
5
);
// There are seldom more than 5 init_vars
_report_result
=
false
;
...
...
agent/src/share/classes/sun/jvm/hotspot/oops/Method.java
浏览文件 @
f0bda8e5
...
...
@@ -127,7 +127,6 @@ public class Method extends Oop {
return
getConstMethod
().
getConstants
();
}
public
MethodData
getMethodData
()
{
return
(
MethodData
)
methodData
.
getValue
(
this
);
}
public
TypeArray
getExceptionTable
()
{
return
getConstMethod
().
getExceptionTable
();
}
/** WARNING: this is in words, not useful in this system; use getObjectSize() instead */
public
long
getMethodSize
()
{
return
methodSize
.
getValue
(
this
);
}
public
long
getMaxStack
()
{
return
maxStack
.
getValue
(
this
);
}
...
...
@@ -328,6 +327,14 @@ public class Method extends Oop {
return
null
;
}
public
boolean
hasExceptionTable
()
{
return
getConstMethod
().
hasExceptionTable
();
}
public
ExceptionTableElement
[]
getExceptionTable
()
{
return
getConstMethod
().
getExceptionTable
();
}
public
boolean
hasCheckedExceptions
()
{
return
getConstMethod
().
hasCheckedExceptions
();
}
...
...
agent/src/share/classes/sun/jvm/hotspot/tools/jcore/ClassWriter.java
浏览文件 @
f0bda8e5
/*
* Copyright (c) 2002, 201
1
, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2002, 201
2
, 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
...
...
@@ -504,11 +504,14 @@ public class ClassWriter implements /* imports */ ClassConstants
2
/* exp. table len. */
+
2
/* code attr. count */
;
TypeArray
exceptionTable
=
m
.
getExceptionTable
();
final
int
exceptionTableLen
=
(
int
)
exceptionTable
.
getLength
();
if
(
exceptionTableLen
!=
0
)
{
boolean
hasExceptionTable
=
m
.
hasExceptionTable
();
ExceptionTableElement
[]
exceptionTable
=
null
;
int
exceptionTableLen
=
0
;
if
(
hasExceptionTable
)
{
exceptionTable
=
m
.
getExceptionTable
();
exceptionTableLen
=
exceptionTable
.
length
;
if
(
DEBUG
)
debugMessage
(
"\tmethod has exception table"
);
codeSize
+=
(
exceptionTableLen
/
4
)
/* exception table is 4-tuple array */
codeSize
+=
exceptionTableLen
/* exception table is 4-tuple array */
*
(
2
/* start_pc */
+
2
/* end_pc */
+
2
/* handler_pc */
+
...
...
@@ -586,15 +589,15 @@ public class ClassWriter implements /* imports */ ClassConstants
dos
.
write
(
code
);
// write exception table size
dos
.
writeShort
((
short
)
(
exceptionTableLen
/
4
)
);
if
(
DEBUG
)
debugMessage
(
"\texception table length = "
+
(
exceptionTableLen
/
4
)
);
dos
.
writeShort
((
short
)
exceptionTableLen
);
if
(
DEBUG
)
debugMessage
(
"\texception table length = "
+
exceptionTableLen
);
if
(
exceptionTableLen
!=
0
)
{
for
(
int
e
=
0
;
e
<
exceptionTableLen
;
e
+=
4
)
{
dos
.
writeShort
((
short
)
exceptionTable
.
getIntAt
(
e
));
dos
.
writeShort
((
short
)
exceptionTable
.
getIntAt
(
e
+
1
));
dos
.
writeShort
((
short
)
exceptionTable
.
getIntAt
(
e
+
2
));
dos
.
writeShort
((
short
)
exceptionTable
.
getIntAt
(
e
+
3
));
for
(
int
e
=
0
;
e
<
exceptionTableLen
;
e
++
)
{
dos
.
writeShort
((
short
)
exceptionTable
[
e
].
getStartPC
(
));
dos
.
writeShort
((
short
)
exceptionTable
[
e
].
getEndPC
(
));
dos
.
writeShort
((
short
)
exceptionTable
[
e
].
getHandlerPC
(
));
dos
.
writeShort
((
short
)
exceptionTable
[
e
].
getCatchTypeIndex
(
));
}
}
...
...
agent/src/share/classes/sun/jvm/hotspot/ui/classbrowser/HTMLGenerator.java
浏览文件 @
f0bda8e5
/*
* Copyright (c) 2002, 201
1
, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2002, 201
2
, 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
...
...
@@ -783,37 +783,39 @@ public class HTMLGenerator implements /* imports */ ClassConstants {
});
// display exception table for this method
TypeArray
exceptionTable
=
method
.
getExceptionTable
();
// exception table is 4 tuple array of shorts
int
numEntries
=
(
int
)
exceptionTable
.
getLength
()
/
4
;
if
(
numEntries
!=
0
)
{
buf
.
h4
(
"Exception Table"
);
buf
.
beginTable
(
1
);
buf
.
beginTag
(
"tr"
);
buf
.
headerCell
(
"start bci"
);
buf
.
headerCell
(
"end bci"
);
buf
.
headerCell
(
"handler bci"
);
buf
.
headerCell
(
"catch type"
);
buf
.
endTag
(
"tr"
);
for
(
int
e
=
0
;
e
<
numEntries
;
e
+=
4
)
{
boolean
hasException
=
method
.
hasExceptionTable
();
if
(
hasException
)
{
ExceptionTableElement
[]
exceptionTable
=
method
.
getExceptionTable
();
int
numEntries
=
exceptionTable
.
length
;
if
(
numEntries
!=
0
)
{
buf
.
h4
(
"Exception Table"
);
buf
.
beginTable
(
1
);
buf
.
beginTag
(
"tr"
);
buf
.
cell
(
Integer
.
toString
(
exceptionTable
.
getIntAt
(
e
)));
buf
.
cell
(
Integer
.
toString
(
exceptionTable
.
getIntAt
(
e
+
1
)));
buf
.
cell
(
Integer
.
toString
(
exceptionTable
.
getIntAt
(
e
+
2
)));
short
cpIndex
=
(
short
)
exceptionTable
.
getIntAt
(
e
+
3
);
ConstantPool
.
CPSlot
obj
=
cpIndex
==
0
?
null
:
cpool
.
getSlotAt
(
cpIndex
);
if
(
obj
==
null
)
{
buf
.
cell
(
"Any"
);
}
else
if
(
obj
.
isMetaData
())
{
buf
.
cell
(
obj
.
getSymbol
().
asString
().
replace
(
'/'
,
'.'
));
}
else
{
buf
.
cell
(
genKlassLink
((
InstanceKlass
)
obj
.
getOop
()));
}
buf
.
headerCell
(
"start bci"
);
buf
.
headerCell
(
"end bci"
);
buf
.
headerCell
(
"handler bci"
);
buf
.
headerCell
(
"catch type"
);
buf
.
endTag
(
"tr"
);
}
buf
.
endTable
();
for
(
int
e
=
0
;
e
<
numEntries
;
e
++)
{
buf
.
beginTag
(
"tr"
);
buf
.
cell
(
Integer
.
toString
(
exceptionTable
[
e
].
getStartPC
()));
buf
.
cell
(
Integer
.
toString
(
exceptionTable
[
e
].
getEndPC
()));
buf
.
cell
(
Integer
.
toString
(
exceptionTable
[
e
].
getHandlerPC
()));
short
cpIndex
=
(
short
)
exceptionTable
[
e
].
getCatchTypeIndex
();
ConstantPool
.
CPSlot
obj
=
cpIndex
==
0
?
null
:
cpool
.
getSlotAt
(
cpIndex
);
if
(
obj
==
null
)
{
buf
.
cell
(
"Any"
);
}
else
if
(
obj
.
isMetaData
())
{
buf
.
cell
(
obj
.
getSymbol
().
asString
().
replace
(
'/'
,
'.'
));
}
else
{
buf
.
cell
(
genKlassLink
((
InstanceKlass
)
obj
.
getOop
()));
}
buf
.
endTag
(
"tr"
);
}
buf
.
endTable
();
}
}
// display constant pool hyperlink
...
...
src/share/vm/ci/ciMethod.cpp
浏览文件 @
f0bda8e5
/*
* Copyright (c) 1999, 201
1
, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 1999, 201
2
, 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
...
...
@@ -79,7 +79,7 @@ ciMethod::ciMethod(methodHandle h_m) : ciObject(h_m) {
_max_locals
=
h_m
()
->
max_locals
();
_code_size
=
h_m
()
->
code_size
();
_intrinsic_id
=
h_m
()
->
intrinsic_id
();
_handler_count
=
h_m
()
->
exception_table
()
->
length
()
/
4
;
_handler_count
=
h_m
()
->
exception_table
_length
()
;
_uses_monitors
=
h_m
()
->
access_flags
().
has_monitor_bytecodes
();
_balanced_monitors
=
!
_uses_monitors
||
h_m
()
->
access_flags
().
is_monitor_matching
();
_is_c1_compilable
=
!
h_m
()
->
is_not_c1_compilable
();
...
...
@@ -198,7 +198,7 @@ void ciMethod::load_code() {
}
// And load the exception table.
typeArrayOop
exc_table
=
me
->
exception_table
(
);
ExceptionTable
exc_table
(
me
);
// Allocate one extra spot in our list of exceptions. This
// last entry will be used to represent the possibility that
...
...
@@ -209,13 +209,12 @@ void ciMethod::load_code() {
*
(
_handler_count
+
1
));
if
(
_handler_count
>
0
)
{
for
(
int
i
=
0
;
i
<
_handler_count
;
i
++
)
{
int
base
=
i
*
4
;
_exception_handlers
[
i
]
=
new
(
arena
)
ciExceptionHandler
(
holder
(),
/* start */
exc_table
->
int_at
(
base
),
/* limit */
exc_table
->
int_at
(
base
+
1
),
/* goto pc */
exc_table
->
int_at
(
base
+
2
),
/* cp index */
exc_table
->
int_at
(
base
+
3
));
/* start */
exc_table
.
start_pc
(
i
),
/* limit */
exc_table
.
end_pc
(
i
),
/* goto pc */
exc_table
.
handler_pc
(
i
),
/* cp index */
exc_table
.
catch_type_index
(
i
));
}
}
...
...
src/share/vm/classfile/classFileParser.cpp
浏览文件 @
f0bda8e5
...
...
@@ -1284,42 +1284,38 @@ static void copy_u2_with_conversion(u2* dest, u2* src, int length) {
}
typeArrayHandle
ClassFileParser
::
parse_exception_table
(
u4
code_length
,
u4
exception_table_length
,
constantPoolHandle
cp
,
TRAPS
)
{
u2
*
ClassFileParser
::
parse_exception_table
(
u4
code_length
,
u4
exception_table_length
,
constantPoolHandle
cp
,
TRAPS
)
{
ClassFileStream
*
cfs
=
stream
();
typeArrayHandle
nullHandle
;
// 4-tuples of ints [start_pc, end_pc, handler_pc, catch_type index]
typeArrayOop
eh
=
oopFactory
::
new_permanent_intArray
(
exception_table_length
*
4
,
CHECK_
(
nullHandle
));
typeArrayHandle
exception_handlers
=
typeArrayHandle
(
THREAD
,
eh
);
int
index
=
0
;
cfs
->
guarantee_more
(
8
*
exception_table_length
,
CHECK_
(
nullHandle
));
// start_pc, end_pc, handler_pc, catch_type_index
for
(
unsigned
int
i
=
0
;
i
<
exception_table_length
;
i
++
)
{
u2
start_pc
=
cfs
->
get_u2_fast
();
u2
end_pc
=
cfs
->
get_u2_fast
();
u2
handler_pc
=
cfs
->
get_u2_fast
();
u2
catch_type_index
=
cfs
->
get_u2_fast
();
// Will check legal target after parsing code array in verifier.
if
(
_need_verify
)
{
u2
*
exception_table_start
=
cfs
->
get_u2_buffer
();
assert
(
exception_table_start
!=
NULL
,
"null exception table"
);
cfs
->
guarantee_more
(
8
*
exception_table_length
,
CHECK_NULL
);
// start_pc, end_pc, handler_pc, catch_type_index
// Will check legal target after parsing code array in verifier.
if
(
_need_verify
)
{
for
(
unsigned
int
i
=
0
;
i
<
exception_table_length
;
i
++
)
{
u2
start_pc
=
cfs
->
get_u2_fast
();
u2
end_pc
=
cfs
->
get_u2_fast
();
u2
handler_pc
=
cfs
->
get_u2_fast
();
u2
catch_type_index
=
cfs
->
get_u2_fast
();
guarantee_property
((
start_pc
<
end_pc
)
&&
(
end_pc
<=
code_length
),
"Illegal exception table range in class file %s"
,
CHECK_
(
nullHandle
));
"Illegal exception table range in class file %s"
,
CHECK_NULL
);
guarantee_property
(
handler_pc
<
code_length
,
"Illegal exception table handler in class file %s"
,
CHECK_
(
nullHandle
));
"Illegal exception table handler in class file %s"
,
CHECK_NULL
);
if
(
catch_type_index
!=
0
)
{
guarantee_property
(
valid_cp_range
(
catch_type_index
,
cp
->
length
())
&&
is_klass_reference
(
cp
,
catch_type_index
),
"Catch type in exception table has bad constant type in class file %s"
,
CHECK_
(
nullHandle
)
);
"Catch type in exception table has bad constant type in class file %s"
,
CHECK_
NULL
);
}
}
exception_handlers
->
int_at_put
(
index
++
,
start_pc
);
exception_handlers
->
int_at_put
(
index
++
,
end_pc
);
exception_handlers
->
int_at_put
(
index
++
,
handler_pc
);
exception_handlers
->
int_at_put
(
index
++
,
catch_type_index
);
}
else
{
cfs
->
skip_u2_fast
(
exception_table_length
*
4
);
}
return
exception_
handlers
;
return
exception_
table_start
;
}
void
ClassFileParser
::
parse_linenumber_table
(
...
...
@@ -1712,6 +1708,7 @@ methodHandle ClassFileParser::parse_method(constantPoolHandle cp, bool is_interf
u4
code_length
=
0
;
u1
*
code_start
=
0
;
u2
exception_table_length
=
0
;
u2
*
exception_table_start
=
NULL
;
typeArrayHandle
exception_handlers
(
THREAD
,
Universe
::
the_empty_int_array
());
u2
checked_exceptions_length
=
0
;
u2
*
checked_exceptions_start
=
NULL
;
...
...
@@ -1798,7 +1795,7 @@ methodHandle ClassFileParser::parse_method(constantPoolHandle cp, bool is_interf
cfs
->
guarantee_more
(
2
,
CHECK_
(
nullHandle
));
// exception_table_length
exception_table_length
=
cfs
->
get_u2_fast
();
if
(
exception_table_length
>
0
)
{
exception_
handlers
=
exception_
table_start
=
parse_exception_table
(
code_length
,
exception_table_length
,
cp
,
CHECK_
(
nullHandle
));
}
...
...
@@ -2002,9 +1999,13 @@ methodHandle ClassFileParser::parse_method(constantPoolHandle cp, bool is_interf
}
// All sizing information for a methodOop is finally available, now create it
methodOop
m_oop
=
oopFactory
::
new_method
(
code_length
,
access_flags
,
linenumber_table_length
,
total_lvt_length
,
checked_exceptions_length
,
oopDesc
::
IsSafeConc
,
CHECK_
(
nullHandle
));
methodOop
m_oop
=
oopFactory
::
new_method
(
code_length
,
access_flags
,
linenumber_table_length
,
total_lvt_length
,
exception_table_length
,
checked_exceptions_length
,
oopDesc
::
IsSafeConc
,
CHECK_
(
nullHandle
));
methodHandle
m
(
THREAD
,
m_oop
);
ClassLoadingService
::
add_class_method_size
(
m_oop
->
size
()
*
HeapWordSize
);
...
...
@@ -2035,16 +2036,15 @@ methodHandle ClassFileParser::parse_method(constantPoolHandle cp, bool is_interf
// Fill in code attribute information
m
->
set_max_stack
(
max_stack
);
m
->
set_max_locals
(
max_locals
);
m
->
constMethod
()
->
set_stackmap_data
(
stackmap_data
());
/**
* The
exception_table
field is the flag used to indicate
* The
stackmap_data
field is the flag used to indicate
* that the methodOop and it's associated constMethodOop are partially
* initialized and thus are exempt from pre/post GC verification. Once
* the field is set, the oops are considered fully initialized so make
* sure that the oops can pass verification when this field is set.
*/
m
->
set_exception_table
(
exception_handlers
());
m
->
constMethod
()
->
set_stackmap_data
(
stackmap_data
());
// Copy byte codes
m
->
set_code
(
code_start
);
...
...
@@ -2055,6 +2055,14 @@ methodHandle ClassFileParser::parse_method(constantPoolHandle cp, bool is_interf
linenumber_table
->
buffer
(),
linenumber_table_length
);
}
// Copy exception table
if
(
exception_table_length
>
0
)
{
int
size
=
exception_table_length
*
sizeof
(
ExceptionTableElement
)
/
sizeof
(
u2
);
copy_u2_with_conversion
((
u2
*
)
m
->
exception_table_start
(),
exception_table_start
,
size
);
}
// Copy checked exceptions
if
(
checked_exceptions_length
>
0
)
{
int
size
=
checked_exceptions_length
*
sizeof
(
CheckedExceptionElement
)
/
sizeof
(
u2
);
...
...
src/share/vm/classfile/classFileParser.hpp
浏览文件 @
f0bda8e5
...
...
@@ -113,8 +113,8 @@ class ClassFileParser VALUE_OBJ_CLASS_SPEC {
objArrayHandle
methods_parameter_annotations
,
objArrayHandle
methods_default_annotations
,
TRAPS
);
typeArrayHandle
parse_exception_table
(
u4
code_length
,
u4
exception_table_length
,
constantPoolHandle
cp
,
TRAPS
);
u2
*
parse_exception_table
(
u4
code_length
,
u4
exception_table_length
,
constantPoolHandle
cp
,
TRAPS
);
void
parse_linenumber_table
(
u4
code_attribute_length
,
u4
code_length
,
CompressedLineNumberWriteStream
**
write_stream
,
TRAPS
);
...
...
src/share/vm/classfile/systemDictionary.cpp
浏览文件 @
f0bda8e5
...
...
@@ -2771,7 +2771,6 @@ class ClassStatistics: AllStatic {
nmethods
++
;
method_size
+=
m
->
size
();
// class loader uses same objArray for empty vectors, so don't count these
if
(
m
->
exception_table
()
->
length
()
!=
0
)
method_size
+=
m
->
exception_table
()
->
size
();
if
(
m
->
has_stackmap_table
())
{
method_size
+=
m
->
stackmap_data
()
->
size
();
}
...
...
src/share/vm/classfile/verifier.cpp
浏览文件 @
f0bda8e5
/*
* Copyright (c) 1998, 201
1
, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 1998, 201
2
, 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
...
...
@@ -1368,47 +1368,48 @@ char* ClassVerifier::generate_code_data(methodHandle m, u4 code_length, TRAPS) {
}
void
ClassVerifier
::
verify_exception_handler_table
(
u4
code_length
,
char
*
code_data
,
int
&
min
,
int
&
max
,
TRAPS
)
{
typeArrayHandle
exhandlers
(
THREAD
,
_method
->
exception_table
());
ExceptionTable
exhandlers
(
_method
());
int
exlength
=
exhandlers
.
length
();
constantPoolHandle
cp
(
THREAD
,
_method
->
constants
());
if
(
exhandlers
()
!=
NULL
)
{
for
(
int
i
=
0
;
i
<
exhandlers
->
length
();)
{
u2
start_pc
=
exhandlers
->
int_at
(
i
++
);
u2
end_pc
=
exhandlers
->
int_at
(
i
++
);
u2
handler_pc
=
exhandlers
->
int_at
(
i
++
);
if
(
start_pc
>=
code_length
||
code_data
[
start_pc
]
==
0
)
{
class_format_error
(
"Illegal exception table start_pc %d"
,
start_pc
);
for
(
int
i
=
0
;
i
<
exlength
;
i
++
)
{
//reacquire the table in case a GC happened
ExceptionTable
exhandlers
(
_method
());
u2
start_pc
=
exhandlers
.
start_pc
(
i
);
u2
end_pc
=
exhandlers
.
end_pc
(
i
);
u2
handler_pc
=
exhandlers
.
handler_pc
(
i
);
if
(
start_pc
>=
code_length
||
code_data
[
start_pc
]
==
0
)
{
class_format_error
(
"Illegal exception table start_pc %d"
,
start_pc
);
return
;
}
if
(
end_pc
!=
code_length
)
{
// special case: end_pc == code_length
if
(
end_pc
>
code_length
||
code_data
[
end_pc
]
==
0
)
{
class_format_error
(
"Illegal exception table end_pc %d"
,
end_pc
);
return
;
}
if
(
end_pc
!=
code_length
)
{
// special case: end_pc == code_length
if
(
end_pc
>
code_length
||
code_data
[
end_pc
]
==
0
)
{
class_format_error
(
"Illegal exception table end_pc %d"
,
end_pc
);
return
;
}
}
if
(
handler_pc
>=
code_length
||
code_data
[
handler_pc
]
==
0
)
{
class_format_error
(
"Illegal exception table handler_pc %d"
,
handler_pc
);
}
if
(
handler_pc
>=
code_length
||
code_data
[
handler_pc
]
==
0
)
{
class_format_error
(
"Illegal exception table handler_pc %d"
,
handler_pc
);
return
;
}
int
catch_type_index
=
exhandlers
.
catch_type_index
(
i
);
if
(
catch_type_index
!=
0
)
{
VerificationType
catch_type
=
cp_index_to_type
(
catch_type_index
,
cp
,
CHECK_VERIFY
(
this
));
VerificationType
throwable
=
VerificationType
::
reference_type
(
vmSymbols
::
java_lang_Throwable
());
bool
is_subclass
=
throwable
.
is_assignable_from
(
catch_type
,
this
,
CHECK_VERIFY
(
this
));
if
(
!
is_subclass
)
{
// 4286534: should throw VerifyError according to recent spec change
verify_error
(
"Catch type is not a subclass of Throwable in handler %d"
,
handler_pc
);
return
;
}
int
catch_type_index
=
exhandlers
->
int_at
(
i
++
);
if
(
catch_type_index
!=
0
)
{
VerificationType
catch_type
=
cp_index_to_type
(
catch_type_index
,
cp
,
CHECK_VERIFY
(
this
));
VerificationType
throwable
=
VerificationType
::
reference_type
(
vmSymbols
::
java_lang_Throwable
());
bool
is_subclass
=
throwable
.
is_assignable_from
(
catch_type
,
this
,
CHECK_VERIFY
(
this
));
if
(
!
is_subclass
)
{
// 4286534: should throw VerifyError according to recent spec change
verify_error
(
"Catch type is not a subclass of Throwable in handler %d"
,
handler_pc
);
return
;
}
}
if
(
start_pc
<
min
)
min
=
start_pc
;
if
(
end_pc
>
max
)
max
=
end_pc
;
}
if
(
start_pc
<
min
)
min
=
start_pc
;
if
(
end_pc
>
max
)
max
=
end_pc
;
}
}
...
...
@@ -1474,35 +1475,36 @@ u2 ClassVerifier::verify_stackmap_table(u2 stackmap_index, u2 bci,
void
ClassVerifier
::
verify_exception_handler_targets
(
u2
bci
,
bool
this_uninit
,
StackMapFrame
*
current_frame
,
StackMapTable
*
stackmap_table
,
TRAPS
)
{
constantPoolHandle
cp
(
THREAD
,
_method
->
constants
());
typeArrayHandle
exhandlers
(
THREAD
,
_method
->
exception_table
());
if
(
exhandlers
()
!=
NULL
)
{
for
(
int
i
=
0
;
i
<
exhandlers
->
length
();)
{
u2
start_pc
=
exhandlers
->
int_at
(
i
++
);
u2
end_pc
=
exhandlers
->
int_at
(
i
++
);
u2
handler_pc
=
exhandlers
->
int_at
(
i
++
);
int
catch_type_index
=
exhandlers
->
int_at
(
i
++
);
if
(
bci
>=
start_pc
&&
bci
<
end_pc
)
{
u1
flags
=
current_frame
->
flags
();
if
(
this_uninit
)
{
flags
|=
FLAG_THIS_UNINIT
;
}
StackMapFrame
*
new_frame
=
current_frame
->
frame_in_exception_handler
(
flags
);
if
(
catch_type_index
!=
0
)
{
// We know that this index refers to a subclass of Throwable
VerificationType
catch_type
=
cp_index_to_type
(
catch_type_index
,
cp
,
CHECK_VERIFY
(
this
));
new_frame
->
push_stack
(
catch_type
,
CHECK_VERIFY
(
this
));
}
else
{
VerificationType
throwable
=
VerificationType
::
reference_type
(
vmSymbols
::
java_lang_Throwable
());
new_frame
->
push_stack
(
throwable
,
CHECK_VERIFY
(
this
));
}
bool
match
=
stackmap_table
->
match_stackmap
(
new_frame
,
handler_pc
,
true
,
false
,
CHECK_VERIFY
(
this
));
if
(
!
match
)
{
verify_error
(
bci
,
"Stack map does not match the one at exception handler %d"
,
handler_pc
);
return
;
}
ExceptionTable
exhandlers
(
_method
());
int
exlength
=
exhandlers
.
length
();
for
(
int
i
=
0
;
i
<
exlength
;
i
++
)
{
//reacquire the table in case a GC happened
ExceptionTable
exhandlers
(
_method
());
u2
start_pc
=
exhandlers
.
start_pc
(
i
);
u2
end_pc
=
exhandlers
.
end_pc
(
i
);
u2
handler_pc
=
exhandlers
.
handler_pc
(
i
);
int
catch_type_index
=
exhandlers
.
catch_type_index
(
i
);
if
(
bci
>=
start_pc
&&
bci
<
end_pc
)
{
u1
flags
=
current_frame
->
flags
();
if
(
this_uninit
)
{
flags
|=
FLAG_THIS_UNINIT
;
}
StackMapFrame
*
new_frame
=
current_frame
->
frame_in_exception_handler
(
flags
);
if
(
catch_type_index
!=
0
)
{
// We know that this index refers to a subclass of Throwable
VerificationType
catch_type
=
cp_index_to_type
(
catch_type_index
,
cp
,
CHECK_VERIFY
(
this
));
new_frame
->
push_stack
(
catch_type
,
CHECK_VERIFY
(
this
));
}
else
{
VerificationType
throwable
=
VerificationType
::
reference_type
(
vmSymbols
::
java_lang_Throwable
());
new_frame
->
push_stack
(
throwable
,
CHECK_VERIFY
(
this
));
}
bool
match
=
stackmap_table
->
match_stackmap
(
new_frame
,
handler_pc
,
true
,
false
,
CHECK_VERIFY
(
this
));
if
(
!
match
)
{
verify_error
(
bci
,
"Stack map does not match the one at exception handler %d"
,
handler_pc
);
return
;
}
}
}
...
...
src/share/vm/interpreter/interpreterRuntime.cpp
浏览文件 @
f0bda8e5
/*
* Copyright (c) 1997, 201
1
, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 1997, 201
2
, 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
...
...
@@ -375,7 +375,6 @@ IRT_ENTRY(address, InterpreterRuntime::exception_handler_for_exception(JavaThrea
Handle
h_exception
(
thread
,
exception
);
methodHandle
h_method
(
thread
,
method
(
thread
));
constantPoolHandle
h_constants
(
thread
,
h_method
->
constants
());
typeArrayHandle
h_extable
(
thread
,
h_method
->
exception_table
());
bool
should_repeat
;
int
handler_bci
;
int
current_bci
=
bci
(
thread
);
...
...
src/share/vm/memory/dump.cpp
浏览文件 @
f0bda8e5
...
...
@@ -231,8 +231,6 @@ public:
if
(
obj
->
is_constMethod
())
{
mark_object
(
obj
);
mark_object
(
constMethodOop
(
obj
)
->
stackmap_data
());
// Exception tables are needed by ci code during compilation.
mark_object
(
constMethodOop
(
obj
)
->
exception_table
());
}
// Mark objects referenced by klass objects which are read-only.
...
...
@@ -513,7 +511,6 @@ public:
for
(
i
=
0
;
i
<
methods
->
length
();
i
++
)
{
methodOop
m
=
methodOop
(
methods
->
obj_at
(
i
));
mark_and_move_for_policy
(
OP_favor_startup
,
m
->
constMethod
(),
_move_ro
);
mark_and_move_for_policy
(
OP_favor_runtime
,
m
->
constMethod
()
->
exception_table
(),
_move_ro
);
mark_and_move_for_policy
(
OP_favor_runtime
,
m
->
constMethod
()
->
stackmap_data
(),
_move_ro
);
}
...
...
src/share/vm/memory/oopFactory.cpp
浏览文件 @
f0bda8e5
...
...
@@ -140,14 +140,15 @@ klassOop oopFactory::new_instanceKlass(Symbol* name, int vtable_len, int itable_
constMethodOop
oopFactory
::
new_constMethod
(
int
byte_code_size
,
int
compressed_line_number_size
,
int
localvariable_table_length
,
int
exception_table_length
,
int
checked_exceptions_length
,
bool
is_conc_safe
,
TRAPS
)
{
klassOop
cmkObj
=
Universe
::
constMethodKlassObj
();
constMethodKlass
*
cmk
=
constMethodKlass
::
cast
(
cmkObj
);
return
cmk
->
allocate
(
byte_code_size
,
compressed_line_number_size
,
localvariable_table_length
,
checked_exceptions
_length
,
is_conc_safe
,
localvariable_table_length
,
exception_table
_length
,
checked_exceptions_length
,
is_conc_safe
,
CHECK_NULL
);
}
...
...
@@ -155,6 +156,7 @@ constMethodOop oopFactory::new_constMethod(int byte_code_size,
methodOop
oopFactory
::
new_method
(
int
byte_code_size
,
AccessFlags
access_flags
,
int
compressed_line_number_size
,
int
localvariable_table_length
,
int
exception_table_length
,
int
checked_exceptions_length
,
bool
is_conc_safe
,
TRAPS
)
{
...
...
@@ -164,6 +166,7 @@ methodOop oopFactory::new_method(int byte_code_size, AccessFlags access_flags,
constMethodOop
cm
=
new_constMethod
(
byte_code_size
,
compressed_line_number_size
,
localvariable_table_length
,
exception_table_length
,
checked_exceptions_length
,
is_conc_safe
,
CHECK_NULL
);
constMethodHandle
rw
(
THREAD
,
cm
);
...
...
src/share/vm/memory/oopFactory.hpp
浏览文件 @
f0bda8e5
...
...
@@ -86,6 +86,7 @@ private:
static
constMethodOop
new_constMethod
(
int
byte_code_size
,
int
compressed_line_number_size
,
int
localvariable_table_length
,
int
exception_table_length
,
int
checked_exceptions_length
,
bool
is_conc_safe
,
TRAPS
);
...
...
@@ -97,6 +98,7 @@ public:
AccessFlags
access_flags
,
int
compressed_line_number_size
,
int
localvariable_table_length
,
int
exception_table_length
,
int
checked_exceptions_length
,
bool
is_conc_safe
,
TRAPS
);
...
...
src/share/vm/oops/constMethodKlass.cpp
浏览文件 @
f0bda8e5
...
...
@@ -65,6 +65,7 @@ bool constMethodKlass::oop_is_conc_safe(oop obj) const {
constMethodOop
constMethodKlass
::
allocate
(
int
byte_code_size
,
int
compressed_line_number_size
,
int
localvariable_table_length
,
int
exception_table_length
,
int
checked_exceptions_length
,
bool
is_conc_safe
,
TRAPS
)
{
...
...
@@ -72,6 +73,7 @@ constMethodOop constMethodKlass::allocate(int byte_code_size,
int
size
=
constMethodOopDesc
::
object_size
(
byte_code_size
,
compressed_line_number_size
,
localvariable_table_length
,
exception_table_length
,
checked_exceptions_length
);
KlassHandle
h_k
(
THREAD
,
as_klassOop
());
constMethodOop
cm
=
(
constMethodOop
)
...
...
@@ -82,12 +84,12 @@ constMethodOop constMethodKlass::allocate(int byte_code_size,
cm
->
init_fingerprint
();
cm
->
set_constants
(
NULL
);
cm
->
set_stackmap_data
(
NULL
);
cm
->
set_exception_table
(
NULL
);
cm
->
set_code_size
(
byte_code_size
);
cm
->
set_constMethod_size
(
size
);
cm
->
set_inlined_tables_length
(
checked_exceptions_length
,
compressed_line_number_size
,
localvariable_table_length
);
localvariable_table_length
,
exception_table_length
);
assert
(
cm
->
size
()
==
size
,
"wrong size for object"
);
cm
->
set_is_conc_safe
(
is_conc_safe
);
cm
->
set_partially_loaded
();
...
...
@@ -100,7 +102,6 @@ void constMethodKlass::oop_follow_contents(oop obj) {
constMethodOop
cm
=
constMethodOop
(
obj
);
MarkSweep
::
mark_and_push
(
cm
->
adr_constants
());
MarkSweep
::
mark_and_push
(
cm
->
adr_stackmap_data
());
MarkSweep
::
mark_and_push
(
cm
->
adr_exception_table
());
// Performance tweak: We skip iterating over the klass pointer since we
// know that Universe::constMethodKlassObj never moves.
}
...
...
@@ -112,7 +113,6 @@ void constMethodKlass::oop_follow_contents(ParCompactionManager* cm,
constMethodOop
cm_oop
=
constMethodOop
(
obj
);
PSParallelCompact
::
mark_and_push
(
cm
,
cm_oop
->
adr_constants
());
PSParallelCompact
::
mark_and_push
(
cm
,
cm_oop
->
adr_stackmap_data
());
PSParallelCompact
::
mark_and_push
(
cm
,
cm_oop
->
adr_exception_table
());
// Performance tweak: We skip iterating over the klass pointer since we
// know that Universe::constMethodKlassObj never moves.
}
...
...
@@ -123,7 +123,6 @@ int constMethodKlass::oop_oop_iterate(oop obj, OopClosure* blk) {
constMethodOop
cm
=
constMethodOop
(
obj
);
blk
->
do_oop
(
cm
->
adr_constants
());
blk
->
do_oop
(
cm
->
adr_stackmap_data
());
blk
->
do_oop
(
cm
->
adr_exception_table
());
// Get size before changing pointers.
// Don't call size() or oop_size() since that is a virtual call.
int
size
=
cm
->
object_size
();
...
...
@@ -139,8 +138,6 @@ int constMethodKlass::oop_oop_iterate_m(oop obj, OopClosure* blk, MemRegion mr)
if
(
mr
.
contains
(
adr
))
blk
->
do_oop
(
adr
);
adr
=
cm
->
adr_stackmap_data
();
if
(
mr
.
contains
(
adr
))
blk
->
do_oop
(
adr
);
adr
=
cm
->
adr_exception_table
();
if
(
mr
.
contains
(
adr
))
blk
->
do_oop
(
adr
);
// Get size before changing pointers.
// Don't call size() or oop_size() since that is a virtual call.
int
size
=
cm
->
object_size
();
...
...
@@ -155,7 +152,6 @@ int constMethodKlass::oop_adjust_pointers(oop obj) {
constMethodOop
cm
=
constMethodOop
(
obj
);
MarkSweep
::
adjust_pointer
(
cm
->
adr_constants
());
MarkSweep
::
adjust_pointer
(
cm
->
adr_stackmap_data
());
MarkSweep
::
adjust_pointer
(
cm
->
adr_exception_table
());
// Get size before changing pointers.
// Don't call size() or oop_size() since that is a virtual call.
int
size
=
cm
->
object_size
();
...
...
@@ -190,7 +186,6 @@ void constMethodKlass::oop_print_on(oop obj, outputStream* st) {
constMethodOop
m
=
constMethodOop
(
obj
);
st
->
print
(
" - constants: "
INTPTR_FORMAT
" "
,
(
address
)
m
->
constants
());
m
->
constants
()
->
print_value_on
(
st
);
st
->
cr
();
st
->
print
(
" - exceptions: "
INTPTR_FORMAT
"
\n
"
,
(
address
)
m
->
exception_table
());
if
(
m
->
has_stackmap_table
())
{
st
->
print
(
" - stackmap data: "
);
m
->
stackmap_data
()
->
print_value_on
(
st
);
...
...
@@ -228,8 +223,6 @@ void constMethodKlass::oop_verify_on(oop obj, outputStream* st) {
typeArrayOop
stackmap_data
=
m
->
stackmap_data
();
guarantee
(
stackmap_data
==
NULL
||
stackmap_data
->
is_perm
(),
"should be in permspace"
);
guarantee
(
m
->
exception_table
()
->
is_perm
(),
"should be in permspace"
);
guarantee
(
m
->
exception_table
()
->
is_typeArray
(),
"should be type array"
);
address
m_end
=
(
address
)((
oop
*
)
m
+
m
->
size
());
address
compressed_table_start
=
m
->
code_end
();
...
...
@@ -244,11 +237,15 @@ void constMethodKlass::oop_verify_on(oop obj, outputStream* st) {
compressed_table_end
+=
stream
.
position
();
}
guarantee
(
compressed_table_end
<=
m_end
,
"invalid method layout"
);
// Verify checked exceptions and local variable tables
// Verify checked exceptions
, exception table
and local variable tables
if
(
m
->
has_checked_exceptions
())
{
u2
*
addr
=
m
->
checked_exceptions_length_addr
();
guarantee
(
*
addr
>
0
&&
(
address
)
addr
>=
compressed_table_end
&&
(
address
)
addr
<
m_end
,
"invalid method layout"
);
}
if
(
m
->
has_exception_handler
())
{
u2
*
addr
=
m
->
exception_table_length_addr
();
guarantee
(
*
addr
>
0
&&
(
address
)
addr
>=
compressed_table_end
&&
(
address
)
addr
<
m_end
,
"invalid method layout"
);
}
if
(
m
->
has_localvariable_table
())
{
u2
*
addr
=
m
->
localvariable_table_length_addr
();
guarantee
(
*
addr
>
0
&&
(
address
)
addr
>=
compressed_table_end
&&
(
address
)
addr
<
m_end
,
"invalid method layout"
);
...
...
@@ -257,12 +254,12 @@ void constMethodKlass::oop_verify_on(oop obj, outputStream* st) {
u2
*
uncompressed_table_start
;
if
(
m
->
has_localvariable_table
())
{
uncompressed_table_start
=
(
u2
*
)
m
->
localvariable_table_start
();
}
else
{
if
(
m
->
has_checked_exceptions
())
{
}
else
if
(
m
->
has_exception_handler
())
{
uncompressed_table_start
=
(
u2
*
)
m
->
exception_table_start
();
}
else
if
(
m
->
has_checked_exceptions
())
{
uncompressed_table_start
=
(
u2
*
)
m
->
checked_exceptions_start
();
}
else
{
}
else
{
uncompressed_table_start
=
(
u2
*
)
m_end
;
}
}
int
gap
=
(
intptr_t
)
uncompressed_table_start
-
(
intptr_t
)
compressed_table_end
;
int
max_gap
=
align_object_size
(
1
)
*
BytesPerWord
;
...
...
@@ -273,8 +270,8 @@ void constMethodKlass::oop_verify_on(oop obj, outputStream* st) {
bool
constMethodKlass
::
oop_partially_loaded
(
oop
obj
)
const
{
assert
(
obj
->
is_constMethod
(),
"object must be klass"
);
constMethodOop
m
=
constMethodOop
(
obj
);
// check whether
exception_table
points to self (flag for partially loaded)
return
m
->
exception_table
()
==
(
typeArrayOop
)
obj
;
// check whether
stackmap_data
points to self (flag for partially loaded)
return
m
->
stackmap_data
()
==
(
typeArrayOop
)
obj
;
}
...
...
@@ -282,6 +279,6 @@ bool constMethodKlass::oop_partially_loaded(oop obj) const {
void
constMethodKlass
::
oop_set_partially_loaded
(
oop
obj
)
{
assert
(
obj
->
is_constMethod
(),
"object must be klass"
);
constMethodOop
m
=
constMethodOop
(
obj
);
// Temporarily set
exception_table
to point to self
m
->
set_
exception_table
((
typeArrayOop
)
obj
);
// Temporarily set
stackmap_data
to point to self
m
->
set_
stackmap_data
((
typeArrayOop
)
obj
);
}
src/share/vm/oops/constMethodKlass.hpp
浏览文件 @
f0bda8e5
/*
* Copyright (c) 2003, 201
0
, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2003, 201
2
, 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
...
...
@@ -46,6 +46,7 @@ public:
DEFINE_ALLOCATE_PERMANENT
(
constMethodKlass
);
constMethodOop
allocate
(
int
byte_code_size
,
int
compressed_line_number_size
,
int
localvariable_table_length
,
int
exception_table_length
,
int
checked_exceptions_length
,
bool
is_conc_safe
,
TRAPS
);
...
...
src/share/vm/oops/constMethodOop.cpp
浏览文件 @
f0bda8e5
...
...
@@ -35,6 +35,7 @@ const u2 constMethodOopDesc::UNSET_IDNUM = 0xFFFF;
int
constMethodOopDesc
::
object_size
(
int
code_size
,
int
compressed_line_number_size
,
int
local_variable_table_length
,
int
exception_table_length
,
int
checked_exceptions_length
)
{
int
extra_bytes
=
code_size
;
if
(
compressed_line_number_size
>
0
)
{
...
...
@@ -49,6 +50,10 @@ int constMethodOopDesc::object_size(int code_size,
extra_bytes
+=
local_variable_table_length
*
sizeof
(
LocalVariableTableElement
);
}
if
(
exception_table_length
>
0
)
{
extra_bytes
+=
sizeof
(
u2
);
extra_bytes
+=
exception_table_length
*
sizeof
(
ExceptionTableElement
);
}
int
extra_words
=
align_size_up
(
extra_bytes
,
BytesPerWord
)
/
BytesPerWord
;
return
align_object_size
(
header_size
()
+
extra_words
);
}
...
...
@@ -73,23 +78,40 @@ u2* constMethodOopDesc::checked_exceptions_length_addr() const {
return
last_u2_element
();
}
u2
*
constMethodOopDesc
::
localvariable
_table_length_addr
()
const
{
assert
(
has_
localvariable_table
(),
"called only if table is present"
);
u2
*
constMethodOopDesc
::
exception
_table_length_addr
()
const
{
assert
(
has_
exception_handler
(),
"called only if table is present"
);
if
(
has_checked_exceptions
())
{
// If checked_exception present, locate immediately before them.
return
(
u2
*
)
checked_exceptions_start
()
-
1
;
}
else
{
// Else, the
linenumber
table is at the end of the constMethod.
// Else, the
exception
table is at the end of the constMethod.
return
last_u2_element
();
}
}
u2
*
constMethodOopDesc
::
localvariable_table_length_addr
()
const
{
assert
(
has_localvariable_table
(),
"called only if table is present"
);
if
(
has_exception_handler
())
{
// If exception_table present, locate immediately before them.
return
(
u2
*
)
exception_table_start
()
-
1
;
}
else
{
if
(
has_checked_exceptions
())
{
// If checked_exception present, locate immediately before them.
return
(
u2
*
)
checked_exceptions_start
()
-
1
;
}
else
{
// Else, the linenumber table is at the end of the constMethod.
return
last_u2_element
();
}
}
}
// Update the flags to indicate the presence of these optional fields.
void
constMethodOopDesc
::
set_inlined_tables_length
(
int
checked_exceptions_len
,
int
compressed_line_number_size
,
int
localvariable_table_len
)
{
int
localvariable_table_len
,
int
exception_table_len
)
{
// Must be done in the order below, otherwise length_addr accessors
// will not work. Only set bit in header if length is positive.
assert
(
_flags
==
0
,
"Error"
);
...
...
@@ -100,6 +122,10 @@ void constMethodOopDesc::set_inlined_tables_length(
_flags
|=
_has_checked_exceptions
;
*
(
checked_exceptions_length_addr
())
=
checked_exceptions_len
;
}
if
(
exception_table_len
>
0
)
{
_flags
|=
_has_exception_table
;
*
(
exception_table_length_addr
())
=
exception_table_len
;
}
if
(
localvariable_table_len
>
0
)
{
_flags
|=
_has_localvariable_table
;
*
(
localvariable_table_length_addr
())
=
localvariable_table_len
;
...
...
@@ -133,3 +159,15 @@ LocalVariableTableElement* constMethodOopDesc::localvariable_table_start() const
addr
-=
length
*
sizeof
(
LocalVariableTableElement
)
/
sizeof
(
u2
);
return
(
LocalVariableTableElement
*
)
addr
;
}
int
constMethodOopDesc
::
exception_table_length
()
const
{
return
has_exception_handler
()
?
*
(
exception_table_length_addr
())
:
0
;
}
ExceptionTableElement
*
constMethodOopDesc
::
exception_table_start
()
const
{
u2
*
addr
=
exception_table_length_addr
();
u2
length
=
*
addr
;
assert
(
length
>
0
,
"should only be called if table is present"
);
addr
-=
length
*
sizeof
(
ExceptionTableElement
)
/
sizeof
(
u2
);
return
(
ExceptionTableElement
*
)
addr
;
}
src/share/vm/oops/constMethodOop.hpp
浏览文件 @
f0bda8e5
...
...
@@ -43,7 +43,6 @@
// | fingerprint 2 |
// | constants (oop) |
// | stackmap_data (oop) |
// | exception_table (oop) |
// | constMethod_size |
// | interp_kind | flags | code_size |
// | name index | signature index |
...
...
@@ -64,7 +63,13 @@
// | (length is u2, elements are 6-tuples of u2) |
// | (see class LocalVariableTableElement) |
// | (access flags bit tells whether table is present) |
// | (indexed from end of contMethodOop) |
// | (indexed from end of constMethodOop) |
// |------------------------------------------------------|
// | exception table + length (length last) |
// | (length is u2, elements are 4-tuples of u2) |
// | (see class ExceptionTableElement) |
// | (access flags bit tells whether table is present) |
// | (indexed from end of constMethodOop) |
// |------------------------------------------------------|
// | checked exceptions elements + length (length last) |
// | (length is u2, elements are u2) |
...
...
@@ -93,6 +98,15 @@ class LocalVariableTableElement VALUE_OBJ_CLASS_SPEC {
};
// Utitily class describing elements in exception table
class
ExceptionTableElement
VALUE_OBJ_CLASS_SPEC
{
public:
u2
start_pc
;
u2
end_pc
;
u2
handler_pc
;
u2
catch_type_index
;
};
class
constMethodOopDesc
:
public
oopDesc
{
friend
class
constMethodKlass
;
friend
class
VMStructs
;
...
...
@@ -100,7 +114,8 @@ private:
enum
{
_has_linenumber_table
=
1
,
_has_checked_exceptions
=
2
,
_has_localvariable_table
=
4
_has_localvariable_table
=
4
,
_has_exception_table
=
8
};
// Bit vector of signature
...
...
@@ -114,7 +129,7 @@ private:
public:
oop
*
oop_block_beg
()
const
{
return
adr_constants
();
}
oop
*
oop_block_end
()
const
{
return
adr_
exception_table
()
+
1
;
}
oop
*
oop_block_end
()
const
{
return
adr_
stackmap_data
()
+
1
;
}
private:
//
...
...
@@ -126,11 +141,6 @@ private:
// Raw stackmap data for the method
typeArrayOop
_stackmap_data
;
// The exception handler table. 4-tuples of ints [start_pc, end_pc,
// handler_pc, catch_type index] For methods with no exceptions the
// table is pointing to Universe::the_empty_int_array
typeArrayOop
_exception_table
;
//
// End of the oop block.
//
...
...
@@ -152,7 +162,8 @@ public:
// Inlined tables
void
set_inlined_tables_length
(
int
checked_exceptions_len
,
int
compressed_line_number_size
,
int
localvariable_table_len
);
int
localvariable_table_len
,
int
exception_table_len
);
bool
has_linenumber_table
()
const
{
return
(
_flags
&
_has_linenumber_table
)
!=
0
;
}
...
...
@@ -163,6 +174,9 @@ public:
bool
has_localvariable_table
()
const
{
return
(
_flags
&
_has_localvariable_table
)
!=
0
;
}
bool
has_exception_handler
()
const
{
return
(
_flags
&
_has_exception_table
)
!=
0
;
}
void
set_interpreter_kind
(
int
kind
)
{
_interpreter_kind
=
kind
;
}
int
interpreter_kind
(
void
)
const
{
return
_interpreter_kind
;
}
...
...
@@ -181,11 +195,6 @@ public:
}
bool
has_stackmap_table
()
const
{
return
_stackmap_data
!=
NULL
;
}
// exception handler table
typeArrayOop
exception_table
()
const
{
return
_exception_table
;
}
void
set_exception_table
(
typeArrayOop
e
)
{
oop_store_without_check
((
oop
*
)
&
_exception_table
,
(
oop
)
e
);
}
bool
has_exception_handler
()
const
{
return
exception_table
()
!=
NULL
&&
exception_table
()
->
length
()
>
0
;
}
void
init_fingerprint
()
{
const
uint64_t
initval
=
CONST64
(
0x8000000000000000
);
_fingerprint
=
initval
;
...
...
@@ -235,6 +244,7 @@ public:
// Object size needed
static
int
object_size
(
int
code_size
,
int
compressed_line_number_size
,
int
local_variable_table_length
,
int
exception_table_length
,
int
checked_exceptions_length
);
int
object_size
()
const
{
return
_constMethod_size
;
}
...
...
@@ -256,6 +266,7 @@ public:
u_char
*
compressed_linenumber_table
()
const
;
// not preserved by gc
u2
*
checked_exceptions_length_addr
()
const
;
u2
*
localvariable_table_length_addr
()
const
;
u2
*
exception_table_length_addr
()
const
;
// checked exceptions
int
checked_exceptions_length
()
const
;
...
...
@@ -265,6 +276,10 @@ public:
int
localvariable_table_length
()
const
;
LocalVariableTableElement
*
localvariable_table_start
()
const
;
// exception table
int
exception_table_length
()
const
;
ExceptionTableElement
*
exception_table_start
()
const
;
// byte codes
void
set_code
(
address
code
)
{
if
(
code_size
()
>
0
)
{
...
...
@@ -282,13 +297,10 @@ public:
// interpreter support
static
ByteSize
constants_offset
()
{
return
byte_offset_of
(
constMethodOopDesc
,
_constants
);
}
static
ByteSize
exception_table_offset
()
{
return
byte_offset_of
(
constMethodOopDesc
,
_exception_table
);
}
// Garbage collection support
oop
*
adr_constants
()
const
{
return
(
oop
*
)
&
_constants
;
}
oop
*
adr_stackmap_data
()
const
{
return
(
oop
*
)
&
_stackmap_data
;
}
oop
*
adr_exception_table
()
const
{
return
(
oop
*
)
&
_exception_table
;
}
bool
is_conc_safe
()
{
return
_is_conc_safe
;
}
void
set_is_conc_safe
(
bool
v
)
{
_is_conc_safe
=
v
;
}
...
...
src/share/vm/oops/generateOopMap.cpp
浏览文件 @
f0bda8e5
/*
* Copyright (c) 1997, 201
1
, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 1997, 201
2
, 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
...
...
@@ -400,10 +400,9 @@ void GenerateOopMap::mark_bbheaders_and_count_gc_points() {
bool
fellThrough
=
false
;
// False to get first BB marked.
// First mark all exception handlers as start of a basic-block
typeArrayOop
excps
=
method
()
->
exception_table
();
for
(
int
i
=
0
;
i
<
excps
->
length
();
i
+=
4
)
{
int
handler_pc_idx
=
i
+
2
;
bb_mark_fct
(
this
,
excps
->
int_at
(
handler_pc_idx
),
NULL
);
ExceptionTable
excps
(
method
());
for
(
int
i
=
0
;
i
<
excps
.
length
();
i
++
)
{
bb_mark_fct
(
this
,
excps
.
handler_pc
(
i
),
NULL
);
}
// Then iterate through the code
...
...
@@ -450,10 +449,9 @@ void GenerateOopMap::mark_reachable_code() {
// Mark entry basic block as alive and all exception handlers
_basic_blocks
[
0
].
mark_as_alive
();
typeArrayOop
excps
=
method
()
->
exception_table
();
for
(
int
i
=
0
;
i
<
excps
->
length
();
i
+=
4
)
{
int
handler_pc_idx
=
i
+
2
;
BasicBlock
*
bb
=
get_basic_block_at
(
excps
->
int_at
(
handler_pc_idx
));
ExceptionTable
excps
(
method
());
for
(
int
i
=
0
;
i
<
excps
.
length
();
i
++
)
{
BasicBlock
*
bb
=
get_basic_block_at
(
excps
.
handler_pc
(
i
));
// If block is not already alive (due to multiple exception handlers to same bb), then
// make it alive
if
(
bb
->
is_dead
())
bb
->
mark_as_alive
();
...
...
@@ -1181,12 +1179,12 @@ void GenerateOopMap::do_exception_edge(BytecodeStream* itr) {
if
(
_has_exceptions
)
{
int
bci
=
itr
->
bci
();
typeArrayOop
exct
=
method
()
->
exception_table
(
);
for
(
int
i
=
0
;
i
<
exct
->
length
();
i
+=
4
)
{
int
start_pc
=
exct
->
int_at
(
i
);
int
end_pc
=
exct
->
int_at
(
i
+
1
);
int
handler_pc
=
exct
->
int_at
(
i
+
2
);
int
catch_type
=
exct
->
int_at
(
i
+
3
);
ExceptionTable
exct
(
method
()
);
for
(
int
i
=
0
;
i
<
exct
.
length
();
i
++
)
{
int
start_pc
=
exct
.
start_pc
(
i
);
int
end_pc
=
exct
.
end_pc
(
i
);
int
handler_pc
=
exct
.
handler_pc
(
i
);
int
catch_type
=
exct
.
catch_type_index
(
i
);
if
(
start_pc
<=
bci
&&
bci
<
end_pc
)
{
BasicBlock
*
excBB
=
get_basic_block_at
(
handler_pc
);
...
...
@@ -2055,7 +2053,7 @@ void GenerateOopMap::compute_map(TRAPS) {
_conflict
=
false
;
_max_locals
=
method
()
->
max_locals
();
_max_stack
=
method
()
->
max_stack
();
_has_exceptions
=
(
method
()
->
exception_table
()
->
length
()
>
0
);
_has_exceptions
=
(
method
()
->
has_exception_handler
()
);
_nof_refval_conflicts
=
0
;
_init_vars
=
new
GrowableArray
<
intptr_t
>
(
5
);
// There are seldom more than 5 init_vars
_report_result
=
false
;
...
...
@@ -2070,9 +2068,10 @@ void GenerateOopMap::compute_map(TRAPS) {
if
(
Verbose
)
{
_method
->
print_codes
();
tty
->
print_cr
(
"Exception table:"
);
typeArrayOop
excps
=
method
()
->
exception_table
();
for
(
int
i
=
0
;
i
<
excps
->
length
();
i
+=
4
)
{
tty
->
print_cr
(
"[%d - %d] -> %d"
,
excps
->
int_at
(
i
+
0
),
excps
->
int_at
(
i
+
1
),
excps
->
int_at
(
i
+
2
));
ExceptionTable
excps
(
method
());
for
(
int
i
=
0
;
i
<
excps
.
length
();
i
++
)
{
tty
->
print_cr
(
"[%d - %d] -> %d"
,
excps
.
start_pc
(
i
),
excps
.
end_pc
(
i
),
excps
.
handler_pc
(
i
));
}
}
}
...
...
src/share/vm/oops/methodOop.cpp
浏览文件 @
f0bda8e5
...
...
@@ -111,25 +111,21 @@ char* methodOopDesc::name_and_sig_as_C_string(Klass* klass, Symbol* method_name,
int
methodOopDesc
::
fast_exception_handler_bci_for
(
KlassHandle
ex_klass
,
int
throw_bci
,
TRAPS
)
{
// exception table holds quadruple entries of the form (beg_bci, end_bci, handler_bci, klass_index)
const
int
beg_bci_offset
=
0
;
const
int
end_bci_offset
=
1
;
const
int
handler_bci_offset
=
2
;
const
int
klass_index_offset
=
3
;
const
int
entry_size
=
4
;
// access exception table
typeArrayHandle
table
(
THREAD
,
constMethod
()
->
exception_table
());
int
length
=
table
->
length
();
assert
(
length
%
entry_size
==
0
,
"exception table format has changed"
);
ExceptionTable
table
(
this
);
int
length
=
table
.
length
();
// iterate through all entries sequentially
constantPoolHandle
pool
(
THREAD
,
constants
());
for
(
int
i
=
0
;
i
<
length
;
i
+=
entry_size
)
{
int
beg_bci
=
table
->
int_at
(
i
+
beg_bci_offset
);
int
end_bci
=
table
->
int_at
(
i
+
end_bci_offset
);
for
(
int
i
=
0
;
i
<
length
;
i
++
)
{
//reacquire the table in case a GC happened
ExceptionTable
table
(
this
);
int
beg_bci
=
table
.
start_pc
(
i
);
int
end_bci
=
table
.
end_pc
(
i
);
assert
(
beg_bci
<=
end_bci
,
"inconsistent exception table"
);
if
(
beg_bci
<=
throw_bci
&&
throw_bci
<
end_bci
)
{
// exception handler bci range covers throw_bci => investigate further
int
handler_bci
=
table
->
int_at
(
i
+
handler_bci_offset
);
int
klass_index
=
table
->
int_at
(
i
+
klass_index_offset
);
int
handler_bci
=
table
.
handler_pc
(
i
);
int
klass_index
=
table
.
catch_type_index
(
i
);
if
(
klass_index
==
0
)
{
return
handler_bci
;
}
else
if
(
ex_klass
.
is_null
())
{
...
...
@@ -980,7 +976,7 @@ methodHandle methodOopDesc::make_invoke_method(KlassHandle holder,
{
int
flags_bits
=
(
JVM_MH_INVOKE_BITS
|
JVM_ACC_PUBLIC
|
JVM_ACC_FINAL
);
methodOop
m_oop
=
oopFactory
::
new_method
(
0
,
accessFlags_from
(
flags_bits
),
0
,
0
,
0
,
IsSafeConc
,
CHECK_
(
empty
));
0
,
0
,
0
,
0
,
IsSafeConc
,
CHECK_
(
empty
));
m
=
methodHandle
(
THREAD
,
m_oop
);
}
m
->
set_constants
(
cp
());
...
...
@@ -994,7 +990,6 @@ methodHandle methodOopDesc::make_invoke_method(KlassHandle holder,
m
->
set_result_index
(
rtf
.
type
());
#endif
m
->
compute_size_of_parameters
(
THREAD
);
m
->
set_exception_table
(
Universe
::
the_empty_int_array
());
m
->
init_intrinsic_id
();
assert
(
m
->
intrinsic_id
()
==
vmIntrinsics
::
_invokeExact
||
m
->
intrinsic_id
()
==
vmIntrinsics
::
_invokeGeneric
,
"must be an invoker"
);
...
...
@@ -1038,6 +1033,7 @@ methodHandle methodOopDesc:: clone_with_new_data(methodHandle m, u_char* new_cod
AccessFlags
flags
=
m
->
access_flags
();
int
checked_exceptions_len
=
m
->
checked_exceptions_length
();
int
localvariable_len
=
m
->
localvariable_table_length
();
int
exception_table_len
=
m
->
exception_table_length
();
// Allocate newm_oop with the is_conc_safe parameter set
// to IsUnsafeConc to indicate that newm_oop is not yet
// safe for concurrent processing by a GC.
...
...
@@ -1045,6 +1041,7 @@ methodHandle methodOopDesc:: clone_with_new_data(methodHandle m, u_char* new_cod
flags
,
new_compressed_linenumber_size
,
localvariable_len
,
exception_table_len
,
checked_exceptions_len
,
IsUnsafeConc
,
CHECK_
(
methodHandle
()));
...
...
src/share/vm/oops/methodOop.hpp
浏览文件 @
f0bda8e5
...
...
@@ -282,12 +282,12 @@ class methodOopDesc : public oopDesc {
}
// exception handler table
typeArrayOop
exception_table
()
const
{
return
constMethod
()
->
exception_table
();
}
void
set_exception_table
(
typeArrayOop
e
)
{
constMethod
()
->
set_exception_table
(
e
);
}
bool
has_exception_handler
()
const
{
return
constMethod
()
->
has_exception_handler
();
}
int
exception_table_length
()
const
{
return
constMethod
()
->
exception_table_length
();
}
ExceptionTableElement
*
exception_table_start
()
const
{
return
constMethod
()
->
exception_table_start
();
}
// Finds the first entry point bci of an exception handler for an
// exception of klass ex_klass thrown at throw_bci. A value of NULL
...
...
@@ -835,4 +835,66 @@ class BreakpointInfo : public CHeapObj {
void
clear
(
methodOop
method
);
};
// Utility class for access exception handlers
class
ExceptionTable
:
public
StackObj
{
private:
ExceptionTableElement
*
_table
;
u2
_length
;
public:
ExceptionTable
(
methodOop
m
)
{
if
(
m
->
has_exception_handler
())
{
_table
=
m
->
exception_table_start
();
_length
=
m
->
exception_table_length
();
}
else
{
_table
=
NULL
;
_length
=
0
;
}
}
int
length
()
const
{
return
_length
;
}
u2
start_pc
(
int
idx
)
const
{
assert
(
idx
<
_length
,
"out of bounds"
);
return
_table
[
idx
].
start_pc
;
}
void
set_start_pc
(
int
idx
,
u2
value
)
{
assert
(
idx
<
_length
,
"out of bounds"
);
_table
[
idx
].
start_pc
=
value
;
}
u2
end_pc
(
int
idx
)
const
{
assert
(
idx
<
_length
,
"out of bounds"
);
return
_table
[
idx
].
end_pc
;
}
void
set_end_pc
(
int
idx
,
u2
value
)
{
assert
(
idx
<
_length
,
"out of bounds"
);
_table
[
idx
].
end_pc
=
value
;
}
u2
handler_pc
(
int
idx
)
const
{
assert
(
idx
<
_length
,
"out of bounds"
);
return
_table
[
idx
].
handler_pc
;
}
void
set_handler_pc
(
int
idx
,
u2
value
)
{
assert
(
idx
<
_length
,
"out of bounds"
);
_table
[
idx
].
handler_pc
=
value
;
}
u2
catch_type_index
(
int
idx
)
const
{
assert
(
idx
<
_length
,
"out of bounds"
);
return
_table
[
idx
].
catch_type_index
;
}
void
set_catch_type_index
(
int
idx
,
u2
value
)
{
assert
(
idx
<
_length
,
"out of bounds"
);
_table
[
idx
].
catch_type_index
=
value
;
}
};
#endif // SHARE_VM_OOPS_METHODOOP_HPP
src/share/vm/prims/jvm.cpp
浏览文件 @
f0bda8e5
...
...
@@ -35,6 +35,7 @@
#include "oops/fieldStreams.hpp"
#include "oops/instanceKlass.hpp"
#include "oops/objArrayKlass.hpp"
#include "oops/methodOop.hpp"
#include "prims/jvm.h"
#include "prims/jvm_misc.hpp"
#include "prims/jvmtiExport.hpp"
...
...
@@ -2179,11 +2180,11 @@ JVM_QUICK_ENTRY(void, JVM_GetMethodIxExceptionTableEntry(JNIEnv *env, jclass cls
klassOop
k
=
java_lang_Class
::
as_klassOop
(
JNIHandles
::
resolve_non_null
(
cls
));
k
=
JvmtiThreadState
::
class_to_verify_considering_redefinition
(
k
,
thread
);
oop
method
=
instanceKlass
::
cast
(
k
)
->
methods
()
->
obj_at
(
method_index
);
typeArrayOop
extable
=
methodOop
(
method
)
->
exception_table
(
);
entry
->
start_pc
=
extable
->
int_at
(
entry_index
*
4
);
entry
->
end_pc
=
extable
->
int_at
(
entry_index
*
4
+
1
);
entry
->
handler_pc
=
extable
->
int_at
(
entry_index
*
4
+
2
);
entry
->
catchType
=
extable
->
int_at
(
entry_index
*
4
+
3
);
ExceptionTable
extable
((
methodOop
(
method
))
);
entry
->
start_pc
=
extable
.
start_pc
(
entry_index
);
entry
->
end_pc
=
extable
.
end_pc
(
entry_index
);
entry
->
handler_pc
=
extable
.
handler_pc
(
entry_index
);
entry
->
catchType
=
extable
.
catch_type_index
(
entry_index
);
JVM_END
...
...
@@ -2192,7 +2193,7 @@ JVM_QUICK_ENTRY(jint, JVM_GetMethodIxExceptionTableLength(JNIEnv *env, jclass cl
klassOop
k
=
java_lang_Class
::
as_klassOop
(
JNIHandles
::
resolve_non_null
(
cls
));
k
=
JvmtiThreadState
::
class_to_verify_considering_redefinition
(
k
,
thread
);
oop
method
=
instanceKlass
::
cast
(
k
)
->
methods
()
->
obj_at
(
method_index
);
return
methodOop
(
method
)
->
exception_table
()
->
length
()
/
4
;
return
methodOop
(
method
)
->
exception_table
_length
()
;
JVM_END
...
...
src/share/vm/prims/jvmtiClassFileReconstituter.cpp
浏览文件 @
f0bda8e5
...
...
@@ -191,15 +191,14 @@ void JvmtiClassFileReconstituter::write_code_attribute(methodHandle method) {
}
}
typeArrayHandle
exception_table
(
thread
(),
const_method
->
exception_table
());
int
exception_table_length
=
exception_table
->
length
();
int
exception_table_entries
=
exception_table_length
/
4
;
ExceptionTable
exception_table
(
method
());
int
exception_table_length
=
exception_table
.
length
();
int
code_size
=
const_method
->
code_size
();
int
size
=
2
+
2
+
4
+
// max_stack, max_locals, code_length
code_size
+
// code
2
+
// exception_table_length
(
2
+
2
+
2
+
2
)
*
exception_table_
entries
+
// exception_table
(
2
+
2
+
2
+
2
)
*
exception_table_
length
+
// exception_table
2
+
// attributes_count
attr_size
;
// attributes
...
...
@@ -209,12 +208,12 @@ void JvmtiClassFileReconstituter::write_code_attribute(methodHandle method) {
write_u2
(
method
->
max_locals
());
write_u4
(
code_size
);
copy_bytecodes
(
method
,
(
unsigned
char
*
)
writeable_address
(
code_size
));
write_u2
(
exception_table_
entries
);
for
(
int
index
=
0
;
index
<
exception_table_length
;
)
{
write_u2
(
exception_table
->
int_at
(
index
++
));
write_u2
(
exception_table
->
int_at
(
index
++
));
write_u2
(
exception_table
->
int_at
(
index
++
));
write_u2
(
exception_table
->
int_at
(
index
++
));
write_u2
(
exception_table_
length
);
for
(
int
index
=
0
;
index
<
exception_table_length
;
index
++
)
{
write_u2
(
exception_table
.
start_pc
(
index
));
write_u2
(
exception_table
.
end_pc
(
index
));
write_u2
(
exception_table
.
handler_pc
(
index
));
write_u2
(
exception_table
.
catch_type_index
(
index
));
}
write_u2
(
attr_count
);
if
(
line_num_cnt
!=
0
)
{
...
...
src/share/vm/prims/jvmtiRedefineClasses.cpp
浏览文件 @
f0bda8e5
/*
* Copyright (c) 2003, 201
1
, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2003, 201
2
, 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
...
...
@@ -2478,23 +2478,17 @@ void VM_RedefineClasses::set_new_constant_pool(
// to use new constant pool indices as needed. The exception table
// holds quadruple entries of the form:
// (beg_bci, end_bci, handler_bci, klass_index)
const
int
beg_bci_offset
=
0
;
const
int
end_bci_offset
=
1
;
const
int
handler_bci_offset
=
2
;
const
int
klass_index_offset
=
3
;
const
int
entry_size
=
4
;
typeArrayHandle
ex_table
(
THREAD
,
method
->
exception_table
());
int
ext_length
=
ex_table
->
length
();
assert
(
ext_length
%
entry_size
==
0
,
"exception table format has changed"
);
for
(
int
j
=
0
;
j
<
ext_length
;
j
+=
entry_size
)
{
int
cur_index
=
ex_table
->
int_at
(
j
+
klass_index_offset
);
ExceptionTable
ex_table
(
method
());
int
ext_length
=
ex_table
.
length
();
for
(
int
j
=
0
;
j
<
ext_length
;
j
++
)
{
int
cur_index
=
ex_table
.
catch_type_index
(
j
);
int
new_index
=
find_new_index
(
cur_index
);
if
(
new_index
!=
0
)
{
RC_TRACE_WITH_THREAD
(
0x00080000
,
THREAD
,
(
"ext-klass_index change: %d to %d"
,
cur_index
,
new_index
));
ex_table
->
int_at_put
(
j
+
klass_index_offset
,
new_index
);
ex_table
.
set_catch_type_index
(
j
,
new_index
);
}
}
// end for each exception table entry
...
...
src/share/vm/prims/methodHandleWalk.cpp
浏览文件 @
f0bda8e5
/*
* Copyright (c) 2008, 201
1
, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2008, 201
2
, 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
...
...
@@ -1796,7 +1796,7 @@ methodHandle MethodHandleCompiler::get_method_oop(TRAPS) {
{
methodOop
m_oop
=
oopFactory
::
new_method
(
bytecode_length
(),
accessFlags_from
(
flags_bits
),
0
,
0
,
0
,
oopDesc
::
IsSafeConc
,
CHECK_
(
empty
));
0
,
0
,
0
,
0
,
oopDesc
::
IsSafeConc
,
CHECK_
(
empty
));
m
=
methodHandle
(
THREAD
,
m_oop
);
}
...
...
@@ -1812,9 +1812,6 @@ methodHandle MethodHandleCompiler::get_method_oop(TRAPS) {
m
->
set_max_locals
(
max_locals
());
m
->
set_size_of_parameters
(
_num_params
);
typeArrayHandle
exception_handlers
(
THREAD
,
Universe
::
the_empty_int_array
());
m
->
set_exception_table
(
exception_handlers
());
// Rewrite the method and set up the constant pool cache.
objArrayOop
m_array
=
oopFactory
::
new_system_objArray
(
1
,
CHECK_
(
empty
));
objArrayHandle
methods
(
THREAD
,
m_array
);
...
...
src/share/vm/runtime/relocator.cpp
浏览文件 @
f0bda8e5
/*
* Copyright (c) 1997, 201
0
, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 1997, 201
2
, 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
...
...
@@ -392,16 +392,16 @@ void Relocator::change_jumps(int break_bci, int delta) {
// The width of instruction at "pc" is changing by "delta". Adjust the
// exception table, if any, of "rc->mb".
void
Relocator
::
adjust_exception_table
(
int
bci
,
int
delta
)
{
typeArrayOop
table
=
method
()
->
exception_table
(
);
for
(
int
index
=
0
;
index
<
table
->
length
();
index
+=
4
)
{
if
(
table
->
int_at
(
index
)
>
bci
)
{
table
->
int_at_put
(
index
+
0
,
table
->
int_at
(
index
+
0
)
+
delta
);
table
->
int_at_put
(
index
+
1
,
table
->
int_at
(
index
+
1
)
+
delta
);
}
else
if
(
bci
<
table
->
int_at
(
index
+
1
))
{
table
->
int_at_put
(
index
+
1
,
table
->
int_at
(
index
+
1
)
+
delta
);
ExceptionTable
table
(
_method
()
);
for
(
int
index
=
0
;
index
<
table
.
length
();
index
++
)
{
if
(
table
.
start_pc
(
index
)
>
bci
)
{
table
.
set_start_pc
(
index
,
table
.
start_pc
(
index
)
+
delta
);
table
.
set_end_pc
(
index
,
table
.
end_pc
(
index
)
+
delta
);
}
else
if
(
bci
<
table
.
end_pc
(
index
))
{
table
.
set_end_pc
(
index
,
table
.
end_pc
(
index
)
+
delta
);
}
if
(
table
->
int_at
(
index
+
2
)
>
bci
)
table
->
int_at_put
(
index
+
2
,
table
->
int_at
(
index
+
2
)
+
delta
);
if
(
table
.
handler_pc
(
index
)
>
bci
)
table
.
set_handler_pc
(
index
,
table
.
handler_pc
(
index
)
+
delta
);
}
}
...
...
src/share/vm/runtime/vmStructs.cpp
浏览文件 @
f0bda8e5
...
...
@@ -379,7 +379,6 @@ static inline uint64_t cast_uint64_t(size_t x)
volatile_nonstatic_field(constMethodOopDesc, _fingerprint, uint64_t) \
nonstatic_field(constMethodOopDesc, _constants, constantPoolOop) \
nonstatic_field(constMethodOopDesc, _stackmap_data, typeArrayOop) \
nonstatic_field(constMethodOopDesc, _exception_table, typeArrayOop) \
nonstatic_field(constMethodOopDesc, _constMethod_size, int) \
nonstatic_field(constMethodOopDesc, _interpreter_kind, jbyte) \
nonstatic_field(constMethodOopDesc, _flags, jbyte) \
...
...
@@ -416,6 +415,10 @@ static inline uint64_t cast_uint64_t(size_t x)
nonstatic_field(LocalVariableTableElement, descriptor_cp_index, u2) \
nonstatic_field(LocalVariableTableElement, signature_cp_index, u2) \
nonstatic_field(LocalVariableTableElement, slot, u2) \
nonstatic_field(ExceptionTableElement, start_pc, u2) \
nonstatic_field(ExceptionTableElement, end_pc, u2) \
nonstatic_field(ExceptionTableElement, handler_pc, u2) \
nonstatic_field(ExceptionTableElement, catch_type_index, u2) \
nonstatic_field(BreakpointInfo, _orig_bytecode, Bytecodes::Code) \
nonstatic_field(BreakpointInfo, _bci, int) \
nonstatic_field(BreakpointInfo, _name_index, u2) \
...
...
@@ -1451,6 +1454,7 @@ static inline uint64_t cast_uint64_t(size_t x)
\
declare_toplevel_type(CheckedExceptionElement) \
declare_toplevel_type(LocalVariableTableElement) \
declare_toplevel_type(ExceptionTableElement) \
\
/******************************************/
\
/* Generation and space hierarchies */
\
...
...
@@ -2292,6 +2296,7 @@ static inline uint64_t cast_uint64_t(size_t x)
declare_constant(constMethodOopDesc::_has_linenumber_table) \
declare_constant(constMethodOopDesc::_has_checked_exceptions) \
declare_constant(constMethodOopDesc::_has_localvariable_table) \
declare_constant(constMethodOopDesc::_has_exception_table) \
\
/*************************************/
\
/* instanceKlass enum */
\
...
...
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录