; ; File: Clock.a ; ; Contains: This file contains routines to directly access the clock. ; ; Copyright: © 1985-1993 by Apple Computer, Inc., all rights reserved. ; ; Change History (most recent first): ; ; 12/13/93 PN Roll in KAOs and Horror changes to support Malcom and AJ ; machines. ; 11/9/93 KW added eieioSTP macros. Only expanded for CygnusX1 ROM ; 5/28/92 kc Change the conventions of ValidatePRAM so that it can be called ; by bsr instead of bsr6. ; 5/28/92 kc Added Register saves/.restores to ValidatePRAM. ; 5/28/92 kc Roll in Horror Changes. Comments follow: ;

11/6/91 SWC Re-wrote clock and PRAM routines to be table-driven so that ; future expansion should be really simple (and clean). Hardware ; dependent routines will now be found in ClockPRAMPrimitives.a. ; Moved PRamIO here from ClockPatches.a since that was all that ; was left there. ; 5/17/92 kc Prepend via equates with "v". ; 5/5/92 SES Rolled in ReadDateTime patch functionality from PatchIIciROM.a. ; This patch is only for machines with Egret. Egret's tick handler ; was modified to update the Time lowmem global, so ReadTime ; simply returns with noErr if on an Egret-based machine. ; <15> 10/18/91 JSM Get rid of all the stupid conditionals. ; <14> 8/29/91 JSM Cleanup header. ; <13> 6/12/91 LN Changed #include 'HardwareEqu.a' to 'HardwarePrivateEqu.a' ; <12> 9/14/90 MSH Removed the lame video-based PRAM scheme for Waimea and power ; manager based clock. TIM has a conventional RTC. ; <11> 7/3/90 CCH Fixed problem with PRAMIO writes. ; <10> 5/14/90 MSH Test for clock in Power Manager used wrong bits. ; <9> 4/12/90 MSH Fixed the Waimea PRAM interface to use the universal tables ; correctly. ; <8> 3/27/90 HJR Add Conditional so that HcMac will build. ; <7> 3/22/90 MSH SysUtil and Clock rewritten to place all hardware dependent ; routines in clock and to remove redundant parameter RAM reading ; and writing routines. Also added Waimea versions of these ; routines. ; <6> 2/28/90 GMR Made changes for Egret code to match new Egret equates. ; <5> 2/12/90 GMR Added ENDIF to fix build for MacPP,HcMac. ; <4> 2/11/90 GMR Fixed WriteEgretPRAM, to delay 100us at end of packet, to give ; Egret time to see completion (fixes a lock up problem). ; <3> 2/10/90 GMR Made ValidatePRAM universal, to support Egret. Pram calls now ; temporarily use Egret's Wr6805Addr command instead of WrPram ; until 6805 code is fixed in next mask. ; <2> 2/4/90 GMR Added partial Egret support, in ReadXPram, WriteXPram, and new ; low level ReadPramByte (for use before Egret manager is ; initialized, e.g. by MMU.a). Still need Egret version of ; ValidatePRAM ; <1.6> 6/16/89 SWC PRAM validation didn't: shifted one byte too many, but doesn't ; anymore. ; <1.5> 6/15/89 SWC Added ValidatePRAM to validate, and if necessary, initialize ; PRAM at start time. ; <1.4> 4/13/89 GGD Removed the support for the Rev7 MacII logic board, and all of ; the ugly conditionals that were needed to support it. Removed ; usage of nEqu.d and StartMacs. Removed conditionals which ; supported two spellings of vRTCEnb (with and without the 'v'), ; and made the spellings consistent in HardwareEqu.a, changed to ; use bit definition equate instead of hard coded constants for ; vRTCData. Converted to feature based conditionals. Added offset ; vBufB to via accesses to clarify which register is being ; accessed. Changed interface to ClkNoMem to have caller pass in ; VIA base address in A1. ; <1.3> 3/6/89 GGD Moved OneSecInt handler from IntHnd to Clock.a. ; <1.2> 2/16/89 rwh Removed conditionals for non-working Vias. ; <1.1> 11/10/88 CCH Fixed Header. ; <1.0> 11/9/88 CCH Adding to EASE. ; <•1.3> 9/23/88 CCH Got rid of inc.sum.d and empty nFiles ; <1.2> 9/16/88 rwh Roll-in onMvMac changes ; <1.1> 6/10/88 MSH Changes made in Feb 88 did not get rolled into ease... Brian! ; <1.0> 2/10/88 BBM Adding file for the first time into EASE… ; 11/18/87 rwh Fix C880 - no RTS5 @ end of ClkNoMem for non-Laguna machines! ; 10/29/87 rwh Port to Modern Victorian (onMvMac) ; 10/27/87 MSH Bug fixes mostly, but did add a XPram mapping table for Laguna. ; 10/21/87 MSH Forgot to load some pointers before call pmgr for Laguna. ; 9/3/87 MSH Port to HcMac (Laguna) requires power manager interface. Does ; not support parameter ram bytes $60-$DF. ReadFrClk, SendToClk ; not supported. Removed ReadPram IMPORT, nobody uses it. ; 10/9/86 bbm Modified to mpw aincludes. ; 8/7/86 RDC Added changes for new NuMac hardware (clk now same as Mac) ; 6/26/86 WRL Put ClkNoMem, ReadFrClk, and SendToClk back in this file (from ; StartInit). ; 4/15/86 RDC Enabled access to XPRamRead and XPRamWrite routines for Reno ; (NuMac) ; 2/19/86 BBM Made some modifications to work under MPW ; 10/31/85 BBM arithmetic done wrong in Read/WriteXPRam. ; 10/30/85 LAK No longer call ReadPram after extended read/write. Use jump ; table vector rather than GetTrapAddress. ; 10/29/85 BBM needed to save one more register across ClkNoMem call. ; 10/25/85 RDC Removed MidMac equate for clock routines (now moved to ; startmain) ; 10/23/85 BBM Changed calling interface to ReadXPRam and WriteXPRam. Also now ; checks if new clock chip present before executing ReadXPRam and ; WriteXPRam. ; 10/3/85 so these routines can be called from the start code (before memory ; test). This is done via three macros: RTS5, BSR6 and RTS6. Also ; supported is the extended command for reads and writes to the ; new clock chip for mac. The entry for the lowest level routine ; just added is ClkNoMem, and it is accessed via BSR5. Added two ; new traps to access all of extra parameter ram, ReadXPRam and ; WriteXPRam. ; 10/2/85 BBM made the lowest level routines not use any memory (like the ; stack), ; 7/24/85 RDC new today - moved from Sysutil.text added changes for MidMac to ; use new interface, int levels ;___________________________________________________________________________________ BLANKS ON STRING ASIS PRINT OFF ; LOAD 'StandardEqu.d' INCLUDE 'HardwarePrivateEqu.a' INCLUDE 'UniversalEqu.a' ; <1.5> INCLUDE 'IOPrimitiveEqu.a' ;

