Hello, dear friend, you can consult us at any time if you have any questions, add WeChat: daixieit

CSCI 2021 Project 3 : Assembly Coding and Debugging

Due : 1 1 :59pm Wed 22-Mar-2023 on Gradescope

Approximately 3.0-4.0% of total grade

Projects are ind iv idual work : no collaboration with other students is allowed. Seek help from course staff if you get stuck for too long.

CODE/TEST DISTRIBUTION : p3-code.z ip

VIDEO OVERVIEW : https ://youtu.be/b iLVZb4VzU8

CHANGELOG :

Wed Mar 15 09 :55 :4 1 AM CDT 2023

The Manual  Inspection  Criteria  for Problem  1 has been  adjusted  so  that  each  function

implementation has 10 points of credit for a total of 60 points for Problem 1. Fr i Mar 3 1 1 :02 : 18 PM CST 2023

Fixed a typo in the code outline for clock_updat_asm.s which included a wrong function name. Added an overview video.

Table of Contents

1. Introduction

2. Download Code and Setup

3. Problem 1 : Clock Display Assembly Functions

3.1. Hand-Code Your Assembly

3.2. General Cautions when coding Assembly

3.3. Register Summary Diagram

3.4. Structure of clock_update_asm.s

3.5. set_tod_from_ports()

3.6. set_display_from_tod

3.7. clock_update

3.8. Grading Criteria for Problem 1

4. Problem 2 : The Binary Bomb

4.1. Quick Links

4.2. Overview

4.3. Machines on which bombs run

4.4. Bomb Download and Setup

4.5. Scoring and Scoreboard (40%)

4.6. WARNING on Downloading Multiple Bombs

4.7. Advice

1 Introduction

This project will feel somewhat familiar in that it is nearly identical to the preceding project : there is a coding problem and a puzzle-solving problem. The major change is that everything is at the assembly level :

Problem 1 re-works the LCD Clock functions from the previous project in x86-64 Assembly rather than C

Problem 2 involves analyzing a binary executable to provide it with the correct input to "defuse" the executable much like the previous project's Puzzlebox problem

Working with assembly will get you a much more acquainted with the low-level details of the x86-64 platform and give you a greater appreciation for "high-level" languages (like C).

2 Download Code and Setup

Download the code pack linked at the top of the page. Unzip this which will create a project folder. Create new files in this folder. Ultimately you will re-zip this folder to submit it.

File                                       State                         Notes

Makefile

Provided

Problem 1 Build file

clock.h

Provided

Problem 1 header file

clock_main.c

Provided

Problem 1 main() function

clock_sim.c

Provided

Problem 1 clock simulator functions

clock_update_asm.s

CREATE

Problem 1 Assembly functions, re-code C in x86-64, ma in f ile to ed it for problem 1

clock_update.c

CREATE

Problem 1 C functions, COPY from Project 2 or see a staff member to discuss

test_clock_update.c

Testing

Problem 1 testing program for clock_update_asm.c

test_clock_update.org

Testing

Problem 1 testing data file

test_hybrid.org

Testing

Problem 1 testing data file for mixed C/Assembly

testy

Testing

Problem 1 test running script

bomb_download.sh

Provided

Problem 2 script used to download a bomb from the server

bombNN.zip

Download

Problem 2 Debugging problem, download from server or use bomb_download.sh

bombNN/

Directory

Created by unzip bombNN.zip and contains the below files

bombNN/bomb.c

Unpack

Problem 2 main() for bomb

bombNN/bomb

Unpack

Problem 2 Executable to debug : this is the important one

bombNN/README

Unpack

Problem 2 Describes "owner" of the bomb

input.txt

Edit

Problem 2 Input for bomb, fill this in to defuse stages

3 Problem 1 : Clock Display Assembly Functions

The functions in this problem are identical to a previous project in which code to support an LCD clock display was written. These functions are :

int set_tod_from_ports (tod_t *tod)

Retrieves value TIME_OF_DAY_PORT and converts this to number of seconds from the beginning of the day with rounding via bit shifts and masking. Then sets the fields of the struct pointed

to by tod to have the correct hours, minutes, seconds, and AM/PM indication. int set_d isplay_from_tod (tod_t tod, int *d isplay)

Given a tod_t struct, reset and alter the bits pointed to by display to cause a proper clock display.

int clock_update ()

Update global CLOCK_DISPLAY_PORT using the TIME_OF_DAY_PORT. Call the previous two functions.

The big change in this iteration will be that the  funct ions  must  be  wr itten  in  x86-64 assembly  code. As C functions each of these is short, up to 85 lines maximum. The assembly versions will be somewhat longer as each C line typically needs 1-4 lines of assembly code to implement fully. Coding these functions  in assembly give you real experience writing working assembly code and working with it in combination with C.

