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.jni.ia32;
014    
015    import org.jikesrvm.VM;
016    import org.jikesrvm.ArchitectureSpecific.Registers;
017    import org.jikesrvm.compilers.common.CompiledMethod;
018    import org.jikesrvm.ia32.RegisterConstants.GPR;
019    import org.jikesrvm.runtime.ExceptionDeliverer;
020    import org.vmmagic.unboxed.Address;
021    import org.vmmagic.pragma.Uninterruptible;
022    
023    /**
024     * Exception delivery mechanisms for JNI on IA32
025     */
026    public class JNIExceptionDeliverer extends ExceptionDeliverer {
027    
028      /**
029       * Deliver exception, not possible for JNI methods
030       * @see org.jikesrvm.runtime.ExceptionDeliverer#deliverException(org.jikesrvm.compilers.common.CompiledMethod, org.vmmagic.unboxed.Address, java.lang.Throwable, org.jikesrvm.ArchitectureSpecific.Registers)
031       */
032      @Uninterruptible
033      @Override
034      public void deliverException(CompiledMethod compiledMethod,
035          Address catchBlockInstructionAddress, Throwable exceptionObject,
036          Registers registers) {
037        // this method should never get called as native methods don't have catch blocks
038        if (VM.VerifyAssertions) VM._assert(VM.NOT_REACHED);
039      }
040    
041      /**
042       * Unwind registers/stack through JNI method
043       * @see org.jikesrvm.runtime.ExceptionDeliverer#unwindStackFrame(org.jikesrvm.compilers.common.CompiledMethod, org.jikesrvm.ArchitectureSpecific.Registers)
044       */
045      @Uninterruptible
046      @Override
047      public void unwindStackFrame(CompiledMethod compiledMethod,
048          Registers registers) {
049        Address fp = registers.getInnermostFramePointer();
050        // Restore nonvolatile registers used by the JNI compiler
051        registers.gprs.set(GPR.EDI.value(), fp.plus(JNICompiler.EDI_SAVE_OFFSET).loadWord());
052        registers.gprs.set(GPR.EBX.value(), fp.plus(JNICompiler.EBX_SAVE_OFFSET).loadWord());
053        registers.gprs.set(GPR.EBP.value(), fp.plus(JNICompiler.EBP_SAVE_OFFSET).loadWord());
054        registers.unwindStackFrame();
055      }
056    
057    }