aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorJason Merrill <jason@yorick.cygnus.com>1999-03-25 03:06:16 +0000
committerJason Merrill <jason@gcc.gnu.org>1999-03-24 22:06:16 -0500
commit5b163de4083bc0d51829489c9a08c7357a5de20c (patch)
tree08a5b1f87d7c24ecab479d4bc480cfa1d0eedfee /gcc
parent63681b5ff9a024c5fd85b4cc853e4c1238f97f12 (diff)
downloadgcc-5b163de4083bc0d51829489c9a08c7357a5de20c.zip
gcc-5b163de4083bc0d51829489c9a08c7357a5de20c.tar.gz
gcc-5b163de4083bc0d51829489c9a08c7357a5de20c.tar.bz2
typeck.c (common_type): Handle cv-qual unification for pointers to members.
* typeck.c (common_type): Handle cv-qual unification for pointers to members. * decl.c (unqualified_namespace_lookup): Return error_mark_node on error. (lookup_name_real): Set LOOKUP_COMPLAIN when *not* parsing. * lex.c (do_identifier): If we got error_mark_node, call lookup_name again. From-SVN: r25967
Diffstat (limited to 'gcc')
-rw-r--r--gcc/cp/ChangeLog11
-rw-r--r--gcc/cp/decl.c12
-rw-r--r--gcc/cp/lex.c25
-rw-r--r--gcc/cp/typeck.c52
4 files changed, 67 insertions, 33 deletions
diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog
index 820923d..1a5033f 100644
--- a/gcc/cp/ChangeLog
+++ b/gcc/cp/ChangeLog
@@ -1,3 +1,14 @@
+1999-03-25 Jason Merrill <jason@yorick.cygnus.com>
+
+ * typeck.c (common_type): Handle cv-qual unification for pointers
+ to members.
+
+ * decl.c (unqualified_namespace_lookup): Return error_mark_node
+ on error.
+ (lookup_name_real): Set LOOKUP_COMPLAIN when *not* parsing.
+ * lex.c (do_identifier): If we got error_mark_node, call
+ lookup_name again.
+
1999-03-24 Martin von Löwis <loewis@informatik.hu-berlin.de>
* class.c (finish_struct_1): Always reset TYPE_FIELDS for empty
diff --git a/gcc/cp/decl.c b/gcc/cp/decl.c
index 6779045..f5e2902 100644
--- a/gcc/cp/decl.c
+++ b/gcc/cp/decl.c
@@ -5291,7 +5291,7 @@ unqualified_namespace_lookup (name, flags)
if (!lookup_using_namespace (name, b, level->using_directives,
scope, flags))
/* Give up because of error. */
- return NULL_TREE;
+ return error_mark_node;
/* Add all _DECLs seen through global using-directives. */
/* XXX local and global using lists should work equally. */
@@ -5301,7 +5301,7 @@ unqualified_namespace_lookup (name, flags)
if (!lookup_using_namespace (name, b, DECL_NAMESPACE_USING (siter),
scope, flags))
/* Give up because of error. */
- return NULL_TREE;
+ return error_mark_node;
if (siter == scope) break;
siter = CP_DECL_CONTEXT (siter);
}
@@ -5388,8 +5388,6 @@ lookup_name_real (name, prefer_type, nonclass, namespaces_only)
prefer_type = looking_for_typename;
flags = lookup_flags (prefer_type, namespaces_only);
- /* During parsing, we need to complain. */
- flags |= LOOKUP_COMPLAIN;
/* If the next thing is '<', class templates are types. */
if (looking_for_template)
flags |= LOOKUP_TEMPLATES_EXPECTED;
@@ -5463,7 +5461,11 @@ lookup_name_real (name, prefer_type, nonclass, namespaces_only)
from_obj = val;
}
else
- flags = lookup_flags (prefer_type, namespaces_only);
+ {
+ flags = lookup_flags (prefer_type, namespaces_only);
+ /* If we're not parsing, we need to complain. */
+ flags |= LOOKUP_COMPLAIN;
+ }
/* First, look in non-namespace scopes. */
for (val = IDENTIFIER_BINDING (name); val; val = TREE_CHAIN (val))
diff --git a/gcc/cp/lex.c b/gcc/cp/lex.c
index 1ed8f0a..9e3cbc1 100644
--- a/gcc/cp/lex.c
+++ b/gcc/cp/lex.c
@@ -2935,7 +2935,7 @@ do_identifier (token, parsing, args)
expressions instead). */
if (args && !current_template_parms && (!id || is_global (id)))
/* If we have arguments and we only found global names, do Koenig
- lookup. */
+ lookup. */
id = lookup_arg_dependent (token, id, args);
/* Remember that this name has been used in the class definition, as per
@@ -2949,18 +2949,19 @@ do_identifier (token, parsing, args)
after the class is complete. (jason 3/12/97) */
&& TREE_CODE (id) != OVERLOAD)
pushdecl_class_level (id);
-
- if (!id || id == error_mark_node)
- {
- if (id == error_mark_node && current_class_type != NULL_TREE)
- {
- id = lookup_nested_field (token, 1);
- /* In lookup_nested_field(), we marked this so we can gracefully
- leave this whole mess. */
- if (id && id != error_mark_node && TREE_TYPE (id) == error_mark_node)
- return id;
- }
+ if (id == error_mark_node)
+ {
+ /* lookup_name quietly returns error_mark_node if we're parsing,
+ as we don't want to complain about an identifier that ends up
+ being used as a declarator. So we call it again to get the error
+ message. */
+ id = lookup_name (token, 0);
+ return error_mark_node;
+ }
+
+ if (!id)
+ {
if (current_template_parms)
return build_min_nt (LOOKUP_EXPR, token);
else if (IDENTIFIER_OPNAME_P (token))
diff --git a/gcc/cp/typeck.c b/gcc/cp/typeck.c
index c1aa214..701738c 100644
--- a/gcc/cp/typeck.c
+++ b/gcc/cp/typeck.c
@@ -562,14 +562,33 @@ common_type (t1, t2)
But ANSI C++ specifies doing this with the qualifiers.
So I turned it on again. */
{
- tree tt1 = TYPE_MAIN_VARIANT (TREE_TYPE (t1));
- tree tt2 = TYPE_MAIN_VARIANT (TREE_TYPE (t2));
- int type_quals = (CP_TYPE_QUALS (TREE_TYPE (t1))
- | CP_TYPE_QUALS (TREE_TYPE (t2)));
+ tree tt1 = TREE_TYPE (t1);
+ tree tt2 = TREE_TYPE (t2);
+ tree b1, b2;
+ int type_quals;
tree target;
+ if (TREE_CODE (tt1) == OFFSET_TYPE)
+ {
+ b1 = TYPE_OFFSET_BASETYPE (tt1);
+ b2 = TYPE_OFFSET_BASETYPE (tt2);
+ tt1 = TREE_TYPE (tt1);
+ tt2 = TREE_TYPE (tt2);
+ }
+ else
+ b1 = b2 = NULL_TREE;
+
+ type_quals = (CP_TYPE_QUALS (tt1) | CP_TYPE_QUALS (tt2));
+ tt1 = TYPE_MAIN_VARIANT (tt1);
+ tt2 = TYPE_MAIN_VARIANT (tt2);
+
if (tt1 == tt2)
target = tt1;
+ else if (b1)
+ {
+ compiler_error ("common_type called with uncommon member types");
+ target = tt1;
+ }
else if (tt1 == void_type_node || tt2 == void_type_node)
target = void_type_node;
else if (tt1 == unknown_type_node)
@@ -580,6 +599,16 @@ common_type (t1, t2)
target = common_type (tt1, tt2);
target = cp_build_qualified_type (target, type_quals);
+
+ if (b1)
+ {
+ if (same_type_p (b1, b2)
+ || (DERIVED_FROM_P (b1, b2) && binfo_or_else (b1, b2)))
+ target = build_offset_type (b2, target);
+ else if (binfo_or_else (b2, b1))
+ target = build_offset_type (b1, target);
+ }
+
if (code1 == POINTER_TYPE)
t1 = build_pointer_type (target);
else
@@ -699,18 +728,9 @@ common_type (t1, t2)
return build_type_attribute_variant (t1, attributes);
case OFFSET_TYPE:
- if (TREE_TYPE (t1) == TREE_TYPE (t2))
- {
- tree b1 = TYPE_OFFSET_BASETYPE (t1);
- tree b2 = TYPE_OFFSET_BASETYPE (t2);
-
- if (same_type_p (b1, b2)
- || (DERIVED_FROM_P (b1, b2) && binfo_or_else (b1, b2)))
- return build_type_attribute_variant (t2, attributes);
- else if (binfo_or_else (b2, b1))
- return build_type_attribute_variant (t1, attributes);
- }
- compiler_error ("common_type called with uncommon member types");
+ /* Pointers to members should now be handled by the POINTER_TYPE
+ case above. */
+ my_friendly_abort (990325);
default:
return build_type_attribute_variant (t1, attributes);