Suggest newer gdbserver if it has no qXfer:exec-file:read

Message ID 20160319201842.GA16540@host1.jankratochvil.net
State New, archived
Headers

Commit Message

Jan Kratochvil March 19, 2016, 8:18 p.m. UTC
  Hi,

currently:
	$ gdbserver-7.9 :1234 true &
	$ gdb -q -ex 'target remote :1234' # that -q is not relevant here
	Remote debugging using :1234
	warning: Could not load vsyscall page because no executable was specified
	try using the "file" command first.
	0x00007ffff7ddcc80 in ?? ()
	(gdb) b main
	No symbol table is loaded.  Use the "file" command.
	Make breakpoint pending on future shared library load? (y or [n]) _

While one may not realize a newer gdbserver would fix that:
	$ gdbserver-7.10 :1234 true &
	$ gdb -q -ex 'target remote :1234' # that -q is not relevant here
	Remote debugging using :1234
	Reading /usr/bin/true from remote target...
	warning: File transfers from remote targets can be slow. Use "set sysroot" to access files locally instead.
	Reading /usr/bin/true from remote target...
	Reading symbols from target:/usr/bin/true...Reading symbols from /usr/lib/debug/usr/bin/true.debug...done.
	done.
	Reading /lib64/ld-linux-x86-64.so.2 from remote target...
	Reading /lib64/ld-linux-x86-64.so.2 from remote target...
	Reading symbols from target:/lib64/ld-linux-x86-64.so.2...Reading symbols from /usr/lib/debug/usr/lib64/ld-2.22.so.debug...done.
	done.
	0x00007ffff7ddcc80 in _start () from target:/lib64/ld-linux-x86-64.so.2
	(gdb) b main
	Breakpoint 1 at 0x555555555650: file src/true.c, line 59.
	(gdb) _

This can be more common case with the popular containers.  Therefore
suggesting to print there also:
	warning: No executable has been specified (see the "file" command) and remote gdbserver does not support packet "qXfer:exec-file:read" - please use FSF gdbserver version 7.10 or later.

OK for check-in?

No regressions on {x86_64,x86_64-m32,i686}-fedora23-linux-gnu.

The "qXfer:exec-file:read" support in GDB and gdbserver was implemented by:
	commit c78fa86a213db1bdef328437ac262a4f54577827
	Author: Gary Benson <gbenson@redhat.com>
	Date:   Fri Apr 17 09:47:30 2015 +0100
	    Implement remote_pid_to_exec_file using qXfer:exec-file:read


Thanks,
Jan
gdb/ChangeLog
2016-03-19  Jan Kratochvil  <jan.kratochvil@redhat.com>

	* remote.c (remote_pid_to_exec_file): Print warning for unsupported
	PACKET_qXfer_exec_file.
  

Comments

Gary Benson March 22, 2016, 9:15 a.m. UTC | #1
Jan Kratochvil wrote:
> gdb/ChangeLog
> 2016-03-19  Jan Kratochvil  <jan.kratochvil@redhat.com>
> 
> 	* remote.c (remote_pid_to_exec_file): Print warning for unsupported
> 	PACKET_qXfer_exec_file.
> 
> diff --git a/gdb/remote.c b/gdb/remote.c
> index af0a08a..d267736 100644
> --- a/gdb/remote.c
> +++ b/gdb/remote.c
> @@ -12977,7 +12977,13 @@ remote_pid_to_exec_file (struct target_ops *self, int pid)
>    char *annex = NULL;
>  
>    if (packet_support (PACKET_qXfer_exec_file) != PACKET_ENABLE)
> -    return NULL;
> +    {
> +      warning (_("No executable has been specified (see the \"file\" command) "
> +                 "and remote gdbserver does not "
> +		 "support packet \"qXfer:exec-file:read\""
> +		 " - please use FSF gdbserver version 7.10 or later."));
> +      return NULL;
> +    }
>  
>    if (filename != NULL)
>      xfree (filename);

This looks good to me.

Thanks,
Gary
  
