From: Joerg-Cyril Hoehle
Subject: solved: loading two object files into CMU
Date: 
Message-ID: <31tr6f$604@hermes.uni-konstanz.de>
Hi,

we've been using GINA for some time now and began to merge different
things when we hit a bug that made it impossible on a Sun to
LOAD-FOREIGN two object files simultaneously.

The Sun manpages say about ld with -A option:

          the  argument  list.  One or both of the -T options may
          be used as well, and will be taken  to  mean  that  the
          newly linked segment will commence at the corresponding
          addresses (which must be a multiple of the page  size).
          The default value is the old value of _end.

The problem is that sys::*foreign-segment-free-pointer* isn't reset
to a page boundary after a load-foreign.

Here is my patch to code/foreign.lisp:

(defun allocate-space-in-foreign-segment (bytes)
  (let* ((pagesize-1 (1- (get-page-size)))
	 (memory-needed (logandc2 (+ bytes pagesize-1) pagesize-1))
	 (addr (int-sap *foreign-segment-free-pointer*))
	 (new-ptr (+ *foreign-segment-free-pointer* bytes)))
    (when (> new-ptr (+ foreign-segment-start foreign-segment-size))
      (error "Not enough memory left."))
    (setf *foreign-segment-free-pointer* #-sparc new-ptr
	  ;; on a Sun, ld with -T must be a multiple of the page size,
	  ;;I don't know about others:
	  #+sparc (+ *foreign-segment-free-pointer* memory-needed))
    (allocate-system-memory-at addr memory-needed)
    addr))

Thanks for CMUCL, and thanks for the source!

For those that cannot or don't want to patch the source, here's what
you can do after a call to load-foreign (and before the next call!):

(setq sys::*foreign-segment-free-pointer*
      (let ((pagesize-1 (1- (sys::get-page-size))))
	(logandc2 (+ sys::*foreign-segment-free-pointer* pagesize-1) pagesize-1)))

 	Joerg Hoehle.
······@inf-wiss.uni-konstanz.de