4

I have this project: Compile a C/C++ program to a CP/M-86 executable (CMD-file) with a modern compiler. The target architecture is 16-bit x86. You may think I am crazy but I am doing this for fun and to learn about CP/M-86 and low level x86 programming in general.

I have little to no knowledge about x86 assembler programming but I have done a "Hello World" example that I can use ASM86 and GENCMD to generate a CMD-file. And it works. ASM86 is an assembler program for CP/M-86 that will generate a H86-file, that is (as far as I understand) Intel Hex Code. GENCMD reads this HEX-file and creates the CMD executable. CMD is the CP/M-86 equivalent of EXE executables know from DOS and Windows.

I have a "modern" tool that will compile and link 16-bit x86 NASM code and output a working CMD that I can run on my CP/M-86 machine - build completely on my Linux machine. However, I need a C/C++ compiler that will create this compatible NASM code. Or maybe some kind of a flat binary that easily converts into a CMD.

The second thing is system calls. I can probably make a print-like function using inline assembly and test that. For now I just want to compile this program, that does not do anything (and hopefully does not do any system calls?):

int main()
{
    return 0;
}

C compilers do exist for CP/M-86 but these are very, very old and pretty much unusable. Especially if I want to do C++, like I really want to. So, it has to be done with a modern compiler like gcc or llvm-clang or something like that.

A last resort could be compiling a 16-bit DOS-compatible EXE and then do some system call translation... but that will be kind of cheating and still be quite time consuming.

How can I reach my goal? Thanks in advance. Any advice is appreciated :-)

Psychonaut
  • 859
  • 8
  • 22
pvh1987
  • 621
  • 5
  • 8
  • 12
  • 2
    [Watcom](http://www.openwatcom.org/index.php/Main_Page) is still maintained and supports generating 16 bit executables, might want to check it out. – Captain Obvlious Apr 16 '14 at 20:44
  • There are C subsets that compile to very small processors. MIT's media labs used some of them. – Jiminion Apr 16 '14 at 20:55
  • 1
    Do you really mean CP/M x86, or DOS? CP/M has been dead for many many years. – Mark Ransom Apr 16 '14 at 21:15
  • @MarkRansom: from memory, but (fortunately!) confirmed by Wikipedia: [CMD was for CP/M what EXE is for DOS](http://en.wikipedia.org/wiki/CMD_file_(CP/M)). Interesting assignment -- I wonder what the background idea is. CP/M is so old, it was already on its way out when I started. – Jongware Apr 16 '14 at 21:44
  • @Jongware that just leads me to believe that the goals of "modern C++ compiler" and "CP/M" are completely incompatible. – Mark Ransom Apr 16 '14 at 22:43
  • Yes, I mean CP/M-86, not DOS. More precisely Concurrent CP/M-86 but I don't think I want to use any advanced "concurrent" features. Actually CCP/M-86 was far more advanced than DOS, especially at its time, despite the "flat" filesystem. I just made an article on my website that explains the NASM "tool" that generates a CMD-file. Take a look at http://rc700.dk/guides/Hello_World_in_ASM86_and_NASM.php (later half of the article). I just need a C++ compiler that will generate compatible NASM code. Thanks for the advice so far :-) – pvh1987 Apr 16 '14 at 23:21

1 Answers1

1

How can I reach my goal?

If you have working C compiler, then I think llvm-cbe is what you are looking for. This is backend for clang-llvm (and any llvm compilers I think), it take llvm intermediate representation (IR) and convert it to C. So you can compile your c++17 code for any machine that has c compiler.

About

int main()
{
    return 0;
}

On linux this code will call open/close (and other file related stuff), because of libc work with stdout/stderr/stdin, also it call exit_group, I not sure about ms-dos, but it should it least somehow report exit code to system.

fghj
  • 8,898
  • 4
  • 28
  • 56