PRINT ON ; Clock PROC EXPORT EXPORT OneSecInt ; <1.3> EXPORT ReadXPRam,WriteXPRam EXPORT ValidatePRAM,PramIO IMPORT PRAMInit ; <1.5> IMPORT PRAMInitTbl ; <1.5> PRINT NOGEN IF NOT BlackBirdDebug THEN ;_______________________________________________________________________ <1.3> ; ; Routine: OneSecInt ; ; Arguments: A1 (input) -- Address of VIA1 ; ; Function: Services 1-second interrupt from clock . . . ; ; NOTE: This handler expects that the interrupt is still pending, and clears ; it by clearing the CA2 interrupt flag on VIA 1 (base address passed ; in register A1). This is correct for all current hardware implementations ; but may not be in the future. ; we support alarm clock flash here in the system code: other functions may ; start the flash simply by clearing bit 1 of AlarmState ; ; AlarmState bit 7 = flash parity ; bit 6 = 1 to enable initial beep ; bit 5 = set to 0 every second by this code (flag to GNEFilter) ; bit 1 = 0 to start flashing ; bit 0 = 0 for global flash enable ; ;_______________________________________________________________________ OneSecInt MOVE.B #1< ADDQ.L #1,Time ; count the second BCLR #5,AlarmState ; flag GNEFilter to flash if enabled TST.B SPVolCtl ; bit 7 is alarm enable BPL.S @done ; exit if not enabled MOVE.L SPAlarm,D0 BEQ.S @done ; exit if no alarm CMP.L Time,D0 ; is it past time? BHI.S @done ; exit if not ; flash apple menu item if there's a window world BCLR #1,AlarmState ; flag GNEFilter to flash @done RTS ; <1.3> ENDIF ;•••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••• ; This is a hack for the one second interrupt. PG&E is suppose to be providing the interrupt ; and it currently does not. After it is working again, this code should disappear. ; REALLY!!! Disappear... ; IF BlackBirdDebug THEN OneSecInt MOVEA.l A1, A0 ; MOVE.l #1000,D0 ; 1 second MOVEA.l jPrimeTime, A1 ; get pointer to the PrimeTime routine JSR (A1) ; restart time manager task ADDQ.L #1,Time ; count the second BCLR #5,AlarmState ; flag GNEFilter to flash if enabled ; we support alarm clock flash here in the system code: other functions may ; start the flash simply by clearing bit 1 of AlarmState ; ; AlarmState bit 7 = flash parity ; bit 6 = 1 to enable initial beep ; bit 5 = set to 0 every second by this code (flag to GNEFilter) ; bit 1 = 0 to start flashing ; bit 0 = 0 for global flash enable TST.B SPVolCtl ; bit 7 is alarm enable BPL.S @done ; exit if not enabled MOVE.L SPAlarm,D0 BEQ.S @done ; exit if no alarm CMP.L Time,D0 ; is it past time? BHI.S @done ; exit if not ; flash apple menu item if there's a window world BCLR #1,AlarmState ; flag GNEFilter to flash @done RTS ; <1.3> ENDIF ;•••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••••• ;________________________________________________________________________________________ ; ; Routine: PramIO ; ; Inputs: A0 - pointer to table of base addresses ; A1 - pointer to ProductInfo record for this machine ; A3 - pointer to PRAM I/O buffer ; D1 - flags indicating which external features are valid ; D3 - bit 31: 0=read, 1=write ; bits 30..16: number of PRAM bytes to read/write (1-256) ; bits 15.. 0: starting PRAM address (0-255) ; ; Outputs: none ; ; Trashes: A3,D3 ; ; Function: reads/writes PRAM bytes from the caller's buffer before traps are set up ;________________________________________________________________________________________ PramIO MOVEM.L D0-D2/A0-A2,-(SP) ;

