Support directly invoking interface default methods

With the Java 8 Language one is allowed to directly call default
interface methods of interfaces one (directly) implements through the
use of the super keyword. We support this behavior through the
invoke-super opcode with the target being an interface.

We add 3 tests for this behavior.

Currently only supports slow-path interpreter.

Invoke-super is currently extremely slow.

Bug: 24618811

Change-Id: I7e06e17326f7dbae0116bd7dfefca151f0092bd2
diff --git a/runtime/common_throws.cc b/runtime/common_throws.cc
index d68b463..46d67bd 100644
--- a/runtime/common_throws.cc
+++ b/runtime/common_throws.cc
@@ -84,6 +84,14 @@
                               PrettyMethod(method).c_str()).c_str());
 }
 
+void ThrowAbstractMethodError(uint32_t method_idx, const DexFile& dex_file) {
+  ThrowException("Ljava/lang/AbstractMethodError;", /* referrer */ nullptr,
+                 StringPrintf("abstract method \"%s\"",
+                              PrettyMethod(method_idx,
+                                           dex_file,
+                                           /* with_signature */ true).c_str()).c_str());
+}
+
 // ArithmeticException
 
 void ThrowArithmeticExceptionDivideByZero() {
@@ -209,6 +217,22 @@
                  msg.str().c_str());
 }
 
+void ThrowIncompatibleClassChangeErrorClassForInterfaceSuper(ArtMethod* method,
+                                                             mirror::Class* target_class,
+                                                             mirror::Object* this_object,
+                                                             ArtMethod* referrer) {
+  // Referrer is calling interface_method on this_object, however, the interface_method isn't
+  // implemented by this_object.
+  CHECK(this_object != nullptr);
+  std::ostringstream msg;
+  msg << "Class '" << PrettyDescriptor(this_object->GetClass())
+      << "' does not implement interface '" << PrettyDescriptor(target_class) << "' in call to '"
+      << PrettyMethod(method) << "'";
+  ThrowException("Ljava/lang/IncompatibleClassChangeError;",
+                 referrer != nullptr ? referrer->GetDeclaringClass() : nullptr,
+                 msg.str().c_str());
+}
+
 void ThrowIncompatibleClassChangeErrorClassForInterfaceDispatch(ArtMethod* interface_method,
                                                                 mirror::Object* this_object,
                                                                 ArtMethod* referrer) {