For reference I am using:
$ /opt/toolchains/x86/djgpp/bin/i586-pc-msdosdjgpp-gcc -v
Using built-in specs.
COLLECT_GCC=/opt/toolchains/x86/djgpp/bin/i586-p […]
Show full quote
$ /opt/toolchains/x86/djgpp/bin/i586-pc-msdosdjgpp-gcc -v
Using built-in specs.
COLLECT_GCC=/opt/toolchains/x86/djgpp/bin/i586-pc-msdosdjgpp-gcc
COLLECT_LTO_WRAPPER=/opt/toolchains/x86/djgpp/bin/../libexec/gcc/i586-pc-msdosdjgpp/12.1.0/lto-wrapper
Target: i586-pc-msdosdjgpp
Configured with: ../gnu/gcc-12.10/configure --target=i586-pc-msdosdjgpp --program-prefix=i586-pc-msdosdjgpp- --prefix=/usr/local/djgpp --disable-nls --disable-plugin --disable-lto --enable-lto --enable-libstdcxx-filesystem-ts --enable-libquadmath-support --with-gmp=/home/vagrant/build-djgpp/build/djcross-gcc-12.1.0/tmpinst --with-mpfr=/home/vagrant/build-djgpp/build/djcross-gcc-12.1.0/tmpinst --with-mpc=/home/vagrant/build-djgpp/build/djcross-gcc-12.1.0/tmpinst --enable-version-specific-runtime-libs --enable-languages=c,c++
Thread model: single
Supported LTO compression algorithms: zlib
gcc version 12.1.0 (GCC)
... my compiler command line is:
gcc -O3 -mtune=i386 -march=i386 -fgnu89-inline -c source1.c -o objfile1.o
... the -fgnu89-inline is purely to have compatability with the Allegro libraries I use, which have older style inlines.
Linker in use is:
$ /opt/toolchains/x86/djgpp/bin/i586-pc-msdosdjgpp-ld -V
GNU ld (GNU Binutils) 2.30
Supported emulations:
i386go32 […]
Show full quote
$ /opt/toolchains/x86/djgpp/bin/i586-pc-msdosdjgpp-ld -V
GNU ld (GNU Binutils) 2.30
Supported emulations:
i386go32
... no special options to ld, just called via the gcc front end as:
gcc -o target.exe objfile1.o objfile2.o libraryX.a libraryY.a
This gets you one of these binaries:
$ file bin/scrolls.exe
bin/scrolls.exe: MS-DOS executable, COFF for MS-DOS, DJGPP go32 DOS extender
I'm not doing any big malloc calls in my code, but the exe is already >1MB, and is happy to run on Dosbox or real >= 386 systems with a copy of cwsdpmi.exe in the same folder. Without it you will get a missing dos extender error when attempting to start the binary.
There are peculiarities when dealing with stuff that lives within the <1MB area (IO ports, video memory ranges, etc), but the last time I checked I think these use cases were documented on the djgpp info pages. For memory mapped devices that live in high memory ranges, there are also some rules that need to be followed (you can't just read/write to them using things like memcpy). It's an edge case (accessing VESA linear frame buffers directly is probably the most common example), but is definitely possible: https://www.delorie.com/djgpp/v2faq/faq18_7.html
BTW, I tend to get pre-built cross-compiler versions of djgpp from: https://github.com/andrewwutw/build-djgpp - these come with gcc, binutils, ld etc... but generally not with make and other supporting tools. I find these are kept much more up to date than the ancient dos-native versions available from djgpp.com; which is probably your only place if you want to run gcc on dos. That's pretty hardcore these days; a cross compiler environment is much more productive.
My collection database and technical wiki:
https://www.target-earth.net