koreth@ssyx.ucsc.edu.ucsc.edu (Steven Grimm) (12/27/88)
Submitted-by: madsen@sask.usask.ca (Jorgen Madsen) Posting-number: Volume 1, Issue 82 Archive-name: mx2v230/part02 #!/bin/sh # this is part 2 of a multipart archive # do not concatenate these parts, unpack them in order with /bin/sh # file ATOMIC.MOD continued # CurArch=2 if test ! -r s2_seq_.tmp then echo "Please unpack part 1 first!" exit 1; fi ( read Scheck if test "$Scheck" != $CurArch then echo "Please unpack part $Scheck next!" exit 1; else exit 0; fi ) < s2_seq_.tmp || exit 1 sed 's/^X//' << 'SHAR_EOF' >> ATOMIC.MOD X END; X NEWPROCESS(dummy,ADR(wsp1),TSIZE(workspace),x); X NEWPROCESS(dummy,ADR(wsp2),TSIZE(workspace),p); X NEWPROCESS(dummy,ADR(wsp3),TSIZE(workspace),t); X currentprocess^.wsp:=ADR(wsp2); X currentprocess^.cor:=p; XEND InitProcesses; X XPROCEDURE EndProcesses; XBEGIN X s0:=currentprocess; X REPEAT X currentprocess:=s0^.next; X s0:=currentprocess; X UNTIL currentprocess^.pid=0; X SuperExec(restorebiosptr); X INC(contextswitch); (* update switch counter *) X TRANSFER(currentprocess^.cor,currentprocess^.cor); XEND EndProcesses; X X(* This is the scheduler which is called by newtrap *) XPROCEDURE sched; XBEGIN X IOTRANSFER(cotick,x,ADDRESS(trapvec)); (* V1.1 baud rate timer *) X LOOP (* interrupt not used by ST *) X currentprocess^.cor:=x; X currentprocess^.ready:=FALSE; X currentprocess^.intflag:=TRUE; (* process interrupted *) X INC(contextswitch); (* update switch counter *) X currentprocess:=s0; (* s0 set to new in newtrap procedure *) X currentprocess^.ready:=TRUE; (* process to start *) X x:=currentprocess^.cor; X IOTRANSFER(cotick,x,ADDRESS(offsetvec)); (* offset vector so not *) X END; (* to overwrite the *) XEND sched; (* newtrap vector *) X XPROCEDURE SwapProcess; (* swap out processes *) XBEGIN X IntEnd; X SuperExec(UpdatecurrentProc); X s0:=currentprocess; X currentprocess^.ready:=FALSE; X LOOP (* find next process *) X currentprocess:=currentprocess^.next; X IF currentprocess^.active AND (currentprocess^.wsp#NIL) THEN X EXIT X END; X END; (* loop *) X currentprocess^.ready:=TRUE; X IF s0^.pid#currentprocess^.pid THEN X SuperExec(UpdateProc); X TRANSFER(s0^.cor,currentprocess^.cor); X END; X IntBegin; XEND SwapProcess; X X(*$P- *) XPROCEDURE UpdateProc; (* update all currentprocess values *) XBEGIN X currentprocess^.slice:=hz200; X ClrInt; X SetTimer; X setbiosptr; X INC(contextswitch); (* update switch counter *) X CODE(4e75H); (* rts *) XEND UpdateProc; X(*$P+ *) X X(*$P- *) XPROCEDURE UpdatecurrentProc; XBEGIN X getbiosptr; X IncSlice; X CODE(4e75H); (* rts *) XEND UpdatecurrentProc; X(*$P+ *) X XPROCEDURE dummy; (* dummy procedure to make newprocess *) XBEGIN XEND dummy; X XPROCEDURE d1(): BOOLEAN; XBEGIN XEND d1; X XPROCEDURE d2(c: CHAR); XBEGIN XEND d2; X XPROCEDURE d3(): LONGCARD; XBEGIN XEND d3; X(* check to see if process s0 is a ZOMBIE, if so return true else false *) XPROCEDURE FindZombieProcess(VAR zombie: BOOLEAN); XBEGIN X IF (NOT s0^.active) AND (s0^.pid#0) AND (s0^.wsp=NIL) THEN X zombie:=TRUE; (* found one *) X ELSE X zombie:=FALSE; (* nada it's alive! *) X END; XEND FindZombieProcess; X XPROCEDURE FindProcess(VAR pid: INTEGER; VAR fp: SIGNAL); XBEGIN X s:=schedproc; X LOOP (* find process id *) X s:=s^.next; X IF (s^.pid=pid) AND (s^.wsp#NIL) THEN (* found id *) X fp:=s; X EXIT; X END; X IF s^.pid=schedproc^.pid THEN (* id not found in list *) X fp:=NIL; X EXIT; X END; X END; XEND FindProcess; X XPROCEDURE FindChildProcess(VAR pid: INTEGER; VAR fp: SIGNAL); XBEGIN X s:=schedproc; X LOOP (* find process child id *) X s:=s^.next; X IF (s^.ppid=pid) AND (s^.wsp#NIL) THEN (* found id *) X fp:=s; X EXIT; X END; X IF s^.pid=schedproc^.pid THEN (* id not found in list *) X fp:=NIL; X EXIT; X END; X END; XEND FindChildProcess; X X(*$P- *) XPROCEDURE IncSlice; (* UPDATE cpu time *) XBEGIN X INC(currentprocess^.tick,hz200-currentprocess^.slice); X currentprocess^.slice:=hz200; X CODE(4e75H); (* rts *) XEND IncSlice; X(*$P+ *) X X(*$P- *) XPROCEDURE SetSlice; (* start timeslice *) XBEGIN X temphz200:=hz200; X CODE(4e75H); (* rts *) XEND SetSlice; X(*$P+ *) X X(*$P- *) XPROCEDURE SetTimer; (* setup number of ticks before switch V1.1 *) XBEGIN X TICKS:=hz200+LONGCARD(currentprocess^.pri*10); X CODE(4e75H); (* rts *) XEND SetTimer; X(*$P+ *) X X(*$P- *) XPROCEDURE ClrInt; (* V1.2 change to int on mfp *) XBEGIN X CODE(8b9H,intnum,0ffffH,0fa11H); (* BCLR intnum, ISRB *) X CODE(8b9H,intnum,0ffffH,0fa15H); (* BCLR intnum, MASKB *) X CODE(4e75H); (* rts *) XEND ClrInt; X(*$P+ *) X X(*$P- *) XPROCEDURE EnableInterrupt; XBEGIN (* setup sched vector interrupt *) X SETREG(8,0fffffa15H); (* load a0 with adr of mfp reg *) X CODE(8d0H,intnum); (* set int mask bit *) X CODE(4e75H); (* rts *) XEND EnableInterrupt; X(*$P+ *) X XPROCEDURE MultiBegin; XBEGIN X SuperExec(ClrInt); X SuperExec(SetTimer); X MULTI:=TRUE; XEND MultiBegin; X XPROCEDURE MultiEnd; XBEGIN X MULTI:=FALSE; X SuperExec(ClrInt); XEND MultiEnd; X XPROCEDURE IntBegin; XVAR ssv : ADDRESS; XBEGIN X ssv:=0H; X Super(ssv); X CODE(46fcH,2300H); (* start interrupts *) X Super(ssv); XEND IntBegin; X XPROCEDURE IntEnd; XVAR ssv : ADDRESS; XBEGIN X ssv:=0H; X Super(ssv); X CODE(46fcH,2700H); (* stop interrupts *) X Super(ssv); XEND IntEnd; X X(*$P- *) XPROCEDURE getbiosptr; XBEGIN X WITH currentprocess^ DO X biosval:=biospointer+46; X termvec:=ptermvec; X gemsave[0]:=gemsaveGvec^; X gemsave[1]:=linea; X gemsave[2]:=gemdos; X gemsave[3]:=gsxgem; X gemsave[4]:=tbios; X gemsave[5]:=xbios; X gemsave[6]:=linef; X gemsave[7]:=level2; X gemsave[8]:=level4; X gemsave[9]:=shellp; X END; X CODE(4e75H); (* rts *) XEND getbiosptr; X(*$P+ *) X X(*$P- *) XPROCEDURE setbiosptr; XBEGIN X WITH currentprocess^ DO X savefrom:=ADDRESS(biospointer); X saveto:=ADDRESS(biosval-46); X saveto^:=savefrom^; X biospointer:=biosval-46; X ptermvec:=termvec; X gemsaveGvec^:=gemsave[0]; X linea:=gemsave[1]; X gemdos:=gemsave[2]; X gsxgem:=gemsave[3]; X tbios:=gemsave[4]; X xbios:=gemsave[5]; X linef:=gemsave[6]; X level2:=gemsave[7]; X level4:=gemsave[8]; X shellp:=gemsave[9]; X END; X CODE(4e75H); (* rts *) XEND setbiosptr; X(*$P+ *) X X(*$P- *) XPROCEDURE restorebiosptr; XBEGIN X savefrom:=biospointer; X saveto:=bios; X saveto^:=savefrom^; X biospointer:=bios; X ptermvec:=oldtermvec; X CODE(4e75H); (* rts *) XEND restorebiosptr; X(*$P+ *) X X(*$P- *) XPROCEDURE intbiosptr; XBEGIN X WITH currentprocess^ DO X savefrom:=ADDRESS(biospointer); X saveto:=ADR(biosave[199]); X saveto^:=savefrom^; X biosval:=ADR(biosave[199]); X biospointer:=biosval; X termvec:=ptermvec; X gemsave[0]:=gemsaveGvec^; X gemsave[1]:=linea; X gemsave[2]:=gemdos; X gemsave[3]:=gsxgem; X gemsave[4]:=tbios; X gemsave[5]:=xbios; X gemsave[6]:=linef; X gemsave[7]:=level2; X gemsave[8]:=level4; X gemsave[9]:=shellp; X END; X CODE(4e75H); (* rts *) XEND intbiosptr; X(*$P+ *) X X(*$P- *) XPROCEDURE newtrap; (* IOTRANSFER executes this code before its *) XBEGIN (* normal vector. *) X X CODE(46fcH,2700H); (* stop interrupts *) X CODE(8b9H,intnum,0ffffH,0fa11H); (* BCLR intnum, ISRB *) X CODE(8b9H,intnum,0ffffH,0fa15H); (* BCLR intnum, MASKB *) X CODE(817H,5); (* BTST 5, (a7) check supermode *) X CODE(6700H+2); (* BEQ.S over rte *) X CODE(4e73H); (* RTE supermode return *) X CODE(48e7H,0fffeH); (* save regs movem *) X CODE(204fH); (* move.l ssp,a0 *) X currentprocess^.ssp:=REGISTER(8)+66; X X IF (currentprocess^.ssp#sspval) X AND (currentprocess^.ssp#accsuperstack) THEN X CODE(4cdfH,7fffH); (* restore regs movem *) X CODE(4e73H); (* rte *) X ELSE X X IncSlice; (* cpu time update *) X s0:=currentprocess; X LOOP (* find next process store in s0 *) X s0:=s0^.next; X WITH s0^ DO X IF (gemsave[14]#0) THEN (* If flags set then process *) X CPFlagptr:=ADR(gemsave[14]); X X IF sleep IN CPFlagptr^ THEN (* sleep flag *) X IF (gemsave[13]#0) AND X (ADDRESS(hz200) >= gemsave[13]) THEN X active:=TRUE; X gemsave[13]:=0; X EXCL(CPFlagptr^,wait); (* clear wait flag *) X EXCL(CPFlagptr^,sleep); (* clear sleep flag *) X END; X END; X IF wait IN CPFlagptr^ THEN (* wait flag *) X IF (waitloc^ = LONGCARD(LAnd(gemsave[11],gemsave[12]))) THEN X active:=TRUE; X gemsave[13]:=0; X EXCL(CPFlagptr^,wait); (* clear wait flag *) X EXCL(CPFlagptr^,sleep); (* clear sleep flag *) X END; X END; X X END; X IF (active) AND (wsp#NIL) THEN X IF misc[0]>=highpri THEN X IF pri>highpri THEN highpri:=pri END; X misc[0]:=pri; X EXIT; X ELSE X INC(misc[0]); (* age process til it's ready to run *) X END; X END; X END; (* with *) X END; (* end LOOP *) X X (* Swap GEM pointers for the processes *) X WITH currentprocess^ DO X gemsave[0]:=gemsaveGvec^; X gemsave[1]:=linea; X gemsave[2]:=gemdos; X gemsave[3]:=gsxgem; X gemsave[4]:=tbios; X gemsave[5]:=xbios; X gemsave[6]:=linef; X gemsave[7]:=level2; X gemsave[8]:=level4; X gemsave[9]:=shellp; X biosval:=biospointer; X termvec:=ptermvec; X END; X WITH s0^ DO X biospointer:=biosval; X ptermvec:=termvec; X gemsaveGvec^:=gemsave[0]; X linea:=gemsave[1]; X gemdos:=gemsave[2]; X gsxgem:=gemsave[3]; X tbios:=gemsave[4]; X xbios:=gemsave[5]; X linef:=gemsave[6]; X level2:=gemsave[7]; X level4:=gemsave[8]; X shellp:=gemsave[9]; X END; X X SetTimer; X s0^.slice:=hz200; (* set next cycle start *) X SETREG(8,oldtrap); (* move IOTRANSFER trap adr *) X CODE(43faH,10); (* lea 12(pc),a1 *) X CODE(2288H); (* move.l a0,(a1) *) X CODE(4cdfH,7fffH); (* restore regs movem *) X CODE(4ef9H,0,0) (* jmp back to routine *) X END; XEND newtrap; X(*$P+ *) X X(*$P-,$S- *) XPROCEDURE NewEtimer; XBEGIN X CODE(48e7H,0fffeH); (* save regs movem *) X IF MULTI THEN X CODE(207cH,0ffffH,0fa15H); (* load a0 with adr of mfp reg *) X CODE(8d0H,intnum); (* set int mask bit *) X CODE(5188H); (* subq.l 8 adj a0 to adr of mfp reg *) X CODE(5988H); (* subq.l 4 adj a0 to adr of mfp reg *) X CODE(8d0H,intnum); (* set int enable bit *) X END; X X SETREG(8,OldEtimer); (* move trap adr *) X CODE(43faH,6); (* lea 8(pc),a1 *) X CODE(2288H); (* move.l a0,(a1) *) X CODE(4ef9H,0,0); (* jmp back to routine *) XEND NewEtimer; X(*$P+,$S- *) X X(*$P- *) (*save trap and set up flag trap for IOTRANSFER to run my code *) XPROCEDURE settrap; (* before executing the IOTRANSFER. *) XBEGIN X CODE(46fcH,2700H); (* stop interrupts V1.1 use 200hz clock *) X TICKS:=10; X OldEtimer:=etimer+4; X etimer:=ADDRESS(NewEtimer); X EnableInterrupt; X MULTI:=FALSE; X oldtrap:=trap+4; (* add 4 to skip over set SR to 2700 *) X trap:=ADDRESS(newtrap); X CODE(46fcH,2300H); (* allow interrupts V1.1 *) X accsuperstack:=sysvector; (* load value from MX2.ACC *) X sysvector:=ADR(sysvar); (* setup sysvar pointers *) X sysvar.currentprocess:=ADR(currentprocess); X sysvar.MULTI:=ADR(MULTI); X sysvar.slicebegin:=ADR(slicebegin); X sysvar.command:=ADR(command); X sysvar.request:=ADR(request); X sysvar.contextswitch:=ADR(contextswitch); X sysvar.CRON:=ADR(CRON); X sysvar.spintenable:=ADR(spintenable); X sysvar.spintmask:=ADR(spintmask); X X sysvar.spint:=ADR(spint[0]); X sysvar.bpsave:=ADR(bpsave); X sysvar.pipes:=ADR(pipes); X sysvar.sysmemsize:=ADR(sysmemsize); X sysvar.gemsaveGvec:=ADR(gemsaveGvec); X sysvar.StartProcess:=StartProcess; X sysvar.SwapProcess:=SwapProcess; X sysvar.TermProcess:=TermProcess; X sysvar.NextPid:=NextPid; X sysvar.SleepProcess:=SleepProcess; X sysvar.WakeupProcess:=WakeupProcess; X sysvar.ChangeProcessPriority:=ChangeProcessPriority; X sysvar.MultiBegin:=MultiBegin; X sysvar.MultiEnd:=MultiEnd; X sysvar.DozeProcess:=DozeProcess; X sysvar.WaitProcess:=WaitProcess; X sysvar.CronActive:=ADR(CronActive); X sysvar.DeviceTable:=ADR(DeviceTable); X FOR I:=ORD(dev0) TO ORD(dev7) DO (* setup user device table *) X DeviceTable[I].bconstat:=devstattype(d1); X DeviceTable[I].bcostat:=devstattype(d1); X DeviceTable[I].bconin:=devintype(d3); X DeviceTable[I].bconout:=devouttype(d2); X END; X FOR I:=0 TO 31 DO (* clear all pipes *) X pipes[I]:=NIL; X END; X FOR I:=0 TO 15 DO (* clear all spints *) X spint[I].proc:=PROC(NIL); X END; X slicebegin:=hz200; X contextswitch:=0; X bios:=biospointer; (* save original pointer *) X oldtermvec:=ptermvec; X CODE(4e75H); (* rts *) X XEND settrap; X(*$P+ *) X XPROCEDURE Initsked; XVAR a,b,ssv : ADDRESS; XBEGIN X MultiEnd; X a:=ADDRESS(OTOS); X b:=ADDRESS(MTOS); X gemsaveGvec:=a; X IF ROMDATE=NEWDATE THEN gemsaveGvec:=b END; X SuperExec(SetTimer); X NEWPROCESS(sched,ADR(wsp0),TSIZE(workspace),cotick); X TRANSFER(x,cotick); X schedproc:=currentprocess; X SuperExec(settrap); X ssv:=0H; X Super(ssv); X sspval:=ssv; X Super(ssv); XEND Initsked; X XPROCEDURE CheckFlag(VAR flag: BOOLEAN): BOOLEAN; XBEGIN X IF flag THEN X RETURN TRUE; X ELSE X RETURN FALSE; X END; XEND CheckFlag; X XPROCEDURE SetFlag(VAR flag: BOOLEAN); XBEGIN X flag:=TRUE; XEND SetFlag; X XPROCEDURE ResetFlag(VAR flag: BOOLEAN); XBEGIN X flag:=FALSE; XEND ResetFlag; X XPROCEDURE CheckResetFlag(VAR flag: BOOLEAN): BOOLEAN; XBEGIN X IF flag THEN X flag:=FALSE; X RETURN TRUE; X ELSE X RETURN FALSE; X END; XEND CheckResetFlag; X XBEGIN XEND ATOMIC. SHAR_EOF chmod 0600 ATOMIC.MOD || echo "restore of ATOMIC.MOD fails" sed 's/^X//' << 'SHAR_EOF' > BITSTUFF.DEF && XDEFINITION MODULE BitStuff; X XFROM SYSTEM IMPORT BYTE, WORD, LONGWORD; X XPROCEDURE LAnd( op1, op2 : LONGWORD):LONGWORD; XPROCEDURE LOr( op1, op2 : LONGWORD):LONGWORD; XPROCEDURE LEor( op1, op2 : LONGWORD):LONGWORD; XPROCEDURE LShl(number : LONGWORD; numbits : CARDINAL):LONGWORD; XPROCEDURE LShr(number : LONGWORD; numbits : CARDINAL):LONGWORD; X XPROCEDURE WAnd( op1, op2 : WORD):WORD; XPROCEDURE WOr( op1, op2 : WORD):WORD; XPROCEDURE WEor( op1, op2 : WORD):WORD; XPROCEDURE WShl(number : WORD; numbits : CARDINAL):WORD; XPROCEDURE WShr(number : WORD; numbits : CARDINAL):WORD; X XPROCEDURE BAnd( op1, op2 : BYTE):BYTE; XPROCEDURE BOr( op1, op2 : BYTE):BYTE; XPROCEDURE BEor( op1, op2 : BYTE):BYTE; XPROCEDURE BShl(number : BYTE; numbits : CARDINAL):BYTE; XPROCEDURE BShr(number : BYTE; numbits : CARDINAL):BYTE; X XEND BitStuff. SHAR_EOF chmod 0600 BITSTUFF.DEF || echo "restore of BITSTUFF.DEF fails" sed 's/^X//' << 'SHAR_EOF' > BITSTUFF.MOD && X(* Some Functions to perform bit manipulation.. bitsets are a 'bit' X clumsy (pun intended) to use and don't operate on LONGWORDS, X so i wrote this. X It may not be the most efficient, but it is effective, enjoy.. X X Russ Damske X*) X(*$T-,$S-,$A+ *) XIMPLEMENTATION MODULE BitStuff; X XFROM SYSTEM IMPORT CODE,BYTE,WORD,LONGWORD, SETREG, REGISTER; X X(*** FOR LONGWORDS ***) X XPROCEDURE LAnd( op1, op2 : LONGWORD):LONGWORD; X(* logically AND's 2 longwords *) XBEGIN X SETREG( 6, op1 ); X SETREG( 7, op2 ); X CODE( 0CE86H ); (* and d6,d7 *) X RETURN LONGWORD( REGISTER( 7 ) ); XEND LAnd; X XPROCEDURE LOr(op1, op2 : LONGWORD):LONGWORD; X(* logically OR's 2 longwords *) XBEGIN X SETREG( 6, op1 ); X SETREG( 7, op2 ); X CODE( 08E86H ); (* or d6,d7 *) X RETURN LONGWORD( REGISTER( 7 ) ); XEND LOr; X XPROCEDURE LEor(op1, op2 : LONGWORD):LONGWORD; X(* logically Exclusive OR of 2 longwords *) XBEGIN X SETREG( 6, op1 ); X SETREG( 7, op2 ); X CODE( 0BD87H ); (* eor d6,d7 *) X RETURN LONGWORD( REGISTER( 7 ) ); XEND LEor; X XPROCEDURE LShl(number : LONGWORD; numbits : CARDINAL):LONGWORD; X(* Shifts number an amount (numbits) left *) XBEGIN X CODE ( 07C00H ); (* moveq.l #0.d6 *) X SETREG( 6, numbits ); X SETREG( 7, number ); X CODE( 0EDAFH ); (* lsl d6,d7 *) X RETURN LONGWORD( REGISTER( 7 ) ); XEND LShl; X XPROCEDURE LShr(number : LONGWORD; numbits : CARDINAL):LONGWORD; X(* Shifts number an amount (numbits) right *) XBEGIN X CODE( 07C00H ); (* moveq.l #0.d6 *) X SETREG( 6, numbits ); X SETREG( 7, number ); X CODE( 0ECAFH ); (* lsr d6,d7 *) X RETURN LONGWORD( REGISTER( 7 ) ); XEND LShr; X X(*** FOR WORDS ***) X XPROCEDURE WAnd( op1, op2 : WORD):WORD; X(* logically AND's 2 words *) XBEGIN X SETREG( 6, op1 ); X SETREG( 7, op2 ); X CODE( 0CE46H ); (* and d6,d7 *) X RETURN WORD( REGISTER( 7 ) ); XEND WAnd; X XPROCEDURE WOr(op1, op2 : WORD):WORD; X(* logically OR's 2 ords *) XBEGIN X SETREG( 6, op1 ); X SETREG( 7, op2 ); X CODE( 08E46H ); (* or d6,d7 *) X RETURN WORD( REGISTER( 7 ) ); XEND WOr; X XPROCEDURE WEor(op1, op2 : WORD):WORD; X(* logically Exclusive OR of 2 words *) XBEGIN X SETREG( 6, op1 ); X SETREG( 7, op2 ); X CODE( 0BD47H ); (* eor d6,d7 *) X RETURN WORD( REGISTER( 7 ) ); XEND WEor; X XPROCEDURE WShl(number : WORD; numbits : CARDINAL):WORD; X(* Shifts number an amount (numbits) left *) XBEGIN X CODE ( 07C00H ); (* moveq.l #0.d6 *) X SETREG( 6, numbits ); X SETREG( 7, number ); X CODE( 0ED6FH ); (* lsl d6,d7 *) X RETURN WORD( REGISTER( 7 ) ); XEND WShl; X XPROCEDURE WShr(number : WORD; numbits : CARDINAL):WORD; X(* Shifts number an amount (numbits) right *) XBEGIN X CODE( 07C00H ); (* moveq.l #0.d6 *) X SETREG( 6, numbits ); X SETREG( 7, number ); X CODE( 0EC6FH ); (* lsr d6,d7 *) X RETURN WORD( REGISTER( 7 ) ); XEND WShr; X X(*** FOR BYTES ***) X XPROCEDURE BAnd( op1, op2 : BYTE):BYTE; X(* logically AND's 2 BYTES *) XBEGIN X SETREG( 6, op1 ); X SETREG( 7, op2 ); X CODE( 0CE06H ); (* and d6,d7 *) X RETURN BYTE( REGISTER( 7 ) ); XEND BAnd; X XPROCEDURE BOr(op1, op2 : BYTE):BYTE; X(* logically OR's 2 BYTES *) XBEGIN X SETREG( 6, op1 ); X SETREG( 7, op2 ); X CODE( 08E06H ); (* or d6,d7 *) X RETURN BYTE( REGISTER( 7 ) ); XEND BOr; X XPROCEDURE BEor(op1, op2 : BYTE):BYTE; X(* logically Exclusive OR of 2 BYTES *) XBEGIN X SETREG( 6, op1 ); X SETREG( 7, op2 ); X CODE( 0BD07H ); (* eor d6,d7 *) X RETURN BYTE( REGISTER( 7 ) ); XEND BEor; X XPROCEDURE BShl(number : BYTE; numbits : CARDINAL):BYTE; X(* Shifts number an amount (numbits) left *) XBEGIN X CODE ( 07C00H ); (* moveq.l #0.d6 *) X SETREG( 6, numbits ); X SETREG( 7, number ); X CODE( 0ED2FH ); (* lsl d6,d7 *) X RETURN BYTE( REGISTER( 7 ) ); XEND BShl; X XPROCEDURE BShr(number : BYTE; numbits : CARDINAL):BYTE; X(* Shifts number an amount (numbits) right *) XBEGIN X CODE( 07C00H ); (* moveq.l #0.d6 *) X SETREG( 6, numbits ); X SETREG( 7, number ); X CODE( 0EC2FH ); (* lsr d6,d7 *) X RETURN BYTE( REGISTER( 7 ) ); XEND BShr; X XEND BitStuff. SHAR_EOF chmod 0600 BITSTUFF.MOD || echo "restore of BITSTUFF.MOD fails" sed 's/^X//' << 'SHAR_EOF' > CLI.MOD && X X(* Copyright 1987 fred brooks LogicTek *) X(* *) X(* *) X(* First Release 12/8/87-FGB *) X(* *) X XMODULE cli; X(*$T-,$S-,$A+ *) X(* IMPORT GEMError; *) XFROM SYSTEM IMPORT ADDRESS, CODE, REGISTER, SETREG; XFROM GEMDOS IMPORT Super,Exec,ExecMode,OldTerm; XFROM BIOS IMPORT BConStat, BConIn, Device; XFROM XBIOS IMPORT SuperExec; XFROM LOGIN IMPORT login; XVAR cmd,dev,sr,pc,oldbios,sp,tsp,usp,newbios : ADDRESS; X bios [0b4H] : ADDRESS; X d0,ssv,sspval : ADDRESS; X i : INTEGER; X active : BOOLEAN; X delay,result : INTEGER; X X(*$P-,$S- *) XPROCEDURE multitaskbios; XBEGIN X CODE(2279H,0,4a2H); (* load saveptr *) X CODE(48e1H,1f1fH); (* save regs *) X CODE(23c9H,0,4a2H); (* update saveptr *) X IF active THEN X SETREG(8,oldbios); (* move trap adr *) X CODE(43faH,22); (* lea 26(pc),a1 *) X CODE(2288H); (* move.l a0,(a1) *) X CODE(2279H,0000,04a2H); (* get saveptr *) X CODE(4cd9H,0f8f8H); (* restore regs movem *) X CODE(23c9H,0000,04a2H); (* update saveptr *) X CODE(4ef9H,0,0) (* jmp back to routine *) X END; X CODE(306fH,0); (* move.w 0(a7),a0 get sr *) X sr:=REGISTER(8); X CODE(206fH,2); (* move.l 2(a7),a0 get pc *) X pc:=REGISTER(8); X X IF sr<3ffH THEN (* called from user mode *) X CODE(4e69H); (* move.l usp,a1 *) X CODE(3069H,2); (* move.w 2(a1),a0 *) X dev:=REGISTER(8); X CODE(4e69H); (* move.l usp,a1 *) X CODE(3069H,0); (* move.w 0(a1),a0 *) X cmd:=REGISTER(8); X IF (cmd=2) THEN X active:=TRUE; X INC(delay); X CODE(5c8fH); (* addq.l #6,a7 correct stack *) X sp:=REGISTER(15); X REPEAT X (* set user mode then back to super *) X IF sp=sspval THEN X tsp:=REGISTER(15); X CODE(4e68H); (* move.l usp,a0 *) X usp:=REGISTER(8); X CODE(46fcH,300H); (* move.w $300,sr *) X FOR i:=0 TO 10 DO END; (* busy loop for mx2 *) X CODE(42a7H); (* clr.l -(sp) *) X CODE(3f3cH,20H); (* move.w $20,-(sp) *) X CODE(4e41H); (* trap #1 *) X SETREG(15,tsp); X SETREG(8,usp); X CODE(4e60H); (* move.l a0,usp *) X END; X CODE(48e7H,7ffeH); (* save regs *) X CODE(9bcdH); (* clr a5 *) X newbios:=bios; X bios:=oldbios; X SETREG(0,0); X IF BConStat(Device(dev)) THEN SETREG(0,-1) END; X bios:=newbios; X CODE(4cdfH,7ffeH); (* restore regs *) X d0:=REGISTER(0); X UNTIL d0#0; X CODE(48e7H,7ffeH); (* save regs *) X CODE(9bcdH); (* clr a5 *) X newbios:=bios; X bios:=oldbios; X SETREG(0,BConIn(Device(dev))); X bios:=newbios; X CODE(4cdfH,7ffeH); (* restore regs *) X d0:=REGISTER(0); X SETREG(9,pc); X CODE(2f09H); (* push pc to stack *) X SETREG(9,sr); X CODE(3f09H); (* push sr to stack *) X active:=FALSE; X SETREG(0,d0); (* move char to d0 *) X CODE(2279H,0000,04a2H); (* get saveptr *) X CODE(4cd9H,0f8f8H); (* restore regs movem *) X CODE(23c9H,0000,04a2H); (* update saveptr *) X CODE(4e73H); (* rte *) X END; X IF (cmd=1) THEN X active:=TRUE; X INC(delay); X CODE(5c8fH); (* addq.l #6,a7 correct stack *) X sp:=REGISTER(15); X CODE(48e7H,7ffeH); (* save regs *) X CODE(9bcdH); (* clr a5 *) X newbios:=bios; X bios:=oldbios; X SETREG(0,0); X IF BConStat(Device(dev)) THEN SETREG(0,-1) END; X bios:=newbios; X d0:=REGISTER(0); X CODE(4cdfH,7ffeH); (* restore regs *) X IF d0=0 THEN X (* set user mode then back to super *) X IF sp=sspval THEN X tsp:=REGISTER(15); X CODE(4e68H); (* move.l usp,a0 *) X usp:=REGISTER(8); X CODE(46fcH,300H); (* move.w $300,sr *) X FOR i:=0 TO 10 DO END; (* busy loop for mx2 *) X CODE(42a7H); (* clr.l -(sp) *) X CODE(3f3cH,20H); (* move.w $20,-(sp) *) X CODE(4e41H); (* trap #1 *) X SETREG(15,tsp); X SETREG(8,usp); X CODE(4e60H); (* move.l a0,usp *) X END; X END; X SETREG(9,pc); X CODE(2f09H); (* push pc to stack *) X SETREG(9,sr); X CODE(3f09H); (* push sr to stack *) X active:=FALSE; X SETREG(0,d0); (* move char to d0 *) X CODE(2279H,0000,04a2H); (* get saveptr *) X CODE(4cd9H,0f8f8H); (* restore regs movem *) X CODE(23c9H,0000,04a2H); (* update saveptr *) X CODE(4e73H); (* rte *) X END; X ELSE (* called from super mode *) X CODE(306fH,8); (* move.w 8(a7),a0 *) X dev:=REGISTER(8); X CODE(306fH,6); (* move.w 6(a7),a0 *) X cmd:=REGISTER(8); X IF (cmd=2) THEN X CODE(5c8fH); (* addq.l #6,a7 correct stack *) X REPEAT X CODE(48e7H,7ffeH); (* save regs *) X CODE(9bcdH); (* clr a5 *) X newbios:=bios; X bios:=oldbios; X SETREG(0,0); X IF BConStat(Device(dev)) THEN SETREG(0,-1) END; X bios:=newbios; X CODE(4cdfH,7ffeH); (* restore regs *) X d0:=REGISTER(0); X UNTIL d0#0; X CODE(48e7H,7ffeH); (* save regs *) X CODE(9bcdH); (* clr a5 *) X newbios:=bios; X bios:=oldbios; X SETREG(0,BConIn(Device(dev))); X bios:=newbios; X CODE(4cdfH,7ffeH); (* restore regs *) X d0:=REGISTER(0); X SETREG(9,pc); X CODE(2f09H); (* push pc to stack *) X SETREG(9,sr); X CODE(3f09H); (* push sr to stack *) X SETREG(0,d0); (* move char to d0 *) X CODE(2279H,0000,04a2H); (* get saveptr *) X CODE(4cd9H,0f8f8H); (* restore regs movem *) X CODE(23c9H,0000,04a2H); (* update saveptr *) X CODE(4e73H); (* rte *) X END; X END; X X SETREG(8,oldbios); (* move trap adr *) X CODE(43faH,22); (* lea 26(pc),a1 *) X CODE(2288H); (* move.l a0,(a1) *) X CODE(2279H,0000,04a2H); (* get saveptr *) X CODE(4cd9H,0f8f8H); (* restore regs movem *) X CODE(23c9H,0000,04a2H); (* update saveptr *) X CODE(4ef9H,0,0) (* jmp back to routine *) X XEND multitaskbios; X(*$P+ *) X X(*$P- *) XPROCEDURE dummyvector; XBEGIN X CODE(4e73H); (* rte *) XEND dummyvector; X(*$P+ *) X X(*$P- *) XPROCEDURE setup; XBEGIN X oldbios:=bios; X bios:=ADDRESS(multitaskbios); X CODE(4e75H); (* RTS *) XEND setup; X(*$P+ *) X X(*$P- *) XPROCEDURE setdown; XBEGIN X bios:=oldbios; X CODE(4e75H); (* RTS *) XEND setdown; X(*$P+ *) X XBEGIN; X ssv:=0H; X Super(ssv); X sspval:=ssv; X Super(ssv); X SuperExec(setup); X login; X SuperExec(setdown); X OldTerm; XEND cli. SHAR_EOF chmod 0600 CLI.MOD || echo "restore of CLI.MOD fails" sed 's/^X//' << 'SHAR_EOF' > COM.MOD && X X(* Copyright 1987 fred brooks LogicTek *) X(* *) X(* *) X(* First Release 12/8/87-FGB *) X(* *) X XMODULE com; XFROM XBIOS IMPORT ConfigureRS232,SerialSpeed,FlowFlavor; XFROM BIOS IMPORT BConStat,BCosStat,BConIn,BConOut,Device; XFROM GEMX IMPORT BasePageAddress; XFROM GEMDOS IMPORT OldTerm; XVAR longchar : LONGCARD; X t : BITSET; X char : CHAR; X port : Device; XBEGIN X char:=BasePageAddress^.CmdLine[1]; X IF (char='m') OR (char='M') THEN X port:=HSS; X ELSE X port:=AUX; X END; X IF port=AUX THEN X IF (char=0c) THEN X ConfigureRS232(BPS1200,NONE,-1,-1,-1,-1); X END; X IF (char='0') THEN X ConfigureRS232(BPS300,NONE,-1,-1,-1,-1); X END; X IF (char='1') THEN X ConfigureRS232(BPS1200,NONE,-1,-1,-1,-1); X END; X IF (char='2') THEN X ConfigureRS232(BPS2400,NONE,-1,-1,-1,-1); X END; X IF (char='4') THEN X ConfigureRS232(BPS4800,NONE,-1,-1,-1,-1); X END; X IF (char='9') THEN X ConfigureRS232(BPS9600,NONE,-1,-1,-1,-1); X END; X IF (char='h') OR (char='H') THEN X ConfigureRS232(BPS19200,NONE,-1,-1,-1,-1); X END; X END; X LOOP X IF BConStat(CON) THEN (* read keyboard *) X longchar:=BConIn(CON); X IF (longchar DIV 65536) = 61H THEN EXIT END; X char:=CHAR(longchar); X BConOut(port,char); X END; X X IF BConStat(port) THEN (* read com port *) X longchar:=BConIn(port); X t:=BITSET(longchar); X EXCL(t,7); X char:=CHAR(t); X BConOut(CON,char); X END; X END; X OldTerm; XEND com. SHAR_EOF chmod 0600 COM.MOD || echo "restore of COM.MOD fails" sed 's/^X//' << 'SHAR_EOF' > KILLLP.MOD && XMODULE killlp; XFROM SYSCALL IMPORT Trigger,SpintInfo; XFROM GEMDOS IMPORT Term; XFROM SYSTEM IMPORT ADDRESS,ADR; XFROM Terminal IMPORT WriteString,WriteLn; XVAR ok : BOOLEAN; X spintcmd : POINTER TO ARRAY [0..1] OF LONGCARD; XBEGIN X IF SpintInfo(0,spintcmd) THEN X spintcmd^[0]:=99; X ok:=Trigger(0); X ELSE X WriteLn; X WriteString("Background spooler not running."); X WriteLn; X ok:=Term(-1); X END; X ok:=Term(0); XEND killlp. SHAR_EOF chmod 0600 KILLLP.MOD || echo "restore of KILLLP.MOD fails" sed 's/^X//' << 'SHAR_EOF' > LOGIN.DEF && XDEFINITION MODULE LOGIN; X X(* read passwd file and sign on user *) XPROCEDURE login; X X(* encrypt password *) XPROCEDURE crypt(VAR red,crypto: ARRAY OF CHAR); X XEND LOGIN. X SHAR_EOF chmod 0600 LOGIN.DEF || echo "restore of LOGIN.DEF fails" sed 's/^X//' << 'SHAR_EOF' > LOGIN.MOD && XIMPLEMENTATION MODULE LOGIN; SHAR_EOF echo "End of part 2, continue with part 3" echo "3" > s2_seq_.tmp exit 0