001 /*
002 * This file is part of the Jikes RVM project (http://jikesrvm.org).
003 *
004 * This file is licensed to You under the Eclipse Public License (EPL);
005 * You may not use this file except in compliance with the License. You
006 * may obtain a copy of the License at
007 *
008 * http://www.opensource.org/licenses/eclipse-1.0.php
009 *
010 * See the COPYRIGHT.txt file distributed with this work for information
011 * regarding copyright ownership.
012 */
013 package org.jikesrvm.osr.ia32;
014
015 import org.jikesrvm.ArchitectureSpecific;
016 import org.jikesrvm.VM;
017 import org.jikesrvm.ia32.BaselineConstants;
018 import org.jikesrvm.runtime.Magic;
019 import org.jikesrvm.scheduler.RVMThread;
020 import org.vmmagic.pragma.NoInline;
021 import org.vmmagic.pragma.Uninterruptible;
022 import org.vmmagic.unboxed.Address;
023 import org.vmmagic.unboxed.Offset;
024
025 /**
026 * A class helps schedule OSRed method, it is called right after thread switch
027 * and highly depends on the calling convention. It should not be interrupted
028 * because it deals with row instruction address.
029 */
030 @Uninterruptible
031 public abstract class PostThreadSwitch implements BaselineConstants {
032
033 /**
034 * This method must not be inlined to keep the correctness
035 * This method is called at the end of threadSwitch, the caller
036 * is threadSwitchFrom<...>
037 */
038 @NoInline
039 public static void postProcess(RVMThread myThread) {
040
041 /* We need to generate thread specific code and install new code.
042 * We have to make sure that no GC happens from here and before
043 * the new code get executed.
044 */
045 // add branch instruction from CTR.
046 ArchitectureSpecific.CodeArray bridge = myThread.bridgeInstructions;
047
048 Address bridgeaddr = Magic.objectAsAddress(bridge);
049
050 if (VM.TraceOnStackReplacement) {
051 VM.sysWrite("osr post processing\n");
052 }
053
054 Offset offset = myThread.tsFPOffset.plus(STACKFRAME_RETURN_ADDRESS_OFFSET);
055 Magic.objectAsAddress(myThread.getStack()).store(bridgeaddr, offset);
056
057 myThread.tsFPOffset = Offset.zero();
058
059 myThread.isWaitingForOsr = false;
060 myThread.bridgeInstructions = null;
061
062 // no GC should happen until the glue code gets executed.
063 }
064 }