Comparing writing “Hello World” using DDT versus ASM in CP/M#

Introduction#

Using DDT, one can use the inline assembler to write small programs. Besides DDT, CP/M also offers ASM to assemble a bit more advanced programs. In this blogpost, I will use both programs to write a small “Hello World” program and compare the workflow between the two procedures.

../_images/assembly-retro.jpg

Dynamic Debugging Tool#

To write a small “Hello World” program using DDT, open up the program and run A100 to start the inline assembler at memory position 0x100.

Type the following assembly instructions

mvi c,9
lxi d,109
call 5
ret

After writing ret, hit the return key twice to return to the command line of DDT. Next, we run s109 to modify the memory starting at location 0x109. We enter the following values

48
65
6c
6c
6f
20
57
6f
72
6c
64
21
24
00

which corresponds to the string “Hello World!$” in ASCII-encoding, followed by a zero. Note that the ‘$’ acts as the terminating character and ‘0x00’ serves as a “padding” character. Feel free to leave it out though, it is not being used.

Note

If you would like to run this program from inside DDT, do not forget to change ret to rst 7. Here, we use ret such that we can run this program from the command prompt.

At this point, the program resides in memory. To exit DDT, type g0. We return to the CP/M prompt A>. Here, we type

save 1 hello.com

which will save a single page of memory (256 bytes), starting at location 0x100 to the file HELLO.COM. We can now execute the program by simply running hello from the command line which will show the “Hello World!” response being written to the terminal.

ASM#

We are going to perform the same task as shown before, but now using ASM. First, let us clean up the previous HELLO.COM file by running

era hello.com

Next, we open the line editor ED. In its command prompt, type I to enter insert mode and we write the following lines of assembly code.

ORG 100H
MVI C,9
LXI D,MSG
CALL 5
RET

MSG:
  DB 'Hello World!$',0

After typing the 0, press CTRL+Z to write the end-of-file marker. You will at this point return to the command line of ED. Type E to exit and save the file to floppy disk.

Warning

It is important that you use single quotation marks to encapsulate the “Hello World!” string. Double quotation marks will not work.

From the CP/M command prompt, you can run

type hello.asm

to see the contents of the file. It should reflect the assembly code as typed in via DDT. At this point, we are ready to start assembling the program. To do so, run

asm hello

Warning

Do not write any extension after “hello” in the command above. In fact, writing asm hello.asm will throw an error message.

The output of the command above should yield

CP/M ASSEMBLER - VER 2.0
0117
000H USE FACTOR
END OF ASSEMBLY

which shows that the final address written to is 0x117. At this point, three files are generated:

  • HELLO.PRN: A print or listing file containing a human-readable listing of the assembly source code along with the corresponding machine code and addresses. This file can be printed using type hello.prn.

  • HELLO.HEX: Intel HEX file containing an ASCII-encoded hexadecimal representation of the machine code. This file can printed using type hello.hex.

  • HELLO.OBJ: An object file containing the machine code generated by the assembler. This can be used in the next step to generate an executable .COM file.

Hint

It is insightful to view the contents of HELLO.PRN and HELLO.HEX using the TYPE command.

Finally, we are going to produce a .COM file by running

load hello

which will yield the following output

FIRST ADDRESS 0100
LAST  ADDRESS 0116
BYTES READ    0017
RECORDS WRITTEN 01

At this point, the file HELLO.COM is created and one can launch it by running hello from the CP/M prompt.

Comparison and conclusion#

For creating quick-and-dirty small assembly programs, I prefer to use DDT as the program that is being written can be tested from the DDT environment. The biggest downside of the inline-assembler however is that there is no functionality for labels and one has to do a bit of mental arithmetics to figure out all the addresses.

For larger programs, ASM in conjunction with ED is the way to go, although ED is not a user-friendly editor. In ASM, labels are supported by which part of job of calculating the addresses can be delegated to the program.