From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (qmail 5787 invoked by alias); 12 Feb 2006 18:49:19 -0000 Received: (qmail 5778 invoked by uid 22791); 12 Feb 2006 18:49:17 -0000 X-Spam-Check-By: sourceware.org Received: from w099.z064220152.sjc-ca.dsl.cnc.net (HELO duck.specifix.com) (64.220.152.99) by sourceware.org (qpsmtpd/0.31) with ESMTP; Sun, 12 Feb 2006 18:49:15 +0000 Received: from [::1] (duck.specifix.com [64.220.152.99]) by duck.specifix.com (Postfix) with ESMTP id B7BC4FC4C; Sun, 12 Feb 2006 10:49:11 -0800 (PST) From: Fred Fish Reply-To: fnf@specifix.com To: Daniel Jacobowitz Subject: Re: [PATCH] Fix ptype problem printing typedefs defined differently in different compilation units Date: Sun, 12 Feb 2006 18:49:00 -0000 User-Agent: KMail/1.9.1 Cc: Jim Blandy , gdb-patches@sourceware.org, fnf@specifix.com References: <200601031517.50309.fnf@specifix.com> <200602111501.01801.fnf@specifix.com> <20060211202059.GB27289@nevyn.them.org> In-Reply-To: <20060211202059.GB27289@nevyn.them.org> MIME-Version: 1.0 Content-Type: text/plain; charset="iso-8859-1" Content-Transfer-Encoding: 7bit Content-Disposition: inline Message-Id: <200602121349.07257.fnf@specifix.com> Mailing-List: contact gdb-patches-help@sourceware.org; run by ezmlm Precedence: bulk List-Subscribe: List-Archive: List-Post: List-Help: , Sender: gdb-patches-owner@sourceware.org X-SW-Source: 2006-02/txt/msg00271.txt.bz2 On Saturday 11 February 2006 15:20, Daniel Jacobowitz wrote: > Well, if the results of ptype_eval and evaluate_type are inconsistent > here, won't the result of doing this be meaningless? And if they were > already consistent, then I'm a little confused how your patch works. ptype_eval extracted the type directly from the expression, while evaluate_type creates a value, which it wasn't prepared to do from just a typedef name. In any case, I think I found a better solution, which is basically to eliminate ptype_eval and let the expression evaluator create a value with the right type. The actual value isn't important, since we're only going to use it's type. This is how the ADA expression evaluator handles evaluating an OP_TYPE expression. > > > Also ptype will now do the RTTI lookup; I'm not sure whether it > > > should or not. > > > > Not sure either, now that you point it out. > > Might as well let it. OK, then we can let whatis_exp handle both ptype and whatis. Attached is a reworked patch, with a couple of additional testsuite changes. -Fred Gdb ChangeLog entry: 2006-02-12 Fred Fish * eval.c (evaluate_subexp_standard): For OP_VAR_VALUE, if exp is a typedef, return a non lval value zero, of the appropriate type, when avoiding side effects. For OP_TYPE, return a non lval value zero, of the appropriate type, when avoiding side effects. * typeprint.c (ptype_eval): Remove function and declaration. (ptype_command): Simplify to just a call to whatis_exp. Testsuite ChangeLog entry: 2006-02-12 Fred Fish * gdb.base/ptype.c: Add afoo for typedef checks. * gdb.base/ptype1.c: Add afoo for typedef checks. * gdb.base/whatis.c: Add typedef foo and var afoo. * gdb.base/ptype.exp: Add tests for 'file'::symbol and 'file'::typename syntax. Add tests using value history. * gdb.base/whatis.exp: Ditto. Index: eval.c =================================================================== RCS file: /cvsroots/latest/src/gdb/gdb/eval.c,v retrieving revision 1.1.1.2 diff -c -p -r1.1.1.2 eval.c *** eval.c 30 Dec 2005 18:53:04 -0000 1.1.1.2 --- eval.c 12 Feb 2006 18:07:29 -0000 *************** evaluate_subexp_standard (struct type *e *** 461,466 **** --- 461,472 ---- value_rtti_target_type () if we are dealing with a pointer or reference to a base class and print object is on. */ + /* If asked to evaluate a typedef, and we are avoiding side effects, + then create a value of the appropriate type to return. */ + if (noside == EVAL_AVOID_SIDE_EFFECTS + && SYMBOL_CLASS (exp->elts[pc + 2].symbol) == LOC_TYPEDEF) + return (allocate_value (SYMBOL_TYPE (exp->elts[2].symbol))); + else return value_of_variable (exp->elts[pc + 2].symbol, exp->elts[pc + 1].block); *************** evaluate_subexp_standard (struct type *e *** 2086,2092 **** return value_of_local ("self", 1); case OP_TYPE: ! error (_("Attempt to use a type name as an expression")); default: /* Removing this case and compiling with gcc -Wall reveals that --- 2092,2106 ---- return value_of_local ("self", 1); case OP_TYPE: ! /* The value is not supposed to be used. This is here to make it ! easier to accommodate expressions that contain types. */ ! (*pos) += 2; ! if (noside == EVAL_SKIP) ! goto nosideret; ! else if (noside == EVAL_AVOID_SIDE_EFFECTS) ! return allocate_value (exp->elts[pc + 1].type); ! else ! error (_("Attempt to use a type name as an expression")); default: /* Removing this case and compiling with gcc -Wall reveals that Index: typeprint.c =================================================================== RCS file: /cvsroots/latest/src/gdb/gdb/typeprint.c,v retrieving revision 1.1.1.2 diff -c -p -r1.1.1.2 typeprint.c *** typeprint.c 30 Dec 2005 18:53:06 -0000 1.1.1.2 --- typeprint.c 12 Feb 2006 18:07:29 -0000 *************** extern void _initialize_typeprint (void) *** 45,52 **** static void ptype_command (char *, int); - static struct type *ptype_eval (struct expression *); - static void whatis_command (char *, int); static void whatis_exp (char *, int); --- 45,50 ---- *************** whatis_command (char *exp, int from_tty) *** 182,236 **** whatis_exp (exp, -1); } - /* Simple subroutine for ptype_command. */ - - static struct type * - ptype_eval (struct expression *exp) - { - if (exp->elts[0].opcode == OP_TYPE) - { - return (exp->elts[1].type); - } - else - { - return (NULL); - } - } - /* TYPENAME is either the name of a type, or an expression. */ static void ptype_command (char *typename, int from_tty) { ! struct type *type; ! struct expression *expr; ! struct cleanup *old_chain; ! ! if (typename == NULL) ! { ! /* Print type of last thing in value history. */ ! whatis_exp (typename, 1); ! } ! else ! { ! expr = parse_expression (typename); ! old_chain = make_cleanup (free_current_contents, &expr); ! type = ptype_eval (expr); ! if (type != NULL) ! { ! /* User did "ptype " */ ! printf_filtered ("type = "); ! type_print (type, "", gdb_stdout, 1); ! printf_filtered ("\n"); ! do_cleanups (old_chain); ! } ! else ! { ! /* User did "ptype " */ ! do_cleanups (old_chain); ! whatis_exp (typename, 1); ! } ! } } /* Print integral scalar data VAL, of type TYPE, onto stdio stream STREAM. --- 180,191 ---- whatis_exp (exp, -1); } /* TYPENAME is either the name of a type, or an expression. */ static void ptype_command (char *typename, int from_tty) { ! whatis_exp (typename, 1); } /* Print integral scalar data VAL, of type TYPE, onto stdio stream STREAM. Index: testsuite/gdb.base/ptype.c =================================================================== RCS file: /cvsroots/latest/src/gdb/gdb/testsuite/gdb.base/ptype.c,v retrieving revision 1.1.1.2 diff -c -p -r1.1.1.2 ptype.c *** testsuite/gdb.base/ptype.c 8 Jan 2006 20:37:18 -0000 1.1.1.2 --- testsuite/gdb.base/ptype.c 10 Feb 2006 21:38:14 -0000 *************** func_type v_func_type; *** 260,265 **** --- 260,266 ---- /***********/ typedef int foo; + static foo afoo = 2; foo intfoo (afoo) { Index: testsuite/gdb.base/ptype.exp =================================================================== RCS file: /cvsroots/latest/src/gdb/gdb/testsuite/gdb.base/ptype.exp,v retrieving revision 1.1.1.2 diff -c -p -r1.1.1.2 ptype.exp *** testsuite/gdb.base/ptype.exp 8 Jan 2006 20:37:19 -0000 1.1.1.2 --- testsuite/gdb.base/ptype.exp 12 Feb 2006 12:54:42 -0000 *************** gdb_test "list intfoo" "" *** 593,598 **** --- 593,610 ---- gdb_test "ptype foo" "type = int" "ptype foo typedef after second list of intfoo" gdb_test "list charfoo" "" gdb_test "ptype foo" "type = char" "ptype foo typedef after second list of charfoo" + # Test the 'file'::exp syntax for variables and types + gdb_test "ptype 'ptype.c'::afoo" "type = int" "ptype 'file'::symbol" + gdb_test "ptype 'ptype.c'::foo" "type = int" "ptype 'file'::typename" + gdb_test "ptype 'ptype1.c'::afoo" "type = char" "ptype 'file'::symbol" + gdb_test "ptype 'ptype1.c'::foo" "type = char" "ptype 'file'::typename" + + # Test printing value history type + + gdb_test "p (long)1" "" + gdb_test "ptype" "type = long" "ptype long value from value history" + gdb_test "p (short)1" "" + gdb_test "ptype" "type = short" "ptype short value from value history" # Test printing type of string constants and array constants, but # requires a running process. These call malloc, and can take a long Index: testsuite/gdb.base/ptype1.c =================================================================== RCS file: /cvsroots/latest/src/gdb/gdb/testsuite/gdb.base/ptype1.c,v retrieving revision 1.1.1.1 diff -c -p -r1.1.1.1 ptype1.c *** testsuite/gdb.base/ptype1.c 8 Jan 2006 20:37:18 -0000 1.1.1.1 --- testsuite/gdb.base/ptype1.c 10 Feb 2006 21:37:55 -0000 *************** *** 1,4 **** --- 1,5 ---- typedef char foo; + static foo afoo = 1; foo charfoo (afoo) { Index: testsuite/gdb.base/whatis.c =================================================================== RCS file: /cvsroots/latest/src/gdb/gdb/testsuite/gdb.base/whatis.c,v retrieving revision 1.1.1.1 diff -c -p -r1.1.1.1 whatis.c *** testsuite/gdb.base/whatis.c 8 Oct 2005 19:36:19 -0000 1.1.1.1 --- testsuite/gdb.base/whatis.c 10 Feb 2006 21:35:00 -0000 *************** unsigned long v_unsigned_long; *** 46,51 **** --- 46,54 ---- float v_float; double v_double; + typedef int foo; + static foo afoo = 1; + /* * Now some derived types, which are arrays, functions-returning, * pointers, structures, unions, and enumerations. Index: testsuite/gdb.base/whatis.exp =================================================================== RCS file: /cvsroots/latest/src/gdb/gdb/testsuite/gdb.base/whatis.exp,v retrieving revision 1.1.1.1 diff -c -p -r1.1.1.1 whatis.exp *** testsuite/gdb.base/whatis.exp 8 Oct 2005 19:36:19 -0000 1.1.1.1 --- testsuite/gdb.base/whatis.exp 12 Feb 2006 12:55:26 -0000 *************** gdb_test "whatis nested_su.inner_union_i *** 402,404 **** --- 402,421 ---- gdb_test "whatis nested_su.inner_union_instance.inner_union_int" \ "type = int" \ "whatis inner union member" + + # Test the 'file'::exp syntax for variables and types + + gdb_test "whatis 'whatis.c'::afoo" \ + "type = foo" \ + "whatis 'file'::symbol" + + gdb_test "whatis 'whatis.c'::foo" \ + "type = int" \ + "whatis 'file'::typename" + + # Test printing value history type + + gdb_test "p (long)1" "" + gdb_test "whatis" "type = long" "whatis long value from value history" + gdb_test "p (short)1" "" + gdb_test "whatis" "type = short" "whatis short value from value history"