MOVEA.L A1,A2 ; point to the ProductInfo

ADDA.L ProductInfo.ClockPRAMPtr(A1),A2 ; and get the address of its clock/PRAM table

MOVE.L 4*cpXPRAMIO(A2),D2 ; get the offset to the routine

BEQ.S @NoEntry ; -> this function is not supported

ADDA.L D2,A2 ; calculate the routine's address

JSR (A2) ; and call it

@NoEntry MOVEM.L (SP)+,D0-D2/A0-A2 ;

RTS ;

;________________________________________________________________________________________ ; ; Routine: ReadXPRAM, WriteXPRAM ; ; Inputs: A0 - pointer to caller's buffer ; D0 - [number of bytes to transfer][starting PRAM address] ; D1 - bit 12: 1=read, 0=write ; ; Outputs: D0 - result code ; ; Trashes: none ; ; Function: reads or writes extended PRAM bytes into the caller's buffer ;________________________________________________________________________________________ ReadXPRAM MOVEM.L A0-A3/D1-D3,-(SP) ;

MOVE.W #($17<<8)+%11100000,D1 ; control byte + mask for reg address[7..5]

BRA.S rwXCommon ;

WriteXPRAM MOVEM.L A0-A3/D1-D3,-(SP) ;

MOVE.W #($07<<8)+%11100000,D1 ; control byte + mask for reg address[7..5]

rwXCommon BTST.B #hwCbClock-8,HWCfgFlags ; do we have a new clock chip (256 PRAM bytes)?

BEQ.S @rwXPRAMErr ; -> no

MOVEA.L UnivInfoPtr,A1 ; point to this machine's product info

