From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (qmail 11053 invoked by alias); 11 Mar 2007 21:07:24 -0000 Received: (qmail 11036 invoked by uid 22791); 11 Mar 2007 21:07:22 -0000 X-Spam-Check-By: sourceware.org Received: from elrond.portugalmail.pt (HELO elrond.portugalmail.pt) (195.245.179.181) by sourceware.org (qpsmtpd/0.31) with ESMTP; Sun, 11 Mar 2007 21:07:16 +0000 Received: from localhost (localhost [127.0.0.1]) by elrond.portugalmail.pt (Postfix) with ESMTP id C44B73B5FC for ; Sun, 11 Mar 2007 21:03:53 +0000 (WET) Received: from elrond.portugalmail.pt ([127.0.0.1]) by localhost (elrond.portugalmail.pt [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id UEN83pZmRTAI for ; Sun, 11 Mar 2007 21:03:50 +0000 (WET) Received: from [127.0.0.1] (88.210.120.216.rev.optimus.pt [88.210.120.216]) (Authenticated sender: pedro_alves@portugalmail.pt) by elrond.portugalmail.pt (Postfix) with ESMTP id 604673C0F1 for ; Sun, 11 Mar 2007 21:03:41 +0000 (WET) Message-ID: <45F46F5A.5020906@portugalmail.pt> Date: Sun, 11 Mar 2007 21:07:00 -0000 From: Pedro Alves User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.1; pt-BR; rv:1.8.0.10) Gecko/20070221 Thunderbird/1.5.0.10 Mnenhy/0.7.4.0 MIME-Version: 1.0 To: gdb-patches@sourceware.org Subject: Re: Breaking in a c++ method with current language set to c. References: <45EB906B.6070408@portugalmail.pt> <20070305124143.GA14835@caradoc.them.org> In-Reply-To: <20070305124143.GA14835@caradoc.them.org> Content-Type: multipart/mixed; boundary="------------050809090404000206080800" X-Antivirus: avast! (VPS 000723-0, 11-03-2007), Outbound message X-Antivirus-Status: Clean 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: 2007-03/txt/msg00118.txt.bz2 This is a multi-part message in MIME format. --------------050809090404000206080800 Content-Type: text/plain; charset=ISO-8859-1; format=flowed Content-Transfer-Encoding: 7bit Content-length: 1934 Daniel Jacobowitz wrote: > On Mon, Mar 05, 2007 at 03:37:15AM +0000, Pedro Alves wrote: > >> I've looked at several ways to fix it, and all but this one turned out more >> invasive than I hoped for, because current_language is used in a several >> places >> (in symtab.c). Instead, I simply wrapped linespec.c:find_method with a >> set_language (lang of A), guarded with a cleanup. >> > > How much invasive? I don't like the global "current language"; like > the global "selected frame", it's prone to this sort of problem when > we'd really rather be looking at a different language. As my first approach I had added a new parameter to lookup_symbol, and changed all the calls throughout to pass the language that seemed to make sense or current_language otherwise. I ended up touching many files I wouldn't be able to test, like fortran, scheme, java and ada support. It was more invasive than I could afford :) (,and probably wrong). As an intermediate step, I came up with this version. It adds a new lookup_symbol_in_language, and tweaks a few worker functions to accept the language by parameter, instead of relying on the current language. lookup_symbol is then a simple wrapper that passes the current_language to the new lookup_symbol_in_language. I needed to tweak ada-lang.c, because the lookup_symbol_in_language name was already taken there. The approach implemented there was similar to my previous patch, that is, it temporarily switched the current language [1]. As I don't have an ada compiler (and I can't fit any on my machine), I can't be be sure I caught all the hard coded current_language uses, so I've just make the ada function static and added a FIXME. Maybe someone will be able to try with the new version in symtab.c. What do you think of this approach? Tested on i686-pc-cygwin, no regressions. Cheers, Pedro Alves [1] http://sourceware.org/ml/gdb-patches/2004-06/msg00152.html --------------050809090404000206080800 Content-Type: text/plain; name="cpp_break_in_c.diff" Content-Transfer-Encoding: 7bit Content-Disposition: inline; filename="cpp_break_in_c.diff" Content-length: 14984 gdb/ * linespec.c: Include language.h. (find_methods): Add language parameter. Call lookup_symbol_in_language. Pass language down. (add_matching_methods): Likewise. Call lookup_symbol_in_language. (add_constructors): Likewise. (find_method): Pass sym_class to collect_methods. (collect_methods): Add sym_class parameter. Pass language down. * symtab.c (lookup_symbol): Rename to ... (lookup_symbol_in_language): ... this. Add language parameter. Use passed language instead of current_language. (lookup_symbol): New as wrapper around lookup_symbol_in_language. (lookup_symbol_aux): Add language parameter. Use passed language instead of current_language. (search_symbols): Indent. * symtab.h (enum language): Forward declare. (lookup_symbol_in_language): Declare. (lookup_symbol): Update description. * ada-lang.h (lookup_symbol_in_language): Remove declaration. * ada-lang.c (lookup_symbol_in_language): Rename to ... (ada_lookup_symbol_in_language): ... this, and make static. (standard_lookup): Call ada_lookup_symbol_in_language. --- gdb/ada-lang.c | 19 ++++++++++++++----- gdb/ada-lang.h | 11 ----------- gdb/linespec.c | 36 ++++++++++++++++++++---------------- gdb/symtab.c | 52 ++++++++++++++++++++++++++++++++++++---------------- gdb/symtab.h | 10 +++++++++- 5 files changed, 79 insertions(+), 49 deletions(-) Index: src/gdb/ada-lang.c =================================================================== --- src.orig/gdb/ada-lang.c 2007-03-09 01:12:02.000000000 +0000 +++ src/gdb/ada-lang.c 2007-03-11 20:42:46.000000000 +0000 @@ -271,6 +271,13 @@ static struct value *ada_evaluate_subexp static void ada_forward_operator_length (struct expression *, int, int *, int *); + +static struct symbol *ada_lookup_symbol_in_language (const char *, + const struct block *, + domain_enum, + enum language, + int *, + struct symtab **); @@ -3828,7 +3835,8 @@ standard_lookup (const char *name, const if (lookup_cached_symbol (name, domain, &sym, NULL, NULL)) return sym; sym = - lookup_symbol_in_language (name, block, domain, language_c, 0, &symtab); + ada_lookup_symbol_in_language (name, block, domain, language_c, + 0, &symtab); cache_symbol (name, domain, sym, block_found, symtab); return sym; } @@ -4221,11 +4229,12 @@ restore_language (void *lang) set_language ((enum language) lang); } -/* As for lookup_symbol, but performed as if the current language - were LANG. */ +/* Look up a symbol by name using the search conventions of + a specific language (optional block, optional symtab). + FIXME: Should use lookup_symbol_in_language from symtab.c instead. */ -struct symbol * -lookup_symbol_in_language (const char *name, const struct block *block, +static struct symbol * +ada_lookup_symbol_in_language (const char *name, const struct block *block, domain_enum domain, enum language lang, int *is_a_field_of_this, struct symtab **symtab) { Index: src/gdb/linespec.c =================================================================== --- src.orig/gdb/linespec.c 2007-03-09 01:12:02.000000000 +0000 +++ src/gdb/linespec.c 2007-03-09 01:44:12.000000000 +0000 @@ -37,6 +37,7 @@ #include "objc-lang.h" #include "linespec.h" #include "exceptions.h" +#include "language.h" /* We share this one with symtab.c, but it is not exported widely. */ @@ -74,7 +75,7 @@ static struct symtabs_and_lines find_met struct type *t, struct symbol *sym_class); -static int collect_methods (char *copy, struct type *t, +static int collect_methods (char *copy, struct type *t, struct symbol *sym_class, struct symbol **sym_arr); static NORETURN void cplusplus_error (const char *name, @@ -83,13 +84,14 @@ static NORETURN void cplusplus_error (co static int total_number_of_methods (struct type *type); -static int find_methods (struct type *, char *, struct symbol **); +static int find_methods (struct type *, char *, enum language, struct symbol **); static int add_matching_methods (int method_counter, struct type *t, + enum language language, struct symbol **sym_arr); static int add_constructors (int method_counter, struct type *t, - struct symbol **sym_arr); + enum language language, struct symbol **sym_arr); static void build_canonical_line_spec (struct symtab_and_line *, char *, char ***); @@ -196,7 +198,7 @@ total_number_of_methods (struct type *ty Note that this function is g++ specific. */ static int -find_methods (struct type *t, char *name, struct symbol **sym_arr) +find_methods (struct type *t, char *name, enum language language, struct symbol **sym_arr) { int i1 = 0; int ibase; @@ -206,8 +208,8 @@ find_methods (struct type *t, char *name unless we figure out how to get the physname without the name of the class, then the loop can't do any good. */ if (class_name - && (lookup_symbol (class_name, (struct block *) NULL, - STRUCT_DOMAIN, (int *) NULL, + && (lookup_symbol_in_language (class_name, (struct block *) NULL, + STRUCT_DOMAIN, language, (int *) NULL, (struct symtab **) NULL))) { int method_counter; @@ -238,12 +240,12 @@ find_methods (struct type *t, char *name if (strcmp_iw (name, method_name) == 0) /* Find all the overloaded methods with that name. */ - i1 += add_matching_methods (method_counter, t, + i1 += add_matching_methods (method_counter, t, language, sym_arr + i1); else if (strncmp (class_name, name, name_len) == 0 && (class_name[name_len] == '\0' || class_name[name_len] == '<')) - i1 += add_constructors (method_counter, t, + i1 += add_constructors (method_counter, t, language, sym_arr + i1); } } @@ -261,7 +263,7 @@ find_methods (struct type *t, char *name if (i1 == 0) for (ibase = 0; ibase < TYPE_N_BASECLASSES (t); ibase++) - i1 += find_methods (TYPE_BASECLASS (t, ibase), name, sym_arr + i1); + i1 += find_methods (TYPE_BASECLASS (t, ibase), name, language, sym_arr + i1); return i1; } @@ -271,7 +273,7 @@ find_methods (struct type *t, char *name array SYM_ARR. Return the number of methods added. */ static int -add_matching_methods (int method_counter, struct type *t, +add_matching_methods (int method_counter, struct type *t, enum language language, struct symbol **sym_arr) { int field_counter; @@ -305,8 +307,9 @@ add_matching_methods (int method_counter if (is_destructor_name (phys_name) != 0) continue; - sym_arr[i1] = lookup_symbol (phys_name, + sym_arr[i1] = lookup_symbol_in_language (phys_name, NULL, VAR_DOMAIN, + language, (int *) NULL, (struct symtab **) NULL); if (sym_arr[i1]) @@ -332,7 +335,7 @@ add_matching_methods (int method_counter array SYM_ARR. Return the number of methods added. */ static int -add_constructors (int method_counter, struct type *t, +add_constructors (int method_counter, struct type *t, enum language language, struct symbol **sym_arr) { int field_counter; @@ -362,8 +365,9 @@ add_constructors (int method_counter, st /* If this method is actually defined, include it in the list. */ - sym_arr[i1] = lookup_symbol (phys_name, + sym_arr[i1] = lookup_symbol_in_language (phys_name, NULL, VAR_DOMAIN, + language, (int *) NULL, (struct symtab **) NULL); if (sym_arr[i1]) @@ -1410,7 +1414,7 @@ find_method (int funfirstline, char ***c /* Find all methods with a matching name, and put them in sym_arr. */ - i1 = collect_methods (copy, t, sym_arr); + i1 = collect_methods (copy, t, sym_class, sym_arr); if (i1 == 1) { @@ -1465,7 +1469,7 @@ find_method (int funfirstline, char ***c them in SYM_ARR. Return the number of methods found. */ static int -collect_methods (char *copy, struct type *t, +collect_methods (char *copy, struct type *t, struct symbol *sym_class, struct symbol **sym_arr) { int i1 = 0; /* Counter for the symbol array. */ @@ -1488,7 +1492,7 @@ collect_methods (char *copy, struct type } } else - i1 = find_methods (t, copy, sym_arr); + i1 = find_methods (t, copy, SYMBOL_LANGUAGE (sym_class), sym_arr); return i1; } Index: src/gdb/symtab.c =================================================================== --- src.orig/gdb/symtab.c 2007-03-09 01:12:02.000000000 +0000 +++ src/gdb/symtab.c 2007-03-09 01:44:12.000000000 +0000 @@ -84,6 +84,7 @@ static struct symbol *lookup_symbol_aux const char *linkage_name, const struct block *block, const domain_enum domain, + enum language language, int *is_a_field_of_this, struct symtab **symtab); @@ -1079,9 +1080,10 @@ fixup_psymbol_section (struct partial_sy code). */ struct symbol * -lookup_symbol (const char *name, const struct block *block, - const domain_enum domain, int *is_a_field_of_this, - struct symtab **symtab) +lookup_symbol_in_language (const char *name, const struct block *block, + const domain_enum domain, enum language lang, + int *is_a_field_of_this, + struct symtab **symtab) { char *demangled_name = NULL; const char *modified_name = NULL; @@ -1093,7 +1095,7 @@ lookup_symbol (const char *name, const s /* If we are using C++ or Java, demangle the name before doing a lookup, so we can always binary search. */ - if (current_language->la_language == language_cplus) + if (lang == language_cplus) { demangled_name = cplus_demangle (name, DMGL_ANSI | DMGL_PARAMS); if (demangled_name) @@ -1103,7 +1105,7 @@ lookup_symbol (const char *name, const s needtofreename = 1; } } - else if (current_language->la_language == language_java) + else if (lang == language_java) { demangled_name = cplus_demangle (name, DMGL_ANSI | DMGL_PARAMS | DMGL_JAVA); @@ -1129,7 +1131,8 @@ lookup_symbol (const char *name, const s } returnval = lookup_symbol_aux (modified_name, mangled_name, block, - domain, is_a_field_of_this, symtab); + domain, lang, + is_a_field_of_this, symtab); if (needtofreename) xfree (demangled_name); @@ -1140,7 +1143,20 @@ lookup_symbol (const char *name, const s return returnval; } -/* Behave like lookup_symbol_aux except that NAME is the natural name +/* Behave like lookup_symbol_in_language, but performed with the + current language. */ + +struct symbol * +lookup_symbol (const char *name, const struct block *block, + domain_enum domain, int *is_a_field_of_this, + struct symtab **symtab) +{ + return lookup_symbol_in_language (name, block, domain, + current_language->la_language, + is_a_field_of_this, symtab); +} + +/* Behave like lookup_symbol except that NAME is the natural name of the symbol that we're looking for and, if LINKAGE_NAME is non-NULL, ensure that the symbol's linkage name matches as well. */ @@ -1148,9 +1164,11 @@ lookup_symbol (const char *name, const s static struct symbol * lookup_symbol_aux (const char *name, const char *linkage_name, const struct block *block, const domain_enum domain, + enum language language, int *is_a_field_of_this, struct symtab **symtab) { struct symbol *sym; + const struct language_defn *langdef; /* Make sure we do something sensible with is_a_field_of_this, since the callers that set this parameter to some non-null value will @@ -1168,13 +1186,15 @@ lookup_symbol_aux (const char *name, con if (sym != NULL) return sym; - /* If requested to do so by the caller and if appropriate for the - current language, check to see if NAME is a field of `this'. */ + /* If requested to do so by the caller and if appropriate for LANGUAGE, + check to see if NAME is a field of `this'. */ + + langdef = language_def (language); - if (current_language->la_value_of_this != NULL + if (langdef->la_value_of_this != NULL && is_a_field_of_this != NULL) { - struct value *v = current_language->la_value_of_this (0); + struct value *v = langdef->la_value_of_this (0); if (v && check_field (v, name)) { @@ -1185,12 +1205,11 @@ lookup_symbol_aux (const char *name, con } } - /* Now do whatever is appropriate for the current language to look + /* Now do whatever is appropriate for LANGUAGE to look up static and global variables. */ - sym = current_language->la_lookup_symbol_nonlocal (name, linkage_name, - block, domain, - symtab); + sym = langdef->la_lookup_symbol_nonlocal (name, linkage_name, + block, domain, symtab); if (sym != NULL) return sym; @@ -3070,7 +3089,8 @@ search_symbols (char *regexp, domain_enu || lookup_symbol (SYMBOL_LINKAGE_NAME (msymbol), (struct block *) NULL, VAR_DOMAIN, - 0, (struct symtab **) NULL) == NULL) + 0, (struct symtab **) NULL) + == NULL) found_misc = 1; } } Index: src/gdb/symtab.h =================================================================== --- src.orig/gdb/symtab.h 2007-03-09 01:12:02.000000000 +0000 +++ src/gdb/symtab.h 2007-03-09 01:44:12.000000000 +0000 @@ -34,6 +34,7 @@ struct block; struct blockvector; struct axs_value; struct agent_expr; +enum language; /* Some of the structures in this file are space critical. The space-critical structures are: @@ -1007,7 +1008,14 @@ extern int asm_demangle; extern struct symtab *lookup_symtab (const char *); -/* lookup a symbol by name (optional block, optional symtab) */ +/* lookup a symbol by name (optional block, optional symtab) in language */ + +extern struct symbol *lookup_symbol_in_language (const char *, const struct block *, + const domain_enum, enum language, + int *, + struct symtab **); + +/* lookup a symbol by name (optional block, optional symtab) in the current language */ extern struct symbol *lookup_symbol (const char *, const struct block *, const domain_enum, int *, Index: src/gdb/ada-lang.h =================================================================== --- src.orig/gdb/ada-lang.h 2007-03-09 01:12:02.000000000 +0000 +++ src/gdb/ada-lang.h 2007-03-09 01:44:12.000000000 +0000 @@ -474,17 +474,6 @@ extern void ada_reset_thread_registers ( extern int ada_build_task_list (void); -/* Look up a symbol by name using the search conventions of - a specific language (optional block, optional symtab). - FIXME: Should be symtab.h. */ - -extern struct symbol *lookup_symbol_in_language (const char *, - const struct block *, - domain_enum, - enum language, - int *, - struct symtab **); - extern int ada_exception_catchpoint_p (struct breakpoint *b); extern struct symtab_and_line --------------050809090404000206080800 Content-Type: text/plain; name="cpp_break_in_c_tests.diff" Content-Transfer-Encoding: 7bit Content-Disposition: inline; filename="cpp_break_in_c_tests.diff" Content-length: 3826 gdb/testsuite/ * gdb.cp/method2.cc: New test. * gdb.cp/method2.exp: New test. * gdb.cp/Makefile.in (EXECUTABLES): Add method2. --- gdb/testsuite/gdb.cp/Makefile.in | 2 - gdb/testsuite/gdb.cp/method2.cc | 27 +++++++++++++++ gdb/testsuite/gdb.cp/method2.exp | 70 +++++++++++++++++++++++++++++++++++++++ 3 files changed, 98 insertions(+), 1 deletion(-) Index: src/gdb/testsuite/gdb.cp/method2.cc =================================================================== --- /dev/null 1970-01-01 00:00:00.000000000 +0000 +++ src/gdb/testsuite/gdb.cp/method2.cc 2007-03-11 20:39:30.000000000 +0000 @@ -0,0 +1,27 @@ +struct A +{ + void method (); + void method (int a); + void method (A* a); +}; + +void +A::method () +{ +} + +void +A::method (int a) +{ +} + +void +A::method (A* a) +{ +} + +int +main (int argc, char** argv) +{ + return 0; +} Index: src/gdb/testsuite/gdb.cp/method2.exp =================================================================== --- /dev/null 1970-01-01 00:00:00.000000000 +0000 +++ src/gdb/testsuite/gdb.cp/method2.exp 2007-03-11 20:39:30.000000000 +0000 @@ -0,0 +1,70 @@ +# Copyright 2007 +# Free Software Foundation, Inc. + +# This program is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 2 of the License, or +# (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software +# Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + +# This file is part of the gdb testsuite + +# This tests setting a break in an ambiguous c++ method with +# current_language set to c. + +if { [skip_cplus_tests] } { continue } + +set testfile "method2" +set srcfile ${testfile}.cc +set binfile ${objdir}/${subdir}/${testfile} + +if { [gdb_compile "${srcdir}/${subdir}/${srcfile}" "${binfile}" executable {debug c++}] != "" } { + untested method2.exp + return -1 +} + +if [get_compiler_info $binfile "c++"] { + return -1 +} + +gdb_exit +gdb_start +gdb_reinitialize_dir $srcdir/$subdir +gdb_load ${binfile} + +if ![runto_main] then { + perror "couldn't run to breakpoint" + continue +} + +proc test_break { lang } { + global gdb_prompt + + gdb_test "set lang $lang" \ + "" \ + "setting language $lang" + + send_gdb "break A::method\n" + gdb_expect { + -re ".0. cancel.*\[\r\n\]*.1. all.*\[\r\n\]*.2. A::method\\(A\\*\\) at .*\[\r\n\]*.3. A::method\\(int\\) at .*\[\r\n\]*\[\r\n\]*.4. A::method\\(\\) at .*\[\r\n\]*> $" { + gdb_test "0" \ + "canceled" \ + "breaking in method ($lang)" + } + -re ".*$gdb_prompt $" { fail "breaking in method ($lang)" } + default { fail "breaking in method ($lang) (timeout)" } + } +} + +test_break "c" +test_break "c++" + +gdb_continue_to_end "continue to end" Index: src/gdb/testsuite/gdb.cp/Makefile.in =================================================================== --- src.orig/gdb/testsuite/gdb.cp/Makefile.in 2007-03-05 03:28:38.000000000 +0000 +++ src/gdb/testsuite/gdb.cp/Makefile.in 2007-03-11 20:39:30.000000000 +0000 @@ -4,7 +4,7 @@ srcdir = @srcdir@ EXECUTABLES = ambiguous annota2 anon-union cplusfuncs cttiadd \ derivation inherit local member-ptr method misc \ overload ovldbreak ref-typ ref-typ2 templates userdef virtfunc namespace \ - ref-types ref-params + ref-types ref-params method2 all info install-info dvi install uninstall installcheck check: @echo "Nothing to be done for $@..." --------------050809090404000206080800--