1 /*
   2  * Copyright (c) 2012, 2016, Oracle and/or its affiliates. All rights reserved.
   3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
   4  *
   5  * This code is free software; you can redistribute it and/or modify it
   6  * under the terms of the GNU General Public License version 2 only, as
   7  * published by the Free Software Foundation.
   8  *
   9  * This code is distributed in the hope that it will be useful, but WITHOUT
  10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  12  * version 2 for more details (a copy is included in the LICENSE file that
  13  * accompanied this code).
  14  *
  15  * You should have received a copy of the GNU General Public License version
  16  * 2 along with this work; if not, write to the Free Software Foundation,
  17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  18  *
  19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  20  * or visit www.oracle.com if you need additional information or have any
  21  * questions.
  22  */
  23 package org.graalvm.compiler.hotspot;
  24 
  25 import org.graalvm.compiler.debug.GraalError;
  26 import org.graalvm.compiler.hotspot.meta.HotSpotConstantLoadAction;
  27 import org.graalvm.compiler.hotspot.meta.HotSpotProviders;
  28 import org.graalvm.compiler.hotspot.nodes.DeoptimizationFetchUnrollInfoCallNode;
  29 import org.graalvm.compiler.hotspot.nodes.EnterUnpackFramesStackFrameNode;
  30 import org.graalvm.compiler.hotspot.nodes.GraalHotSpotVMConfigNode;
  31 import org.graalvm.compiler.hotspot.nodes.LeaveCurrentStackFrameNode;
  32 import org.graalvm.compiler.hotspot.nodes.LeaveDeoptimizedStackFrameNode;
  33 import org.graalvm.compiler.hotspot.nodes.LeaveUnpackFramesStackFrameNode;
  34 import org.graalvm.compiler.hotspot.nodes.PushInterpreterFrameNode;
  35 import org.graalvm.compiler.hotspot.nodes.SaveAllRegistersNode;
  36 import org.graalvm.compiler.hotspot.nodes.UncommonTrapCallNode;
  37 import org.graalvm.compiler.hotspot.nodes.aot.LoadConstantIndirectlyNode;
  38 import org.graalvm.compiler.hotspot.nodes.aot.ResolveConstantNode;
  39 import org.graalvm.compiler.hotspot.nodes.aot.ResolveMethodAndLoadCountersNode;
  40 import org.graalvm.compiler.hotspot.nodes.profiling.RandomSeedNode;
  41 import org.graalvm.compiler.hotspot.replacements.EncodedSymbolConstant;
  42 import org.graalvm.compiler.lir.LIRFrameState;
  43 import org.graalvm.compiler.lir.StandardOp.SaveRegistersOp;
  44 import org.graalvm.compiler.lir.VirtualStackSlot;
  45 import org.graalvm.compiler.lir.gen.LIRGenerator;
  46 import org.graalvm.compiler.lir.gen.LIRGeneratorTool;
  47 
  48 import jdk.vm.ci.hotspot.HotSpotMetaspaceConstant;
  49 import jdk.vm.ci.hotspot.HotSpotObjectConstant;
  50 import jdk.vm.ci.meta.Constant;
  51 import jdk.vm.ci.meta.DeoptimizationAction;
  52 import jdk.vm.ci.meta.DeoptimizationReason;
  53 import jdk.vm.ci.meta.ResolvedJavaMethod;
  54 import jdk.vm.ci.meta.Value;
  55 
  56 /**
  57  * This interface defines the contract a HotSpot backend LIR generator needs to fulfill in addition
  58  * to abstract methods from {@link LIRGenerator} and {@link LIRGeneratorTool}.
  59  */
  60 public interface HotSpotLIRGenerator extends LIRGeneratorTool {
  61 
  62     /**
  63      * Emits an operation to make a tail call.
  64      *
  65      * @param args the arguments of the call
  66      * @param address the target address of the call
  67      */
  68     void emitTailcall(Value[] args, Value address);
  69 
  70     void emitDeoptimizeCaller(DeoptimizationAction action, DeoptimizationReason reason);
  71 
  72     /**
  73      * Emits code for a {@link SaveAllRegistersNode}.
  74      *
  75      * @return a {@link SaveRegistersOp} operation
  76      */
  77     SaveRegistersOp emitSaveAllRegisters();
  78 
  79     /**
  80      * Emits code for a {@link LeaveCurrentStackFrameNode}.
  81      *
  82      * @param saveRegisterOp saved registers
  83      */
  84     default void emitLeaveCurrentStackFrame(SaveRegistersOp saveRegisterOp) {
  85         throw GraalError.unimplemented();
  86     }
  87 
  88     /**
  89      * Emits code for a {@link LeaveDeoptimizedStackFrameNode}.
  90      *
  91      * @param frameSize
  92      * @param initialInfo
  93      */
  94     default void emitLeaveDeoptimizedStackFrame(Value frameSize, Value initialInfo) {
  95         throw GraalError.unimplemented();
  96     }
  97 
  98     /**
  99      * Emits code for a {@link EnterUnpackFramesStackFrameNode}.
 100      *
 101      * @param framePc
 102      * @param senderSp
 103      * @param senderFp
 104      * @param saveRegisterOp
 105      */
 106     default void emitEnterUnpackFramesStackFrame(Value framePc, Value senderSp, Value senderFp, SaveRegistersOp saveRegisterOp) {
 107         throw GraalError.unimplemented();
 108     }
 109 
 110     /**
 111      * Emits code for a {@link LeaveUnpackFramesStackFrameNode}.
 112      *
 113      * @param saveRegisterOp
 114      */
 115     default void emitLeaveUnpackFramesStackFrame(SaveRegistersOp saveRegisterOp) {
 116         throw GraalError.unimplemented();
 117     }
 118 
 119     /**
 120      * Emits code for a {@link PushInterpreterFrameNode}.
 121      *
 122      * @param frameSize
 123      * @param framePc
 124      * @param senderSp
 125      * @param initialInfo
 126      */
 127     default void emitPushInterpreterFrame(Value frameSize, Value framePc, Value senderSp, Value initialInfo) {
 128         throw GraalError.unimplemented();
 129     }
 130 
 131     /**
 132      * Emits code for a {@link LoadConstantIndirectlyNode}.
 133      *
 134      * @param constant
 135      * @return value of loaded address in register
 136      */
 137     default Value emitLoadObjectAddress(Constant constant) {
 138         throw GraalError.unimplemented();
 139     }
 140 
 141     /**
 142      * Emits code for a {@link LoadConstantIndirectlyNode}.
 143      *
 144      * @param constant
 145      * @return Value of loaded address in register
 146      */
 147     @SuppressWarnings("unused")
 148     default Value emitLoadMetaspaceAddress(Constant constant, HotSpotConstantLoadAction action) {
 149         throw GraalError.unimplemented();
 150     }
 151 
 152     /**
 153      * Emits code for a {@link GraalHotSpotVMConfigNode}.
 154      *
 155      * @param markId type of address to load
 156      * @return value of loaded global in register
 157      */
 158     default Value emitLoadConfigValue(int markId) {
 159         throw GraalError.unimplemented();
 160     }
 161 
 162     /**
 163      * Emits code for a {@link ResolveConstantNode} to resolve a {@link HotSpotObjectConstant}.
 164      *
 165      * @param constantDescription a description of the string that need to be materialized (and
 166      *            interned) as java.lang.String, generated with {@link EncodedSymbolConstant}
 167      * @return Returns the address of the requested constant.
 168      */
 169     @SuppressWarnings("unused")
 170     default Value emitObjectConstantRetrieval(Constant constant, Value constantDescription, LIRFrameState frameState) {
 171         throw GraalError.unimplemented();
 172     }
 173 
 174     /**
 175      * Emits code for a {@link ResolveConstantNode} to resolve a {@link HotSpotMetaspaceConstant}.
 176      *
 177      * @param constantDescription a symbolic description of the {@link HotSpotMetaspaceConstant}
 178      *            generated by {@link EncodedSymbolConstant}
 179      * @return Returns the address of the requested constant.
 180      */
 181     @SuppressWarnings("unused")
 182     default Value emitMetaspaceConstantRetrieval(Constant constant, Value constantDescription, LIRFrameState frameState) {
 183         throw GraalError.unimplemented();
 184     }
 185 
 186     /**
 187      * Emits code for a {@link ResolveMethodAndLoadCountersNode} to resolve a
 188      * {@link HotSpotMetaspaceConstant} that represents a {@link ResolvedJavaMethod} and return the
 189      * corresponding MethodCounters object.
 190      *
 191      * @param klassHint a klass in which the method is declared
 192      * @param methodDescription is symbolic description of the constant generated by
 193      *            {@link EncodedSymbolConstant}
 194      * @return Returns the address of the requested constant.
 195      */
 196     @SuppressWarnings("unused")
 197     default Value emitResolveMethodAndLoadCounters(Constant method, Value klassHint, Value methodDescription, LIRFrameState frameState) {
 198         throw GraalError.unimplemented();
 199     }
 200 
 201     /**
 202      * Emits code for a {@link ResolveConstantNode} to resolve a klass
 203      * {@link HotSpotMetaspaceConstant} and run static initializer.
 204      *
 205      * @param constantDescription a symbolic description of the {@link HotSpotMetaspaceConstant}
 206      *            generated by {@link EncodedSymbolConstant}
 207      * @return Returns the address of the requested constant.
 208      */
 209     @SuppressWarnings("unused")
 210     default Value emitKlassInitializationAndRetrieval(Constant constant, Value constantDescription, LIRFrameState frameState) {
 211         throw GraalError.unimplemented();
 212     }
 213 
 214     /**
 215      * Emits code for a {@link RandomSeedNode}.
 216      *
 217      * @return value of the counter
 218      */
 219     default Value emitRandomSeed() {
 220         throw GraalError.unimplemented();
 221     }
 222 
 223     /**
 224      * Emits code for a {@link UncommonTrapCallNode}.
 225      *
 226      * @param trapRequest
 227      * @param mode
 228      * @param saveRegisterOp
 229      * @return a {@code Deoptimization::UnrollBlock} pointer
 230      */
 231     default Value emitUncommonTrapCall(Value trapRequest, Value mode, SaveRegistersOp saveRegisterOp) {
 232         throw GraalError.unimplemented();
 233     }
 234 
 235     /**
 236      * Emits code for a {@link DeoptimizationFetchUnrollInfoCallNode}.
 237      *
 238      * @param mode
 239      * @param saveRegisterOp
 240      * @return a {@code Deoptimization::UnrollBlock} pointer
 241      */
 242     default Value emitDeoptimizationFetchUnrollInfoCall(Value mode, SaveRegistersOp saveRegisterOp) {
 243         throw GraalError.unimplemented();
 244     }
 245 
 246     /**
 247      * Gets a stack slot for a lock at a given lock nesting depth.
 248      */
 249     VirtualStackSlot getLockSlot(int lockDepth);
 250 
 251     @Override
 252     HotSpotProviders getProviders();
 253 
 254     Value emitCompress(Value pointer, CompressEncoding encoding, boolean nonNull);
 255 
 256     Value emitUncompress(Value pointer, CompressEncoding encoding, boolean nonNull);
 257 
 258 }