This is the mail archive of the gdb-patches@sourceware.org mailing list for the GDB project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

PING: Re: [PATCH] Improve MI -var-info-path-expression for nested struct/union case.


Ping.

On 17/04/2014 1:05 PM, Andrew Burgess wrote:
> The MI command -var-info-path-expression currently does not handle some
> cases of nested structures / unions correctly, consider the following
> source file:
> 
> int
> main ( void )
> {
>   struct a_t
>   {
>     int var;
>   };
> 
>   struct s_t
>   {
>     struct a_t a;
>   };
> 
>   struct s_t s;
> 
>   return 0; /* Break Here (line 16) */
> }
> 
> And this gdb session:
> 
> (gdb) break 16
> Breakpoint 1 at 0x400550: file nested.c, line 16.
> (gdb) run
> Starting program: /projects/firepath_work/aburgess/tmp/nested.x 
> Can't read symbols from system-supplied DSO at 0x2aaaaaaab000: File truncated
> 
> Breakpoint 1, main () at nested.c:16
> 16        return 0; /* Break Here (line 16) */
> (gdb) interpreter-exec mi "-var-create var1 @ s"
> ^done,name="var1",numchild="1",value="{...}",type="struct s_t",thread-id="1",has_more="0"
> (gdb) interpreter-exec mi "-var-list-children var1"
> ^done,numchild="1",children=[child={name="var1.a",exp="a",numchild="1",type="struct a_t",thread-id="1"}],has_more="0"
> (gdb) interpreter-exec mi "-var-list-children var1.a"
> ^done,numchild="1",children=[child={name="var1.a.var",exp="var",numchild="0",type="int",thread-id="1"}],has_more="0"
> (gdb) interpreter-exec mi "-var-info-path-expression var1.a.var"
> ^done,path_expr="(s).var"
> (gdb) interpreter-exec mi "-data-evaluate-expression (s).var"
> ^error,msg="There is no member named var."
> 
> Notice that the result of the -var-info-path-expression is wrong, and, not
> surprisingly causes and error when passed into -data-evaluate-expression.
> 
> With this patch the result is instead this:
> 
> (gdb)  interpreter-exec mi "-var-info-path-expression var1.a.var"
> ^done,path_expr="((s).a).var"
> (gdb) interpreter-exec mi "-data-evaluate-expression ((s).a).var"
> ^done,value="-8320"
> 
> The changes to varobj.c feel like it might be possible to simplify them,
> but I can't figure out how, any change I make seems to regress something,
> so for now I'm proposing this patch.  The change is very contained anyway,
> so if someone can improve it later it's not going to cause any disruption.
> 
> OK to apply?
> 
> Thanks,
> Andrew
> 
> 
> gdb/ChangeLog:
> 
> 	* varobj.c (is_path_expr_parent): Improve test for anonymous
> 	structures and unions.
> 
> gdb/testsuite/ChangeLog:
> 
> 	* gdb.mi/var-cmd.c (do_nested_struct_union_tests): New function
> 	setting up test structures.
> 	(main): Call new test function.
> 	* gdb.mi/mi2-var-child.exp: Create additional breakpoint in new
> 	test function, continue into test function and walk test
> 	structures.
> ---
>  gdb/testsuite/gdb.mi/mi2-var-child.exp | 61 +++++++++++++++++++++++++++++++
>  gdb/testsuite/gdb.mi/var-cmd.c         | 65 ++++++++++++++++++++++++++++++++++
>  gdb/varobj.c                           | 30 +++++++++++++---
>  3 files changed, 152 insertions(+), 4 deletions(-)
> 
> diff --git a/gdb/testsuite/gdb.mi/mi2-var-child.exp b/gdb/testsuite/gdb.mi/mi2-var-child.exp
> index d2f65c5..d9f5991 100644
> --- a/gdb/testsuite/gdb.mi/mi2-var-child.exp
> +++ b/gdb/testsuite/gdb.mi/mi2-var-child.exp
> @@ -1162,6 +1162,10 @@ set lineno [gdb_get_line_number "anonymous type tests breakpoint"]
>  mi_create_breakpoint \
>      "$srcfile:$lineno" {[0-9]+} keep {do_anonymous_type_tests} \
>      ".*var-cmd.c" $lineno $hex "break in do_anonymous_type_tests"
> +set lineno [gdb_get_line_number "nested struct union tests breakpoint"]
> +mi_create_breakpoint \
> +    "$srcfile:$lineno" {[0-9]+} keep {do_nested_struct_union_tests} \
> +    ".*var-cmd.c" $lineno $hex "break in do_nested_struct_union_tests"
>  mi_execute_to "exec-continue" "breakpoint-hit" "do_anonymous_type_tests" ""\
>      ".*" ".*" {"" "disp=\"keep\""} \
>      "continue to do_anonymous_type_tests breakpoint"
> @@ -1235,5 +1239,62 @@ set tree {
>  
>  mi_walk_varobj_tree c $tree verify_everything
>  
> +mi_send_resuming_command "exec-continue" \
> +    "continuing execution to enter do_nested_struct_union_tests"
> +mi_expect_stop "breakpoint-hit" "do_nested_struct_union_tests" ".*" ".*" ".*" \
> +    {.* disp="keep"} "Run till MI stops in do_nested_struct_union_tests"
> +
> +set tree {
> +  {struct ss} var {
> +    {struct s_a} a1 {
> +      int a {}
> +    }
> +    {struct s_b} b1 {
> +      int b {}
> +    }
> +    {union u_ab} u1 {
> +      {struct s_a} a {
> +        int a {}
> +      }
> +      {struct s_b} b {
> +        int b {}
> +      }
> +    }
> +    anonymous union {
> +      {struct s_a} a2 {
> +        int a {}
> +      }
> +      {struct s_b} b2 {
> +        int b {}
> +      }
> +    }
> +    {union {...}} u2 {
> +      {struct s_a} a3 {
> +        int a {}
> +      }
> +      {struct s_b} b3 {
> +        int b {}
> +      }
> +    }
> +  }
> +}
> +
> +mi_walk_varobj_tree c $tree verify_everything
> +
> +set tree {
> +  {struct {...}} var2 {
> +    {td_u_ab} ab {
> +      {td_s_a} a {
> +	int a {}
> +      }
> +      {td_s_b} b {
> +	int b {}
> +      }
> +    }
> +  }
> +}
> +
> +mi_walk_varobj_tree c $tree verify_everything
> +
>  mi_gdb_exit
>  return 0
> diff --git a/gdb/testsuite/gdb.mi/var-cmd.c b/gdb/testsuite/gdb.mi/var-cmd.c
> index 698b294..c519aa1 100644
> --- a/gdb/testsuite/gdb.mi/var-cmd.c
> +++ b/gdb/testsuite/gdb.mi/var-cmd.c
> @@ -552,6 +552,70 @@ do_anonymous_type_tests (void)
>    return; /* anonymous type tests breakpoint */
>  }
>  
> +void
> +do_nested_struct_union_tests (void)
> +{
> +  struct s_a
> +  {
> +    int a;
> +  };
> +  struct s_b
> +  {
> +    int b;
> +  };
> +  union u_ab
> +  {
> +    struct s_a a;
> +    struct s_b b;
> +  };
> +  struct ss
> +  {
> +    struct s_a a1;
> +    struct s_b b1;
> +    union u_ab u1;
> +
> +    /* Anonymous union.  */
> +    union
> +    {
> +      struct s_a a2;
> +      struct s_b b2;
> +    };
> +
> +    union
> +    {
> +      struct s_a a3;
> +      struct s_b b3;
> +    } u2;
> +  };
> +
> +  typedef struct
> +  {
> +    int a;
> +  } td_s_a;
> +
> +  typedef struct
> +  {
> +    int b;
> +  } td_s_b;
> +
> +  typedef union
> +  {
> +    td_s_a a;
> +    td_s_b b;
> +  } td_u_ab;
> +
> +  struct ss var;
> +  struct
> +  {
> +    td_u_ab ab;
> +  } var2;
> +
> +  memset (&var, 0, sizeof (var));
> +  memset (&var2, 0, sizeof (var2));
> +
> +  return; /* nested struct union tests breakpoint */
> +}
> +
>  int
>  main (int argc, char *argv [])
>  {
> @@ -563,6 +627,7 @@ main (int argc, char *argv [])
>    do_at_tests ();
>    do_bitfield_tests ();
>    do_anonymous_type_tests ();
> +  do_nested_struct_union_tests ();
>    exit (0);
>  }
>  
> diff --git a/gdb/varobj.c b/gdb/varobj.c
> index 10ef5b7..33083b2 100644
> --- a/gdb/varobj.c
> +++ b/gdb/varobj.c
> @@ -1075,12 +1075,34 @@ is_path_expr_parent (struct varobj *var)
>    if (CPLUS_FAKE_CHILD (var))
>      return 0;
>  
> -  type = varobj_get_value_type (var);
> +  type = varobj_get_gdb_type (var);
>  
>    /* Anonymous unions and structs are also not path_expr parents.  */
> -  return !((TYPE_CODE (type) == TYPE_CODE_STRUCT
> -	    || TYPE_CODE (type) == TYPE_CODE_UNION)
> -	   && TYPE_NAME (type) == NULL);
> +  if ((TYPE_CODE (type) == TYPE_CODE_STRUCT
> +       || TYPE_CODE (type) == TYPE_CODE_UNION)
> +      && TYPE_NAME (type) == NULL
> +      && TYPE_TAG_NAME (type) == NULL)
> +    {
> +      if (var->parent != NULL)
> +	{
> +	  const struct type *parent_type;
> +
> +	  parent_type = varobj_get_gdb_type (var->parent);
> +	  if (TYPE_CODE (parent_type) == TYPE_CODE_STRUCT
> +	      || TYPE_CODE (parent_type) == TYPE_CODE_UNION)
> +	    {
> +	      const char *field_name;
> +
> +	      gdb_assert (var->index < TYPE_NFIELDS (parent_type));
> +	      field_name = TYPE_FIELD_NAME (parent_type, var->index);
> +	      return !(field_name == NULL || *field_name == '\0');
> +	    }
> +	}
> +
> +      return 0;
> +    }
> +
> +  return 1;
>  }
>  
>  /* Return the path expression parent for VAR.  */
> 


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]