Example: Use of Predefined Macros in OS/2
version() is a routine from
UnZip that
prints as much compilation info as is known, based entirely on predefined
compiler macros. Its output looks something like this:
Compiled with emx+gcc 2.5.8 for OS/2 2.x or 3.x (32-bit) on Jan 27 1995.
In the listing below, note that the Borland version numbers are probably
wrong; they're based on the MS-DOS version of the compiler, which is why
the debugging section is included at the end. The value of the
__WATCOM__ variable is unknown, too. (Any
and all information appreciated; please mail it to
newt@pobox.com.)
OS/2 version() routine:
void version()
{
int len;
#if defined(__IBMC__) || defined(__WATCOMC__) || defined(_MSC_VER)
char buf[80];
#endif
len = sprintf((char *)slide, "Compiled with %s%s for %s%s%s%s.\n\n",
#ifdef __GNUC__
# ifdef __EMX__ /* __EMX__ is defined as "1" only (sigh) */
"emx+gcc ", __VERSION__,
# else
"gcc/2 ", __VERSION__,
# endif
#else
#ifdef __IBMC__
"IBM C Set/2", (sprintf(buf, " %d.%02d", __IBMC__/100,__IBMC__%100), buf),
#else
#ifdef __WATCOMC__
"Watcom C", (sprintf(buf, " (__WATCOMC__ = %d)", __WATCOMC__), buf),
#else
#ifdef __TURBOC__
# ifdef __BORLANDC__
"Borland C++",
# if (__BORLANDC__ < 0x0200)
" 1.0",
# else
# if (__BORLANDC__ == 0x0200)
" 2.0",
# else
# if (__BORLANDC__ == 0x0400)
" 3.0",
# else
# if (__BORLANDC__ == 0x0410)
" 3.1",
# else
# if (__BORLANDC__ == 0x0452)
" 4.0",
# else /* these two are guesses based on DOS version */
# if (__BORLANDC__ == 0x0460)
" 4.5",
# else
" later than 4.5",
# endif
# endif
# endif
# endif
# endif
# endif
# else
"Turbo C",
# if (__TURBOC__ >= 661)
"++ 1.0 or later",
# else
# if (__TURBOC__ == 661)
" 3.0?",
# else
# if (__TURBOC__ == 397)
" 2.0",
# else
" 1.0 or 1.5?",
# endif
# endif
# endif
# endif
#else
#ifdef MSC
"Microsoft C ",
# ifdef _MSC_VER
(sprintf(buf, "%d.%02d", _MSC_VER/100, _MSC_VER%100), buf),
# else
"5.1 or earlier",
# endif
#else
"unknown compiler", "",
#endif /* MSC */
#endif /* __TURBOC__ */
#endif /* __WATCOMC__ */
#endif /* __IBMC__ */
#endif /* __GNUC__ */
"OS/2",
/* GRR: does IBM C/2 identify itself as IBM rather than Microsoft? */
#if (defined(MSC) || (defined(__WATCOMC__) && !defined(__386__)))
# if defined(M_I86HM) || defined(__HUGE__)
" (16-bit, huge)",
# else
# if defined(M_I86LM) || defined(__LARGE__)
" (16-bit, large)",
# else
# if defined(M_I86MM) || defined(__MEDIUM__)
" (16-bit, medium)",
# else
# if defined(M_I86CM) || defined(__COMPACT__)
" (16-bit, compact)",
# else
# if defined(M_I86SM) || defined(__SMALL__)
" (16-bit, small)",
# else
# if defined(M_I86TM) || defined(__TINY__)
" (16-bit, tiny)",
# else
" (16-bit)",
# endif
# endif
# endif
# endif
# endif
# endif
#else
" 2.x or 3.x (32-bit)",
#endif
#ifdef __DATE__
" on ", __DATE__
#else
"", ""
#endif
);
message(slide, (ulg)len, 0); /* MSC can't handle huge macro expansions */
/* temporary debugging code for Borland compilers only */
#ifdef __TURBOC__
Info(slide, 0, ((char *)slide, "\t(__TURBOC__ = 0x%04x = %d)\n", __TURBOC__,
__TURBOC__));
#ifdef __BORLANDC__
Info(slide, 0, ((char *)slide, "\t(__BORLANDC__ = 0x%04x)\n",__BORLANDC__));
#else
Info(slide, 0, ((char *)slide, "\tdebug(__BORLANDC__ not defined)\n"));
#endif
#ifdef __TCPLUSPLUS__
Info(slide, 0, ((char *)slide, "\t(__TCPLUSPLUS__ = 0x%04x)\n",
__TCPLUSPLUS__));
#else
Info(slide, 0, ((char *)slide, "\tdebug(__TCPLUSPLUS__ not defined)\n"));
#endif
#ifdef __BCPLUSPLUS__
Info(slide, 0, ((char *)slide, "\t(__BCPLUSPLUS__ = 0x%04x)\n\n",
__BCPLUSPLUS__));
#else
Info(slide, 0, ((char *)slide, "\tdebug(__BCPLUSPLUS__ not defined)\n\n"));
#endif
#endif /* __TURBOC__ */
} /* end function version() */
Click here to see UnZip's multi-compiler OS/2
makefile.
Click here to return to the February 1995 Tip o' the
Month.
Last modified 12 August 2000 by
newt@pobox.com , you betcha.