Subject: Re: Summary: Thoughts on implementing Scheme in C
From: rpw3@rigden.engr.sgi.com (Rob Warnock)
Date: 17 Nov 2000 05:27:46 GMT
Newsgroups: comp.lang.scheme
Message-ID: <8v2fki$4d9r$1@fido.engr.sgi.com>
Bill Richter  <richter@poincare.math.nwu.edu> wrote:
+---------------
| rpw3@rigden.engr.sgi.com (Rob Warnock) responds to me:
|    Then you have no problem! In practice, if you allow small amounts
|    of platform-dependent #ifdef's in your C code, you can write a
|    Scheme system that's *very* portable.
| 
| Thanks, Rob.  Can you relate this to Matthias's article?  What
| arguments of Matthias's against C do these #ifdef's circumvent?
+---------------

When treading in these waters it's very important to distinguish the
limits of *completely* standard-conformant behavior, including things
that are "undefined" by the standard(s) [here, both C & R5RS], from
how *specific* implementations of either C or Scheme actually work.

Matthias was addressing the former, quite rigorously. But once those
limits are relaxed, and one permits oneself to descend into the "baling
wire & spit" world of actual specific implementations, all bets are off.
*Anything* that "works" is "legal", at that point. 

Here's just a small sample of #ifdefs from Elk Scheme's "heap-gen.c",
the generational version of the GC that comes with Elk (it comes with
several styles of GC, by the way, just in case one of them won't work
on your machine!!):

	#include <limits.h>
	#include <sys/types.h>
	#ifdef HAS_MPROTECT
	#  include <sys/mman.h>
	#endif
	#ifdef SYSCONF_PAGESIZE
	#  define link FOO
	#  include <unistd.h>
	#  undef link
	#  if defined(_SC_PAGE_SIZE) && !defined(_SC_PAGESIZE)   /* Wrong in HP-UX */
	#    define _SC_PAGESIZE _SC_PAGE_SIZE
	#  endif
	#endif
	#ifdef SIGSEGV_SIGINFO
	#  include <siginfo.h>
	#  include <ucontext.h>
	#endif
	...
	/* pagebase is #defined in object.h if ARRAY_BROKEN is not defined. */
	#ifdef ARRAY_BROKEN
	  pageno_t pagebase;
	#endif
	...
	ifdef ALIGN_8BYTE
	#  define MAX_OBJECTWORDS       (PAGEWORDS - 1)
	#  define NEEDED_PAGES(size)    (((size) + PAGEWORDS) / PAGEWORDS)
	#else
	#  define MAX_OBJECTWORDS       PAGEWORDS
	#  define NEEDED_PAGES(size)    (((size) + PAGEWORDS - 1) / PAGEWORDS)
	#endif
	...
		p = PAGE_TO_OBJ (stable_queue);
	#ifdef ALIGN_8BYTE
		p++;
	#endif
	...
	#ifdef HAS_MPROTECT
	    InstallHandler ();
	#endif
	[...lots of other examples omitteed...]

See? Lots and lots of little low-level twiddly stuff to get it to work
on *specific* platforms and implementations...

+---------------
| Matthias's article didn't seem particularly interested in portability:
| But by sticking to `strict portable C' we've got a fixed target
| language to address the issue of implementing Scheme.
+---------------

Actually, I think Matthias's article *was* about portability! But the
problem is, the C standard doesn't provide for certain things you *need*
to implement Scheme portably.

For example, Baker's "Cheney on the MTA" trick *will* in fact work (or
can be made to work with a few conditionals) on nearly every existing
implementation of C, but it's not "legal C" according to the ANSI standard.


-Rob

-----
Rob Warnock, 31-2-510		rpw3@sgi.com
Network Engineering		http://reality.sgi.com/rpw3/
Silicon Graphics, Inc.		Phone: 650-933-1673
1600 Amphitheatre Pkwy.		PP-ASEL-IA
Mountain View, CA  94043