ARM: Enable safepoints for JIT-compiled code

Xerxes Rånby xerxes at zafena.se
Tue Jan 10 09:11:17 PST 2012


2012-01-10 15:31, Andrew Haley skrev:
> I've found the bug that broke safepoints.  It turns out that safepoints
> do not convert a PC address to a bytecode index, so you have to set the
> bytecode pointer explicitly whenever at a safepoint.  I'm intend to apply
> this to trunk and branch, given RM approval.
> 
> Andrew.

Thank you for making the garbage collector happy.
one question and one suggestion inline below:

> 
> 2012-01-09  Andrew Haley  <aph at redhat.com>
...
> 
> 	* arm_port/hotspot/src/cpu/zero/vm/cppInterpreter_arm.S
> 	(method_entry_freq_count_overflow): Make sure self_link is set
> 	when re-entering JIT-compiled code.

> diff -r 4d6b4215b78f -r 57ae0e361acf arm_port/hotspot/src/cpu/zero/vm/cppInterpreter_arm.S
> --- a/arm_port/hotspot/src/cpu/zero/vm/cppInterpreter_arm.S	Thu Dec 22 11:54:40 2011 -0500
> +++ b/arm_port/hotspot/src/cpu/zero/vm/cppInterpreter_arm.S	Mon Jan 09 13:34:27 2012 -0500
> @@ -3371,6 +3371,7 @@
>  #ifdef THUMB2EE
>  #define THUMB2_MAXLOCALS 1000
>  call_thumb2:
> +	str	istate, [istate, #ISTATE_SELF_LINK]

What makes the self-link un-set?



> diff -r 4d6b4215b78f -r 57ae0e361acf arm_port/hotspot/src/cpu/zero/vm/thumb2.cpp
> --- a/arm_port/hotspot/src/cpu/zero/vm/thumb2.cpp	Thu Dec 22 11:54:40 2011 -0500
> +++ b/arm_port/hotspot/src/cpu/zero/vm/thumb2.cpp	Mon Jan 09 13:34:27 2012 -0500
> @@ -791,6 +791,9 @@
>    }
>  #endif
> 
> +  fflush(stdout);
> +  fflush(stderr);
> +
>    opcodes.init_disassemble_info(&info, stdout, (fprintf_ftype)fprintf);
>    info.arch = bfd_arch_arm;
>    opcodes.disassemble_init_for_target(&info);
> @@ -950,6 +953,7 @@
>        }
>      }
>    }
> +  fflush(stdout);
>  }
>  #endif

Ok.


> 
> @@ -4342,9 +4346,8 @@
> 
>  // Insert code to poll the SafepointSynchronize state and call
>  // Helper_SafePoint.
> -void Thumb2_Safepoint(Thumb2_Info *jinfo, int stackdepth)
> -{
> -#if 0  // Causes maysterious segfaults
> +void Thumb2_Safepoint(Thumb2_Info *jinfo, int stackdepth, int bci)
> +{
>    Thumb2_Flush(jinfo);
>    int r_tmp = Thumb2_Tmp(jinfo, 0);
>    mov_imm(jinfo->codebuf, r_tmp, (u32)SafepointSynchronize::address_of_state());
> @@ -4353,11 +4356,11 @@
>    {
>      unsigned loc = forward_16(jinfo->codebuf);
>    Thumb2_save_locals(jinfo, stackdepth);
> +    mov_imm(jinfo->codebuf, ARM_R1, bci+CONSTMETHOD_CODEOFFSET);

Can we improve this part and calculate bci+CONSTMETHOD_CODEOFFSET+METHOD_CONSTMETHOD here?
to reduce jit code buffer usage, see below.

>      bl(jinfo->codebuf, handlers[H_SAFEPOINT]);
>    Thumb2_restore_locals(jinfo, stackdepth);
>      bcc_patch(jinfo->codebuf, COND_NE, loc);
>    }
> -#endif
>  }
> 

>  int Thumb2_Branch(Thumb2_Info *jinfo, unsigned bci, unsigned cond, int stackdepth)
> @@ -4369,7 +4372,7 @@
> 
>      if (jinfo->bc_stackinfo[dest_taken] & BC_COMPILED) {
>        loc = forward_16(jinfo->codebuf);
> -      Thumb2_Safepoint(jinfo, stackdepth);
> +      Thumb2_Safepoint(jinfo, stackdepth, bci);
...
> -	Thumb2_Return(jinfo, opc_return);
> +	Thumb2_Return(jinfo, opc_return, bci);
>  	break;
>        }
> 

OK

> @@ -7742,11 +7746,20 @@
>  // H_SAFEPOINT
>    handlers[H_SAFEPOINT] = out_pos(&codebuf);
>    stm(&codebuf, (1<<ARM_LR), ARM_SP, PUSH_FD, 1);
> +
> +  // Set up BytecodeInterpreter->_bcp for the GC
> +  // bci+CONSTMETHOD_CODEOFFSET is passed in ARM_R1
> +  ldr_imm(&codebuf, ARM_R0, Ristate, ISTATE_METHOD, 1, 0);

> +  ldr_imm(&codebuf, ARM_R0, ARM_R0, METHOD_CONSTMETHOD, 1, 0);
> +  add_reg(&codebuf, ARM_R0, ARM_R0, ARM_R1);

since METHOD_CONSTMETHOD are constant and generaded by the asm_helper
can we move this ldr_imm and add_reg to the Thumb2_Safepoint c++ function?

> +  str_imm(&codebuf, ARM_R0, Ristate, ISTATE_BCP, 1, 0);
> +
>    mov_imm(&codebuf, ARM_IP, (u32)Helper_SafePoint);
>    mov_reg(&codebuf, ARM_R0, Rthread);
>    blx_reg(&codebuf, ARM_IP);
>    ldm(&codebuf, (1<<ARM_LR), ARM_SP, POP_FD, 1);
>    cmp_imm(&codebuf, ARM_R0, 0);
> +
>    // The sequence here is delicate.  We need to seet things up so that
>    // it looks as though Thumb2_Handle_Exception_NoRegs was called
>    // directly from a compiled method.
> @@ -7759,6 +7772,29 @@
>    cb->hp += codebuf.idx * 2;
> 
>    thumb2_codebuf = cb;
> +
> +#if 0 // Disassemble the codebuf we just created.  For debugging
> +  Opcodes opcodes;
> +  if (t2ee_print_disass) {
> +    struct disassemble_info info;
> +    info.arch = bfd_arch_arm;
> +    opcodes.disassemble_init_for_target(&info);
> +    opcodes.init_disassemble_info(&info, stdout, (fprintf_ftype)fprintf);
> +    info.endian = BFD_ENDIAN_LITTLE;
> +    info.endian_code = BFD_ENDIAN_LITTLE;
> +    info.buffer = (bfd_byte *)codebuf.codebuf;
> +    info.buffer_vma = (bfd_vma)codebuf.codebuf;
> +    info.buffer_length = codebuf.idx * sizeof(short);
> +    info.disassembler_options = (char *)"force-thumb";
> +    int len;
> +    for (unsigned int i = 0; i < codebuf.idx * sizeof(short); i += len) {
> +      printf("0x%08x:\t", ((int)codebuf.codebuf)+i);
> +      len = opcodes.print_insn_little_arm(((bfd_vma)codebuf.codebuf)+i, &info);
> +      if (len == -1) len = 2;
> +      putchar('\n');
> +    }
> +  }
> +#endif
>  }
> 
>  #endif // THUMB2EE

OK

All in all good.

Cheers
Xerxes



More information about the distro-pkg-dev mailing list