The goal of the project is to gain more familiarity with C by writing two utility functions that will be useful for processing the input for a disassembler (the subject of a future project). You will also develop test cases to test your two functions. The actual specifications for the program appear below in the Description section.
You may work on this project individually or in groups of two.
Clone the DisUtil repository from Kit. This repository has a number of starter files in it. You will be modifying some, and using others.
Files You Will Modify:
Other Useful Files:
- disUtilDriver.c: test driver - contains the
main
function that callsverifyMIPSInstruction
and, if a line of code has the correct format, callstestBinToDec
to test thebinToDec
function. (A test driver is amain
function written solely to "drive" tests of other functions.) The driver needs additional calls totestBinToDec
to testbinToDec
more thoroughly.- verifyMIPSInstruction.c: one of the two incomplete utility functions that are the focus of this assignment
- binToDec.c: the other incomplete utility function
- testfileStarter.txt: a file that has some sample input for testing
verifyMIPSInstruction
but needs more test data
- Makefile: specifies how to compile both this program and the future disassembler program
- disUtil.h (a header file for this program)
- process_arguments.c (function that processes command-line arguments passed to the
main
function; used in test driver; has an associated process_arguments.h header file)- same.c (defines a constant called SAME used by process_arguments; has an associated same.h header file)
- printFuncs.h (a header file for the following two print functions)
- printDebug.c (prints debugging messages; used in test driver)
- printError.c (prints error messages; used in
verifyMIPSInstruction
)
Running the Starter Code:
The provided code should compile and run, although it does not yet have the functionality this program should have.
The Makefile
contains information for the make
command, telling it how to compile this program (and the future
disassembler program). To compile this program,
type make
at a command-line
prompt. If you are using an IDE, your IDE may be able to use
makefiles.
The make
command will create a compiled executable called
disUtil
.
You can run your program by typing its name at the command line. It
takes two optional parameters: a filename and an integer 1 if you want
to turn on debugging.
If you run the program with the minimalist starter test file
provided above, you'll see that for now it just prints a 5-character
substring of each line in the test file. (To start with, the program will
claim that each substring represents the value 0, regardless of what the
value really is.)
./disUtil testfileStarter.txt run the program with the given test file ./disUtil testfileStarter.txt 1 ... and with debugging on
You can modify the
testfileStarter.txt
test file and
run the program again to see how its behavior changes. (The test file is just
made of plain ASCII text, so you can modify it with any program that
allows you to edit plain text files. Note that C source files are also
plain text files, so you can use whatever you use to edit C source files to
also edit test files.) Test the program with and without the second
parameter, 1
.
The input file for our future disassembler will contain strings representing MIPS machine code, one instruction per line. Actual MIPS instructions would be stored in 32-bit integers; instead, our file will contain lines of 32 characters ('0' or '1'), where each line represents the 32 bits in a machine language MIPS instruction ("pseudo-binary").
Example input line:
01010101000000000000010101010110
If that string represented 4 8-bit positive integers, we could interpret it
as representing the 4 decimal numbers 85, 0, 5, 86.
(01010101 00000000 00000101 01010110
)
The purpose of the functions you are completing in this project is to read in the strings representing MIPS machine code, make sure they are valid, and decode string subsets in decimal format.
The main
function in the test driver
(disUtilDriver.c
)
currently reads lines in from a file until reaching the end of the file.
If the line ends with a newline, the program
strips the newline from the string by replacing it with a null byte.
It then calls verifyMIPSInstruction
(currently just a
skeleton) to verify that the string format is appropriate for a
MIPS machine code instruction, or to print an error otherwise.
If the instruction format is valid, main
calls
testBinToDec
, which in turn calls binToDec
(which
is also currently just a stub).
You can leave main
as it is for now, while you complete and test
verifyMIPSInstruction
.
Once you have completed the binToDec
function, you will need
to modify the main
function to call
testBinToDec
several times with various parameters, to test
binToDec
effectively and print the results. (Currently
main
only calls testBinToDec
once.)
The verifyMIPSInstruction
function should verify that the
string provided to it is 32 characters long and that
the characters in the string are all 0's or 1's (character
'0' or character '1'). If the instruction is valid,
verifyMIPSInstruction
should return 1. Otherwise,
it should print an error message indicating the error and the line
on which it occurred before returning 0.
Test your modifications before going further by adding appropriate data to the existing test file or by creating new data files. Run the program with debugging turned on to see your test results. (See the section above on running the program.) Be sure to include tests cases that exercise every path through your code as well as all appropriate boundary conditions (e.g., empty lines, too-long lines, invalid data in the first / last positions, etc.).
Ensuring Quality
As specified in the syllabus, your program should adhere to the Kalamazoo College CS Program Style Guide and Documentation Standards, including use of the Braces Line Up style pattern.
The
Makefile
I have provided specifies a set of compiler options that will help you catch many errors at compile time. These options generate warnings about questionable constructions that often indicate programmer confusion or actual logic errors. You may have to make adjustments to theMakefile
, though, if the specific options or option names for your compiler are somewhat different.
The binToDec
function should interpret a substring of
characters in an array as a binary number, convert it to an integer,
and return the integer. The first parameter is the
array of characters; the second and third parameters are the beginning
index and ending index of the substring. For example, assume A is a
character array that contains the following characters.
1 0 1 1 0 1 0 0 1The call
binToDec(A, 2, 5)
should convert the string of binary
digits '1' '1' '0' '1'
(the substring A[2] - A[5], inclusive) to the
integer 13
and return it. One approach, using an algorithm for
converting a binary number to a decimal number, involves evaluating the
binary value from the least significant digit to the most significant
digit, adding in (or not) the appropriate power of two to the decimal
value. Rather than calculating the power of two for each digit,
you can store the power of two in a variable and multiply it by two
when you go to the next digit. (What should the power-of-two variable
be initialized to for the least significant digit?)
To test binToDec
thoroughly, you should modify
main
to call testBinToDec
in a number of
different ways, rather than just once. Think particularly about what kinds
of boundary conditions you should test for.
Alternatives: There's a similarly efficient algorithm that processes the binary digits left-to-right, multiplying the decimal value by two each time it goes on to the next binary digit. Or, if you are interested in using the C left-shift operator, you can use that instead.
Your submission should contain;
Your program should also work with other input files that may be
developed for consistent grading.
(Note:
It is a good idea to run
make clean
in the directory before submitting; this
will remove the machine-specific executable and intermediate "object
code" files, since your code will have to be re-compiled on the grader's
machine anyway.)
Rubric:
The rubric for grading this project is based on the following general categories.
Compiles and runs 1 pt `verifyMIPSInstruction` functionality 1 pt `binToDec` functionality 1 pt Comments, Documentation, Clean Programming Style 1 pt Test Cases for `verifyMIPSInstruction` (based on data file) 1 pt Test Cases for `binToDec` (based on calls to testBinToDec) 1 pt Reasonable efficiency 1 pt
Note that developing a thorough test suite is an important aspect of this assignment.