[net.lang.c] CPP symbol usage and portability

rcd@opus.UUCP (Dick Dunn) (10/19/84)

This took off from one of the CPP predefined symbol listings...
> 	#ifdef SYSTEM_X
> 		... Way to do it on sys X ...
> 	#else
> 		... Way to do it somewhere else ...
> 	#endif
> 
> Of course, this breaks when a program is spread to more that a few machines.

There's a way around that.  However, it's made messy by the fact that there
isn't an else-if construct for the preprocessor.  You build a sequence of
tests for each machine and a final branch, taken only when none of the
others are, either gives the default code or has a line of informative non-
code (to generate a compilation error) instructing you what you must fix:
	#ifdef SYS_X
		...code for X
	#else
	#ifdef SYS_Y
		...code for Y
	#else
		***Replace this line with code for mumble on your machine.
	#endif
	#endif

> What we really need here is something quite different: a set of #defines
> telling us what *features* are available on the target machine...

You can get some fair part of this if you have a common header file for
your code which has something like:
	#ifdef	SYS_X
	#define	FEATURE1
	#define FEATURE3
	#endif

	#ifdef	SYS_Y
	#define	FEATURE2
	#define	FEATURE3

A lot of this depends on how much you are worrying about portability / 
adaptability.
-- 
Dick Dunn	{hao,ucbvax,allegra}!nbires!rcd		(303)444-5710 x3086
   ...Lately it occurs to me what a long, strange trip it's been.

lwall@sdcrdcf.UUCP (Larry Wall) (10/22/84)

In article <915@opus.UUCP> rcd@opus.UUCP (Dick Dunn) writes:
> > What we really need here is something quite different: a set of #defines
> > telling us what *features* are available on the target machine...
>
>You can get some fair part of this if you have a common header file for
>your code which has something like:
>	#ifdef	SYS_X
>	#define	FEATURE1
>	#define FEATURE3
>	#endif
>
>	#ifdef	SYS_Y
>	#define	FEATURE2
>	#define	FEATURE3
>
>A lot of this depends on how much you are worrying about portability / 
>adaptability.

The trouble with this is that systems are multiplying out there faster than
we can keep track of them, and when your program shows up on a system that
you didn't know about, it will get only the default symbol values, which are
pretty sure to be incorrect.

I've been leaning more toward the feature by feature view lately.  You can
see the evolution of my thoughts in the Configure script I wrote for the
rn distribution kit.  Near the beginning it tries to figure out the system
type.  But does it use the system type for anything important?  Nope.  Only
to guess at a default answer here or there.  I try to determine the presence
or absence of each feature independently.

The reason for this is that there are more and more hybrid systems out
there.  What in the world is a Version 7 system with some Berkeley and some
USG extensions?  If I rely on the fact that it looks like a V7 system, rn
won't have any way to do a non-blocking read.  But one of those extensions
might have been FIONREAD, or O_NDELAY.  There's no way (currently) to find
out except by snooping around.

While I think Configure is a step in the right direction, it would be nice
if all the info was gathered into one spot so that snooping wasn't necessary.
The main problem that I see is: who is to say which features are to be, er,
featured.

What is needed is some way for each program to interrogate just those
features it's interested in, without having to worry about new feature
definitions cluttering up somebody or other's namespace.  The word
"interrogate" implies something a little more active than the current
include business, but not necessarily as active as calling getfoobars()s.
In fact, it could be done with with includes, if each feature definition
were "guarded" by a standard format symbol that you define before including
the feature list if you want to know about a given feature:

#ifdef GET_FOOBAR
#define FOOBAR		/* yes we foobar regularly */
#endif

#ifdef GET_BLURFL
#undef BLURFL		/* promised in the next release */
#endif

I agree, this is all very kludgey, but a given program would only have to
avoid colliding with new symbols of the form GET_*.

However it's done, whether at compile or run time, whether by shell script
or include file, the important thing is that a program only import the
names it is interested in.  The current CPP definitions do not have this, er,
feature.

Sorry, I'm not feeling very well either.

Larry Wall
{allegra,burdvax,cbosgd,hplabs,ihnp4,sdcsvax}!sdcrdcf!lwall