Patches for ELK on the SPARC. This was my first sparc program, so it could be stupid in places, but it seems to work. Any and all bugs are my fault, and anything that works is due to help from from Mark Weiser, John Gilmore, and Mitch Bradley's kick-ass Sun-4 Forth system. Some times it seems to try to allocate huge amounts of memory, and runs out of stack space. I haven't tracked this bug down yet, but please let me know if you do. -Don Hopkins (don@brillig.umd.edu) * Changed files: ** Makefile: Put the following definitions in the top level Makefile. I changed the GENERIC and the SCHEME_DIR definitions to do the quoting differently, because it was confusing the SunOS 3.2 compiler. SCHEME_DIR= /f/net/scm/scm GENERIC= char * MACHTYPE= sparc # vax 68k 386 sparc DIR= -DDEF_LOAD_DIR=\\\"$(SCHEME_DIR)\\\" GEN= -DGENERIC=\"$(GENERIC)\" CFLAGS= $(INC) $(DIR) $(GEN) -O4 # SunOS 4.0 LDFLAGS= -x # 4.n BSD ** src/config.h: Right before the end of the #ifdef sun section, add the following: # ifdef sparc /* This is outside of this .h file cause the sun 3 3.2 preprocesser barfs on pragma, even if it's ifdef'ed out. */ # include "sparc.h" # endif I found I had to change the heap size to get the test programs to work (I doubled it from 512 to 1024): #define HEAP_SIZE 1024 /* in KBytes */ * New files: ** src/sparc.h: Required because SunOS 3.2 cpp barfs on "#pragma". Enclosed. ** src/stack.s.sparc: Implements stack manipulation code on sparc. Enclosed. ** src/alloca.s.sparc: Just an empty file. (Not enclosed. Buy me a beer, and I'll be happy to supply you with a uuencoded compressed tar file with a hand-made empty file that will work very well for this purpose.) * Instructions: Apply the changes to "Makefile" and "src/config.h". Put the files "src/sparc.h" and "src/stack.s.sparc" in place. Make an empty file, "src/alloca.s.sparc" (unless you'd rather buy me a beer). Type "make" in the top level directory. * Files: ** src/sparc.h #include extern int saveenv(), jmpenv(); #pragma unknown_control_flow(saveenv,jmpenv) ** src/stack.s.sparc /* int stksize(); */ .globl _stksize .globl _Special _stksize: set _stkbase,%o1 ld [%o1],%o1 mov %sp,%o0 sub %o1,%o0,%o0 retl add %o0,256,%o0 /* int saveenv(char* envbuf); */ .globl _saveenv _saveenv: save %sp,-96,%sp /* new window */ /* i0: char *envbuf */ t 0x3 /* ST_FLUSH_WINDOWS trap */ st %i7,[%i0+4] /* saved PC */ mov %y,%l0 st %l0,[%i0+8] /* Y register */ #ifdef notdef /* Illegal instruction. This doesn't seem to be necessary... */ mov %psr,%l0 st %l0,[%i0+12] /* PSR register */ #endif st %sp,[%i0+16] /* SP register */ st %fp,[%i0+20] /* FP register */ st %g1,[%i0+40] /* save globals */ st %g2,[%i0+44] st %g3,[%i0+48] st %g4,[%i0+52] st %g5,[%i0+56] st %g6,[%i0+60] st %g7,[%i0+64] mov %sp,%l0 /* %l0 source */ add %i0,128,%l1 /* %l1 dest */ set _stkbase,%l2 /* %l2 limit */ ld [%l2],%l2 rep1: /* copy stack to buf */ ld [%l0],%l3 st %l3,[%l1] inc 4,%l1 cmp %l0,%l2 bleu rep1 inc 4,%l0 sub %l1,%l0,%l1 /* %l1 relocation offset */ st %l1,[%i0] /* store at front of buffer */ set _Special,%i0 /* return value */ ld [%i0],%i0 ret restore /* dead jmpenv(const char* envbuf, int retcode); */ .globl _jmpenv _jmpenv: save %sp,-96,%sp /* new window */ /* i0: char *envbuf */ /* i1: int retcode */ t 0x3 /* ST_FLUSH_WINDOWS trap */ ld [%i0+16],%l1 /* l1: SP register */ mov %l1,%sp add %i0,128,%l0 /* %l0: source */ /* %l1: dest */ set _stkbase,%l2 /* %l2: limit */ ld [%l2],%l2 rep2: /* copy buf to stack */ ld [%l0],%l3 st %l3,[%l1] inc 4,%l1 cmp %l1,%l2 bleu rep2 inc 4,%l0 ld [%i0+40],%g1 ld [%i0+44],%g2 ld [%i0+48],%g3 ld [%i0+52],%g4 ld [%i0+56],%g5 ld [%i0+60],%g6 ld [%i0+64],%g6 ld [%i0+20],%fp #ifdef notdef ld [%i0+12],%l0 /* Illegal instruction. This doesn't seem to be necessary... */ mov %l0,%psr #endif ld [%i0+8],%l0 mov %l0,%y ld [%i0+4],%i7 nop /* ??? */ mov %i1,%i0 ret restore