Pedro Alves March 22, 2016, 12:24 p.m. UTC | #2
On 03/19/2016 08:18 PM, Jan Kratochvil wrote:
> Hi,
>
> currently:
> 	$ gdbserver-7.9 :1234 true &
> 	$ gdb -q -ex 'target remote :1234' # that -q is not relevant here
> 	Remote debugging using :1234
> 	warning: Could not load vsyscall page because no executable was specified
> 	try using the "file" command first.
> 	0x00007ffff7ddcc80 in ?? ()
> 	(gdb) b main
> 	No symbol table is loaded.  Use the "file" command.
> 	Make breakpoint pending on future shared library load? (y or [n]) _
>
> While one may not realize a newer gdbserver would fix that:
> 	$ gdbserver-7.10 :1234 true &
> 	$ gdb -q -ex 'target remote :1234' # that -q is not relevant here
> 	Remote debugging using :1234
> 	Reading /usr/bin/true from remote target...
> 	warning: File transfers from remote targets can be slow. Use "set sysroot" to access files locally instead.
> 	Reading /usr/bin/true from remote target...
> 	Reading symbols from target:/usr/bin/true...Reading symbols from /usr/lib/debug/usr/bin/true.debug...done.
> 	done.
> 	Reading /lib64/ld-linux-x86-64.so.2 from remote target...
> 	Reading /lib64/ld-linux-x86-64.so.2 from remote target...
> 	Reading symbols from target:/lib64/ld-linux-x86-64.so.2...Reading symbols from /usr/lib/debug/usr/lib64/ld-2.22.so.debug...done.
> 	done.
> 	0x00007ffff7ddcc80 in _start () from target:/lib64/ld-linux-x86-64.so.2
> 	(gdb) b main
> 	Breakpoint 1 at 0x555555555650: file src/true.c, line 59.
> 	(gdb) _
>
> This can be more common case with the popular containers.  Therefore
> suggesting to print there also:
> 	warning: No executable has been specified (see the "file" command) and remote gdbserver does not support packet "qXfer:exec-file:read" - please use FSF gdbserver version 7.10 or later.
>
> OK for check-in?
>
> No regressions on {x86_64,x86_64-m32,i686}-fedora23-linux-gnu.
>
> The "qXfer:exec-file:read" support in GDB and gdbserver was implemented by:
> 	commit c78fa86a213db1bdef328437ac262a4f54577827
> 	Author: Gary Benson<gbenson@redhat.com>
> 	Date:   Fri Apr 17 09:47:30 2015 +0100
> 	    Implement remote_pid_to_exec_file using qXfer:exec-file:read
>
>
> Thanks,
> Jan
>
>
> gdbexec.patch
>
>
> gdb/ChangeLog
> 2016-03-19  Jan Kratochvil<jan.kratochvil@redhat.com>
>
> 	* remote.c (remote_pid_to_exec_file): Print warning for unsupported
> 	PACKET_qXfer_exec_file.
>
> diff --git a/gdb/remote.c b/gdb/remote.c
> index af0a08a..d267736 100644
> --- a/gdb/remote.c
> +++ b/gdb/remote.c
> @@ -12977,7 +12977,13 @@ remote_pid_to_exec_file (struct target_ops *self, int pid)
>     char *annex = NULL;
>
>     if (packet_support (PACKET_qXfer_exec_file) != PACKET_ENABLE)
> -    return NULL;
> +    {
> +      warning (_("No executable has been specified (see the \"file\" command) "
> +                 "and remote gdbserver does not "
> +		 "support packet \"qXfer:exec-file:read\""
> +		 " - please use FSF gdbserver version 7.10 or later."));
> +      return NULL;
> +    }

I think this will print the warning after connecting to any
random stub, not just gdbserver.  Won't it be confusing
to suggest FSF gdbserver in that case?

Thanks,
Pedro Alves
  
Jan Kratochvil March 22, 2016, 1:16 p.m. UTC | #3
On Tue, 22 Mar 2016 13:24:03 +0100, Pedro Alves wrote:
> On 03/19/2016 08:18 PM, Jan Kratochvil wrote:
> >    if (packet_support (PACKET_qXfer_exec_file) != PACKET_ENABLE)
> >-    return NULL;
> >+    {
> >+      warning (_("No executable has been specified (see the \"file\" command) "
> >+                 "and remote gdbserver does not "
> >+		 "support packet \"qXfer:exec-file:read\""
> >+		 " - please use FSF gdbserver version 7.10 or later."));
> >+      return NULL;
> >+    }
> 
> I think this will print the warning after connecting to any
> random stub, not just gdbserver.  Won't it be confusing
> to suggest FSF gdbserver in that case?

(1) I think this message can only appear during a mistake.  Is it right?
In fact this is my primary concern with this patch.
In such case I find any info better than no info.

(2) Still it may suggest they could for example implement qXfer:exec-file:read
in their gdbserver stub if appropriate.  I believe that people who use custom
gdbserver stub are more aware of how to fix it than normal
(=desktop/enterprise) OS developers who just try to debug some programs.

