Add prototype reference support into Dx backend

- The future invoke-polymorphic opcodes will need to have a
reference to a method and to a prototype. Reference to a method
already exists into the backend but reference to a prototype
does not exists, thus add this concept.

Bug: 31543917
Change-Id: Ibb1bbca124470719859cd9da8a89e776e8570725
diff --git a/dx/src/com/android/jack/dx/dex/file/DexFile.java b/dx/src/com/android/jack/dx/dex/file/DexFile.java
index 5bc9cb6..916d5c8 100644
--- a/dx/src/com/android/jack/dx/dex/file/DexFile.java
+++ b/dx/src/com/android/jack/dx/dex/file/DexFile.java
@@ -23,6 +23,7 @@
 import com.android.jack.dx.rop.cst.CstEnumRef;
 import com.android.jack.dx.rop.cst.CstFieldRef;
 import com.android.jack.dx.rop.cst.CstMethodRef;
+import com.android.jack.dx.rop.cst.CstPrototypeRef;
 import com.android.jack.dx.rop.cst.CstString;
 import com.android.jack.dx.rop.cst.CstType;
 import com.android.jack.dx.util.ByteArrayAnnotatedOutput;
@@ -442,6 +443,8 @@
       fieldIds.intern((CstFieldRef) cst);
     } else if (cst instanceof CstEnumRef) {
       fieldIds.intern(((CstEnumRef) cst).getFieldRef());
+    } else if (cst instanceof CstPrototypeRef) {
+      protoIds.intern(((CstPrototypeRef) cst).getPrototype());
     } else if (cst == null) {
       throw new NullPointerException("cst == null");
     }
@@ -467,6 +470,8 @@
       return methodIds.get(cst);
     } else if (cst instanceof CstFieldRef) {
       return fieldIds.get(cst);
+    } else if (cst instanceof CstPrototypeRef) {
+      return protoIds.get(cst);
     } else {
       return null;
     }
diff --git a/dx/src/com/android/jack/dx/dex/file/ProtoIdsSection.java b/dx/src/com/android/jack/dx/dex/file/ProtoIdsSection.java
index 33cb976..4740173 100644
--- a/dx/src/com/android/jack/dx/dex/file/ProtoIdsSection.java
+++ b/dx/src/com/android/jack/dx/dex/file/ProtoIdsSection.java
@@ -17,6 +17,7 @@
 package com.android.jack.dx.dex.file;
 
 import com.android.jack.dx.rop.cst.Constant;
+import com.android.jack.dx.rop.cst.CstPrototypeRef;
 import com.android.jack.dx.rop.type.Prototype;
 import com.android.jack.dx.util.AnnotatedOutput;
 import com.android.jack.dx.util.Hex;
@@ -24,6 +25,8 @@
 import java.util.Collection;
 import java.util.TreeMap;
 
+import javax.annotation.Nonnull;
+
 /**
  * Proto (method prototype) identifiers list section of a
  * {@code .dex} file.
@@ -53,8 +56,14 @@
 
   /** {@inheritDoc} */
   @Override
-  public IndexedItem get(Constant cst) {
-    throw new UnsupportedOperationException("unsupported");
+  @Nonnull
+  public IndexedItem get(@Nonnull Constant cst) {
+    throwIfNotPrepared();
+
+    IndexedItem result = protoIds.get(((CstPrototypeRef) cst).getPrototype());
+    assert result != null;
+
+    return result;
   }
 
   /**
diff --git a/dx/src/com/android/jack/dx/io/IndexType.java b/dx/src/com/android/jack/dx/io/IndexType.java
index 515af59..7129597 100644
--- a/dx/src/com/android/jack/dx/io/IndexType.java
+++ b/dx/src/com/android/jack/dx/io/IndexType.java
@@ -41,6 +41,9 @@
   /** field reference index */
   FIELD_REF,
 
+  /** prototype reference index */
+  PROTOTYPE_REF,
+
   /** inline method index (for inline linked method invocations) */
   INLINE_METHOD,
 
diff --git a/dx/src/com/android/jack/dx/rop/cst/CstPrototypeRef.java b/dx/src/com/android/jack/dx/rop/cst/CstPrototypeRef.java
new file mode 100644
index 0000000..c954aac
--- /dev/null
+++ b/dx/src/com/android/jack/dx/rop/cst/CstPrototypeRef.java
@@ -0,0 +1,108 @@
+/*
+ * 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.
+ */
+
+package com.android.jack.dx.rop.cst;
+
+import com.android.jack.dx.rop.type.Prototype;
+import com.android.jack.dx.rop.type.Type;
+
+import javax.annotation.Nonnull;
+
+/**
+ * Constants of type reference to a {@Link Prototype}.
+ */
+public final class CstPrototypeRef extends TypedConstant {
+
+  /** {@code non-null;} the reference prototype */
+  @Nonnull
+  private final Prototype prototype;
+
+  /**
+   * Constructs an instance from a {@link CstPrototypeRef}.
+   *
+   * @param prototype {@code non-null;} the referenced prototype
+   */
+  public CstPrototypeRef(@Nonnull Prototype prototype) {
+    assert prototype != null;
+    this.prototype = prototype;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public final boolean equals(@Nonnull Object other) {
+    if (!(other instanceof CstPrototypeRef)) {
+      return false;
+    }
+
+    return prototype.equals(((CstPrototypeRef) other).prototype);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public final int hashCode() {
+    return prototype.hashCode();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  protected int compareTo0(@Nonnull Constant other) {
+    return prototype.compareTo(((CstPrototypeRef) other).prototype);
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  @Nonnull
+  public String toString() {
+    return typeName() + '{' + toHuman() + '}';
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  @Nonnull
+  public String typeName() {
+    return "prototype";
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  public boolean isCategory2() {
+    return false;
+  }
+
+  /**
+   * Gets the referenced prototype. This doesn't include a {@code this} argument.
+   *
+   * @return {@code non-null;} the referenced prototype
+   */
+  @Nonnull
+  public final Prototype getPrototype() {
+    return prototype;
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  @Nonnull
+  public Type getType() {
+    return prototype.getReturnType();
+  }
+
+  /** {@inheritDoc} */
+  @Override
+  @Nonnull
+  public String toHuman() {
+    return prototype.toString();
+  }
+}