ADDA.L ProductInfo.ClockPRAMPtr(A1),A1 ; and get the address of its clock/PRAM table

MOVE.L 4*cpXParam(A1),D3 ; get the offset to the routine

BEQ.S @NoEntry ; -> this function is not supported

ADDA.L D3,A1 ; calculate the routine's address

JSR (A1) ; and call it

@NoEntry MOVEM.L (SP)+,A0-A3/D1-D3 ;

RTS ;

@rwXPRAMErr MOVEQ #PRWrErr,D0 ; no extended PRAM so just return an error

BRA.S @NoEntry ;

;________________________________________________________________________________________

; ; Routine: ValidatePRAM ; ; Inputs: A6 - return address ; A0 - pointer to table of base addresses ; A1 - pointer to ProductInfo record for this machine ; D0 - flags indicating which base addresses are valid ; D1 - flags indicating which external features are valid ; D2 - bits 31..16, hwCfgFlags info (possibly unknown) ; bits 15.. 8, BoxFlag info (possibly unknown) ; bits 7.. 0, Address Decoder Kind (zero if unknown) ; D7 - bits 31..16: logic board type ; bits 15.. 0: CPU type (0 = 68000, 1 = 68010, etc) ; ; Outputs: none ; ; Trashes: A2,A3 ; ; Function: checks that parameter RAM is valid, and if it's not, initializes it to ; its default state ;________________________________________________________________________________________ ValidatePRAM MOVEM.L D0-D3/A0-A3,-(SP) ; register saves from StartINIT <8.6> LEA -256(SP),SP ; allocate a PRAM buffer on the stack

MOVEA.L SP,A3 ; point to the buffer

MOVE.L #(0<<31)|\ ; read

(32<<16)|\ ; 32 bytes

(0<<0),D3 ; from PRAM address 0

BSR PramIO ;

CMPI.B #$A8,16(SP) ; is the "old" (20 byte) PRAM signature valid?

BEQ.S @CheckXPRAM ; -> yes, move on

BIGLEA PRAMInit,A3 ; point to table of default values

MOVE.L #(1<<31)|\ ; write

(16<<16)|\ ; 16 bytes

(16<<0),D3 ; starting at PRAM address 16

BSR PramIO ; write out the first 16 bytes of original PRAM

BIGLEA PRAMInit+16,A3 ; point to table of default values

MOVE.L #(1<<31)|\ ; write

(4<<16)|\ ; 4 bytes

(8<<0),D3 ; starting at PRAM address 8

BSR PramIO ; write out the last 4 bytes of original PRAM

@CheckXPRAM LEA @XPRAMSig,A3 ;

MOVE.L 12(SP),D3 ; are the extended PRAM signature bytes valid?

CMP.L (A3),D3 ;

BEQ.S @Done ; -> yes, we're done

MOVE.L #(1<<31)|\ ; write

(4<<16)|\ ; 4 bytes

(12<<0),D3 ; starting at PRAM address 12

BSR PramIO ; write out the correct extended PRAM signature bytes

MOVEA.L SP,A3 ; point to our stack buffer

MOVEQ #(256-32)/4-1,D3 ; and zero each byte

@ClearBuf CLR.L (A3)+ ;

DBRA D3,@ClearBuf ;

BIGLEA PRAMInitTbl,A2 ; point to the table of default extended PRAM values

LEA $76-32(SP),A3 ; and where they'll go in the buffer

MOVEQ #$89-$76,D3 ; copy them into the buffer

@CopyXDefs MOVE.B (A2)+,(A3)+ ;

DBRA D3,@CopyXDefs ;

MOVEA.L SP,A3 ; point to the buffer

MOVE.L #(1<<31)|\ ; write

((256-32)<<16)|\ ; 256-32 bytes

(32<<0),D3 ; starting at PRAM address 32

BSR PramIO ;

@Done LEA 256(SP),SP ; clean up the stack

MOVEM.L (SP)+,D0-D3/A0-A3 ; restore regs from StartINIT <8.6> RTS ;

@XPRAMSig DC.L 'NuMc' ; extended PRAM validity bytes (slot-based machines)

END