// Copyright (c) 2019, the R8 project authors. Please see the AUTHORS file
// for details. All rights reserved. Use of this source code is governed by a
// BSD-style license that can be found in the LICENSE file.

package com.android.tools.r8.ir.desugar;

import static org.objectweb.asm.Opcodes.INVOKEINTERFACE;
import static org.objectweb.asm.Opcodes.INVOKESPECIAL;
import static org.objectweb.asm.Opcodes.INVOKESTATIC;
import static org.objectweb.asm.Opcodes.INVOKEVIRTUAL;

import com.android.tools.r8.cf.code.CfArrayStore;
import com.android.tools.r8.cf.code.CfConstNumber;
import com.android.tools.r8.cf.code.CfInstruction;
import com.android.tools.r8.cf.code.CfInvoke;
import com.android.tools.r8.cf.code.CfLabel;
import com.android.tools.r8.cf.code.CfLoad;
import com.android.tools.r8.cf.code.CfNew;
import com.android.tools.r8.cf.code.CfNewArray;
import com.android.tools.r8.cf.code.CfReturn;
import com.android.tools.r8.cf.code.CfStackInstruction;
import com.android.tools.r8.cf.code.CfStore;
import com.android.tools.r8.cf.code.CfThrow;
import com.android.tools.r8.cf.code.CfTryCatch;
import com.android.tools.r8.graph.CfCode;
import com.android.tools.r8.graph.DexClass;
import com.android.tools.r8.graph.DexItemFactory;
import com.android.tools.r8.graph.DexType;
import com.android.tools.r8.ir.code.MemberType;
import com.android.tools.r8.ir.code.ValueType;
import com.google.common.collect.ImmutableList;
import java.util.List;

public class ServiceLoaderSourceCode {

  // This is building the following implementation for service-loader rewriting:
  // public static <S> Iterator<S> loadS() {
  //   try {
  //     return Arrays.asList(X, Y, Z).iterator();
  //   } catch (Throwable t) {
  //     throw new ServiceConfigurationError(t.getMessage(), t);
  //   }
  // }
  public static CfCode generate(
      DexType serviceType, List<DexClass> classes, DexItemFactory factory) {
    ImmutableList.Builder<CfInstruction> builder = ImmutableList.builder();

    CfLabel tryCatchStart = new CfLabel();
    CfLabel tryCatchEnd = new CfLabel();

    builder.add(
        tryCatchStart,
        new CfConstNumber(classes.size(), ValueType.INT),
        new CfNewArray(factory.createArrayType(1, serviceType)));

    for (int i = 0; i < classes.size(); i++) {
      builder.add(
          new CfStackInstruction(CfStackInstruction.Opcode.Dup),
          new CfConstNumber(i, ValueType.INT),
          new CfNew(classes.get(i).type),
          new CfStackInstruction(CfStackInstruction.Opcode.Dup),
          new CfInvoke(
              INVOKESPECIAL,
              factory.createMethod(
                  classes.get(i).type,
                  factory.createProto(factory.voidType),
                  factory.constructorMethodName),
              false),
          new CfArrayStore(MemberType.OBJECT));
    }

    builder.add(
        new CfInvoke(INVOKESTATIC, factory.javaUtilArraysMethods.asList, false),
        new CfInvoke(
            INVOKEINTERFACE,
            factory.createMethod(
                factory.listType,
                factory.createProto(factory.iteratorType),
                factory.createString("iterator")),
            true),
        tryCatchEnd,
        new CfReturn(ValueType.OBJECT));

    // Build the exception handler.
    CfLabel tryCatchHandler = new CfLabel();
    builder.add(
        tryCatchHandler,
        new CfStore(ValueType.OBJECT, 0),
        new CfNew(factory.serviceLoaderConfigurationErrorType),
        new CfStackInstruction(CfStackInstruction.Opcode.Dup),
        new CfLoad(ValueType.OBJECT, 0),
        new CfInvoke(INVOKEVIRTUAL, factory.throwableMethods.getMessage, false),
        new CfLoad(ValueType.OBJECT, 0),
        new CfInvoke(
            INVOKESPECIAL,
            factory.createMethod(
                factory.serviceLoaderConfigurationErrorType,
                factory.createProto(factory.voidType, factory.stringType, factory.throwableType),
                factory.constructorMethodName),
            false),
        new CfThrow());

    CfTryCatch cfTryCatch =
        new CfTryCatch(
            tryCatchStart,
            tryCatchEnd,
            ImmutableList.of(factory.throwableType),
            ImmutableList.of(tryCatchHandler));

    return new CfCode(
        null, 5, 1, builder.build(), ImmutableList.of(cfTryCatch), ImmutableList.of());
  }
}
