This project demonstrates how to draw a horizontal line on the Hack computer screen using both Hack assembly and C.
It includes low-level bitwise address computations and pixel manipulation in simulated screen memory.
The Hack computer’s display is a bitmap memory region starting at address 16384 (SCREEN).
Each word (16 bits) represents 16 horizontal pixels, and the screen is 512×256 pixels, meaning each row has 32 words.
This project draws a horizontal line from coordinates (x1, y) to (x2, y) by:
- Computing the start and end word addresses for a given row.
- Generating bit masks to fill pixels between
x1andx2. - Writing to the Hack’s screen memory directly.
You’ll find both:
/assembly_code→ Hack assembly version/c_code→ equivalent C implementation for clarity and testing
Each pixel is stored in memory at:
| Register | Purpose |
|---|---|
R0 |
y-coordinate |
R1 |
x1 (becomes x1 mod 16 after division) |
R2 |
x2 (becomes x2 mod 16 after division) |
R3 |
color (1 = white, 0 = black) |
R4 |
start word address |
R5 |
end word address |
R6 |
loop counter |
R7 |
temporary register (bit mask) |
- Multiply
yby 32 to get the row offset. - Divide
x1andx2by 16 to find the start and end words. - Add
SCREENbase address to get absolute memory addresses. - Fill bits between
x1andx2usingset_pixel()function.
The Hack Assembly implementation should be tested inside the Nand2Tetris CPU emulator.
Version 1 contains more optimized however not memory saving approach, and Version 2 uses less registers, however speed is compromised.
The corresponding registers for x1, x2, y and color (1 for black, 0 for white) should be set.
The C version emulates Hack screen memory in an array and applies the same bitwise logic:
#define WIDTH 512
#define HEIGHT 256
#define WORDS_PR (WIDTH / 16)
#define SIZE (HEIGHT * WORDS_PR)
extern unsigned short screen[SIZE]; // 8192 words, like in hack
void clear_image(unsigned char color);
void set_pixel(int x, int y, unsigned char color);
void horizontal_line(int y, int x1, int x2, unsigned char color);
void vertical_line(int y, int x1, int x2, unsigned char color);
void write_bmp(const char *filename);To test the C version simply compile the project:
make #compile the project
./draw_test #run the program
display output.bmp #display the result- Nand2Tetris Hack Computer
- CPU Emulator
- GCC for the C version