{dbinit.mc
Last edited: Purcell,     3-Feb-85 21:52:44  interface real page stays at 3 {%4}.
Lichtenberg 20-Jun-85 18:42:56 Added daybreak IO port initialization
Lichtenberg 28-May-85 21:00:29 Cleanup.
Lichtenberg 18-Jun-85 15:26:24 Map the IO page.
by cal 11-Jan-85 14:36:07
}


{*** WARNING:
          The following constants are used without labels in this module:
	  Real page # of the beginning of the usable real memory - See comment #RP#
	  Virtual Page # of the beginning of mapped memory - See comment #VP#
	  

}
Reserve[0F6F,0FFF];	{Kernel}

SetTask[0];
RegDef[rFP2VP,R,9];  {isn't having 8 extra r registers great?!?}
RegDef[rhFP2VP,RH,9];

StartAddress[Germ];

Set[IORgnVP, 040];   {rotated 8 bits to the right}
Set[IORgnRP, 05];   {rotated 8 bits to the right}
Set[IORgnSize, 64'd];

Set[InterfacePageRP,3];

Set[bigVMrefFlg, 75'b];
Set[vmSizeLoc, 100'b];
RegDef[u3FFF,U,15];

Set[JumpAddrC1, 0F07]; {Noop at this addr -- replace by GOTO[x] to start at x, c2}
Set[JumpAddrC2, 0F08]; {Noop at this addr -- replace by GOTO[x] to start at x, c3}
Set[JumpAddrC3, 0F09]; {Noop at this addr -- replace by GOTO[x] to start at x, c1}


Set[T0Count, 40];
Set[T1Count, 41];
Set[T2Count, 42];
Set[T012Control, 43];
Set[T0Disable, 48];
Set[T0Enable, 4C];
Set[T12Disable, 50];
Set[T12Enable, 54];

Set[T0Mode2, 34];
Set[T1Mode0, 50];
Set[T1Mode2, 74];
Set[T2Mode2, 0B4];
{
Set[T0InitialLSB, 035];
Set[T0InitialMSB, 0C]; {0C35 hex = 3125 decimal counts = 50 milliseconds}
}


Set[T0InitialLSB, 011];
Set[T0InitialMSB, 04]; {0C35 hex = 1041 decimal counts = 16 milliseconds}

BootTrap: {From trap branch in Refill.mc ----?}
	Noop,						       c1, at[JumpAddrC1];
	Noop,						       c2, at[JumpAddrC2];
	Noop,						       c3, at[JumpAddrC3];

Germ:

{set up timer counters}

at[0F00],


	rhRx ← T0Disable,					c1;
	TOSH ← T0InitialLSB,					c2;
	TT ← T0Mode2,						c3;

	IO ← [rhRx, 0], ClrMPIntIOP,				c1;
	MDR ← 0, {disable counter 0}				c2;
	rhRx ← T12Disable,					c3;

	IO ← [rhRx, 0],						c1;
	MDR ← 0, {disable counters 1 and 2}			c2;
	rhRx ← T012Control,					c3;

	IO ← [rhRx, 0],						c1;
	MDR ← TT, {set counter 0 mode},				c2;
	TT ← T2Mode2,						c3;

	IO ← [rhRx, 0],						c1;
	MDR ← TT, {set counter 2 mode},				c2;
	rhRx ← T0Count,						c3;

	IO ← [rhRx, 0],						c1;
	MDR ← TOSH, {set counter 0 initial count LSB},		c2;
	TOSH ← T0InitialMSB,					c3;

	IO ← [rhRx, 0],						c1;
	MDR ← TOSH, {set counter 0 initial count MSB},		c2;
	rhRx ← T2Count,						c3;

	IO ← [rhRx, 0],						c1;
	MDR ← 0, {set counter 2 initial count LSB},		c2;
	TT ← T1Mode0,						c3;

	IO ← [rhRx, 0],						c1;
	MDR ← 0, {set counter 2 initial count MSB},		c2;
	rhRx ← T0Enable,					c3;

	IO ← [rhRx, 0],						c1;
	MDR ← 0, {enable counter 0}				c2;
	rhRx ← T12Enable,					c3;

	IO ← [rhRx, 0],						c1;
	MDR ← 0, {enable counters 1 and 2}			c2;
	rhRx ← T012Control,					c3;

	IO ← [rhRx, 0],						c1;
	MDR ← TT, {set counter 1 setup mode},			c2;
	TT ← T1Mode2,						c3;

	IO ← [rhRx, 0],						c1;
	MDR ← TT, {set counter 1 mode},				c2;
	rhRx ← T1Count,						c3;

	IO ← [rhRx, 0],						c1;
	MDR ← 0, {set counter 1 initial count LSB},		c2;
	TOSH ← 1,							c3;

	IO ← [rhRx, 0],						c1;
	MDR ← 0, {set counter 1 initial count MSB}, 	c2;
	uWDC ← TOSH, ClrIE,  {disable interrupts}			c3;

	rhTT ← 6'b{INTERFACEspace},			c1;

{update Interface page and interpret FPTOVP}
StartDBInit:
	MAPA ← 4, 	c2;
	, c3;
	
	, c1;
	TT ← 0{INTERFACEbase},	c2;
	TT ← TT LRot8,	c3;
	

{Time to vacate the map}

	rhRx← {1%M}4,		c1;
 	Rx ← Rx xor ~Rx,	c2;  
	TOS ← 60{vacant},	c3;
	
vacLp:	MAR← [rhRx, Rx+0], ZeroBr,	c1;
	MDR← TOS{vacant}, Rx← Rx-1, BRANCH[$, vDone],	c2;
vac3:	GOTO[vacLp],	c3;

vDone: Noop,	c3;

	Rx ← InterfacePageRP ,	c1;  
	Rx ← Rx LRot8, c2;

	rhRx ← 0C0, Rx ← Rx + 0C0{dirty},	c3;

	Map{InterfacePage} ← [rhTT,TT],	c1;
	MDR ← Rx,	c2;
	,	c3;

	MAR← [rhRx, 15'b{MachineType} + 0],	c1;
	MDR ← 8{\DAYBREAK},	c2;
	TOS ← 0C,	c3;
 
	
{For now, we'll tell the machine how much memory it has:}
	
{Look up the FP of the FP2VP table - we'll need it later}

	MAR ← [rhRx, 73'b{fp2vp} + 0], c1;
	TOS ← TOS LRot8, c2;
	rFP2VP ← MD, c3;
	
{rFP2VP was a file page.  We have to add in the appropriate offset from the beginning
 of real memory.  For the daybreak, the sysout file was loaded in starting at what would have
 been RP 2 on the DLion, but is now moved up 300H pgs by the gap in the real address space}
 
	rFP2VP ← rFP2VP + 0FF + 1, {and the additional 300H} c1;  
	rFP2VP ← rFP2VP + 0FF + 1, {and the additional 300H} c2;  
	rFP2VP ← rFP2VP + 0FF + 1, {and the additional 300H} c3;  
	
	Q ← TOS, c1;
	TOS ← ~0FF, c2;
	rFP2VP ← rFP2VP + 1, c3; {add in pilot page offset problem}
	
	rhFP2VP ← rFP2VP ← rFP2VP LRot8, c1;
	TOS ← ~0FF, c2;
	rFP2VP ← rFP2VP and TOS, c3;
	
{r/rh FP2VP contains the REAL address of the start of the FP2VP table.
 Real Memory starts at FP 560h, so that's the offset to be added to 
 the beginning of FP2VP....    #RP#}
 	TOS ← 2, c1;
	TOS ← TOS LRot8, c2;
	TOS ← TOS + 5F, c3;   
	
	
	rFP2VP ← rFP2VP + TOS, c1;
	
	TOS ← 5, c2;
	TOS ← TOS LRot8, c3;  {see c3 of next click}

	MAR ← [rhRx, bigVMrefFlg  + 0], c1;
	MDR ← 1 {true}, c2;
	TOS ← TOS + 60, c3;
		
	
{faking the size of real memory at 1.0 mb plus display bank... but fp2vp routines
 use this number to compare with the last real page number, so for FP2VP setup it has
 to be the real mccoy...  BFF.  We'll tell Lisp 8FF pages exist on the IFPage}
 
 
{=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=}

{this section tells Lisp via the IFPage how much memory it has.

    0CFF = 1.6 megabytes  (use TT ← 0D)
    1CFF = 3.5 megabytes  (use TT ← 1D)
    1BFF = something	  (use TT ← 1C)
    
}

	TT ← 1D, {0D for smallmem}	c1;
	TT ← TT LRot8,	c2;
	Q ← TT - 1,	c3;


	MAR← [rhRx, 70'b{NRealPages} + 0],	c1;
	MDR ← Q{NRealPages} ,	c2;


{=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=}

	TT  ← RShift1 0, SE←1,	c3;
	MAR ← [rhRx, vmSizeLoc + 0], c1;
	MDR ← TT, c2;
	, c3;


{=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=}

{this section tells the FP2VP routines how much memory to map:

   0FFF = 1.6 megabytes  (use TT ← 10)
   1FFF = 3.5 megabytes  (use TT ← 20)
   1EFF = something      (use TT ← 1F)
   
   
 
}

	TT ← 20,	c1;	  
	TT ← TT LRot8,	c2;
	Q ← TT - 1,	c3;


	

{********************************************************************
   interpret FPTOVP setup -- assume FPTOVP doesn't cross segment
   for i(acR) ← 501'b=141h(201h) IOPage+1 to MaxRealPage (rC)	
	unless FPTOVP[i-1]=none (-1)	
	do MAP[FPTOVP[i-1]]:vp ← i	
********************************************************************}

{We know where FP2VP is in REAL memory now -- it's at r/rh FP2VP
 Q Hasn't been touched - it contains the number of the last real page
 TOS is "i": it contains the number of the page that starts it all off, which
 in this case is 25Eh, as that's the first real page we're mapping.}
 
{ TOS (our "i") already contains 560H, the proper index into the table}

{Subtract the offset from the beginning of VMEM that the sysout was loaded into #VP#}
	

	, c1;
{Set up rh/Rx to point at the map, 40000}
	Rx ← 0, c2;
	rhRx ← 4, c3;
	

{ *******************************************************************
	interpret FPTOVP Loop 	
	r/rh FP2VP      FPTOVP[i-1] ptr 	
	rB:  (Rx)	FPTOVP[i-1]:vp	
	rC:  (TOS)	i ← {501'b=141h}{201h}IOPage+1		
	Q:      	NRealPages= C00		
	rBrh:(rhRx)	10000{Map}
*********************************************************************}


{ Top of FP2VP Loop:  Dig the VP number out of the FP2VP Table, put the 
   VP number in Rx }

f2vLp:	MAR← rFP2VP ← [rhFP2VP, rFP2VP + 0],	c1;
	,	c2;
	Rx{vp} ← MD ,	c3;

{ If the entry we just got was a -1 (FFFF Hex), don't change the map entry
  (leave it vacant) }


	Ybus ← Rx + 1, CarryBr,	c1;
 	TOS ← TOS LRot8, BRANCH[$, none],	c2;
	, c3;

	MAR← [rhRx, Rx + 0],c1;
	MDR ← TOS{i}, GOTO[none],	c2;
none:	TOS ← TOS LRot8,	c3;

	TOS ← TOS + 1,	c1;
	Ybus ← TOS xor Q{NRealPages}, ZeroBr,	c2;
	rFP2VP ← rFP2VP + 1, BRANCH[f2vLp, $],	c3;

	Rx ← 0FF,	c1;
	TOS ← {2%M}5,		c2;	
	rhRx ← {1%M}4,	c3;

{ *****  Map[IOPageVp=0FF] ← Real 5,,0000  ***** }
	rhTT ← 0, c1;
	Rx ← oldIOPageHigh, c2;    {mitch was shocked... screwed up real bad here!
							signed, James O'Toole   (with a capital T)
					Now mitch is really shocked.  Probably due to lack of
					sleep and boredom waiting for this and that.  This
					change got put in the wrong file!!!	     }
	TT ← ~0FF, c3;
	
	Map ← [rhTT, TT], c1;
	MDR ← Rx, c2;
	, c3;


{ ***** Map the Dove I/O region: 64 pages from VP[C00] to RP[500] ******}

	{start u register init here}
	Rx ← 0C1 LRot1,	c1;
	Rx ← Rx LRot1,	c2;
	uPcBreak ← Rx,	c3;

	,	c1;
	Q ← rhRx,	c2;
	UGsave ← Q,	c3;

	Rx ← VALspace,	c1;
	uValHigh ← Rx,	c2;
	TT ← 1,	c3;

	Rx ← Rx xor ~Rx,	c1;
	unboundPvar ← Rx,	c2;
	unboundFvar ← Rx,	c3;

	uStkLimO ← Rx,	c1;
	uWP ← 0,	c2;
	uWDC ← TT{uWDC inited by mesaInit},	c3;

	Rx ←  ~0FD,	c1;
	Rx ← Rx LRot8,	c2;
	uBfResidualRhmask ← Rx{2FF},	c3;

	Rx ←  0A0,	c1;
	Rx ← Rx LRot8,	c2;
	uFreeStackBlock ← Rx{0A000},	c3;

	Rx ←  0FF + 1,	c1;
	uFxNoPushReturn ← Rx{100h},	c2;
	Rx ←  LShift1(Rx + Rx), SE←0,	c3;

	uFxInCall ← Rx{400h},	c1;
	Rx ←  7F,	c2;
	u7F ← Rx{7F},	c3;

	Rx ←  ~0FF,	c1;{OK}
	u0FF ← ~Rx{~0FF},	c2;
	uFF00 ←  Q ← Rx{~0FF},	c3;

	Rx ← Q{0FF00} or 1,	c1;
	Rx ← Rx LRot8,	c2;
	u1FF ← Rx{1FF},	c3;

	Rx ← Q{0FF00} or 3,	c1;
	Rx ← Rx LRot8,	c2;
	uTT3FF ← Rx{3FF},	c3;

	Rx ← Q{0FF00} or 3,	c1;
	Rx ← Rx LRot8,	c2;
	,	c3;

	Rx ← Q{0FF00} or 0F,	c1;
	Rx ← Rx LRot8,	c2;
	u0FFF ← Rx{0FFF},	c3;

	Rx ← Q{0FF00} or 1F,	c1;
	Rx ← Rx LRot8,	c2;
	u1FFF ← Rx{1FFF},	c3;

	Rx ← Q{0FF00} or 3F,	c1;
	Rx ← Rx LRot8,	c2;
	uTT3FFF ← Rx{3FFF},	c3;

	Rx ← Q{0FF00} or 3F,	c1;
	Rx ← Rx LRot8,	c2;
	u3FFF ← Rx{3FFF},	c3;

	Rx ← Q{0FF00} or 7F,	c1;
	Rx ← Rx LRot8,	c2;
	u7FFF ← Rx{7FFF},	c3;

	Rx ← Q{0FF00} or 7,	c1;
	Rx ← Rx LRot8,	c2;
	u7FF ← Rx{7FF},	c3;

	rhInt ← rInt ← 0+0,	c1;  		{Set interrupts pending = 0}
	Rx ← Rx xor 1,	c2;
	u7FE ← Rx{7FF},	c3;
	
	Rx ← 20, c1;
	Rx ← Rx LRot8, c2;
	u2000 ← Rx, c3;

	Rx ← 0,	c1;
	uLispOptions ← Rx,	c2;
	TT ← RShift1 0, SE←1 , c3;

	Rx ← 80,	c1;
	Rx ←  Rx LRot8,	c2;
	uBFmark ← Rx{8000},	c3;

{compliance: using uSTACKspace with duplicated high byte for bind ptr}

	Rx ← STACKspace,	c1;
	Rx ← Rx LRot8,	c2;
	Rx ← Rx or STACKspace,	c3;

	u8000 ← TT,	c1;
	uSTACKspace ← Rx,	c2;
	Rx ← 0C0,	c3;

	Rx ←  Rx LRot8,	c1;
	Noop,	c2;
	uFXmark ← Rx{C000},	c3;

	Set[UFNTablePageHalf, Rshift[UFNTablebase, 9]];
	Rx ←  UFNTablePageHalf,	c1;
	Rx ←  Rx LRot8,	c2;
	uUFNTableBaseHalf ← Rx,	c3;

	Rx ← 88,	c1;
	Rx ← Rx LRot8,	c2;
	Q ← Rx,	c3;
	
	TT ← LShift1 97, SE ← 0,				c1;
	uMaintPanel ← TT, {012E}				c2;
	Q ← rhIOP ← 5,						c3;
	
	uIORgnHigh ← Q,						c1;
	rIORgn ← 20,						c2;
	rIORgn ← rIORgn LRot8, {IORgn real addr = 52000}	c3;

	rIOP ← rIORgn + 2,	c1;
	Rx ← 1 RRot1, rhRx ← 1,	c2;
	Rx{4000} ← Rx RShift1, c3;


{**** Clear out the old IOPage ***}

	TT ← 0FF, c1;
	rhTT ← oldIOPageHigh, c2;
	Rx ← 0, c3;
ClrIOPgLp:	
	MAR ← [rhTT, TT + 0],  BRANCH[$,DoneIOPage], c1;
	MDR ← Rx, c2;
	TT ← TT - 1, NegBr,GOTO[ClrIOPgLp],  c3;
DoneIOPage: , c2;
	,c3;
	
	{Say "Hi"... write 1185 on the MP}
	TOS ← 4,  L3 ← L3.INITMP, c1;
	TOS ← TOS LRot8, c2;
	TOS ← TOS + 0A1, c3;
	
	TT ← uMaintPanel, CALL[WriteMPEntry], c1;

	
	, c1, at[L3.INITMP,10,DoveMiscOut];
	SetIE {enable interrupts}, c2;
	GOTO[dbinitthru],	c3;

	{ E N D }