Request to commit - ARM + Shark - OSR support

Edward Nevill ed at camswl.com
Thu Oct 15 10:15:10 PDT 2009


Hi Folks,

The following patch adds OSR support to ARM + Shark.

It also fixes a number of bugs. The most important of these is a
change to src/share/vm/interpreter/bytecodeInterpreter.cpp.

This change is necessary because the C bytecode interpreter does not
support rewritten bytecodes. Instead it just throws a fatal error.
Now the Asm Interpreter does in fact rewrite some of the bytecodes.

Now with Shark support, the Shark JIT may in fact call the C
interpreter with a method which has bytecodes which have been rewritten
by the Asm interpreter. In fact, this was a bug all along as the
Asm interpreter can back out to the C interpreter in a number of
cases, most notably if JVMTI is enabled.

What the change does is, in the default case, it looks up the original
bytecode. If the current bytecode != the original it uses the original
as the opcode instead and tries the bytecode again.

Here is the actual diff for bytecodeInterpreter.cpp extracted from the
bigger diff below.

+@@ -2330,6 +2330,16 @@
+       }
+ 
+       DEFAULT:
++	  // ECN: Deal with rewritten bytecodes
++	  if ((Bytecodes::Code)opcode < Bytecodes::number_of_codes) {
++		Bytecodes::Code original_opcode = Bytecodes::java_code((Bytecodes::Code)opcode);
++
++		if ((jubyte)original_opcode != opcode) {
++			opcode = (jubyte)original_opcode;
++			goto opcode_switch;
++		}
++	  }
++	  
+           fatal2("\t*** Unimplemented opcode: %d = %s\n",
+                  opcode, Bytecodes::name((Bytecodes::Code)opcode));
+           goto finish;

So, the new code only affects the case where it was about to throw a
fatal error, where it checks to see if the bytecode was rewritten and
if so substitutes the new opcode and goes back to execute that.

The second change is a change to src/share/vm/shark/sharkCacheDecache.cpp

The change is to delete an UnImplemented() statement which I was
getting with ARM + Shark OSR. The change was suggested by Gary Benson.

The remainder of the changes are to cppInterpreter_arm.S

ChangeLog to follow.

Regards,
Ed

----------  CUT HERE -------------------------------------------------
diff -ruNE original/icedtea6/Makefile.am new/icedtea6/Makefile.am
--- original/icedtea6/Makefile.am	2009-10-15 17:18:04.000000000 +0100
+++ new/icedtea6/Makefile.am	2009-10-15 17:48:52.000000000 +0100
@@ -559,6 +559,7 @@
 ICEDTEA_FSG_PATCHES =
 
 ICEDTEA_PATCHES = \
+	patches/icedtea-support-rewrite.patch \
 	patches/icedtea-notice-safepoints.patch \
 	patches/hotspot/$(HSBUILD)/icedtea-bytecodeInterpreter.patch \
 	patches/icedtea-signature-iterator.patch \
