OSDN Git Service

cp:
authornathan <nathan@138bc75d-0d04-0410-961f-82ee72b054a4>
Mon, 17 Oct 2005 17:25:17 +0000 (17:25 +0000)
committernathan <nathan@138bc75d-0d04-0410-961f-82ee72b054a4>
Mon, 17 Oct 2005 17:25:17 +0000 (17:25 +0000)
PR c++/24386
* cp-tree.h (BASELINK_QUALIFIED_P): New.
* pt.c (tsubst_copy_and_build): <CALL_EXPR case>: Use it.
* typeck.c (finish_class_member_access_expr): Set it.
testsuite:
PR c++/24386
* g++.dg/template/overload7.C: New.

git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@105507 138bc75d-0d04-0410-961f-82ee72b054a4

gcc/cp/ChangeLog
gcc/cp/cp-tree.h
gcc/cp/pt.c
gcc/cp/typeck.c
gcc/testsuite/ChangeLog
gcc/testsuite/g++.dg/template/overload7.C [new file with mode: 0644]

index a725969..08344ee 100644 (file)
@@ -1,5 +1,10 @@
 2005-10-17  Nathan Sidwell  <nathan@codesourcery.com>
 
 2005-10-17  Nathan Sidwell  <nathan@codesourcery.com>
 
+       PR c++/24386
+       * cp-tree.h (BASELINK_QUALIFIED_P): New.
+       * pt.c (tsubst_copy_and_build): <CALL_EXPR case>: Use it.
+       * typeck.c (finish_class_member_access_expr): Set it.
+
        PR c++/21353
        * decl.c (check_default_argument): Don't check
        processing_template_decl or uses_template_parms here.
        PR c++/21353
        * decl.c (check_default_argument): Don't check
        processing_template_decl or uses_template_parms here.
index 9a2becc..b63d08e 100644 (file)
@@ -52,6 +52,7 @@ struct diagnostic_context;
       TYPENAME_IS_ENUM_P (in TYPENAME_TYPE)
       REFERENCE_REF_P (in INDIRECT_EXPR)
       QUALIFIED_NAME_IS_TEMPLATE (in SCOPE_REF)
       TYPENAME_IS_ENUM_P (in TYPENAME_TYPE)
       REFERENCE_REF_P (in INDIRECT_EXPR)
       QUALIFIED_NAME_IS_TEMPLATE (in SCOPE_REF)
+      BASELINK_QUALIFIED_P (in BASELINK)
    1: IDENTIFIER_VIRTUAL_P (in IDENTIFIER_NODE)
       TI_PENDING_TEMPLATE_FLAG.
       TEMPLATE_PARMS_FOR_INLINE.
    1: IDENTIFIER_VIRTUAL_P (in IDENTIFIER_NODE)
       TI_PENDING_TEMPLATE_FLAG.
       TEMPLATE_PARMS_FOR_INLINE.
@@ -341,6 +342,9 @@ struct tree_overload GTY(())
    requested.  */
 #define BASELINK_OPTYPE(NODE) \
   (TREE_CHAIN (BASELINK_CHECK (NODE)))
    requested.  */
 #define BASELINK_OPTYPE(NODE) \
   (TREE_CHAIN (BASELINK_CHECK (NODE)))
+/* Non-zero if this baselink was from a qualified lookup.  */
+#define BASELINK_QUALIFIED_P(NODE) \
+  TREE_LANG_FLAG_0 (BASELINK_CHECK (NODE))
 
 struct tree_baselink GTY(())
 {
 
 struct tree_baselink GTY(())
 {
index 3de54a4..d25130a 100644 (file)
@@ -8720,9 +8720,17 @@ tsubst_copy_and_build (tree t,
          }
        else
          {
          }
        else
          {
-           qualified_p = (TREE_CODE (function) == COMPONENT_REF
-                          && (TREE_CODE (TREE_OPERAND (function, 1))
-                              == SCOPE_REF));
+           if (TREE_CODE (function) == COMPONENT_REF)
+             {
+               tree op = TREE_OPERAND (function, 1);
+
+               qualified_p = (TREE_CODE (op) == SCOPE_REF
+                              || (BASELINK_P (op)
+                                  && BASELINK_QUALIFIED_P (op)));
+             }
+           else
+             qualified_p = false;
+           
            function = tsubst_copy_and_build (function, args, complain,
                                              in_decl,
                                              !qualified_p);
            function = tsubst_copy_and_build (function, args, complain,
                                              in_decl,
                                              !qualified_p);
index e3c431d..a7edfc1 100644 (file)
@@ -2055,10 +2055,18 @@ finish_class_member_access_expr (tree object, tree name, bool template_p)
   expr = build_class_member_access_expr (object, member, access_path,
                                         /*preserve_reference=*/false);
   if (processing_template_decl && expr != error_mark_node)
   expr = build_class_member_access_expr (object, member, access_path,
                                         /*preserve_reference=*/false);
   if (processing_template_decl && expr != error_mark_node)
-    return build_min_non_dep (COMPONENT_REF, expr,
-                             orig_object,
-                             BASELINK_P (member) ? member : orig_name,
-                             NULL_TREE);
+    {
+      if (BASELINK_P (member))
+       {
+         if (TREE_CODE (orig_name) == SCOPE_REF)
+           BASELINK_QUALIFIED_P (member) = 1;
+         orig_name = member;
+       }
+      return build_min_non_dep (COMPONENT_REF, expr,
+                               orig_object, orig_name,
+                               NULL_TREE);
+    }
+  
   return expr;
 }
 
   return expr;
 }
 
index e17dc16..319812a 100644 (file)
@@ -1,5 +1,8 @@
 2005-10-17  Nathan Sidwell  <nathan@codesourcery.com>
 
 2005-10-17  Nathan Sidwell  <nathan@codesourcery.com>
 
+       PR c++/24386
+       * g++.dg/template/overload7.C: New.
+
        PR c++/22551
        * g++.dg/other/switch2.C: Remove expected warnings.
 
        PR c++/22551
        * g++.dg/other/switch2.C: Remove expected warnings.
 
diff --git a/gcc/testsuite/g++.dg/template/overload7.C b/gcc/testsuite/g++.dg/template/overload7.C
new file mode 100644 (file)
index 0000000..28bd16c
--- /dev/null
@@ -0,0 +1,31 @@
+// { dg-do run }
+
+// Copyright (C) 2005 Free Software Foundation, Inc.
+// Contributed by Nathan Sidwell 17 Oct 2005 <nathan@codesourcery.com>
+
+// PR 24386:Wrong virtual function called
+// Origin:  Scott Snyder snyder@fnal.gov
+
+struct A
+{
+  virtual int Foo () { return 1; }
+};
+struct B : public A
+{
+  virtual int Foo () { return 2; }
+};
+
+template <class T>
+int Bar (T *a)
+{
+  if (static_cast<A*>(a)->A::Foo () != 1)
+    return 1;
+  if (static_cast<A*>(a)->Foo () != 2)
+    return 2;
+  return 0;
+}
+
+int main ()
+{
+  return Bar (new B);
+}