Next Step on CPU

The C Program Compilation of RISC-V Angel

After weeks of debugging the 32-bit RISC-V engine, discussion with my supervisor, and searching over the internet, I finally found out the problem. The problem is with the stack pointer, the RISC-V Angel is not designed in the way of initializing their own stack pointer. Therefore, I have to initialize the stack pointer manually or to create a new crt0.o that initialize the stack pointer to solve the problem. Fortunately, the manual initialization in the JavaScript code is sufficient to do the job, and I even tested it out with several C programs.

The Debugger

After solving the C program compilation for the 32-bit simulator, my supervisor has assigned me a new task on developing a debugger for the simulator. As previously I had been using a lot of IDE before, a debugger sounds to be familiar to me. However, it does not seems to be easy to develop a debugger as well. I searched over the internet about how a debugger works, and gathered as much information about debugger as possible.

To start off the implementation of debugger, I decided just to implement for the breakpoint feature for this week. So I started off with finding the way to get the number of instructions that had been executed by each C program. This took me quite some time as I have to read through the “gdb manual” and find out the way to gather the information well. There are two ways that can be done to find out the number of instructions that has been executed by C program

riscv32-unkown-elf-objdump -SD vmlinux | less

This is the first way I found that could be useful as the command separates the C program and assembly and output them in a mixed form

gdb : info line line_number

This is the second way that I found, that enable the printing of the C program line number, with the starting address and the ending address of the instruction. This is the perfect match of information that I needed to write the debugger as the ending address could be used as a stopping instruction point for the breakpoint implementation.

After trying with the gdb commands and ensures all the functionality, I was having problem in how to write the command line out in C++. Thanks to my colleague Sumia, she told me that we could actually write the command by using simple “system()”. This really solved a lot of my problem, and I decided to use files to proceed with my debugger implementation. By using file functions in C++, I saved the command that need to be executed in the gdb into a file, and opened it using the gdb vmlinux -x file_name command to execute the specific file that contains the command. Then, I save the output of the gdb “info line ” commands into another file, and then extract the output addresses that I needed for each C program line using the regular expression, which can be referred from Sumia’s blog. I found out that the regular expression really helps a lot in the extraction! And finally, I save the addresses into a JSON file to be called in the JavaScript code.

Finally, by using the addresses called, the implementation of the breakpoint can be done by putting simple logic on comparing the current instruction that going to be run. However, the breakpoint implementation is just the starting point of implementing the debugger, I am expecting to face more interesting challenge next week 🙂

You may also like...

Leave a Reply