summaryrefslogtreecommitdiffstats
path: root/runtime/class_linker.cc
diff options
context:
space:
mode:
authorAlex Light <allight@google.com>2016-05-02 18:51:34 -0700
committerAlex Light <allight@google.com>2016-05-03 13:09:28 -0700
commitb554343e1d72104f0b26e749c1877d0566667a85 (patch)
tree7ac8e8c4bcb027550f1cf93449447253dcadda20 /runtime/class_linker.cc
parenta421e9e758ebb29d3ca7d2b8911e8dfa9a3ded22 (diff)
downloadandroid_art-b554343e1d72104f0b26e749c1877d0566667a85.tar.gz
android_art-b554343e1d72104f0b26e749c1877d0566667a85.tar.bz2
android_art-b554343e1d72104f0b26e749c1877d0566667a85.zip
Fix vtable corruption.
Due to failing to keep track of superclass implementations of interface methods we could end up in situations where methods were placed onto a class's vtable multiple times. This could cause virtual and interface dispatches on subclasses to fail by causing corruption of the subclass's vtable and iftable. Bug: 28333278 (cherry picked from commit d6c2bfaff8850a9a02ee9b75cf8c96eadd8d5c69) Change-Id: I37d9740ca912daf37cdf9ff82697bbc5db46177a
Diffstat (limited to 'runtime/class_linker.cc')
-rw-r--r--runtime/class_linker.cc9
1 files changed, 9 insertions, 0 deletions
diff --git a/runtime/class_linker.cc b/runtime/class_linker.cc
index c92304f647..e7a560b398 100644
--- a/runtime/class_linker.cc
+++ b/runtime/class_linker.cc
@@ -6635,6 +6635,15 @@ bool ClassLinker::LinkInterfaceMethods(
// The method is not overridable by a default method (i.e. it is directly implemented
// in some class). Therefore move onto the next interface method.
continue;
+ } else {
+ // If the super-classes method is override-able by a default method we need to keep
+ // track of it since though it is override-able it is not guaranteed to be 'overridden'.
+ // If it turns out not to be overridden and we did not keep track of it we might add it
+ // to the vtable twice, causing corruption in this class and possibly any subclasses.
+ DCHECK(vtable_impl == nullptr || vtable_impl == supers_method)
+ << "vtable_impl was " << PrettyMethod(vtable_impl) << " and not 'nullptr' or "
+ << PrettyMethod(supers_method) << " as expected. IFTable appears to be corrupt!";
+ vtable_impl = supers_method;
}
}
// If we haven't found it yet we should search through the interfaces for default methods.