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 */
013package org.jikesrvm.compilers.opt.specialization;
014
015import org.jikesrvm.classloader.NormalMethod;
016import org.jikesrvm.compilers.common.CompiledMethod;
017import org.jikesrvm.compilers.opt.OptOptions;
018import org.jikesrvm.compilers.opt.driver.CompilationPlan;
019import org.jikesrvm.compilers.opt.driver.OptimizationPlanElement;
020import org.jikesrvm.compilers.opt.driver.OptimizationPlanner;
021import org.jikesrvm.compilers.opt.driver.OptimizingCompiler;
022
023/**
024 * This class represents a specialization context meaning
025 * "the invokee is thread local".
026 * We use this context to remove unnecessary synchronizations.
027 */
028public final class InvokeeThreadLocalContext implements SpecializationContext {
029
030  public InvokeeThreadLocalContext() {
031  }
032
033  @Override
034  public SpecializedMethod findOrCreateSpecializedVersion(NormalMethod source) {
035    // first check if the specialization database contains
036    // a specialized version from this context.
037    java.util.Iterator<SpecializedMethod> versions = SpecializationDatabase.getSpecialVersions(source);
038    if (versions != null) {
039      while (versions.hasNext()) {
040        SpecializedMethod spMethod = versions.next();
041        SpecializationContext context = spMethod.getSpecializationContext();
042        if (context == this) {
043          return spMethod;
044        }
045      }
046    }
047    // none found. create one.
048    SpecializedMethod spMethod = createSpecializedMethod(source);
049    // register it in the database.
050    SpecializationDatabase.registerSpecialVersion(spMethod);
051    // return it.
052    return spMethod;
053  }
054
055  private SpecializedMethod createSpecializedMethod(NormalMethod method) {
056    return (new SpecializedMethod(method, this));
057  }
058
059  /**
060   * Generate code to specialize a method in this context. Namely, invoke
061   * the opt compiler with the INVOKEE_THREAD_LOCAL option.
062   * @param source the method to compile
063   */
064  @Override
065  public CompiledMethod specialCompile(NormalMethod source) {
066    CompilationPlan plan = new CompilationPlan(source, optimizationPlan, null, options);
067    return OptimizingCompiler.compile(plan);
068  }
069
070  /**
071   * The default optimization options, with the INVOKEE_THREAD_LOCAL flag
072   * set true.
073   */
074  private static OptOptions options;
075  /**
076   * The default optimization plan.
077   */
078  private static OptimizationPlanElement[] optimizationPlan;
079
080  /**
081   * Initialize static members.
082   */
083  public static void init() {
084    options = new OptOptions();
085    optimizationPlan = OptimizationPlanner.createOptimizationPlan(options);
086    // all objects in the specialized method will be thread local
087    options.ESCAPE_INVOKEE_THREAD_LOCAL = true;
088  }
089}
090