From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (qmail 1482 invoked by alias); 19 Oct 2010 20:27:57 -0000 Received: (qmail 1473 invoked by uid 22791); 19 Oct 2010 20:27:55 -0000 X-SWARE-Spam-Status: No, hits=-6.3 required=5.0 tests=AWL,BAYES_00,RCVD_IN_DNSWL_HI,SPF_HELO_PASS,T_RP_MATCHES_RCVD X-Spam-Check-By: sourceware.org Received: from mx1.redhat.com (HELO mx1.redhat.com) (209.132.183.28) by sourceware.org (qpsmtpd/0.43rc1) with ESMTP; Tue, 19 Oct 2010 20:27:50 +0000 Received: from int-mx09.intmail.prod.int.phx2.redhat.com (int-mx09.intmail.prod.int.phx2.redhat.com [10.5.11.22]) by mx1.redhat.com (8.13.8/8.13.8) with ESMTP id o9JKRmf6008407 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK) for ; Tue, 19 Oct 2010 16:27:48 -0400 Received: from ns3.rdu.redhat.com (ns3.rdu.redhat.com [10.11.255.199]) by int-mx09.intmail.prod.int.phx2.redhat.com (8.14.4/8.14.4) with ESMTP id o9JKRmNf023416 for ; Tue, 19 Oct 2010 16:27:48 -0400 Received: from [10.15.16.129] (dhcp-10-15-16-129.yyz.redhat.com [10.15.16.129]) by ns3.rdu.redhat.com (8.13.8/8.13.8) with ESMTP id o9JKRlsO027063 for ; Tue, 19 Oct 2010 16:27:47 -0400 Message-ID: <4CBDFF43.7000403@redhat.com> Date: Tue, 19 Oct 2010 20:27:00 -0000 From: sami wagiaalla User-Agent: Mozilla/5.0 (X11; U; Linux x86_64; en-US; rv:1.9.2.8) Gecko/20100806 Fedora/3.1.2-1.fc13 Lightning/1.0b2pre Thunderbird/3.1.2 MIME-Version: 1.0 To: gdb-patches@sourceware.org Subject: Re: [patch 1/2] Overload resolution among children of a common ancestor References: <4C7BD80C.1050906@redhat.com> In-Reply-To: <4C7BD80C.1050906@redhat.com> Content-Type: multipart/mixed; boundary="------------040006080803010606030604" X-IsSubscribed: yes Mailing-List: contact gdb-patches-help@sourceware.org; run by ezmlm Precedence: bulk List-Id: List-Subscribe: List-Archive: List-Post: List-Help: , Sender: gdb-patches-owner@sourceware.org X-SW-Source: 2010-10/txt/msg00302.txt.bz2 This is a multi-part message in MIME format. --------------040006080803010606030604 Content-Type: text/plain; charset=ISO-8859-1; format=flowed Content-Transfer-Encoding: 7bit Content-length: 128 This patch introduces a rank struct to be used instead of the int that is normally used to represent the rank of a conversion. --------------040006080803010606030604 Content-Type: text/x-patch; name="overload_rank.patch" Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename="overload_rank.patch" Content-length: 11508 Create and use struct rank. 2010-10-18 Sami Wagiaalla * gdbtypes.h: Create struct rank. Convert all 'BADNESS' macros to const struct rank declarations. (sum_ranks): New function. (compare_ranks): New function. * valops.c (find_oload_champ): Updated. (classify_oload_match): Use compare_ranks. Improved comments. (compare_parameters): Use compare_ranks. * gdbtypes.c (sum_ranks): New function. (compare_ranks): New function. (compare_badness): Use compare_ranks. (rank_function): Use global constants instead of literals. (rank_one_type): Ditto. Return struct rank. Use sum_ranks. diff --git a/gdb/gdbtypes.c b/gdb/gdbtypes.c index d08dbfe..6213f3c 100644 --- a/gdb/gdbtypes.c +++ b/gdb/gdbtypes.c @@ -2012,6 +2012,30 @@ is_unique_ancestor (struct type *base, struct value *val) +/* Return the sum of the rank of A with the rank of B. */ +struct rank +sum_ranks (struct rank a, struct rank b) +{ + struct rank c; + c.rank = a.rank + b.rank; + return c; +} + +/* Compare rank A and B and return: + 0 if a = b + 1 if a is better than b + -1 if b is better than a. */ +int +compare_ranks (struct rank a, struct rank b) +{ + if (a.rank == b.rank) + return 0; + + if (a.rank < b.rank) + return 1; + + return -1; +} /* Functions for overload resolution begin here */ @@ -2036,7 +2060,7 @@ compare_badness (struct badness_vector *a, struct badness_vector *b) /* Subtract b from a */ for (i = 0; i < a->length; i++) { - tmp = a->rank[i] - b->rank[i]; + tmp = compare_ranks (b->rank[i], a->rank[i]); if (tmp > 0) found_pos = 1; else if (tmp < 0) @@ -2084,7 +2108,7 @@ rank_function (struct type **parms, int nparms, arguments and ellipsis parameter lists, we should consider those and rank the length-match more finely. */ - LENGTH_MATCH (bv) = (nargs != nparms) ? LENGTH_MISMATCH_BADNESS : 0; + LENGTH_MATCH (bv) = (nargs != nparms) ? LENGTH_MISMATCH_BADNESS : EXACT_MATCH_BADNESS; /* Now rank all the parameters of the candidate function */ for (i = 1; i <= min_len; i++) @@ -2195,12 +2219,12 @@ types_equal (struct type *a, struct type *b) * PARM is to ARG. The higher the return value, the worse the match. * Generally the "bad" conversions are all uniformly assigned a 100. */ -int +struct rank rank_one_type (struct type *parm, struct type *arg) { if (types_equal (parm, arg)) - return 0; + return EXACT_MATCH_BADNESS; /* Resolve typedefs */ if (TYPE_CODE (parm) == TYPE_CODE_TYPEDEF) @@ -2211,11 +2235,11 @@ rank_one_type (struct type *parm, struct type *arg) /* See through references, since we can almost make non-references references. */ if (TYPE_CODE (arg) == TYPE_CODE_REF) - return (rank_one_type (parm, TYPE_TARGET_TYPE (arg)) - + REFERENCE_CONVERSION_BADNESS); + return (sum_ranks (rank_one_type (parm, TYPE_TARGET_TYPE (arg)), + REFERENCE_CONVERSION_BADNESS)); if (TYPE_CODE (parm) == TYPE_CODE_REF) - return (rank_one_type (TYPE_TARGET_TYPE (parm), arg) - + REFERENCE_CONVERSION_BADNESS); + return (sum_ranks (rank_one_type (TYPE_TARGET_TYPE (parm), arg), + REFERENCE_CONVERSION_BADNESS)); if (overload_debug) /* Debugging only. */ fprintf_filtered (gdb_stderr, @@ -2246,7 +2270,7 @@ rank_one_type (struct type *parm, struct type *arg) case TYPE_CODE_ARRAY: if (types_equal (TYPE_TARGET_TYPE (parm), TYPE_TARGET_TYPE (arg))) - return 0; + return EXACT_MATCH_BADNESS; return INCOMPATIBLE_TYPE_BADNESS; case TYPE_CODE_FUNC: return rank_one_type (TYPE_TARGET_TYPE (parm), arg); @@ -2289,7 +2313,7 @@ rank_one_type (struct type *parm, struct type *arg) { /* This case only for character types */ if (TYPE_NOSIGN (arg)) - return 0; /* plain char -> plain char */ + return EXACT_MATCH_BADNESS; /* plain char -> plain char */ else /* signed/unsigned char -> plain char */ return INTEGER_CONVERSION_BADNESS; } @@ -2301,7 +2325,7 @@ rank_one_type (struct type *parm, struct type *arg) unsigned long -> unsigned long */ if (integer_types_same_name_p (TYPE_NAME (parm), TYPE_NAME (arg))) - return 0; + return EXACT_MATCH_BADNESS; else if (integer_types_same_name_p (TYPE_NAME (arg), "int") && integer_types_same_name_p (TYPE_NAME (parm), @@ -2325,7 +2349,7 @@ rank_one_type (struct type *parm, struct type *arg) { if (integer_types_same_name_p (TYPE_NAME (parm), TYPE_NAME (arg))) - return 0; + return EXACT_MATCH_BADNESS; else if (integer_types_same_name_p (TYPE_NAME (arg), "int") && integer_types_same_name_p (TYPE_NAME (parm), @@ -2391,19 +2415,19 @@ rank_one_type (struct type *parm, struct type *arg) if (TYPE_NOSIGN (parm)) { if (TYPE_NOSIGN (arg)) - return 0; + return EXACT_MATCH_BADNESS; else return INTEGER_CONVERSION_BADNESS; } else if (TYPE_UNSIGNED (parm)) { if (TYPE_UNSIGNED (arg)) - return 0; + return EXACT_MATCH_BADNESS; else return INTEGER_PROMOTION_BADNESS; } else if (!TYPE_NOSIGN (arg) && !TYPE_UNSIGNED (arg)) - return 0; + return EXACT_MATCH_BADNESS; else return INTEGER_CONVERSION_BADNESS; default: @@ -2437,7 +2461,7 @@ rank_one_type (struct type *parm, struct type *arg) case TYPE_CODE_PTR: return BOOL_PTR_CONVERSION_BADNESS; case TYPE_CODE_BOOL: - return 0; + return EXACT_MATCH_BADNESS; default: return INCOMPATIBLE_TYPE_BADNESS; } @@ -2449,7 +2473,7 @@ rank_one_type (struct type *parm, struct type *arg) if (TYPE_LENGTH (arg) < TYPE_LENGTH (parm)) return FLOAT_PROMOTION_BADNESS; else if (TYPE_LENGTH (arg) == TYPE_LENGTH (parm)) - return 0; + return EXACT_MATCH_BADNESS; else return FLOAT_CONVERSION_BADNESS; case TYPE_CODE_INT: @@ -2468,7 +2492,7 @@ rank_one_type (struct type *parm, struct type *arg) case TYPE_CODE_FLT: return FLOAT_PROMOTION_BADNESS; case TYPE_CODE_COMPLEX: - return 0; + return EXACT_MATCH_BADNESS; default: return INCOMPATIBLE_TYPE_BADNESS; } diff --git a/gdb/gdbtypes.h b/gdb/gdbtypes.h index 5617a1d..56590b2 100644 --- a/gdb/gdbtypes.h +++ b/gdb/gdbtypes.h @@ -849,11 +849,17 @@ struct vbase struct vbase *next; /* next in chain */ }; +/* Struct used to store conversion rankings. */ +struct rank + { + int rank; + }; + /* Struct used for ranking a function for overload resolution */ struct badness_vector { int length; - int *rank; + struct rank *rank; }; /* GNAT Ada-specific information for various Ada types. */ @@ -1396,45 +1402,52 @@ extern int is_unique_ancestor (struct type *, struct value *); #define LENGTH_MATCH(bv) ((bv)->rank[0]) /* Badness if parameter list length doesn't match arg list length */ -#define LENGTH_MISMATCH_BADNESS 100 +static const struct rank LENGTH_MISMATCH_BADNESS = {100}; + /* Dummy badness value for nonexistent parameter positions */ -#define TOO_FEW_PARAMS_BADNESS 100 +static const struct rank TOO_FEW_PARAMS_BADNESS = {100}; /* Badness if no conversion among types */ -#define INCOMPATIBLE_TYPE_BADNESS 100 +static const struct rank INCOMPATIBLE_TYPE_BADNESS = {100}; + +/* Badness of an exact match. */ +static const struct rank EXACT_MATCH_BADNESS = {0}; /* Badness of integral promotion */ -#define INTEGER_PROMOTION_BADNESS 1 +static const struct rank INTEGER_PROMOTION_BADNESS = {1}; /* Badness of floating promotion */ -#define FLOAT_PROMOTION_BADNESS 1 +static const struct rank FLOAT_PROMOTION_BADNESS = {1}; /* Badness of converting a derived class pointer to a base class pointer. */ -#define BASE_PTR_CONVERSION_BADNESS 1 +static const struct rank BASE_PTR_CONVERSION_BADNESS = {1}; /* Badness of integral conversion */ -#define INTEGER_CONVERSION_BADNESS 2 +static const struct rank INTEGER_CONVERSION_BADNESS = {2}; /* Badness of floating conversion */ -#define FLOAT_CONVERSION_BADNESS 2 +static const struct rank FLOAT_CONVERSION_BADNESS = {2}; /* Badness of integer<->floating conversions */ -#define INT_FLOAT_CONVERSION_BADNESS 2 +static const struct rank INT_FLOAT_CONVERSION_BADNESS = {2}; /* Badness of conversion of pointer to void pointer */ -#define VOID_PTR_CONVERSION_BADNESS 2 +static const struct rank VOID_PTR_CONVERSION_BADNESS = {2}; /* Badness of conversion of pointer to boolean. */ -#define BOOL_PTR_CONVERSION_BADNESS 3 +static const struct rank BOOL_PTR_CONVERSION_BADNESS = {3}; /* Badness of converting derived to base class */ -#define BASE_CONVERSION_BADNESS 2 +static const struct rank BASE_CONVERSION_BADNESS = {2}; /* Badness of converting from non-reference to reference */ -#define REFERENCE_CONVERSION_BADNESS 2 +static const struct rank REFERENCE_CONVERSION_BADNESS = {2}; /* Non-standard conversions allowed by the debugger */ /* Converting a pointer to an int is usually OK */ -#define NS_POINTER_CONVERSION_BADNESS 10 +static const struct rank NS_POINTER_CONVERSION_BADNESS = {10}; + +extern struct rank sum_ranks (struct rank a, struct rank b); +extern int compare_ranks (struct rank a, struct rank b); extern int compare_badness (struct badness_vector *, struct badness_vector *); extern struct badness_vector *rank_function (struct type **, int, struct type **, int); -extern int rank_one_type (struct type *, struct type *); +extern struct rank rank_one_type (struct type *, struct type *); extern void recursive_dump_type (struct type *, int); diff --git a/gdb/valops.c b/gdb/valops.c index fe4576e..eb0bb7d 100644 --- a/gdb/valops.c +++ b/gdb/valops.c @@ -2884,7 +2884,7 @@ find_oload_champ (struct type **arg_types, int nargs, int method, for (jj = 0; jj < nargs - static_offset; jj++) fprintf_filtered (gdb_stderr, "...Badness @ %d : %d\n", - jj, bv->rank[jj]); + jj, bv->rank[jj].rank); fprintf_filtered (gdb_stderr, "Overload resolution champion is %d, ambiguous? %d\n", oload_champ, oload_ambiguous); @@ -2918,9 +2918,15 @@ classify_oload_match (struct badness_vector *oload_champ_bv, for (ix = 1; ix <= nargs - static_offset; ix++) { - if (oload_champ_bv->rank[ix] >= 100) + /* If this conversion is as bad as INCOMPATIBLE_TYPE_BADNESS + or worse return INCOMPATIBLE. */ + if (compare_ranks (oload_champ_bv->rank[ix], + INCOMPATIBLE_TYPE_BADNESS) <= 0) return INCOMPATIBLE; /* Truly mismatched types. */ - else if (oload_champ_bv->rank[ix] >= 10) + /* Otherwise If this conversion is as bad as + NS_POINTER_CONVERSION_BADNESS or worse return NON_STANDARD. */ + else if (compare_ranks (oload_champ_bv->rank[ix], + NS_POINTER_CONVERSION_BADNESS) <= 0) return NON_STANDARD; /* Non-standard type conversions needed. */ } @@ -3056,9 +3062,9 @@ compare_parameters (struct type *t1, struct type *t2, int skip_artificial) for (i = 0; i < TYPE_NFIELDS (t2); ++i) { - if (rank_one_type (TYPE_FIELD_TYPE (t1, start + i), - TYPE_FIELD_TYPE (t2, i)) - != 0) + if (compare_ranks (rank_one_type (TYPE_FIELD_TYPE (t1, start + i), + TYPE_FIELD_TYPE (t2, i)), + EXACT_MATCH_BADNESS) != 0) return 0; } --------------040006080803010606030604--