===================================================================
@@ -12005,10 +12005,15 @@ get_binfo_at_offset (tree binfo, HOST_WI
break;
}
else
- if (BINFO_OFFSET (base_binfo) - BINFO_OFFSET (binfo) < pos
+ if ((tree_to_shwi (BINFO_OFFSET (base_binfo))
+ - tree_to_shwi (BINFO_OFFSET (binfo)))
+ * BITS_PER_UNIT < pos
+ /* Rule out types with no virtual methods or we can get confused
+ here by zero sized bases. */
+ && BINFO_VTABLE (TYPE_BINFO (BINFO_TYPE (base_binfo)))
&& (!containing_binfo
- || (BINFO_OFFSET (containing_binfo)
- < BINFO_OFFSET (base_binfo))))
+ || (tree_to_shwi (BINFO_OFFSET (containing_binfo))
+ < tree_to_shwi (BINFO_OFFSET (base_binfo)))))
containing_binfo = base_binfo;
if (found_binfo)
{
===================================================================
@@ -0,0 +1,30 @@
+/* { dg-do compile } */
+class A;
+class B {};
+struct C {
+ virtual void dispatch();
+ int traversal_map_;
+};
+template <typename> class F : public virtual C {};
+
+struct I : F<A>, F<int> {};
+struct J : B, I {};
+class D {};
+struct L {
+ L(D &, int &p2) : map_(p2) {}
+ virtual void traverse(int &p1) {
+ int &s = p1;
+ names<L>(s, names_);
+ }
+ int &map_;
+ J names_;
+ template <typename> void names(int &, C &p2) { p2.dispatch(); }
+};
+
+struct G : D {
+ G(D &, int &p2) : map_(p2) { L(*this, map_); }
+ int &map_;
+};
+
+int a;
+void fn1(D &p1) { G(p1, a); }