CS61C Summer 2012 Lab 5

Goals

Assemblers output object files. Object files are binary files that contain the machine code and data that corresponds to the assembly code that you (or a compiler) wrote. Several object files can be linked together to form executable files. Object files and executable files can come in several different formats. The most common one is the Executable and Linking Format (ELF). The purpose of the first part of this lab is to familiarize you with the ELF file formats and with assembling and linking files.

The purpose of the second part of this lab is to improve your understanding of Floating Point behavior.

Reading

Initial preparation

All lab exercises should be completed with a partner. Note that the mips-{gcc,objdump,readelf} commands will only run on certain INST computers (the lab computers work just fine).

Copy the directory ~cs61c/labs/05 to an appropriate directory under your home directory.

Info

From class, we know that the toolchain executes the following steps to make your executable:

  1. Compile your source files into assembly (compiler)
  2. Assemble the assembly files into object files (assembler)
  3. Combine your object files into an executable (linker)

Compiler

To create the assembly files which result from the first stage (compilation), you can execute the following:

$ mips-gcc -S input.c

Please note the capital S. This will create a file called input.s which contains the assembly for input.c.

Assembler

To create the object files which result from the second stage (assembly), you can execute either of the following:

$ mips-gcc -c input.c

or:

$ mips-gcc -c input.s

Either command will create an object file called input.o.

Linking

To create the final executable from multiple object files, you can just pass the filenames to gcc like this:

$ mips-gcc input1.o input2.o -o finalexe

This creates an executable called 'finalexe' that results from linking the two given object files.

Unfortunately, mips-gcc will complain if you try to do this right now, so you will not be linking any files yourselves. Instead, we will provide you with the linked executable.

Object Dump

The object files are binary files and not readable in an editor, so we need to make use of another utility to view the contents. To view the contents of an object file, you can use mips-objdump as follows:

$ mips-objdump -x -d input.o > input.o.dump

The -x option tells mips-objdump to print information about all of the sections and the -d option tells it to disassemble the instructions in the .text section. Open the .dump files in your favorite text editor and look them over. There will be many fields that you do not understand but you should recognize certain things. In particular, the part that begins with the label "Sections:" tells you the section name, size of the section, virtual memory address of the section (VMA), and some interesting flags (CONTENTS, ALLOC, etc.)

Additionally, mips-readelf can print out some of the information in the object file in a more human-friendly format. You can do this using:

	$ mips-readelf -a input.o > input.o.readelf

The file command

The name of a file usually gives you a good idea about the type of a file. For example, you know, usually, a file named input.c should be a C program, while a file input.s is usually an assembly program. But what about a file input.o? The Unix command file can report the type of a file. For example, the following command tells you the type of input.o:

$ file input.o

Exercises

Exercise 1: Assembling and Linking

Part 1: Assembling

When the object files are created, the absolute addresses of functions and data are unknown. Instead, relative addresses are specified in the left most column. Create the file stack.o by the command:

$ mips-gcc -c stack.c

Then create an object dump of the resulting stack.o by:

$ mips-objdump -x -d stack.o > stack.o.dump

Inspect the file stack.o.dump in your favorite text editor. What are the addresses of the functions IsEmpty, Push, and Pop in stack.o? Are these addresses relative or absolute addresses? Why?

Create an object dump of teststack.o following similar steps as above. Look at teststack.o.dump. The main function calls several functions that are in the stack.o object file. What instruction does it use to call the functions found in stack.o? What is the significance of the line following each of these function calls containing the word R_MIPS_26? (hint: it is used in the linking process)

Part 2: Linking

Unfortunately, mips-gcc has problems with linking files right now. So instead of linking stack.o and teststack.o yourselves, we have done it for you. linked.o is the resulting file after linking the two files mentioned above. Because linked.o does not have any unresolved references, we call it an executable. Like the other object files, opening it in a text editor is not very revealing. Instead, dump it using mips-objdump and open the resulting file. Note that there are MANY symbols in this file that we did not define. These are all linked in by default. You may ignore these symbols.

What are the addresses of the functions isEmpty, Push, and Pop in the executable? Are these addresses relative or absolute addresses? How do you know?

What is the address of the structure ourStack in the final executable? What section (.data, .text, or another section) was the global vraiable ourStack placed in?

Checkoff

Exercise 2: Floating Point

Part 1: Roundoff

Find a positive floating point value x, for which x+1.0=x due to roundoff issues. Verify your result in fp.s. Now find the smallest positive floating point value x for which x+1.0=x. Determine the stored exponent and fraction for x (either on the computer or on paper).

Note: fp.s will allow you to experiment with adding floating point values. It prints out the floating point values of x and x+1.0 and their hexadecimal representations.

Part 2: Associativity

Using what you have learned from the last part, determine three positive floating point values such that adding these numbers in a different order can yield a different result. Write some code into fp.s to show this (print out 2 different sums from the same 3 floating point numbers).This shows that for three floating point numbers a, b, and c, a+b+c does not necessarily equal c+b+a. (Hint: Experiment with adding up different amounts of the x value you determined in part 3, and the value 1.0).

Checkoff