(3) Do you have a better idea?  One could add "if approproate" in that
message but I find that excessive.  One could detect FSF gdbserver
(if possible, I do not think it is, BTW it could be good to identify
variant+version of gdbserver over the protocol) but then still if it either is
or is not a FSF gdbserver that message may be relevant in some cases.


Thanks,
Jan
  
Pedro Alves March 22, 2016, 1:56 p.m. UTC | #4
On 03/22/2016 01:16 PM, Jan Kratochvil wrote:
> On Tue, 22 Mar 2016 13:24:03 +0100, Pedro Alves wrote:
>> On 03/19/2016 08:18 PM, Jan Kratochvil wrote:
>>>     if (packet_support (PACKET_qXfer_exec_file) != PACKET_ENABLE)
>>> -    return NULL;
>>> +    {
>>> +      warning (_("No executable has been specified (see the \"file\" command) "
>>> +                 "and remote gdbserver does not "
>>> +		 "support packet \"qXfer:exec-file:read\""
>>> +		 " - please use FSF gdbserver version 7.10 or later."));
>>> +      return NULL;
>>> +    }
>>
>> I think this will print the warning after connecting to any
>> random stub, not just gdbserver.  Won't it be confusing
>> to suggest FSF gdbserver in that case?
> 
> (1) I think this message can only appear during a mistake.  Is it right?
> In fact this is my primary concern with this patch.
> In such case I find any info better than no info.
> 
> (2) Still it may suggest they could for example implement qXfer:exec-file:read
> in their gdbserver stub if appropriate.  I believe that people who use custom
> gdbserver stub are more aware of how to fix it than normal
> (=desktop/enterprise) OS developers who just try to debug some programs.
> 
> (3) Do you have a better idea?  One could add "if approproate" in that
> message but I find that excessive.  One could detect FSF gdbserver
> (if possible, I do not think it is, BTW it could be good to identify
> variant+version of gdbserver over the protocol) but then still if it either is
> or is not a FSF gdbserver that message may be relevant in some cases.
> 

- It's usually a mistake, though you can genuinely not have a
  binary available.  Not "only", but "usually".

- Random stubs may not know at all the executable that is running -- the
  remote end is often just bare metal raw memory, no concept of elf, etc.
  So it's not just a matter of implementing a packet - more tooling might
  and I suspect will, be necessary.  OTOH, there are OSs where it's just not
  possible, by design, to retrieve the name of the executable a process
  is running, like OpenBSD (I find it odd not to allow a ptracer access
  to that, but, alas).

- I think the important points are:

  - The user did not specify the executable manually.

  - The target/server does not support automatic executable
    retrieval. 

- I see that at least the following choices to correct the situation:

  #1 - Upgrade server to some version that supports automatic automatic
       executable retrieval.

  #2 - Hack on stub/server yourself to add support for automatic 
       executable retrieval, if possible on the target.

  #3 - Use the "file" command.

If you're connecting with a new gdb to an older gdbserver, it usually
means that installing a newer gdbserver is more than a couple
seconds work, and may not even be possible.  I think #3 will be the
path most often taken.

So I'd suggest:

   warning: No executable has been specified and target does not support
   determining executable automatically.  Try using the \"file\" command.

Seeing this, users that can hack on a remote stub will probably
realize that there's now some way for gdb to automatically retrieve
the executable.  We don't need to expose implementation details for those
users; they'll be savvy enough to find the necessary info in the RSP
manual.  For other users, talking about implementation details may
largely be noise.

Thinking of local/remote parity (and perhaps some day using gdbserver
for local debugging), that text is also generic enough that it could
be emitted by common code instead.

WDYT?

Thanks,
Pedro Alves
  

Patch

diff --git a/gdb/remote.c b/gdb/remote.c
index af0a08a..d267736 100644
--- a/gdb/remote.c
+++ b/gdb/remote.c
@@ -12977,7 +12977,13 @@  remote_pid_to_exec_file (struct target_ops *self, int pid)
   char *annex = NULL;
 
   if (packet_support (PACKET_qXfer_exec_file) != PACKET_ENABLE)
-    return NULL;
+    {
+      warning (_("No executable has been specified (see the \"file\" command) "
+                 "and remote gdbserver does not "
+		 "support packet \"qXfer:exec-file:read\""
+		 " - please use FSF gdbserver version 7.10 or later."));
+      return NULL;
+    }
 
   if (filename != NULL)
     xfree (filename);