Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

RISC-V Remote Target Support? #598

Closed
kallisti5 opened this issue Jan 12, 2021 · 13 comments
Closed

RISC-V Remote Target Support? #598

kallisti5 opened this issue Jan 12, 2021 · 13 comments

Comments

@kallisti5
Copy link

Is your feature request related to a problem? Please describe.
Looking for RISC-V support :-)

set architecture riscv
riscv       riscv:rv32  riscv:rv64 
gef➤  gef-remote -q localhost:1234
[!] Command 'gef-remote' failed to execute properly, reason: Unknown architecture: The target architecture is set to "riscv".
gef➤  gef-remote -q localhost:1234
[!] Command 'gef-remote' failed to execute properly, reason: Unknown architecture: The target architecture is set to "riscv:rv64".
@Grazfather
Copy link
Collaborator

Risc 5 is supported, it's just not detecting it properly. Try setting it manually: pi set_arch("riscv")

You're not giving us a lot to go on. Take a look and try to see why it's not detecting it.

@Grazfather
Copy link
Collaborator

If you are using gdb >= 10.1 then this incorrect detection is probably due to #594, which should be fixed soon.

@kallisti5
Copy link
Author

Ah yup. gdb 10.1

I should note that running the non-gef specific remote target 127.0.0.1:1234 works as expected. I'll close this one as a duplicate of #594

@Grazfather
Copy link
Collaborator

Thank you.

Would you be able to check out that commit to verify that it fixes the issue for you?

Thanks

@kallisti5
Copy link
Author

@Grazfather hm.. maybe I closed this one too soon :-)

Using the latest gef from dev....

[kallisti5@eris generated.riscv64]$ riscv64-elf-gdb
Exception caught while booting Guile.
Error in function "make_objcode_from_file":
bad header on object file: "\x7fELF\x02\x01\x01ÿ\x00\x00\x00\x00\x00\x00\x00\x00"
riscv64-elf-gdb: warning: Could not complete Guile gdb module initialization from:
/usr/share/gdb/guile/gdb/boot.scm.
Limited Guile support is available.
Suggest passing --data-directory=/path/to/gdb/data-directory.
GNU gdb (GDB) 10.1
Copyright (C) 2020 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.
Type "show copying" and "show warranty" for details.
This GDB was configured as "--host=x86_64-pc-linux-gnu --target=riscv64-elf".
Type "show configuration" for configuration details.
For bug reporting instructions, please see:
<https://www.gnu.org/software/gdb/bugs/>.
Find the GDB manual and other documentation resources online at:
    <http://www.gnu.org/software/gdb/documentation/>.

For help, type "help".
Type "apropos word" to search for commands related to "word".
GEF for linux ready, type `gef' to start, `gef config' to configure
92 commands loaded for GDB 10.1 using Python engine 3.9
gef➤  gef-remote -q localhost:1234
[!] Command 'gef-remote' failed to execute properly, reason: unsupported architecture: auto" (currently "riscv
gef➤  

@kallisti5 kallisti5 reopened this Apr 14, 2021
@kallisti5
Copy link
Author

To be honest.. things have gotten a bit worse:

gef➤  pi set_arch("riscv")
<__main__.RISCV object at 0x7f71502a8e80>
gef➤  add-symbol-file /home/kallisti5/Code/haiku/generated.riscv64/objects/haiku/riscv64/debug_1/system/boot/efi/boot_loader_efi 0xfe6bc000
add symbol table from file "/home/kallisti5/Code/haiku/generated.riscv64/objects/haiku/riscv64/debug_1/system/boot/efi/boot_loader_efi" at
	.text_addr = 0xfe6bc000
Reading symbols from /home/kallisti5/Code/haiku/generated.riscv64/objects/haiku/riscv64/debug_1/system/boot/efi/boot_loader_efi...
Python Exception <class 'OSError'> CPU type is currently not supported: riscv: 
gef➤  

Not calling pi set_arch("riscv")

For help, type "help".
Type "apropos word" to search for commands related to "word".
GEF for linux ready, type `gef' to start, `gef config' to configure
92 commands loaded for GDB 10.1 using Python engine 3.9
gef➤  add-symbol-file /home/kallisti5/Code/haiku/generated.riscv64/objects/haiku/riscv64/debug_1/system/boot/efi/boot_loader_efi 0xfe6bc000
add symbol table from file "/home/kallisti5/Code/haiku/generated.riscv64/objects/haiku/riscv64/debug_1/system/boot/efi/boot_loader_efi" at
	.text_addr = 0xfe6bc000
Reading symbols from /home/kallisti5/Code/haiku/generated.riscv64/objects/haiku/riscv64/debug_1/system/boot/efi/boot_loader_efi...
Python Exception <class 'gdb.error'> Not supported on this target.: 

Here are the valid riscv architectures:

gef➤  set architecture
Requires an argument. Valid arguments are riscv, riscv:rv64, riscv:rv32, auto.

@kallisti5
Copy link
Author

