对象创建
interpreterRuntime.cpp 解释器中new指令的入口:
// 宏展开
// IRT_ENTRY(void, InterpreterRuntime::_new(JavaThread* thread, ConstantPool* pool, int index))
void InterpreterRuntime::_new(JavaThread* thread, ConstantPool* pool, int index) { ThreadInVMfromJava __tiv(thread); HandleMarkCleaner __hm(thread); Thread* __the_thread__ = thread; os::verify_stack_alignment();
// 宏展开
// Klass* k_oop = pool->klass_at(index, CHECK);
Klass* k_oop = pool->klass_at(index, __the_thread__); if ((((ThreadShadow*)__the_thread__)->has_pending_exception())) return ; (void)(0);
instanceKlassHandle klass (THREAD, k_oop);
// Make sure we are not instantiating an abstract klass
klass->check_valid_for_instantiation(true, CHECK);
// Make sure klass is initialized
klass->initialize(CHECK);
// At this point the class may not be fully initialized
// because of recursive initialization. If it is fully
// initialized & has_finalized is not set, we rewrite
// it into its fast version (Note: no locking is needed
// here since this is an atomic byte write and can be
// done more than once).
//
// Note: In case of classes with has_finalized we don't
// rewrite since that saves us an extra check in
// the fast version which then would call the
// slow version anyway (and do a call back into
// Java).
// If we have a breakpoint, then we don't rewrite
// because the _breakpoint bytecode would be lost.
oop obj = klass->allocate_instance(CHECK); // SimonNote: 解释器创建对象实力入口
thread->set_vm_result(obj);
//======再往上找谁调进来的,调用栈已经不好观察了,直接贴代码。这个好像不对,再分析
// bytecodeInterpreter.cpp
CASE(_new): {
// ......
CALL_VM(InterpreterRuntime::_new(THREAD, METHOD->constants(), index),
handle_exception);
}
关于对象直接转unsigned char指针的写法,在codeBlob.hpp中有很多这种写法,最简单的示例如下:
typedef unsigned char u_char;
typedef u_char* address;
void CodeBlob::printSize(){
std::cout << _size << std::endl;
address aa = (address)this; // 这样写是没语法错误的,转换后aa的内存地址和this一样的。
std::cout << aa << std::endl;
}
至于怎么调到InterpreterRuntime::_new这个方法的,是从汇编指令直接跳过来的,具体的可以看《虚拟机解释器与bytecode对接》一文。
怎么调试new指令new你自己的类
要调试这个new指令怎么new你自己的类(你做实验的类),怎么做?
因为JVM在执行一个main方法时,前面会new200+个类,要调到你自己的类,得有个办法才行,不然F8一路按下去要按好久。
我的办法是:
在 InterpreterRuntime::_new加上 k_oop->name()->print();
IRT_ENTRY(void, InterpreterRuntime::_new(JavaThread* thread, ConstantPool* pool, int index))
Klass* k_oop = pool->klass_at(index, CHECK);
k_oop->name()->print();instanceKlassHandle klass (THREAD, k_oop);
// 这样能把每次new的class名给打出来
这样就能发现我自己的类大概是在new指令被调用了261次后才被new,于是对此处断点加上ignore count为261,这样便能调试到new我自己的测试类了。
new指令为对象分配空间
此处我的测试类是Group
public class Group {
private int id;
private long t1;
private long t2;
private long t3;
private String name;
public Group(int id, String name) {
this.id = id;
this.name = name;
}
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
@Override
public String toString() {
return "Group [id=" + id + ", name=" + name + "]";
}
}
计算对象大小:
instanceOop InstanceKlass::allocate_instance(TRAPS) {
bool has_finalizer_flag = has_finalizer(); // Query before possible GC
int size = size_helper(); // Query before forming handle.
KlassHandle h_k(THREAD, this);
instanceOop i;
i = (instanceOop)CollectedHeap::obj_allocate(h_k, size, CHECK_NULL);
if (has_finalizer_flag && !RegisterFinalizersAtInit) {
i = register_finalizer(i, CHECK_NULL);
}
return i;
}
此处size为6,我理解此处的单位是heapword即byte。
分配空间的栈:
Copy::pd_fill_to_words() at copy_x86.hpp:49 0x7ffff61faf7c
Copy::fill_to_words() at copy.hpp:236 0x7ffff61fae72
ThreadLocalAllocBuffer::allocate() at threadLocalAllocBuffer.inline.hpp:44 0x7ffff61fb04e
CollectedHeap::allocate_from_tlab() at collectedHeap.inline.hpp:181 0x7ffff61fb97a
CollectedHeap::common_mem_allocate_noinit() at collectedHeap.inline.hpp:124 0x7ffff61fb6d9
CollectedHeap::common_mem_allocate_init() at collectedHeap.inline.hpp:173 0x7ffff61fb8e2
CollectedHeap::obj_allocate() at collectedHeap.inline.hpp:201 0x7ffff660a876
InstanceKlass::allocate_instance() at instanceKlass.cpp:1,104 0x7ffff65f36fd
InterpreterRuntime::_new() at interpreterRuntime.cpp:172 0x7ffff6652fb8
分配空间的代码:
// threadLocalAllocBuffer.inline.hpp
inline HeapWord* ThreadLocalAllocBuffer::allocate(size_t size) {
invariants();
HeapWord* obj = top();
if (pointer_delta(end(), obj) >= size) {
// successful thread-local allocation
#ifdef ASSERT
// Skip mangling the space corresponding to the object header to
// ensure that the returned space is not considered parsable by
// any concurrent GC thread.
size_t hdr_size = oopDesc::header_size();
Copy::fill_to_words(obj + hdr_size, size - hdr_size, badHeapWordVal);
#endif // ASSERT
// This addition is safe because we know that top is
// at least size below end, so the add can't wrap.
set_top(obj + size);
invariants();
return obj;
}
return NULL;
}
// copy_x86.hpp
static void pd_fill_to_words(HeapWord* tohw, size_t count, juint value) {
#ifdef AMD64
julong* to = (julong*) tohw;
julong v = ((julong) value << 32) | value;
while (count-- > 0) {
*to++ = v;
}
#else
juint* to = (juint*)tohw;
count *= HeapWordSize / BytesPerInt;
while (count-- > 0) {
*to++ = value;
}
#endif // AMD64
}
编译hsdis
cd /home/appweb/600.self/03.code/01.cpp/01.jdk8-b120/hotspot-jdk8-b120/hotspot/src/share/tools/hsdis
wget ftp://sourceware.org/pub/binutils/snapshots/binutils-2.20.51.tar.bz2
tar -xjvf binutils-2.20.51.tar.bz2
export BINUTILS=binutils-2.20.51
gedit binutils-2.20.51/binutils/configure # 修改一下 注释掉下面的代码
#if test "${ERROR_ON_WARNING}" = yes ; then
# GCC_WARN_CFLAGS="$GCC_WARN_CFLAGS -Werror"
# NO_WERROR="-Wno-error"
#fi
gedit binutils-2.20.51/bfd//configure # 修改一下 注释掉上面的代码
make all64
# 编译成功后 copy so文件到对应目录
cp build/linux-amd64/hsdis-amd64.so ~/600.self/03.code/01.cpp/01.jdk8-b120/hotspot-jdk8-b120/build/linux-x86_64-normal-server-slowdebug/jdk/lib/amd64/server/
编译好后,放到正确的路径下,就可以用-XX:+PrintInterpreter打印出汇编代码了。
解释器
new一个对象的汇编代码翻译
public class ObjectCreateTest1 {
public static void main(String[] args) {
Group g = new Group(1, "g-1");
}
}
字节码翻译时,内存地址查看
MacroAssembler MacroAssembler {...}
Assembler Assembler {...}
AbstractAssembler AbstractAssembler {...}
ResourceObj ResourceObj {...}
_code_section CodeSection * 0x7ffff7fdd5e0
_start address 0x7fffe10449e0 "Pé*"
附:new指令的翻译:
;_new
;start:0x7fffe10449e0
;end:0x7fffe1044e00
00007fffe10449e0: push %rax
00007fffe10449e1: jmpq 0x7fffe1044a10
00007fffe10449e6: sub $0x8,%rsp
00007fffe10449ea: vmovss %xmm0,(%rsp)
00007fffe10449ef: jmpq 0x7fffe1044a10
00007fffe10449f4: sub $0x10,%rsp
00007fffe10449f8: vmovsd %xmm0,(%rsp)
00007fffe10449fd: jmpq 0x7fffe1044a10
00007fffe1044a02: sub $0x10,%rsp
00007fffe1044a06: mov %rax,(%rsp)
00007fffe1044a0a: jmpq 0x7fffe1044a10
00007fffe1044a0f: push %rax
; 下面开始进入TemplateTable::_new
00007fffe1044a10: movzwl 0x1(%r13),%edx
00007fffe1044a15: bswap %edx
00007fffe1044a17: shr $0x10,%edx
; _masm->get_unsigned_2_byte_index_at_bcp(rdx, 1); 翻译出来的指令到上一行结束
00007fffe1044a1a: mov -0x18(%rbp),%rsi
00007fffe1044a1e: mov 0x10(%rsi),%rsi
00007fffe1044a22: mov 0x8(%rsi),%rsi
00007fffe1044a26: mov 0x10(%rsi),%rax
; _masm->get_cpool_and_tags(rsi, rax); 翻译出来的指令到上一行结束
00007fffe1044a2a: cmpb $0x7,0x4(%rax,%rdx,1)
; const int tags_offset = Array<u1>::base_offset_in_bytes();
; _masm->cmpb(Address(rax, rdx, Address::times_1, tags_offset), JVM_CONSTANT_Class);
; 翻译出来的指令到上一行结束
00007fffe1044a2f: jne 0x7fffe1044b92
; _masm->jcc(Assembler::notEqual, slow_case);
00007fffe1044a35: mov 0x58(%rsi,%rdx,8),%rsi
;// get InstanceKlass
; _masm->movptr(rsi, Address(rsi, rdx, Address::times_8, sizeof(ConstantPool)));
00007fffe1044a3a: cmpb $0x4,0x16a(%rsi)
;// make sure klass is initialized & doesn't have finalizer
; // make sure klass is fully initialized
; _masm->cmpb(Address(rsi, InstanceKlass::init_state_offset()), InstanceKlass::fully_initialized);
00007fffe1044a41: jne 0x7fffe1044b92
; _masm->jcc(Assembler::notEqual, slow_case)
00007fffe1044a47: mov 0xc(%rsi),%edx
; // get instance_size in InstanceKlass (scaled to a count of bytes)
; _masm->movl(rdx, Address(rsi, Klass::layout_helper_offset()));
00007fffe1044a4a: test $0x1,%edx
; // test to see if it has a finalizer or is malformed in some way
; _masm->testl(rdx, Klass::_lh_instance_slow_path_bit);
00007fffe1044a50: jne 0x7fffe1044b92
; _masm->jcc(Assembler::notZero, slow_case);
00007fffe1044a56: mov 0x70(%r15),%rax
; _masm->movptr(rax, Address(r15_thread, in_bytes(JavaThread::tlab_top_offset())));
00007fffe1044a5a: lea (%rax,%rdx,1),%rbx
;_masm->lea(rbx, Address(rax, rdx, Address::times_1));
00007fffe1044a5e: cmp 0x80(%r15),%rbx
;_masm->cmpptr(rbx, Address(r15_thread, in_bytes(JavaThread::tlab_end_offset())));
00007fffe1044a65: ja 0x7fffe1044a74
;_masm->jcc(Assembler::above, allow_shared_alloc ? allocate_shared : slow_case);
00007fffe1044a6b: mov %rbx,0x70(%r15)
;_masm->movptr(Address(r15_thread, in_bytes(JavaThread::tlab_top_offset())), rbx);
00007fffe1044a6f: jmpq 0x7fffe1044aa6
; _masm->jmp(initialize_object);
00007fffe1044a74: movabs $0x7ffff0025338,%r10
; _masm->bind(allocate_shared);
; ExternalAddress top((address)Universe::heap()->top_addr());
; ExternalAddress end((address)Universe::heap()->end_addr());
; const Register RtopAddr = rscratch1;
; const Register RendAddr = rscratch2;
; _masm->lea(RtopAddr, top);
00007fffe1044a7e: movabs $0x7ffff00252e8,%r11
; _masm->lea(RendAddr, end);
00007fffe1044a88: mov (%r10),%rax
; _masm->movptr(rax, Address(RtopAddr, 0));
00007fffe1044a8b: lea (%rax,%rdx,1),%rbx
;// For retries rax gets set by cmpxchgq
; Label retry;
; _masm->bind(retry);
; _masm->lea(rbx, Address(rax, rdx, Address::times_1));
00007fffe1044a8f: cmp (%r11),%rbx
; _masm->cmpptr(rbx, Address(RendAddr, 0));
00007fffe1044a92: ja 0x7fffe1044b92
; _masm->jcc(Assembler::above, slow_case);
00007fffe1044a98: lock cmpxchg %rbx,(%r10)
; _masm->lock();
; _masm->cmpxchgptr(rbx, Address(RtopAddr, 0));
00007fffe1044a9d: jne 0x7fffe1044a8b
; _masm->jcc(Assembler::notEqual, retry);
00007fffe1044a9f: add %rdx,0xd0(%r15)
; _masm->incr_allocated_bytes(r15_thread, rdx, 0);
00007fffe1044aa6: sub $0x10,%edx
; // The object is initialized before the header. If the object size is
; // zero, go directly to the header initialization.
; _masm->bind(initialize_object);
; _masm->decrementl(rdx, sizeof(oopDesc));
00007fffe1044aa9: je 0x7fffe1044abd
; _masm->jcc(Assembler::zero, initialize_header);
00007fffe1044aaf: xor %ecx,%ecx
00007fffe1044ab1: shr $0x3,%edx
00007fffe1044ab4: mov %rcx,0x8(%rax,%rdx,8)
00007fffe1044ab9: dec %edx// Initialize object fields
00007fffe1044abb: jne 0x7fffe1044ab4
; _masm->xorl(rcx, rcx); // use zero reg to clear memory (shorter code)
; _masm->shrl(rdx, LogBytesPerLong); // divide by oopSize to simplify the loop
; {
; _masm->bind(loop);
; _masm->movq(Address(rax, rdx, Address::times_8, sizeof(oopDesc) - oopSize), rcx);
; _masm->decrementl(rdx);
00007fffe1044abd: mov 0xb0(%rsi),%r10
00007fffe1044ac4: mov %r10,(%rax)
; _masm->movptr(rscratch1, Address(rsi, Klass::prototype_header_offset()));
; _masm->movptr(Address(rax, oopDesc::mark_offset_in_bytes()), rscratch1);
00007fffe1044ac7: xor %ecx,%ecx
00007fffe1044ac9: mov %ecx,0xc(%rax)
00007fffe1044acc: shr $0x3,%rsi
00007fffe1044ad0: mov %esi,0x8(%rax)
; _masm->xorl(rcx, rcx); // use zero reg to clear memory (shorter code)
; _masm->store_klass_gap(rax, rcx); // zero klass gap for compressed oops
; _masm->store_klass(rax, rsi); // store klass last
00007fffe1044ad3: cmpb $0x0,0x16317681(%rip) # 0x7ffff735c15b <DTraceAllocProbes>
00007fffe1044ada: je 0x7fffe1044b8d
; SkipIfEqual skip(_masm, &DTraceAllocProbes, false);
00007fffe1044ae0: push %rax
; _masm->push(atos); // save the return value
00007fffe1044ae1: mov %rax,%rdi
00007fffe1044ae4: cmpq $0x0,-0x10(%rbp)
00007fffe1044aec: je 0x7fffe1044b69
00007fffe1044af2: mov %rsp,-0x28(%rsp)
00007fffe1044af7: sub $0x80,%rsp
00007fffe1044afe: mov %rax,0x78(%rsp)
00007fffe1044b03: mov %rcx,0x70(%rsp)
00007fffe1044b08: mov %rdx,0x68(%rsp)
00007fffe1044b0d: mov %rbx,0x60(%rsp)
00007fffe1044b12: mov %rbp,0x50(%rsp)
00007fffe1044b17: mov %rsi,0x48(%rsp)
00007fffe1044b1c: mov %rdi,0x40(%rsp)
00007fffe1044b21: mov %r8,0x38(%rsp)
00007fffe1044b26: mov %r9,0x30(%rsp)
00007fffe1044b2b: mov %r10,0x28(%rsp)
00007fffe1044b30: mov %r11,0x20(%rsp)
00007fffe1044b35: mov %r12,0x18(%rsp)
00007fffe1044b3a: mov %r13,0x10(%rsp)
00007fffe1044b3f: mov %r14,0x8(%rsp)
00007fffe1044b44: mov %r15,(%rsp)
00007fffe1044b48: movabs $0x7ffff6c8ceb8,%rdi
00007fffe1044b52: movabs $0x7fffe1044af2,%rsi
00007fffe1044b5c: mov %rsp,%rdx
00007fffe1044b5f: and $0xfffffffffffffff0,%rsp
00007fffe1044b63: callq 0x7ffff68024fa <MacroAssembler::debug64(char*, long, long*)>
00007fffe1044b68: hlt
00007fffe1044b69: test $0xf,%esp
00007fffe1044b6f: je 0x7fffe1044b87
00007fffe1044b75: sub $0x8,%rsp
00007fffe1044b79: callq 0x7ffff699de5c <SharedRuntime::dtrace_object_alloc(oopDesc*)>
00007fffe1044b7e: add $0x8,%rsp
00007fffe1044b82: jmpq 0x7fffe1044b8c
00007fffe1044b87: callq 0x7ffff699de5c <SharedRuntime::dtrace_object_alloc(oopDesc*)>
; _masm->call_VM_leaf(CAST_FROM_FN_PTR(address, SharedRuntime::dtrace_object_alloc), rax); // 这一句翻译出了很多句指令
00007fffe1044b8c: pop %rax
; _masm->pop(atos); // restore the return value
00007fffe1044b8d: jmpq 0x7fffe1044e00
; _masm->jmp(done);
00007fffe1044b92: mov -0x18(%rbp),%rsi
00007fffe1044b96: mov 0x10(%rsi),%rsi
00007fffe1044b9a: mov 0x8(%rsi),%rsi
; _masm->get_constant_pool(c_rarg1);
00007fffe1044b9e: movzwl 0x1(%r13),%edx
00007fffe1044ba3: bswap %edx
00007fffe1044ba5: shr $0x10,%edx
; _masm->get_unsigned_2_byte_index_at_bcp(c_rarg2, 1);
00007fffe1044ba8: callq 0x7fffe1044bb2
00007fffe1044bad: jmpq 0x7fffe1044e00
00007fffe1044bb2: lea 0x8(%rsp),%rax
00007fffe1044bb7: mov %r13,-0x38(%rbp)
00007fffe1044bbb: cmpq $0x0,-0x10(%rbp)
00007fffe1044bc3: je 0x7fffe1044c40
00007fffe1044bc9: mov %rsp,-0x28(%rsp)
00007fffe1044bce: sub $0x80,%rsp
00007fffe1044bd5: mov %rax,0x78(%rsp)
00007fffe1044bda: mov %rcx,0x70(%rsp)
00007fffe1044bdf: mov %rdx,0x68(%rsp)
00007fffe1044be4: mov %rbx,0x60(%rsp)
00007fffe1044be9: mov %rbp,0x50(%rsp)
00007fffe1044bee: mov %rsi,0x48(%rsp)
00007fffe1044bf3: mov %rdi,0x40(%rsp)
00007fffe1044bf8: mov %r8,0x38(%rsp)
00007fffe1044bfd: mov %r9,0x30(%rsp)
00007fffe1044c02: mov %r10,0x28(%rsp)
00007fffe1044c07: mov %r11,0x20(%rsp)
00007fffe1044c0c: mov %r12,0x18(%rsp)
00007fffe1044c11: mov %r13,0x10(%rsp)
00007fffe1044c16: mov %r14,0x8(%rsp)
00007fffe1044c1b: mov %r15,(%rsp)
00007fffe1044c1f: movabs $0x7ffff6c8ceb8,%rdi
00007fffe1044c29: movabs $0x7fffe1044bc9,%rsi
00007fffe1044c33: mov %rsp,%rdx
00007fffe1044c36: and $0xfffffffffffffff0,%rsp
00007fffe1044c3a: callq 0x7ffff68024fa <MacroAssembler::debug64(char*, long, long*)>
00007fffe1044c3f: hlt
00007fffe1044c40: push %r10
00007fffe1044c42: cmp 0x16346f27(%rip),%r12 # 0x7ffff738bb70 <_ZN8Universe17_narrow_ptrs_baseE>
00007fffe1044c49: je 0x7fffe1044cc6
00007fffe1044c4f: mov %rsp,-0x28(%rsp)
00007fffe1044c54: sub $0x80,%rsp
00007fffe1044c5b: mov %rax,0x78(%rsp)
00007fffe1044c60: mov %rcx,0x70(%rsp)
00007fffe1044c65: mov %rdx,0x68(%rsp)
00007fffe1044c6a: mov %rbx,0x60(%rsp)
00007fffe1044c6f: mov %rbp,0x50(%rsp)
00007fffe1044c74: mov %rsi,0x48(%rsp)
00007fffe1044c79: mov %rdi,0x40(%rsp)
00007fffe1044c7e: mov %r8,0x38(%rsp)
00007fffe1044c83: mov %r9,0x30(%rsp)
00007fffe1044c88: mov %r10,0x28(%rsp)
00007fffe1044c8d: mov %r11,0x20(%rsp)
00007fffe1044c92: mov %r12,0x18(%rsp)
00007fffe1044c97: mov %r13,0x10(%rsp)
00007fffe1044c9c: mov %r14,0x8(%rsp)
00007fffe1044ca1: mov %r15,(%rsp)
00007fffe1044ca5: movabs $0x7ffff6cf9a40,%rdi
00007fffe1044caf: movabs $0x7fffe1044c4f,%rsi
00007fffe1044cb9: mov %rsp,%rdx
00007fffe1044cbc: and $0xfffffffffffffff0,%rsp
00007fffe1044cc0: callq 0x7ffff68024fa <MacroAssembler::debug64(char*, long, long*)>
00007fffe1044cc5: hlt
00007fffe1044cc6: pop %r10
00007fffe1044cc8: mov %r15,%rdi
00007fffe1044ccb: mov %rbp,0x200(%r15)
00007fffe1044cd2: mov %rax,0x1f0(%r15)
00007fffe1044cd9: test $0xf,%esp
00007fffe1044cdf: je 0x7fffe1044cf7
00007fffe1044ce5: sub $0x8,%rsp
00007fffe1044ce9: callq 0x7ffff6652d9a <InterpreterRuntime::_new(JavaThread*, ConstantPool*, int)>
00007fffe1044cee: add $0x8,%rsp
00007fffe1044cf2: jmpq 0x7fffe1044cfc
00007fffe1044cf7: callq 0x7ffff6652d9a <InterpreterRuntime::_new(JavaThread*, ConstantPool*, int)>
00007fffe1044cfc: push %rax
00007fffe1044cfd: push %rdi
00007fffe1044cfe: push %rsi
00007fffe1044cff: push %rdx
00007fffe1044d00: push %rcx
00007fffe1044d01: push %r8
00007fffe1044d03: push %r9
00007fffe1044d05: push %r10
00007fffe1044d07: mov %rsp,%r10
00007fffe1044d0a: and $0xfffffffffffffff0,%rsp
00007fffe1044d0e: push %r10
00007fffe1044d10: push %r11
00007fffe1044d12: mov $0x1,%edi
00007fffe1044d17: callq 0x7ffff73b3030 <__GI___pthread_getspecific>
00007fffe1044d1c: pop %r11
00007fffe1044d1e: pop %rsp
00007fffe1044d1f: pop %r10
00007fffe1044d21: pop %r9
00007fffe1044d23: pop %r8
00007fffe1044d25: pop %rcx
00007fffe1044d26: pop %rdx
00007fffe1044d27: pop %rsi
00007fffe1044d28: pop %rdi
00007fffe1044d29: cmp %rax,%r15
00007fffe1044d2c: je 0x7fffe1044da9
00007fffe1044d32: mov %rsp,-0x28(%rsp)
00007fffe1044d37: sub $0x80,%rsp
00007fffe1044d3e: mov %rax,0x78(%rsp)
00007fffe1044d43: mov %rcx,0x70(%rsp)
00007fffe1044d48: mov %rdx,0x68(%rsp)
00007fffe1044d4d: mov %rbx,0x60(%rsp)
00007fffe1044d52: mov %rbp,0x50(%rsp)
00007fffe1044d57: mov %rsi,0x48(%rsp)
00007fffe1044d5c: mov %rdi,0x40(%rsp)
00007fffe1044d61: mov %r8,0x38(%rsp)
00007fffe1044d66: mov %r9,0x30(%rsp)
00007fffe1044d6b: mov %r10,0x28(%rsp)
00007fffe1044d70: mov %r11,0x20(%rsp)
00007fffe1044d75: mov %r12,0x18(%rsp)
00007fffe1044d7a: mov %r13,0x10(%rsp)
00007fffe1044d7f: mov %r14,0x8(%rsp)
00007fffe1044d84: mov %r15,(%rsp)
00007fffe1044d88: movabs $0x7ffff6cf9bb8,%rdi
00007fffe1044d92: movabs $0x7fffe1044d32,%rsi
00007fffe1044d9c: mov %rsp,%rdx
00007fffe1044d9f: and $0xfffffffffffffff0,%rsp
00007fffe1044da3: callq 0x7ffff68024fa <MacroAssembler::debug64(char*, long, long*)>
00007fffe1044da8: hlt
00007fffe1044da9: pop %rax
00007fffe1044daa: movabs $0x0,%r10
00007fffe1044db4: mov %r10,0x1f0(%r15)
00007fffe1044dbb: movabs $0x0,%r10
00007fffe1044dc5: mov %r10,0x200(%r15)
00007fffe1044dcc: cmpq $0x0,0x8(%r15)
00007fffe1044dd4: je 0x7fffe1044ddf
00007fffe1044dda: jmpq 0x7fffe1000420
00007fffe1044ddf: mov 0x250(%r15),%rax
00007fffe1044de6: movabs $0x0,%r10
00007fffe1044df0: mov %r10,0x250(%r15)
00007fffe1044df7: mov -0x38(%rbp),%r13
00007fffe1044dfb: mov -0x30(%rbp),%r14
; call_VM(rax, CAST_FROM_FN_PTR(address, InterpreterRuntime::_new), c_rarg1, c_rarg2);
00007fffe1044dff: retq
00007fffe1044e00: int3
arraylength字节码翻译成汇编指令:
;start:0x7fffe10453a0
;end:0x7fffe10453a4
00007fffe10453a0: pop %rax
00007fffe10453a1: mov 0xc(%rax),%eax
00007fffe10453a4: int3
原文地址:https://www.cnblogs.com/simoncook/p/11194057.html
时间: 2024-11-05 02:34:13