src/jdk.internal.vm.compiler/share/classes/org.graalvm.compiler.core/src/org/graalvm/compiler/core/target/Backend.java
Index Unified diffs Context diffs Sdiffs Patch New Old Previous File Next File hotspot Sdiff src/jdk.internal.vm.compiler/share/classes/org.graalvm.compiler.core/src/org/graalvm/compiler/core/target

src/jdk.internal.vm.compiler/share/classes/org.graalvm.compiler.core/src/org/graalvm/compiler/core/target/Backend.java

Print this page




   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.core.target;
  24 


  25 import org.graalvm.compiler.asm.Assembler;
  26 import org.graalvm.compiler.code.CompilationResult;
  27 import org.graalvm.compiler.core.common.CompilationIdentifier;
  28 import org.graalvm.compiler.core.common.LIRKind;
  29 import org.graalvm.compiler.core.common.alloc.RegisterAllocationConfig;
  30 import org.graalvm.compiler.core.common.spi.ForeignCallDescriptor;
  31 import org.graalvm.compiler.core.common.spi.ForeignCallsProvider;
  32 import org.graalvm.compiler.debug.Debug;
  33 import org.graalvm.compiler.debug.Debug.Scope;
  34 import org.graalvm.compiler.lir.LIR;
  35 import org.graalvm.compiler.lir.asm.CompilationResultBuilder;
  36 import org.graalvm.compiler.lir.asm.CompilationResultBuilderFactory;
  37 import org.graalvm.compiler.lir.framemap.FrameMap;
  38 import org.graalvm.compiler.lir.framemap.FrameMapBuilder;
  39 import org.graalvm.compiler.lir.gen.LIRGenerationResult;
  40 import org.graalvm.compiler.lir.gen.LIRGeneratorTool;
  41 import org.graalvm.compiler.nodes.StructuredGraph;
  42 import org.graalvm.compiler.nodes.spi.NodeLIRBuilderTool;
  43 import org.graalvm.compiler.phases.tiers.SuitesProvider;
  44 import org.graalvm.compiler.phases.tiers.TargetProvider;
  45 import org.graalvm.compiler.phases.util.Providers;
  46 import org.graalvm.util.EconomicSet;
  47 
  48 import jdk.vm.ci.code.BailoutException;
  49 import jdk.vm.ci.code.CodeCacheProvider;
  50 import jdk.vm.ci.code.CompilationRequest;
  51 import jdk.vm.ci.code.CompiledCode;
  52 import jdk.vm.ci.code.InstalledCode;
  53 import jdk.vm.ci.code.Register;
  54 import jdk.vm.ci.code.RegisterConfig;
  55 import jdk.vm.ci.code.TargetDescription;
  56 import jdk.vm.ci.code.ValueKindFactory;
  57 import jdk.vm.ci.meta.ConstantReflectionProvider;
  58 import jdk.vm.ci.meta.JavaKind;
  59 import jdk.vm.ci.meta.MetaAccessProvider;
  60 import jdk.vm.ci.meta.ResolvedJavaMethod;
  61 import jdk.vm.ci.meta.SpeculationLog;
  62 
  63 import java.util.ArrayList;
  64 
  65 /**
  66  * Represents a compiler backend for Graal.
  67  */
  68 public abstract class Backend implements TargetProvider, ValueKindFactory<LIRKind> {
  69 
  70     private final Providers providers;
  71     private final ArrayList<CodeInstallationTaskFactory> codeInstallationTaskFactories;
  72 
  73     public static final ForeignCallDescriptor ARITHMETIC_FREM = new ForeignCallDescriptor("arithmeticFrem", float.class, float.class, float.class);
  74     public static final ForeignCallDescriptor ARITHMETIC_DREM = new ForeignCallDescriptor("arithmeticDrem", double.class, double.class, double.class);
  75 
  76     protected Backend(Providers providers) {
  77         this.providers = providers;
  78         this.codeInstallationTaskFactories = new ArrayList<>();
  79     }
  80 
  81     public synchronized void addCodeInstallationTask(CodeInstallationTaskFactory factory) {
  82         this.codeInstallationTaskFactories.add(factory);
  83     }
  84 


 138     public abstract NodeLIRBuilderTool newNodeLIRBuilder(StructuredGraph graph, LIRGeneratorTool lirGen);
 139 
 140     /**
 141      * Creates the assembler used to emit the machine code.
 142      */
 143     protected abstract Assembler createAssembler(FrameMap frameMap);
 144 
 145     /**
 146      * Creates the object used to fill in the details of a given compilation result.
 147      */
 148     public abstract CompilationResultBuilder newCompilationResultBuilder(LIRGenerationResult lirGenResult, FrameMap frameMap, CompilationResult compilationResult,
 149                     CompilationResultBuilderFactory factory);
 150 
 151     /**
 152      * Turns a Graal {@link CompilationResult} into a {@link CompiledCode} object that can be passed
 153      * to the VM for code installation.
 154      */
 155     protected abstract CompiledCode createCompiledCode(ResolvedJavaMethod method, CompilationRequest compilationRequest, CompilationResult compilationResult);
 156 
 157     /**
 158      * @see #createInstalledCode(ResolvedJavaMethod, CompilationRequest, CompilationResult,
 159      *      SpeculationLog, InstalledCode, boolean)
 160      */
 161     public InstalledCode createInstalledCode(ResolvedJavaMethod method, CompilationResult compilationResult,
 162                     SpeculationLog speculationLog, InstalledCode predefinedInstalledCode, boolean isDefault) {
 163         return createInstalledCode(method, null, compilationResult, speculationLog, predefinedInstalledCode, isDefault);
 164     }
 165 
 166     /**
 167      * @see #createInstalledCode(ResolvedJavaMethod, CompilationRequest, CompilationResult,
 168      *      SpeculationLog, InstalledCode, boolean, Object[])
 169      */
 170     @SuppressWarnings("try")
 171     public InstalledCode createInstalledCode(ResolvedJavaMethod method, CompilationRequest compilationRequest, CompilationResult compilationResult,
 172                     SpeculationLog speculationLog, InstalledCode predefinedInstalledCode, boolean isDefault) {
 173         return createInstalledCode(method, compilationRequest, compilationResult, speculationLog, predefinedInstalledCode, isDefault, null);
 174     }
 175 
 176     /**
 177      * Installs code based on a given compilation result.
 178      *
 179      * @param method the method compiled to produce {@code compiledCode} or {@code null} if the
 180      *            input to {@code compResult} was not a {@link ResolvedJavaMethod}
 181      * @param compilationRequest the compilation request or {@code null}
 182      * @param compilationResult the code to be compiled
 183      * @param predefinedInstalledCode a pre-allocated {@link InstalledCode} object to use as a
 184      *            reference to the installed code. If {@code null}, a new {@link InstalledCode}
 185      *            object will be created.
 186      * @param speculationLog the speculation log to be used
 187      * @param isDefault specifies if the installed code should be made the default implementation of
 188      *            {@code compRequest.getMethod()}. The default implementation for a method is the
 189      *            code executed for standard calls to the method. This argument is ignored if
 190      *            {@code compRequest == null}.
 191      * @param context a custom debug context to use for the code installation.
 192      * @return a reference to the compiled and ready-to-run installed code
 193      * @throws BailoutException if the code installation failed
 194      */
 195     @SuppressWarnings("try")
 196     public InstalledCode createInstalledCode(ResolvedJavaMethod method, CompilationRequest compilationRequest, CompilationResult compilationResult,
 197                     SpeculationLog speculationLog, InstalledCode predefinedInstalledCode, boolean isDefault, Object[] context) {
 198         Object[] debugContext = context != null ? context : new Object[]{getProviders().getCodeCache(), method, compilationResult};
 199         CodeInstallationTask[] tasks = new CodeInstallationTask[codeInstallationTaskFactories.size()];
 200         for (int i = 0; i < codeInstallationTaskFactories.size(); i++) {
 201             tasks[i] = codeInstallationTaskFactories.get(i).create();
 202         }
 203         try (Scope s = Debug.scope("CodeInstall", debugContext)) {

 204             for (CodeInstallationTask task : tasks) {
 205                 task.preProcess(compilationResult);
 206             }
 207 
 208             CompiledCode compiledCode = createCompiledCode(method, compilationRequest, compilationResult);
 209             InstalledCode installedCode = getProviders().getCodeCache().installCode(method, compiledCode, predefinedInstalledCode, speculationLog, isDefault);
 210 
 211             // Run post-code installation tasks.
 212             try {
 213                 for (CodeInstallationTask task : tasks) {
 214                     task.postProcess(installedCode);
 215                 }
 216                 for (CodeInstallationTask task : tasks) {
 217                     task.releaseInstallation(installedCode);
 218                 }
 219             } catch (Throwable t) {
 220                 installedCode.invalidate();
 221                 throw t;
 222             }
 223             return installedCode;
 224         } catch (Throwable e) {
 225             throw Debug.handle(e);
 226         }
 227     }
 228 
 229     /**
 230      * Installs code based on a given compilation result.
 231      *
 232      * @param method the method compiled to produce {@code compiledCode} or {@code null} if the
 233      *            input to {@code compResult} was not a {@link ResolvedJavaMethod}
 234      * @param compilationRequest the request or {@code null}
 235      * @param compilationResult the code to be compiled
 236      * @return a reference to the compiled and ready-to-run installed code
 237      * @throws BailoutException if the code installation failed
 238      */
 239     public InstalledCode addInstalledCode(ResolvedJavaMethod method, CompilationRequest compilationRequest, CompilationResult compilationResult) {
 240         return createInstalledCode(method, compilationRequest, compilationResult, null, null, false);
 241     }
 242 
 243     /**
 244      * Installs code based on a given compilation result and sets it as the default code to be used
 245      * when {@code method} is invoked.
 246      *
 247      * @param method the method compiled to produce {@code compiledCode} or {@code null} if the
 248      *            input to {@code compResult} was not a {@link ResolvedJavaMethod}
 249      * @param compilationResult the code to be compiled
 250      * @return a reference to the compiled and ready-to-run installed code
 251      * @throws BailoutException if the code installation failed
 252      */
 253     public InstalledCode createDefaultInstalledCode(ResolvedJavaMethod method, CompilationResult compilationResult) {
 254         return createInstalledCode(method, compilationResult, null, null, true);
 255     }
 256 
 257     /**
 258      * Emits the code for a given graph.
 259      *
 260      * @param installedCodeOwner the method the compiled code will be associated with once
 261      *            installed. This argument can be null.
 262      */
 263     public abstract void emitCode(CompilationResultBuilder crb, LIR lir, ResolvedJavaMethod installedCodeOwner);
 264 
 265     /**
 266      * Translates a set of registers from the callee's perspective to the caller's perspective. This
 267      * is needed for architectures where input/output registers are renamed during a call (e.g.
 268      * register windows on SPARC). Registers which are not visible by the caller are removed.
 269      */
 270     public abstract EconomicSet<Register> translateToCallerRegisters(EconomicSet<Register> calleeRegisters);
 271 
 272     /**
 273      * Gets the compilation id for a given {@link ResolvedJavaMethod}. Returns
 274      * {@code CompilationIdentifier#INVALID_COMPILATION_ID} in case there is no such id.




   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.core.target;
  24 
  25 import java.util.ArrayList;
  26 
  27 import org.graalvm.compiler.asm.Assembler;
  28 import org.graalvm.compiler.code.CompilationResult;
  29 import org.graalvm.compiler.core.common.CompilationIdentifier;
  30 import org.graalvm.compiler.core.common.LIRKind;
  31 import org.graalvm.compiler.core.common.alloc.RegisterAllocationConfig;
  32 import org.graalvm.compiler.core.common.spi.ForeignCallDescriptor;
  33 import org.graalvm.compiler.core.common.spi.ForeignCallsProvider;
  34 import org.graalvm.compiler.debug.DebugContext;

  35 import org.graalvm.compiler.lir.LIR;
  36 import org.graalvm.compiler.lir.asm.CompilationResultBuilder;
  37 import org.graalvm.compiler.lir.asm.CompilationResultBuilderFactory;
  38 import org.graalvm.compiler.lir.framemap.FrameMap;
  39 import org.graalvm.compiler.lir.framemap.FrameMapBuilder;
  40 import org.graalvm.compiler.lir.gen.LIRGenerationResult;
  41 import org.graalvm.compiler.lir.gen.LIRGeneratorTool;
  42 import org.graalvm.compiler.nodes.StructuredGraph;
  43 import org.graalvm.compiler.nodes.spi.NodeLIRBuilderTool;
  44 import org.graalvm.compiler.phases.tiers.SuitesProvider;
  45 import org.graalvm.compiler.phases.tiers.TargetProvider;
  46 import org.graalvm.compiler.phases.util.Providers;
  47 import org.graalvm.util.EconomicSet;
  48 
  49 import jdk.vm.ci.code.BailoutException;
  50 import jdk.vm.ci.code.CodeCacheProvider;
  51 import jdk.vm.ci.code.CompilationRequest;
  52 import jdk.vm.ci.code.CompiledCode;
  53 import jdk.vm.ci.code.InstalledCode;
  54 import jdk.vm.ci.code.Register;
  55 import jdk.vm.ci.code.RegisterConfig;
  56 import jdk.vm.ci.code.TargetDescription;
  57 import jdk.vm.ci.code.ValueKindFactory;
  58 import jdk.vm.ci.meta.ConstantReflectionProvider;
  59 import jdk.vm.ci.meta.JavaKind;
  60 import jdk.vm.ci.meta.MetaAccessProvider;
  61 import jdk.vm.ci.meta.ResolvedJavaMethod;
  62 import jdk.vm.ci.meta.SpeculationLog;
  63 


  64 /**
  65  * Represents a compiler backend for Graal.
  66  */
  67 public abstract class Backend implements TargetProvider, ValueKindFactory<LIRKind> {
  68 
  69     private final Providers providers;
  70     private final ArrayList<CodeInstallationTaskFactory> codeInstallationTaskFactories;
  71 
  72     public static final ForeignCallDescriptor ARITHMETIC_FREM = new ForeignCallDescriptor("arithmeticFrem", float.class, float.class, float.class);
  73     public static final ForeignCallDescriptor ARITHMETIC_DREM = new ForeignCallDescriptor("arithmeticDrem", double.class, double.class, double.class);
  74 
  75     protected Backend(Providers providers) {
  76         this.providers = providers;
  77         this.codeInstallationTaskFactories = new ArrayList<>();
  78     }
  79 
  80     public synchronized void addCodeInstallationTask(CodeInstallationTaskFactory factory) {
  81         this.codeInstallationTaskFactories.add(factory);
  82     }
  83 


 137     public abstract NodeLIRBuilderTool newNodeLIRBuilder(StructuredGraph graph, LIRGeneratorTool lirGen);
 138 
 139     /**
 140      * Creates the assembler used to emit the machine code.
 141      */
 142     protected abstract Assembler createAssembler(FrameMap frameMap);
 143 
 144     /**
 145      * Creates the object used to fill in the details of a given compilation result.
 146      */
 147     public abstract CompilationResultBuilder newCompilationResultBuilder(LIRGenerationResult lirGenResult, FrameMap frameMap, CompilationResult compilationResult,
 148                     CompilationResultBuilderFactory factory);
 149 
 150     /**
 151      * Turns a Graal {@link CompilationResult} into a {@link CompiledCode} object that can be passed
 152      * to the VM for code installation.
 153      */
 154     protected abstract CompiledCode createCompiledCode(ResolvedJavaMethod method, CompilationRequest compilationRequest, CompilationResult compilationResult);
 155 
 156     /**
 157      * @see #createInstalledCode(DebugContext, ResolvedJavaMethod, CompilationRequest,
 158      *      CompilationResult, SpeculationLog, InstalledCode, boolean, Object[])
 159      */
 160     public InstalledCode createInstalledCode(DebugContext debug, ResolvedJavaMethod method, CompilationResult compilationResult,
 161                     SpeculationLog speculationLog, InstalledCode predefinedInstalledCode, boolean isDefault) {
 162         return createInstalledCode(debug, method, null, compilationResult, speculationLog, predefinedInstalledCode, isDefault, null);
 163     }
 164 
 165     /**
 166      * @see #createInstalledCode(DebugContext, ResolvedJavaMethod, CompilationRequest,
 167      *      CompilationResult, SpeculationLog, InstalledCode, boolean, Object[])
 168      */
 169     @SuppressWarnings("try")
 170     public InstalledCode createInstalledCode(DebugContext debug, ResolvedJavaMethod method, CompilationRequest compilationRequest, CompilationResult compilationResult,
 171                     SpeculationLog speculationLog, InstalledCode predefinedInstalledCode, boolean isDefault) {
 172         return createInstalledCode(debug, method, compilationRequest, compilationResult, speculationLog, predefinedInstalledCode, isDefault, null);
 173     }
 174 
 175     /**
 176      * Installs code based on a given compilation result.
 177      *
 178      * @param method the method compiled to produce {@code compiledCode} or {@code null} if the
 179      *            input to {@code compResult} was not a {@link ResolvedJavaMethod}
 180      * @param compilationRequest the compilation request or {@code null}
 181      * @param compilationResult the code to be compiled
 182      * @param predefinedInstalledCode a pre-allocated {@link InstalledCode} object to use as a
 183      *            reference to the installed code. If {@code null}, a new {@link InstalledCode}
 184      *            object will be created.
 185      * @param speculationLog the speculation log to be used
 186      * @param isDefault specifies if the installed code should be made the default implementation of
 187      *            {@code compRequest.getMethod()}. The default implementation for a method is the
 188      *            code executed for standard calls to the method. This argument is ignored if
 189      *            {@code compRequest == null}.
 190      * @param context a custom debug context to use for the code installation
 191      * @return a reference to the compiled and ready-to-run installed code
 192      * @throws BailoutException if the code installation failed
 193      */
 194     @SuppressWarnings("try")
 195     public InstalledCode createInstalledCode(DebugContext debug, ResolvedJavaMethod method, CompilationRequest compilationRequest, CompilationResult compilationResult,
 196                     SpeculationLog speculationLog, InstalledCode predefinedInstalledCode, boolean isDefault, Object[] context) {
 197         Object[] debugContext = context != null ? context : new Object[]{getProviders().getCodeCache(), method, compilationResult};
 198         CodeInstallationTask[] tasks = new CodeInstallationTask[codeInstallationTaskFactories.size()];
 199         for (int i = 0; i < codeInstallationTaskFactories.size(); i++) {
 200             tasks[i] = codeInstallationTaskFactories.get(i).create();
 201         }
 202         try (DebugContext.Scope s2 = debug.scope("CodeInstall", debugContext);
 203                         DebugContext.Activation a = debug.activate()) {
 204             for (CodeInstallationTask task : tasks) {
 205                 task.preProcess(compilationResult);
 206             }
 207 
 208             CompiledCode compiledCode = createCompiledCode(method, compilationRequest, compilationResult);
 209             InstalledCode installedCode = getProviders().getCodeCache().installCode(method, compiledCode, predefinedInstalledCode, speculationLog, isDefault);
 210 
 211             // Run post-code installation tasks.
 212             try {
 213                 for (CodeInstallationTask task : tasks) {
 214                     task.postProcess(installedCode);
 215                 }
 216                 for (CodeInstallationTask task : tasks) {
 217                     task.releaseInstallation(installedCode);
 218                 }
 219             } catch (Throwable t) {
 220                 installedCode.invalidate();
 221                 throw t;
 222             }
 223             return installedCode;
 224         } catch (Throwable e) {
 225             throw debug.handle(e);
 226         }
 227     }
 228 
 229     /**
 230      * Installs code based on a given compilation result.
 231      *
 232      * @param method the method compiled to produce {@code compiledCode} or {@code null} if the
 233      *            input to {@code compResult} was not a {@link ResolvedJavaMethod}
 234      * @param compilationRequest the request or {@code null}
 235      * @param compilationResult the code to be compiled
 236      * @return a reference to the compiled and ready-to-run installed code
 237      * @throws BailoutException if the code installation failed
 238      */
 239     public InstalledCode addInstalledCode(DebugContext debug, ResolvedJavaMethod method, CompilationRequest compilationRequest, CompilationResult compilationResult) {
 240         return createInstalledCode(debug, method, compilationRequest, compilationResult, null, null, false);
 241     }
 242 
 243     /**
 244      * Installs code based on a given compilation result and sets it as the default code to be used
 245      * when {@code method} is invoked.
 246      *
 247      * @param method the method compiled to produce {@code compiledCode} or {@code null} if the
 248      *            input to {@code compResult} was not a {@link ResolvedJavaMethod}
 249      * @param compilationResult the code to be compiled
 250      * @return a reference to the compiled and ready-to-run installed code
 251      * @throws BailoutException if the code installation failed
 252      */
 253     public InstalledCode createDefaultInstalledCode(DebugContext debug, ResolvedJavaMethod method, CompilationResult compilationResult) {
 254         return createInstalledCode(debug, method, compilationResult, null, null, true);
 255     }
 256 
 257     /**
 258      * Emits the code for a given graph.
 259      *
 260      * @param installedCodeOwner the method the compiled code will be associated with once
 261      *            installed. This argument can be null.
 262      */
 263     public abstract void emitCode(CompilationResultBuilder crb, LIR lir, ResolvedJavaMethod installedCodeOwner);
 264 
 265     /**
 266      * Translates a set of registers from the callee's perspective to the caller's perspective. This
 267      * is needed for architectures where input/output registers are renamed during a call (e.g.
 268      * register windows on SPARC). Registers which are not visible by the caller are removed.
 269      */
 270     public abstract EconomicSet<Register> translateToCallerRegisters(EconomicSet<Register> calleeRegisters);
 271 
 272     /**
 273      * Gets the compilation id for a given {@link ResolvedJavaMethod}. Returns
 274      * {@code CompilationIdentifier#INVALID_COMPILATION_ID} in case there is no such id.


src/jdk.internal.vm.compiler/share/classes/org.graalvm.compiler.core/src/org/graalvm/compiler/core/target/Backend.java
Index Unified diffs Context diffs Sdiffs Patch New Old Previous File Next File