Cross compiling for MS-DOS (DJGPP) from OS X

So building on DOOM, I thought I’d try to build a djgpp cross compiler from my main OS X box, as compiling under DOSBox is… just too slow. Luckily Delorie has a page on building a cross compiler.

I started out with binutils-2.9.1, just as he does, with a few things thrown in…

First I had to run configure like this, as OS X didn’t exist back then, let alone x64 cpu’s..
./configure --target=i586-pc-msdosdjgpp --host=i386-netbsd --prefix=/usr/local/djgpp
Next the following error is thrown…

strerror.c:463: error: conflicting type qualifiers for ‘sys_nerr’

So I just edited libiberty/strerror.c, and commented out the following line.

Next up was a strange error in gas/targ-cpu.h

targ-cpu.h:374: error: array type has incomplete element type
targ-cpu.h:378: error: previous declaration of ‘flag_16bit_code’ was here

I simply commented out the lines.

Then later while compiling gas/write.c it bombs out because of an undefined type.. One of which was commented out in targ-cpu.h . The easiest fix is to go to the start of the relax_align procedure and just add in the definition:

extern const struct relax_type md_relax_table[];

Next up was gcc. I couldn’t get 2.8.1 to build, instead I built gcc-2.95.3.

I had to configure gcc like this:
./configure --target=i586-pc-msdosdjgpp --host=i386-netbsd --prefix=/usr/local/djgpp
And it threw the same error as binutils… with the same fix (commenting out the line in libiberty/strerror.c).

strerror.c:465: error: conflicting type qualifiers for ‘sys_nerr’

I also had an error pop up like this:

./config/i386/i386.c:142:22: error: macro “strcat” requires 2 arguments

And again I just commented it out.

Under OSX the makeinfo parts crashed, so I simply removed them from the makefile. With a little more tweaking the cross compiler was ready!


The cool thing is that now I can run make with the -j4 flags allowing gcc to run on each of the cpu cores letting me build doom in under 3 seconds!

i586-pc-msdosdjgpp-gcc -O2 -DNORMALUNIX dos/doomdef.o dos/doomstat.o dos/dstrings.o dos/i_system.o dos/i_sound.o dos/i_video.o dos/i_net.o dos/tables.o dos/f_finale.o dos/f_wipe.o dos/d_main.o dos/d_net.o dos/d_items.o dos/g_game.o dos/m_menu.o dos/m_misc.o dos/m_argv.o dos/m_bbox.o dos/m_fixed.o dos/m_swap.o dos/m_cheat.o dos/m_random.o dos/am_map.o dos/p_ceilng.o dos/p_doors.o dos/p_enemy.o dos/p_floor.o dos/p_inter.o dos/p_lights.o dos/p_map.o dos/p_maputl.o dos/p_plats.o dos/p_pspr.o dos/p_setup.o dos/p_sight.o dos/p_spec.o dos/p_switch.o dos/p_mobj.o dos/p_telept.o dos/p_tick.o dos/p_saveg.o dos/p_user.o dos/r_bsp.o dos/r_data.o dos/r_draw.o dos/r_main.o dos/r_plane.o dos/r_segs.o dos/r_sky.o dos/r_things.o dos/w_wad.o dos/wi_stuff.o dos/v_video.o dos/st_lib.o dos/st_stuff.o dos/hu_stuff.o dos/hu_lib.o dos/s_sound.o dos/z_zone.o dos/info.o dos/sounds.o dos/i_main.o \
-o dos/dosdoom

real 0m1.174s
user 0m2.626s
sys 0m0.679s

How’s that for fast?

For any curious OS X 64bit users out there you can download my binary toolchain here.

I would imagine that if you stuck with versions of binutils & gcc that build on your platform you too should be able to build a MS-DOS DJGPP cross compiler. And there is nothing like native 64bit tools for building for DOSBox… Oh and DOOM runs just fine, although I guess screen shots of the cross compiled exe is… redundant.

7 thoughts on “Cross compiling for MS-DOS (DJGPP) from OS X

  1. Interesting in that I just tried cross compiling djgpp myself, only two days after your post. I earlier built an i586-elf version and it compiled just fine. Tried djgpp and it bombs with "configure: error: cannot compute suffix of object files: cannot compile" resulting from a config step trying to determoine gcc version.

    This was with gcc-4.5.1 and binutils-2.20, so a little different.

  2. yeah I find older gcc's easier to deal with…. then again it may very well be me.

    Then again my favorite version is 2.5.8 …. lol

    what platform are you cross compiling from?

    I do have to say, that once it's working it's sooooo worth it, as things build on modern machines vs antiques like MS-DOS… but you can't beat the size of a MS-DOS install!!!!!

  3. The “ar” program in the binary toolchain seems not work?
    I tried:

    # create an empty file x.c
    touch x.c
    /usr/local/bin/i586-pc-msdosdjgpp-gcc -o x.o -c x.c
    /usr/local/bin/i586-pc-msdosdjgpp-ar cru x.a x.o

    will print:

    Abort trap: 6

    I run it on MacBook Pro Retina, OSX 10.8.4

    run uname -a:
    Darwin Andrew-MBPR.local 12.4.0 Darwin Kernel Version 12.4.0: Wed May 1 17:57:12 PDT 2013; root:xnu-2050.24.15~1/RELEASE_X86_64 x86_64

    • Hmm it’s killing itself…

      #0 0x00007fff8df1cd46 in __kill ()
      #1 0x00007fff86992ec0 in __abort ()
      #2 0x00007fff8695477d in __chk_fail ()
      #3 0x00007fff86954958 in __sprintf_chk ()
      #4 0x000000010000a3dd in coff_write_armap ()
      #5 0x0000000100009b97 in _bfd_compute_and_write_armap ()
      #6 0x00000001000092d0 in _bfd_write_archive_contents ()
      #7 0x0000000100011e3e in bfd_close ()
      #8 0x0000000100004a9d in write_archive ()
      #9 0x0000000100005165 in replace_members ()
      #10 0x0000000100004325 in main ()

      I don’t know offhand beyond this, maybe rebuild the toolchain with the new compiler in 10.8 ..?

Leave a Reply

Your email address will not be published. Required fields are marked *

This site uses Akismet to reduce spam. Learn how your comment data is processed.