8 # Note that gdb comes with its own testsuite. I was unable to figure out how to
9 # run that testsuite against the spike simulator.
12 for directory
in (os
.getcwd(), os
.path
.dirname(testlib
.__file
__)):
13 fullpath
= os
.path
.join(directory
, path
)
14 if os
.path
.exists(fullpath
):
19 """Compile a single .c file into a binary."""
20 dst
= os
.path
.splitext(args
[0])[0]
21 cc
= os
.path
.expandvars("$RISCV/bin/riscv64-unknown-elf-gcc")
22 cmd
= [cc
, "-g", "-O", "-o", dst
]
24 found
= find_file(arg
)
30 result
= os
.system(cmd
)
31 assert result
== 0, "%r failed" % cmd
35 # http://stackoverflow.com/questions/2838244/get-open-tcp-port-in-python/2838309#2838309
37 s
= socket
.socket(socket
.AF_INET
, socket
.SOCK_STREAM
)
39 port
= s
.getsockname()[1]
44 def __init__(self
, binary
, halted
=False, with_gdb
=True, timeout
=None):
45 """Launch spike. Return tuple of its process and the port it's running on."""
48 cmd
+= ["timeout", str(timeout
)]
50 cmd
+= [find_file("spike")]
54 self
.port
= unused_port()
55 cmd
+= ['--gdb-port', str(self
.port
)]
59 logfile
= open("spike.log", "w")
60 self
.process
= subprocess
.Popen(cmd
, stdin
=subprocess
.PIPE
, stdout
=logfile
,
70 def wait(self
, *args
, **kwargs
):
71 return self
.process
.wait(*args
, **kwargs
)
75 path
= os
.path
.expandvars("$RISCV/bin/riscv64-unknown-elf-gdb")
76 self
.child
= pexpect
.spawn(path
)
77 self
.child
.logfile
= file("gdb.log", "w")
79 self
.command("set width 0")
80 self
.command("set height 0")
82 self
.command("set print entry-values no")
85 """Wait for prompt."""
86 self
.child
.expect("\(gdb\)")
88 def command(self
, command
, timeout
=-1):
89 self
.child
.sendline(command
)
90 self
.child
.expect("\n", timeout
=timeout
)
91 self
.child
.expect("\(gdb\)", timeout
=timeout
)
92 return self
.child
.before
.strip()
94 def c(self
, wait
=True):
96 return self
.command("c")
98 self
.child
.sendline("c")
99 self
.child
.expect("Continuing")
102 self
.child
.send("\003");
103 self
.child
.expect("\(gdb\)")
105 def x(self
, address
, size
='w'):
106 output
= self
.command("x/%s %s" % (size
, address
))
107 value
= int(output
.split(':')[1].strip(), 0)
111 output
= self
.command("p %s" % obj
)
112 value
= int(output
.split('=')[-1].strip())
116 return self
.command("stepi")