moraes@cs.toronto.edu (Mark Moraes) (12/16/89)
bin@primate.wisc.edu (Brain in Neutral) writes: ># if mips ># if ultrix > DECstation ># else > true MIPS ># endif ># endif Not so fast. SGI also defines "mips" on the Iris4D machines -- why not, it's the CPU they use. One possible solution, seen to work on our Iris4D (Irix3.2), our DS3100s (Ultrix3.1), and our M/120 (Riscos4.0: #ifdef mips # ifdef ultrix # define ULTRIX_MIPS # define arch "ultrix-mips" # endif # ifdef sgi # define IRIS4D # define arch "iris4d" # endif # ifndef arch /* * Must be MIPSCo MIPS. Anyone know a way to differentiate between * RISCOS4.0 and UMIPS via cpp? */ # define MIPS # define arch "mips" # endif #endif Then one can use the symbols MIPS, IRIS4D, or ULTRIX_MIPS. Note: this will presumably change once vendors start shipping truly ANSI compatible compilers -- ANSI prohibits this sort of random pollution of the namespace. (It'll be __mips__ or suchlike, and life will become even more complicated, as people try to keep code backwards compatible with things like"#if defined(mips) || defined(__mips__)")) Another solution is to stick a wrapper script around cc, and get it to define the symbols you want. The shell script I use for our SGI machines is enclosed below. *Soapbox on* It is probably much better to ifdef on specific features that one needs (eg. BSD_SIGNALS, JOB_CONTROL, DIRENT, SHMEM, etc) than on a specific vendor type, considering the way the zillion and one "standard" deviants, er, variants, of Un*x are growing warts, er, features. Relying on even the vendors operating system remaining the same is probably not portable. As for the simple distinction between BSD and SYSV, that's gone a long time ago, thanks to extensive cross-breeding... Then one can create configuration headers per machine -- s-machine.h, sysdep.h, whatever, defining specific features on a per release basis, as is sometimes necessary :-( The joys of maintaining a single source tree for multiple architectures and OS deviants! *Soapbox off* #! /bin/sh - # Fake CC driver that includes local and bsd stuff and links compatibility # bsd routines. Also defines __iris4d__ and __irix__, as well # as linking in /local/lib libraries before system defaults. # Also munges output error messages from cc to BSD format, so it can # be automatically parsed by Jove. # Mark Moraes, University of Toronto realcc=/usr/bin/cc includes= args= for i do case "$i" in -I*) includes="$includes $i";; -v) set -x;; esac done includes="$includes -I/local/include -I/usr/include/bsd" tmp=/tmp/cc.bsd.$$ trap 'rm -f $tmp; exit $status' 0 $realcc -D__iris4d__ -D__irix__ $includes -L/local/lib "$@" -lbsd 2> $tmp status=$? # Postprocess errors - cc can produce stuff on stdout, for cc -M, f'rinstance sed 's/^[^:]*: \([^:]*: \)\([^,]*\), \([^:]*: \)\(.*\)/"\2", \3\1\4/' $tmp >&2
msc@ramoth.esd.sgi.com (Mark Callow) (12/19/89)
In article <89Dec15.145750est.2273@neat.cs.toronto.edu>, moraes@cs.toronto.edu (Mark Moraes) writes: > > *Soapbox on* > > It is probably much better to ifdef on specific features that one > needs (eg. BSD_SIGNALS, JOB_CONTROL, DIRENT, SHMEM, etc) than on a > specific vendor type, considering the way the zillion and one > "standard" deviants, er, variants, of Un*x are growing warts, er, > features. Relying on even the vendors operating system remaining the > same is probably not portable. As for the simple distinction between > BSD and SYSV, that's gone a long time ago, thanks to extensive > cross-breeding... > > Then one can create configuration headers per machine -- s-machine.h, > sysdep.h, whatever, defining specific features on a per release basis, > as is sometimes necessary :-( The joys of maintaining a single source > tree for multiple architectures and OS deviants! > > *Soapbox off* Yes, Yes,a thousand times yes. Even though the system vendors don't define "feature ifdefs" you can write your code as if you had them. You simply have to create a header that does all the ugly stuff (like that in the rest of the referenced article) and sets the appropriate "featuredefs". We tried to persuade the X consortium to change the ifdef's in X to a scheme like this. Their response was lukewarm.
yar@cs.su.oz (Ray Loyzaga) (12/21/89)
In article <2103@odin.SGI.COM> msc@sgi.com writes: > In article <89Dec15.145750est.2273@neat.cs.toronto.edu>, > moraes@cs.toronto.edu (Mark Moraes) writes: > > It is probably much better to ifdef on specific features that one > > needs (eg. BSD_SIGNALS, JOB_CONTROL, DIRENT, SHMEM, etc) than on a > > specific vendor type, considering the way the zillion and one > > [Deleted] > > Then one can create configuration headers per machine -- s-machine.h, > > sysdep.h, whatever, defining specific features on a per release basis, > > as is sometimes necessary :-( The joys of maintaining a single source > > tree for multiple architectures and OS deviants! > > > > *Soapbox off* > > Yes, Yes,a thousand times yes. > > Even though the system vendors don't define "feature ifdefs" you can write > your code as if you had them. You simply have to create a header that does > all the ugly stuff (like that in the rest of the referenced article) and > sets the appropriate "featuredefs". > We tried to persuade the X consortium to change the ifdef's in X to a scheme > like this. Their response was lukewarm. The only problem with this approach is that all the sources that you develop will have #includes of files that are not available on any other system, you could #ifdef the includes but on the basis of what? The bottom line is that you need to have an "include" file that defines the way the system is set up, and this file is sourced by cpp with every invocation. This file should contain the "standard defines" such as mips or sysV etc, these are currently compiled into cpp or a caller program and mean that the user must rely on the result of the output of "strings" on cpp or cc, and some guesswork, or hope that any changes are reflected in the manuals on each release. I'd be much more comfortable in reading a file such as /etc/local-system which contains -Dmips -DBSD4 etc, and having cpp doing something like #!/bin/sh /lib/cpp.real `cat /etc/local-system` "$@" The inbuilt defines couldn't be clearer and there would be no need to include any files that are unlikely to exist on other machines. We currently use such a system to communicate some kernel changes that affect the sizes of system structures to all the system sources without having to edit them.
lamaster@ames.arc.nasa.gov (Hugh LaMaster) (12/22/89)
In article <2103@odin.SGI.COM> msc@sgi.com writes: >In article <89Dec15.145750est.2273@neat.cs.toronto.edu>, >Even though the system vendors don't define "feature ifdefs" you can write >your code as if you had them. You simply have to create a header that does >all the ugly stuff (like that in the rest of the referenced article) and >sets the appropriate "featuredefs". I agree with most of what is written here, but, I sure could use a standard way to determine from the shell what architecture of machine I am on. I wish, for example, that the "arch" command could be made universal, and would return a string which has 2 simple components. For example: sun3 sun4 decvax decmips sgimips (or whatever you want, as long as it is unique). BTW, I currently use if [] tests on files to guess, when something else is not available, but this doesn't work reliably because of differences in filesystem mounts, which optional software is loaded, etc. Hugh LaMaster, m/s 233-9, UUCP ames!lamaster NASA Ames Research Center ARPA lamaster@ames.arc.nasa.gov Moffett Field, CA 94035 Phone: (415)694-6117
casey@gauss.llnl.gov (Casey Leedom) (12/24/89)
| From: moraes@cs.toronto.edu (Mark Moraes) | | It is probably much better to ifdef on specific features that one needs | (eg. BSD_SIGNALS, JOB_CONTROL, DIRENT, SHMEM, etc) than on a specific | vendor type ... I agree, but if you do this, please use the proposed POSIX defines for this. That way you shouldn't have to change too much when POSIX actually makes it out of the shop. (Sorry, I don't have the draft standard on me, so I can't provide any details on what the proposed defines are or even which file a POSIX conforming program is supposed to include to get the set of Supported Feature Constants.) Casey
mike@BRL.MIL (Mike Muuss) (12/30/89)
Here is the script that I use to determine the type of system that code is compiling on. This is an important part of the BRL-CAD Package's ability to port between so many different UNIX systems. Best, -Mike ------- #!/bin/sh # M A C H I N E T Y P E . S H # # A Shell script to determine the machine architecture type, # operating system variant (Berkeley or SysV), and # the presence of Berkeley-style TCP networking capability. # The machine type must be FOUR characters or less. # # This is useful to permit the separation of # incompatible binary program files, and to drive proper tailoring # of some of the Makefiles. # # Note that this Shell script uses the same mechanism (ie, CPP) # to determine the system type as the main Cakefile (Cakefile.defs) # uses. To support a new type of machine, the same #ifdef construction # will be required both here and in Cakefile.defs # # Command args: # [none] Print only machine type # -m Print only machine type # -s Print only system type, BRL style: (BSD, SYSV) # -a Print only system type, ATT style: (BSD, ATT) # -n Print only HAS_TCP variable # -b -v Print all, in Bourne-Shell legible form # # Info note: On a VAX-11/780, this script takes about 1.3 CPU seconds to run # # Mike Muuss, BRL, 10-May-1988 # With thanks to Terry Slattery and Bob Reschly for assistance # $Revision: 9.2 $ # Ensure /bin/sh. Make no remarks here, just do it. export PATH || (sh $0 $*; kill $$) FILE=/tmp/machtype$$ trap '/bin/rm -f ${FILE}; exit 1' 1 2 3 15 # Clean up temp file /lib/cpp << EOF > ${FILE} #line 1 "$0" #if defined(unix) && defined(m68k) # undef aux MACHINE=aux; UNIXTYPE=SYSV; HAS_TCP=0; HAS_SYMLINKS=1; #endif #ifdef vax # undef vax MACHINE=vax; UNIXTYPE=BSD; HAS_TCP=1; HAS_SYMLINKS=1; #endif #ifdef alliant # undef fx MACHINE=fx; UNIXTYPE=BSD; HAS_TCP=1; HAS_SYMLINKS=1; #endif #ifdef gould # undef sel MACHINE=sel; UNIXTYPE=BSD; HAS_TCP=1; HAS_SYMLINKS=1; #endif #if defined(sgi) && !defined(mips) /* Silicon Graphics 3D */ # undef sgi MACHINE=3d; UNIXTYPE=SYSV; HAS_TCP=1; HAS_SYMLINKS=1; #endif #if defined(sgi) && defined(mips) /* Silicon Graphics 4D, which uses the MIPS chip */ # undef sgi MACHINE=4d; UNIXTYPE=SYSV; HAS_TCP=1; HAS_SYMLINKS=1; #endif #if defined(sun) && !defined(sparc) # undef sun # undef sun3 MACHINE=sun3; UNIXTYPE=BSD; HAS_TCP=1; HAS_SYMLINKS=1; #endif #if defined(sparc) # undef sun # undef sun4 MACHINE=sun4; UNIXTYPE=BSD; HAS_TCP=1; HAS_SYMLINKS=1; #endif #if defined(apollo) # undef apollo MACHINE=apollo; UNIXTYPE=BSD; HAS_TCP=1; HAS_SYMLINKS=1; #endif #if defined(CRAY1) /* Cray X-M/P running UNICOS. */ # undef xmp MACHINE=xmp; UNIXTYPE=SYSV; HAS_TCP=1; HAS_SYMLINKS=0; #endif #if defined(CRAY2) # undef cr2 MACHINE=cr2; UNIXTYPE=SYSV; HAS_TCP=1; HAS_SYMLINKS=0; #endif #ifdef convex # undef c1 MACHINE=c1; UNIXTYPE=BSD; HAS_TCP=1; HAS_SYMLINKS=1; #endif #ifdef ardent # undef ard /* The network code is not tested yet */ MACHINE=ard; UNIXTYPE=SYSV; HAS_TCP=0; HAS_SYMLINKS=1; #endif #ifdef stellar # undef stl /* The network code is not tested yet */ MACHINE=stl; UNIXTYPE=SYSV; HAS_TCP=0; HAS_SYMLINKS=0; #endif #ifdef eta10 /* ETA-10 running UNIX System V. */ /* The network support is different enough that is isn't supported yet */ # undef eta MACHINE=eta; UNIXTYPE=SYSV; HAS_TCP=0; HAS_SYMLINKS=0; #endif #ifdef pyr # undef pyr MACHINE=pyr; UNIXTYPE=BSD; # Pyramid can be dual-environment, assume BSD HAS_TCP=1; HAS_SYMLINKS=1; #endif EOF # Note that we depend on CPP's "#line" messages to be ignored as comments # when sourced by the "." command here: . ${FILE} /bin/rm -f ${FILE} # See if we learned anything by all this if test x${MACHINE} = x then echo "$0: ERROR, unable to determine machine type." 1>&2 echo "$0: Consult installation instructions for details." 1>&2 MACHINE=//error// UNIXTYPE=--error-- HAS_TCP=0 HAS_SYMLINKS=0 # Performing an "exit 1" here does not help any if this script # is being invoked by, eg, grave accents (which is a typical use). # So, simply return the error strings invented above, # which should cause more sensible errors downstream than # having Shell variables competely unset. fi # Special cases for discriminating between different versions of # systems from vendors. # Try very hard to avoid putting stuff here, because this technique # is not available for use in "Cakefile.defs", so special handling # will be required. #case ${MACHINE} in # #4d) # if test -d /usr/NeWS # then # # This is definitely an SGI sw Release 3.? system # if test ! -x /tmp/gt # then # echo 'main(){char b[50];gversion(b);printf("%2.2s\\n",b+4);exit(0);}'>/tmp/gt.c # cc /tmp/gt.c -lgl -o /tmp/gt # fi # case `/tmp/gt` in # GT) MACHINE=4gt;; # PI) MACHINE=4p;; # Personal Iris # *) MACHINE=4d;; # esac # else # # This is an SGI sw Release 2 system # MACHINE=4d2 # Unsupported # fi;; # #esac # Now, look at first arg to determine output behavior case x$1 in x|x-m) echo ${MACHINE}; exit 0;; x-s) echo ${UNIXTYPE}; exit 0;; x-n) echo ${HAS_TCP}; exit 0;; x-a) if test ${UNIXTYPE} = BSD then echo BSD else echo ATT fi exit 0;; x-v|x-b) echo "MACHINE=${MACHINE}; UNIXTYPE=${UNIXTYPE}; HAS_TCP=${HAS_TCP}; HAS_SYMLINKS=${HAS_SYMLINKS}" exit 0;; *) echo "$0: Unknown argument $1" 1>&2; break;; esac exit 1