/*
 * Copyright (C) 2016 The Android Open Source Project
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

public class Main {
  /// CHECK-START: void Main.staticNop() inliner (before)
  /// CHECK:                          InvokeStaticOrDirect

  /// CHECK-START: void Main.staticNop() inliner (after)
  /// CHECK-NOT:                      InvokeStaticOrDirect

  public static void staticNop() {
    Second.staticNop(11);
  }

  /// CHECK-START: void Main.nop(Second) inliner (before)
  /// CHECK:                          InvokeVirtual

  /// CHECK-START: void Main.nop(Second) inliner (after)
  /// CHECK-NOT:                      InvokeVirtual

  public static void nop(Second s) {
    s.nop();
  }

  /// CHECK-START: java.lang.Object Main.staticReturnArg2(java.lang.String) inliner (before)
  /// CHECK-DAG:  <<Value:l\d+>>      ParameterValue
  /// CHECK-DAG:  <<Ignored:i\d+>>    IntConstant 77
  /// CHECK-DAG:  <<ClinitCk:l\d+>>   ClinitCheck
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:  <<Invoke:l\d+>>     InvokeStaticOrDirect [<<Ignored>>,<<Value>>{{(,[ij]\d+)?}},<<ClinitCk>>]
  /// CHECK-DAG:                      Return [<<Invoke>>]

  /// CHECK-START: java.lang.Object Main.staticReturnArg2(java.lang.String) inliner (after)
  /// CHECK-DAG:  <<Value:l\d+>>      ParameterValue
  /// CHECK-DAG:                      Return [<<Value>>]

  /// CHECK-START: java.lang.Object Main.staticReturnArg2(java.lang.String) inliner (after)
  /// CHECK-NOT:                      InvokeStaticOrDirect

  public static Object staticReturnArg2(String value) {
    return Second.staticReturnArg2(77, value);
  }

  /// CHECK-START: long Main.returnArg1(Second, long) inliner (before)
  /// CHECK-DAG:  <<Second:l\d+>>     ParameterValue
  /// CHECK-DAG:  <<Value:j\d+>>      ParameterValue
  /// CHECK-DAG:  <<NullCk:l\d+>>     NullCheck [<<Second>>]
  /// CHECK-DAG:  <<Invoke:j\d+>>     InvokeVirtual [<<NullCk>>,<<Value>>]
  /// CHECK-DAG:                      Return [<<Invoke>>]

  /// CHECK-START: long Main.returnArg1(Second, long) inliner (after)
  /// CHECK-DAG:  <<Value:j\d+>>      ParameterValue
  /// CHECK-DAG:                      Return [<<Value>>]

  /// CHECK-START: long Main.returnArg1(Second, long) inliner (after)
  /// CHECK-NOT:                      InvokeVirtual

  public static long returnArg1(Second s, long value) {
    return s.returnArg1(value);
  }

  /// CHECK-START: int Main.staticReturn9() inliner (before)
  /// CHECK:      {{i\d+}}            InvokeStaticOrDirect

  /// CHECK-START: int Main.staticReturn9() inliner (before)
  /// CHECK-NOT:                      IntConstant 9

  /// CHECK-START: int Main.staticReturn9() inliner (after)
  /// CHECK-DAG:  <<Const9:i\d+>>     IntConstant 9
  /// CHECK-DAG:                      Return [<<Const9>>]

  /// CHECK-START: int Main.staticReturn9() inliner (after)
  /// CHECK-NOT:                      InvokeStaticOrDirect

  public static int staticReturn9() {
    return Second.staticReturn9();
  }

  /// CHECK-START: int Main.return7(Second) inliner (before)
  /// CHECK:      {{i\d+}}            InvokeVirtual

  /// CHECK-START: int Main.return7(Second) inliner (before)
  /// CHECK-NOT:                      IntConstant 7

  /// CHECK-START: int Main.return7(Second) inliner (after)
  /// CHECK-DAG:  <<Const7:i\d+>>     IntConstant 7
  /// CHECK-DAG:                      Return [<<Const7>>]

  /// CHECK-START: int Main.return7(Second) inliner (after)
  /// CHECK-NOT:                      InvokeVirtual

  public static int return7(Second s) {
    return s.return7(null);
  }

  /// CHECK-START: float Main.return42f(Second) inliner (before)
  /// CHECK:      {{f\d+}}            InvokeVirtual

  /// CHECK-START: float Main.return42f(Second) inliner (before)
  /// CHECK-NOT:                      FloatConstant 42

  /// CHECK-START: float Main.return42f(Second) inliner (after)
  /// CHECK-DAG:  <<Const42f:f\d+>>   FloatConstant 42
  /// CHECK-DAG:                      Return [<<Const42f>>]

  /// CHECK-START: float Main.return42f(Second) inliner (after)
  /// CHECK-NOT:                      InvokeVirtual

  public static float return42f(Second s) {
    return s.return42f();
  }

  /// CHECK-START: java.lang.String Main.staticReturnNull() inliner (before)
  /// CHECK:      {{l\d+}}            InvokeStaticOrDirect

  /// CHECK-START: java.lang.String Main.staticReturnNull() inliner (before)
  /// CHECK-NOT:                      NullConstant

  /// CHECK-START: java.lang.String Main.staticReturnNull() inliner (after)
  /// CHECK-DAG:  <<Null:l\d+>>       NullConstant
  /// CHECK-DAG:                      Return [<<Null>>]

  /// CHECK-START: java.lang.String Main.staticReturnNull() inliner (after)
  /// CHECK-NOT:                      InvokeStaticOrDirect

  public static String staticReturnNull() {
    return Second.staticReturnNull();
  }

  /// CHECK-START: java.lang.Object Main.returnNull(Second) inliner (before)
  /// CHECK:      {{l\d+}}            InvokeVirtual

  /// CHECK-START: java.lang.Object Main.returnNull(Second) inliner (before)
  /// CHECK-NOT:                      NullConstant

  /// CHECK-START: java.lang.Object Main.returnNull(Second) inliner (after)
  /// CHECK-DAG:  <<Null:l\d+>>       NullConstant
  /// CHECK-DAG:                      Return [<<Null>>]

  /// CHECK-START: java.lang.Object Main.returnNull(Second) inliner (after)
  /// CHECK-NOT:                      InvokeVirtual

  public static Object returnNull(Second s) {
    return s.returnNull();
  }

  /// CHECK-START: int Main.getInt(Second) inliner (before)
  /// CHECK:      {{i\d+}}            InvokeVirtual

  /// CHECK-START: int Main.getInt(Second) inliner (after)
  /// CHECK:      {{i\d+}}            InstanceFieldGet

  /// CHECK-START: int Main.getInt(Second) inliner (after)
  /// CHECK-NOT:                      InvokeVirtual

  public static int getInt(Second s) {
    return s.getInstanceIntField();
  }

  /// CHECK-START: double Main.getDouble(Second) inliner (before)
  /// CHECK:      {{d\d+}}            InvokeVirtual

  /// CHECK-START: double Main.getDouble(Second) inliner (after)
  /// CHECK:      {{d\d+}}            InstanceFieldGet

  /// CHECK-START: double Main.getDouble(Second) inliner (after)
  /// CHECK-NOT:                      InvokeVirtual

  public static double getDouble(Second s) {
    return s.getInstanceDoubleField(22);
  }

  /// CHECK-START: java.lang.Object Main.getObject(Second) inliner (before)
  /// CHECK:      {{l\d+}}            InvokeVirtual

  /// CHECK-START: java.lang.Object Main.getObject(Second) inliner (after)
  /// CHECK:      {{l\d+}}            InstanceFieldGet

  /// CHECK-START: java.lang.Object Main.getObject(Second) inliner (after)
  /// CHECK-NOT:                      InvokeVirtual

  public static Object getObject(Second s) {
    return s.getInstanceObjectField(-1L);
  }

  /// CHECK-START: java.lang.String Main.getString(Second) inliner (before)
  /// CHECK:      {{l\d+}}            InvokeVirtual

  /// CHECK-START: java.lang.String Main.getString(Second) inliner (after)
  /// CHECK:      {{l\d+}}            InstanceFieldGet

  /// CHECK-START: java.lang.String Main.getString(Second) inliner (after)
  /// CHECK-NOT:                      InvokeVirtual

  public static String getString(Second s) {
    return s.getInstanceStringField(null, "whatever", 1234L);
  }

  /// CHECK-START: int Main.staticGetInt(Second) inliner (before)
  /// CHECK:      {{i\d+}}            InvokeStaticOrDirect

  /// CHECK-START: int Main.staticGetInt(Second) inliner (after)
  /// CHECK:      {{i\d+}}            InvokeStaticOrDirect

  /// CHECK-START: int Main.staticGetInt(Second) inliner (after)
  /// CHECK-NOT:                      InstanceFieldGet

  public static int staticGetInt(Second s) {
    return Second.staticGetInstanceIntField(s);
  }

  /// CHECK-START: double Main.getDoubleFromParam(Second) inliner (before)
  /// CHECK:      {{d\d+}}            InvokeVirtual

  /// CHECK-START: double Main.getDoubleFromParam(Second) inliner (after)
  /// CHECK:      {{d\d+}}            InvokeStaticOrDirect

  /// CHECK-START: double Main.getDoubleFromParam(Second) inliner (after)
  /// CHECK-NOT:                      InstanceFieldGet
  /// CHECK-NOT:                      InvokeVirtual

  public static double getDoubleFromParam(Second s) {
    return s.getInstanceDoubleFieldFromParam(s);
  }

  /// CHECK-START: int Main.getStaticInt(Second) inliner (before)
  /// CHECK:      {{i\d+}}            InvokeVirtual

  /// CHECK-START: int Main.getStaticInt(Second) inliner (after)
  /// CHECK:      {{i\d+}}            InvokeStaticOrDirect

  /// CHECK-START: int Main.getStaticInt(Second) inliner (after)
  /// CHECK-NOT:                      InstanceFieldGet
  /// CHECK-NOT:                      StaticFieldGet
  /// CHECK-NOT:                      InvokeVirtual

  public static int getStaticInt(Second s) {
    return s.getStaticIntField();
  }

  /// CHECK-START: long Main.setLong(Second, long) inliner (before)
  /// CHECK:                          InvokeVirtual

  /// CHECK-START: long Main.setLong(Second, long) inliner (after)
  /// CHECK:                          InstanceFieldSet

  /// CHECK-START: long Main.setLong(Second, long) inliner (after)
  /// CHECK-NOT:                      InvokeVirtual

  public static long setLong(Second s, long value) {
    s.setInstanceLongField(-1, value);
    return s.instanceLongField;
  }

  /// CHECK-START: long Main.setLongReturnArg2(Second, long, int) inliner (before)
  /// CHECK:                          InvokeVirtual

  /// CHECK-START: long Main.setLongReturnArg2(Second, long, int) inliner (after)
  /// CHECK-DAG:  <<Second:l\d+>>     ParameterValue
  /// CHECK-DAG:  <<Value:j\d+>>      ParameterValue
  /// CHECK-DAG:  <<Arg2:i\d+>>       ParameterValue
  /// CHECK-DAG:  <<NullCk:l\d+>>     NullCheck [<<Second>>]
  /// CHECK-DAG:                      InstanceFieldSet [<<NullCk>>,<<Value>>]
  /// CHECK-DAG:  <<NullCk2:l\d+>>    NullCheck [<<Second>>]
  /// CHECK-DAG:  <<IGet:j\d+>>       InstanceFieldGet [<<NullCk2>>]
  /// CHECK-DAG:  <<Conv:j\d+>>       TypeConversion [<<Arg2>>]
  /// CHECK-DAG:  <<Add:j\d+>>        Add [<<IGet>>,<<Conv>>]
  /// CHECK-DAG:                      Return [<<Add>>]

  /// CHECK-START: long Main.setLongReturnArg2(Second, long, int) inliner (after)
  /// CHECK-NOT:                      InvokeVirtual

  public static long setLongReturnArg2(Second s, long value, int arg2) {
    int result = s.setInstanceLongFieldReturnArg2(value, arg2);
    return s.instanceLongField + result;
  }

  /// CHECK-START: long Main.staticSetLong(Second, long) inliner (before)
  /// CHECK:                          InvokeStaticOrDirect

  /// CHECK-START: long Main.staticSetLong(Second, long) inliner (after)
  /// CHECK:                          InvokeStaticOrDirect

  /// CHECK-START: long Main.staticSetLong(Second, long) inliner (after)
  /// CHECK-NOT:                      InstanceFieldSet

  public static long staticSetLong(Second s, long value) {
    Second.staticSetInstanceLongField(s, value);
    return s.instanceLongField;
  }

  /// CHECK-START: long Main.setLongThroughParam(Second, long) inliner (before)
  /// CHECK:                          InvokeVirtual

  /// CHECK-START: long Main.setLongThroughParam(Second, long) inliner (after)
  /// CHECK:                          InvokeStaticOrDirect

  /// CHECK-START: long Main.setLongThroughParam(Second, long) inliner (after)
  /// CHECK-NOT:                      InstanceFieldSet
  /// CHECK-NOT:                      InvokeVirtual

  public static long setLongThroughParam(Second s, long value) {
    s.setInstanceLongFieldThroughParam(s, value);
    return s.instanceLongField;
  }

  /// CHECK-START: float Main.setStaticFloat(Second, float) inliner (before)
  /// CHECK:                          InvokeVirtual

  /// CHECK-START: float Main.setStaticFloat(Second, float) inliner (after)
  /// CHECK:                          InvokeStaticOrDirect

  /// CHECK-START: float Main.setStaticFloat(Second, float) inliner (after)
  /// CHECK-NOT:                      InstanceFieldSet
  /// CHECK-NOT:                      StaticFieldSet
  /// CHECK-NOT:                      InvokeVirtual

  public static float setStaticFloat(Second s, float value) {
    s.setStaticFloatField(value);
    return s.staticFloatField;
  }

  /// CHECK-START: java.lang.Object Main.newObject() inliner (before)
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>{{(,[ij]\d+)?}}] method_name:java.lang.Object.<init>

  /// CHECK-START: java.lang.Object Main.newObject() inliner (after)
  /// CHECK-NOT:                      InvokeStaticOrDirect

  public static Object newObject() {
    return new Object();
  }

  /// CHECK-START: double Main.constructBase() inliner (before)
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>{{(,[ij]\d+)?}}] method_name:Base.<init>

  /// CHECK-START: double Main.constructBase() inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence
  /// CHECK-NOT:                      InstanceFieldSet

  public static double constructBase() {
    Base b = new Base();
    return b.intField + b.doubleField;
  }

  /// CHECK-START: double Main.constructBase(int) inliner (before)
  /// CHECK-DAG:  <<Value:i\d+>>      ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<Value>>{{(,[ij]\d+)?}}] method_name:Base.<init>

  /// CHECK-START: double Main.constructBase(int) inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence

  /// CHECK-START: double Main.constructBase(int) inliner (after)
  /// CHECK-DAG:  <<Value:i\d+>>      ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  /// CHECK-DAG:                      InstanceFieldSet [<<Obj>>,<<Value>>]

  /// CHECK-START: double Main.constructBase(int) inliner (after)
  /// CHECK-DAG:                      InstanceFieldSet
  /// CHECK-NOT:                      InstanceFieldSet

  public static double constructBase(int intValue) {
    Base b = new Base(intValue);
    return b.intField + b.doubleField;
  }

  /// CHECK-START: double Main.constructBaseWith0() inliner (before)
  /// CHECK-DAG:  <<Value:i\d+>>      IntConstant 0
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<Value>>{{(,[ij]\d+)?}}] method_name:Base.<init>

  /// CHECK-START: double Main.constructBaseWith0() inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence
  /// CHECK-NOT:                      InstanceFieldSet

  public static double constructBaseWith0() {
    Base b = new Base(0);
    return b.intField + b.doubleField;
  }

  /// CHECK-START: java.lang.String Main.constructBase(java.lang.String) inliner (before)
  /// CHECK-DAG:  <<Value:l\d+>>      ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<Value>>{{(,[ij]\d+)?}}] method_name:Base.<init>

  /// CHECK-START: java.lang.String Main.constructBase(java.lang.String) inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence

  /// CHECK-START: java.lang.String Main.constructBase(java.lang.String) inliner (after)
  /// CHECK-DAG:  <<Value:l\d+>>      ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  /// CHECK-DAG:                      InstanceFieldSet [<<Obj>>,<<Value>>]

  /// CHECK-START: java.lang.String Main.constructBase(java.lang.String) inliner (after)
  /// CHECK-DAG:                      InstanceFieldSet
  /// CHECK-NOT:                      InstanceFieldSet

  public static String constructBase(String stringValue) {
    Base b = new Base(stringValue);
    return b.stringField;
  }

  /// CHECK-START: java.lang.String Main.constructBaseWithNullString() inliner (before)
  /// CHECK-DAG:  <<Null:l\d+>>       NullConstant
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<Null>>{{(,[ij]\d+)?}}] method_name:Base.<init>

  /// CHECK-START: java.lang.String Main.constructBaseWithNullString() inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence

  /// CHECK-START: java.lang.String Main.constructBaseWithNullString() inliner (after)
  /// CHECK-NOT:                      InstanceFieldSet

  public static String constructBaseWithNullString() {
    String stringValue = null;
    Base b = new Base(stringValue);
    return b.stringField;
  }

  /// CHECK-START: double Main.constructBase(double, java.lang.Object) inliner (before)
  /// CHECK-DAG:  <<DValue:d\d+>>     ParameterValue
  /// CHECK-DAG:  <<OValue:l\d+>>     ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<DValue>>,<<OValue>>{{(,[ij]\d+)?}}] method_name:Base.<init>

  /// CHECK-START: double Main.constructBase(double, java.lang.Object) inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence

  /// CHECK-START: double Main.constructBase(double, java.lang.Object) inliner (after)
  /// CHECK-DAG:  <<DValue:d\d+>>     ParameterValue
  /// CHECK-DAG:  <<OValue:l\d+>>     ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  /// CHECK-DAG:                      InstanceFieldSet [<<Obj>>,<<DValue>>]
  /// CHECK-DAG:                      InstanceFieldSet [<<Obj>>,<<OValue>>]

  /// CHECK-START: double Main.constructBase(double, java.lang.Object) inliner (after)
  /// CHECK-DAG:                      InstanceFieldSet
  /// CHECK-DAG:                      InstanceFieldSet
  /// CHECK-NOT:                      InstanceFieldSet

  public static double constructBase(double doubleValue, Object objectValue) {
    Base b = new Base(doubleValue, objectValue);
    return (b.objectField != null) ? b.doubleField : -b.doubleField;
  }

  /// CHECK-START: double Main.constructBase(int, double, java.lang.Object) inliner (before)
  /// CHECK-DAG:  <<IValue:i\d+>>     ParameterValue
  /// CHECK-DAG:  <<DValue:d\d+>>     ParameterValue
  /// CHECK-DAG:  <<OValue:l\d+>>     ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<IValue>>,<<DValue>>,<<OValue>>{{(,[ij]\d+)?}}] method_name:Base.<init>

  /// CHECK-START: double Main.constructBase(int, double, java.lang.Object) inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence

  /// CHECK-START: double Main.constructBase(int, double, java.lang.Object) inliner (after)
  /// CHECK-DAG:  <<IValue:i\d+>>     ParameterValue
  /// CHECK-DAG:  <<DValue:d\d+>>     ParameterValue
  /// CHECK-DAG:  <<OValue:l\d+>>     ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  /// CHECK-DAG:                      InstanceFieldSet [<<Obj>>,<<IValue>>]
  /// CHECK-DAG:                      InstanceFieldSet [<<Obj>>,<<DValue>>]
  /// CHECK-DAG:                      InstanceFieldSet [<<Obj>>,<<OValue>>]

  /// CHECK-START: double Main.constructBase(int, double, java.lang.Object) inliner (after)
  /// CHECK-DAG:                      InstanceFieldSet
  /// CHECK-DAG:                      InstanceFieldSet
  /// CHECK-DAG:                      InstanceFieldSet
  /// CHECK-NOT:                      InstanceFieldSet

  public static double constructBase(int intValue, double doubleValue, Object objectValue) {
    Base b = new Base(intValue, doubleValue, objectValue);
    double tmp = b.intField + b.doubleField;
    return (b.objectField != null) ? tmp : -tmp;
  }

  /// CHECK-START: double Main.constructBaseWith0DoubleNull(double) inliner (before)
  /// CHECK-DAG:  <<IValue:i\d+>>     IntConstant 0
  /// CHECK-DAG:  <<DValue:d\d+>>     ParameterValue
  /// CHECK-DAG:  <<OValue:l\d+>>     NullConstant
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<IValue>>,<<DValue>>,<<OValue>>{{(,[ij]\d+)?}}] method_name:Base.<init>

  /// CHECK-START: double Main.constructBaseWith0DoubleNull(double) inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence

  /// CHECK-START: double Main.constructBaseWith0DoubleNull(double) inliner (after)
  /// CHECK-DAG:  <<DValue:d\d+>>     ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  /// CHECK-DAG:                      InstanceFieldSet [<<Obj>>,<<DValue>>]

  /// CHECK-START: double Main.constructBaseWith0DoubleNull(double) inliner (after)
  /// CHECK-DAG:                      InstanceFieldSet
  /// CHECK-NOT:                      InstanceFieldSet

  public static double constructBaseWith0DoubleNull(double doubleValue) {
    Base b = new Base(0, doubleValue, null);
    double tmp = b.intField + b.doubleField;
    return (b.objectField != null) ? tmp : -tmp;
  }

  /// CHECK-START: double Main.constructBase(int, double, java.lang.Object, java.lang.String) inliner (before)
  /// CHECK-DAG:  <<IValue:i\d+>>     ParameterValue
  /// CHECK-DAG:  <<DValue:d\d+>>     ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<IValue>>,<<DValue>>,{{l\d+}},{{l\d+}}{{(,[ij]\d+)?}}] method_name:Base.<init>

  /// CHECK-START: double Main.constructBase(int, double, java.lang.Object, java.lang.String) inliner (after)
  /// CHECK-DAG:  <<IValue:i\d+>>     ParameterValue
  /// CHECK-DAG:  <<DValue:d\d+>>     ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<IValue>>,<<DValue>>,{{l\d+}},{{l\d+}}{{(,[ij]\d+)?}}] method_name:Base.<init>

  /// CHECK-START: double Main.constructBase(int, double, java.lang.Object, java.lang.String) inliner (after)
  /// CHECK-NOT:                      InstanceFieldSet

  public static double constructBase(
      int intValue, double doubleValue, Object objectValue, String stringValue) {
    Base b = new Base(intValue, doubleValue, objectValue, stringValue);
    double tmp = b.intField + b.doubleField;
    tmp = (b.objectField != null) ? tmp : -tmp;
    return (b.stringField != null) ? 2.0 * tmp : 0.5 * tmp;
  }

  /// CHECK-START: double Main.constructBase(double) inliner (before)
  /// CHECK-DAG:  <<Value:d\d+>>      ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<Value>>{{(,[ij]\d+)?}}] method_name:Base.<init>

  /// CHECK-START: double Main.constructBase(double) inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence

  /// CHECK-START: double Main.constructBase(double) inliner (after)
  /// CHECK-DAG:  <<Value:d\d+>>      ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  /// CHECK-DAG:                      InstanceFieldSet [<<Obj>>,<<Value>>]

  /// CHECK-START: double Main.constructBase(double) inliner (after)
  /// CHECK-DAG:                      InstanceFieldSet
  /// CHECK-NOT:                      InstanceFieldSet

  public static double constructBase(double doubleValue) {
    Base b = new Base(doubleValue);
    return b.intField + b.doubleField;
  }

  /// CHECK-START: double Main.constructBaseWith0d() inliner (before)
  /// CHECK-DAG:  <<Value:d\d+>>      DoubleConstant
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<Value>>{{(,[ij]\d+)?}}] method_name:Base.<init>

  /// CHECK-START: double Main.constructBaseWith0d() inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence
  /// CHECK-NOT:                      InstanceFieldSet

  public static double constructBaseWith0d() {
    Base b = new Base(0.0);
    return b.intField + b.doubleField;
  }

  /// CHECK-START: double Main.constructBase(java.lang.Object) inliner (before)
  /// CHECK-DAG:  <<OValue:l\d+>>     ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<OValue>>{{(,[ij]\d+)?}}] method_name:Base.<init>

  /// CHECK-START: double Main.constructBase(java.lang.Object) inliner (after)
  /// CHECK-DAG:  <<OValue:l\d+>>     ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<OValue>>{{(,[ij]\d+)?}}] method_name:Base.<init>

  /// CHECK-START: double Main.constructBase(java.lang.Object) inliner (after)
  /// CHECK-NOT:                      InstanceFieldSet

  public static double constructBase(Object objectValue) {
    Base b = new Base(objectValue);
    double tmp = b.intField + b.doubleField;
    return (b.objectField != null) ? tmp + 1.0 : tmp - 1.0;
  }

  /// CHECK-START: double Main.constructBase(int, long) inliner (before)
  /// CHECK-DAG:  <<IValue:i\d+>>     ParameterValue
  /// CHECK-DAG:  <<JValue:j\d+>>     ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<IValue>>,<<JValue>>{{(,[ij]\d+)?}}] method_name:Base.<init>

  /// CHECK-START: double Main.constructBase(int, long) inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence

  /// CHECK-START: double Main.constructBase(int, long) inliner (after)
  /// CHECK-DAG:  <<IValue:i\d+>>     ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  /// CHECK-DAG:                      InstanceFieldSet [<<Obj>>,<<IValue>>]

  /// CHECK-START: double Main.constructBase(int, long) inliner (after)
  /// CHECK-DAG:                      InstanceFieldSet
  /// CHECK-NOT:                      InstanceFieldSet

  public static double constructBase(int intValue, long placeholder) {
    Base b = new Base(intValue, placeholder);
    return b.intField + b.doubleField;
  }

  /// CHECK-START: double Main.constructDerived() inliner (before)
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>{{(,[ij]\d+)?}}] method_name:Derived.<init>

  /// CHECK-START: double Main.constructDerived() inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence
  /// CHECK-NOT:                      InstanceFieldSet

  public static double constructDerived() {
    Derived d = new Derived();
    return d.intField + d.doubleField;
  }

  /// CHECK-START: double Main.constructDerived(int) inliner (before)
  /// CHECK-DAG:  <<Value:i\d+>>      ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<Value>>{{(,[ij]\d+)?}}] method_name:Derived.<init>

  /// CHECK-START: double Main.constructDerived(int) inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence

  /// CHECK-START: double Main.constructDerived(int) inliner (after)
  /// CHECK-DAG:  <<Value:i\d+>>      ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  /// CHECK-DAG:                      InstanceFieldSet [<<Obj>>,<<Value>>]

  /// CHECK-START: double Main.constructDerived(int) inliner (after)
  /// CHECK-DAG:                      InstanceFieldSet
  /// CHECK-NOT:                      InstanceFieldSet

  public static double constructDerived(int intValue) {
    Derived d = new Derived(intValue);
    return d.intField + d.doubleField;
  }

  /// CHECK-START: double Main.constructDerivedWith0() inliner (before)
  /// CHECK-DAG:  <<Value:i\d+>>      IntConstant 0
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<Value>>{{(,[ij]\d+)?}}] method_name:Derived.<init>

  /// CHECK-START: double Main.constructDerivedWith0() inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence
  /// CHECK-NOT:                      InstanceFieldSet

  public static double constructDerivedWith0() {
    Derived d = new Derived(0);
    return d.intField + d.doubleField;
  }

  /// CHECK-START: java.lang.String Main.constructDerived(java.lang.String) inliner (before)
  /// CHECK-DAG:  <<Value:l\d+>>      ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<Value>>{{(,[ij]\d+)?}}] method_name:Derived.<init>

  /// CHECK-START: java.lang.String Main.constructDerived(java.lang.String) inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence

  /// CHECK-START: java.lang.String Main.constructDerived(java.lang.String) inliner (after)
  /// CHECK-NOT:                      InstanceFieldSet

  public static String constructDerived(String stringValue) {
    Derived d = new Derived(stringValue);
    return d.stringField;
  }

  /// CHECK-START: double Main.constructDerived(double) inliner (before)
  /// CHECK-DAG:  <<Value:d\d+>>      ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<Value>>{{(,[ij]\d+)?}}] method_name:Derived.<init>

  /// CHECK-START: double Main.constructDerived(double) inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence

  /// CHECK-START: double Main.constructDerived(double) inliner (after)
  /// CHECK-DAG:  <<Value:d\d+>>      ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  /// CHECK-DAG:                      InstanceFieldSet [<<Obj>>,<<Value>>]

  /// CHECK-START: double Main.constructDerived(double) inliner (after)
  /// CHECK-DAG:                      InstanceFieldSet
  /// CHECK-NOT:                      InstanceFieldSet

  public static double constructDerived(double doubleValue) {
    Derived d = new Derived(doubleValue);
    return d.intField + d.doubleField;
  }

  /// CHECK-START: double Main.constructDerivedWith0d() inliner (before)
  /// CHECK-DAG:  <<Value:d\d+>>      DoubleConstant
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<Value>>{{(,[ij]\d+)?}}] method_name:Derived.<init>

  /// CHECK-START: double Main.constructDerivedWith0d() inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence
  /// CHECK-NOT:                      InstanceFieldSet

  public static double constructDerivedWith0d() {
    Derived d = new Derived(0.0);
    return d.intField + d.doubleField;
  }

  /// CHECK-START: double Main.constructDerived(int, double, java.lang.Object) inliner (before)
  /// CHECK-DAG:  <<IValue:i\d+>>     ParameterValue
  /// CHECK-DAG:  <<DValue:d\d+>>     ParameterValue
  /// CHECK-DAG:  <<OValue:l\d+>>     ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<IValue>>,<<DValue>>,<<OValue>>{{(,[ij]\d+)?}}] method_name:Derived.<init>

  /// CHECK-START: double Main.constructDerived(int, double, java.lang.Object) inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence

  /// CHECK-START: double Main.constructDerived(int, double, java.lang.Object) inliner (after)
  /// CHECK-DAG:  <<DValue:d\d+>>     ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  /// CHECK-DAG:                      InstanceFieldSet [<<Obj>>,<<DValue>>]

  /// CHECK-START: double Main.constructDerived(int, double, java.lang.Object) inliner (after)
  /// CHECK-DAG:                      InstanceFieldSet
  /// CHECK-NOT:                      InstanceFieldSet

  public static double constructDerived(int intValue, double doubleValue, Object objectValue) {
    Derived d = new Derived(intValue, doubleValue, objectValue);
    double tmp = d.intField + d.doubleField;
    return (d.objectField != null) ? tmp : -tmp;
  }

  /// CHECK-START: double Main.constructDerived(int, double, java.lang.Object, java.lang.String) inliner (before)
  /// CHECK-DAG:  <<IValue:i\d+>>     ParameterValue
  /// CHECK-DAG:  <<DValue:d\d+>>     ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<IValue>>,<<DValue>>,{{l\d+}},{{l\d+}}{{(,[ij]\d+)?}}] method_name:Derived.<init>

  /// CHECK-START: double Main.constructDerived(int, double, java.lang.Object, java.lang.String) inliner (after)
  /// CHECK-DAG:  <<IValue:i\d+>>     ParameterValue
  /// CHECK-DAG:  <<DValue:d\d+>>     ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<IValue>>,<<DValue>>,{{l\d+}},{{l\d+}}{{(,[ij]\d+)?}}] method_name:Derived.<init>

  /// CHECK-START: double Main.constructDerived(int, double, java.lang.Object, java.lang.String) inliner (after)
  /// CHECK-NOT:                      InstanceFieldSet

  public static double constructDerived(
      int intValue, double doubleValue, Object objectValue, String stringValue) {
    Derived d = new Derived(intValue, doubleValue, objectValue, stringValue);
    double tmp = d.intField + d.doubleField;
    tmp = (d.objectField != null) ? tmp : -tmp;
    return (d.stringField != null) ? 2.0 * tmp : 0.5 * tmp;
  }

  /// CHECK-START: double Main.constructDerived(float) inliner (before)
  /// CHECK-DAG:  <<Value:f\d+>>      ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<Value>>{{(,[ij]\d+)?}}] method_name:Derived.<init>

  /// CHECK-START: double Main.constructDerived(float) inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence

  /// CHECK-START: double Main.constructDerived(float) inliner (after)
  /// CHECK-DAG:  <<Value:f\d+>>      ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  /// CHECK-DAG:                      InstanceFieldSet [<<Obj>>,<<Value>>]

  /// CHECK-START: double Main.constructDerived(float) inliner (after)
  /// CHECK-DAG:                      InstanceFieldSet
  /// CHECK-NOT:                      InstanceFieldSet

  public static double constructDerived(float floatValue) {
    Derived d = new Derived(floatValue);
    return d.intField + d.doubleField + d.floatField;
  }

  /// CHECK-START: double Main.constructDerived(int, double, java.lang.Object, float) inliner (before)
  /// CHECK-DAG:  <<IValue:i\d+>>     ParameterValue
  /// CHECK-DAG:  <<DValue:d\d+>>     ParameterValue
  /// CHECK-DAG:  <<OValue:l\d+>>     ParameterValue
  /// CHECK-DAG:  <<FValue:f\d+>>     ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<IValue>>,<<DValue>>,<<OValue>>,<<FValue>>{{(,[ij]\d+)?}}] method_name:Derived.<init>

  /// CHECK-START: double Main.constructDerived(int, double, java.lang.Object, float) inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence

  /// CHECK-START: double Main.constructDerived(int, double, java.lang.Object, float) inliner (after)
  /// CHECK-DAG:  <<IValue:i\d+>>     ParameterValue
  /// CHECK-DAG:  <<DValue:d\d+>>     ParameterValue
  /// CHECK-DAG:  <<FValue:f\d+>>     ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  /// CHECK-DAG:                      InstanceFieldSet [<<Obj>>,<<IValue>>]
  /// CHECK-DAG:                      InstanceFieldSet [<<Obj>>,<<DValue>>]
  /// CHECK-DAG:                      InstanceFieldSet [<<Obj>>,<<FValue>>]

  /// CHECK-START: double Main.constructDerived(int, double, java.lang.Object, float) inliner (after)
  /// CHECK-DAG:                      InstanceFieldSet
  /// CHECK-DAG:                      InstanceFieldSet
  /// CHECK-DAG:                      InstanceFieldSet
  /// CHECK-NOT:                      InstanceFieldSet

  public static double constructDerived(
      int intValue, double doubleValue, Object objectValue, float floatValue) {
    Derived d = new Derived(intValue, doubleValue, objectValue, floatValue);
    double tmp = d.intField + d.doubleField + d.floatField;
    return (d.objectField != null) ? tmp : -tmp;
  }

  /// CHECK-START: int Main.constructBaseWithFinalField() inliner (before)
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>{{(,[ij]\d+)?}}] method_name:BaseWithFinalField.<init>

  /// CHECK-START: int Main.constructBaseWithFinalField() inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence
  /// CHECK-NOT:                      InstanceFieldSet

  public static int constructBaseWithFinalField() {
    BaseWithFinalField b = new BaseWithFinalField();
    return b.intField;
  }

  /// CHECK-START: int Main.constructBaseWithFinalField(int) inliner (before)
  /// CHECK-DAG:  <<Value:i\d+>>      ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<Value>>{{(,[ij]\d+)?}}] method_name:BaseWithFinalField.<init>

  /// CHECK-START: int Main.constructBaseWithFinalField(int) inliner (after)
  /// CHECK-NOT:                      InvokeStaticOrDirect

  /// CHECK-START: int Main.constructBaseWithFinalField(int) inliner (after)
  /// CHECK-DAG:  <<Value:i\d+>>      ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  /// CHECK-DAG:                      ConstructorFence
  /// CHECK-DAG:                      InstanceFieldSet [<<Obj>>,<<Value>>]
  /// CHECK-DAG:                      ConstructorFence

  /// CHECK-START: int Main.constructBaseWithFinalField(int) inliner (after)
  /// CHECK-DAG:                      InstanceFieldSet
  /// CHECK-NOT:                      InstanceFieldSet

  public static int constructBaseWithFinalField(int intValue) {
    BaseWithFinalField b = new BaseWithFinalField(intValue);
    return b.intField;
  }

  /// CHECK-START: int Main.constructBaseWithFinalFieldWith0() inliner (before)
  /// CHECK-DAG:  <<Value:i\d+>>      IntConstant 0
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<Value>>{{(,[ij]\d+)?}}] method_name:BaseWithFinalField.<init>

  /// CHECK-START: int Main.constructBaseWithFinalFieldWith0() inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence
  /// CHECK-NOT:                      InstanceFieldSet

  public static int constructBaseWithFinalFieldWith0() {
    BaseWithFinalField b = new BaseWithFinalField(0);
    return b.intField;
  }

  /// CHECK-START: double Main.constructDerivedWithFinalField() inliner (before)
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>{{(,[ij]\d+)?}}] method_name:DerivedWithFinalField.<init>

  /// CHECK-START: double Main.constructDerivedWithFinalField() inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence
  /// CHECK-NOT:                      InstanceFieldSet

  public static double constructDerivedWithFinalField() {
    DerivedWithFinalField d = new DerivedWithFinalField();
    return d.intField + d.doubleField;
  }

  /// CHECK-START: double Main.constructDerivedWithFinalField(int) inliner (before)
  /// CHECK-DAG:  <<Value:i\d+>>      ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<Value>>{{(,[ij]\d+)?}}] method_name:DerivedWithFinalField.<init>

  /// CHECK-START: double Main.constructDerivedWithFinalField(int) inliner (after)
  /// CHECK-NOT:                      InvokeStaticOrDirect

  /// CHECK-START: double Main.constructDerivedWithFinalField(int) inliner (after)
  /// CHECK-DAG:  <<Value:i\d+>>      ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  /// CHECK-DAG:                      ConstructorFence
  /// CHECK-DAG:                      InstanceFieldSet [<<Obj>>,<<Value>>]
  /// CHECK-DAG:                      ConstructorFence

  /// CHECK-START: double Main.constructDerivedWithFinalField(int) inliner (after)
  /// CHECK-DAG:                      InstanceFieldSet
  /// CHECK-NOT:                      InstanceFieldSet

  public static double constructDerivedWithFinalField(int intValue) {
    DerivedWithFinalField d = new DerivedWithFinalField(intValue);
    return d.intField + d.doubleField;
  }

  /// CHECK-START: double Main.constructDerivedWithFinalFieldWith0() inliner (before)
  /// CHECK-DAG:  <<Value:i\d+>>      IntConstant 0
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<Value>>{{(,[ij]\d+)?}}] method_name:DerivedWithFinalField.<init>

  /// CHECK-START: double Main.constructDerivedWithFinalFieldWith0() inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence
  /// CHECK-NOT:                      InstanceFieldSet

  public static double constructDerivedWithFinalFieldWith0() {
    DerivedWithFinalField d = new DerivedWithFinalField(0);
    return d.intField + d.doubleField;
  }

  /// CHECK-START: double Main.constructDerivedWithFinalField(double) inliner (before)
  /// CHECK-DAG:  <<Value:d\d+>>      ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<Value>>{{(,[ij]\d+)?}}] method_name:DerivedWithFinalField.<init>

  /// CHECK-START: double Main.constructDerivedWithFinalField(double) inliner (after)
  /// CHECK-NOT:                      InvokeStaticOrDirect

  /// CHECK-START: double Main.constructDerivedWithFinalField(double) inliner (after)
  /// CHECK-DAG:  <<Value:d\d+>>      ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  /// CHECK-DAG:                      ConstructorFence
  /// CHECK-DAG:                      InstanceFieldSet [<<Obj>>,<<Value>>]
  /// CHECK-DAG:                      ConstructorFence

  /// CHECK-START: double Main.constructDerivedWithFinalField(double) inliner (after)
  /// CHECK-DAG:                      InstanceFieldSet
  /// CHECK-NOT:                      InstanceFieldSet

  public static double constructDerivedWithFinalField(double doubleValue) {
    DerivedWithFinalField d = new DerivedWithFinalField(doubleValue);
    return d.intField + d.doubleField;
  }

  /// CHECK-START: double Main.constructDerivedWithFinalFieldWith0d() inliner (before)
  /// CHECK-DAG:  <<Value:d\d+>>      DoubleConstant
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<Value>>{{(,[ij]\d+)?}}] method_name:DerivedWithFinalField.<init>

  /// CHECK-START: double Main.constructDerivedWithFinalFieldWith0d() inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence
  /// CHECK-NOT:                      InstanceFieldSet

  public static double constructDerivedWithFinalFieldWith0d() {
    DerivedWithFinalField d = new DerivedWithFinalField(0.0);
    return d.intField + d.doubleField;
  }

  /// CHECK-START: double Main.constructDerivedWithFinalField(int, double) inliner (before)
  /// CHECK-DAG:  <<IValue:i\d+>>     ParameterValue
  /// CHECK-DAG:  <<DValue:d\d+>>     ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<IValue>>,<<DValue>>{{(,[ij]\d+)?}}] method_name:DerivedWithFinalField.<init>

  /// CHECK-START: double Main.constructDerivedWithFinalField(int, double) inliner (after)
  /// CHECK-NOT:                      InvokeStaticOrDirect

  /// CHECK-START: double Main.constructDerivedWithFinalField(int, double) inliner (after)
  /// CHECK-DAG:  <<Value:d\d+>>      ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  /// CHECK-DAG:                      ConstructorFence
  /// CHECK-DAG:                      InstanceFieldSet [<<Obj>>,<<Value>>]
  /// CHECK-DAG:                      ConstructorFence

  /// CHECK-START: double Main.constructDerivedWithFinalField(int, double) inliner (after)
  /// CHECK-DAG:                      InstanceFieldSet
  /// CHECK-DAG:                      InstanceFieldSet
  /// CHECK-NOT:                      InstanceFieldSet

  /// CHECK-START: double Main.constructDerivedWithFinalField(int, double) inliner (after)
  /// CHECK-DAG:                      ConstructorFence
  /// CHECK-DAG:                      ConstructorFence
  /// CHECK-NOT:                      ConstructorFence

  public static double constructDerivedWithFinalField(int intValue, double doubleValue) {
    DerivedWithFinalField d = new DerivedWithFinalField(intValue, doubleValue);
    return d.intField + d.doubleField;
  }

  /// CHECK-START: double Main.constructDerivedWithFinalFieldWith0And0d() inliner (before)
  /// CHECK-DAG:  <<IValue:i\d+>>     IntConstant 0
  /// CHECK-DAG:  <<DValue:d\d+>>     DoubleConstant
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<IValue>>,<<DValue>>{{(,[ij]\d+)?}}] method_name:DerivedWithFinalField.<init>

  /// CHECK-START: double Main.constructDerivedWithFinalFieldWith0And0d() inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence
  /// CHECK-NOT:                      InstanceFieldSet

  public static double constructDerivedWithFinalFieldWith0And0d() {
    DerivedWithFinalField d = new DerivedWithFinalField(0, 0.0);
    return d.intField + d.doubleField;
  }

  /// CHECK-START: int Main.constructDerivedInSecondDex() inliner (before)
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>{{(,[ij]\d+)?}}] method_name:DerivedInSecondDex.<init>

  /// CHECK-START: int Main.constructDerivedInSecondDex() inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence
  /// CHECK-NOT:                      InstanceFieldSet

  public static int constructDerivedInSecondDex() {
    DerivedInSecondDex d = new DerivedInSecondDex();
    return d.intField;
  }

  /// CHECK-START: int Main.constructDerivedInSecondDex(int) inliner (before)
  /// CHECK-DAG:  <<Value:i\d+>>      ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<Value>>{{(,[ij]\d+)?}}] method_name:DerivedInSecondDex.<init>

  /// CHECK-START: int Main.constructDerivedInSecondDex(int) inliner (after)
  /// CHECK-DAG:  <<Value:i\d+>>      ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<Value>>{{(,[ij]\d+)?}}] method_name:DerivedInSecondDex.<init>

  /// CHECK-START: int Main.constructDerivedInSecondDex(int) inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      ConstructorFence
  /// CHECK-NOT:                      InstanceFieldSet

  public static int constructDerivedInSecondDex(int intValue) {
    DerivedInSecondDex d = new DerivedInSecondDex(intValue);
    return d.intField;
  }

  /// CHECK-START: int Main.constructDerivedInSecondDexWith0() inliner (before)
  /// CHECK-DAG:  <<Value:i\d+>>      IntConstant 0
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<Value>>{{(,[ij]\d+)?}}] method_name:DerivedInSecondDex.<init>

  /// CHECK-START: int Main.constructDerivedInSecondDexWith0() inliner (after)
  /// CHECK-DAG:  <<Value:i\d+>>      IntConstant 0
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<Value>>{{(,[ij]\d+)?}}] method_name:DerivedInSecondDex.<init>

  /// CHECK-START: int Main.constructDerivedInSecondDexWith0() inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      ConstructorFence
  /// CHECK-NOT:                      InstanceFieldSet

  public static int constructDerivedInSecondDexWith0() {
    DerivedInSecondDex d = new DerivedInSecondDex(0);
    return d.intField;
  }

  /// CHECK-START: int Main.constructDerivedInSecondDex(long) inliner (before)
  /// CHECK-DAG:  <<Value:j\d+>>      ParameterValue
  /// CHECK-DAG:  <<Obj:l\d+>>        NewInstance
  // Note: The ArtMethod* (typed as int or long) is optional after sharpening.
  /// CHECK-DAG:                      InvokeStaticOrDirect [<<Obj>>,<<Value>>{{(,[ij]\d+)?}}] method_name:DerivedInSecondDex.<init>

  /// CHECK-START: int Main.constructDerivedInSecondDex(long) inliner (after)
  /// CHECK:                          ConstructorFence
  /// CHECK-NOT:                      InvokeStaticOrDirect
  /// CHECK-NOT:                      ConstructorFence
  /// CHECK-NOT:                      InstanceFieldSet

  public static int constructDerivedInSecondDex(long placeholder) {
    DerivedInSecondDex d = new DerivedInSecondDex(placeholder);
    return d.intField;
  }

  public static void main(String[] args) throws Exception {
    Second s = new Second();

    // Replaced NOP pattern.
    staticNop();
    nop(s);
    // Replaced "return arg" pattern.
    assertEquals("arbitrary string", staticReturnArg2("arbitrary string"));
    assertEquals(4321L, returnArg1(s, 4321L));
    // Replaced "return const" pattern.
    assertEquals(9, staticReturn9());
    assertEquals(7, return7(s));
    assertEquals(42.0f, return42f(s));
    assertEquals(null, staticReturnNull());
    assertEquals(null, returnNull(s));
    // Replaced IGET pattern.
    assertEquals(42, getInt(s));
    assertEquals(-42.0, getDouble(s));
    assertEquals(null, getObject(s));
    assertEquals("placeholder", getString(s));
    // Not replaced IGET pattern.
    assertEquals(42, staticGetInt(s));
    assertEquals(-42.0, getDoubleFromParam(s));
    // SGET.
    assertEquals(4242, getStaticInt(s));
    // Replaced IPUT pattern.
    assertEquals(111L, setLong(s, 111L));
    assertEquals(345L, setLongReturnArg2(s, 222L, 123));
    // Not replaced IPUT pattern.
    assertEquals(222L, staticSetLong(s, 222L));
    assertEquals(333L, setLongThroughParam(s, 333L));
    // SPUT.
    assertEquals(-11.5f, setStaticFloat(s, -11.5f));

    if (newObject() == null) {
      throw new AssertionError("new Object() cannot be null.");
    }

    assertEquals(0.0, constructBase());
    assertEquals(42.0, constructBase(42));
    assertEquals(0.0, constructBaseWith0());
    assertEquals("something", constructBase("something"));
    assertEquals(null, constructBaseWithNullString());
    assertEquals(11.0, constructBase(11.0, new Object()));
    assertEquals(-12.0, constructBase(12.0, null));
    assertEquals(30.0, constructBase(17, 13.0, new Object()));
    assertEquals(-34.0, constructBase(19, 15.0, null));
    assertEquals(-22.5, constructBaseWith0DoubleNull(22.5));
    assertEquals(-8.0, constructBase(2, 14.0, null, null));
    assertEquals(-64.0, constructBase(4, 28.0, null, "placeholder"));
    assertEquals(13.0, constructBase(24, 2.0, new Object(), null));
    assertEquals(30.0, constructBase(11, 4.0, new Object(), "placeholder"));
    assertEquals(43.0, constructBase(43.0));
    assertEquals(0.0, constructBaseWith0d());
    assertEquals(1.0, constructBase(new Object()));
    assertEquals(-1.0, constructBase((Object) null));
    assertEquals(123.0, constructBase(123, 65L));

    assertEquals(0.0, constructDerived());
    assertEquals(73.0, constructDerived(73));
    assertEquals(0.0, constructDerivedWith0());
    assertEquals(null, constructDerived("something else"));
    assertEquals(18.0, constructDerived(18.0));
    assertEquals(0.0, constructDerivedWith0d());
    assertEquals(-7.0, constructDerived(5, 7.0, new Object()));
    assertEquals(-4.0, constructDerived(9, 4.0, null));
    assertEquals(0.0, constructDerived(1, 9.0, null, null));
    assertEquals(0.0, constructDerived(2, 8.0, null, "placeholder"));
    assertEquals(0.0, constructDerived(3, 7.0, new Object(), null));
    assertEquals(0.0, constructDerived(4, 6.0, new Object(), "placeholder"));
    assertEquals(17.0, constructDerived(17.0f));
    assertEquals(-5.5, constructDerived(6, -7.0, new Object(), 6.5f));

    assertEquals(0, constructBaseWithFinalField());
    assertEquals(77, constructBaseWithFinalField(77));
    assertEquals(0, constructBaseWithFinalFieldWith0());
    assertEquals(0.0, constructDerivedWithFinalField());
    assertEquals(-33.0, constructDerivedWithFinalField(-33));
    assertEquals(0.0, constructDerivedWithFinalFieldWith0());
    assertEquals(-44.0, constructDerivedWithFinalField(-44.0));
    assertEquals(0.0, constructDerivedWithFinalFieldWith0d());
    assertEquals(88, constructDerivedWithFinalField(22, 66.0));
    assertEquals(0.0, constructDerivedWithFinalFieldWith0And0d());

    assertEquals(0, constructDerivedInSecondDex());
    assertEquals(123, constructDerivedInSecondDex(123));
    assertEquals(0, constructDerivedInSecondDexWith0());
    assertEquals(0, constructDerivedInSecondDex(7L));
  }

  private static void assertEquals(int expected, int actual) {
    if (expected != actual) {
      throw new AssertionError("Wrong result: " + expected + " != " + actual);
    }
  }

  private static void assertEquals(float expected, float actual) {
    if (expected != actual) {
      throw new AssertionError("Wrong result: " + expected + " != " + actual);
    }
  }

  private static void assertEquals(double expected, double actual) {
    if (expected != actual) {
      throw new AssertionError("Wrong result: " + expected + " != " + actual);
    }
  }

  private static void assertEquals(Object expected, Object actual) {
    if (expected != actual && (expected == null || !expected.equals(actual))) {
      throw new AssertionError("Wrong result: " + expected + " != " + actual);
    }
  }
}
