Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
openanolis
dragonwell8_hotspot
提交
42f4caa1
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看板
提交
42f4caa1
编写于
1月 04, 2010
作者:
T
twisti
浏览文件
操作
浏览文件
下载
差异文件
Merge
上级
35daeae1
d359f8ec
变更
8
展开全部
隐藏空白更改
内联
并排
Showing
8 changed file
with
1241 addition
and
58 deletion
+1241
-58
src/cpu/x86/vm/methodHandles_x86.cpp
src/cpu/x86/vm/methodHandles_x86.cpp
+3
-1
src/share/vm/classfile/javaClasses.cpp
src/share/vm/classfile/javaClasses.cpp
+4
-0
src/share/vm/classfile/javaClasses.hpp
src/share/vm/classfile/javaClasses.hpp
+1
-0
src/share/vm/classfile/vmSymbols.cpp
src/share/vm/classfile/vmSymbols.cpp
+80
-53
src/share/vm/classfile/vmSymbols.hpp
src/share/vm/classfile/vmSymbols.hpp
+75
-4
src/share/vm/includeDB_core
src/share/vm/includeDB_core
+4
-0
src/share/vm/prims/methodHandleWalk.cpp
src/share/vm/prims/methodHandleWalk.cpp
+805
-0
src/share/vm/prims/methodHandleWalk.hpp
src/share/vm/prims/methodHandleWalk.hpp
+269
-0
未找到文件。
src/cpu/x86/vm/methodHandles_x86.cpp
浏览文件 @
42f4caa1
...
...
@@ -268,8 +268,9 @@ void MethodHandles::remove_arg_slots(MacroAssembler* _masm,
}
#ifndef PRODUCT
extern
"C"
void
print_method_handle
(
oop
mh
);
void
trace_method_handle_stub
(
const
char
*
adaptername
,
oop
Desc
*
mh
,
oop
mh
,
intptr_t
*
entry_sp
,
intptr_t
*
saved_sp
,
intptr_t
*
saved_bp
)
{
...
...
@@ -280,6 +281,7 @@ void trace_method_handle_stub(const char* adaptername,
adaptername
,
(
intptr_t
)
mh
,
(
intptr_t
)
entry_sp
,
(
intptr_t
)(
saved_sp
-
entry_sp
),
(
intptr_t
)(
base_sp
-
last_sp
),
(
intptr_t
)
saved_bp
);
if
(
last_sp
!=
saved_sp
)
printf
(
"*** last_sp="
INTPTR_FORMAT
"
\n
"
,
(
intptr_t
)
last_sp
);
if
(
Verbose
)
print_method_handle
(
mh
);
}
#endif //PRODUCT
...
...
src/share/vm/classfile/javaClasses.cpp
浏览文件 @
42f4caa1
...
...
@@ -2403,6 +2403,10 @@ oop java_dyn_MethodType::ptype(oop mt, int idx) {
return
ptypes
(
mt
)
->
obj_at
(
idx
);
}
int
java_dyn_MethodType
::
ptype_count
(
oop
mt
)
{
return
ptypes
(
mt
)
->
length
();
}
// Support for java_dyn_MethodTypeForm
...
...
src/share/vm/classfile/javaClasses.hpp
浏览文件 @
42f4caa1
...
...
@@ -1027,6 +1027,7 @@ class java_dyn_MethodType: AllStatic {
static
oop
form
(
oop
mt
);
static
oop
ptype
(
oop
mt
,
int
index
);
static
int
ptype_count
(
oop
mt
);
static
symbolOop
as_signature
(
oop
mt
,
bool
intern_if_not_found
,
TRAPS
);
static
void
print_signature
(
oop
mt
,
outputStream
*
st
);
...
...
src/share/vm/classfile/vmSymbols.cpp
浏览文件 @
42f4caa1
/*
* Copyright 1997-200
8
Sun Microsystems, Inc. All Rights Reserved.
* Copyright 1997-200
9
Sun Microsystems, Inc. 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
...
...
@@ -70,6 +70,7 @@ static const char* vm_symbol_bodies = VM_SYMBOLS_DO(VM_SYMBOL_BODY, VM_ALIAS_IGN
void
vmSymbols
::
initialize
(
TRAPS
)
{
assert
((
int
)
SID_LIMIT
<=
(
1
<<
log2_SID_LIMIT
),
"must fit in this bitfield"
);
assert
((
int
)
SID_LIMIT
*
5
>
(
1
<<
log2_SID_LIMIT
),
"make the bitfield smaller, please"
);
assert
(
vmIntrinsics
::
FLAG_LIMIT
<=
(
1
<<
vmIntrinsics
::
log2_FLAG_LIMIT
),
"must fit in this bitfield"
);
if
(
!
UseSharedSpaces
)
{
const
char
*
string
=
&
vm_symbol_bodies
[
0
];
...
...
@@ -271,6 +272,44 @@ vmSymbols::SID vmSymbols::find_sid(symbolOop symbol) {
return
sid
;
}
static
vmIntrinsics
::
ID
wrapper_intrinsic
(
BasicType
type
,
bool
unboxing
)
{
#define TYPE2(type, unboxing) ((int)(type)*2 + ((unboxing) ? 1 : 0))
switch
(
TYPE2
(
type
,
unboxing
))
{
#define BASIC_TYPE_CASE(type, box, unbox) \
case TYPE2(type, false): return vmIntrinsics::box; \
case TYPE2(type, true): return vmIntrinsics::unbox
BASIC_TYPE_CASE
(
T_BOOLEAN
,
_Boolean_valueOf
,
_booleanValue
);
BASIC_TYPE_CASE
(
T_BYTE
,
_Byte_valueOf
,
_byteValue
);
BASIC_TYPE_CASE
(
T_CHAR
,
_Character_valueOf
,
_charValue
);
BASIC_TYPE_CASE
(
T_SHORT
,
_Short_valueOf
,
_shortValue
);
BASIC_TYPE_CASE
(
T_INT
,
_Integer_valueOf
,
_intValue
);
BASIC_TYPE_CASE
(
T_LONG
,
_Long_valueOf
,
_longValue
);
BASIC_TYPE_CASE
(
T_FLOAT
,
_Float_valueOf
,
_floatValue
);
BASIC_TYPE_CASE
(
T_DOUBLE
,
_Double_valueOf
,
_doubleValue
);
#undef BASIC_TYPE_CASE
}
#undef TYPE2
return
vmIntrinsics
::
_none
;
}
vmIntrinsics
::
ID
vmIntrinsics
::
for_boxing
(
BasicType
type
)
{
return
wrapper_intrinsic
(
type
,
false
);
}
vmIntrinsics
::
ID
vmIntrinsics
::
for_unboxing
(
BasicType
type
)
{
return
wrapper_intrinsic
(
type
,
true
);
}
methodOop
vmIntrinsics
::
method_for
(
vmIntrinsics
::
ID
id
)
{
if
(
id
==
_none
)
return
NULL
;
symbolOop
cname
=
vmSymbols
::
symbol_at
(
class_for
(
id
));
symbolOop
mname
=
vmSymbols
::
symbol_at
(
name_for
(
id
));
symbolOop
msig
=
vmSymbols
::
symbol_at
(
signature_for
(
id
));
if
(
cname
==
NULL
||
mname
==
NULL
||
msig
==
NULL
)
return
NULL
;
klassOop
k
=
SystemDictionary
::
find_well_known_klass
(
cname
);
if
(
k
==
NULL
)
return
NULL
;
return
instanceKlass
::
cast
(
k
)
->
find_method
(
mname
,
msig
);
}
#define VM_INTRINSIC_INITIALIZE(id, klass, name, sig, flags) #id "\0"
static
const
char
*
vm_intrinsic_name_bodies
=
...
...
@@ -330,15 +369,15 @@ inline bool match_F_RNY(jshort flags) {
}
// These are for forming case labels:
#define ID3(x, y, z) (( j
int
)(z) + \
((j
int
)(y) << vmSymbols::log2_SID_LIMIT) + \
((j
int
)(x) << (2*vmSymbols::log2_SID_LIMIT)) )
#define ID3(x, y, z) (( j
long
)(z) + \
((j
long
)(y) << vmSymbols::log2_SID_LIMIT) + \
((j
long
)(x) << (2*vmSymbols::log2_SID_LIMIT)) )
#define SID_ENUM(n) vmSymbols::VM_SYMBOL_ENUM_NAME(n)
vmIntrinsics
::
ID
vmIntrinsics
::
find_id
(
vmSymbols
::
SID
holder
,
vmSymbols
::
SID
name
,
vmSymbols
::
SID
sig
,
jshort
flags
)
{
vmIntrinsics
::
ID
vmIntrinsics
::
find_id
_impl
(
vmSymbols
::
SID
holder
,
vmSymbols
::
SID
name
,
vmSymbols
::
SID
sig
,
jshort
flags
)
{
assert
((
int
)
vmSymbols
::
SID_LIMIT
<=
(
1
<<
vmSymbols
::
log2_SID_LIMIT
),
"must fit"
);
// Let the C compiler build the decision tree.
...
...
@@ -383,62 +422,50 @@ const char* vmIntrinsics::short_name_as_C_string(vmIntrinsics::ID id, char* buf,
}
// These are
for friendly printouts of intrinsics:
// These are
to get information about intrinsics.
vmSymbols
::
SID
vmIntrinsics
::
class_for
(
vmIntrinsics
::
ID
id
)
{
#ifndef PRODUCT
#define VM_INTRINSIC_CASE(id, klass, name, sig, fcode) \
case id: return SID_ENUM(klass);
#define ID4(x, y, z, f) ((ID3(x, y, z) << vmIntrinsics::log2_FLAG_LIMIT) | (jlong) (f))
switch
(
id
)
{
VM_INTRINSICS_DO
(
VM_INTRINSIC_CASE
,
VM_SYMBOL_IGNORE
,
VM_SYMBOL_IGNORE
,
VM_SYMBOL_IGNORE
,
VM_ALIAS_IGNORE
);
}
#undef VM_INTRINSIC_CASE
#endif //PRODUCT
return
vmSymbols
::
NO_SID
;
static
const
jlong
intrinsic_info_array
[
vmIntrinsics
::
ID_LIMIT
+
1
]
=
{
#define VM_INTRINSIC_INFO(ignore_id, klass, name, sig, fcode) \
ID4(SID_ENUM(klass), SID_ENUM(name), SID_ENUM(sig), vmIntrinsics::fcode),
0
,
VM_INTRINSICS_DO
(
VM_INTRINSIC_INFO
,
VM_SYMBOL_IGNORE
,
VM_SYMBOL_IGNORE
,
VM_SYMBOL_IGNORE
,
VM_ALIAS_IGNORE
)
0
#undef VM_INTRINSIC_INFO
};
inline
jlong
intrinsic_info
(
vmIntrinsics
::
ID
id
)
{
return
intrinsic_info_array
[
vmIntrinsics
::
ID_from
((
int
)
id
)];
}
vmSymbols
::
SID
vmIntrinsics
::
name_for
(
vmIntrinsics
::
ID
id
)
{
#ifndef PRODUCT
#define VM_INTRINSIC_CASE(id, klass, name, sig, fcode) \
case id: return SID_ENUM(name);
vmSymbols
::
SID
vmIntrinsics
::
class_for
(
vmIntrinsics
::
ID
id
)
{
jlong
info
=
intrinsic_info
(
id
);
int
shift
=
2
*
vmSymbols
::
log2_SID_LIMIT
+
log2_FLAG_LIMIT
,
mask
=
right_n_bits
(
vmSymbols
::
log2_SID_LIMIT
);
assert
(((
ID4
(
1021
,
1022
,
1023
,
15
)
>>
shift
)
&
mask
)
==
1021
,
""
);
return
vmSymbols
::
SID
(
(
info
>>
shift
)
&
mask
);
}
switch
(
id
)
{
VM_INTRINSICS_DO
(
VM_INTRINSIC_CASE
,
VM_SYMBOL_IGNORE
,
VM_SYMBOL_IGNORE
,
VM_SYMBOL_IGNORE
,
VM_ALIAS_IGNORE
);
}
#undef VM_INTRINSIC_CASE
#endif //PRODUCT
return
vmSymbols
::
NO_SID
;
vmSymbols
::
SID
vmIntrinsics
::
name_for
(
vmIntrinsics
::
ID
id
)
{
jlong
info
=
intrinsic_info
(
id
);
int
shift
=
vmSymbols
::
log2_SID_LIMIT
+
log2_FLAG_LIMIT
,
mask
=
right_n_bits
(
vmSymbols
::
log2_SID_LIMIT
);
assert
(((
ID4
(
1021
,
1022
,
1023
,
15
)
>>
shift
)
&
mask
)
==
1022
,
""
);
return
vmSymbols
::
SID
(
(
info
>>
shift
)
&
mask
);
}
vmSymbols
::
SID
vmIntrinsics
::
signature_for
(
vmIntrinsics
::
ID
id
)
{
#ifndef PRODUCT
#define VM_INTRINSIC_CASE(id, klass, name, sig, fcode) \
case id: return SID_ENUM(sig);
switch
(
id
)
{
VM_INTRINSICS_DO
(
VM_INTRINSIC_CASE
,
VM_SYMBOL_IGNORE
,
VM_SYMBOL_IGNORE
,
VM_SYMBOL_IGNORE
,
VM_ALIAS_IGNORE
);
}
#undef VM_INTRINSIC_CASE
#endif //PRODUCT
return
vmSymbols
::
NO_SID
;
jlong
info
=
intrinsic_info
(
id
);
int
shift
=
log2_FLAG_LIMIT
,
mask
=
right_n_bits
(
vmSymbols
::
log2_SID_LIMIT
);
assert
(((
ID4
(
1021
,
1022
,
1023
,
15
)
>>
shift
)
&
mask
)
==
1023
,
""
);
return
vmSymbols
::
SID
(
(
info
>>
shift
)
&
mask
);
}
vmIntrinsics
::
Flags
vmIntrinsics
::
flags_for
(
vmIntrinsics
::
ID
id
)
{
#ifndef PRODUCT
#define VM_INTRINSIC_CASE(id, klass, name, sig, fcode) \
case id: return fcode;
switch
(
id
)
{
VM_INTRINSICS_DO
(
VM_INTRINSIC_CASE
,
VM_SYMBOL_IGNORE
,
VM_SYMBOL_IGNORE
,
VM_SYMBOL_IGNORE
,
VM_ALIAS_IGNORE
);
}
#undef VM_INTRINSIC_CASE
#endif //PRODUCT
return
F_none
;
jlong
info
=
intrinsic_info
(
id
);
int
shift
=
0
,
mask
=
right_n_bits
(
log2_FLAG_LIMIT
);
assert
(((
ID4
(
1021
,
1022
,
1023
,
15
)
>>
shift
)
&
mask
)
==
15
,
""
);
return
Flags
(
(
info
>>
shift
)
&
mask
);
}
...
...
src/share/vm/classfile/vmSymbols.hpp
浏览文件 @
42f4caa1
...
...
@@ -346,9 +346,14 @@
\
/* common signatures names */
\
template(void_method_signature, "()V") \
template(void_boolean_signature, "()Z") \
template(void_byte_signature, "()B") \
template(void_char_signature, "()C") \
template(void_short_signature, "()S") \
template(void_int_signature, "()I") \
template(void_long_signature, "()J") \
template(void_boolean_signature, "()Z") \
template(void_float_signature, "()F") \
template(void_double_signature, "()D") \
template(int_void_signature, "(I)V") \
template(int_int_signature, "(I)I") \
template(int_bool_signature, "(I)Z") \
...
...
@@ -853,6 +858,46 @@
\
do_intrinsic(_invoke, java_lang_reflect_Method, invoke_name, object_array_object_object_signature, F_R) \
/* (symbols invoke_name and invoke_signature defined above) */
\
do_intrinsic(_checkSpreadArgument, sun_dyn_MethodHandleImpl, checkSpreadArgument_name, checkSpreadArgument_signature, F_S) \
do_name( checkSpreadArgument_name, "checkSpreadArgument") \
do_name( checkSpreadArgument_signature, "(Ljava/lang/Object;I)V") \
\
/* unboxing methods: */
\
do_intrinsic(_booleanValue, java_lang_Boolean, booleanValue_name, void_boolean_signature, F_R) \
do_name( booleanValue_name, "booleanValue") \
do_intrinsic(_byteValue, java_lang_Byte, byteValue_name, void_byte_signature, F_R) \
do_name( byteValue_name, "byteValue") \
do_intrinsic(_charValue, java_lang_Character, charValue_name, void_char_signature, F_R) \
do_name( charValue_name, "charValue") \
do_intrinsic(_shortValue, java_lang_Short, shortValue_name, void_short_signature, F_R) \
do_name( shortValue_name, "shortValue") \
do_intrinsic(_intValue, java_lang_Integer, intValue_name, void_int_signature, F_R) \
do_name( intValue_name, "intValue") \
do_intrinsic(_longValue, java_lang_Long, longValue_name, void_long_signature, F_R) \
do_name( longValue_name, "longValue") \
do_intrinsic(_floatValue, java_lang_Float, floatValue_name, void_float_signature, F_R) \
do_name( floatValue_name, "floatValue") \
do_intrinsic(_doubleValue, java_lang_Double, doubleValue_name, void_double_signature, F_R) \
do_name( doubleValue_name, "doubleValue") \
\
/* boxing methods: */
\
do_name( valueOf_name, "valueOf") \
do_intrinsic(_Boolean_valueOf, java_lang_Boolean, valueOf_name, Boolean_valueOf_signature, F_S) \
do_name( Boolean_valueOf_signature, "(Z)Ljava/lang/Boolean;") \
do_intrinsic(_Byte_valueOf, java_lang_Byte, valueOf_name, Byte_valueOf_signature, F_S) \
do_name( Byte_valueOf_signature, "(B)Ljava/lang/Byte;") \
do_intrinsic(_Character_valueOf, java_lang_Character, valueOf_name, Character_valueOf_signature, F_S) \
do_name( Character_valueOf_signature, "(C)Ljava/lang/Character;") \
do_intrinsic(_Short_valueOf, java_lang_Short, valueOf_name, Short_valueOf_signature, F_S) \
do_name( Short_valueOf_signature, "(S)Ljava/lang/Short;") \
do_intrinsic(_Integer_valueOf, java_lang_Integer, valueOf_name, Integer_valueOf_signature, F_S) \
do_name( Integer_valueOf_signature, "(I)Ljava/lang/Integer;") \
do_intrinsic(_Long_valueOf, java_lang_Long, valueOf_name, Long_valueOf_signature, F_S) \
do_name( Long_valueOf_signature, "(J)Ljava/lang/Long;") \
do_intrinsic(_Float_valueOf, java_lang_Float, valueOf_name, Float_valueOf_signature, F_S) \
do_name( Float_valueOf_signature, "(F)Ljava/lang/Float;") \
do_intrinsic(_Double_valueOf, java_lang_Double, valueOf_name, Double_valueOf_signature, F_S) \
do_name( Double_valueOf_signature, "(D)Ljava/lang/Double;") \
\
/*end*/
...
...
@@ -983,7 +1028,12 @@ class vmIntrinsics: AllStatic {
F_Y
,
// !static ?native synchronized
F_RN
,
// !static native !synchronized
F_SN
,
// static native !synchronized
F_RNY
// !static native synchronized
F_RNY
,
// !static native synchronized
FLAG_LIMIT
};
enum
{
log2_FLAG_LIMIT
=
4
// checked by an assert at start-up
};
public:
...
...
@@ -995,15 +1045,32 @@ public:
static
const
char
*
name_at
(
ID
id
);
private:
static
ID
find_id_impl
(
vmSymbols
::
SID
holder
,
vmSymbols
::
SID
name
,
vmSymbols
::
SID
sig
,
jshort
flags
);
public:
// Given a method's class, name, signature, and access flags, report its ID.
static
ID
find_id
(
vmSymbols
::
SID
holder
,
vmSymbols
::
SID
name
,
vmSymbols
::
SID
sig
,
jshort
flags
);
jshort
flags
)
{
ID
id
=
find_id_impl
(
holder
,
name
,
sig
,
flags
);
#ifdef ASSERT
// ID _none does not hold the following asserts.
if
(
id
==
_none
)
return
id
;
#endif
assert
(
class_for
(
id
)
==
holder
,
"correct id"
);
assert
(
name_for
(
id
)
==
name
,
"correct id"
);
assert
(
signature_for
(
id
)
==
sig
,
"correct id"
);
return
id
;
}
static
void
verify_method
(
ID
actual_id
,
methodOop
m
)
PRODUCT_RETURN
;
//
No need for these in the product
:
//
Find out the symbols behind an intrinsic
:
static
vmSymbols
::
SID
class_for
(
ID
id
);
static
vmSymbols
::
SID
name_for
(
ID
id
);
static
vmSymbols
::
SID
signature_for
(
ID
id
);
...
...
@@ -1013,4 +1080,8 @@ public:
// Access to intrinsic methods:
static
methodOop
method_for
(
ID
id
);
// Wrapper object methods:
static
ID
for_boxing
(
BasicType
type
);
static
ID
for_unboxing
(
BasicType
type
);
};
src/share/vm/includeDB_core
浏览文件 @
42f4caa1
...
...
@@ -2814,6 +2814,10 @@ methodDataOop.hpp oop.hpp
methodDataOop.hpp orderAccess.hpp
methodDataOop.hpp universe.hpp
methodHandleWalk.hpp methodHandles.hpp
methodHandleWalk.cpp methodHandleWalk.hpp
methodHandles.hpp frame.inline.hpp
methodHandles.hpp globals.hpp
methodHandles.hpp interfaceSupport.hpp
...
...
src/share/vm/prims/methodHandleWalk.cpp
0 → 100644
浏览文件 @
42f4caa1
此差异已折叠。
点击以展开。
src/share/vm/prims/methodHandleWalk.hpp
0 → 100644
浏览文件 @
42f4caa1
/*
* Copyright 2008-2010 Sun Microsystems, Inc. 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 Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
* CA 95054 USA or visit www.sun.com if you need additional information or
* have any questions.
*
*/
// Low-level parser for method handle chains.
class
MethodHandleChain
:
StackObj
{
public:
typedef
MethodHandles
::
EntryKind
EntryKind
;
private:
Handle
_root
;
// original target
Handle
_method_handle
;
// current target
bool
_is_last
;
// final guy in chain
bool
_is_bound
;
// has a bound argument
BasicType
_arg_type
;
// if is_bound, the bound argument type
int
_arg_slot
;
// if is_bound or is_adapter, affected argument slot
jint
_conversion
;
// conversion field of AMH or -1
methodHandle
_last_method
;
// if is_last, which method we target
Bytecodes
::
Code
_last_invoke
;
// if is_last, type of invoke
const
char
*
_lose_message
;
// saved argument to lose()
void
set_method_handle
(
Handle
target
,
TRAPS
);
void
set_last_method
(
oop
target
,
TRAPS
);
static
BasicType
compute_bound_arg_type
(
oop
target
,
methodOop
m
,
int
arg_slot
,
TRAPS
);
oop
MethodHandle_type_oop
()
{
return
java_dyn_MethodHandle
::
type
(
method_handle_oop
());
}
oop
MethodHandle_vmtarget_oop
()
{
return
java_dyn_MethodHandle
::
vmtarget
(
method_handle_oop
());
}
int
MethodHandle_vmslots
()
{
return
java_dyn_MethodHandle
::
vmslots
(
method_handle_oop
());
}
int
DirectMethodHandle_vmindex
()
{
return
sun_dyn_DirectMethodHandle
::
vmindex
(
method_handle_oop
());
}
oop
BoundMethodHandle_argument_oop
()
{
return
sun_dyn_BoundMethodHandle
::
argument
(
method_handle_oop
());
}
int
BoundMethodHandle_vmargslot
()
{
return
sun_dyn_BoundMethodHandle
::
vmargslot
(
method_handle_oop
());
}
int
AdapterMethodHandle_conversion
()
{
return
sun_dyn_AdapterMethodHandle
::
conversion
(
method_handle_oop
());
}
public:
MethodHandleChain
(
Handle
root
,
TRAPS
)
:
_root
(
root
)
{
set_method_handle
(
root
,
THREAD
);
}
bool
is_adapter
()
{
return
_conversion
!=
-
1
;
}
bool
is_bound
()
{
return
_is_bound
;
}
bool
is_last
()
{
return
_is_last
;
}
void
next
(
TRAPS
)
{
assert
(
!
is_last
(),
""
);
set_method_handle
(
MethodHandle_vmtarget_oop
(),
THREAD
);
}
Handle
method_handle
()
{
return
_method_handle
;
}
oop
method_handle_oop
()
{
return
_method_handle
();
}
oop
method_type_oop
()
{
return
MethodHandle_type_oop
();
}
jint
adapter_conversion
()
{
assert
(
is_adapter
(),
""
);
return
_conversion
;
}
int
adapter_conversion_op
()
{
return
MethodHandles
::
adapter_conversion_op
(
adapter_conversion
());
}
BasicType
adapter_conversion_src_type
()
{
return
MethodHandles
::
adapter_conversion_src_type
(
adapter_conversion
());
}
BasicType
adapter_conversion_dest_type
()
{
return
MethodHandles
::
adapter_conversion_dest_type
(
adapter_conversion
());
}
int
adapter_conversion_stack_move
()
{
return
MethodHandles
::
adapter_conversion_stack_move
(
adapter_conversion
());
}
int
adapter_conversion_stack_pushes
()
{
return
adapter_conversion_stack_move
()
/
MethodHandles
::
stack_move_unit
();
}
int
adapter_conversion_vminfo
()
{
return
MethodHandles
::
adapter_conversion_vminfo
(
adapter_conversion
());
}
int
adapter_arg_slot
()
{
assert
(
is_adapter
(),
""
);
return
_arg_slot
;
}
oop
adapter_arg_oop
()
{
assert
(
is_adapter
(),
""
);
return
BoundMethodHandle_argument_oop
();
}
BasicType
bound_arg_type
()
{
assert
(
is_bound
(),
""
);
return
_arg_type
;
}
int
bound_arg_slot
()
{
assert
(
is_bound
(),
""
);
return
_arg_slot
;
}
oop
bound_arg_oop
()
{
assert
(
is_bound
(),
""
);
return
BoundMethodHandle_argument_oop
();
}
methodOop
last_method_oop
()
{
assert
(
is_last
(),
""
);
return
_last_method
();
}
Bytecodes
::
Code
last_invoke_code
()
{
assert
(
is_last
(),
""
);
return
_last_invoke
;
}
void
lose
(
const
char
*
msg
,
TRAPS
);
const
char
*
lose_message
()
{
return
_lose_message
;
}
};
// Structure walker for method handles.
// Does abstract interpretation on top of low-level parsing.
// You supply the tokens shuffled by the abstract interpretation.
class
MethodHandleWalker
:
StackObj
{
public:
struct
_ArgToken
{
};
// dummy struct
typedef
_ArgToken
*
ArgToken
;
// Abstract interpretation state:
struct
SlotState
{
BasicType
_type
;
ArgToken
_arg
;
SlotState
()
:
_type
(),
_arg
()
{}
};
static
SlotState
make_state
(
BasicType
type
,
ArgToken
arg
)
{
SlotState
ss
;
ss
.
_type
=
type
;
ss
.
_arg
=
arg
;
return
ss
;
}
private:
MethodHandleChain
_chain
;
GrowableArray
<
SlotState
>
_outgoing
;
// current outgoing parameter slots
int
_outgoing_argc
;
// # non-empty outgoing slots
// Replace a value of type old_type at slot (and maybe slot+1) with the new value.
// If old_type != T_VOID, remove the old argument at that point.
// If new_type != T_VOID, insert the new argument at that point.
// Insert or delete a second empty slot as needed.
void
change_argument
(
BasicType
old_type
,
int
slot
,
BasicType
new_type
,
ArgToken
new_arg
);
SlotState
*
slot_state
(
int
slot
)
{
if
(
slot
<
0
||
slot
>=
_outgoing
.
length
())
return
NULL
;
return
_outgoing
.
adr_at
(
slot
);
}
BasicType
slot_type
(
int
slot
)
{
SlotState
*
ss
=
slot_state
(
slot
);
if
(
ss
==
NULL
)
return
T_ILLEGAL
;
return
ss
->
_type
;
}
bool
slot_has_argument
(
int
slot
)
{
return
slot_type
(
slot
)
<
T_VOID
;
}
#ifdef ASSERT
int
argument_count_slow
();
#endif
// Return a bytecode for converting src to dest, if one exists.
Bytecodes
::
Code
conversion_code
(
BasicType
src
,
BasicType
dest
);
void
walk_incoming_state
(
TRAPS
);
public:
MethodHandleWalker
(
Handle
root
,
TRAPS
)
:
_chain
(
root
,
THREAD
),
_outgoing
(
THREAD
,
10
),
_outgoing_argc
(
0
)
{
}
MethodHandleChain
&
chain
()
{
return
_chain
;
}
// plug-in abstract interpretation steps:
virtual
ArgToken
make_parameter
(
BasicType
type
,
klassOop
tk
,
int
argnum
,
TRAPS
)
=
0
;
virtual
ArgToken
make_prim_constant
(
BasicType
type
,
jvalue
*
con
,
TRAPS
)
=
0
;
virtual
ArgToken
make_oop_constant
(
oop
con
,
TRAPS
)
=
0
;
virtual
ArgToken
make_conversion
(
BasicType
type
,
klassOop
tk
,
Bytecodes
::
Code
op
,
ArgToken
src
,
TRAPS
)
=
0
;
virtual
ArgToken
make_fetch
(
BasicType
type
,
klassOop
tk
,
Bytecodes
::
Code
op
,
ArgToken
base
,
ArgToken
offset
,
TRAPS
)
=
0
;
virtual
ArgToken
make_invoke
(
methodOop
m
,
vmIntrinsics
::
ID
iid
,
Bytecodes
::
Code
op
,
bool
tailcall
,
int
argc
,
ArgToken
*
argv
,
TRAPS
)
=
0
;
// For make_invoke, the methodOop can be NULL if the intrinsic ID
// is something other than vmIntrinsics::_none.
// and in case anyone cares to related the previous actions to the chain:
virtual
void
set_method_handle
(
oop
mh
)
{
}
void
lose
(
const
char
*
msg
,
TRAPS
)
{
chain
().
lose
(
msg
,
THREAD
);
}
const
char
*
lose_message
()
{
return
chain
().
lose_message
();
}
ArgToken
walk
(
TRAPS
);
};
// An abstract interpreter for method handle chains.
// Produces an account of the semantics of a chain, in terms of a static IR.
// The IR happens to be JVM bytecodes.
class
MethodHandleCompiler
:
public
MethodHandleWalker
{
private:
Thread
*
_thread
;
struct
PrimCon
{
BasicType
_type
;
jvalue
_value
;
};
// Accumulated compiler state:
stringStream
_bytes
;
GrowableArray
<
Handle
>
_constant_oops
;
GrowableArray
<
PrimCon
*>
_constant_prims
;
int
_max_stack
;
int
_num_params
;
int
_max_locals
;
int
_name_index
;
int
_signature_index
;
// Stack values:
enum
TokenType
{
tt_void
,
tt_parameter
,
tt_temporary
,
tt_constant
};
ArgToken
make_stack_value
(
TokenType
tt
,
BasicType
type
,
int
id
)
{
return
ArgToken
(
((
intptr_t
)
id
<<
8
)
|
((
intptr_t
)
type
<<
4
)
|
(
intptr_t
)
tt
);
}
public:
virtual
ArgToken
make_parameter
(
BasicType
type
,
klassOop
tk
,
int
argnum
,
TRAPS
)
{
return
make_stack_value
(
tt_parameter
,
type
,
argnum
);
}
virtual
ArgToken
make_oop_constant
(
oop
con
,
TRAPS
)
{
return
make_stack_value
(
tt_constant
,
T_OBJECT
,
find_oop_constant
(
con
));
}
virtual
ArgToken
make_prim_constant
(
BasicType
type
,
jvalue
*
con
,
TRAPS
)
{
return
make_stack_value
(
tt_constant
,
type
,
find_prim_constant
(
type
,
con
));
}
virtual
ArgToken
make_conversion
(
BasicType
type
,
klassOop
tk
,
Bytecodes
::
Code
op
,
ArgToken
src
,
TRAPS
);
virtual
ArgToken
make_fetch
(
BasicType
type
,
klassOop
tk
,
Bytecodes
::
Code
op
,
ArgToken
base
,
ArgToken
offset
,
TRAPS
);
virtual
ArgToken
make_invoke
(
methodOop
m
,
vmIntrinsics
::
ID
iid
,
Bytecodes
::
Code
op
,
bool
tailcall
,
int
argc
,
ArgToken
*
argv
,
TRAPS
);
int
find_oop_constant
(
oop
con
);
int
find_prim_constant
(
BasicType
type
,
jvalue
*
con
);
public:
MethodHandleCompiler
(
Handle
root
,
TRAPS
)
:
MethodHandleWalker
(
root
,
THREAD
),
_thread
(
THREAD
),
_bytes
(
50
),
_constant_oops
(
THREAD
,
10
),
_constant_prims
(
THREAD
,
10
),
_max_stack
(
0
),
_max_locals
(
0
),
_name_index
(
0
),
_signature_index
(
0
)
{
}
const
char
*
bytes
()
{
return
_bytes
.
as_string
();
}
int
constant_length
()
{
return
_constant_oops
.
length
();
}
int
max_stack
()
{
return
_max_stack
;
}
int
max_locals
()
{
return
_max_locals
;
}
int
name_index
()
{
return
_name_index
;
}
int
signature_index
()
{
return
_signature_index
;
}
symbolHandle
name
()
{
return
symbolHandle
(
_thread
,
(
symbolOop
)
constant_oop_at
(
_name_index
)());
}
symbolHandle
signature
()
{
return
symbolHandle
(
_thread
,
(
symbolOop
)
constant_oop_at
(
_signature_index
)());
}
bool
constant_is_oop_at
(
int
i
)
{
return
(
_constant_prims
.
at
(
i
)
==
NULL
);
}
Handle
constant_oop_at
(
int
i
)
{
assert
(
constant_is_oop_at
(
i
),
""
);
return
_constant_oops
.
at
(
i
);
}
PrimCon
*
constant_prim_at
(
int
i
)
{
assert
(
!
constant_is_oop_at
(
i
),
""
);
return
_constant_prims
.
at
(
i
);
}
// Compile the given MH chain into bytecode.
void
compile
(
TRAPS
);
};
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录