diff -ruNE original/icedtea6/patches/icedtea-support-rewrite.patch new/icedtea6/patches/icedtea-support-rewrite.patch
--- original/icedtea6/patches/icedtea-support-rewrite.patch	1970-01-01 01:00:00.000000000 +0100
+++ new/icedtea6/patches/icedtea-support-rewrite.patch	2009-10-15 17:46:28.000000000 +0100
@@ -0,0 +1,19 @@
+--- openjdk/hotspot/src/share/vm/interpreter/bytecodeInterpreter.cpp	2009-10-14 10:19:45.000000000 +0100
++++ openjdk/hotspot/src/share/vm/interpreter/bytecodeInterpreter.cpp	2009-10-15 17:34:12.000000000 +0100
+@@ -2330,6 +2330,16 @@
+       }
+ 
+       DEFAULT:
++	  // ECN: Deal with rewritten bytecodes
++	  if ((Bytecodes::Code)opcode < Bytecodes::number_of_codes) {
++		Bytecodes::Code original_opcode = Bytecodes::java_code((Bytecodes::Code)opcode);
++
++		if ((jubyte)original_opcode != opcode) {
++			opcode = (jubyte)original_opcode;
++			goto opcode_switch;
++		}
++	  }
++	  
+           fatal2("\t*** Unimplemented opcode: %d = %s\n",
+                  opcode, Bytecodes::name((Bytecodes::Code)opcode));
+           goto finish;
diff -ruNE original/icedtea6/ports/hotspot/src/cpu/zero/vm/cppInterpreter_arm.S new/icedtea6/ports/hotspot/src/cpu/zero/vm/cppInterpreter_arm.S
--- original/icedtea6/ports/hotspot/src/cpu/zero/vm/cppInterpreter_arm.S	2009-10-15 17:18:06.000000000 +0100
+++ new/icedtea6/ports/hotspot/src/cpu/zero/vm/cppInterpreter_arm.S	2009-10-15 17:38:27.000000000 +0100
@@ -17,11 +17,25 @@
 
 #ifdef HOTSPOT_ASM
 
+#define ARMv4
+
 #ifdef SHARK
 #define USE_COMPILER
 #endif
 
-#define ARMv4
+#ifdef USE_COMPILER
+
+#define MP_COMPILE_THRESHOLD	0x10000		// 65536 - must be a single MOV constant
+#define UP_COMPILE_THRESHOLD	0x30000		// 196608 - must be a single MOV constant
+
+#ifndef DISABLE_ON_STACK_REPLACEMENT
+#define ON_STACK_REPLACEMENT
+#endif
+#ifndef ENABLE_BG_COMP_ON_NON_MP
+#define DISABLE_BG_COMP_ON_NON_MP
+#endif
+
+#endif // USE_COMPILER
 
 #ifndef DISABLE_NOTICE_SAFEPOINTS
 #define NOTICE_SAFEPOINTS
@@ -237,6 +251,25 @@
 #endif
 	.endm
 
+ at ------------------------------------------------
+@ On stack replacement macro
+@ Usage:
+@	OSR	<compiler specific code>
+ at ------------------------------------------------
+	.macro	OSR	p1, p2, p3, p4
+#ifdef ON_STACK_REPLACEMENT
+  .ifnes "\p4", ""
+	\p1 \p2, \p3, \p4
+  .else
+    .ifnes "\p3", ""
+	\p1 \p2, \p3
+    .else
+	\p1 \p2
+    .endif
+  .endif
+#endif
+	.endm
+
 	.macro	Opcode	label
 	ALIGN_OPCODE
 do_\label:
@@ -2581,42 +2614,39 @@
 	PUSH	tmp2
 	DISPATCH_FINISH
 