Here's the raw GDB stub output from qemu-system-riscv64. I hate it 😆

$qXfer:features:read:target.xml:0,4096#1E

+$l<?xml version="1.0"?><!DOCTYPE target SYSTEM "gdb-target.dtd"><target><xi:include href="riscv-64bit-cpu.xml"/><xi:include href="riscv-64bit-fpu.xml"/><xi:include href="riscv-64bit-csr.xml"/><xi:include href="riscv-64bit-virtual.xml"/></target>#68

There's no "<architecture>" defined there from the qemu code. Looking at qemu's gdbstub...

   if (strncmp(p, "target.xml", len) == 0) {
        char *buf = process->target_xml;
        const size_t buf_sz = sizeof(process->target_xml);

        /* Generate the XML description for this CPU.  */
        if (!buf[0]) {
            GDBRegisterState *r;

            pstrcat(buf, buf_sz,
                    "<?xml version=\"1.0\"?>"
                    "<!DOCTYPE target SYSTEM \"gdb-target.dtd\">"
                    "<target>");
            if (cc->gdb_arch_name) {
                gchar *arch = cc->gdb_arch_name(cpu);
                pstrcat(buf, buf_sz, "<architecture>");
                pstrcat(buf, buf_sz, arch);
                pstrcat(buf, buf_sz, "</architecture>");
                g_free(arch);
            }

So it looks like qemu isn't setting gdb_arch_name for riscv. Looking through the qemu source code...

qemu/qemu@edf6478

Oops... a really recent addition :-)

So.. it looks like gdb is calling no architecture defined in the target.xml as "auto"

gef might want to handle "auto" with some special warning case :-)

@kallisti5
Copy link
Author

I compiled qemu 6.0, and it indeed reports architecture now...

$qXfer:features:read:target.xml:0,4096#1E
+$l<?xml version="1.0"?><!DOCTYPE target SYSTEM "gdb-target.dtd"><target><architecture>riscv:rv64</architecture><xi:include href="riscv-64bit-cpu.xml"/><xi:include href="riscv-64bit-fpu.xml"/><xi:include href="riscv-64bit-virtual.xml"/><xi:include href="riscv-csr.xml"/></target>#6e

Now gef shows:

gef➤  gef-remote -q 127.0.0.1:1234
[!] Command 'gef-remote' failed to execute properly, reason: unsupported architecture: riscv:rv64

A quick patch to gef:

[kallisti5@eris generated.riscv64]$ diff -Naur ~/.gdbinit-gef-stock.py ~/.gdbinit-gef.py
--- /home/kallisti5/.gdbinit-gef-stock.py	2021-04-14 08:43:21.201598648 -0500
+++ /home/kallisti5/.gdbinit-gef.py	2021-04-14 08:44:00.975034941 -0500
@@ -6320,6 +6320,9 @@
         elif arch.startswith("sparc"):
             current_elf.e_machine = Elf.SPARC
             current_arch = SPARC()
+        elif arch.startswith("riscv"):
+            current_elf.e_machine = Elf.RISCV
+            current_arch = RISCV()
         else:
             raise RuntimeError("unsupported architecture: {}".format(arch))
 

Back to the original error 😠 under qemu 6.0

gef➤  gef-remote -q 127.0.0.1:1234
[!] Command 'gef-remote' failed to execute properly, reason: unsupported architecture: auto" (currently "riscv

@Grazfather
Copy link
Collaborator

You'll have to break this into separate issue. Can you debug risc5 locally?

What are you using as your riscv target? Do you have some easy qemu setup I could use to reproduce.

@kallisti5
Copy link
Author

to reproduce, qemu-system-riscv64 -s -S is enough to give gdb / gef something to connect to. qemu-system-riscv64 ships in os packages for Fedora / ArchLinux that I know of.

However for the fix I mentioned above, you might have to compile qemu-system-riscv64 6.x from upstream qemu.

I've attached my qemu 6.x qemu-system-riscv64, but it likely won't help much if you don't have matching system libraries to run it
qemu-riscv64.zip

@Grazfather
Copy link
Collaborator

Yes, I have that, I'll have to take some time to get a linux system running in it, it's just not a priority for me right now.

@stefanct
Copy link

JFYI, AFAICT running an OS within qemu is not required to investigate the problem. The parameters he mentioned halt the CPU at reset and one can use gdb to run a bare-metal binary. This is a common setup for embedded systems/microcontrollers (where you also debug via GDB's remote function and a gdb server stub running in a hardware debugger dongle. This will be less useful with riscv64 but for riscv32 microcontrollers. (I am working on hw security mechanisms on these thus my interest in this issue ;)

@Grazfather
Copy link
Collaborator

I do not have this same issue (years later 😅).

I am using this dockerfile to install both qemu and gdb with riscv64 support.

It still isn't perfect, because it doesn't know how to map the stack, but I think that's another issue.

If any of you are still using riscv, I would be curious to understand how it's behaving for you now.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

4 participants
@kallisti5 @stefanct @Grazfather and others