The code setup and tests are mostly ident ical for this problem as for the previous C version of the problem. Refer to original Clock LCD Display Problem description for a broad overview of the simulator and files associated with it.

3.1 Hand-Code Your Assembly

As discussed in class, one can generate assembly code from C code with appropriate compiler flags. This can be useful for getting oriented and as a beginning to the code your assembly versions of the functions. However, this exercise is about writing assembly yourself to gain a deeper understanding of it.

Code that is clearly comp iler-generated w ith no hand cod ing w ill rece ive 0 cred it.

No credit will be given on manual inspection

Penalties will be assessed for Automated Tests which lower credit to 0

Do not let that dissuade you from looking at compiler-generated assembly code from you C solution to the functions. Make sure that you take the following steps which are part of the manual inspection criteria.

Base your Assembly code on your C code

The files to be submitted for this problem include

clock_update.c : C version of the functions

clock_update_asm.s : Assembly version of the functions

Graders may examine these for a correspondence between to the algorithm used in the C version to the Assembly version. Compiler generated assembly often does significant re-arrangements of assembly code with many intermediate labels that hand-written code will not have.

If  you  were  not  able  to  complete  the  C  funct ions  for  the  Project  2  or  were  not conf ident in your solut ions, see a course staff member who w ill help you get them up and runn ing qu ickly.

Annotate your Assembly Thoroughly

Comment your assembly code A LOT. While good C code can be quite self-explanatory with descriptive variable names and clear control structures, assembly is rarely so easy to understand. Include clear commentary on your assembly. This should include

Subdividing functions into smaller blocks with comments describing what the blocks accomplish. Descriptions of which "variables" from the C side are held in which registers.

Descriptions of most assembly lines and their effect on the variables held in the registers. Descriptions of any data such as bitmasks stored in the assembly code.

Use informative label names like .ROUNDING_UP to convey further meaning about what goals certain positions in code are accomplishing.

Use D iv is ion

While it is a slow instruction that is cumbersome to set up, using idivX division instruction is the most human-readable means to compute several results needed in the required functions. Compiler generated code uses many tricks to avoid integer division so a lack of idivX instructions along this line will be a clear sign little effort has been put into the assembly code.

3.2 General Cautions when coding Assembly

1. Get your editor set up to make coding assembly easier. If you are using VS Code, the following video will  show  you  how  to  install  an  extension  to  do  syntax  highlighting  and  block comment/uncomment operations in assembly : https://youtu.be/AgmXUFOEgIw

2. Be disciplined about your register use : comment what "variables" are in which registers as it is up to you to keep track. The #1 advice from past students to future students is "Comment the Crap out of your assembly code" on this project.

3. Be Careful with constants : forgetting a $ in constants will lead to a bare, absolute memory address which will likely segfault your program. Contrast :


# rax = 0

# rax = *(0) : segfault

# bare 0 is memory address 0 - out of bounds


Running  your programs,  assembly  code  included,  in Valgrind  can help  to  identify  these problems. In Valgrind output, look for a line number in the assembly code which has absolute memory addresses or a register that has an invalid address.

4. Recognize that in x86-64 function parameters are passed in registers for up to 6 arguments. These are arranged as follows

1. rdi / edi / di (arg 1)

2. rsi / esi / si (arg 2)

3. rdx / edx / dx (arg 3)

4. rcx / ecx / cx (arg 4)

5. r8 / r8d / r8w (arg 5)

6. r9 / r9d / r9w (arg 6)

and the specific register corresponds to how argument sizes (64 bit args in rdi, 32 bit in edi, etc). The functions you will write have few arguments so they will all be in registers.

5. Use registers sparingly. The following registers (64-bit names) are "scratch" registers or "caller save." Functions may alter them freely (though some may contain function arguments).


rax rcx rdx rdi rsi r8 r9 r10 r11  # Caller save registers


No special actions need to be taken at the end of the function regarding these registers except that rax should contain the function return value.

Remaining registers are "callee save" : if used, their original values must be restored before returning from the function.

rbx rbp r12 r13 r14 r15            # Callee save registers

This is typically done by pushing the callee registers to be used on the stack, using them, them popping them off the stack in reverse order. Avoid this if you can (and you probably can in our case).

6. Be careful to adjust the stack pointer using pushX/popX or subq/addq . Keep in mind the stack must be aligned to 16-byte boundaries for function calls to work correctly. Above all, don't treat rsp as a general purpose register.

3.3 Register Summary Diagram

For reference, here is a picture that appears in the lecture slides that summarizes the names and special uses for the registers in x86-64.

Figure 1 : Summary of general purpose register usages in x86-64.

3.4 Structure of clock_update_asm.s

Below is a rough outline of the structure of required assmebly file. Consider copying this file as you get started and commenting parts of it out as needed.

.text