1. Goals for this week
-
Compilation steps and practice with IA32 assembly
-
Disassemble binary executables with objdump and gdb.
-
ALU condition codes (flags) in Lab assignment 3.
-
Explore real computer hardware.
2. Handy References
-
GDB References
-
Tools for examining phases of compiling and running C programs
-
GDB Guide for more information about using
gdb
andddd
(see the Assembly code debugging section).
-
-
Logisim References
3. Getting your code
Your warm-up code for this week is pushed to your Lab3 repo. To make sure you have the warm-up code:
-
cd into your
cs31/labs
subdirectory
cd ~/cs31/labs
cd Lab3-user1-user2/warmup-code/
git pull
ls
# you should see these additional
# files in your warmup-code folder
Makefile conditions.c simpleops.c truthtable.txt
4. Using gcc to generate IA32 assembly
Let’s try out gcc to build IA32 assembly files and .o
files and look at the results. Open up simpleops.c
.
We are going to look at how to use gcc to create an assembly version of
this file, and how to create a object .o
file, and how to examine its
contents. We are also going to look at how to used gdb to see the assembly
code and to step through the execution of individual instructions.
If you open up the Makefile you can see the rules for building .s
, .o
and executable files from simpleops.c
. We will be compiling the 32-bit
version of instructions, so we will use the -m32
flag.
gcc -m32 -S simpleops.c # just runs the assembler to create a .s text file
gcc -m32 -c simpleops.s # compiles to a relocatable object binary file (.o)
gcc -m32 -o simpleops simpleops.o # creates a 32-bit executable file
To see the machine code and assembly code mappings in the .o
file:
objdump -d simpleops.o
You can compare this to the assembly file:
cat simpleops.s
5. gdb disassemble
Next, let’s try disassembling code using gdb. The gdb debugger supports debugging at the assembly code level by stepping through the execution of individual IA32 instructions, examing register values, and disassembing functions. Today, we are just going to look at the disassemble functionality of gdb. We will revisit debugging at the assembly code level over the next few weeks.
gdb ./simpleops
(gdb) break main
(gdb) run
In gdb you can disassemble code using the disass
command:
(gdb) disass main
I’ll show you a few other gdb commands for debugging at the assembly code level, but we will revisit this in later weeks.
(gdb) break main (gdb) run (gdb) disass (gdb) ni # execute next instruction (gdb) disass (gdb) ni # execute a few more ... (gdb) disass (gdb) print $eax # print out the value stored in CPU register eax
I’ll show you a few other gdb commands for debugging at the assembly code
When we are done, entry quit
to quit the gdb session:
(gdb) quit
6. The Lab 3 ALU Flags
Next, let’s talk about the flags (the condition codes) part of the ALU lab. We will do this in the context of examping some example operations, and considering how the flags should be set
Let’s look at the conditions.c
program:
$ vim conditions.c
This program includes some example arithmetic and bit-wise operations, operations that your ALU will implement. We will use it to reason about the ALU flags part of {labassn}[Lab 3].
Recall the flags (or condition codes) are used encode state about the result of an ALU operation. For the ALU you are building in logism, the flags are defined as the following:
EF: Is set (1), if the two operands are equal. Otherwise, it is clear (0). ZF: Is set, if the computed result is zero. SF: Is set, if the computed result's most significant bit is set (i.e., it's negative if interpreted as signed). CF: Is set, if the computed result caused an overflow, when interpreted as an unsigned operation. OF: Is set, if the computed result caused an overflow, when interpreted as a signed operation.
Let’s compile conditions.c
and run the program and look at some of the
example operations and think about what the flag settings should be
for these examples.
$ make
$ ./conditions
ADD
---
unsigned 2147483647 + 4 is 2147483651 (0x80000003)
signed 2147483647 + 4 is -2147483645 (0x80000003)
SUB
---
unsigned 3 - 5 is 4294967294 (0xfffffffe)
signed 3 - 5 is -2 (0xfffffffe)
...
The first couple examples are ADD and SUB operations. Think about
the value of each of the 5 flags for each of these example operations.
In other words, which flags should be set (1) and which should be clear (0)
as the result of adding 2147483647 + 4
? And which should be set and
which should be clear as the result of 3 - 5
?
Next, let’s consider the OR and AND examples, and how the flags should be set for these examples.
7. Computer Teardown
You’ve each been assigned to a group. Each group is assigned a computer that you can take apart.
The goal is to find as many parts of a computer as you can. We have tools available to remove parts from your computer, and here are a few links that may be helpful:
Try to identify some of the following:
-
the processor
-
RAM memory card(s)
-
the backplane
-
the chipset, PCI and Memory buses
-
expansion slots
-
the hard drive (what’s inside?)
-
the network interface card (NIC)
-
the graphics card
-
where do different ports go?
-
… then see what else you can find
Before leaving lab, please clean-up all spare parts, screws, etc. that you have removed by putting them in the boxes. You do not need to put the cases in the boxes, just all loose parts. Cases can be left on the desks. CPU thermal glue is toxic, so just to be safe I recommend washing your hands after lab today. |