-@ ip = branch offset
-@ r0 = 1st bytecode
-@ jpc has been updated
 	Opcode	goto
         ldrsb   r1, [jpc, #1]
         ldrb    tmp1, [jpc, #2]
+branch_taken:
         orr     tmp1, tmp1, r1, lsl #8
         DISPATCH_START_REG	tmp1
-branch_taken:
-	ldr	r2, [dispatch, #SafePointSynchronize_state_Address-XXX]
 	cmp	tmp1, #0
+	ble	do_backedge
+	DISPATCH_FINISH
+
+do_backedge:
   USEC	ldr	tmp2, [istate, #ISTATE_METHOD]
-	ldr	r1, [r2]
-	bgt	branch_no_check
+  OSR	ldr	lr, [dispatch, #InterpreterInvocationLimit_Address-XXX]
+  USEC	ldr	r1, [tmp2, #METHOD_BACKEDGECOUNTER]
+  USEC	ldr	ip, [tmp2, #METHOD_INVOCATIONCOUNTER]
+  USEC	add	r1, r1, #INVOCATIONCOUNTER_COUNTINCREMENT
+  OSR	ldr	lr, [lr]
+  USEC	add	ip, ip, #INVOCATIONCOUNTER_COUNTINCREMENT
+  USEC	str	r1, [tmp2, #METHOD_BACKEDGECOUNTER]
+  OSR	cmp	r1, lr
+  USEC	str	ip, [tmp2, #METHOD_INVOCATIONCOUNTER]
+  OSR	bcs	do_osr
 
-@ ECN: The C code does...
-@	if (UseCompiler && UseLoopCounter) {
-@		BACKEDGE_COUNT->increment();
-@		...
-@	}
-@ However, I just increment the counter because the check is actually
-@ more expensive than the increment. I don't believe this matters
-@ semantically, since is UseCompiler or UseLoopCounter is false then
-@ we shouldn't even be looking at the backedge counter.
-@
-@ ECN:	Concerns about counter overflowing
-@
-  USEC	ldr	r3, [tmp2, #METHOD_BACKEDGECOUNTER]
+osr_continue:
+	ldr	ip, [dispatch, #SafePointSynchronize_state_Address-XXX]
+	ldr	r1, [ip]
 	cmp	r1, #1
-  USEC	add	r3, r3, #INVOCATIONCOUNTER_COUNTINCREMENT
-  USEC	str	r3, [tmp2, #METHOD_BACKEDGECOUNTER]
-
-	bne	branch_no_check
+	beq	do_synchronize
+	DISPATCH_STATE	1
+	DISPATCH_FINISH
 
-	sub	jpc, jpc, tmp1		@ Point jpc back at the branch!!!
 
+do_synchronize:
 	add	r0, istate, #ISTATE_THREAD
 	bl	HandleMarkCleanerD
 	ldr	r0, [istate, #ISTATE_THREAD]
@@ -2631,16 +2661,90 @@
 	CACHE_JPC
 	cmp	r3, #0
 	bne	handle_exception
+	DISPATCH	0
+
+#ifdef ON_STACK_REPLACEMENT
+do_osr:
+	ldr	ip, [dispatch, #UseOnStackReplacement_Address-XXX]
+	ldrb	ip, [ip]
+	cmp	ip, #0
+	beq	osr_continue
+
+	DECACHE_JPC
+	DECACHE_STACK
+	ldr	r0, [istate, #ISTATE_THREAD]
+	sub	r1, jpc, tmp1
+	bl	_ZN18InterpreterRuntime26frequency_counter_overflowEP10JavaThreadPh
+	ldr	r3, [istate, #ISTATE_THREAD]
+	ASSERT_LOCALS_CACHED
+	ASSERT_STACK_CACHED
+	CACHE_CP
+	ldr	r1, [r3, #THREAD_PENDING_EXC]
+	CACHE_JPC
+	cmp	r1, #0
+	bne	handle_exception
+	cmp	r0, #0
+	beq	1f
+	ldr	r1, [r0, #56]
+	cmn	r1, #2
+	bne	osr_migrate
+1:
+	DISPATCH_START	0
+	b	osr_continue
+#endif
+
+#ifdef ON_STACK_REPLACEMENT
+osr_migrate:
+	ldr	tmp1, [r0, #128]	@ osr_method->osr_entry()
+	ldr	tmp2, [istate, #ISTATE_ADVANCE_PC]
+@	ldr	istate, [istate, #ISTATE_NEXT_FRAME]
+	mov	r0, r3
+	bl	_ZN13SharedRuntime19OSR_migration_beginEP10JavaThread
+	mov	r1, r0
+	ldr	r0, [istate, #ISTATE_METHOD]
+	ldrh	lr, [r0, #METHOD_MAXLOCALS]
+	ldrh	ip, [r0, #METHOD_SIZEOFPARAMETERS]
+	ldr	r3, [istate, #ISTATE_THREAD]
+	sub	lr, lr, ip
+	ldr	r2, [r3, #THREAD_TOP_ZERO_FRAME]
+	add	ip, r2, #4
+	ldr	r2, [r2]
+	add	ip, ip, lr, lsl #2
+	str	r2, [r3, #THREAD_TOP_ZERO_FRAME]
+	str	ip, [r3, #THREAD_JAVA_SP]
+	mov	r2, tmp1
+@ r0 = method
+@ r1 = osr_buf
+@ r2 = osr_entry
+	mov	lr, pc
+	ldr	pc, [tmp1]
 
-	DISPATCH_START_REG	tmp1	@ Refetch opcode and update jpc again
-branch_no_check:
-@ ECN: There is no protection against INVOCATIONCOUNTER overflowing!!!
-  USEC	ldr	r3, [tmp2, #METHOD_INVOCATIONCOUNTER]
+	cmp	tmp2, #0
+	ldmeqfd	arm_sp!, {regset, pc}
+
+	ldr	istate, [istate, #ISTATE_NEXT_FRAME]
+        ldr	lr, [istate, #-ISTATE_NEXT_FRAME+ISTATE_THREAD]!
+        CACHE_JPC
+        ldr     stack, [lr, #THREAD_JAVA_SP]
+        ldr     r2, [istate, #ISTATE_STACK_LIMIT]
+        sub     stack, stack, #4
+
+        ldr     r1, [lr, #THREAD_TOP_ZERO_FRAME]
+        add     r2, r2, #4
+        str     r2, [lr, #THREAD_JAVA_SP]
+        str     r1, [lr, #THREAD_LAST_JAVA_SP]
+        ldr     r3, [lr, #THREAD_PENDING_EXC]
+        DISPATCH_START_REG tmp2
+        CACHE_LOCALS
 	DISPATCH_NEXT
-  USEC	add	r3, r3, #INVOCATIONCOUNTER_COUNTINCREMENT
 	DISPATCH_NEXT
-  USEC	str	r3, [tmp2, #METHOD_INVOCATIONCOUNTER]
+        cmp     r3, #0
+        DISPATCH_NEXT
+        bne     return_exception
+	DISPATCH_NEXT
+        CACHE_CP
 	DISPATCH_FINISH
+#endif
 
 	Opcode	ifeq
 	Opcode	ifnull
@@ -2648,11 +2752,8 @@
         ldrsb   r1, [jpc, #1]
         ldrb    tmp1, [jpc, #2]
         cmp     r3, #0
-        orreq   tmp1, tmp1, r1, lsl #8
-        ldreqb  r0, [jpc, tmp1]!
-        ldrneb  r0, [jpc, #3]!
 	beq	branch_taken
-	DISPATCH_BYTECODE
+	DISPATCH	3
 
 	Opcode	ifne
 	Opcode	ifnonnull
@@ -2660,55 +2761,40 @@
         ldrsb   r1, [jpc, #1]
         ldrb    tmp1, [jpc, #2]
         cmp     r3, #0
-        orrne   tmp1, tmp1, r1, lsl #8
-        ldrneb  r0, [jpc, tmp1]!
-        ldreqb  r0, [jpc, #3]!
 	bne	branch_taken
-	DISPATCH_BYTECODE
+	DISPATCH	3
 
 	Opcode	iflt
         POP     r3
         ldrsb   r1, [jpc, #1]
         ldrb    tmp1, [jpc, #2]
         cmp     r3, #0
-        orrlt   tmp1, tmp1, r1, lsl #8
-        ldrltb  r0, [jpc, tmp1]!
-        ldrgeb  r0, [jpc, #3]!
 	blt	branch_taken
-	DISPATCH_BYTECODE
+	DISPATCH	3
 
 	Opcode	ifge
         POP     r3
         ldrsb   r1, [jpc, #1]
         ldrb    tmp1, [jpc, #2]
         cmp     r3, #0
-        orrge   tmp1, tmp1, r1, lsl #8
-        ldrgeb  r0, [jpc, tmp1]!
-        ldrltb  r0, [jpc, #3]!
 	bge	branch_taken
-	DISPATCH_BYTECODE
+	DISPATCH	3
 
 	Opcode	ifgt
         POP     r3
         ldrsb   r1, [jpc, #1]
         ldrb    tmp1, [jpc, #2]
         cmp     r3, #0
-        orrgt   tmp1, tmp1, r1, lsl #8
-        ldrgtb  r0, [jpc, tmp1]!
-        ldrleb  r0, [jpc, #3]!
 	bgt	branch_taken
-	DISPATCH_BYTECODE
+	DISPATCH	3
 
 	Opcode	ifle
         POP     r3
         ldrsb   r1, [jpc, #1]
         ldrb    tmp1, [jpc, #2]
         cmp     r3, #0
-        orrle   tmp1, tmp1, r1, lsl #8
-        ldrleb  r0, [jpc, tmp1]!
-        ldrgtb  r0, [jpc, #3]!
 	ble	branch_taken
-	DISPATCH_BYTECODE
+	DISPATCH	3
 
 	Opcode	if_icmpeq
 	Opcode	if_acmpeq
@@ -2716,11 +2802,8 @@
         ldrsb   r1, [jpc, #1]
         ldrb    tmp1, [jpc, #2]
         cmp     r3, r2
-        orreq   tmp1, tmp1, r1, lsl #8
-        ldreqb  r0, [jpc, tmp1]!
-        ldrneb  r0, [jpc, #3]!
 	beq	branch_taken
-	DISPATCH_BYTECODE
+	DISPATCH	3
 
 	Opcode	if_icmpne
 	Opcode	if_acmpne
@@ -2728,55 +2811,40 @@
         ldrsb   r1, [jpc, #1]
         ldrb    tmp1, [jpc, #2]
         cmp     r3, r2
-        orrne   tmp1, tmp1, r1, lsl #8
-        ldrneb  r0, [jpc, tmp1]!
-        ldreqb  r0, [jpc, #3]!
 	bne	branch_taken
-	DISPATCH_BYTECODE
+	DISPATCH	3
 
 	Opcode	if_icmplt
         POP    r2, r3
         ldrsb   r1, [jpc, #1]
         ldrb    tmp1, [jpc, #2]
         cmp     r3, r2
-        orrlt   tmp1, tmp1, r1, lsl #8
-        ldrltb  r0, [jpc, tmp1]!
-        ldrgeb  r0, [jpc, #3]!
 	blt	branch_taken
-	DISPATCH_BYTECODE
+	DISPATCH	3
 
 	Opcode	if_icmpge
         POP    r2, r3
         ldrsb   r1, [jpc, #1]
         ldrb    tmp1, [jpc, #2]
         cmp     r3, r2
-        orrge   tmp1, tmp1, r1, lsl #8
-        ldrgeb  r0, [jpc, tmp1]!
-        ldrltb  r0, [jpc, #3]!
 	bge	branch_taken
-	DISPATCH_BYTECODE
+	DISPATCH	3
 
 	Opcode	if_icmpgt
         POP    r2, r3
         ldrsb   r1, [jpc, #1]
         ldrb    tmp1, [jpc, #2]
         cmp     r3, r2
-        orrgt   tmp1, tmp1, r1, lsl #8
-        ldrgtb  r0, [jpc, tmp1]!
-        ldrleb  r0, [jpc, #3]!
 	bgt	branch_taken
-	DISPATCH_BYTECODE
+	DISPATCH	3
 
 	Opcode	if_icmple
         POP    r2, r3
         ldrsb   r1, [jpc, #1]
         ldrb    tmp1, [jpc, #2]
         cmp     r3, r2
-        orrle   tmp1, tmp1, r1, lsl #8
-        ldrleb  r0, [jpc, tmp1]!
-        ldrgtb  r0, [jpc, #3]!
 	ble	branch_taken
-	DISPATCH_BYTECODE
+	DISPATCH	3
 
 	Opcode	ireturn
 	Opcode	freturn
@@ -4407,6 +4475,7 @@
 	rsb	r3, r0, r3
 	rsb	r3, r3, arm_sp
 	cmp	r3, #32768
+
 	bge	fast_normal_entry_with_len
 
 	b	stack_overflow_before_frame
@@ -6229,12 +6298,14 @@
 
 	ALIGN_CODE
 bci_init:
+	stmfd	sp!, {r4, lr}
+
 	adrl	r3, dispatch_init_adcon
 	ldm	r3, {r0, r1}
 	add	r0, r0, r3
-	add	r1, r1, r0
+	add	r4, r1, r0
 	adrl	r2, adcon_init_table
-	mov	r3, r1
+	mov	r1, r4
 1:
 	ldr	ip, [r2], #4
 	cmp	ip, #0
@@ -6243,12 +6314,37 @@
 	bne	1b
 	adrl	r2, main_dispatch_table
 	mov	r1, #256
+	mov	r3, r4
 2:
 	ldr	ip, [r2], #4
 	str	ip, [r3], #4
 	subs	r1, r1, #1
 	bne	2b
 
+#ifdef USE_COMPILER
+
+#define	NPROCESSORS_CONF	83
+
+	mov	r0, #NPROCESSORS_CONF
+	bl	sysconf
+	cmp	r0, #2
+
+#ifdef DISABLE_BG_COMP_ON_NON_MP
+	movcc	r0, #0
+	ldrcc	r1, [r4, #BackgroundCompilation_Address-XXX]
+	strccb	r0, [r1]
+#endif
+
+	movcs	r0, #MP_COMPILE_THRESHOLD
+	movcc	r0, #UP_COMPILE_THRESHOLD
+	ldr	r1, [r4, #CompileThreshold_Address-XXX]
+	str	r0, [r1]
+
+
+#endif // USE_COMPILER
+
+	ldmfd	sp!, {r4, lr}
+
 #ifdef HW_FP
 vfp_init:
 	stmfd	sp!, {r4, r5, lr}
@@ -6348,6 +6444,9 @@
 	.word	_ZN11JvmtiExport28_can_post_interpreter_eventsE(GOT)
 	.word	UseCompiler(GOT)
 	.word	_ZN17InvocationCounter26InterpreterInvocationLimitE(GOT)
+	.word	CompileThreshold(GOT)
+	.word	BackgroundCompilation(GOT)
+	.word	UseOnStackReplacement(GOT)
 	.word	0
 
 	ALIGN_DATA
@@ -6627,9 +6726,14 @@
 CodeTrace_Buffer_Base:
 	.space	CODETRACE_BUFFER_SIZE
 #endif
+	.word	0, 0, 0, 0, 0, 0, 0, 0
+	.word	0, 0, 0, 0, 0
 DispatchBreakPoint:					.word	0
 VFP_Flag:						.word	0
 CodeTrace_Idx:						.word	0
+UseOnStackReplacement_Address:				.word	0
+BackgroundCompilation_Address:				.word	0
+CompileThreshold_Address:				.word	0
 InterpreterInvocationLimit_Address:			.word	0
 UseCompiler_Address:					.word	0
 can_post_interpreter_events:				.word	0
diff -ruNE original/icedtea6/ports/hotspot/src/share/vm/shark/sharkCacheDecache.cpp new/icedtea6/ports/hotspot/src/share/vm/shark/sharkCacheDecache.cpp
--- original/icedtea6/ports/hotspot/src/share/vm/shark/sharkCacheDecache.cpp	2009-10-15 17:18:06.000000000 +0100
+++ new/icedtea6/ports/hotspot/src/share/vm/shark/sharkCacheDecache.cpp	2009-10-15 17:39:25.000000000 +0100
@@ -189,9 +189,6 @@
                                           int box_offset,
                                           int obj_offset)
 {
-  if (max_monitors() > 1)
-    Unimplemented();   // XXX which order will they be in?
-
   // Copy the monitor from the OSR buffer to the frame
   int src_offset = max_locals() + index * 2;
   builder()->CreateStore(



More information about the distro-pkg-dev mailing list