sys7.1-doc-wip/Patches/PatchIIROM.a

7124 lines
285 KiB
Plaintext
Raw Permalink Blame History

This file contains invisible Unicode characters

This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

;
; Hacks to match MacOS (most recent first):
;
; <Sys7.1> 8/3/92 Clobbered SlotVBLQ after disposing the block to prevent use-after-free.
; 9/2/94 SuperMario ROM source dump (header preserved below)
;
;
; File: PatchIIROM.a
;
; Contains: patches for the ROMs first shipped in a Macintosh II ($0178)
;
; Copyright: © 1986-1992 by Apple Computer, Inc., all rights reserved.
;
; Change History (most recent first):
;
; <90> 1/19/92 DTY Look at emAppleTalkInactiveOnBoot before checking out the
; AppleTalk version. If AppleTalk was inactive, dont set up the
; LAP Manager. This is part of a large conspiracy to convince the
; universe that AppleTalk really isnt around if it is inactive.
; <89> 12/4/91 csd #1016447: Added support for Scruffy. Dont install the MaxBlock
; patch if Scruffy in installed.
; <88> 6/12/91 LN added #include 'InternalOnlyEqu.a'
; <87> 6/12/91 LN removed #include 'HardwareEqu.a'
; <86> 3/17/91 eh Serial driver status calls 9 and $8000 now return hardcoded
; driver version instead of getting it from DCE. This obviates the
; need for the linked patch to _Open to patch the version number
; in the DCE, a fix which was causing FileShare to crash.
; <85> 3/4/91 dba dty: get rid of SysVers conditionals
; <84> 2/21/91 eh (djw) Fixed bug in serial driver that was preventing use of one
; port when Nike was printing on the other.
; <83> 2/6/91 eh (djw) Fix bug that was causing Smartcom not to be able to do a
; direct connect. We were trashing d1 in the FixInitSCC patch. Now
; we don't.
; <82> 1/19/91 mbs (jg) Include ATalkPrivateEQU.a to get AGBHandle definitions that
; were moved out of ATalkEQU.a
; <81> 1/19/91 eh (djw) Patch Port A async serial driver headers to insert
; signature word for use in serial driver linked patch. Insert
; signature before already patched port B headers. Change port B
; arbitration code to call 'atkv' Gestalt call instead of old
; 'atlk'.
; <80> 1/14/91 eh (djw) Added external clocking support for Nike printer to the
; Async Serial Driver.
; <79> 1/8/91 gbm (sab) Fix Daves removal of the unmount patch, which Chris (csd)
; says he did without having Chris look at it. This is, if true,
; a hanging offense. If you see Dave in the halls after this
; date, then he probably got off with just a public flogging.
; <78> 1/8/91 dnf (csd) Since the File System no longer attempts to save the bits
; behind the disk switch hook, the patch to the code which did
; that is no longer necessary.
; <77> 12/15/90 djw (jwk) Add SCSI Mgr support for Quantum 7.9 ROM problem by adding
; a separate TIB interpreter and replacing blind write
; <76> 12/14/90 dnf (jsm) Turn all patches on ExtFSHook off for 7.0 since they have
; been moved to LaterFileMgrPatches.a
; <75> 12/14/90 bbm (djw) roll in linked comefrompatch from patchIIrom.a.
; <74> 12/14/90 dba <JDR> get rid of VMCalls.a
; <73> 12/13/90 BBM (stb) move the patch to compactmem into memorymgrpatches.a.
; <72> 12/11/90 BBM (fjs) Eliminate HUnlock patch code under 7.0. This code was
; commented wrong. The patch was to fix a bug in GetPicTable
; (Color QuickDraw). Since that routine is completely replaced by
; the System file in 7.0, this patch is no longer needed. In
; actual fact, the patch is better than the ROM code but still has
; a bug in it which is fixed in 7.0.
; <71> 12/7/90 JSM <dba> Move patch on _DisposDialog and come-from patches on
; _GetAuxWin, _DetachResource, and _SetWinColor to
; DialogMgrPatches.a, ifdef come-from patch on _HandToHand and
; patches to [CouldFree][AlertDialog] for pre-7.0 only, since we
; no longer support the Could and Free calls in 7.0.
; <70> 11/27/90 JSM <gbm> Move come-from patch on _SetPort inside DrawItem to
; DialogMgrPatches.a.
; <69> 11/26/90 JSM <bbm> Move come-from patch on _StackSpace inside RgnOp to
; QuickDrawPatches.a, move come-from patches on _DisposeHandle
; inside CloseDialog and _ValidRect inside SetIText to
; DialogMgrPatches.a.
; <68> 11/21/90 gbm & dba; Get rid of the nasty patch to GetResource that is set up
; for a Font Mgr. patch for 7.0. It was causing nasty bugs, and
; not doing anyone any good, since the other patch was
; conditionalized out already!
; <67> 11/20/90 JSM <dba> Move come-from patch on _GetResource inside GetNextEvent
; to disable FKEYs from the keypad to ToolboxEventMgrPatches.a.
; <66> 11/9/90 dba & gbm & JSM; Move LoadResource patch that checks for errors
; while loading WDEFs and CDEFs to WindowMgrPatches.a and
; ControlMgrPatches.a — one more step towards the obsolescence of
; this file; conditionalize out the come-from patch on SwapFont
; when we have TrueType, since TrueType patches in a whole new
; SwapFont
; <65> 10/31/90 dba & csd; kill 8•24 GC loading code for 7.0 (StartSystem.a does it
; now)
; <64> 10/29/90 KST Fixing a bug in "ExtBTFile" patch that didn't handle reentrant
; call correctly. (code read by B.Bruffey).
; <63> 10/22/90 gbm (mostly dba) get rid of ReleaseResource patch for boot code in
; 7.0, since the old ROM boot code isnt used in 7.0
; <62> 9/25/90 KIP Change Sound Mgr. to a linked patch.
; <61> 9/23/90 dba Reinstate the patch to GetNewCWindow that loads 'pltt' resources
; for 7.0.
; <60> 9/22/90 dba get rid of Time Mgr. patching here since we now use the real
; TimeMgr.a to make a linked patch; get rid of obsolete ADB
; patches
; <59> 8/18/90 dba get rid of ptchInst 7 and 8 (Sony Format and Eject patches) and
; ptchInst 14 and 15 (SwapHMMUMode and SwapPMMUMode) as they are
; now linked patches
; <58> 8/17/90 DTY Removed Slot Manager ptch (13) since its a linked patch now.
; <57> 8/14/90 DTY Removed ptchInst 0 since TextEdit is now a linked patch.
; <56> 8/8/90 SAM Changing DispatchHelper & ProcHelper into an old style ptch.
; •••--> Temporary <--••• Remove when the Sound ptch get converted
; into an Lptch.
; <55> 8/7/90 DTY ptch 34 be linked now.
; <54> 7/30/90 dnf Remove installation of ptch 18 (File Manager) and ptch 6 (Btree
; Manager), now linked patches
; <53> 7/23/90 dba get rid of MenuMgrPatchII
; <52> 7/23/90 dba get rid of ptch 25 for 7.0; it is covered by DialogMgrPatches;
; get rid of extraneous pre-6.0.6 SysVers conditionals; removed
; ptchInst 16 since PrGlue is a linked patch
; <51> 7/20/90 DTY Remove ptchInst 10 & 11 since Bass is now a linked patch.
; <50> 7/20/90 gbm Change some identifiers to eliminate assembler warnings
; <49> 7/19/90 CCH NEEDED FOR SIXPACK: Removed HwPriv patch. The HwPriv trap is now
; a linked patch.
; <48> 7/19/90 EH Add VM support for async.a, the SerSetBuf control call. Also
; rolled in the BAP stuff so we can get rid of the SINI resources.
; <47> 7/19/90 GMR Install ptch 7 on SuperDrive ROMS as well now.
; <46> 7/16/90 gbm Get rid of warnings...
; <45> 7/16/90 VL Fixed out-of-range references (including DelMCEntries,
; LoadResource and NewOldPatToNew) by using SetTrapFar instead of
; InstToolTp.
; <44> 7/2/90 DTY Remove ptchInst 21 since Resource Manager extensions are now in
; a linked patch.
; <43> 6/29/90 DDG Fixed out-of-range references in the patch install area again.
; <42> 6/26/90 DTY Remove ptchInst 2 since NotificationMgr is now a linked patch.
; <41> 6/25/90 DTY Remove ptchInst 9 since ScrollSpeedFix is a linked patch.
; <40> 6/25/90 DDG Fixed out-of-range references in the patch install area
; (specificly the menu manager traps).
; <39> 6/19/90 VL Remove PtchInst 29 since MiscPatches is a linked patch
; now.
; <38> 6/12/90 JSM Remove PtchInst 33 since PPC Toolbox is a linked patch now.
; <37> 6/11/90 EMT Moved alternate trap dispatcher loading to boot blocks.
; <36> 6/7/90 EMT Remove PtchInst 17 since Layer Manager is a linked patch now.
; <35> 6/7/90 VL Remove PtchInst 28 since HelpMgr is a linked patch now.
; <34> 5/29/90 DDG NEEDED FOR SIXPACK: Changed all the sixpack conditionals from
; six-point-oh-seven to six-point-oh-six.
; <33> 5/10/90 JSM AliasMgr now a linked patch, don't install it here anymore.
; <32> 4/23/90 EMT Conditionalized out routines replaced by 32-bit QuickDraw:
; StretchBits, MoveTo, OpenRgn, CloseRgn, PlotCIcon, OldPatToNew,
; BitsToPix, MakeITable, MapRect, NewPixPat, MakeScale, RgnBlt,
; GetSeek, ColorMap, DrawPicture, StdBits.
; <31> 4/18/90 DDG Rolling in the ReallocHandle patch from the sys6 sources.
; <30> 4/16/90 SMB Changed 'ptch' 27 conditionals to include it for 6.0.6 builds.
; <29> 4/16/90 DDG Rolled over some changes from the system 6 split offs to the
; main sources: We added patch 25 (generic system patches), a
; hwPriv patch, the patch for the tiburon video card, and we
; changed the equate for spline fonts to use the build variable
; hasSplineFonts.
; <28> 3/29/90 EH Changed slot interrupt priority order AGAIN. $FF is highest.
; <27> 3/23/90 NC Added ptch 43 for System 6.0.6 on up. This is for Sound.
; <26> 3/15/90 djw Enable slot manager patch (ptch 13) for bigbang (it works now)
; <25> 3/7/90 dba change DetachResource to use BackToTrap
; <24> 2/22/90 JSM Comment out (temporarily?) slot manager patch 13 for 7.0 (see
; Dave Wong).
; <23> 2/22/90 DDG Changed the installation of the HiliteMenu trap from InstToolTp
; to SetTrapFar.
; <22> 2/14/90 BBM Jcrsrtask patch was breaking mouse movement, because someone
; changed almost all the labels in its globals.
; <21> 2/14/90 EMT Conditionalized PaintOne and PaintBehind patches - these are now
; part of the Layer Manager.
; <20> 2/5/90 DDG Changed the installation of the MenuSelect trap patch from
; InstToolTp to SetTrapFar. This also required that I specify the
; real trap number.
; <19> 2/3/90 NC Removed SysBeep patch. SysBeep will be patched for 6.1 and 7.0
; from the Sound Manager.
; <18> 2/2/90 JWK NEEDED FOR 6.0.5: Changed SCSI Mgr bus error handler to chain to
; previously installed bus error handler if a non-SCSI bus error
; occurs. Also fixed a bug causing a -1 to be returned by blind
; reads or writes if less than five bus errors occurred during a
; transfer.
; <17> 2/2/90 EH Fixed Slot Interrupt patch to use the standard macros from
; patchmacros.a
; <16> 2/2/90 BAL Changed InstOsTp to setTrapFar for recoverHandle patch.
; <15> 2/2/90 KON NEEDED FOR 6.0.5: Recover handle now checks for pointers in the
; MF heap.
; <14> 2/2/90 GGD NEEDED FOR 6.0.5: Modified the Deferred Task Manager to enable
; interrupts when returning just so QuickMail servers will
; continue to work (their bug, but we'll fix them for now).
; <13> 2/1/90 csd Needed for 6.0.5: Changed 32-Bit QuickDraw loader to stash a
; magic cookie if it cant find the right resource. This indicates
; an older version of 32-Bit QuickDraw. INIT 7 checks the magic
; cookie and puts up an alert.
; <12> 2/1/90 NC Now patches SysBeep for system 6.1 on up.
; <11> 1/26/90 EMT Fixed <4> conflict with the Layer Manager; both patch
; SetWinColor.
; <10> 1/25/90 KON NEEDED FOR 6.0.5: QD version is Offscreen version + $100, not
; $200.
; <9> 1/23/90 KON NEEDED FOR 6.0.5: Added Gestalt stuff for Quickdraw.
; <8> 1/22/90 PKE Used new InstallGestaltEarly symbol to control whether Gestalt's
; ptch 5 installation is done earlier (needed for TextEdit 3.0),
; and made it happen for SysVers>=$605 instead of SysVers>=$700.
; (This is already in the System6Proj sources).
; <7> 1/18/90 DVB Include PalettePriv.a, remove some compile-control slime
; <6> 1/15/90 CCH Fixed out-of-range offset.
; <5> 1/12/90 CCH Added include of “HardwarePrivateEqu.a”.
; <4> 1/4/90 DAF Corrected color dialog color table handling. This entailed
; removing a patch on GetResource and modifying one on SetWinColor.
; <3> 1/4/90 dba NEEDED FOR 6.0.5: (the 32-Bit QD stuff is needed for 6.0.5)
; redid the comments; added extra slop to RgnOp (StackSpace) patch
; so that it does not have to be patched out by 32-Bit QD; made it
; a MAIN instead of a PROC to get dead-code stripping; changed
; some symbols to avoid warnings; got rid of some 32-Bit QD
; patches that are superceded by the new version of 32-Bit QD;
; changed the code that loads the 32-Bit QD file to work only with
; new files (changed 'ptch' ID from 32 to 132); do not load the
; WaitNextEvent patch out of 7.0 builds
; <2> 12/21/89 dvb Modified to use qd32 pmgr.
; <1> 12/17/89 CCH Adding for the first time into BBS.
; <8.4> 12/11/89 GMR Added ptchInst 8; Sony Format patch is now in it's own patch
; file (FormatPatch.a).
; <8.3> 11/29/89 GGD NEEDED FOR 6.0.5 Replaced the prior patch to the Deferred Task
; Manager (which still had a small bug) with the fixed code from
; the IIci/Portable ROMs. Enabled the Extended Time Manager (which
; matches the code that is in the IIci/Portable ROMs). Enabled the
; New ADB Manager (which matches the code that is in the IIci
; ROM). Initialized the new LowMems VIA2 and TimeViaDB which were
; introduced with the IIci ROM.
; <8.2> 11/21/89 EMT NEEDED FOR 6.0.5: Added humane scrolling.
; <8.1> 11/20/89 BAL Fixed up conditionals for install code as well.
; <8.0> 11/20/89 BAL Changed paletteMgr.a and QuickPolysPatch.a to PaletteMgrPatch.a
; and QuickPolysMacIIPatch.a Removed QuickerDraw.a and several
; other CQD patches from the 7.0 build.
; <7.9> 10/25/89 rwh NICE FOR 6.0.5: add ptch38, backpatch of hwPriv trap for Rom
; revs 1.0, 1.2.
; <7.8> 10/16/89 GMR Re-added ptch34 - ADB manager patch, for system 7.0
; <7.7> 10/11/89 djw Changed to install slot mgr ptch AFTER 32 bit QuickDraw ptch
; <7.6> 10/10/89 djw Added ptch 13 - slot manager patch for system 7.0
; <7.5> 10/10/89 GMR Backed out ptch 34, until it can be cleaned up
; <7.4> 10/6/89 JSM Removed SnarfMan 'ptch', now PACK 13.
; <7.3> 10/3/89 GMR Added Ptch 34, Gary D's new ADB manager, for 7.0.
; <7.2> 9/25/89 BAL Integrated 32-Bit QuickDraw into 7.0 build process.
; <7.1> 9/18/89 CVC Integrate the PPC Toolbox as a ptch the first time.
; <7.0> 9/18/89 RLC Moved ptch 28 (Help Mgr) to after the FCQD (32bitQD) install.
; <6.9> 9/5/89 PKE Install Script Manager 7.0 extensions, ptch 27.
; <6.8> 8/30/89 dba got rid of fast traps for QDExtensions patch since Traps.a has
; the appropriate macros (sure to anger my pal, Bruce Leak)
; <6.7> 8/28/89 SES Removed references to nFiles. Changed DeclRomEqu.a to RomEqu.a.
; <6.6> 8/21/89 PKE NEEDED FOR 6.0.4: • only re-load the standard clut into QDColors
; if QDColors exists; this is so that A/UX will work •
; Conditionalize 6.4 for Scripts604 OR (SysVers >= $700)
; <6.5> 8/21/89 BAL NEEDED FOR 6.0.4: Fixed patch to PenNormal to first call through
; to ROM.
; <6.4> 8/19/89 PKE NEEDED FOR 6.0.4 (SCRIPTS BUILD) & 7.0: Moved PtchInst 5
; (Gestalt) ahead of other PtchInsts so they can use Gestalt.
; <6.3> 8/17/89 djw NEEDED FOR 6.0.4: Added 32 bit QD patch to slot manager to fix a
; bug in pRead4Bytes. Was doing a long read from NuBus - patch
; skips long read to only bytes.
; <6.2> 8/17/89 CCH Now gets SCC base addresses from low-mem globals. Also added
; definition of vBase2 to this Mac II-only patch file since
; NuMac-only features will be going away.
; <6.1> 8/15/89 DAF NEEDED FOR 6.0.4: removed patches (for gamma) to NewGDevice and
; one time boot gamma fixer
; <6.0> 8/15/89 dba NEEDED FOR 6.0.4: moved some patches here from MacIIMenuPatch
; because they patch QuickDraw traps and will be overpatched
; unless they are installed after 32-Bit QuickDraw; in WDEF 0
; patch (one of the above patches from MacIIMenuPatch) use a
; StripAddress technique instead of funky cmpRA with $A08XXXXX
; address. patch PaintOne to do nothing if WWExist is non-0; got
; rid of milestones and used new PatchMacs macros instead; tried
; to change gamma table stuff so that old cards get the TFB gamma
; table instead of the linear one (done by DAF) as in an earlier
; patch, but this does not seem to work yet on the Radius monitor
; in Giffords office; moved NewGDevice patch after 32-Bit
; QuickDraw so it will not be overpatched moved the boot gamma
; one-shot code so it *will* be loaded under A/UX (and after
; 32-Bit QuickDraw); changed the NewGWorld patch so that the
; current port is saved; re-load the standard clut into QDColors
; so that the green channel is fixed; changed the cut-back code to
; use new long-distance macros from PatchMacs
; <5.9> 8/14/89 BAL NEEDED FOR 6.0.4: (really dvb) Added tailpatch to Initpalettes
; to kill misROMmed ExitToShell patch.
; <5.8> 8/12/89 dba NEEDED FOR 6.0.4: installed new MacIIMenuPatch patches;
; rearranged as needed
; <5.7> 8/11/89 dba NEEDED FOR 6.0.4: moved patches in and out of A/UX as a result
; of soul-searching, conversation with Dave Berry, and code review
; of IIci patches; made HNoPurge patch A/UX-friendly; made ATP
; duplicate-request patch 32-bit clean by deleting unecessary
; CLR.B
; <5.6> 8/9/89 GMR Added ptch 29 - BigBang only patches for all ROMs
; <5.5> 8/7/89 DAF FOR 6.0.4 BUILD - Added two sets of patches that correct the
; start code to load the default gamma tables from each video card
; rather than stuffing the standard Mac II gamma table into every
; card. One set works on the boot screen, the other fixes the rest
; <5.4> 8/2/89 EVA Reversed Slot Handler priority scheme back to what it was prior
; to <3.7> patch
; <5.3> 8/1/89 BG Added GGD's optimized A-Trap Dispatcher.
; <5.2> 8/1/89 CSD Needed for 6.0.4: Fixed a bug in ColorMap which affects
; scrolling in old ports. Also changed OffscreenVersNum to 1.0 so
; it's less than the version of 32-Bit QuickDraw in Aurora.
; <5.1> 7/31/89 EVA conditionalized out patch <3.7> for big bang
; <5.0> 7/26/89 GMR Needed for 6.0.4: Added Sony Eject patch (ptch 7)
; <4.9> 7/25/89 GGD Needed for 6.0.4, Fixed change <3.1> by REALLY deleting change
; PB261.
; <4.8> 7/25/89 BAL Needed for 6.0.4: Fixed crashing bugs in offscreen graphics
; support.
; <•4.7> 7/21/89 DAF FOR 6.0.4 BUILD - Removed CheckDevices fix from GetResource.
; Removed QDColors green fix from GetResource, too. These patches
; are taken care of by the QDCheckDevices init and a new ROM
; override
; <4.6> 7/3/89 NJC Sound Manager Extensions (ptch 23) rolled in for real.
; <4.5> 6/30/89 BBM Added partial resources to System 7.0 ('ptch' 21).
; <4.4> 6/29/89 RLC Added HelpMgr PtchInst 28
; <4.3> 6/26/89 BAL dvb For 6.0.4 Move initpalettes call from initmenus to end of
; initwindows.
; <4.2> 6/21/89 NJC Added a ptchinst 3 to if it wasn't already there and added in a
; commented-out ptchinst 23 for the sound dispatcher,DJ, and S.M.
; enhancements.
; <4.1> 6/13/89 dnf Moved btree ptch install after hfs70 ptch install.
; <4.0> 6/12/89 BAL Patched up 32-Bit QD's StdBits.
; <3.9> 6/12/89 BAL Removed patch to GetForeColor because it didn't always work and
; I didn't like it. Added a fix to 32-Bit QuickDraw's stdBits.
; <•3.8> 6/10/89 CEL Moved Private.a QuickDraw Equates into proper QuickDraw private
; file (colorequ.a), got rid of QuickDraw nFiles dependencies and
; fixed up necessary files…
; <3.7> 6/5/89 EVA Patch Slot Interrupt/VBL handlers
; <3.6> 5/31/89 CEL Only defined Spline_Font variable if it is undefined - makes it
; easier to build test 6.0.4 systems
; <3.5> 5/31/89 prp Added Alias Manager Support
; <3.4> 5/30/89 dnf Changed comment for ptch 18 (18 is now HFS 7.0 enhancements)
; <3.3> 5/23/89 jaz Change version conditionals to check for $700 instead of $604
; <3.2> 5/19/89 jaz Add code to patch in Gary D's new Extended Time Manager
; <3.1> 5/18/89 rwh replaced PB261 SwapMMUMode patch with new one that installs ptch
; 14 or 15. ptch14 fixes the 'HMMU systems lose sound interrupts'
; bug, ptch 15 is a better swapMMUMode for PMMU machines.
; <3.0> 5/16/89 EMT Moved include of ToolTrapFix so that it would be executed at
; installation time.
; <2.9> 5/15/89 CEL Previously, I grouped the patches that effect the spline font
; routines together with the spline font patch. This relocated the
; patches below that32-bit QDat. 32-bit QD got patched out. Sorry
; team!
; <2.8> 5/15/89 EKN Added load of File IDs patch (#18).
; <2.7> 5/13/89 EMT Added Window Manager extensions (Layers).
; <2.6> 5/8/89 NMB Replaced PrGlue with Ginsu's PrGlue.
; <2.5> 5/3/89 CEL Fixed out of range error in compile for the sys604 build
; <2.4> 5/3/89 CEL Rolling in Bass for the first time into EASE…
; <2.3> 4/17/89 CCH Put in a milestone for NewStretchBits.
; <2.1> 4/11/89 JSM Install SnarfMan 'ptch'.
; <•2.0> 4/11/89 CCH Rolled out Altair changes in a big way.
; <1.9> 3/22/89 CCH Replaced SE hard addresses for FSQSync and CmdDone in Cache
; Control trap with Mac II hard addresses. Also looks for
; DiskCachePriv.a in Aincludes dir now.
; <1.8> 3/13/89 CCH Resolved some out-of-range offsets for Big Bang, and added
; B-Tree Mgr patch installation.
; <1.7> 2/22/89 CCH Added install code to bring in Gestalt patch.
; <1.6> 2/21/89 CCH Added milestones so file would link because it is now larger
; than a 16-bit offset can deal with. This is temporary, and
; should be fixed right when patches are rearranged.
; <1.5> 2/21/89 JB (DNF, actually) These files seems to work, so I'm checking them
; back in.
; <1.4> 2/20/89 JB Cleaned up revision history comments.
; <1.3> 2/20/89 JB Moved cache control trap, MapFBlock patch, and "not a Mac disk"
; ExtFSPatch from BeforePatches.a
; <1.2> 1/31/89 CCH Merged changes from 6.0.3.
; <1.1> 1/6/89 CCH Added changes from 6.0.3 sources for building 6.0.4 and 7.0.
; <1.0> 11/16/88 CCH Added to EASE.
; PMAB581> 10/16/88 GGD Installed latest version of TimeMgr, which also includes work
; around for bug with Rockwell VIAs (6.0.3 and Altair) Replaces
; PMAB564
; <PB578> 10/5/88 bbm moved everything aroung so the stupid thing would link.
; <PB576> 10/4/88 GGD Changed SuperDrive MFM formatting on Mac IIx ROMs to be more
; compatible with IBM (Altair and 6.0.3)
; <PB575> 10/3/88 EMT Support for PMAB568 (Menu Manager)
; PMAB574> 9/25/88 jwk Rolled old SCSI Mgr enhancements to support new SCSI Mgr trap.
; 9/24/88 rwh roll in PB541 22jul88 rwh from 6.0.2 sources: fix PowerOff trap
; patch PB091 to delay & rts instead of infinite loop after
; turning machine off. For machines w/o soft poweroff, Shutdown
; Manager will then put up the 'Safe to Restart' dialog.
; <PB573> 9/22/88 jwk Cleaned up Deferred Task dispatcher for Mac II.
; <PB571> 9/8/88 djw Fixed bugs in PB499 - get gDevice handle from MainDevice low
; mem, Next1sRsrc and SecondaryInit bug
; <PB570> 9/8/88 BAL Added install code for FCQD. Look for and execute 'ptch' ID:-24
; PMAB564> 8/18/88 ggd Patched in the New Improved Time Manager for all CPUs,
; Completely replaces old Time Manager, and replaces patches on
; MacPlus and MacSE.
; <PB553> 7/28/88 djw/RPD Added A/UX conditional test for PB499 start code patch, and
; moved slot manager part of patch out of A/UX.
; <PB512> 6/24/88 JB Added patch to fix UpdAltMDB to use correct disk address on
; 1440k disks
; <PB520> 7/1/88 AWC Removed installation of NewPWindow
; <PB499> 6/24/88 djw Add secondary init and search features to slot manager. Added
; patch code to start manager just before patch cutback.
; <S497> 6/7/88 med Changed Script Manager to ptch resource
; <s483> 4/29/88 bbm changed hardwired constant to HiIntMask (see s481).
; <PB482> 4/27/88 DAF Fixed desktop color pattern (again) to be MPW Shell friendly.
; This involves moving the desk pat back to the system heap, but
; correctly dealing with existing pats.
; <s481> 4/27/88 bbm There was a small window after the vremove where a timer
; interrupt could happen. Since the sound driver services the
; timer in the vbl task, the code to reinstall the vbl task would
; never happen.
; PMAB466> 4/13/88 JWK Fixed SCSIGet to perform cleaner arbitration.
; <PB465> 4/13/88 BAL/DAF Altered PB375 to use BackColor (once again) as the transparent
; color.
; <PB464> 4/12/88 AGH Changed JMPROM to BackToTrap for DisposHandle for A/UX.
; <PB463> 4/11/88 DAF Moved Palette Manger installs into the A/UX patch group
; <PM459> 4/7/88 AWC Fixed DisposePalette/CloseWindow bug; implemented AppPalette and
; DisposeBit
; <PB458> 4/1/88 BAL Fixed OpenPicture to re-dereference picsave handle after
; NewPixPat.
; PMAB457> 4/7/88 RWW Fixed CloseDialog to properly dispose TERecord
; <PB452> 4/1/88 BAL Fixed a bug in OR-mode patterned lines and ovals in
; quickerdraw.a
; PMAB449> 3/30/88 rwh replace SysEnvirons code w/INCLUDE SysEnvirons.a (Version 2!)
; <PB447> 3/30/88 DBG Fixed patch to SetupStretch to be completely A/UX friendly.
; <PB445> 3/28/88 DAF Fixed PB408 by extending patched routine.
; PMAB442> 3/25/88 EKH Fixed 'PatchInstall' fail bug. (Wasn't calling SysErr
; correctly).
; PMAB440> 3/24/88 AWC Removed include for QuickPolysEqu.a, which is now imbedded in
; QuickPolysPatch.a
; <PB438> 3/23/88 DAF Improved PB435. Moved desktop ppat to app heap rather than
; system heap.
; <PB435> 3/22/88 DAF I (STUPIDLY) handled the deskCPat lo-mem incorrectly causing
; many bytes of system heap to disappear when launching apps. This
; set of patches on InitWindows (via GetPixPat) and SetDeskCPat
; correct the problem.
; <PB433> 3/22/88 DAF Improved the QuickerDraw dispatch back to ROM. Save a few
; instructions and a few cycles.
; <PB428> 3/18/88 DAF Made QuickerDraw.a installs A/UX friendly. Likewise for PB408.
; Thanks to Andy Heninger for LEARom macro.
; <PB427> 3/17/88 BAL Fixed some bugs in arithmetic modes in quickerdraw.a
; <PB421> 3/7/88 DAF Removed conditional include of QuickerDraw.a. The trap
; installation is still conditional.
; PMAB417> 3/3/88 EMT Patch GetMenuBar and SetMenuBar to handle saved bits correctly.
; <PB415> 3/1/88 DAF/BAL Added QuickerDraw conditionally - set Quicker EQU 1 to enable
; <PB408> 2/26/88 DAF Added a small fix to 32X scaling in SetupStretch (CQD Vector)
; PMAB407> 2/26/88 DAF Removed PMAB370 (UprStr). I didn't know that you could use
; UprStr to just strip diacriticals. My post processing was
; causing AppleShare to get grave accents accidentally when
; stripping names. This can still be fixed, it just requires a
; deeper fix rather than post processing.
; <PB404> 2/25/88 DAF Fixed and improved SaveEntries and RestoreEntries
; PMAB401> 2/23/88 djw Bug in async driver - killIO did not set reg D0 to good return
; status. Combine with patch PMAB372
; <PB386> 2/9/88 djw Fix PMAB372 incorrect use of CmpRA for ROM resource address
; <PB384> 2/9/88 DAF Set crsrBusy during Mac II ShowCursor to prevent garbaged
; cursors.
; <PB373> 2/3/88 AGH Fix A/UX Hostile patches.
; <PB375> 1/27/88 BAL Patched ColorMap to set transColor from RGBOpColor instead of
; backColor.
; <PB373> 1/26/88 AGH Fixed Install code for A/UX Macros to allow CMPRA to work with
; return addresses from ROM Resources
; PMAB372> 1/26/88 djw Fixed DTR bug in async serial driver - a jump to the wrong label
; PMAB370> 1/25/88 DAF UprStr had an "a" instead of a "`" in it's case table, so I
; added a post-call scan of the string to fix this.
; <S369> 1/25/88 DAF Made a fix to WDEF 0 via PenNormal here, at menu mgr's PenNormal
; <PB366> 1/25/88 bbm fixed a bug in maxblock.
; PMAB364> 1/23/88 EMT Fix Pop-up menus to come up on any screen
; <PB362> 1/21/88 BAL Extended drText patch to fix fractional pen positioning in new
; ports.
; PMAB354> 1/7/88 EMT Unimplemented Toolbox versions of 12 bisexual traps
; <PB352> 1/6/88 BAL Fixed drawPicture to condense pixmap -> bitmap in place when
; BitsProc is not StdBits.
; PMAB340> 12/17/87 EMT Miscellaneous fixes to NMgr + System Alarm uses NMgr.
; <PB337> 12/16/87 bbm fixed SetOSDef to keep it from trashing PRam.
; <PB336> 12/16/87 AGH Add back install code that was accidently removed by PB302.
; PMAB335> 12/15/87 EMT ptchInstall now calls SysError on failure
; <PB330> 12/14/87 AGH/EMT Fixed bug in A/UX friendly patching
; PMAB329> 12/10/87 JWK Fixed PMAB295 to avoid 10sec delay when booting without SCSI
; devices attached.
; <PB323> 12/7/87 BAL Changed makeScaleTbl patch (PB233) to restore d7 before bitblt.
; <PB319> 12/2/87 AWC Modified StdPoly so QuickDraw regions are not used.
; PMAB318> 11/30/87 jw Added new improved sound manager.
; PMAB317> 11/28/87 EMT Added Notification Manager.
; <PB313> 11/25/87 bbm Fixed the fontmanager. When a synthetic font of greater than
; 128k was displayed, the offset to the width table was not
; retrieved right. fixed by patching hsetstate.
; PMAB315> 11/25/87 RWW Err, GetResource doesn't return resNotFound? Fixed ptchInstall
; <PMAB310> 11/24/87 PYG/EMT Make WaitNextEvent trap for Classic Mac OS.
; PMAB309> 11/24/87 RWW Massive, world-shattering change - yank TE patches and do this
; whizzy new installation. This one patch, in one fell swoop,
; replaces the following old, sometimes ugly patches:
; PMAB308> 11/24/87 RWW Added ptchInstall, which installs 'ptch' resources. This saves
; keeping duplicate copies of identical code in several patch
; files.
; <PB305> 11/22/87 DAF fixed buffer size calculations in RgnOp
; <PB304> 11/22/87 DAF fixed "wrong result when no change" bug in GrowWindow
; <PB302> 11/17/87 AGH Massive changes to make all patches A/UX friendly.
; PMAB301> 11/15/87 ABO Fix ATP delayed duplicate response bug
; PMAB295> 10/20/87 SHF Modified last call to SCSILoad -- increased patched select
; timeout to 25 msec (was 5); made more robust for CD ROM.
; <PB292> 9/30/87 DAF Fixed DisposPixPat/DisposeCCursor and CloseCPort/ClosePort to
; test for NIL pathandles to save the General CDEV. The pairs of
; routines above are multiple names for the same code (but
; different traps!)
; <PAB291> 9/26/87 DBG Changed mouse button debounce time back to 20 msec, and changed
; code so that mouse downs always get noticed. The code will now
; never discard a down/up pair, only up/down pairs.
; <PAB288> 9/24/87 CSL Reduced the mouse button delayed time from 20 msec. to 10 msec.
; <PB286> 9/22/87 BAL Patched RSect to fix DrText for offscreen pixmaps.
; PMAB284> 9/21/87 JTC Fix patch to MoveHHi to weed out dinky free block cases. Fix
; involves moving more of patched loop into RAM.
; <S281> 9/18/87 bbm sound manager uses sound manager uses soundactive different than
; sound driver. Thus soundactive could be true with no sound vbl
; task installed. So now we check for an error from vremove, which
; we should have done in the first place. (This is the same patch
; as S278, which got deleted when pb279 was checked in.)
; <PB279> 9/18/87 DAF Fixed picture recording of regions and polygons.
; <S277> 9/16/87 DAF Removed install of _InitWindows patch, since the _InitPalettes
; is now done in INIT=31. NOTE: I did NOT remove the patch from
; PaletteMgr.a. In the new ROM sources, _InitPalettes should be
; done during startup.
; PMAB271> 9/14/87 BB/JB Modified unmount patch PB245 to unconditionally unmount a volume
; if the HFS bit is set in the ioTrap word.
; PMAB270> 9/13/87 FJL Patch DrawPicture to first check for valid picture handle and
; pointer, then do GetState, lock, and SetState on return. At the
; request of Sheila, Phil and Scott.
; <PB268> 9/10/87 DAF Detached DRVR resource loaded in PB238
; <PB266> 9/8/87 BAL Change equate for ExTbl in patch for setCCursor (PB206).
; <s263> 9/7/87 bbm The current sound driver uses low memory as a vbl queue element.
; A bug occurs if sound is active. The low memory queue element is
; zeroed regardless if there is a next element in the queue or
; not. Thus the machine may hang. The fix forces the sound vbl
; queue element to be last in the queue always.
; <PB262> 9/4/87 AWC Patched ActivatePalette: Blo.S => Bhi.S to fix color priority
; problem
; <PB261> 9/4/87 rwh Patched SwapMMUMode: prevent hang when already in mode neing
; swapped to.
; <PB260> 9/2/87 BAL Patched GetSeek to prevent region clipping to overshoot minRect.
; Patch recomputes bufSize(a6) for rgnBlt, stretch, drawArc,
; drawLine.
; <PB259> 9/1/87 AWC Patched NewPWindow so it doesn't polymerize the stack.
; <PB258> 9/1/87 BAL Patched rgnBlt to attempt TrimRect(clipRgn,minRect) for faster
; windows.
; <PB257> 9/1/87 BAL Fixed patch to MakeScaleTbl (PB233) to delete 1 bit search proc.
; PMAB255> 8/31/87 FJL Menu enable bits no longer get shifted randomly when more than
; 32 items are added to a menu. Patch DrawMenuBar and call
; HiliteMenu(0) and HiliteMenu(TheMenu) after so don't have
; dangling "bits behind" the menu title
; PMAB253> 8/27/87 CRC Fixed MaxSizeRsrc in FontMgr for Radius (once again)
; <PB251> 8/26/87 RDC Fix bug in PB236 patch so MicroBug still works if no debugger
; installed.
; PABM250> 8/25/87 MBK TextEdit: Patched DisposPtr and StackSpace to fix Pixel2Char
; dispose bug
; <PB245> 8/25/87 BB/JB Patch UnmountVol to prevent unmount when files are open.
; PMAB242> 8/24/87 BAL changed patch to patConvert (PB206) to use the proper equate for
; return address comparison
; PMAB241> 8/24/87 RDC Added patch for BadTrap handler routine to save registers before
; exiting to SysError routine
; <PB236> 8/24/87 RDC Added patch for NMI handler routine to pass proper error code to
; SysError routine so new MacsBug doesn't get confused.
; <PA237> 8/19/87 BB/JB Patched FClose to fix problem which failed to release BTCB's for
; OffLine, Eject, and Unmount.
; <PB238> 8/19/87 DAF Added patch to Open to correct loading of slot drivers and
; videoInit to reload the boot video driver if a newer one is in
; the system file.
; <C864> 8/12/87 rwh added RomPaletteMgr equate. It must be here for assembly to
; work. Its a Cxxx, not a PBxxx, cuz PaletteMgr.a is in Post Mac2
; ROMs also.
; <PB233> 8/7/87 BAL Patch MakeScaleTbl so that copybits color mapping only happens
; if absolutely necessary.
; <PB232> 8/4/87 bbm added some parameter checking to writeXParm.
; <PB231> 7/28/87 rwh add Rich Castro's fix to deferred task dispatcher: make it
; dequeue the task BEFORE calling it.
; <PB230> 7/24/87 DBG&BAL Was jumping back into ROM (for ROMNotProc case) with D0 trashed,
; so we jump back in a little earlier to restore its contents.
; <PAB229> 7/23/87 WRL MouseDrvr MouseDrvr New, improved mouse button debouncing code
; for ADB machines.
; <PB217> 7/22/87 BAL Patch RSECT in order to fix fast DrawLine in CGrafPorts
; <PB220> 7/22/87 SHF Fixed SCSI Mgr to clear up occasional hanging during reads.
; PMAB226> 7/21/87 GWN Backout PMAB216.
; PMAB216> 7/21/87 GWN Patch Read, Write, Control and Status to fix Async problem.
; <PB215> 7/21/87 FJL Fix GNEFilter to do GetClip after SetPort instead of before.
; <PB212> 7/20/87 DAF Improved Disk Switch Hook patch. Updated some palette manager
; patches.
; PMAB210> 7/20/87 DAF Fixed some resource handling in the window and control managers.
; <PB208> 7/18/87 SHF SCSIMgr: Added a delay to the bus error retry code.
; <PB206> 7/16/87 EHB HUnlock GetPicTable
; <PB206> 7/16/87 EHB BitsToMap CopyBits
; <PB206> 7/16/87 EHB MapRect DrawPicture
; <PB206> 7/16/87 EHB PatConvert SetCCursor
; <PB204> 7/13/87 DAF PaintOne, PaintBehind wmgrasm1:PaintDesk
; <PB204> 7/13/87 DAF PaintOne, PaintBehind wmgrasm1:PaintDesk WindowMgr: Fixed
; PaintDesk to switch to sysheap in case of deskCPat pattern
; expansion.
; PABM197> 7/9/87 MBK HLock TEStylInsert TextEdit: Fix to TEStylInsert call when
; record is deactivated
; PABM198> 7/9/87 MBK HLock,HUnlock,TEDispose,TESetSelect,TEClick,TEDispatch,TEKey
; TextEdit: Fix to allow styles to be set at null selection
; PABM201> 7/9/87 MBK FindLine SetLineHite TextEdit: Fix to allow fixed line heights
; to work
; PABM202> 7/9/87 MBK FindLine RecalLines TextEdit: Fix to recalibration bomb when
; text length = 32,767
; PABM203> 7/9/87 MBK FindLine RecalLines TextEdit: Fix to deletion bug (display would
; get messed up)
; <PB195> 7/9/87 CRC Dialog Manager: fixes color Could/Free Alert/Dialog, and orphan
; handle patched: GetAuxWin DisposDlg DetachRsrc SetWinColor
; HandToHand CouldAlert CouldDialog FreeAlert FreeDialog to
; correct: CouldAlert FreeAlert CouldDialog FreeDialog
; GetNewDialog Alert
; <PB196> 7/9/87 CRC SetPort DrawDialog Dialog Manager: fixe to leave port alone
; across user item if no color items note: this is patched in
; MacIIMenuPatch
; <PAB191> 7/2/87 CSL ADBReInit Kbd.a Added pre- and post- processing routine hook for
; ADBReinit.
; <PAB192> 7/2/87 EMT ADBProc KbdDrvr Use JADBProc to clean up on ADBReInit
; <PB189> 7/1/87 CRC StretchBits DrawText reverse order of shadow only for old port,
; bic and or modes.
; PABM187> 7/1/87 CRC GetMaskTab, GetResource FMSwapFont fixes fractenable underline
; <> plain widths bug patched GetResource to set register flag,
; and GetMaskTab for bug fix
; <PB188> 7/1/87 CRC FixDiv CharExtra translate zero size into correct size
; PABM186> 7/1/87 CRC GetHandleSize RealFont removed PB164 and replace GetHandleSize
; w/ MaxSizeRsrc
; <PAB185> 6/29/87 ABO Fix NBP write-to-zero on lookup bug.
; 6/10/87 JTC Amend format of patches for use by A/UX Toolbox. Idea is to
; split the install code into two parts, one that installs on all
; machines, and one that installs only when NOT on A/UX. The
; latter is handy for those OS-ish routines that have no exact
; correspondent on A/UX. Subtleties like patching
; <PB172> 4/10/87 JTC&SMD Fix problem with D3 not being initialized on B2D conversions.
; <PB170> 4/8/87 DBG&BAL The ROM Optimization Squad decrees that JSR + RTS = JMP (in PB112).
; <PB169> 4/8/87 DBG&BAL Fixed bug in patch to SetIText (PBAM109): 24-bit ROM addresses vs. 32
; <PB168> 4/8/87 DBG&BAL Remove patch to GetSeek (part of PB093), since any negative
; coordinates passed to StretchBits are in error. (Mac Plus
; compatibility??)
; <PB167> 4/8/87 DBG Fix patch to patch to _BitsToPix (PB162) to keep A0 where ROM
; expects.
; <PB166> 4/8/87 DBG Fix patch to _BitsToMap (PB122) so that dstmap gets wedged to
; port only if 1) thePort is printer port, and 2) dstmap is
; currently screenbits
; <PBM164> 4/7/87 JTC&JDT DANGER: Patch RealFont with caution after this, since we look
; into the stack at RealFont internal return addresses.
; <PB160> 4/1/87 AWC PMgr; fix D5 save; regs in P2CT; AnimXXX intfc chg; animation
; fix
; <PB158> 3/30/87 JTC Tweak install of Palette jIAZInit patch to use daisy chain.
; <PB153> 3/30/87 FJL Removed fix to GetMaxDevice call in StandardMBDF.a. Changed
; MenuMgrPatchII.a and PatchIIROM.a
; PABM150> 3/28/87 JTC&JAF SysEnvirons patch
; <PB148> 3/28/87 EHB Added patch to checkDevices to make monochrome/color work. Moved
; InitGDevice patch into this one.
; <PB146> 3/27/87 CRC Patched FixMul to fix bug if input value to CharExtra is
; negative.
; <PB147> 3/27/87 EHB New palette mgr. Patched the RGBxxColor family of routines.
; PABM139> 3/26/87 MBK Patched FindLine to fix recal delete bug.
; <PB136> 3/24/87 JTC GetNewControl GetNewControl Little fix to LINK with even count.
; <PB137> 3/24/87 EHB Revised BitsToMap patch to make printing work.
; <PB131> 3/24/87 JTC Patch ReleaseResource to fix start code to detach DSAT=2. Since
; its a one-shot, just blast the correct address back when done.
; BEWARE: If you patch ReleaseResource further, disable my revert
; BEWARE: code that bolts the old ROM address back in.
; <PB126> 3/23/87 EHB Added CalcCMask, SeedCFill, and newBitsToMap
; <PB125> 3/20/87 DAF Patched MakeITable to not SysError when it can't allocate the
; cube or queue in the app heap. Now it returns an error in QDErr.
; <PB122> 3/19/87 EHB Added 3 QuickDraw patches
; <PB121> 3/19/87 DAF DiskSwitchAlert TFS:TFS.a/DSHook Modified disk switch alert to
; post an update if the mainscreen is not in 1-bit mode. This
; patches DskSwtchHook in lo-mem- not a trap!
; <PAB117> 3/19/87 CRC LoadResource FMSwapFont if fast path fails because of disk
; switch, recover with panache.
; <PB112> 3/19/87 mgl Sound Manager timer interrupt patch
; <PB110> 3/18/87 FJL Menu Manager patches for: variable speed scrolling,
; PopUpMenuSelect, GetItemCmd, SetItemCmd
; PBAM109> 3/17/87 CRC ValidRect GetIText patched ValidRect to restore register
; clobbered by DrawItem in SetIText
; <PB103> 3/10/87 EHB/AWC Palette Manager
; PMAB102> 3/10/87 EMT Fixed all patches to not use FKEYs when code came from keypad.
; <PB093> 3/9/87 EHB 3 QuickDraw patches: StdPoly: Put proper opcode to new pictures
; GetSeek: Watch for negative sources (when called by stretch)
; PlotCIcon: Set fg to black and bk to white
; <PB092> 3/9/87 JTC CompactMem MemMgr: MoveHHi Prevent creation of bogus tiny free
; blocks.
; <PB071> 3/7/87 SHF SCSIWrite, SCSIWBlind OS:SCSIMgr.a Fix bus error handler, DMA
; turn-off check
; <PAB87> 3/6/87 CSL Patch JCrsrTask to support absolute cursor position.
; <PB086> 3/5/87 MBK HUnlock TextEdit.a:InsertRecal fixed obscure recal bug
; <PAB87> 3/6/87 CSL Patch JCrsrTask to support absolute cursor position.
; <PB079> 3/2/87 CRC improper mode, hilite fixes
; <PB071> 3/7/87 SHF Fix bus error handler, DMA turn-off check
; <PB091> 3/8/87 RDC Fix timing problem in poweroff routine
; <PB074> 3/2/87 ABO Fix re-entrancy problem (don't install if already there)
; <PB069> 2/27/87 mbk fix for Mac+ (!) scrolling bug
; <PB0689> 2/27/87 mbk added TextEdit patch for International
; <PB0679> 2/27/87 mbk added TextEdit patch for International
;
STRING ASIS
MACHINE MC68020
LOAD 'StandardEqu.d'
include 'ATalkEqu.a' ; <PABM150>
include 'ATalkPrivateEqu.a' ; <81>
include 'ApplDeskBus.a'
include 'HardwarePrivateEqu.a'
include 'MMUEqu.a' ; <3.1>
include 'PrEqu.a'
include 'PrPrivate.a'
include 'ColorEqu.a'
include 'SCSIEqu.a'
INCLUDE 'SlotMgrEqu.a'
INCLUDE 'VideoEqu.a'
INCLUDE 'PaletteEqu.a'
INCLUDE 'PalettePriv.a' ; <dvb 18Jan90>
INCLUDE 'QDHooks.a'
INCLUDE 'ROMEqu.a' ; <PM238/DAF><6.7>
INCLUDE 'PatchMacros.a'
INCLUDE 'ScriptPriv.a' ; <30>
INCLUDE 'InternalOnlyEqu.a'
IF (&TYPE('SPLINE_FONT') = 'UNDEFINED') THEN
SPLINE_FONT EQU hasSplineFonts ; <29> modified 4/16/90 DDG
ENDIF
IF (&TYPE('Scripts604') = 'UNDEFINED') THEN
Scripts604 EQU 0 ;<6.6><08/21/89 pke>
ENDIF
Quicker EQU 1 ; set to zero to not build QuickerDraw, 1 to include <PB415>
ROM78Fix MAIN EXPORT
IMPORT RAMSysInit
EXPORT SysBase,CutBack
; Cut back Code:
;
; SysBase is the entry point for ROM78Fix. Upon entry D1.L contains our handle.
;
; Once the patches have been installed, this code is cut back to exclude the patch
; installation code.
SysBase
jmpFar RAMSysInit ; <6.0>
DC.L ('PTCH') ; resource type
DC.W $0178 ; patch ID $78 processor $01.
DC.W 0 ; current version number.
; cut back the ram-based system code to exclude this initialization code
CutBack
_SetHandleSize ; adjust our size
MOVEQ #$7F,D0 ; a soon to be large number
SWAP D0
_CompactMem ,SYS ; optional comma
RTS ; all done
;################################ PATCH CODE GOES HERE #######################################
;____________________________________________________________________________________
; PAB87 06Mar87 CSL patch out the JcrsrTask to support absolute cursor position.
; The whole Jcrsrtask routine is replaced by the patch below.
;
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 06Mar87 #PAB87 (JcrsrTask) (InsertRecal)
;
; OMIT FROM A/UX
;
CrsrPtch PROC EXPORT
;
; ===================================================================
; Constants. Size of the mapping table.
; ===================================================================
;
MaxL EQU 8 ; Maximum value of L
RomScrnPin EQU $4081B1EA
; ===================================================================
; Globals. First words of this resource.
; ===================================================================
;
Cnt EQU 0 ; word: number of valid error deltas
MaxCnt EQU Cnt+2 ; word: limit on number of error deltas
Err7 EQU MaxCnt+2 ; word: time-7 error magnitude
Err6 EQU Err7+2 ; word: time-6 error magnitude
Err5 EQU Err6+2 ; word: time-5 error magnitude
Err4 EQU Err5+2 ; word: time-4 error magnitude
Err3 EQU Err4+2 ; word: time-3 error magnitude
Err2 EQU Err3+2 ; word: time-2 error magnitude
Err1 EQU Err2+2 ; word: time-1 error magnitude
Error EQU Err1+2 ; word: accumulated error
GSize EQU Error+2
;
;
; ===================================================================
; Code. @MouseMap+EntryOff
; ===================================================================
;
TST.B CrsrNew ; Mouse changed?
BEQ Done ; No … return
TST.B CrsrBusy ; Cursor locked?
BNE Done ; Yes … return
;
TST.B CrsrCouple ; Cursor coupled to mouse?
BEQ NoComp ; No … skip computation <DSV>
;
MOVE.W MTemp+H,D0 ; Find ∆Mx
SUB.W RawMouse+H,D0
;
MOVE.W MTemp+V,D1 ; Find ∆My
SUB.W RawMouse+V,D1
;
MOVE.W D0,D2 ; x := |∆Mx|
BGE.S AbsX1
NEG.W D2
AbsX1
;
MOVE.W D1,D3 ; y := |∆My|
BGE.S AbsY1
NEG.W D3
AbsY1
;
move.l MickeyBytes,a0 ; <10/7/86 SMH> get globals
CMP.W D2,D3 ; D3 := magnitude(x,y)
BLS.S MagDone
EXG D2,D3
MagDone
ASR.W #1,D3
ADD.W D2,D3
;
; *** BEGIN NEW ***
;
BNE.S DoComp ; Zero magnitude … dont compute ***
MOVE.W #1,Cnt(A0) ; No hits ***
CLR.W Error(A0) ; No errors ***
BRA DoPin ; Update the cursor ***
DoComp
;
MOVEM.L D4-D5,-(A7) ; Save off registers
MOVE.W Cnt(A0),D4 ; D4 is the number of samples
CMP.W MaxCnt(A0),D4 ; Is Cnt less than MaxCnt
BGE.S CountOK
ADD.W #1,Cnt(A0) ; Yes … we will have one more error
CountOK
;
MOVE.W D3,D5 ; Magnitude at current time
;
MOVE.W D4,D2 ; Get Count
SUB.W #1,D2 ; Index into JTab
ASL.W #1,D2 ; REQUIRES BRA.Ss IN JUMP TABLES
JMP JTab(PC,D2.W) ; Jump to the right code per Count
;
JTab
BRA.S E1 ; Count = 1
BRA.S E2 ; Count = 2
BRA.S E3 ; Count = 3
BRA.S E4 ; Count = 4
BRA.S E5 ; Count = 5
BRA.S E6 ; Count = 6
BRA.S E7 ; Count = 7
; *** BRA.S E8 ; Count = 8 ***
;
E8 ADD.W Err7(A0),D5 ; Accumulate time-7 magnitude
;
E7 ADD.W Err6(A0),D5 ; Accumulate time-6 magnitude
MOVE.W Err6(A0),Err7(A0) ; Shift out time-6 magnitude
;
E6 ADD.W Err5(A0),D5 ; Accumulate time-5 magnitude
MOVE.W Err5(A0),Err6(A0) ; Shift out time-5 magnitude
;
E5 ADD.W Err4(A0),D5 ; Accumulate time-4 magnitude
MOVE.W Err4(A0),Err5(A0) ; Shift out time-4 magnitude
;
E4 ADD.W Err3(A0),D5 ; Accumulate time-3 magnitude
MOVE.W Err3(A0),Err4(A0) ; Shift out time-3 magnitude
;
E3 ADD.W Err2(A0),D5 ; Accumulate time-2 magnitude
MOVE.W Err2(A0),Err3(A0) ; Shift out time-2 magnitude
;
E2 ADD.W Err1(A0),D5 ; Accumulate time-1 magnitude
MOVE.W Err1(A0),Err2(A0) ; Shift out time-1 magnitude
;
E1 MOVE.W D3,Err1(A0) ; Shift out current magnitude
;
MOVE.W D4,D2 ; Round up the divide
ASR.W #1,D2 ; by half the denominator
ADD.W D2,D5
EXT.L D5 ; Set up for the divide
DIVU D4,D5 ; Find the average magnitude
;
MOVE.W D3,D4 ; Get the original magnitude
SUB.W D5,D3 ; Find distance to average magnitude
ADD.W Error(A0),D3 ; Add on the accumulated error
CMP.W #-1,D3 ; Define -1 div 2 = 0
BNE.S DivOK
CLR.W D3
DivOK ASR.W #1,D3 ; Get half of it
MOVE.W D3,Error(A0) ; Update it
ADD.W D5,D3 ; Desired mag is average+Error
;
CMP.W #255,D5 ; mag := MAX(mag,255)
BLS.S MaxDone
MOVE.B #255,D5
MaxDone
;
move.l MickeyBytes,a0 ; <10/7/86 SMH> get at globals
add #GSize,a0 ; <10/24/86 SMH> point to table
CLR.W D2 ; i := 0
;
Search
ADD.B #1,D2 ; repeat
CMP.B (A0)+,D5 ; i := i+1
BHI.S Search ; until mag ≤ Table[i]
;
MULS D2,D3 ; D4 := i*(Mag(∆M)+Error)
;
MULS D3,D0 ; ∆Cx := (∆Mx*i*(Mag(∆M)+Error))/Mag(∆M)
DIVS D4,D0 ; <<<<<< D3 >>>>>>>
;
MULS D3,D1 ; ∆Cy := (∆My*i*(Mag(∆M)+Error))/Mag(∆M)
DIVS D4,D1 ; <<<<<< D3 >>>>>>>
;
MOVEM.L (A7)+,D4-D5 ; Restore registers
;
; *** END NEW ***
;
ADD.W D0,RawMouse+H ; Update raw mouse location
ADD.W D1,RawMouse+V
;
DoPin
LEA CrsrPin,A0 ; Bounding rect for cursor ***
MOVE.L RawMouse,D0 ; Pin mouse inside rect
JSR RomScrnPin ; return to SHOWIT if screen changes
;
MOVE.L D0,RawMouse ; Update cursor locations
MOVE.L D0,MTemp
;
AND.L MouseMask,D0 ; Do jerky masking to drop low bits
MOVE.L MouseOffset,D1 ; Get the offset
BEQ.S SkipPin ; Skip 2nd pin if not
ADD.L D1,D0 ; Do jerky offset
JSR RomScrnPin ; return to SHOWIT if screen changes
SkipPin
MOVE.L D0,Mouse ; Actual mouse location
;
Repaint
TST.B CrsrObscure ; Unpaint the cursor
BNE.S Unpainted
_HideCursor ; Hide the cursor
Unpainted
;
CLR.B CrsrNew ; Cursor is fresh
CLR.B CrsrObscure ; Cursor is not obscured
_ShowCursor ; Repaint the cursor
;
; *** BEGIN NEW ***
;
RTS ; Goodbye
;
Done
move.l MickeyBytes,a0 ; <10/7/86 SMH> get globals
MOVE.W #1,Cnt(A0) ; No hits
CLR.W Error(A0) ; No errors
RTS ; Goodbye
;
NoComp
move.l MickeyBytes,a0 ; <10/7/86 SMH> get globals
MOVE.W #1,Cnt(A0) ; No hits
CLR.W Error(A0) ; No errors
BRA.S Repaint ; Update the cursor
;
; *** END NEW ***
ENDPROC
;____________________________________________________________________________________
; PB073 2Mar87 ABO VInstall atalk:nonres.a
; PAB185 29Jun87 ABO VInstall atalk:nonres.a
;
; PB073 Fixes a re-entrancy problem in nonres.a within MPP.
; PAB185 Fixes an NBP lookup bug where if the response comes back too quickly it
; is written to location zero.
;
; If we're doing a VInstall from Nonres, and the queue element we're installing
; is already there, don't install. If we're doing a lookup, skip the first write.
;
; s263 The current sound driver uses low memory as a vbl queue element. A bug occurs
; if sound is active. The low memory queue element is zeroed regardless if there is a
; next element in the queue or not. Thus the machine may hang. The fix forces the
; sound vbl queue element to be last in the queue always.
;
; s481 there was a small window after the vremove where a timer interrupt could happen.
; Since the sound driver services the timer in the vbl task, the code to reinstall the
; vbl task would never happen.
;
; s483 changed hardwired constant to HiIntMask (see s481).
;
; OMIT FROM A/UX
NewVInstall PROC EXPORT
CalledFrom EQU $1C ; Where we were called from (return addr)
SkipBytes EQU 18 ; No. of bytes to skip write (PAB185)
ROMVInstall EQU $40806344 ; ROM VInstall address
NRVBLHnd EQU $82D2DC ; VBL task address in ROM
tst.b SoundActive ; sound playing? fixes trashed vbl queue <s263>
beq.s @TruVinst ; if not, just do real vinstall <s263>
move.w sr,-(sp) ; Save sr <s481>
ori.w #HiIntMask,sr ; Disable interrupts <s483>
move.l a0,-(sp) ; save new vbl element on stack <s263>
lea SoundVBL,a0 ; point at hertzfelds vbl element <s263>
_VRemove ; remove sound vbl element <s263>
move.l (sp)+,a0 ; get new vbl element back in a0 <s263>
tst.w d0 ; check for error from vremove <s281>
bne.s @popstatus ; if error then dont reinstall sound vbl <s281>
bsr.s @TruVinst ; install new vbl element back in queue <s263>
lea SoundVBL,a0 ; get sound vbl element, and install it <s263>
bsr.s @TruVinst ; install sound vbl element back in queue <s481>
move.w (sp)+,sr ; Restore interrupts <s481>
rts ; <s481>
@popstatus ; <s481>
move.w (sp)+,sr ; Restore interrupts <s481>
@TruVinst ; <s263>
MOVE.L VBLAddr(A0),D1 ; D1 = VBL task address
AND.L MaskBC,D1 ; Mask off high bits to be sure
CMP.L #NRVBLHnd,D1 ; Called from NBP VBL task?
BNE.S @30 ; Branch if not
; PAB185 start
MOVE.L -4(A0),A2 ; A2 -> queue element from call
CMP #LookupName,CSCode(A2) ; Was it a lookup request?
BNE.S @5 ; Branch if not
TST.B VBLCount(A2) ; Check count (used to be count(A2)... I can't believe this code ever worked!)
BEQ.S @3 ; Branch if zero (leave alone)
ADDQ.B #1,VBLCount(A2) ; Need to add one since aren't sending now
@3 ADD.L #SkipBytes,CalledFrom(SP) ; Skip past the write
MOVE #1,VBLCount(A0) ; Set to send out real soon
; PAB185 end
@5 MOVE SR,-(SP) ; Save SR
MOVE #$2600,SR ; Disable interrupts
LEA VBLQueue+QHead,A2 ; A2 -> Head of VBL queue
@10 TST.L (A2) ; Done?
BEQ.S @20 ; Branch if so
MOVE.L (A2),A2 ; A2 -> next element
CMP.L A2,A0 ; Matches the one we're installing?
BNE.S @10 ; Loop if not
MOVE (SP)+,SR ; Restore SR
MOVEQ #0,D0 ; Indicate no error
RTS ; Return (already installed)
@20 MOVE (SP)+,SR ; Restore SR
@30 JMP ROMVInstall ; Jump to ROM VInstall code
ENDPROC
;___________________________________________________________________________
; PB071 07Mar87 SHF SCSIWrite, SCSIWBlind OS:SCSIMgr.a
; Fix bus error handler, DMA turn-off check
; PB208 18Jul87 SHF SCSIWBlind OS:SCSIMgr.a
; PB220 22Jul87 SHF SCSIRead,SCSIRBlind OS:SCSIMgr.a
; Fixed hanging bug at end of read data transfer.
;
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 06Mar87 #PB071 (SCSIWrite,SCSIWBlind) (SCSIWrite,SCSIWBlind)
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 18Jul87 #PB208 (SCSIWBlind) (SCSIWBlind)
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 22Jul87 #PB220 (SCSIRead,SCSIRBlind) (SCSIRead,SCSIRBlind)
;
; This patch fixes a bug in the SCSI Manager's bus error handler. It also
; fixes a bug in the 'check for turning off DMA' code which crept in
; somewhere between Maui and Becks.
;
; OMIT FROM A/UX
;
;
PatchSCSIRead EQU 1 ; patch SCSI Read (it and Write are patched <PB208>)
NewSCSIMgr PROC EXPORT
EXPORT NewSCSIGet,mySCSIRead, mySCSIRBlind, mySCSIWrite, mySCSIWBlind
;
; Stack frame for blind read/write bus error information
;
OldBusErrVct EQU -4 ; long
BusErrCount EQU -6 ; word
LocalSize EQU -6 ; total a6 offset for locals
zeroReg EQU d7 ; SCSI Manager convention
; should be in a separate "SCSIMgrPrivate" include file <PMAB466/JWK>
maxOpcode EQU 8 ; highest numbered TIB opcode
numSCSIVect EQU 24 ; max. number of selectors <C936/06Nov87> <PMAB466/JWK>
jmpTblSize EQU numSCSIVect*4 ; <C936/06Nov87> <PMAB466/JWK>
G_State EQU jmpTblSize+1 ; byte <PMAB466/JWK>
ROMRegSave EQU $408266B4
ROMUnimp EQU $408266FE
ROMDataEnd EQU $4082681A
ROMBlCmp1 EQU $40826B4A
ROMBlRd1 EQU $40826B54
ROMBlWr1 EQU $40826B9C
ROMGetExit EQU $40826744 ; exit the SCSIGet code <PMAB466/JWK>
ROMGetArb EQU $4082673A ; jump to "bsr Arbitrate" and continue <PMAB466/JWK>
move.l (sp)+,a0 ; get the return address
move.w (sp)+,d0 ; function selector (word)
move.l a0,-(sp) ; push the return address
cmp.w #numSCSIVect,d0 ; valid selector?
bhs.s @Unimp ; Sorry, Charlie
link a6,#LocalSize ; locals for bus error stuff
jmp ROMRegSave ; carry on as before
@Unimp
jmp ROMUnimp ; give them the bomb
;———————————————————————————————————————————————————————————————————————————————————————
;
; PMAB466 13Apr88 JWK SCSIGet SCSIMgr.a
;
; This cleans up the SCSIGet arbitration scheme. A "bset" instruction is used to
; test-and-set the SCSI Mgr's G_State global state variable. The ROM implementation
; could allow two processes into the SCSI Mgr code.
;
NewSCSIGet
bset.b #0,G_State(a4) ; mark SCSI Mgr state as "sBusy" <PMAB466/JWK>
beq.s @1 ; if zero, SCSI Mgr was free <PMAB466/JWK>
moveq.l #scMgrBusyErr,d0 ; SCSI Mgr is busy <PMAB466/JWK>
jmp ROMGetExit ; get out <PMAB466/JWK>
@1
jmp ROMGetArb ; jump to "bsr Arbitrate" and continue <PMAB466/JWK>
;--------------------------------------------------------------------------
;
; FUNCTION SCSIWrite(Control:Ptr): INTEGER;
; FUNCTION SCSIWBlind(Control:Ptr): INTEGER;
; FUNCTION SCSIRead(Control:Ptr): INTEGER;
; FUNCTION SCSIRBlind(Control:Ptr): INTEGER;
; (8) (12)
;
; This is the heart of the SCSI data transfer code, which includes the
; Transfer Information Block (TIB) interpreter.
;
mySCSIWBlind
bset #15,d4 ; blind flag
mySCSIWrite
st.b d4 ; set write flag
IF PatchSCSIRead THEN
bra.s myDataCommon
mySCSIRBlind
bset #15,d4 ; blind flag
mySCSIRead
move.b zeroReg,d4 ; clear write flag
move.b #iIO,sTCR+WrOffs(a3) ; match Data In phase
move.b #iDMA,sMR+WrOffs(a3) ; set DMA mode
move.b zeroReg,sIDMArx+WrOffs(a3) ; start DMA for a read
ENDIF
myDataCommon
moveq.l #bDMAR,d3 ; bit for DREQ test used in DataXFER <29Oct85>
move.l 8(a6),a1 ; get the control block pointer
bra.s @exec ; tighten loop by branching first
@c_compare
move.b #1,d4 ; this means compare to DataXFER <29Oct85>
; FALL THROUGH to @c_inc
@c_inc ; INC Addr,count
bsr.s @DataXFER ; move some data <23Apr86 LAK>
bne.s @data_end
add.l d2,scParam1(a1) ; increment the pointer
; FALL THROUGH to @next_cmd
@next_cmd
@c_nop ; NOP, just skip the command
add.w #SCSIZE,a1 ; move the command pointer
; FALL THROUGH to @exec
@exec
move.w scOpcode(a1),d0 ; get the function opcode
move.l scParam1(a1),a2 ; get the generic address
move.l scParam2(a1),d2 ; get the generic count
cmp.w #maxOpcode,d0 ; valid opcode?
bhi.s @c_badop ; return error if not
jmp @JmpTable(d0.w*2) ; go to jump table
@JmpTable
bra.s @c_badop ; 0 is not a valid opcode
bra.s @c_inc ; 1
bra.s @c_noinc ; 2
bra.s @c_add ; 3
bra.s @c_move ; 4
bra.s @c_loop ; 5
bra.s @c_nop ; 6
bra.s @c_stop ; 7
bra.s @c_compare ; 8
@c_badop
moveq.l #scBadParmsErr,d0 ; bad opcode
bra.s @data_end
@c_noinc ; NOINC addr,count
bsr.s @DataXFER ; move some data <23Apr86 LAK>
bne.s @data_end
bra.s @next_cmd ; and process next command
@c_add ; ADD addr,data
add.l d2,(a2) ; the count added to the where
bra.s @next_cmd
@c_move ; MOVE addr1,addr2
move.l d2,a0
move.l (a2),(a0) ; simple enough
bra.s @next_cmd
@c_loop ; LOOP relative addr,count
subq.l #1,d2 ; drop the count
beq.s @next_cmd ; if count = 1, quit loop <PB208>
move.l d2,scParam2(a1) ; put the count back for next time
add.l a2,a1 ; modify the command pointer
bra.s @exec ; and process the next command
@c_stop
moveq.l #noErr,d0 ; indicate no error, fall through.
@data_end
jmp ROMDataEnd ; back to the ROM
;--------------------------------------------------------------------------
;
; Move some data. d2 bytes into/from a2->.
; d4 contains modifying information:
; bit 15 is the blind bit.
; d4.b = minus = write
; = zero = read
; = plus = compare
;
; d2 contains the byte count on entry.
;
@DataXFER
moveq.l #0,d0 ; assume success (error code 0)
lea sBSR(a3),a4 ; save later indexing
tst.l d2 ; zero count?
beq.w @Xfer_rts ; yes, so exit
movem.l a1/d2,-(sp) ; save these registers
move.w #5,BusErrCount(a6) ; initialize count-down variable
move.l BusErrVct,OldBusErrVct(a6) ; keep old vector
lea @BusErrHandler,a0 ; use our handler
move.l a0,BusErrVct
tst.b d4 ; read or write?
bpl.s @RdCmp
@wreq
btst.b #bREQ,sCSR(a3) ; test for *REQ
beq.s @wreq
move.b zeroReg,sTCR+WrOffs(a3) ; match data out
move.b #iDMA,sMR+WrOffs(a3) ; set DMA mode
move.b #iDB,sICR+WrOffs(a3) ; assert data bus
move.b zeroReg,sDMAtx+WrOffs(a3) ; start write DMA
IF PatchSCSIRead THEN
bra.s @ckphase
@RdCmp
btst.b d3,(a4) ; test DRQ
bne.s @BlChk ; if there, ready for bytes
btst.b #bREQ,sCSR(a3) ; test for *REQ in case of phase error
beq.s @RdCmp ; no req either, must be seeking
ENDIF
@ckphase
btst.b #bPM,(a4) ; phase check
bne.s @BlChk ; branch if OK
moveq.l #scPhaseErr,d0
bra.w @Xfer_done
@BlChk
tst.w d4 ; if d4 is <1, these are blinds...
bmi.s @BlkStart ; go to the blind code
subq.l #1,d2 ; decr for DBRA
move.l d2,d5 ; make a copy of the byte count
swap d5 ; and get high word in d5
;
; Polled transfer modes
;
move.l SCSIDMA,a1 ; use the global
IF PatchSCSIRead THEN
tst.b d4 ; write/read?
bmi.s @SnWr ; it's a write
lea sIDR(a1),a0 ; input data offset
beq.s @SnRd ; it's a read
; else it's a compare
;
; This is the loop for polled compares. Byte count is in d2,d5
;
@SnCmp
btst.b d3,(a4) ; DRQ?
beq.s @SnCmpChk ; no, so check phase
move.b (a0),d1 ; get data byte
cmp.b (a2)+,d1 ; same?
beq.s @SnCmp1
moveq.l #scCompareErr,d0 ; record compare error
@SnCmp1
dbra d2,@SnCmp
dbra d5,@SnCmp
bra.s @RdDone
@SnCmpChk
btst.b #bPM,(a4) ; phase OK?
bne.s @SnCmp ; continue if it is
bra.s @RdPhaseErr ; else return error
;
; This is the loop for polled reads. Byte count is in d2,d5
;
@SnRd
btst.b d3,(a4) ; DRQ?
beq.s @SnRdChk ; no, so check phase
move.b (a0),(a2)+ ; read bytes into memory
@SnRd1
dbra d2,@SnRd
dbra d5,@SnRd
bra.s @RdDone
@SnRdChk
btst.b #bPM,(a4) ; phase OK?
bne.s @SnRd ; continue if it is
@RdPhaseErr
moveq.l #scPhaseErr,d0 ; else return error
bra.s @RdDone
ENDIF ; (IF PatchSCSIRead)
;
; This is the loop for polled writes. Byte count is in d2,d5
;
@SnWr
btst.b d3,(a4) ; DRQ?
beq.s @SnWrChk ; no, so check phase
move.b (a2)+,(a1) ; write bytes from memory
@SnWr1
dbra d2,@SnWr
dbra d5,@SnWr
bra.s @WrDone
@SnWrChk
btst.b #bPM,(a4) ; phase OK?
bne.s @SnWr ; continue if it is
moveq.l #scPhaseErr,d0 ; else return error
bra.s @DMAOff
;
; We get here for blind mode operations...
;
@BlkStart
move.l SCSIHsk,a1 ; hardware-handshaking write
lea sIDR(a1),a0 ; read address (NOTE: sODR = 0)
@DRQSync
btst.b d3,(a4) ; first wait for DMA to start
beq.s @DRQSync
IF PatchSCSIRead THEN
tst.b d4 ; test the I/O direction
beq.s @StartBlRd ; it's a read...
bmi.s @StartBlWr ; or a write...
; must be a compare, so fall through
@StartBlCmp
jsr ROMBlCmp1 ; do the ROM version
bra.s @RdDone
@StartBlRd
jsr ROMBlRd1 ; do the ROM version
bra.s @RdDone
ENDIF
@StartBlWr
jsr ROMBlWr1 ; do the ROM version
; We shouldn't turn off DMA mode before the last byte was
; taken. If the NCR chip asserts DRQ, then the peripheral got
; the byte. If the peripheral changes the bus phase, then it
; must have also gotten it.
@WrDone
btst.b d3,(a4) ; did we get DRQ?
bne.s @DMAOff ; if so, then turn DMA mode off
btst.b #bPM,(a4) ; still in the same phase?
bne.s @WrDone ; if so, then wait around...
@DMAOff
move.b zeroReg,sMR+WrOffs(a3) ; clear DMA mode
move.b zeroReg,sICR+WrOffs(a3) ; disable data bus
bra.s @Xfer_done ; <PB208>
@RdDone
btst.b #bREQ,sCSR(a3) ; test for *REQ <PB208>
beq.s @Xfer_Done ; if it's gone, we're done <PB220>
btst.b #bPM,(a4) ; still in same phase? <PB220>
bne.s @RdDone ; if so, go back and wait <PB220>
@Xfer_Done
move.l OldBusErrVct(a6),BusErrVct ; restore previous vector
movem.l (sp)+,a1/d2 ; restore the registers
tst.w d0 ; set the condition codes
@Xfer_rts
rts
;____________________________________________________________________________ jwk <18>
;
; BusErrHandler -- New and improved chaining SCSI bus error handler.
; When the SCSI Mgr is performing a blind data transfer, it patches
; out the bus error vector. The old SCSI Mgr bus error handler
; assumed that if it got called, it must be handling a SCSI bus error.
; Unfortunately, NuBus cards could bus error while the SCSI Mgr is
; installed. To be a better bus error citizen, the SCSI bus error
; handler now checks for a SCSI address as the fault address, and
; chains to the bus error handler that it replaced.
;
@BusErrHandler
move.l d0,-(sp) ; save d0 <18>
moveq.l #$ffffff9c,d0 ; mask = $ffffff9c <start>
and.l 4+$10(sp),d0 ; clear variable bits of the fault address
cmp.l SCSIHsk,d0 ; was it a SCSI chip access ?
beq.s @start ; if so, start processing the bus error
move.l (sp)+,d0 ; restore d0
move.l OldBusErrVct(a6),-(sp) ; put old bus error handler addr on stack <end>
rts ; jump to old handler, assuming it'll RTE <18>
@start
subq.w #1,BusErrCount(a6) ; retry until we get tired
beq.s @CleanUp
move.w TimeDBRA,d0 ; DBRA's per millisecond <18>
lsr.w #4,d0 ; 1ms/16 = approximately 62us (was 50us) <18>
@ErrWait dbra d0,@ErrWait ; recovery time (was 50us) <C865/PB208> <18>
move.l (sp)+,d0 ; restore d0 <18>
rte ; haven't reached max, so restart
@CleanUp
addq.l #4,sp ; throw away copy of d0 on stack <18>
move.w (sp),d0 ; get sr from the stack
bfextu 6(sp){0:4},d1 ; get format code from stack
cmp.b #$0A,d1 ; short exception frame?
bne.s @Drop46w ; no, so use larger frame
adda.w #16*2,sp ; dispose of the 16-word frame
bra.s @DummyFrame ; and finish up
@Drop46w ; format code $0B
adda.w #46*2,sp ; dispose of the 46-word frame
@DummyFrame
move.w zeroReg,-(sp) ; format code 0 (four word frame)
pea @Continue ; PC value
move.w d0,-(sp) ; sr value
rte ; 'return' from the fake exception
@Continue
moveq.l #scBusTOErr,d0 ; assume a slow peripheral
btst.b #bPM,sBSR(a3) ; phase change? <C478/10Dec86> <v1.5><18>
bne.s @ErrorDone ; no phase change
moveq.l #scPhaseErr,d0 ; return phase change error
@ErrorDone
rts ; return to TIB interpreter
;
; End of chaining SCSI bus error handler patch
;____________________________________________________________________________ jwk <18>
;_________________________________________________________________________________________ <72> djw
; Beginning code for Quantum 7.9 ROM fix
;
; Detailed description of the Quantum problem and solution:
;
; Quantum drives with the firmware version 7.9, has a problem with loosing the last byte
; of a block during a multi-block write. The problem occurs when the time between blocks
; written to the SCSI bus on the CPU side, is greater than 482 microseconds. This may
; occur in situations where there are a lot of interrupts. When conditions are right and
; the problem happens, the last byte of the previous block (in a multi-block transaction),
; is "eaten" by the drive. Any checksum or CRC calculated by the drive is correct,
; because the drive calculates it after the byte has been corrupted. This problem is
; especially frequent when email packages are installed on the Mac, since they generate
; a lot of interrupts which take a long time. This problem only occurs during fast
; writes in the SCSI manager (pseudo-dma mode).
;
; The way the SCSI manager currently works is it gets a TIB packet which contains the
; instructions on how to talk to a particular device. Included in the TIB is when to
; re-synchronize with the drive by waiting for a *REQ. When we see *REQ, the SCSI
; manager then begins the next TIB data transfer instruction and loads a byte of data
; into the 53C80's output register. After the first byte is "manually" sent, the
; hardware handshaking automatically takes care of the *REQ and *ACK handshaking. When
; the TIB write transfer is complete, pseudo-dma is disable, which releases *ACK,
; completing the handshake. This allows the target to assert *REQ when it is ready.
;
; The window of vulnerability is between the last byte of the previous block and the
; first byte of the next block. More correctly, it is between the rising edge of *ACK
; and the falling edge of the next *ACK. Because we release *ACK to synchronize, an
; interrupt may come in and delay the next transfer.
;
; The solution to the problem is to pre-load a data byte into the 53C80's data output
; register before we release *ACK. There are two ways of releasing *ACK: disable pseudo
; dma, and write a byte to the data output register. Leaving pseudo-dma enabled through
; the entire TIB will mean that whenever a *REQ occurs, there will be data available in
; the output register. This means there will be no delay between bytes because the
; hardware is not subject to interrupt delays.
;
; This patch therefore involves patching the TIB interpreter and the fast write routine
; in the SCSI manager. There are five versions of the SCSI manager to patch: Mac Plus,
; SE, Mac II, Portable, and IIci.
;
;_________________________________________________________________________________________
; QuantumWBlindII - patch to NewSCSIWBlind
;
; This code replaces the original SCSIWBlind entry point. The new entry for blind
; writes enables pseudo-dma on a per-transaction basis. Pseudo-dma was previously
; enabled only on a per-TIB-instruction basis. We completely patch out the existing
; ROM and system patch code for blind writes. This includes the TIB interpeter and
; the blind data transfer routine.
;
; Input: reg a3 = base of SCSI read addr
; a6 = SCSI stack frame
; d7 = zero
;
Export QuantumWBlindII
QuantumWBlindII
; This is the entry to the TIB interpeter for blind writes. Enable pseudo-dma mode
; for the duration of the write transaction.
move.b d7,sTCR+WrOffs(a3) ; set to match data out phase (to zero)
move.b #iDMA,sMR+WrOffs(a3) ; enable DMA in mode register
move.b #iDB,sICR+WrOffs(a3) ; assert data bus in initiator command reg
move.b d7,sDMAtx+WrOffs(a3) ; start write DMA
; Start of TIB interpreter
dataCommon
move.l 8(a6),a1 ; get the TIB pointer
bra.s @exec ; tighten loop by branching first
@c_inc
bsr.s FastWriteFix ; go to write blind routine
bne.s @data_end ; if error, bail out
add.l d1,scParam1(a1) ; increment the pointer
; FALL THROUGH to @next_cmd ; continue
@next_cmd
@c_nop ; also NOP, just skip the command
add.w #scSize,a1 ; point to the next TIB instruction
; FALL THROUGH to @exec
@exec
move.w scOpcode(a1),d1 ; get the function opcode
move.l scParam1(a1),a2 ; get the generic address
move.l scParam2(a1),d2 ; get the generic count
cmp.w #maxOpcode,d1 ; valid opcode ?
bhi.s @c_badop ; return err if not
jmp @JmpTable(d1.w*2) ; jump into table
@JmpTable
bra.s @c_badop ; 0 is not a valid opcode
bra.s @c_inc ; 1
bra.s @c_noinc ; 2
bra.s @c_add ; 3
bra.s @c_move ; 4
bra.s @c_loop ; 5
bra.s @c_nop ; 6
bra.s @c_stop ; 7
nop ; 8 not valid
; fall through to @c_badop
@c_badop
moveq.l #scBadparmsErr,d0 ; bad opcode
bra.s @data_end
@c_noinc ; NOINC addr,count
bsr.s FastWriteFix ; go to write blind routine
bne.s @data_end ; if error, exit
bra.s @next_cmd ; else process next command
@c_add ; ADD addr,data
add.l d2,(a2) ; the count added to the address
bra.s @next_cmd ; process the next command
@c_move ; MOVE addr1,addr2
move.l d2,a0 ; get the destination address
move.l (a2),(a0) ; simple enough
bra.s @next_cmd ; process the next command
@c_loop ; LOOP relative addr,count
tst.l d2 ; check for zero loop count
beq.s @next_cmd ; if count is already zero, quit loop
subq.l #1,d2 ; drop the count
move.l d2,scParam2(a1) ; put the count back for next time
beq.s @next_cmd ; if count exhausted, don't loop
add.l a2,a1 ; modify the command pointer
bra.s @exec ; and process the next command
@c_stop
moveq.l #noErr,d0 ; indicate no error
; FALL THROUGH to @data_end
@data_end
jmp (ROMDataEnd) ; back to ROM <77> djw
;_________________________________________________________________________________________
; FastWriteFix - patch to FastWrite
;
; This code replaces the low level data transfer routine for fast writes in the SCSI
; manager. It is rewritten to assume psuedo-dma is always on, and to do the device
; synchronization (looking for *REQ and *DRQ), after loading a data byte into the
; output register of the 5380. We don't have to worry about zero-byte transfers. They
; are weeded out in the calling routine (Transfer).
;
; Entry: d2 = number of bytes to transfer
; a2 = ptr to data buffer to transfer
; a3 = base addr of NCR 53C80
;
; Exit: d1 = number of bytes actually transfered. This value is only good if
; the transfer was good with no errors. It is inaccurate when an
; error aborts the transfer.
FastWriteFix
@savedregs Reg d2-d4/a1-a2/a5
; Setup for the transfer by installing our bus exception handler and saving
; registers.
movem.l @savedregs,-(sp)
move.w #5,BusErrCount(a6) ; store upper limit for allowable bus errors <77> djw
lea.l sBSR(a3),a1 ; a1 = sBSR(a3) by convention
lea @Done,a5 ; a5 = return addr if bus excptn
move.l BusErrVct,OldBusErrVct(a6) ; keep old vector
lea @BusErrHandler,a0 ; get addr of exception handler
move.l a0,BusErrVct ; install it in exception table
move.l SCSIHsk,a0 ; point to addr for pseudo-dma (hhsk)
; Check for zero count transactions
moveq.l #noErr,d0 ; assume no error
move.l d2,d1 ; make a copy of the count - is it zero ?
beq @Done ; no bytes to xfer - done
; Pre-load the NCR 53C80's output register with a byte of data. If we are in
; the middle of a multi-block write, *ACK is currently asserted. Writing a byte
; to the output register will release *ACK, completing the handshaking, allowing
; the target to assert *REQ.
sub.l #1,d2 ; dec number of bytes to xfer
move.b (a2)+,(a0) ; write data byte to output register
; With *ACK released, determine if the target is in sync. We cannot look for
; *REQ to be asserted, because the target may have already accepted the data byte
; and released *REQ at this point. We can sync on DRQ which will signal when
; the NCR 53C80 is ready to accept a data byte, meaning a *REQ from the target
; must have already occurred and our data byte was taken.
@syncWait
btst.b #bDMAR,(a1) ; check bus & status reg for DRQ
bne.s @doWrite ; DRQ present - sync-ed up so proceed
btst.b #bREQ,sCSR(a3) ; no DRQ - is *REQ present ?
beq.s @syncWait ; no *REQ yet - wait for sync
btst.b #bPM,(a1) ; with *REQ, check phase lines
bne.s @syncWait ; still in data out phase - wait
moveq.l #0,d1 ; out of phase - did not xfer any bytes
moveq.l #scPhaseErr,d0 ; return error
bra.s @Done ; exit
; Perform the write to the SCSI chip. First align the bytes to longs, then
; align them to 32 byte chunks. Transfer the bulk of the data in 32 byte
; blocks.
; Reg d2.l = number of bytes to move
@doWrite
cmpi.l #3,d2 ; check for very short copy
bls.s @veryShort ; skip alignment if very short
move.l a2,d0 ; get addr of data buffer
andi.l #$00000003,d0 ; check for long word alignment
beq.s @Aligned ; if no alignment needed
subq.l #4,d0 ; bias by 4 to get correct index
jmp @Aligned(d0.w*2) ; do the alignment
move.b (a2)+,(a0) ; move a byte
move.b (a2)+,(a0) ; move a byte
move.b (a2)+,(a0) ; move a byte
@Aligned
add.l d0,d2 ; adjust the byte count (d0 = neg)
move.l d2,d4 ; save tail byte count
lsr.w #2,d2 ; adjust to number of longs to move
moveq.l #7,d0 ; mask for starting index
and.l d2,d0 ; number of long words to move first
neg.w d0 ; negate to index backwards
lsr.l #3,d2 ; number of 32 byte blocks to move
move.l d2,d3 ; get number of 32*64K byte blks to move
swap d3 ; count in low word
jmp @CopyStart(d0.w*2) ; jump into the loop
@CopyLoop move.l (a2)+,(a0) ; move a 32 byte block of data....
move.l (a2)+,(a0) ; ... 4 bytes at a time
move.l (a2)+,(a0)
move.l (a2)+,(a0)
move.l (a2)+,(a0)
move.l (a2)+,(a0)
move.l (a2)+,(a0)
move.l (a2)+,(a0)
@CopyStart dbra d2,@CopyLoop ; loop in chunks of 32 bytes
dbra d3,@CopyLoop ; loop in chunks of 32*64K bytes
andi.l #$00000003,d4 ; check for tail alignment
move.l d4,d2 ; d2 = number of bytes remaining
@veryShort
neg.w d2 ; negate to index backwards
jmp @Remaining(d2.w*2) ; write remaining bytes
move.b (a2)+,(a0) ; move a byte
move.b (a2)+,(a0) ; move a byte
move.b (a2)+,(a0) ; move a byte
@Remaining
; Before exiting this routine, make sure that the peripheral has actually accepted
; the data byte. Wait for a DRQ (meaning the SCSI chip is ready for another byte)
; before exiting.
@DoneWait
moveq.l #noErr,d0 ; set good return
btst.b #bDMAR,(a1) ; check for DRQ (a1 = sBSR(a3))
bne.s @Done ; if DRQ, peripheral got the byte
btst.b #bREQ,sCSR(a3) ; no DRQ - is *REQ present ?
beq.s @DoneWait ; no *REQ yet - wait for it
btst.b #bPM,(a1) ; are we still in phase ?
bne.s @DoneWait ; if so, keep waiting
@Done
move.l OldBusErrVct(a6),BusErrVct ; restore previous Bus Error vector
movem.l (sp)+,@savedregs
tst.w d0 ; set the condition codes
rts ; we're done
;_________________________________________________________________________________________
; BusErrHandler - SCSI manager's bus exception handler for blind writes
;
; The SCSI manager patches out the bus exception vector during blind transfers. If
; a device fails to handshake within 4 microseconds, we get a bus exception. Retry
; the access to the SCSI chip a set number of times. If we exceed the rety count,
; then pop the exception stack frame and fake a short frame on the stack. Return
; from exception a given location.
;
; Input: a5 = addr to return to if retries expire
; a6 = SCSI manager locals
;
; Trashes reg d0 if retry expires
;
@BusErrHandler
move.l d0,-(sp) ; save d0
; Access to a number of SCSI addresses could cause a bus exception. Mask off the low
; bits of the fault address to get the base address. If it matches the SCSI chip's
; base address
moveq.l #$ffffff9c,d0 ; mask = $ffffff9c
and.l 4+$10(sp),d0 ; clear variable bits of the fault address
cmp.l SCSIHsk,d0 ; was it a SCSI chip access ?
beq.s @start ; if so, start processing the bus error
move.l (sp)+,d0 ; restore d0
move.l OldBusErrVct(a6),-(sp) ; jump to original handler
rts
; At this point, we believe the exception was caused by the SCSI manager. Decrement
; the re-try count. Continue re-trying the access until the count expires. Delay
; 62 microseconds between re-trys to allow the device to get its act together.
@start
subq.w #1,BusErrCount(a6) ; retry until we get tired
beq.s @CleanUp
move.w TimeDBRA,d0 ; DBRA's per millisecond
lsr.w #4,d0 ; 1ms/16 = approximately 62us (was 50us)
@ErrWait dbra d0,@ErrWait ; recovery time (was 50us)
move.l (sp)+,d0 ; restore d0
rte ; haven't reached max, so restart
; The device access failed past the retry count. Pop the bus exception stack
; frame and fake a short exception frame.
@CleanUp
addq.l #4,sp ; throw away copy of d0 on stack
move.w (sp),d0 ; get sr from the stack
adda.w #46*2,sp ; dispose of the 46-word frame
move.w #0,-(sp) ; format code 0 (four word frame)
move.l a5,-(sp) ; new return address
move.w d0,-(sp) ; sr value
; Determine whether this was a phase change or a device timeout from hardware handshaking
moveq.l #scBusTOErr,d0 ; assume a slow peripheral
btst.b #bREQ,sCSR(a3) ; is *REQ present ?
beq.s @ErrorDone ; no *REQ - assume timeout error
btst.b #bPM,sBSR(a3) ; phase change?
bne.s @ErrorDone ; no phase change
moveq.l #scPhaseErr,d0 ; return phase change error
@ErrorDone
rte ; 'return' from the fake exception
Endp
; end of SCSI patch
;
;___________________________________________________________________________
;____________________________________________________________________________ CCH <3.2>
; Record to describe gestalt function parameters
;
; Used by the following two gestalt patches <3.2> and <2.5>
;
gestaltParmFrame record {oldA6},decrement
result ds.w 1 ; OSErr
argSize equ *-8
gestaltSelector ds.l 1 ; packed array [1..4] of char
gestaltResult ds.l 1 ; addr of longint result
return ds.l 1
oldA6 ds.l 1
localFrame equ *
endR
;____________________________________________________________________________ CCH <3.2>
; Gestalt function for gestaltQuickdrawVersion
;
; The following is a patch to the gestaltQuickdrawVersion selector.
;
; Routine gestaltQDVers (
; gestaltSelector: OSType; = PACKED ARRAY [1..4] OF CHAR;
; VAR gestaltResult: Longint;
; ): OSErr; = Integer;
;
gestaltQD32Vers PROC EXPORT
with gestaltParmFrame
link a6,#localFrame
clr.l -(sp) ;make room for result
_OffScreenVersion
move.l gestaltResult(a6),a0 ; get address to place result
move.l (sp)+, d0 ; get QD version from GWorld
add.w #$100, d0
move.l d0, (a0) ; return version number for ci
move.w #noErr,result(a6) ; return no error
unlk a6
move.l (sp)+,a0 ; get return value
add.l #argSize,sp ; restore stack pointer
jmp (a0) ; return
ENDPROC
;____________________________________________________________________________________
; PB091 Cxxx 8Mar87 RDC PowerOff OS:InterruptHandlers.a
;
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 8Mar87 #PB091 (PowerOff) (PowerOff)
;
; PB541 Cxxx 22jul88 rwh PowerOff OS:InterruptHandlers.a
;
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 22jul88 PB541 (PowerOff) (PowerOff)
;
; Interrupt Handler patch for Power button interrupt. This patch fixes
; problem of turning system off from rear power button. If the button
; is depressed for too long the system will power off and then turn right
; back on. To fix the problem we wait for the button to be released before
; actually powering off the system. Also use timing constant to do about
; a half second delay before poweroff - fixed constant used instead of system
; determined value (i.e., TimeDBRA) for safety reasons.
; <PB541> Fix things so that PowerOff trap RETURNS if the machine didn't power off. This
; lets us use the Mac II ROM (actually, the Mac IIx ROM) in machines like Fafnir which
; do not have a soft power-off feature. The ShutDown code call to PowerOff conveniently
; is followed by the 'Its safe to Restart' dialog box code.
;
; <PB541> Note that we changed the TRAP vector to point to a different place than the
; power button interrupt vector, so we can still do the debounce/RTE code that was
; already here (Why the RTE stuff? Who knows, but don't change it cuz Mac II's do work).
; The trap now points to a place where we can to an rts. In the power button interrupt
; case on Mac II's, the two second delay should be ample time for the machine to power
; off before executing the rts (with a bogus return address cuz there is an interrupt
; stack frame on the stack, not a return address)
;
; OMIT FROM A/UX
;____________________________________________________________________________________
IF (&TYPE('vBase2') = 'UNDEFINED') THEN ; <6.2> Needed for Mac II Patch file
vBase2 EQU $50f02000 ; <6.2>
ENDIF ; <6.2>
NewPowerOff PROC EXPORT
EXPORT PowerOff ; <PB541>
ROMPowerOff EQU $408062EE ; ROM PowerOff address
OnemsDBRA EQU $0A3C ; about one ms DBRA loop (same as TimeDBRA)
PowerBtn BSET #6,NMIFlag ; use bit in NMIFlag as indicator
BNE.S PowerRTE ; skip if already in routine
; (button still depressed)
move.w #$2500,SR ; drop level to allow switch debounce <PB541>
bsr.s PowerOff ; attempt suicide (Fafnir won't) <PB541>
PowerRTE RTE ; just return until button released <PB541>
; entry point used by shutdown trap
PowerOff movem.l a0/d0-d1,-(sp) ; save regs, in case no soft poweroff <PB541>
CLR.L D0 ; clear for use
MOVE.W #OnemsDBRA,D0 ; get 1ms constant
MULU.W #500,D0 ; setup half second delay
MOVE.L D0,D1 ; save result
SWAP D1 ; setup high word
@1 DBRA D0,@1 ; decrement low word
DBRA D1,@1 ; then high word
;<PB541> JMP ROMPowerOff ; go back to ROM to do poweroff <PB541>
bsr.s Pause2Sec ; wait before dying <PB541>
MOVE.L #VBase2,A0 ; get base address of VIA2 <PB541>
BCLR.B #v2PowerOff,vBufB(A0) ; set VIA bits for poweroff <PB541>
BSET.B #v2PowerOff,vDirB(A0) ; goodbye... <PB541>
bsr.s Pause2Sec ; wait before rising from the dead <PB541>
movem.l (sp)+,a0/d0-d1 ; unsave regs, in case no soft poweroff <PB541>
rts ; this rts gets executed on machines <PB541>
; that don't have soft power-off <PB541>
; so ShutDown falls into 'safe to <PB541>
; restart' dialog <PB541>
Pause2Sec MOVEQ #OneSecConst*2,D0 ; setup twosec delay <PB541>
SWAP D0 ; to debounce button <PB541>
@1 SUBQ.L #1,D0 ; <PB541>
BNE.S @1 ; <PB541>
rts
ENDPROC
**********************************************************************************
* PB136 GetNewControl GetNewControl
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 24Mar87 #PB136 (GetNewControl) (GetNewControl)
;
* 24Mar87 JTC Patch GetNewControl to fix first instruction, that is, patch to
* use even-sized stack frame.
**********************************************************************************
MyGetNewControl PROC
ROMGNC2 EQU $1538A ; <PB302>
link a6,#-2 ; take two bytes, even if need just one
jmpRom ROMGNC2
ENDPROC
;-----------------------------------------------------------------------------
; PABM150 28Mar87 JTC&JAF New SysEnvirons call.
;
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 28Mar87 #PABM150 (SysEnvirons) (SysEnvirons)
;
INCLUDE 'SysEnvirons.a' ;<PMAB449>
*************************************************************************
* PB172 Patch Pack4 to fix Pack4 as implemented in ROM. In case of bin 2 dec
* conversion, signaled by opword bits $0B, clear bit #30 of D3 (or all bits, if
* you please) for use as an internal variable. By its nature, this patch should
* work (or cause no problems) for ANY version of Pack4, so we neednt test whether
* were in the ROM version or not. Without this patch, numbers may be too
* small by 1ulp in decimal, so that 100 is 99.9999999 and the hideous like.
;
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 01jan1904 #PB172 (Pack4) (Pack4)
;
*************************************************************************
myPack4 proc
MOVEM.L D0/A0-A1,-(SP) ; two work regs and a slot for the pack address
@P4Retry
MOVE.L AppPacks+16,D0 ; low-mem handle
BEQ.S @P4NoHand ; no handle, no speed
MOVEA.L D0,A0 ; need to deref
MOVE.L (A0),8(SP) ; alleged ptr into rts cell
BEQ.S @P4LoadIt ; purged, no speed
BRA.S @P4GotIt
@P4NoHand ; get it the old-fashioned way
CLR.L -(SP) ; room for handle
MOVE.L #'PACK',-(SP) ;
MOVE.W #4,-(SP) ;
MOVE.W #MapTrue,ROMMapInsert ; use ROM map as well
_GetResource
MOVE.L (SP)+,AppPacks+16
BNE.S @P4Retry
@P4Die
MOVEQ #21,D0 ; Pack4notfound
_SysError ; out of luck this time...
@P4LoadIt
MOVE.L A0,-(SP) ; handle
MOVE.W #MapTrue,ROMMapInsert ; use ROM map as well
_LoadResource
MOVE.L (A0),8(SP) ; jam address of package
BEQ.S @P4Die ; if not loaded out of luck
@P4GotIt
MOVEQ #$1F,D0 ; mask for opcode bits
AND.W 16(SP),D0 ; D0<A0<ADRS<RET<opword<3longs
CMPI.B #$0B,D0 ; is it bin2dec?
BNE.S @P4Safe ; if not, go on as usual
; Now munge frame to save d3 across call, return to patch, and strip all
; extraneous parameters.
MOVEM.L (SP)+,D0/A0 ; stack: pack<rts<opword<3longs
MOVE.L D3,-(SP) ; save d3 across the dreaded call
MOVE.L 22(SP),-(SP) ; R3<d3<pack<rts<op<3longs
MOVE.L 22(SP),-(SP) ; R2<R3<d3<pack<rts<op<3longs
MOVE.L 22(SP),-(SP) ; R1<R2<R3<d3<pack<rts<op<3longs
MOVE.W 24(SP),-(SP) ; op<R1<R2<R3<d3<pack<rts<op<3longs
PEA @P4cleanUp ; now have new stack frame
MOVE.L 22(SP),-(SP) ; pack<ourrts<op<R1<R2<R3<d3<pack<rts<op<3longs
MOVEQ #0,D3 ; dummy up internal variable LostDigitFlag
RTS ; off to Pack4 at last!
@P4cleanUp ; resume here with d3<pack<rts<op<3longs
MOVE.L (SP)+,D3 ; restore our friend
ADDQ.L #4,SP ; strip pack, leaving rts<op<3longs
MOVE.L (SP),14(SP) ; op<2longs<rts
ADDA.W #14,SP ; rts
RTS ; back to original caller
@P4Safe
MOVEM.L (SP)+,D0/A0 ; restore work regs
RTS ; branch to package with clean stack
endproc ; myPack4
; ******************************************************************************************
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 16Jul87 #PB206 (PatConvert) (SetCCursor)
PatConvert PROC EXPORT
;-------------------------------------------------------------
;
; Replace PatConvert to fix a bug in SetCCursor
;
; BUG8: A2 would be trashed while expanding the cursor's
; data, and then be used in the multiple device loop (crash!).
FromSetCC EQU $1AF5C ;Return address we want <PB302>
ROMPatCvt EQU $1F36A ;Routine we're patching <PB302>
ROMA2ok EQU $1AF8C ;Where to go when done <PB302>
EXTBL EQU $22C16 ;Table of expand routines<<PB266 BAL 08Sep87>><PB302>
CMPRA FromSetCC,(SP) ;called by setCCursor? <<PB242 BAL 24Aug87>><PB302>
;used to be #ROMPatCvt <<PB242 BAL 24Aug87>>
BNE.S @NotUs ;=> no, continue
ADDQ #4,SP ;strip old return address
PEA @Patch ;and push new address
@NotUs JMPROM ROMPatCvt ;call the real routine <PB302>
@Patch MOVE.L (SP)+,THEGDEVICE ;RESTORE GRAFDEVICE
; EXPAND THE MASK TO THE CURRENT DEPTH
MOVE D3,D0 ;GET DEPTH
MOVEQ #0,D1 ;DEFAULT SHIFT = 0
@NXTSHFT1 LSR #1,D0 ;CHECK NEXT DEPTH BIT
BCS.S @GOTSHFT1 ;=>GOT SHIFT
ADDQ #1,D1 ;ELSE ADD ONE TO SHIFT
BRA.S @NXTSHFT1 ;LOOP UNTIL WE HIT A ONE
@GOTSHFT1 MOVE.L A2,-(SP) ;preserve A2 across expansion
LEA THECRSR+MASK,A0 ;SRC = CURSOR MASK
MOVE.L ([GDCCXMASK,A4]),A1 ;POINT TO EXPANDED MASK (LOCKED)
MOVE.L A1,A2 ;GET START OF DST BUFFER
MOVE #32,D0 ;GET #BYTES OF SOURCE
LSL D1,D0 ;MULTIPLY BY DEPTH
ADD D0,A2 ;POINT TO END OF BUFFER
LEA ([ROMBASE],EXTBL),A3 ;POINT TO ROUTINE TABLE <PB302>
ADD 0(A3,D1*2),A3 ;USE DEPTH TO SELECT ROUTINE
MOVEQ #0,D0 ;CLEAR HIGH PART OF D0
JSR (A3) ;EXPAND 32*DEPTH BYTES
MOVE.L (SP)+,A2 ;restore A2
JMPROM ROMA2ok ;=> return with A2 restored <PB302>
;___________________________________________________________________________
; PB212 CXXX 20Jul87 DAF GetNewCWindow
;
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 20Jul87 #PB212 (GetNewCWindow) (GetNewCWindow)
;
;
; FUNCTION GetNewCWindow(windowID: INTEGER; wStorage: Ptr; behind: windowPtr):windowPtr;
;
; GetNewWindow allocates a new window using the parameters contained
; in the "WIND" resource specified by the windowID
;
myGetNewCWindow PROC EXPORT
GetWDone EQU $15338 ; <PB302>
NoGetNew1 EQU $1537A ; <PB302>
result EQU 18 ; parameter equates
winID EQU 16
wStor EQU 12
behind EQU 8
VisState EQU -1 ; flag for resource's vis state <C314/31Oct86> DAF
Align EQU -2 ; another byte to re-align stack frame <C666/22Jan87> DAF
LINK A6,#Align ; build stack frame
MOVE.L A3,-(SP) ; preserve a work register
CLR.L result(A6) ; set result to NIL
SUBQ #4,SP ; make space for result
MOVE.L #'WIND',-(SP) ; push resource class "WIND"
MOVE.W winID(A6),-(SP) ; push window ID
_GetResource ; get the resource
MOVE.L (SP)+,A3 ; keep handle in A3
MOVE.L A3,D0 ; did we get one?
BNE.S @1 ; if so, continue <PB212>
JMPROM NoGetNew1 ; if not, don't allocate one <PB302>
@1
MOVE.L (A3),A0 ; keep pointer in A0
;
; OK, we got the parameter block so call NewWindow to allocate the window
;
SUBQ #4,SP ; make space for result
MOVE.L wStor(A6),-(SP) ; push wStorage
MOVE.L A0,-(SP) ; push pointer to boundsRect
PEA 18(A0) ; push pointer to title
MOVE.B 10(A0),VisState(A6) ; keep original vis state <A353/05Nov86> DAF
CLR.W -(SP) ; push vis FALSE <A353/05Nov86> DAF
MOVE.W 8(A0),-(SP) ; push procID <A353/05Nov86> DAF
MOVE.L behind(A6),-(SP) ; push "behind"
MOVE.W 12(A0),-(SP) ; push GoAway flag
MOVE.L 14(A0),-(SP) ; push the refCon
MOVEA.L A3,A0 ; handle <C169>
_HLock ; trash D0 <C169>
_NewCWindow ; allocate a color window <C106 EHB>
clr.l -(sp) ; make room for palette handle <erich>
move winID(a6),-(SP) ; push window ID <erich>
_GetNewPalette ; fetchez la palette <erich>
move.l (sp)+,d0 ; well? <erich>
Beq.S NoWindowPltt ; sorry, no automatic palette today AWC.PB459
Move.L D0,A0 ; get the palette AWC.PB459
Move.L (A0),A0 ; dereference it AWC.PB459
Move PmPrivate(A0),D1 ; grab the update bits AWC.PB459
Lsr #1,D1 ; put them in position AWC.PB459
BSet #NNewBit,D1 ; use the new CUpdates format AWC.PB459
BSet #DisposeBit,PmPrivate(A0) ; set for automatic disposal AWC.PB459
move.l (sp),-(sp) ; push the window <erich>
move.l d0,-(sp) ; push the palette <erich>
move D1,-(sp) ; push cUpdates AWC.PB459
_SetPalette ; <erich>
NoWindowPltt ; AWC.PB459
JMPROM GetWDone ; and back to the ROM <PB212/DAF> <PB302>
ENDPROC
;___________________________________________________________________________
; PB217 CXXX 22Jul87 BAL RSECT
;
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 22Jul87 #PB217 (RSECT) (DrawLine)
;AppleSystemPatch PatchIIROM.a 22Sep87 #PB286 (RSECT) (DrText)
;
;
; 2 Patches to RSect to fix bug in DrawLine, DrText
;
; DrawLine fast case is taken for black or white patterned single
; pixel horizontal or vertical lines. The test for black or white patterns
; in the ROM DrawLine is incompatible with new patterns. This patch
; allows fastline to be used in CGrafPorts.
;
; When skipping the shieldCursor call for offscreen pixmaps, drText branched <<PB286>>
; to NotFast instead of GetPtrs. This resulted in all offscreen drawing unnecessarily <<PB286>>
; taking the slow text drawing case--furthermore crashes would occur if the offscreen drawing <<PB286>>
; was to a multibit pixmap. <<PB286>>
;
;------------------------------------------------------------------
;___________________________________________________________________________
; PB286 CXXX 22Sep87 BAL RSECT
;
;
; 1st Patch to RSect to fix bug in DrText
;
; When skipping the shieldCursor call for offscreen pixmaps, drText branched <<PB286>>
; to NotFast instead of GetPtrs. This resulted in all offscreen drawing unnecessarily <<PB286>>
; taking the slow text drawing case--furthermore crashes would occur if the offscreen drawing <<PB286>>
; was to a multibit pixmap. <<PB286>>
;
; PB362
;
; Extend this patch to fix fractional pen positioning in new ports
;------------------------------------------------------------------------
MyTextFix PROC EXPORT
;------------------------------------------------------------
;
; PROCEDURE DrText(count: INTEGER; textAddr: Ptr; numer,denom: Point);
;
; DRAWS CHARACTERS INTO THE CURRENT PORT'S BITMAP.
; THE FONT AND ATTRIBUTES ARE GIVEN IN THE CURRENT PORT'S CHARSTYLE.
;
oldIteration EQU 0
;-------------------------------------------
;
; KERNED STRIKE FONT FORMAT OFFSETS:
;
FORMAT EQU 0 ;WORD
MINCHAR EQU 2 ;WORD
MAXCHAR EQU 4 ;WORD
MAXWD EQU 6 ;WORD
FBBOX EQU 8 ;WORD fKernMax
FBBOY EQU 10 ;WORD save as nDescent; unused except as high owTLoc
FBBDX EQU 12 ;WORD fRectWidth
FBBDY EQU 14 ;WORD fRectHeight
LENGTH EQU 16 ;WORD owTLoc
ASCENTVAL EQU 18 ;WORD
DESCENTVAL EQU 20 ;WORD
XOFFSET EQU 22 ;WORD leading
RASTER EQU 24 ;WORD rowWords
;------------------------------------------------------
;
; A6 OFFSETS OF PARAMETERS AFTER LINK:
;
PARAMSIZE EQU 14 ;SIZE OF PARAMETERS
CHARCOUNT EQU PARAMSIZE+8-2 ;WORD
TEXTADDR EQU CHARCOUNT-4 ;LONG
NUMER EQU TEXTADDR-4 ;LONG, POINT
DENOM EQU NUMER-4 ;LONG, POINT
;-----------------------------------------------------------
;
; A6 OFFSETS OF LOCAL VARIABLES AFTER LINK:
;
SAVESTK EQU -4 ;long stack before allocating buffers
TEXTRECT EQU SAVESTK-8 ;RECT original bounding rect
TEXTR2 EQU TEXTRECT-8 ;RECT copy of textRext used by maprect
MINRECT EQU TEXTR2-8 ;RECT minimum rect for clipping
BUFEND EQU MINRECT-4 ;LONG where the offscreen buffer ends
BUFSIZE EQU BUFEND-2 ;WORD the size of the offscreen buffer
BUFROW EQU BUFSIZE-2 ;WORD the rowBytes for the offscreen buffer
BUF2START EQU BUFROW-4 ;LONG second buffer used for shadow
BUF2END EQU BUF2START-4 ;LONG where shadow buffer ends
BUFLEFT EQU BUF2END-2 ;WORD output left edge
HEIGHT EQU BUFLEFT-2 ;WORD font fRectHeight copy
SRCPTR EQU HEIGHT-4 ;LONG used only in wide character case as temp
DSTPTR EQU SRCPTR-4 ;LONG used only in wide character case as temp
BUFSTART EQU DSTPTR-4 ;LONG \ start of bits buffer
SRCADDR EQU BUFSTART-4 ;LONG >- these 3 grouped: address of font bits
SRCROW EQU SRCADDR-4 ;LONG / rowbytes of font bits
maskStart EQU SRCROW-4 ;LONG \ start of mask buffer
maskAddr EQU maskStart-4 ;LONG >- these 3 grouped: address of mask bits
mSrcRow EQU maskAddr-4 ;LONG / rowbytes of mask bits
FROMRECT EQU mSrcRow-8 ;RECT mapRect parameter
TORECT EQU FROMRECT-8 ;RECT mapRect parameter
PENLOC EQU TORECT-4 ;POINT copy of original pnLoc
SPWIDTH EQU PENLOC-4 ;FIXED POINT width of space
CHARLOC EQU SPWIDTH-4 ;FIXED POINT fractional pen position
HEIGHTAB EQU CHARLOC-4 ;LONG pointer to font height table
WIDTAB EQU HEIGHTAB-4 ;LONG pointer to font offset/width table
LOCTAB EQU WIDTAB-4 ;LONG pointer to font location table
SAVEA5 EQU LOCTAB-4 ;LONG register saved so can be reused
characterExtra EQU SAVEA5-4 ;LONG fixed point extra added to each character
maskBitsPtr EQU characterExtra-4 ;LONG pointer to maskBits, sourcePix, or 0
bkCol EQU maskBitsPtr-4 ;LONG full of the background color
leftBack EQU bkCol-4 ;LONG bkCol masked to the left part of the character
rightBack EQU leftBack-4 ;LONG bkCol masked to the right part of the character
REALBOUNDS EQU rightBack-4 ;LONG USED FOR SHIELDCURSOR
leftOffset EQU REALBOUNDS-8 ;2 LONGs offset used by bit field instructions in charblt
maskSize EQU leftOffset-2 ;WORD size of mask buffer
mBufRow EQU maskSize-2 ;WORD \ these 2 mask buffer row size
maskBlts EQU mBufRow-6 ;3 WORDS / grouped: saved state for mask blit
FAKERGN EQU maskBlts-10 ;RECTANGULAR REGION
FAKEPTR EQU FAKERGN-4 ;LONG, FAKE MASTER POINTER
INFO EQU FAKEPTR-8 ;4 WORDS font info record returned by txMeasure (unused)
NUMER2 EQU INFO-4 ;Point copy of numer for iterative case
DENOM2 EQU NUMER2-4 ;Point copy of denom for iterative case
charsRemain EQU DENOM2-2 ;word remaining characters to draw in iterative case
SRCBITS EQU charsRemain-14 ;bitMap input to shadow stretchBits, bitsToPix
SRCPIX EQU SRCBITS-(PMREC+CTREC+20) ;pixMap input to normal stretchbits
maskBits EQU SRCPIX-14 ;bitMap input to bitsToPix for font mask
DSTPIX EQU maskBits-(PMREC+CTREC+20) ;pixMap destination
FASTFLAG EQU DSTPIX-1 ;BYTE flag set if source ORing to screen is OK
maskFont EQU FASTFLAG-1 ;byte flag set if a maskFont is available + requested
STRETCH EQU maskFont-1 ;BOOLEAN flag set if numerator not equal denominator
HEIGHTFLAG EQU STRETCH-1 ;byte flag set if font has a height table
TOPHT EQU HEIGHTFLAG-2 ;word character top & height from font or clip
MAXMIN EQU TOPHT-2 ;word number of characters in font
MINCH EQU MAXMIN-2 ;word first character in font
bitDepth EQU MINCH-2 ;word \ These two bits per pixel in font
bkCol1 EQU bitDepth-2 ;word / grouped. 1 pixel worth of background color
italicSlop EQU bkCol1-2 ;word extra width due to italic, bold, outline, shadow
kernAdjust EQU italicSlop-2 ;word left kerning due to kerning and italic
penLocHFrac EQU kernAdjust-2 ;word fractional pen position for recursive calls
longCount EQU penLocHFrac-2 ;word loop counter for doMove
charWidth EQU longCount-2 ;word width in pixels of current character blt
stackOffset EQU charWidth-2 ;word 2 if stack was word aligned before link
countCopy EQU stackOffset-2 ;word copy of character count, decremented as drawn
CRSRFLAG EQU countCopy-2 ;WORD
locMode EQU CRSRFLAG-2 ;word copy of text mode, adjusted if arith. + 1 bit
bitShift EQU locMode-2 ;word how far to shift to multiply by bitDepth
orNotOK EQU bitShift-1 ;Boolean true if bit extract/insert must be used instead
notMaskPass EQU orNotOK-1 ;Boolean true if blit is not creating font mask
textCopyMode EQU notMaskPass-1 ;Boolean true if blit must use extract/insert
orMode EQU textCopyMode-1 ;Boolean true if mode is srcOr & forecolor is black
colorSource EQU orMode-1 ;Boolean true if font contains colors (nonblack/white)
saveHilite EQU colorSource-1 ;byte saved hilite flag for iterative state
VARSIZE EQU (((colorSource+1)/4)-1)*4 ;SIZE OF VARIABLES long aligned
ROMRSect equ $1d58a ;ROM RSect code <PB302>
fromROMDrText equ $1a238 ;ROM RSect call return address <PB302>
ROMgoOn equ $1a562 ;ROM normal re-entry point <PB302>
ROMIterate equ $19f7e ;ROM iteration re-entry point <PB302>
ROMGoHome equ $1ab64 ;ROM do nothing re-entry point <PB302>
; _RSECT ;CALC INTERSECTION
;Do rsect then come back to us
comeBack
bne.s continue ;yes, non-empty intersection
goHome JMPROM ROMGoHome ;QUIT IF NO INTERSECTION
continue
MOVE (SP)+,textR2+right(A6) ;restore text right
;
; Set up srcAddr, srcRow, and height
;
LEA 26(A2),A0 ;GET START OF FONT BITMAP
MOVE.L A0,SRCADDR(A6) ;SAVE FOR LATER
MOVEQ #0,D1 ;zero high word
MOVE RASTER(A2),D1 ;GET WORDS PER ROW IN FONT
MOVE bitShift(A6),D0
LSL.L D0,D1 ;scale up font rowWords
ADD.L D1,D1 ;DOUBLE FOR BYTES PER ROW
MOVE.L D1,SRCROW(A6) ;REMEMBER FOR LATER
MOVE FBBDY(A2),HEIGHT(A6) ;SETUP HEIGHT FOR LATER
;
; Test for fast case:
; not stretched, no color mapping, txMode = srcOr, same bits per pixel
; not bold, italic, underlined, outlined or shadowed,
; visRgn and clipRgn both rectangular.
;
TST.W 6(A4) ;TEST BOLD AND ITALIC
BNE NOTFAST ;NOT FAST UNLESS BOTH ZERO
TST.B orMode(A6) ;IS TEXT MODE SRCOR ? (or srcCopy + mask, see above)
BEQ NOTFAST ;NO, NOT FAST
TST.W 10(A4) ;TEST ULTHICK AND SHADOW
BNE NOTFAST ;NOT FAST UNLESS BOTH ZERO
TST.B STRETCH(A6) ;IS TEXT STRETCHED ?
BNE NOTFAST ;YES, NOT FAST
MOVE.L ([CLIPRGN,A3]),A0 ;GET CLIPRGN HANDLE, dereferenced
MOVEQ #10,D0
CMP RGNSIZE(A0),D0 ;IS CLIPRGN RECTANGULAR ?
BNE NOTFAST ;NO, NOT FAST
MOVEQ #1,D0
MOVE bitShift(A6),D1 ;get the depth of the source map
LSL D1,D0 ;turn into 1 … 8
CMP DSTPIX+PIXELSIZE(A6),D0 ;same depth per pixel?
BNE NOTFAST ;=>NOPE
MOVE.L VISRGN(A3),A1 ;GET VISRGN HANDLE
MOVE.L (A1),A0 ;DE-REFERENCE IT
CMP RGNSIZE(A0),D0 ;IS VISRGN RECTANGULAR ?
BEQ.S FAST ;YES, TAKE FAST OPTIMIZATION
;
; All systems go except for VisRgn not rectangular.
; Check if visRgn sect minRect is rectangular.
; IF TrimRect(visRgn,minRect) THEN take the fast way.
;
MOVE.L A1,-(SP) ;PUSH VISRGN
PEA MINRECT(A6) ;PUSH MINRECT
JSR ([$E00+$329*4]) ;_TRIMRECT ;CALL TRIMRECT
BLT.s GOHOME ;quit if intersection empty
BGT NOTFAST ;continue if non-rectangular
;
; Fast case, go directly to screen.
; If text is clipped vertically, then clear heightflag and update TOPHT
;
FAST ST FASTFLAG(A6) ;REMEMBER WE'RE GOING FAST
CLR.B maskFont(A6) ;no need for second mask pass in fast case
CLR.L bkCol(A6) ;zero out back color long
MOVE MINRECT+TOP(A6),D0 ;GET MINRECT.TOP
MOVE MINRECT+BOTTOM(A6),D1 ;GET MINRECT.BOTTOM
SUB TEXTRECT+TOP(A6),D0 ;was top clipped ?
BNE.S VCLIP ;yes, handle clip
CMP TEXTRECT+BOTTOM(A6),D1 ;was bottom clipped ?
BEQ.S VCLIPOK ;no, continue
VCLIP CLR.B HEIGHTFLAG(A6) ;can't use height table
MOVE.B D0,TOPHT(A6) ;use adjusted top
SUB MINRECT+TOP(A6),D1 ;calc clipped height
MOVE.B D1,TOPHT+1(A6) ;replace TOPHT
VCLIPOK MOVE TEXTRECT+TOP(A6),D0 ;GET DST TOP
SUB DSTPIX+BOUNDS+TOP(A6),D0 ;CONVERT TO GLOBAL COORDINATES
MOVE DSTPIX+ROWBYTES(A6),D1 ;GET ROWBYTES
AND #RBMASK,D1 ;CLEAR OFF FLAG BITS
MULS D1,D0 ;MULT BY ROWBYTES
ADD.L DSTPIX+BASEADDR(A6),D0 ;ADD START OF DST BITMAP
MOVE.L D0,BUFSTART(A6) ;SET UP BUFSTART FOR LATER
MOVE D1,BUFROW(A6) ;SET UP BUFROW FOR LATER
MOVE DSTPIX+BOUNDS+LEFT(A6),BUFLEFT(A6) ;REMEMBER BUFLEFT
MOVE.L THEGDEVICE,A0 ;GET CURRENT DEVICE
MOVE.L (A0),A0 ;POINT AT IT
MOVE.L GDPMAP(A0),A0 ;GET ITS PIXMAP
MOVE.L (A0),A0 ;POINT AT IT
MOVE.L BASEADDR(A0),D0 ;GET BASE OF SCREEN
CMP.L DSTPIX+BASEADDR(A6),D0 ;DRAWING TO SCREEN?
SEQ CRSRFLAG(A6) ;IF SO, SET FLAG
bne GETPTRS ;=>NO, so just skip skieldCursor--don't go slow! <PB362>
PEA MINRECT(A6) ;PUSH SHIELD RECT
MOVE.L REALBOUNDS(A6),-(SP) ;PUSH DELTA FOR GLOBAL
JSR ([$E00+$55*4]) ;_SHIELDCURSOR ;HIDE CURSOR IF IT INTERSECTS
;_____________________________________________________________________
;
; <<Begin PB362 BAL>>
BRA GETPTRS
;
; Slow case: Setup for an off-screen buffer.
;
; Calc bufLeft: (LONG-align to avoid shift)
;
NOTFAST SF FASTFLAG(A6) ;NOT GOING DIRECTLY TO SCREEN
MOVE TEXTRECT+LEFT(A6),D0 ;GET TEXTRECT LEFT
SUB DSTPIX+BOUNDS+LEFT(A6),D0 ;CONVERT TO GLOBAL
AND #$FFE0,D0 ;TRUNC TO LONG BOUND
ADD DSTPIX+BOUNDS+LEFT(A6),D0 ;RETURN TO LOCAL COORDS
MOVE D0,BUFLEFT(A6) ;REMEMBER FOR LATER
;
; Calculate buffer size
;
MOVEQ #0,D1 ;clear high word
MOVE TEXTRECT+RIGHT(A6),D1 ;BUFRIGHT := TEXTRECT RIGHT
SUB D0,D1 ;WIDTH:=BUFRIGHT-BUFLEFT
MOVE D1,D2 ;mask depth as well
MOVE bitShift(A6),D4 ;convenient constant
LSL.L D4,D1 ;scale up by pixel size + 1 for mask
LSR.L #5,D1 ;CONVERT DOTS TO LONGS
ADD #2,D1 ;ROUND UP PLUS EXTRA LONG
MOVE HEIGHT(A6),D3 ;GET HEIGHT
MULU D1,D3 ;BUFSIZE:=HEIGHT*BUFROW LONGS
; if the intermediate result is too big, stop before going any further
CMP.L #$1C00,D3 ;is it bigger than 28K? (unit is longs)
BGT.S DoSubDivide ;if so, draw fewer characters at a time
MOVE D3,BUFSIZE(A6) ;SAVE FOR LATER
ADD D1,D3 ;add for stretch srcBuf
LSL #2,D1 ;QUAD BUFROW FOR BYTES
MOVE D1,BUFROW(A6) ;SAVE FOR LATER
MOVE TEXTR2+RIGHT(A6),D5
SUB TEXTR2+LEFT(A6),D5
LSR #5,D5 ;convert to longs
ADDQ #2,D5 ;account for slop
MOVE D5,D0
ADD D0,D3 ;in case clip is nonrectangular
ADD D0,D3 ;in case vis is nonrectangular
LSL D4,D0 ;scale up by source depth
ADD D0,D3 ;add stretch destination buffer size
MULU dstPix+pixelSize(A6),D5 ;size of composite mask
ADD D5,D3 ;include it
;if srcDepth not equal to dstDepth, add stretch dest. buf. again
ADD D5,D3 ;include space for scale buffer
;set up maskSize, maskRow
TST.B maskFont(A6) ;do we need a mask to pass to stretchBits?
BEQ.S @noMask
LSR #5,D2 ;CONVERT DOTS TO LONGS
ADD #2,D2 ;ROUND UP PLUS EXTRA LONG
ADD D2,D1 ;total number of longs
MOVE HEIGHT(A6),D0 ;GET HEIGHT
MULU D2,D0 ;BUFSIZE:=HEIGHT*BUFROW LONGS
MOVE D0,maskSize(A6) ;SAVE FOR LATER
LSL #2,D2 ;QUAD BUFROW FOR BYTES
MOVE D2,mBufRow(A6) ;SAVE FOR LATER
ADD D0,D3 ;add for stack check calculation
ADD D2,D3 ;add for stretch srcMaskBuf
MOVE TEXTR2+RIGHT(A6),D0
SUB TEXTR2+LEFT(A6),D0
LSR #5,D0 ;convert from dots to longs
ADD D0,D3 ;add stretch mask destination buffer size
@noMask
;
; Calculate total stack requirements for off-screen buffers.
;
TST.B 11(A4) ;ARE WE SHADOWING ?
BEQ.S @1 ;NO, CONTINUE
ADD bufSize(A6),D3 ;YES, CALC 2*BUFSIZE
ADD D1,D3 ;add in 4 * source rows for shadow
@1 LSL.L #2,D3 ;CALC TOTAL STACK BYTES NEEDED
; how much slop? size of scale table (256 bytes maximum)
; size of stretch stack frame (750 bytes for parameters, local stack frame, saved regs),
; and about 1K for interrupts.
ADD.L #2048,D3 ;ADD 2 KBYTE SLOP
;
; If stack is too small to allocate buffer(s), then draw half as many characters at a time.
;
_StackAvail ;Get StackAvail IN D0
CMP.L D0,D3 ;IS stackNeeded > stackAvail ?
BLE.S StackAlmost ;NO, CONTINUE
DoSubDivide
MOVE stackOffset(A6),D6 ;2 if stack was not aligned, otherwise, 0
MOVE charCount(A6,D6),D0 ;how many characters to draw
MOVE D0,D7 ;figure half
LSR #1,D7
BNE.S @subDivide ;if more than 1 left, can subdivide problem
SUBQ #1,charsRemain(A6) ;pretend the one character was drawn
BRA GoHome ;if only 1 character, punt
@subDivide
; *** look for space character? Could adjust D7 to coincide with a space if any, making
; *** drawing look better (for italics, kerns)
TST charsRemain(A6) ;if zero, this is the first time through
BNE.S @notFirst
MOVE.B HiliteMode,saveHilite(A6) ;save original in case stretch is called multiple times
MOVE D0,charsRemain(A6) ;initialize partial count drawing location
@notFirst
MOVE.L PENLOC(A6),PNLOC(A3) ;RESTORE PNLOC TO ORIGINAL
TST PORTBITS+ROWBYTES(A3) ; is it a new port?
BPL.S @useOld ; no, no fraction to restore
MOVE PenLocHFrac(A6),pnLocHFrac(A3) ;restore fraction if applicable
@useOld
MOVE D7,charCount(A6,D6) ;reset count to draw
doIterate
MOVE.L grafGlobals(A5),A4 ;set up grafGlobals pointer for getting real width
MOVE.L numer2(A6),numer(A6,D6) ;restore numerator
MOVE.L denom2(A6),denom(A6,D6) ;restore denominator
MOVE.B saveHilite(A6),HiliteMode ;restore hilite bit
JMPROM ROMIterate ;draw first half of string <PB362>
; draw the second half of the string, but drawing no more characters than could be successfully
; drawn by the first half.
secondHalf
MOVEQ #0,D7 ;zero high word
MOVE stackOffset(A6),D6 ;2 if stack was not aligned, otherwise, 0
MOVE charCount(A6,D6),D7 ;number of characters drawn last
MOVE charsRemain(A6),D0 ;how many characters remain?
CMP D0,D7 ;dont try to draw more than worked last
BLE.S @ok
MOVE D0,charCount(A6,D6) ;draw what remains for the second half
@ok
ADD.L D7,textAddr(A6,D6) ;bump source address by half already drawn
BRA.S doIterate
; ————————————————————————————————————————————————————————————————————————————————————————————
;
; Allocate and clear an off-screen buffer
;
; If the source font is only 1 bit deep, clear the screen to white. Also, if the transfer
; mode is xor, bic, or, clear the screen to white. If an arithmetic mode or copy and
; source is multibits deep, assume depth of source font is equal to destination depth.
; Also assume that background of buffer must be colored the same as the port background color.
StackAlmost
MOVEQ #0,D0
TST bitShift(A6) ;is source 1 bit?
BEQ.S @whiteBackCol
CMP #srcXor,locMode(A6) ;srcXor?
BEQ.S @whiteBackCol ;even if font contains colors, leave background white
TST.B colorSource(A6) ;font contains color?
BNE.S @useBackCol ;if so, must color the buffer
CMP #$32,locMode(A6) ;hilite?
BEQ.S @whiteBackCol ;leave background white if so
BTST #5,locMode+1(A6) ;arithmetic?
BEQ.S @whiteBackCol ;if copy, or leave background white
@useBackCol
SUBQ #6,SP ;allocate VAR RGBColor
MOVE.L SP,-(SP) ;point to VAR RGBColor
_GetBackColor ;ask for the background color
CLR.L -(SP) ;make room for function result
PEA 4(SP) ;point to VAR RGBColor
_Color2Index
MOVEQ #0,D0
MOVEQ #32,D1 ;
MOVE bitDepth(A6),D2 ;get destination bits per pixel
@nxtPixel
ASL.L D2,D0
OR 2(SP),D0 ;or in result of color2Index
SUB D2,D1
BGT.S @nxtPixel
ADD #10,SP ;strip RGBColor and long result
@whiteBackCol
MOVE.L D0,bkCol(A6) ;save for comparing with background, later
STACKOK MOVE bufSize(A6),D3
SUBQ #1,D3 ;INIT DBRA LOOP COUNT
MOVE.L D0,-(SP) ;PAD BUFFER WITH AN EXTRA ZERO
MOVE.L SP,BUFEND(A6) ;REMEMBER WHERE BUFFER ENDS
CLRLOOP MOVE.L D0,-(SP)
DBRA D3,CLRLOOP ;ALLOCATE AND CLEAR BUFFER
MOVE.L SP,BUFSTART(A6) ;REMEMBER START OF BUFFER
MOVE.L D0,-(SP) ;PAD BUFFER WITH AN EXTRA ZERO
TST.B maskFont(A6)
BEQ.S @noMask
MOVE maskSize(A6),D3
SUBQ #1,D3
CLR.L -(SP)
@clrMask
CLR.L -(SP)
DBRA D3,@clrMask
MOVE.L SP,maskStart(A6)
@noMask
CLR.L -(SP)
;
; Get pointers to location table, width table, and height table in font
;
GETPTRS LEA 26(A2),A0 ;GET START OF FONT BITMAP
MOVEQ #0,D0 ;zero high word
MOVE FBBDY(A2),D0 ;GET HEIGHT OF FONT BITMAP
MULU.L SRCROW(A6),D0 ;CALC TOTAL SIZE OF STRIKE
ADD.L D0,A0 ;A1 := START OF LOC TABLE
MOVE.L A0,LOCTAB(A6) ;SAVE FOR LATER
; *** could test bitShift first and only check fNDescent if bitDepth > 1 …
MOVE.W fNDescent(A2),D0 ;possibly the high word of owTLoc
SWAP D0 ;put it in the high word
BPL.S @notNegative
MOVEQ #0,D0 ;old fonts have negative of ascent here
@notNegative
MOVE LENGTH(A2),D0 ;HOW MANY WORDS IN STRIKE BODY
LEA 16(A2,D0.L*2),A1 ;GET START OF WIDTH TABLE
MOVE.L A1,WIDTAB(A6) ;SAVE FOR LATER
MOVE MAXCHAR(A2),D0 ;GET MAXCHAR
MOVE MINCHAR(A2),D1 ;GET MINCHAR
MOVE D1,MINCH(A6) ;STASH MINCHAR FOR LATER
SUB D1,D0 ;CALC MAXCHAR-MINCHAR
MOVE D0,MAXMIN(A6) ;SAVE FOR LATER
ADD #3,D0 ;CALC MAXMIN+3
BTST #1,1(A2) ;DOES FONT HAVE WIDTH TABLE ?
BEQ.S NOWID ;NO, CONTINUE
ADD D0,D0 ;SKIP WIDTH TABLE
NOWID LEA 0(A1,D0*2),A0 ;POINT TO HEIGHT TABLE
MOVE.L A0,HEIGHTAB(A6) ;SAVE FOR LATER
;
; Set up space width
;
MOVE.L widthTabHandle,A0 ;point to width table
MOVE.L (A0),A0
MOVE.L 128(A0),SPWIDTH(A6) ;get width of the space char
;
; Setup misc stuff in registers for speed
;
MOVE BUFLEFT(A6),D1 ;GET BUFLEFT
MOVE PENLOC+H(A6),D0 ;GET PEN LOCATION
ADD kernAdjust(A6),D0 ;ADJUST FOR KERNING
SUB D1,D0 ;MAKE CHARLOC RELATIVE TO BUFLEFT
MOVE.W D0,CHARLOC(A6) ;INIT INT PART OF CHARLOC
TST PORTBITS+ROWBYTES(A3) ;is it a new port?
BPL.S @useOld ;no, set fraction to 1/2
;
; The following line is the only one source line changed in this patch <PB362> BAL
;
MOVE penLocHFrac(A6),CHARLOC+2(A6) ;set up fractional part <PB362> BAL
BRA.S @goOn
@useOld
MOVE #$8000,CHARLOC+2(A6)
@goOn
JMPROM ROMgoOn ;jmp back to ROM
;
; <<End PB362 BAL>>
;_____________________________________________________________________
ENDPROC
;___________________________________________________________________________
; PB217 CXXX 22Jul87 BAL RSECT
;
;
; 2nd Patch to RSect to fix bug in DrawLine
;
; DrawLine fast case is taken for black or white patterned single
; pixel horizontal or vertical lines. The test for black or white patterns
; in the ROM DrawLine is incompatible with new patterns. This patch
; allows fastline to be used in CGrafPorts.
;
;------------------------------------------------------------------
MyRSect PROC EXPORT
IMPORT myTextFix
;------------------------------------------------
;
; A6 OFFSETS OF DrawLine PARAMETERS AFTER LINK:
;
PARAMSIZE EQU 8 ;SIZE OF PARAMETERS
P1 EQU PARAMSIZE+8-4 ;POINT
P2 EQU P1-4 ;POINT
;-------------------------------------------------
;
; A6 OFFSETS OF LOCAL VARIABLES AFTER LINK:
;
; STACK FRAME VARS USED BY SEEKMASK (CALLED BY STRETCHBITS, RGNBLT, DRAWARC, DRAWLINE)
;
RECTFLAG EQU -2 ;WORD
VERT EQU RECTFLAG-2 ;WORD
RGNBUFFER EQU VERT-4 ;LONG
BUFLEFT EQU RGNBUFFER-2 ;WORD
BUFSIZE EQU BUFLEFT-2 ;WORD
EXRTN EQU BUFSIZE-4 ;LONG
SEEKMASK EQU EXRTN-4 ;LONG
DSTMASKBUF EQU SEEKMASK-4 ;LONG
DSTMASKALIGN EQU DSTMASKBUF-4 ;LONG
STATEA EQU DSTMASKALIGN-RGNREC ;RGN STATE RECORD
STATEB EQU STATEA-RGNREC ;RGN STATE RECORD
STATEC EQU STATEB-RGNREC ;RGN STATE RECORD
; STACK FRAME VARS USED BY PATEXPAND
; (CALLED BY STRETCHBITS, RGNBLT, BITBLT, DRAWARC, DRAWLINE)
EXPAT EQU STATEC-4 ;LONG
PATVMASK EQU EXPAT-2 ;WORD (must follow expat)
PATHMASK EQU PATVMASK-2 ;WORD (must follow PATVMASK)
PATROW EQU PATHMASK-2 ;WORD (must follow PATHMASK)
PATHPOS EQU PATROW-2 ;WORD
PATVPOS EQU PATHPOS-2 ;WORD
LOCMODE EQU PATVPOS-2 ;WORD
PIXSRC EQU LOCMODE-1 ;BYTE YES
NEWPATT EQU LOCMODE-2 ;BYTE YES
LOCPAT EQU NEWPATT-4 ;LONG YES
FCOLOR EQU LOCPAT-4 ;LONG YES
BCOLOR EQU FCOLOR-4 ;LONG
DSTPIX EQU BCOLOR-(PMREC+CTREC+20) ;PIXMAP
DSTSHIFT EQU DSTPIX-2 ;WORD
; these shared stack frame vars are set up and used by the arithmetic drawing modes
weight EQU DSTSHIFT-6 ;RGB weight for averaging
pin EQU weight ;RGB used by max, min
notWeight EQU weight-6 ;RGB complement of weight (for average)
multiColor EQU notWeight-2 ;byte set if source contains nonblack/white colors
colorTable EQU multiColor-4 ;long pointer to color table
invColor EQU colorTable-4 ;long pointer to inverse color table
invSize EQU invColor-2 ;word resolution of inverse color table
rtShift EQU invSize-2 ;Word used by average how far to shift
transColor EQU rtShift-4 ;long copy of backcolor for transparent
hilitColor EQU transColor-4 ;long hilite color pixels
; STACK FRAME VARS USED ONLY BY DRAWLINE
LINERECT EQU hilitColor-8 ;RECT
MINRECT EQU LINERECT-8 ;RECT
SAVESTK EQU MINRECT-4 ;LONG
MODECASE EQU SAVESTK-4 ;LONG
LFTEDGE EQU MODECASE-4 ;LONG, FIXED POINT
RGHTEDGE EQU LFTEDGE-4 ;LONG, FIXED POINT
SLOPE EQU RGHTEDGE-4 ;LONG, FIXED POINT
DSTLEFT EQU SLOPE-4 ;LONG
SAVEA5 EQU DSTLEFT-4 ;LONG
PORT EQU SAVEA5-4 ;LONG
FASTFLAG EQU PORT-2 ;BYTE
BIGRGN EQU FASTFLAG-4 ;LONG, RgnHandle
DSTROW EQU BIGRGN-2 ;WORD
CRSRFLAG EQU DSTROW-2 ;WORD
REALBOUNDS EQU CRSRFLAG-4 ;LONG
VARSIZE EQU REALBOUNDS ;SIZE OF LOCAL VARIABLES
DrawLineRSect equ $1c222 ; <PB302>
ROMRSect equ $1d58a ; <PB302>
ROMGoHome equ $1c62e ; <PB302>
ROMDone equ $1c61e ; <PB302>
ROMFlagOK equ $1c2b8 ; <PB302>
ROMoldPat equ $1c284 ; <PB302>
fromROMDrText equ $1a238 ;ROM RSect call return address
;-----------------------------------------------------------------------
;
; CALC MINRECT, THE INTERSECTION OF LINERECT, BITMAP BOUNDS,
; CLIPRGN BBOX, AND VISRGN BBOX. QUIT IF NO INTERSECTION.
;
; PEA LINERECT(A6) ;PUSH LINE RECT
; PEA DSTPIX+BOUNDS(A6) ;PUSH PIXMAP BOUNDS
; PEA RGNBBOX(A2) ;PUSH CLIPRGN BBOX
; PEA RGNBBOX(A3) ;PUSH VISRGN BBOX
; MOVE #4,-(SP) ;PUSH NRECTS=4
; PEA MINRECT(A6) ;PUSH DST ADDR
; _RSECT ;CALC INTERSECTION
CMPRA DrawLineRsect,(sp) ;was RSect called from drawline?
beq.s fixROM ;yes, go patch the code after the call
CMPRA fromROMDrText,(sp) ;was RSect called from drText?
beq.s fixText ;yes, go patch the code after the call
JMPROM ROMRSect ;no, continue with RSect
fixROM lea myRet,a0 ;trash a0
move.l a0,(sp) ;force return to us
JMPROM ROMRSect
fixText lea myTextFix,a0 ;trash a0
move.l a0,(sp) ;force return to us
JMPROM ROMRSect
myRet bne.s continue ;continue with patch if intersect not empty
JMPROM ROMGoHome ;QUIT IF NO INTERSECT
continue
;-----------------------------------------------------------
;
; HIDE CURSOR IF CURSOR INTERSECTS MINRECT AND DST IS SCREEN.
; (A5 must contain global ptr)
;
MOVE.L SAVEA5(A6),A5 ;GET GLOBAL PTR
MOVE.L THEGDEVICE,A0 ;GET CURRENT DEVICE
MOVE.L (A0),A0 ;POINT AT IT
MOVE.L GDPMAP(A0),A0 ;GET ITS PIXMAP
MOVE.L (A0),A0 ;POINT AT IT
MOVE.L BASEADDR(A0),D0 ;GET BASE OF SCREEN
CMP.L DSTPIX+BASEADDR(A6),D0 ;DRAWING TO SCREEN?
SEQ CRSRFLAG(A6) ;IF SO, SET FLAG
BNE.S NOTSCRN ;=>NO
PEA MINRECT(A6) ;PUSH SHIELDRECT PARAMETER
MOVE.L REALBOUNDS(A6),-(SP) ;PUSH DELTA FOR GLOBAL
_SHIELDCURSOR ;HIDE CURSOR IF IT INTERSECTS
NOTSCRN MOVE.L PORT(A6),A5 ;GET BACK THEPORT
;-----------------------------------------------------------
;
; CHECK FOR BOTH VISRGN AND CLIPRGN RECTANGULAR
;
CLR.B FASTFLAG(A6) ;FASTFLAG := FALSE
CMP #10,RGNSIZE(A2) ;IS CLIPRGN RECTANGULAR ?
BNE.S FLAGOK ;NO, CONTINUE
CMP #10,RGNSIZE(A3) ;IS VISRGN RECTANGULAR ?
BEQ.S CKPAT ;YES, CONTINUE
;-----------------------------------------------------------
;
; If only visRgn is non-rectangular, then check if
; its intersection with minrect would be rectangular.
; IF TrimRect(visRgn,minRect) then treat as rectangular.
;
MOVE.L visRgn(A5),-(SP) ;push rgnHandle
PEA minRect(A6) ;push addr of minRect
_TrimRect ;call trimRect
Bge.s @1
JMPROM ROMDone ;quit if intersection empty
@1 BGT.S FLAGOK ;continue if non-rectangular
;-----------------------------------------------------------
;
; CHECK FOR BLACK OR WHITE PATTERN
;
CKPAT BTST #5,LocMode+1(A6) ;AN ARITHMETIC MODE?
BNE.S FLAGOK ;SKIP FAST CASE IF SO
MOVE.L LOCPAT(A6),A0 ;POINT TO PATTERN/PIXPAT HANDLE
;patched code begins here:
tst.b NewPatt(A6) ;is it a new pattern?
Beq.s @oldPat ;=>yes, skip pixpat fields
move.l (a0),a0 ;get the pixpat handle
move.l (a0),a0 ;get the pixpat pointer
TST PATTYPE(A0) ;is it an old-style pattern?
BNE.S FLAGOK ;=>no, skip fast case
move.l patData(a0),a0 ;get handle to pattern data
move.l (a0),a0 ;get pattern ptr
@oldPat JMPROM ROMoldPat ;return to ROM code w/ pattern ptr in a0
;MOVE.L (A0)+,D0 ;GET 1ST HALF OF PATTERN
;CMP.L (A0)+,D0 ;IS IT SAME AS 2ND HALF ?
;BNE.S FLAGOK ;NO, CONTINUE
;NOT.L D0 ;IS PATTERN BLACK ?
;BEQ.S YESFLAG ;YES, WE MADE IT
;NOT.L D0 ;IS PATTERN WHITE ?
;BNE.S FLAGOK ;NO, CONTINUE
;EOR #4,LOCMODE(A6) ;YES, ALTER MODE AS IF BLACK
;YESFLAG ST FASTFLAG(A6) ;RECT CLIPPED AND BLACK
FlagOK JMPROM ROMFlagOK
ENDPROC
;----------------------------------------------------------------------------------------
; PB231 28Jul87 rwh/rdc DisPtchTsk DisPtchTsk
; Patch for dispatching of deferred tasks
; PB573 22Sep88 jwk DisPtchTsk
; Cleaned up using ggd's technique.
; <8.3> 28Nov89 GGD Replaced with the code that shipped in the IIci ROM.
; Fixes problem in earlier version which could cause deferred
; tasks to be delayed until the next interrupt occurs if a new
; task was queued while the last task was running. (It needs to
; check to see if the queue is empty AFTER running the task, with
; interrupts masked during the check)
; <14> 02Feb90 GGD Re-Enabled interrupts upon exiting this routine to fix QuickMail <14>
; servers (for now at least), because they call through jDisptch at <14>
; application level and wind up with all interrupts being masked, <14>
; and this code expects to only be called from then end of an interrupt <14>
; handler, which will restore the interrupt level via an RTE. <14>
;
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 28Jul87 PB231 (DisPtchTsk) (DisPtchTsk)
;
; Patch for dispatching of deferred tasks
; The fix is to first dequeue the request and then execute it rather than vice versa.
; This should fix a bug related to requeueing of the same task found by the AppleShare crew
; Note that regs D0-D3, A0-A3 are previously saved by the interrupt handlers
; NOT IN A/UX
NewDisPtch PROC EXPORT
ROMDequeue EQU $4080602A
vDisptch BTST.B #INVBL,QFLAGS+VBLQUEUE ; doing VBL tasks? **begin** <8.3>
BNE.S @Exit ; if so, keep deferring
BSET.B #InDTQ,DTQFlags ; already in dispatcher?
BEQ.S @DspStart ; check the queue if not
@Exit RTS ; otherwise exit
@DspLoop MOVEA.L D0,A0 ; else setup ptr for use
LEA DTQueue,A1 ; get ptr to queue
JSR ROMDeQueue ; dequeue task to be executed
MOVEA.L DTAddr(A0),A2 ; get ptr to first task
MOVEA.L DTParm(A0),A1 ; get optional parameter
ANDI.W #$F8FF,SR ; enable all ints
JSR (A2) ; and go do task
@DspStart ORI.W #HiIntMask,SR ; disable all ints
MOVE.L DTskQHdr,D0 ; get queue head
BNE.S @DspLoop ; loop if tasks exist
BCLR.B #InDTQ,DTQFlags ; clear indicator
ANDI.W #$F8FF,SR ; enable all ints (to fix QuickMail) <14>
RTS ; and exit **end** <8.3>
ENDPROC
;----------------------------------------------------------------------------------------
; PB232 04aug87 bbm WriteXPRam WriteXPRam ; OS trap $52
; Patch to check validity of parameters to WriteXPRam
;
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 04aug87 PB232 (WriteXPRam) (WriteXPRam)
;
; Patch to check validity of parameters to WriteXPRam
; NOT IN A/UX
NewWriteXPRam PROC EXPORT
ROMWriteXPRam EQU $4080DD82
move.l d1,-(sp) ; save working regs.
move.l d0,d1 ; get copy of input parameters
swap d1 ;
add.w d0,d1 ; check if addressing past end of chip.
bcs.s @errexit ; …could be carry if there is a lot of garbage in high bytes.
cmp.w #$0100,D1 ; …addressing past end means >= #$100.
bcc.s @errexit ; …do unsigned compare.
move.l (sp)+,d1 ; restore regs.
jmp ROMWriteXPRam ; go to real trap
@errexit
move.l (sp)+,d1 ; restore regs.
moveq #-1,d0 ; signal error
rts ; and return
ENDPROC
;----------------------------------------------------------------------------------------
; PB238 19aug87 DAF Patch Open to check driver version numbers when opening slot devices
; PB268 10Sep87 DAF Detached DRVR resource opened in PB238ß
;
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 19aug87 PB238 (Open) (Open)
;AppleSystemPatch PatchIIROM.a 10Sep87 PB268 (Open) (Open)
;
; This patch corrects Open so that the latest version of a driver is open whether it is
; in the slot card, or in the system file. It is in support of video driver overrides
; but acts correctly for all slot devices. It could be much smaller, but the Juggler
; team doesn't patch Open at the low-level, so doing it this way saves having two versions.
; I neglected to detach the DRVR resource I loaded, and switch launching was killing the system.
; This patch corrects that problem.
;
; NOT IN A/UX <PB302>
;______________________________________________________________________
MyOpen PROC EXPORT
ROMDetRefNum EQU $40806902
NonSlotDrvr EQU $4080696E
IsSlotDrvr EQU $408067C2
SetUpspBlk EQU $408067EE
OldDrvr EQU $40806966
DrvrBad EQU $40806956
ToFSOpen EQU $40806830
MOVEM.L D3-D5/A2-A4,-(SP) ; observe pascal regsave conventions <C133/29Aug86>
MOVE.L A0,D5 ; save parameter block pointer
MOVE.W D1,IOTrap(A0) ; and D1
MOVE.W IOFileType(A0), D2 ; save for desk acc check
MOVE.L IOFileName(A0), A0 ; point A0 to input filename for search of installed drivers
MOVEQ #0,D1 ; clear high bytes
MOVE.B (A0)+,D1 ; IOFileName length
CMP.B #$40,D2 ; is it from OpenDeskAcc?? <01Nov85>
BNE.S @100
JMP NonSlotDrvr
@100
CMP.B #'.',(A0) ; does name start with a period?
BEQ.S @150 ; <PB238/DAF>
JMP ToFSOpen ; <PB238/DAF>
;+++ BNE.S ToFSOpen ; must be for the file system if not a
; deskmgr call or driver name is not prefixed with period
@150
JSR IsSlotDrvr ; is this a slot device? <C600>
BEQ.S @200
JMP NonSlotDrvr ; branch if not. <C600>
@200
; ---------+++++++++++ Begin Slot Driver +++++++++++--------- <C133/29Aug86>
WITH spBlock, seBlock
; Initialize the SDM parameter block
SlotDrvr SUB.L #spBlockSize,SP ; Allocate parameter block for slot manager
MOVE.L SP,A4 ; Save pointer to spBlock.
JSR SetUpspBlk ; Set up some of the SDM parameters. <C600>
; First search for the driver among those already installed . . .
MOVE.W UnitNtryCnt, D2 ; number of units to check
SUB.W #BgnSlotUnit,D2 ; adjust for # of slot unit entries.
MOVEQ #BgnSlotRef,D4 ; init refnum index
MOVE.L UTableBase, A3 ; get address of the unit I/O table
MOVEQ #BgnSlotUnit,D0 ; adjust to beginning of slot unit entries.
LSL.L #2,D0
ADD.L D0,A3 ; A3 <- ptr to unit table, beginning at slot DCE's.
; REPEAT
@Repeat MOVE.L (A3)+,D0 ; get next Device Control Entry handle
BEQ.S @Until ; branch if no entry installed
MOVE.L D0,A2 ; prepare to de-reference it.
MOVE.L (A2),D0 ; de-reference it.
BNE.S @10 ; branch if ok <C750>
CLR.L -(A3) ; Clear the bad UT entry. <C750>
BRA.S @Repeat ; Continue at top of loop <C750>
@10 MOVE.L D0,A1 ; A1 <- ptr to DCE <C750>
MOVE.B dCtlSlot(A1),D0 ; do the slot numbers match?
CMP.B spSlot(A4),D0
BNE.S @Until ; if not then continue search.
MOVE.B dCtlSlotId(A1),D0 ; do the sResource Id's match?
CMP.B spId(A4),D0
BNE.S @Until ; if not then continue search. <C523>
MOVE.B dCtlExtDev(A1),D0 ; do the Device Id's match? <C523>
CMP.B spExtDev(A4),D0 ; <C523><C537>
BEQ.S DCEFound ; if yes then DCE is found. <C523>
@Until SUBQ #1,D4 ; bump refnum index
SUBQ.W #1,D2 ; next unit table entry
BGT.S @Repeat ; continue searching.
; UNTIL (proper DCE is found) OR (unit table entries are exhausted)
BRA.S LookInRsrc ; not installed, begin looking for driver in resources.
; DCE was among the installed slot drivers, but is the driver still installed?
DCEFound MOVE.L dctlDriver(A1),D0 ; D0 <- handle to the driver
BEQ.S BadDCE ; if driver handle is nil then there is no driver.
MOVE.L D0,A1
MOVE.L (A1),D0 ; D0 <- ptr to the driver
BEQ.S @300 ;
JMP OldDrvr ; if driver ptr is not nil then driver is already here, goto DrvrLock.
@300
BadDCE MOVE.L A2,A0 ; if no driver, then purge the DCE, and reload and install the driver.
_DisposPtr ; dispose of DCE
MOVE.L #0,-(A3) ; clear unit table entry
; It wasn't among the installed slot drivers, so check resources . . .
LookInRsrc SUBQ #4,SP ; make room for result
MOVE.L #'DRVR',-(SP) ; push resource class DRVR
MOVE.L spIOFileName(A4),-(SP) ; push name pointer
MOVE.W #MapTrue,ROMMapInsert ; in case it's in sys ROM <C632/14Jan87> DAF
_GetNamedResource ; search resource files first (blows A0, D1??)
MOVE.L (SP)+,D3 ; did it find one? D3 <- handle to driver.
; get the slot driver too... ; <PB238/DAF>
LookInSlot
MOVE.L A4,A0 ; set A0 for use by the slot manager.
_sGetDriver ; get the slot driver
BEQ.S @1 ; continue if no error
TST.L D3 ; was there a resource drvr? <PB238/DAF>
BNE.S DetRefNum ;
JMP DrvrBad
@1 MOVE.L spResult(A0),A3 ; get the handle to the driver <PB238/DAF>
MOVE.L (A3),A1 ; get the pointer to the driver <PB238/DAF>
CLR.L D0 ; for upcoming add <PB238/DAF>
MOVE.B drvrName(A1),D0 ; get the driver name length <PB238/DAF>
ADDQ #2,D0 ; Adjust offset to version field <PB238/DAF>
BCLR #0,D0 ; Adjust to word alignment <PB238/DAF>
MOVE.W drvrName(A1,D0.W),D0 ; Get the sDriver version number <PB238/DAF>
;
; compare DRVR resource version with sDrvr version, being careful to test if the
; drivers were really present. Iff the DRVR version is greater, use it, else
; use the slot drvr, or finally, no driver available, return error
;
TST.L D3 ; is there a resource driver? <PB238/DAF>
BEQ.S @UseSlot ; if no system driver, use sDrvr <PB238/DAF>
MOVE.L D3,A0 ; get handle in an A-reg <PB238/DAF>
MOVE.L (A0),A0 ; get pointer <PB238/DAF>
CLR.L D2 ; for upcoming add <PB238/DAF>
MOVE.B drvrName(A0),D2 ; get the driver name length <PB238/DAF>
ADDQ #2,D2 ; Adjust offset to version field. <PB238/DAF>
BCLR #0,D2 ; Adjust alignment. <PB238/DAF>
CMP.W drvrName(A0,D2.W),D0 ; Compare versions with sDrvr <PB238/DAF>
BGE.S @UseSlot ; if sDrvr ≥ drvr, then use sDrvr <PB238/DAF>
MOVE.L A3,A0 ; get rid of slot driver <PB238/DAF>
_DisposHandle ;
MOVE.L D3,-(SP) ; we need to detach the resource! <PB268/DAF>
_DetachResource ; <PB268/DAF>
BRA.S DetRefNum
@UseSlot
MOVE.L D3,-(SP) ; push the resource handle <PB238/DAF>
_ReleaseResource ; we're using the sDrvr, so dump the system drvr <PB238/DAF>
MOVE.L A3,D3 ; slotDrvr handl in A3 <PB238/DAF>
DetRefNum
JMP ROMDetRefNum ; and back to the ROM
ENDPROC
;____________________________________________________________________________________
; PP235 FClosePatch patch:
;
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 19Aug87 PP235 (FClose) (FClose)
;
; This patch fixes a problem in FClose which results in the catalog and extents file
; BTCB's not being released for an Eject call. The branch following a test for a system
; CNID was reversed.
;
; Patched using the "FClose" vector.
;
; The corresponding source code change for this patch was made to TFSRFN2.a in
; the "FClose" routine.
;
; NOT IN A/UX <PB302>
;____________________________________________________________________________________
RomMFSClose EQU $4080A860 ; MFS Close code
FClose3 EQU $4080A71E ; @3 in ROM FClose
FCloseCont EQU $4080A708 ; MOVE after inverted branch instruction "BLS.S @3"
FClosePatch proc
MOVE.L (SP)+,-(A6) ; save caller's addr <01Oct85>
MOVEM.L A0-A5/D1-D3,-(A6) ; Store scratch registers <28Oct85>
CMPI.W #Tsigword,VCBSigWord(A2) ; is sigword that of TFS? <01Oct85>
BNE.S @2 ; no, must be MFS
TST.L FCBBTCBPtr(A1,D1) ; BTCB associated with this open file?
BEQ.S @3 ; No - just an ordinary file
CMPI.L #NxFreeFN,FCBFlNm(A1,D1) ; a system file? <21May86>
BCC.S @3 ; no, some other BTree file <12Aug87>
JMP FCloseCont
@2 JMP RomMFSClose
@3 JMP FClose3
endproc ; *** End of FClose patch ***
;____________________________________________________________________________________
; PB236 NMI Handler patch
;
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 24Aug87 PB236 (GenExcps) (GenExcps)
;AppleSystemPatch PatchIIROM.a 26Aug87 PB251 (GenExcps) (GenExcps)
;
; This code patches the NMI handler routine so that it passes correct error code to SysError
; routine. This is needed by the new MacsBug debugger to be released with MPW 2.1.
;
; NOT IN A/UX <PB302>
;____________________________________________________________________________________
NewNMIExcp PROC EXPORT
ROMExcp EQU $40802112 ; ROM entry point for interrupt exceptions w/
; debugger installed
ROMExcp2 EQU $4080211E ; ROM entry point for interrupt exceptions w/o <PB251>
; debugger installed
BSET #7,NMIFlag ; use high bit of NMI flag as indicator
BEQ.S @1 ; process first interrupt
RTE ; else just ignore
@1 TST.L MacJmp ; any debugger installed? <PB251>
BEQ.S @2 ; no, take exit for MicroBug <PB251> <PB251>
JMP ROMExcp ; go process it, sets D0=13 for MacsBug
@2 JMP ROMExcp2 ; go process it, sets D0=$13 for MicroBug <PB251>
ENDPROC
;____________________________________________________________________________________
; PMAB241 BadTrap Handler patch
;
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 24Aug87 PMAB241 (BadTrap) (BadTrap)
;
; This patch is to salvage D0 reg for MacsBug on Debugger traps which use the ROM BadTrap routine.
; Fix is to save regs prior to using D0 reg for error code.
;
; NOT IN A/UX <PB302>
;____________________________________________________________________________________
NewBadTrap PROC EXPORT
ROMSysErr3 EQU $40802126 ; ROM entry point in SysErr after save of regs
MOVEM.L D0-D7/A0-A7,SEVars ; save all regs for debugger
MOVEQ #12,D0 ; signal bad trap error
JMP ROMSyserr3 ; and go to ROM, don't resave regs
ENDPROC
;____________________________________________________________________________________
; PB534 SETCCURSOR Patch
; by Bruce & Dave
;
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 13Sep87 PB270 (SetCCursor) (SetCCursor)
;
; Patch SetCCursor to first lock the ccursor handle, SetState on return.
;____________________________________________________________________________________
MySETCCURSOR PROC EXPORT
ROMSetCCursor equ $1d734 ;SetCCursor entry point in ROM
move.l 4(sp),a0 ;get ccursor handle
_HGetState ;handle already in A0
Move.B D0, -(SP) ;save state on the stack
_HLock ;and lock it down for the call
Move.L a0, -(SP) ;copy crsr handle
JSRROM ROMSetCCursor ;jump into the rom
Move.L 6(SP), A0 ;get crsr handle
Move.B (SP)+, D0 ;restore pic handle state
_HSetState
rtd #4 ;return to sender
;____________________________________________________________________________________
; PB279 Picture Recording patches
;
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 18Sep87 PB279 (StdRgn,StdPoly) (StdRgn,StdPoly)
;
; In MacII PICT2's, opcode is word rather than byte sized. Previously existing code in
; these std routines took advantage of the old byte-sizing for opcode generation. As
; a result, it is possible to generate bogus word opcodes based on whatever happened
; to be in the registers at the time of execution. This patch clears the hi byte of
; these register halves so the opcodes will be OK. The StdPoly patch is patched elsewhere
; with another StdPoly patch.
;____________________________________________________________________________________
StdRgn PROC EXPORT
ROMStdRgn EQU $236B4 ; entry into StdRgn in ROM <PB302>
LINK A6,#0 ;NO LOCALS
MOVEM.L D6-D7/A2-A4,-(SP) ;SAVE REGS
MOVEQ #0,D7 ; clear the loword of the register <PB279/DAF>
JMPROM ROMStdRgn ; <PB302>
;____________________________________________________________________________________
; PB292 PatHandle Verification Patches
;
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 30Sep87 PB292 (DisposPixPat,DisposCCursor) (DisposPixPat,DisposCCursor)
;
; When you throw away a pixpat or cursor, verify that the object was not thrown away
; or purged.
;
; When you close a cGrafPort, verify that all pixPat handles are not NIL before
; disposing. This is particularily critical for FillPixPat, since it is a handle
; provided to FillCSomething, and may have been independently disposed.
;
;____________________________________________________________________________________
FixDisposPixPat PROC EXPORT
FixDisposCCursor PROC EXPORT
ROMDispPPat EQU $1EEB2 ; re-enter the ROM code here <PB302>
MOVE.L 4(SP),D0 ; get the pixPat handle
BEQ.S goBack ; if NIL, then do nothing
MOVE.L D0,A1 ; move to A-reg
MOVE.L (A1),D0 ; if purged, then do nothing
BEQ.S goBack ;
MOVE.L D0,A1 ; move to A-reg
JMPROM ROMDispPPat ; and continue in the ROM
GoBack RTD #4 ; clean stack and return
FixCloseCPort PROC EXPORT
FixClosePort PROC EXPORT
DelPortList EQU $1E8AA ; <PB302>
ROMNxtPat EQU $1EA34 ; <PB302>
MOVE.L 4(SP),-(SP) ;PUSH GRAFPTR
JSRROM DelPortList ;DELETE PORT FROM PORTLIST <PB302>
MOVE.L 4(SP),A0 ;GET PORT
MOVE.L CLIPRGN(A0),A0 ;GET CLIPRGN HANDLE
_DisposHandle ;DISCARD IT
MOVE.L 4(SP),A0 ;GET PORT
MOVE.L VISRGN(A0),A0 ;GET VISRGN HANDLE
_DisposHandle ;DISCARD IT
MOVE.L 4(SP),A0 ;GET PORT
TST PortBits+RowBytes(A0) ;IS IT A NEW PORT?
BPL.S DONE ;=>NO, STRIP PARAMS AND RETURN
;-------------------------------------------
;
; DISPOSE OF OLD COLOR PATTERNS, BUT NOT NEW
;
MOVEQ #-1,D0 ; init loop counter <PB292/30Sep87> DAF
MOVE.L bkPixPat(A0),D1 ; get handle <PB292/30Sep87> DAF
BSR.S SetPPat ; if NIL, get rid of it, else push <PB292/30Sep87> DAF
MOVE.L pnPixPat(A0),D1 ; get handle <PB292/30Sep87> DAF
BSR.S SetPPat ; if NIL, get rid of it, else push <PB292/30Sep87> DAF
MOVE.L fillPixPat(A0),D1 ; get handle <PB292/30Sep87> DAF
BSR.S SetPPat ; if NIL, get rid of it, else push <PB292/30Sep87> DAF
JMPROM ROMNxtPat ; and back to ROM <PB292/30Sep87> DAF <PB302>
SetPPat MOVE.L (SP)+,A1 ; get return address <PB292/30Sep87> DAF
BEQ.S NILPPat ; if NIL, don't dispose it <PB292/30Sep87> DAF
MOVE.L D1,-(SP) ; push it <PB292/30Sep87> DAF
ADDQ #1,D0 ; and increment counter <PB292/30Sep87> DAF
NILPPat JMP (A1) ; return <PB292/30Sep87> DAF
Done RTD #4 ;
ENDPROC
;____________________________________________________________________________________
; PMAB301 ATP delayed duplicate response bug patch
;
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 16Nov87 PMAB301 SendRequest SendRequest
;
; If a delayed duplicate response came in to ATP it could overwrite a valid response
; before it was thrown out due to a bad TID. Patch SendRequest to install a new socket
; listener which checks the TID first. Patch installed in the ATP control hook.
;
; NOT IN A/UX <PB302>
;____________________________________________________________________________________
ATPPatch PROC EXPORT
ROMJATPEx2 EQU $4082B8B8
ROMSndRqInit EQU $4082B994
ToROMSendReq EQU $4082B8D8
ROMATPIgnore EQU $4082BE58
ROMReadResp EQU $4082BE6C
TCBE EQU 12 ; Number of TCB's
TSktNum EQU 4 ; Offset to socket no.
TQElPtr EQU TSktNum+TCBE ; Offset to qEl ptr
CMP #SendRequest,CSCode(A0) ; Is it SendRequest?
BNE.S AnRTS ; Just return if not
MOVE.L MaskBC,D3 ; D3 = mask value
MOVE.L ROMBase,D2 ; D2 = ROM base
AND.L D3,D2 ; D2 = masked ROM base
AND.L (SP),D3 ; D3 = masked calling address
CMP.L D2,D3 ; Make sure called from ROM
BLO.S AnRTS ; Just return if not
ADDQ #4,SP ; Pop return address
MOVE.L AbusVars,A2 ; A2 -> MPP variables
MOVE.L ATPVars(A2),A2 ; A2 -> ATP variables
MOVE.L AddrBlock(A0),D3 ; D3 = address block from queue element
AND.B #FlagMask,ATPFlags(A0) ; Make sure nothing but flag bits
MOVE #TooManyReqs,D0 ; Assume too many concurrent requests
MOVEQ #TCBE-1,D2 ; D2 = offset into TCB table
@10 TST.B TSktNum(A2,D2) ; Is this entry free?
DBEQ D2,@10 ; Keep going until got one
BNE.S @20 ; Return error if none
JSR ROMSndRqInit ; Do initial setup. A3 -> data area.
BNE.S @20 ; Just return if error
CLR.B D1 ; Indicate we want a dynamic socket
LEA newATPRead,A1 ; A1 -> new socket listener
JMP ToROMSendReq ; Jump into ROM
@20 JMP ROMJATPEx2
AnRTS RTS ; Just return if not SendRequest
;
; This is the real patch. We make sure the TID matches before reading in
; the response
;
newATPRead MOVEQ #ATPHdSz,D3 ; D3 = size to read
CMP.B #ATP,-(A3) ; Make sure DDP type was ATP (46)
BNE.S @20 ; Ignore it if not, (RHA ptr now even)
JSR (A4) ; Read header into RHA
BNE.S AnRTS ; Just return if error
MOVE.L ATPVars(A2),A5 ; A5 -> our local variables
MOVE.B DDPDstSkt-DDPType-ATPHdSz(A3),D0 ; D0 = dest. socket no.
MOVE.B ATPControl-ATPHdSz(A3),D2 ; D2 = control byte
BPL.S @20 ; Ignore if not a response (2)
ADD.B D2,D2 ; Shift it left one bit
BMI.S @20 ; Ignore if not a response (3)
;
; Incoming response - find the TCB for it and read it in
;
MOVEQ #TCBE-1,D2 ; D2 = number to search, less one
LEA TSktNum+TCBE(A5),A5 ; A5 -> past sockets
@10 CMP.B -(A5),D0 ; This it? (fast loop!)
DBEQ D2,@10 ; Try all we can
BNE.S @20 ; Ignore it if no match
SUB D2,A5 ; A5 -> start of TCB table
LSL #2,D2 ; D2 = offset to queue element pointer
ADD D2,A5 ; A5 -> queue element ptr, offset
MOVE.L TQElPtr-TSktNum(A5),A5 ; A5 -> queue element
;
; *** The actual fix ***
;
MOVE ATPTransID-ATPHdSz(A3),D0 ; D0 = TID from packet
CMP ReqTID(A5),D0 ; Is it the one we want?
BNE.S @20 ; If not just ignore it
JMP ROMReadResp ; Otherwise continue
@20 JMP ROMATPIgnore ; Ignore the packet
;____________________________________________________________________________________
; PB337 SetOSDef Patch
;
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 16dec87 PB337 SetOSDef SetOSDef
;
; The trap SetOSDef is used to tell the start code to boot off of a foreign OS. The Problem
; was SetOSDef just stuffed whatever A0 was pointing to into pram. There was no validity
; check. The trap number is A083, which happens to be the high word of a master pointer
; pointing at ROM resources. So if your program crashed and executed garbage, such as
; master pointers, whatever A0 was pointing to got written to pram. This meant your machine
; would no longer recognize your hard disk. The fix was to change the interface, since
; noone was using this trap nohow, nowhere, and add a password. The password was put into
; lowmemory to keep the same glue in the compiliers.
;
nSetOSDef PROC EXPORT
AppPhne EQU $09961010 ;
realSetOS EQU $40801578 ;
Peril EQU $0CDC ;
cmpi.l #AppPhne,Peril ; check if oneshot is on
bne.s @errexit ;
clr.l Peril ;
jmp realSetOS ; go to real trap
@errexit ;
clr.l Peril ;
moveq #-1,d0 ; signal error
rts ; and return
ENDPROC ; end nSetOSDef
;____________________________________________________________________________________
; PB366 maxblock Patch
;
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 25jan88 PB366 maxblock maxblock
;
; PB366 25jan88 bbm fixed a bug in maxblock.
;
nMaxBlock PROC EXPORT
realMxBlk EQU $E05E ;offset to routine Maxblock in rom (from rombase)
JsrRom realMxBlk ;go do maxblock and then do a postfix.
tst.l D0 ;check for an error.
ble.s @rtn ;if an error or zero just return.
subq.l #2,D0 ;else adjust maximum size by two.
@rtn rts ;
;____________________________________________________________________________________
; PMAB372 Async serial driver patch
;
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 26jan88 PMAB372 (AOutOpen,RAIntHnd) (RAIntHnd)
;AppleSystemPatch PatchIIROM.a 09Feb88 PB386 (AOutOpen)
;AppleSystemPatch PatchIIROM.a 23Feb88 PMAB401 (Control) (Control)
; If hardware handshaking is enabled, and the receiver de-asserts DTR, but the sender ignores
; it and keeps sending, the receiver will go into an infinite loop in the receive interrupt
; routine. This was caused by a jump to the wrong label. The patch is installed in a patch
; vector for the async driver. Needed to include all async driver code which jumped to
; the receive interrupt handler.
; 24May90 <48> (Control) Ctl #9
; OK, so this is a mess. Let's sort thru the various tangles.
; First off, the N&C BAP stuff had to be rolled in for 7.0, so that the patch
; they had put in their SINI resources stopped stomping this one. This entailed --
; -- patching out the .BOut and .BIn driver headers such that all the B driver
; calls would get driver storage ptr from ExpandMem instead of PortBVars.
; See end of patch.
; -- patching TB and ExtB interrupt handlers to get driver storage ptr from
; ExpandMem instead of PortBVars.
; See end of patch.
; -- changing the already patched SCB and RB interrupt handlers
; to get driver storage ptr from ExpandMem instead of PortBVars.
; -- patching the routines (mostly interrupt handlers) that used the lowMem
; BInDCE to now just get the DCE ptr from the Unit Table. (Yeah, the offset
; is hardcoded-- sue me).
; -- patching the Open and Close calls for port B to incorporate the BAP stuff
; to call the LAP mgr to arbitrate for port B.
; Second, Control call 9 had to be patched to hold the buffer in memory for VM.
; This meant i had to patch .AOut and .BOut close as well to unhold the buffer.
;
;
;AppleSystemPatch PatchIIROM.a 17Dec90 <80> (all B driver entry points,InitSCC,all int handlers)
; We need to add provide nike printer support. This entails:
; -- patch control call 16 to use bit 6 for setting external/internal clocking modes.
; -- Patch to add status call to return version.
; -- Patch InitSCC routine to use this RAM-based table so
; that clocking mode is now variable instead of hard-wired to internal only.
; -- set clock divide to 1 instead of 16 for external clocking
; -- clear HWHS enable since we can't clock and handshake on same line
; -- Patch whole ExtIntHandler so we can (set bit 3 of AsyncErr if break rcvd) at end of rtn.
; Also, we change the BAP stuff such that it is also supported in 6.x, not just 7.0
; -- Always get the driver storage pointer for port B from extended mem
; -- Call Gestalt in Open and Close to determine version of AppleTalk to see which
; port arbitration scheme we should use, ours or the LAP mgr's.
;
;AppleSystemPatch PatchIIROM.a 16Jan91 <81> (all A driver entry points)
; We patch all the port A driver headers (port B driver headers already patched)
; so that we can put a signature word before each header that we can use
; to identify ourselves as the Apple async serial driver. We do this
; right now so that that our linked patch on Open (in Serialpatches.a) will
; not stomp the version number of some third party driver that sticks them-
; selves into our spot in the unit table. I think this idea will come in
; handy later as well.
; I think i'll use the signature word 'wong'.
;
; Also, fix the port arbitration code in Open and Close to make call to the
; new 'atkv' Gestalt call instead of the old 'atlk' call. We do this because
; the new call return atalk version number regardless of whether MPP driver
; is open (i.e. appletalk is active).
;
; <84> Fixed bug in external clock stuff that was causing us to disable
; internal clocking on both ports if we were trying to do external
; clocking on just one. So Nike would print but Tabasco would just
; sit there. The fix was to set clocking params at each time we go
; thru InitSCC, rather than just once during the external clocking
; control call. This way even tho the ports share the InitSCCTable,
; we set the Table properly by keying off of the value in CtlOptions
; variable, which they don't share.
; <86> Status calls 9 and $8000 now return static version number for driver
; instead of what's in the DCE.
asyncPatch PROC EXPORT
; Equates
SerialVers equ 5 ; current version 3/91 <86>
SCCARWOFF equ 2 ; SCC A side R/W offset <A357/06nov86>
SCCBRWOFF equ 0 ; SCC B side R/W offset <A357/06nov86>
PortAVars EQU SerialVars ; serial chan A variables and buffer
AInDCE EQU PortAVars+4 ; Device Control Entry ptr for input
PortBVars EQU AInDCE+4 ; serial port B variables and buffer
BInDCE EQU PortBVars+4 ; Device Control Entry ptr for input
; next come variable offsets within the user's local variable buffer
OutDCE EQU 0 ;(4) long DCE pointer for output driver
SCCOffset EQU 4 ;(2) word of SCC offset . . .
InBufPtr EQU 6 ;(4) pointer to local input buffer
BufSize EQU 10 ;(2) size of local input buffer
BufLow EQU 12 ;(2) low buf byte count to send XOn
BufHigh EQU 14 ;(2) bytes from end of buffer to send XOff
SWHS EQU 16 ;(1) software handshake enable
HWHS EQU 17 ;(1) hardware handshake enable
XONChar EQU 18 ;(1) input char which continues output (SWHS)
XOFFChar EQU 19 ;(1) input char which stops output
Options EQU 20 ;(1) bit 4 = abort on parity error
; bit 5 = abort on overrun
; bit 6 = abort on framing error
PostOptions EQU 21 ;(1) bit 7=1 enables posting break changes
; bit 5=1 enables posting handshake changes
InSWHS EQU 22 ;(1) input XOn/XOff flow control enable
InHWHS EQU 23 ;(1) input RTS (DTR) flow ctl enb <14Oct85>
AsyncErr EQU 24 ;(1) error indications (cumulative)
SoftOR EQU 0 ; bit 0 = soft overrun
; bit 4 = parity error
; bit 5 = overrun error
; bit 6 = framing error
FlowOff EQU 25 ;(1) $80 = input flow shut off by XOff, $40 by DTR
ReadCmd EQU 26 ;(1) FF = read command pending
WriteCmd EQU 27 ;(1) FF = write command pending
CTSFlag EQU 28 ;(1) FF = CTS asserted
XOFFlag EQU 29 ;(1) FF = XOFF pending
LastWR5 EQU 30 ;(1) WR5 value with last DTR state <14Oct85>
DTRNegVal EQU 31 ;(1) WR5 value used to negate DTR <14Oct85>
SCCReset EQU 32 ;(1) WR9 value for reset
StopBits EQU 33 ;(1) stop bits/parity option (WR4 value)
WR1AVal EQU 34 ;(1) first WR1 value to write
WR3AVal EQU 35 ;(1) first WR3 value to write
WR5AVal EQU 36 ;(1) first WR5 value to write
BaudLoCnst EQU 37 ;(2) 2 byte baud rate constant (WR12-13)
BaudHiCnst EQU 38
RcvrBits EQU 39 ;(1) 1 byte receiver bits/char (WR3 value)
XmitBits EQU 40 ;(1) 1 byte xmitter bits/char (WR5 value)
WReqPin EQU 41 ;(1) w/req pin state (WR1 value)
lastSetup EQU 42 ;(2) last SCC init values . . .
BufIndex EQU 44 ;(2) index into local buffer (insert)
BufOutdex EQU 46 ;(2) index into local buffer (remove)
LocalBuf EQU 48 ;(64) local buffer for input chars
LclBufSize EQU 64 ; default input buffer size = 64 bytes
HSCount EQU 112 ;(2) count of CTS pulses in VBL time (clk detect) <14Oct85>
LastTime EQU 114 ;(4) ticks time of last CTS pulse (clk detect) <14Oct85>
SendXOnff EQU 118 ;(1) flag to xmit logic to send XOn/XOff <14Oct85>
CharMask EQU 119 ;(1) $1F,$3F,$7F, or $FF mask for input chars <14Oct85>
PEChar EQU 120 ;(1) char to change incoming parity errors to <14Oct85>
AltChar EQU 121 ;(1) char to change incoming PEChars to <14Oct85>
InSWHS1 EQU 122 ;(1) saved InSWHS state <14Oct85>
CtlOptions EQU 123 ;(1) bits 0-6=0 (reserved). bit 7=1 to leave <14Oct85>
; DTR state unchanged at close.
SaveExInt EQU 124 ;(4) saved Ext int vector <14Oct85>
SaveTxInt EQU 128 ;(4) saved TxD int vector <14Oct85>
SaveRxInt EQU 132 ;(4) saved RxD int vector <14Oct85>
SaveSxInt EQU 136 ;(4) saved Special Rx int vector <14Oct85>
LclVarSize EQU 140 ; output driver storage size <14Oct85>
;
; ROM ADDRESS OFFSETS
;
; where did we come from?
fromAOutOpen EQU $4082AC58 ; addr's to compare on stack - called from ROM rsrc <PB386>
fromAInOpen EQU $4082abf4
fromBOutOpen EQU $4082AC86 ;
fromBInOpen EQU $4082ABFC ; new arbitration for port B and new PortBVars
fromControl EQU $4082AF74 ; <PMAB401>
fromClose EQU $4082ae96 ;
fromStatus EQU $4082af22
fromInitSCC EQU $4082ae14
; open call patch equates
backToAinOpen EQU $2abf4 ; ROM offsets (use macros for operations)
backToAOutOpen EQU $2AC74
backToBInOpen EQU $2AC00
backToBOutOpen EQU $2ACA0 ; different return addr's for 6.X and 7.0
ROM_TAIntHnd EQU $2b1c8 ; interrupt handlers we're NOT patching
backToPollDtain EQU $2B2E8
ToContOut EQU $2B1EA
ToGoodFinish EQU $2B18A
ToGetBufRegs EQU $2B262
ToGetBufCnt EQU $2B272
ToCtlXOff EQU $2B390
ToPut EQU $2B38A
backToPut EQU $2B386
ToRdReqDone EQU $2B3F6
ToCtlSet EQU $2b0a6
toContOut1 EQU $2b1ee
; Control Patch equates
backToBypassControl EQU $2af86
ROM_CtlGood EQU $2afbc
ROM_CtlExit EQU $2afbe
; SerialBuf (ctl call 9) patch equates
FinishCall9 EQU $2b01a
; Control Call 16 patch equates
InitSCC EQU $2ae04
;
; Status patch equates
backToStatus EQU $2af3c
;InitSCC patch equates
backToInitSCC EQU $2ae14
initData EQU $2add0
; close patch equates
SyncOutput EQU $2aee8
InitSCC1 EQU $2ae0a
ResetData EQU $2ae5a
ResetLth EQU $10
freePort EQU $2aed6
; bypass driver ROM entrypoint addresses <81>
;port A
ROM_AInEntryOpen EQU $2abf2
ROM_AInEntryClose EQU $2aee4
ROM_AInEntryPrime EQU $2b1fa
ROM_AOutEntryOpen EQU $2ac56
ROM_AOutEntryClose EQU $2ae6a
ROM_AOutEntryPrime EQU $2b146
ROM_AEntryControl EQU $2af60
ROM_AEntryStatus EQU $2af0e
;port B
backToBInOpenStart EQU $2ABFA
backToBOutOpenStart EQU $2AC84
ToBOutClose EQU $2AE7E
backToBInPrime EQU $2B204
backToBOutPrime EQU $2B150
backToBControl EQU $2AF6A
backToBStatus EQU $2AF18
; for BAP only interrupt handler patches
backToTXIntHnd EQU $2B1CC
; for BAP only patches-- since these are not in Interfaces or Internals,
; where they should be
LUsePortB EQU 17 ; request use of printer port ;<2.0>
LFreePortB EQU 18 ; grant use of printer port ;<2.0>
LStatPortB EQU 19 ; obtain current printer port status ;<2.0>
LAPMgrPtr EQU $B18 ; This points to start of LapMgr ;<2.0>
LAPMgrCall EQU 2 ; Offset to make LAP manager calls ;<2.0>
;
; Miscellaneous patch equates
;
BInDCEOffset EQU 28 ; offset of .BIn DCE handle from UTableBase
;**************************************************************************
; Start of async driver patch code
;**************************************************************************
movem.l d0-d1,-(SP) ; save reg D0
MOVE.L 12(SP),D0 ; get D0 = return address
_StripAddress
move.l d0,d1 ; d1 = stripped return address
move.l #fromAOutOpen,D0 ; test for ChkAConfig call from AOutOpen
_StripAddress
cmp.l d0,d1
BEQ.w OpenAFix ; no, then called for SCC channel A
move.l #fromAInOpen,D0 ; test for ChkBConfig call from BInOpen
_StripAddress
cmp.l d0,d1
BEQ.w OpenAFix ; no, then called for SCC channel B
move.l #fromBOutOpen,D0 ; test for ChkBConfig call from BOutOpen
_StripAddress
cmp.l d0,d1
BEQ.w OpenBFix ; no, then called for SCC channel B
move.l #fromBInOpen,D0 ; test for ChkBConfig call from BInOpen
_StripAddress
cmp.l d0,d1
BEQ.w OpenBFix ; no, then called for SCC channel B
MOVE.L 8(SP),D0 ; get immediate return address
_StripAddress
move.l d0,d1 ; d1 = stripped return address
move.l #fromControl,D0 ; test for call from Control
_StripAddress
cmp.l d0,d1
BEQ.w ControlFix ; no, then called from Control
move.l #fromStatus,D0 ; test for call from Status <80>
_StripAddress
cmp.l d0,d1
BEQ.w StatusFix ; no, then called from Status
move.l #fromClose,d0 ; to fix bypass close calls <80>
_StripAddress
cmp.l d0,d1
beq.w CloseFix ; no, then called from Close
move.l #fromInitSCC,D0 ; test for call from InitSCC
_StripAddress
cmp.l d0,d1
BEQ.w InitSCCFix ; no, then called from InitSCC
movem.l (SP)+,D0-d1 ; restore reg D0
RTS ; back to ROM
;_______________________________________________________________________
;
; Close fixes
; -- unhold the buffer we may have held in control call #9 for 7.0 VM
; -- do that nutty BAP stuff to free port B
;
CloseFix
ADD.L #12,SP ; pop save reg d0,d1 and rtrn addr--we jump back
move.l a1,-(sp) ; save DCE ptr
; for BAP
; if close is for port B,we'll just stomp over what ROM put in a6
cmpa.l #PortAVars,a6 ; from port A
beq.s @common ; yes, then move on to common code
move.l ExpandMem,a6 ; no, then get storage ptr for port B
lea ExpandMemRec.emSerdVars(a6),a6
@common
MOVE.L (A6),A2 ; get locals pointer <14Oct85>
TST.B CtlOptions(A2) ; leave DTR unchanged? <14Oct85>
bmi.s @1 ; <C216/16oct86>
bclr #7,XmitBits(A2) ; no, clear the DTR bit <C216/16oct86>
bclr #7,WR5AVal(A2) ; <C216/16oct86>
@1 bclr #3,XmitBits(A2) ; always clear Tx enable <C216/16oct86>
jsrROM SyncOutput ; delay until last char has cleared <14Oct85>
; output buffer
LeaROM ResetData,A3
MOVEQ #ResetLth,D1
jsrROM InitSCC1 ; shut down the channel
; for VM
; now that we've shut down the channel it should be safe to unhold
; the input buffer. we don't check for VM error because we can't do
; much about it.
jsr UnHoldInputBuf ; unhold the buffer if necessary
; for BAP
; we replace ROM's port arbitration stuff with BAP stuff
; too bad the ROM port arbitration code comes at the END of the close call
LEA SaveExInt(A2),A3 ; reinstall former int handlers <14Oct85>
MOVE.L (A3)+,(A5) ; <14Oct85>
MOVE.L (A3)+,(A4)+ ; <14Oct85>
ADDQ.L #4,A4 ; <14Oct85>
MOVE.L (A3)+,(A4)+ ; <14Oct85>
MOVE.L (A3),(A4) ; <14Oct85>
move.l (sp)+,a1 ; restore DCE ptr
MOVE.L DCtlStorage(A1),A0 ; get storage handle
_DisposHandle ; get rid of it
CLR.L DCtlStorage(A1) ; without a trace
CLR.L (A6) ; get rid of ptr address <14Oct85>
tst.w d3 ; what port are we?
beq.s @freeB ; port b; do that BAP thing to free port
jmpROM freePort ; port a; finish up in ROM 2aed6
@freeB
move.l ExpandMem,a0 ; <90>
tst.w ExpandMemRec.emAppleTalkInactiveOnBoot(a0) ; <90> If AppleTalk is inactive, dont set up the LAP manager
bnz.s @freeThePort ; <90> AppleTalk is not active.
move.l #'atkv',d0 ; what version of Appletalk? <81>
_Gestalt
tst.w d0 ; <90> Check error code
bnz.s @freeThePort ; <90> If Gestalt does not know the selector, AppleTalk is not active
move.l a0,d0 ; get high byte (version) into low byte
rol.l #8,d0
cmp.b #53,d0 ; is Atalk version 53 or greater?
bge.s @useLAP ; yes, then call LAP manager, it exists
@freeThePort
jmpROM freePort ; no, then finish up in ROM
@useLAP move.w #LFreePortB,d0 ; call LAP Manager to free port B
move.b #useAsync,d1
move.l LAPMgrPtr,a0
jsr LAPMgrCall(a0)
move.w #0,d0 ; no error on close
rts
;
; UnHoldInputBuf -- unholds the the buffer that may have been held
; Called by: control, close
; Inputs: a2 -- ptr to the serial vars
; Destroys: d0, a0, a1
;
; if old buffer was held, we better unhold it. it will have been held
; if it was not our LocalBuf, i.e. was not in the system heap
; first time thru this loop InBufPtr is 0.
UnHoldInputBuf
move.l #gestaltVMAttr,d0 ; is VM installed?
_Gestalt
move.w a0,d0
beq.s @goodEnd ; if not, we're outta here
; check usual case...is inBufPtr equal to LocalBufPtr?
move.l d1,-(sp) ; save a reg
lea LocalBuf(a2),a0 ;inBufPtr = LocalBufPtr?
move.l a0,d1
move.l InBufPtr(a2),d0
eor.l d1,d0
_StripAddress ; ignore differences in the high bits
move.l (sp)+,d1 ; restore a reg
tst.l d0 ;
beq.s @goodEnd ; same, so don't need to unhold
; check first time thru case, when InBufPtr
; would equal zero
move.l InBufPtr(a2),d0 ; for first time thru, is InBufPtr zero?
beq.s @goodEnd ; yes, then don't need to unhold
; unhold the puppy
movea.l d0,a0 ; a0 <- ptr
moveq #0,d0 ; clear out count
move.w BufSize(a2),d0 ;
movea.l d0,a1 ; a1<- cnt
_UnholdMemory ; unhold the old buffer
rts
@goodEnd moveq #0,d0 ; everything a-ok
rts
;_______________________________________________________________________
;
; Routine: InitSCC
; Patch: --We patch this routine to use the InitData table here in RAM
; instead of the one in ROM. We do this so that the values in
; WR11 and WR14 aren't hardcoded, so that we can support external
; clocking.
; --We also fix the value of StopBits (WR4) here to have the clock
; divide bits correspond to the the external/internal clock state
; indicated in CtlOptions. We do this here so that CtlConfig calls
; won't stomp StopBits in the ToSCCInit routine.
; --We also disable HWHS so we don't try to use CTS line for both
; clocking and handshaking.
clkBit equ 6 ; bit 6 in CtlOptions controls ext/int SCC clk
clkDvdBit equ 6 ; divide clock bit in WR4
clkMask equ %01000000 ; mask for getting at clkBit <84>
extClkSrc equ %00101000 ; SCC clk src is TRxC (CTS) pin (WR11) <84>
intClkSrc equ %01010000 ; SCC clk src is baud rate generator (WR11) <84>
BRGEnbl equ %00000001 ; enable baud rate generator (WR14) <84>
BRGDsbl equ %00000000 ; disable baud rate generator (WR14) <84>
SCCDataTable
DC.B $02,9 ; status in low bits, MIE disabled
clkDvd DC.B 4,$FF ; x16 clk, stop bits, parity options
DC.B 1,$FF ; WR1 reg, first write
DC.B 3,$FF ; bits/char option rcvr
DC.B 5,$FF ; bits/char option xmitter
DC.B $00,2 ; zero interrupt vector
DC.B $00,10 ; NRZ encoding
ClkMode DC.B $50,11 ; brgen/TRxC clk to rcvr, xmitter--default to internal
DC.B 12,$FF ; set baud rate low byte
DC.B 13,$FF ; set baud rate high byte
DC.B 3,$FF ; enable rcvr
DC.B 5,$FF ; enable xmitter
BRGEnable DC.B $01,14 ; enb/disable baud rate generator from RTxC pin --default to on
dc.b $A0,15 ; Break, CTS external ints (dcd not needed) <2.3>
DC.B $10,0 ; reset ext/status twice
DC.B $10,0
DC.B 1,$FF ; w/req pin configuration
DC.B $0A,9 ; enable interrupts, status in low bits
SCCDataTableLth EQU *-SCCDataTable ;
InitSCCFix
movem.l (SP)+,d0-d1 ; restore saved regs (we might need d1) <83>
ADD.L #4,SP ; pop saved retrn addr--we jump back
move.l a3,d0
cmpRA InitData,d0 ; are we initializing SCC?
bne @done
lea SCCDataTable,a3 ; use our RAM table instead of the ROM one
moveq #SCCDataTableLth,d1
movem.l d1/a0,-(sp) ; save out reg's <84>
; default to internally clocked state <84>
bset.b #clkDvdBit,StopBits(a2) ; default to a divide-by-16 clock <84>
moveq #intClkSrc,d0 ; internal clocking source <84>
moveq #BRGEnbl,d1 ; enable baud rate generator <84>
btst.b #clkBit,CtlOptions(a2) ; are we externally clocked?
beq.s @load ; not externally clocked, so load
; set to externally clocked state
bclr.b #clkDvdBit,StopBits(a2) ; set to a divide-by-one clock <84>
moveq #extClkSrc,d0 ; external clock source <84>
moveq #BRGDsbl,d1 ; disable baud rate generator <84>
clr.b HWHS(a2) ; make sure we're not trying to do HWHS <84>
@load lea ClkMode,a0 ; load params into InitSCC data table <84>
move.b d0,(a0) ; <84>
lea BRGEnable,a0 ; <84>
move.b d1,(a0) ; <84>
movem.l (sp)+,d1/a0 ; restore reg's <84>
@done jmpROM backToInitSCC ; finish up in ROM
;_______________________________________________________________________
;
; Routine: Status
; Patch: We patch status to add a call to return the driver's version.
StatusFix
ADD.L #12,sp ; pop save reg d0,d1, return addr--we jump back to ROM
MOVE.W IOTrap(A0),-(SP) ; save trap to distinguish immed calls<14Oct85>
MOVE.L A1,-(SP) ; save passed DCE for in/out <14Oct85>
MOVE.W SR,-(SP) ; disable interrupts for ctl call <14Oct85>
ORI #HiIntMask,SR ; <A357/06nov86>
LEA CSCode(A0),A0 ; get pointer to return parameters
MOVEQ #StatusErr,D0 ; assume status error
MOVE.L A2,D1 ; have our variables been set up? <14Oct85>
Bgt @stat1 ; exit if not (only input side open)<14Oct85>
jmpROM ROM_CtlExit ; just like ROM
@stat1 MOVE.W (A0)+,D1 ; get opcode
cmpi.w #9,d1 ; do we care?
beq.s @version ; yes
cmpi.w #$8000,d1 ; largest negative number csCode for Version
beq.s @version ; yes
jmpROM BackToStatus ; no
@version move.b #SerialVers,(a0) ; return the version <86>
jmpROM ROM_CtlGood
;_______________________________________________________________________
;
; Routine: Control
; Patch: We patch control for the following reasons:
; 1) to add VM support for control call 9--lock/unlock the buffer
; 2) to add external clock support in control call 16
; Called from Control - clear reg D0 in case this call is for KillIO
ControlFix
@0 adda.w #12,sp ; from control - flush saved reg D0,d1, and return addr
CLR.L D0 ; clear reg D0 for killIO <PMAB401>
MOVE.W IOTrap(A0),-(SP) ; save trap to distinguish immed calls<14Oct85>
MOVE.L A1,-(SP) ; save passed DCE for in/out <14Oct85>
MOVE.W SR,-(SP) ; disable interrupts for ctl call <14Oct85>
ORI #HiIntMask,SR ; <A357/06nov86>
LEA CSCode(A0),A0 ; get parameters
MOVE.W (A0)+,D1 ; get opcode
cmpi #9,d1 ; opcode 9?
beq CtlBuffer ; if so, handle here in the patch
cmpi #16,d1 ; opcode 16? (ctlOptions) <extClk>
beq CtlSwitchCTSClock ; <extClk>
jmpROM backToBypassControl ; if not, let ROM handle it
; Routine: SetCtlBuffer -- Opcode 9
;
; Patch: The patch is needed for 7.0 VM. We must 'hold' the buffer in memory
; so that there is no possibility it is paged out at interrupt time (which
; would have the potential for causing a double page fault).
CtlBuffer CLR.L BufIndex(A2) ; clear in and out indices
MOVE.L (A0)+,A4 ; buffer pointer
moveq #0,d1 ; clear out length reg
MOVE.W (A0),D1 ; length of buffer?
BEQ.S InstllLBuf ; if zero, revert to our own buffer
; hold the new non-local buffer so VM doesn't page it out
move.l #gestaltVMAttr,d0 ; is VM installed? not on a mac II w/o MMU
_Gestalt
move.w a0,d0
beq.s InstllABuf ; if not, skip the hold
movea.l a4,a0 ; hold buffer addr
movea.l d1,a1 ; hold buffer count
; since VM won't let us call _holdmemory with interrupts
; masked, we set the interrupt level back to that app's
; interrupt level, which hopefully was zero. If so, then
; everything should be peachy. If not, then we return the
; error that VM spits at us.
move.w sr,-(sp) ; save out our int lvl
move.w 2(sp),d0 ; get app's int lvl
and.w (sp),d0 ; and set us to that
move.w d0,sr
_HoldMemory ; hold the new buffer in memory
move.w (sp)+,sr ; and restore our int lvl
tst.w d0 ; did we get our physical buffer?
beq.s InstllABuf ; yes, go on
Ctl_Err jmpROM ROM_CtlExit ; no, then pass back VM error
; InstllLBuf is also called from OpenInstall!
InstllLBuf LEA LocalBuf(A2),A4 ; use our meager local buffer for now
MOVEQ #LclBufSize,D1 ;
InstllABuf
; since VM won't let us call _holdmemory with interrupts
; masked, we set the interrupt level back to that app's
; interrupt level, which hopefully was zero. If so, then
; everything should be peachy. If not, then we return the
; error that VM spits at us.
move.w sr,-(sp) ; save our int lvl
move.w 2(sp),d0 ; get app's int lvl
and.w (sp),d0 ; and set us to that
move.w d0,sr
jsr UnHoldInputBuf ; unhold the buffer if necessary
move.w (sp)+,sr ; restore our int lvl
tst.w d0 ; did we release old buffer?
bne.s Ctl_Err ; no, pass back VM error
jsrROM FinishCall9 ; and finish up the call in ROM
jmpROM ROM_CtlGood ; and go back to ctl call dispatcher
; Routine: SetCtlOptions -- Opcode 16
; Patch: We patch this routine so that bit 6 of CtlOptions variable now
; controls a switch to internal/external clocking on the CTS (HSIn) line.
; We must call InitSCC to get the clocking option to kick in.
; Inputs: byte number in IOPB value
; (26) [$0010]
; (28) bit 7 = 0 for drop DTR at close
; bit 7 = 1 for leave DTR unchanged at close
; bit 6 = 0 for internal clocking
; bit 6 = 1 for external clocking
; bits 0-5 reserved for future use
; Notes: We will not put control for the GPI internal/external
; clocking switch here, as that requires the control of
; HW external to the SCC (namely, the VIA vSync pin). Control
; of the GPIa line is in _HWPriv.
;
CtlSwitchCTSClock
move.b (a0),CtlOptions(a2) ; store new value <84>
jsrROM InitSCC ; set up the SCC according to new value <84>
jmpROM ROM_CtlGood ; finish up in ROM <84>
;_______________________________________________________________________
;
; Open Fixes
;
;
; Channel A - replace receive routine vectors installed by async open
OpenAFix
ADD.L #8,SP ; pop save reg D0,d1 - not needed <PMAB401>
MOVE.L (SP)+,A0 ; pop A0 = addr to continue ChkConfig
move.l (sp)+,a2 ; save async open ret addr
JSR (A0) ; finish ChkConfig (A1,D1,D2 params)
move.l a2,d0 ; did we come from .Ain or .Aout? <81>
_StripAddress
move.l d0,d1
move.l #fromAOutOpen,d0
_StripAddress
cmp.l d0,d1
beq.s @out ; we came from .Aout
@in lea AsyncAIn,a2 ; we came from .Ain-- store new .Ain driver header in DCE
move.l a2,(a1)
jmpROM backToAinOpen ; and finish up in ROM
@out lea AsyncAOut,a2 ; store new driver header for AOut into DCE
move.l a2,(a1)
LEA PortAVars,A2 ; local variables address
PEA NewPollDtain ; new disk poll routine
PEA NewSCAIntHnd ; new special RxD int handler
PEA NewRAIntHnd ; new RxD int handler
peaROM ROM_TAIntHnd,-(sp) ; ROM--TxD int handler
PEA Lvl2DT+16 ; SCC interrupt dispatch table, chan A
PEA NewExtAIntHnd ; External int handler
JmpRom backToAOutOpen ; JUMP BACK INTO ROM
; Channel B - almost the same patch as channel A
; Except of course for the BAP stuff
OpenBFix
move.l ExpandMem,a0 ; <90>
tst.w ExpandMemRec.emAppleTalkInactiveOnBoot(a0) ; <90> If AppleTalk is inactive, dont set up the LAP manager
bnz.s @appleTalkInactive ; <90> AppleTalk is not active.
move.l #'atkv',d0 ; what version of Appletalk? <81>
_Gestalt
tst.w d0 ; <90>
bne.s @appleTalkInactive ; <90>
move.l a0,d0 ; get high byte (version) into low byte
rol.l #8,d0
cmp.b #53,d0 ; is Atalk version 53 or greater?
bge.s @useLAP ; yes, than call LAP manager, it exists
@appleTalkInactive
; no, use old chkConfig
add.l #8,sp ; pop saved d0, d1 -- not needed
movea.l (sp)+,a0 ; pop A0 = addr to continue non-BAP ChkConfig
move.l (sp)+,a2 ; save Open return addr
jsr (a0) ; go do the ROM chkConfig rtn
bra.s @gotPort
@useLAP add.l #12,sp ; pop d0,d1,ROM ChkConfig addr
move.l (sp)+,a2 ; save Open return addr
movem.l a1-a2,-(sp) ; save out reg's we might use
move.w #LStatPortB,d0 ; request status of the printer port
move.l LAPMgrPtr,a0
jsr LAPMgrCall(a0)
cmp.b #useAsync,d1 ; do we already own the port?
beq.s @rstrReg ; yes
move.w #LUsePortB,d0 ; no, request use of the printer port-
move.b #useAsync,d1 ; for the serial driver-
move.l LAPMgrPtr,a0 ; by calling the LAP Manager
jsr LAPMgrCall(a0)
cmp.w #noErr,d0 ; did we get the printer port?
beq.s @rstrReg ; yes
movem.l (sp)+,a1-a2 ; no,restore reg's
rts ; return to IO Core: we already popped ret addrs and regs
@rstrReg
movem.l (sp)+,a1-a2 ; restore reg's
@gotPort
move.l a2,d0 ; get Open return addr
_StripAddress
move.l d0,d1
move.l #fromBOutOpen,D0 ; test for ChkBConfig call from BOutOpen
_StripAddress
cmp.l d0,d1
beq.s @out
@in lea AsyncBIn,a2 ; store new driver header for BIn into DCE
move.l a2,(a1)
JmpRom backToBInOpen ; jump back into ROM in BInOpen
@out
lea AsyncBOut,a2
move.l a2,(a1) ; store new driver header for BOut into DCE
move.l ExpandMem,a2 ; get storage ptr
lea ExpandMemRec.emSerdVars(a2),a2
CLR.L -(SP) ; no disk poll routine
PEA NewSCBIntHnd ; new special RxD int handler
PEA NewRBIntHnd ; new RxD int handler
pea NewTBIntHnd ; TxD int handler
pea Lvl2DT ; SCC interrupt dispatch table, chan A
pea NewExtBIntHnd ; External int handler
JmpRom backToBOutOpen ; JUMP BACK INTO ROM
;-----------------------------------------------------------------------
;
; Interrupt Handlers
;
;-----------------------------------------------------------------------
;_______________________________________________________________________
;
; Routine: PollDtaIn
; Arguments: A5.L (input) -- AVBufA pointer
; A6.L (input) -- SCC channel A Data pointer
; PollStack -- start of stack data
; This routine should be jsr'ed to, with polled input data
; on the stack (high-order bytes between current SP+4 and
; PollStack address).
; Function: Processes input data from disk driver polling.
;
AsyncPRAddr EQU PollRtnAddr ; don't use DskRtnAddr because Sony driver uses it
NewPollDtaIn
MOVE.L PollStack,A4 ; start of data
MOVE.L (SP)+, AsyncPRAddr ; save return address <01Feb85>
StorData TST.B (A5) ; SCC data available?
BMI.S @1
MOVE.B (A6),-(SP) ; push it on the stack
BRA.S StorData ; get it emptied out . . .
@1 CMP.L SP,A4 ; processed all data?
BEQ.S @2 ; exit if so
SUBQ #2,A4 ; skip over garbage byte
MOVE.B (A4),D0 ; get next byte
LEA PortAVars,A3 ; get appropriate variables (channel A)
move.l SCCRd,a0 ; and scc pointers for RxBF routine <6.2>
adda.l #ACtl,a0 ; <6.2>
move.l SCCWr,a1 ; get scc write base ptr <6.2>
adda.l #ACtl,a1 ; <6.2>
BSR.S PollStash ; store it, using our RxBF routines
BRA.S StorData
@2 JmpRom backToPollDtain ; <patch> JUMP BACK TO ROM
;________________________________________________________________________
;
; Routine: RXIntHnd
;
; Arguments: A0 (input) -- chan A/B control read address
; A1 (input) -- chan A/B control write address
;
; Function: This routine handles SCC receiver interrupts for
; both channels; the data is read and stashed, IODone called
; if necessary.
; Patch: forBAP, get driver storage ptr from expanded mem
; get DCE ptr from UTable
NewRBIntHnd
move.l ExpandMem,a2 ; use ExpandMem instead of PortBVars
move.l ExpandMemRec.emSerdVars(a2),a2
movea.l UTableBase,a3 ; get .Bin DCE ptr in a3
movea.l BInDCEOffset(a3),a3
movea.l (a3),a3
MOVE.B SCCData(A0),D0 ; get the data byte from SCC
bra.s PS1
NewRAIntHnd LEA PortAVars,A3 ; get appropriate variables (chan A)
RXIntHnd MOVE.B SCCData(A0),D0 ; get the data byte
PollStash MOVE.L (A3)+,A2 ; get pointer to local variables
MOVE.L (A3),A3 ; and DCE pointer
PS1 AND.B CharMask(A2),D0 ; zero unused high bits <14Oct85>
MOVE.B PEChar(A2),D1 ; Are we translating PE Characters?
BEQ.S @1 ; No, just save the char.
CMP.B D1,D0 ; Is the new char a PEChar?
BNE.S @1 ; No, just do normal stuff
MOVE.B AltChar(A2),D0 ; Make sure that a good char <14Oct85>
; doesn't look like PEChar.
@1 TST.B SWHS(A2) ; software handshake enabled?
BEQ.S StashIt ; branch if not
CMP.B XONChar(A2),D0 ; was this an XON? <14Oct85>
BNE.S @2 ; <patch>
JmpRom ToContOut ; <patch> BEQ.S ContOut
@2 CMP.B XOFFChar(A2),D0 ; how about an XOFF? <14Oct85>
BNE.S StashIt ; if not, then stash the character
ST XOFFlag(A2) ; if so, then note it
BRA.S InputRTS ; and exit
; stash byte in the user's buffer if a request is pending, otherwise use our own
StashIt TST.B ReadCmd(A2) ; read request pending?
BEQ.S PutInOurBuf ; if there isn't one, stash it in ours
PutInUserBuf
MOVE.L A3,A1 ; get DCE pointer
PEA @1 ; <patch> BSR.S toStash
MOVE.L JStash,-(SP) ; <patch>
RTS ; <patch>
@1 BPL.S InputRTS ; if request isn't finished, just RTS
CLR.B ReadCmd(A2) ; no longer a read request pending
JmpRom ToGoodFinish ; <patch> BRA.S GoodFinish
PutInOurBuf
JsrRom ToGetBufRegs ; <patch> BSR GetBufRegs
MOVE.B D0,0(A3,D1.W) ; stash the byte
ADDQ.W #1,D1 ; update BufIndex
CMP.W D3,D1
BNE.S @1 ; br if not at the end
MOVEQ #0,D1 ; otherwise, reset to 0
@1 CMP.W D2,D1 ; hit the output index?
BNE.S @2 ; br if not
BSET #SoftOR,AsyncErr(A2); note the soft overrun
BRA.S InputRTS ; and exit without updating index
@2 MOVE.W D1,BufIndex(A2) ; update index
TST.W InSWHS(A2) ; XON/XOFF or DTR input flow control?<14Oct85>
BEQ.S InputRTS ; br if not
JsrRom ToGetBufCnt ; <patch> BSR.S GetBufCnt
SUB.W D0,D3 ; bytes to top
CMP.W BufHigh(A2),D3 ; past the max limit?
BCC.S InputRTS ; exit if not
TST.B InHWHS(A2) ; input DTR flow control? <14Oct85>
BNE.S @4 ; <patch>
JmpRom ToCtlXOff ; <patch> BEQ.S CtlXOff
@4 BSET #6,FlowOff(A2) ; have we negated DTR? <14Oct85>
BEQ.S @3 ; <patch>
JmpRom ToPut ; <patch> HERE'S THE ONE LINE THAT CHANGED - BNE.S @3
@3 JmpRom backToPut ; <patch> JUMP BACK TO ROM
InputRTS RTS ; <patch>
;________________________________________________________________________
;
; Routine: SCIntHnd
;
; Arguments: A0 (input) -- channel A/B control read address
; A1 (input) -- channel A/B control write address
;
; Function: This routine handles SCC special condition interrupts:
; these occur when an input character is received that has
; a parity error, framing error, or causes an overrun.
; If the option is set to abort on the error, the character
; is discarded and the input request (if any) aborted; otherwise,
; the error is noted and the character buffered as usual.
; Patch: forBAP, get driver storage ptr from expanded mem
; get DCE ptr from UTable
NewSCBIntHnd
move.l ExpandMem,a3 ; use ExpandMem instead of PortBVars
move.l ExpandMemRec.emSerdVars(a3),a2
movea.l UTableBase,a3 ; get .Bin DCE ptr in a3
movea.l BInDCEOffset(a3),a3
movea.l (a3),a3
bra.s SC1 ; and branch around port a code
NewSCAIntHnd
LEA PortAVars,A3 ; get appropriate variables (chan A)
SCIntHnd
MOVE.L (A3)+,A2 ; get local variables pointer
MOVE.L (A3),A3 ; and DCE pointer (delay, too)
SC1 MOVE.B #1,(A1) ; point to error reg
MOVE.B (A0),D1 ; read the error condition
MOVEQ #$70,D3 ; form $70 mask
AND.B D3,D1 ; isolate error bits
OR.B D1,AsyncErr(A2) ; accumulate errors (delay, too)
MOVE.B SCCData(A0),D0 ; get the data byte
AND.B CharMask(A2),D0 ; zero unused high-order bits <14Oct85>
MOVE.B Options(A2),D2 ; get abort options
AND.B D1,D2 ; should we abort?
MOVE.B #$30,(A1) ; reset the error flag
AND.B D3,D2
BNE.S @2 ; br if we should abort . . .
MOVE.B PEChar(A2),D3 ; alternate char for parity errors?
BEQ.S @1 ; br if not
CMP.B D0,D3 ; Is the incoming char equal to the PEChar?
BNE.S @0 ; No, no substitution needed.
MOVE.B AltChar(A2),D0 ; Make sure that a good char <14Oct85>
; doesn't look like PEChar.
@0 BTST #4,D1 ; parity error?
BEQ.S @1 ; br if not
MOVE.B D3,D0 ; replace it
@1 BRA StashIt ; go stash it . . .
@2 TST.B ReadCmd(A2) ; if we have no pending read command
BEQ.S InputRTS ; then just discard the character
MOVEQ #RcvrErr,D0 ; otherwise, note the error
JmpRom ToRdReqDone ; <patch> JUMP BACK TO ROM
;________________________________________________________________________
;
; Routine: TBIntHnd
; for BAP
; Get the variables ptr from expand mem for the interrupt handlers
;
NewTBIntHnd
move.l ExpandMem,a2 ; use ExpandMem instead of PortBVars
move.l ExpandMemRec.emSerdVars(a2),a2
JmpRom backToTXIntHnd ; back to ROM
;________________________________________________________________________
;
; Routine: ExtIntHnd
; for BAP
; Get the variables ptr from expand mem for the interrupt handlers
; Get input DCE ptr from the Unit Table
;
; -- patch to set bit 3 in AsyncErr (had to patch in ALL code before).
; -- also fix the RdReqDone problem
NewExtBIntHnd
move.l ExpandMem,a3 ; use ExpandMem instead of PortBVars
move.l ExpandMemRec.emSerdVars(a3),a2
movea.l UTableBase,a3 ; get .BIn DCE ptr in a3
movea.l 28(a3),a3
movea.l (a3),a3
bra.s ExtIntHnd
NewExtAIntHnd
LEA PortAVars,A3 ; get appropriate variables - chan A
MOVE.L (A3)+,A2 ; get pointer to local variables
MOVE.L (A3),A3 ; get .AIn DCE ptr in a3
ExtIntHnd
MOVE.B D1,D2 ; changed bits
AND.B postOptions(A2),D2 ; post this change?
BEQ.S @0 ; br if not
MOVEM.L D0/A0,-(SP) ; preserve these registers
MOVE.W #IODrvrEvt,A0
ASL.W #8,D0 ; make room for 'changed' values
MOVE.B D1,D0
SWAP D0 ; make room for input driver refnum
MOVE.W DCtlRefnum(A3),D0
_PostEvent ; and post the event
MOVEM.L (SP)+,D0/A0
@0 TST.B D1 ; see if it's a change in break status
BMI.S extBreak ; branch if it was a break interrupt
LSL.B #2,D0 ; must be CTS change
SMI CTSFlag(A2) ; set flags according to CTS
; This piece of code is used to detect a clock into the HWHS line
; and shut off the ext/sts interrupt for the handshake line.
CMP.W #80,HSCount(A2) ; exceeded 80 transitions in 16 MS? <14Oct85>
BCS.S @2 ; br if not <14Oct85>
MOVEQ #-128,D0 ; ($80) leave break ints enabled <14Oct85>
MOVEQ #15,D1 ; write register 15 <14Oct85>
jsrROM ToCtlSet ; <patch>
@2 MOVE.L Ticks,D2 ; get current tick time <14Oct85>
CMP.L LastTime(A2),D2 ; same as last? <14Oct85>
BEQ.S @3 ; br if so <14Oct85>
MOVE.L D2,LastTime(A2) ; new last time <14Oct85>
CLR.W HSCount(A2) ; restart count for new time <14Oct85>
@3 ADDQ #1,HSCount(A2) ; update count <14Oct85>
jmpROM toContOut1 ;<patch> BRA ContOut1--if freshly asserted, continue output<14Oct85>
extBreak TST.B D0 ; check break level
BMI.S @1 ; if it's asserted, terminate any input
MOVE.B SCCData(A0),D0 ; otherwise (end of break), discard null
@done RTS ; and return <2.5>
@1 MOVEQ #BreakRecd,D0 ; note the break
bset.b #3,AsyncErr(a2) ; we now note break level in status <80>
TST.B ReadCmd(A2) ; read request pending?
BEQ.S @done ; no, then just return <2.5>
jmpROM ToRdReqDone ; a3 has input DCE ptr
;_______________________________________________________________________ <81>
;
; Patched Driver headers (with signature long word before each header)
;
DC.b 'wong' ; our personal signature
AsyncAIn
DC.W $4D00 ; read, control, status, lock
DC.W 0,0 ; not an ornament
DC.W 0 ; no menu
DC.W AInOpen-AsyncAIn ; Initialization routine
DC.W AInPrime-AsyncAIn ; input Prime routine
DC.W AControl-AsyncAIn ; shared Control routine
DC.W AStatus-AsyncAIn ; shared Status routine
DC.W AInClose-AsyncAIn ; Close routine
DC.B 4 ; channel A input driver
DC.B '.AIn '
DC.b 'wong' ; our personal signature
AsyncAOut
DC.W $4E00 ; write, control, status, lock
DC.W 0,0 ; not an ornament
DC.W 0 ; no menu
DC.W AOutOpen-AsyncAOut ; Initialization routine
DC.W AOutPrime-AsyncAOut ; output Prime routine
DC.W AControl-AsyncAOut ; shared Control routine
DC.W AStatus-AsyncAOut ; shared Status routine
DC.W AOutClose-AsyncAOut ; Close routine
DC.B 5 ; channel A output driver
DC.B '.AOut'
DC.b 'wong' ; our personal signature
AsyncBIn
DC.W $4D00 ; read, control, status, lock
DC.W 0,0 ; not an ornament
DC.W 0 ; no menu
DC.W BInOpen-AsyncBIn ; Initialization routine
DC.W BInPrime-AsyncBIn ; input Prime routine
DC.W BControl-AsyncBIn ; shared Control routine
DC.W BStatus-AsyncBIn ; shared Status routine
DC.W BInClose-AsyncBIn ; Close routine
DC.B 4 ; channel B input driver
DC.B '.BIn '
DC.b 'wong' ; our personal signature
AsyncBOut
DC.W $4E00 ; write, control, status, lock
DC.W 0,0 ; not an ornament
DC.W 0 ; no menu
DC.W BOutOpen-AsyncBOut ; Initialization routine
DC.W BOutPrime-AsyncBOut ; output Prime routine
DC.W BControl-AsyncBOut ; shared Control routine
DC.W BStatus-AsyncBOut ; shared Status routine
DC.W BOutClose-AsyncBOut ; Close routine
DC.B 5 ; channel B output driver
DC.B '.BOut'
;_______________________________________________________________________ <81>
;
; jumping to ROM from our patched entry points
;
AInOpen jmpROM ROM_AInEntryOpen ;port a
AInClose jmpROM ROM_AInEntryClose
AInPrime jmpROM ROM_AInEntryPrime
AOutOpen jmpROM ROM_AOutEntryOpen
AOutClose jmpROM ROM_AOutEntryClose
AOutPrime jmpROM ROM_AOutEntryPrime
AControl jmpROM ROM_AEntryControl
AStatus jmpROM ROM_AEntryStatus
BInOpen JmpRom backToBInOpenStart ;port b
BOutOpen JmpRom backToBOutOpenStart
BInClose
moveq #0,d0 ; shorter to return than to jump to ROM
rts
BOutClose
JmpRom ToBOutClose ; don't need to screw with this other than
; patch above
BInPrime
move.l ExpandMem,a2 ; use ExpandMem instead of PortBVars
move.l ExpandMemRec.emSerdVars(a2),a2 ;
JmpRom backToBInPrime ; location to return to BInPrime
BOutPrime
move.l ExpandMem,a2 ; use ExpandMem instead of PortBVars
move.l ExpandMemRec.emSerdVars(a2),a2 ;
JmpRom backToBOutPrime ; location to return to BOutPrime
BControl
move.l ExpandMem,a2 ; use ExpandMem instead of PortBVars
move.l ExpandMemRec.emSerdVars(a2),a2 ;
JmpRom backToBControl ; location to return to BControl
BStatus
move.l ExpandMem,a2 ; use ExpandMem instead of PortBVars
move.l ExpandMemRec.emSerdVars(a2),a2 ;
JmpRom backToBStatus ; location to return to BStatus
;
; End of Async.a Patch <48><80><81>
;_____________________________________________________________________________________________
;____________________________________________________________________________________
; PB435 InitWindows
; PB438 InitWindows
; PB482 InitWindows
;
; This pair of patches correct an incorrect use of the DeskCPat lo-mem. Previously, I
; was overwriting the lo-mem pattern handle. Now, if it is a handle, I do a DisposPixPat
; first. And the system heap is safe for mankind once again.
;
; Removed patch to GetPixPat, and fixed it in InitWindows instead.
;
; Moved DeskCPat back to the system heap. Tested and used existing DeskCPat, if present.
MySetDeskCPat PROC EXPORT
SDCP1 EQU $10816
SDCP2 EQU $1082A
TST.L 4(SP) ; is the newPatt NIL?
BEQ.S @TurnOff ; yes, so switch back to binary <C666/22Jan87> DAF
MOVE.L DeskCPat,D1 ; get the pattern handle <PB435>
BEQ.S @1 ; if NIL then continue <PB435>
CMP.L MinusOne,D1 ; if uninitialized then continue <PB435>
BEQ.S @1 ; <PB435>
MOVE.L D1,-(SP) ; push the current pathandle <PB435>
_DisposPixPat ; flush old one <PB435>
@1 MOVE.L 4(SP),DeskCPat ; set it <C666/22Jan87> DAF
JMPRom SDCP1 ; continue in ROM <PB435>
@TurnOff JMPRom SDCP2 ; binary pat continue in ROM <PB435>
myInitWindows PROC EXPORT
IW1 EQU $F88E ; ROM returns here
; Stack Frame definition ; <C203> DAF
LocalVar EQU 0 ; stack frame eliminated <C491/08Dec86> DAF
; Added patches: cancel pending PaintBehind; reset alarm parity; and say
; that the window world exists. <EHB 1/23/85>
MOVEQ #7,D0 ; handy bit number <EHB 1/23/85>
BSET D0,DSWndUpdate ; cancel pending PaintBehind <EHB 1/23/85>
BSET D0,AlarmState ; reset alarm parity <EHB 1/23/85>
CLR.B WWExist ; say the window world exists <EHB 1/23/85>
MOVE.L MinusOne,SaveUpdate ;enable update accumulation and erasing
; set up the deskPattern from Sys.resource
SUBQ #4,SP ;make room for function result
MOVE #deskPatID,-(SP) ;push pattern ID of deskPattern
_GetPattern ;tell resource manager to get it
MOVE.L (SP)+,A0 ;get the pattern handle
MOVE.L (A0),A0 ;get pattern pointer
MOVE.L (A0)+,DeskPattern ;init the deskPattern
MOVE.L (A0),DeskPattern+4 ;don't forget 2nd half of it
; load the DeskCPat from the system if pCDeskPat enabled. The MPW Shell is has its own
; special memory management calls in the app zone, so we do this on the system zone to
; avoid conflicts. We need the cooperation of the Control Panel to keep the pattern in
; the correct zone.
TST.B pCDeskPat ; test flag <C725/31Jan87 DAF>
BPL.S @12 ; if hi bit clear, don't load ppat <C725/31Jan87 DAF>
MOVE.L DeskCPat,D0 ; get the deskCPat to see if it's already present <PB482/27Apr88> DAF
BEQ.S @10 ; if NIL, then load the pat <PB482/27Apr88> DAF
CMP.L MinusOne,D0 ; is it minus one? <PB482/27Apr88> DAF
BNE.S @12 ; if not, then use the existing one <PB482/27Apr88> DAF
@10
MOVE.L theZone,-(SP) ; save the current zone <PB482/27Apr88> DAF
MOVE.L sysZone,theZone ; switch to the system zone <PB482/27Apr88> DAF
SUBQ #4,SP ; make room for function result
MOVE #deskPatID,-(SP) ; push pattern ID of deskCPat
_GetPixPat ; tell resource manager to get it from system
MOVE.L (SP)+,DeskCPat ; put handle to pattern in lomem, overwriting invalid previous pixPat
BNE.S @11 ; if not present, use binary pat <C725/31Jan87 DAF>
BCLR #7,pCDeskPat ; clear the cDeskPat bit <C725/31Jan87 DAF>
@11 MOVE.L (SP)+,theZone ; restore the current zone <PB482/27Apr88> DAF
@12
PEA @initwinTail ; 'return address', for tailpatch <dvb> 4.3
LINK A6,#LocalVar ; make a stack frame <C203> DAF
; BEWARE!! - MacII saves more registers than MacSE, MacPlus !!
MOVEM.L D3-D7/A3-A4,-(SP) ;save work registers
JMPRom IW1 ; return to ROM
@initwinTail _InitPalettes ; <dvb> 4.3
RTS
;____________________________________________________________________________________
; PB512 -- UpdAltMDB patch
;
; This patch fixes a problem that occurs when an HFS alternate MDB is to be
; updated on a SuperDrive 1440k floppy. The problem occurs due to the way
; the routine UpdAltMDB determines the size of a floppy disk. The driver
; for the SuperDrive implements a Status call that returns a drive size list.
; We attempt to use this Status call, and if it fails, default to the old
; way of determining drive size (1-sided, 2-sided flag in the DQE).
;
; Due to the fact that the UpdAltMDB routine is not vectored, this patch
; dynamically patches out GetBlock for the duration of all calls to ExtBTFile
; so that GetBlock checks for a call from within the UpdAltMDB routine.
; If detected, the above method of determining disk size is employed
; and the result placed in register D2, where it is later used to
; read/write the alternate MDB. Afterwards, the GetBlock "come-from"
; patch is undone until the next instance of a call to ExtBTFile.
;
; PB512 24Jun88 JB Added patch to fix UpdAltMDB to use correct disk address
; on 1440k disks
; PB549 27Jul88 JB Modified to not make 'Get Format List' Status call unless
; doing so to the Sony driver. Fixes problems with 3rd party
; disks that either die, return garbage, or ignore CSCode
; altogether. Hope this can change someday...
; 29Oct90 KST Added a counter so that we will not overwrite jGetBlock
; when this patch is reentered.
;____________________________________________________________________________________
AltMDBPatch PROC
EXPORT MyExtBTF,svExtBTFile,svExtBTCounter
;
; Format List record returned by the SuperDrive version of the Sony Driver
;
; One record per possible drive configuration is returned on a
; Status call with csCode = 6. The entry with bit 6 in flflags set
; is the 'current disk' configuration and is the entry used to
; determine drive size.
;
FmtLstRec record 0 ;
frsize ds.l 1 ; Disk size in BYTES
frflags ds.b 1 ; flags
frspt ds.b 1 ; sectors per track
frtracks ds.w 1 ; total # of tracks
flrecsize equ * ; size of the format list record
endr
FmtLstCode equ 6 ; CSCode value for 'Get Format List' Status call
NFRecs equ 16 ; max # of FmtLstRec to allocate on the stack
;
; Save cells for some vectors:
;
svExtBTFile ds.l 1
svGetBlock ds.l 1
svExtBTCounter ds.w 1 ; counter flag initialized to $ffff <25Sep90>
;
; "Come from" address for call to GetBlock out of the
; UpdAltMDB routine:
;
fromUAMDB EQU $4080c648 ; SE=$408b84, MacII=$4080c648
MyExtBTF
;
; Install our GetBlock patch for the duration of this
; ExtBTFile call...
;
lea svExtBTCounter,a0 ; get the counter <25Sep90>
add.w #1,(a0) ; incr by one <25Sep90>
bgt.s @skip ; re-entered <25Sep90>
lea svGetBlock,a0 ; Install our GetBlock filter
move.l JGetBlock,(a0) ; ...for the duration of
lea MyGetBlock,a0 ; ...the call to ExtBTFile
move.l a0,JGetBlock ; We now "see" all GetBlock calls...
;
; Call the real ExtBTFile routine
;
@skip
move.l (sp)+,-(a6) ; Save async return address
pea @0 ; Where the real ExtBTFile will return...
move.l svExtBTFile,-(sp) ; Fake a JSR to the real ExtBTFile
rts
@0
;
; After calling ExtBTFile, undo the temporary patch to GetBlock...
;
lea svExtBTCounter,a0 ; get the counter <25Sep90>
sub.w #1,(a0) ; decr by one <25Sep90>
bpl.s @10 ; don't undo yet, we're nested now <25Sep90>
lea svGetBlock,a0 ; Restore the real GetBlock routine
move.l (a0),JGetBlock ; ...vector (ROM **or** RAM Cache)
@10
move.l (a6)+,-(sp) ; Restore our return addr
tst.w d0 ; Set condition codes
rts ; ...bye
;__________________________________________________________________
; This is where the real work is done. If this GetBlock filter
; catches a call from within the UpdAltMDB routine, we fudge the
; contents of D2, which is the block address of the alternate MDB.
;__________________________________________________________________
MyGetBlock
cmp.l #fromUAMDB,(sp) ; Call from within UpdAltMDB?
bne doGetBlock ; No, just do the old GetBlock...
;
; Get here on the call to GetBlock that we are looking for.
; Determine the real size of the disk and update D2 appropriately.
;
WITH FmtLstRec
movem.l a0/a2/d0/d1,-(sp) ; Save what we use...
;
; Try the Sony Driver control call to attempt to discover
; drive size. If it fails, revert to the old assumptions...
;
sub.w #NFRecs*flrecsize,sp ; Make space for the format records
move.l sp,a2 ; Save format record buffer address
;
; Push an ioparamblk on the stack
;
moveq #(ioQElSize+1)/2-1,d0 ;
@1 clr.w -(sp) ;
dbf d0,@1 ;
move.l sp,a0 ; Parameter block address
; Check here for Sony driver because 3rd party disk drivers don't <JB/27Jul88>
; correctly support _Status calls. Some don't even check the value <JB/27Jul88>
; of the CSCode parameter!!! For now, don't call any driver except <JB/27Jul88>
; our own Sony driver. Maybe someday we'll get all drivers to support <JB/27Jul88>
; the 'Format List' status call... <JB/27Jul88>
moveq #0,d2 ; Vol size in 512-byte blocks if not a Sony <JB/27Jul88>
move.w dQDrvSz(a3),d2 ; <JB/27Jul88>
cmp.w #dskRfN,dQRefNum(a3) ; Is this a Sony drive? <JB/27Jul88>
bne.s ckVersn ; Skip Status call if not, check DQE version...<JB/27Jul88>
move.w dQDrive(a3),ioVRefNum(a0) ; drive number
move.w dQRefNum(a3),ioRefNum(a0) ; driver refnum
move.w #FmtLstCode,csCode(a0) ; Opcode for 'Return Format List'
move.w #NFRecs,csParam(a0) ; max number of format records to return
move.l a2,csParam+2(a0) ; ptr to place to return format records
_Status ; Ask driver for drive sizes
bne.s guessiz ; If any error, guess the size...
;
; Scan the returned list of format records for the entry which
; describes the 'current disk'.
;
move.w csParam(a0),d0 ; Number of format entries returned
beq.s guessiz ; Go guess if driver returned zilch...
sub.w #1,d0 ; ...for DBF loop
@2
btst #6,frflags(a2) ; Is this entry for the 'current disk'
bne.s @3 ; Xfer if so...
add.w #flrecsize,a2 ; Else, point to next record
dbf d0,@2 ; ...and try again
bra.s guessiz ; No 'current disk' found, go guess...
@3
move.l frsize(a2),d2 ; Get drive size in BLOCKS
bra.s GVSzExit ; And return...
;
; Attempt to determine the drive size by looking at the
; drive queue element. This method used for any driver not
; supporting the control call.
;
guessiz:
move.w #800,d2 ; assume single-sided sony
tst.b dQDrvSz(a3) ; TwoSideFmt?
beq.s @1 ; br if not
add.l d2,d2 ; two-sided, double size
@1
ckVersn:
tst.w qType(a3) ; new version element?
beq.s GVSzExit ; br if not
move.l dQDrvSz(a3),d2 ; it's a long in the new world
swap d2 ; but swapped for compatibility
GVSzExit
add.w #ioQElSize+(NFRecs*flrecsize),sp ; Discard stuff on the stack
movem.l (sp)+,a0/a2/d0/d1 ; Restore scratch registers
ENDWITH
subq #2,d2 ; Convert disk size in blocks to alt MDB address
;__________________________________________________________________
; Do the actual GetBlock call -- D2 adjusted, if necessary
;__________________________________________________________________
doGetBlock
move.l svGetBlock,-(sp) ; Continue in the real GetBlock...
rts
ENDPROC ; **** End of AltMDBPatch patch ****
;____________________________________________________________________________________
; PB531 12Jul88 DAF DrawII Sucks Bug
;
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 12Jul88 #PB531 (PaintRect) (PaintRect)
;AppleSystemPatch PatchIIROM.a 12Jul88 #PB531 (FrameRect) (FrameRect)
;
; Draw II (released version) does a VERY BAD thing. It records multiple versions of objects
; in PICTs using a bunch of invalid transfer modes and side effects to prevent certain
; objects from showing up on the LaserWriter or screen. Stretch no-op's on invalid penmodes
; but bitBlt doesn't so, you get garbage on the screen (garbage in, garbage out). These
; patches on FrameRect and PaintRect no-op if the penmode is invalid. Gross. We shouldn't
; fix this, but I'm sure we'll get even.
;
MyPaintRect PROC EXPORT
ROMPaintRect EQU $1D398 ;
MOVE.L grafGlobals(A5),A0 ; get pointer to grafGlobs
MOVE.L thePort(A0),A0 ; look at thePort
CMP.W #16,pnMode(A0) ; is it greater than 16?
BLT.S @OTay ; nope
CMP.W #31,pnMode(A0) ; is it less then 31?
BGT.S @OTay ; nope
MOVE.L (SP)+,A0 ; get the result
ADDQ #4,SP ; pitch the rect
JMP (A0) ; and return to app
@OTay JMPROM ROMPaintRect ; continue with PaintRect
MyFrameRect PROC EXPORT
ROMFrameRect EQU $1D394 ;
MOVE.L grafGlobals(A5),A0 ; get pointer to grafGlobs
MOVE.L thePort(A0),A0 ; look at thePort
CMP.W #16,pnMode(A0) ; is it greater than 16?
BLT.S @OTay ; nope
CMP.W #31,pnMode(A0) ; is it less then 31?
BGT.S @OTay ; nope
MOVE.L (SP)+,A0 ; get the result
ADDQ #4,SP ; pitch the rect
JMP (A0) ; and return to app
@OTay JMPROM ROMFrameRect ; continue with FrameRect
;____________________________________________________________________________________
; PB546 26Jul88 DAF ShowCursor Patch
;
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 12Jul88 #PB546 (jShowCursor) (jShowCursor)
;
; A vestige of the MacPlus ShowCursor code was it's calculation of save space (whether the cursor
; could be saved in one long word or not). This calculation assumes that pixelsize is 1, which
; obviously isn't the case. The result was that too large of a save space was sometimes allocated
; and could cause bytes that are just past the right edge of the screen to get trashed. BlackJack
; leaves no free bytes between rows, and as a result, the left edge of the screen can get trashed.
; This patch, by BAL, corrects the save space calculation.
;
;_______________________________________________________________________
;
; SHOWCURSOR - Called from CrsrVBLTask and via Jump Table.
;
; Adds 1 to CRSRSTATE and paints cursor if zero and cursor is
; not already visible.
;
MYSHOWCURSOR PROC EXPORT
ToShowCrsr EQU $1ADC2
ShftTbl EQU $1EC92
ExTbl EQU $22C16
DoneShow EQU $1AE26
MOVE.B #1,CRSRBUSY ;MARK CHANGE IN PROGRESS
TST.L CRSRPTR ;CURSOR ALLOCATED?
BMI.S DONEHIDE ;=>NO, JUST RETURN
ADDQ #1,CRSRSTATE ;CURSOR HIDDEN ONE LESS DEEP
BLT.S DONEHIDE ;QUIT IF STILL HIDDEN
CLR CRSRSTATE ;DON'T LET CRSRSTATE GET > 0
TST.B CRSRVIS ;IS CURSOR ALREADY VISIBLE?
BEQ DoPatch ;no, so do the redraw
DONEHIDE
CLR.B CrsrBusy ;all done
RTS
DoPatch
MOVEM.L D0-D7/A0-A6,-(SP) ;SAVE REGISTERS
LEA THECRSR+DATA,A2 ;POINT TO THE CURSOR
;-----------------------------------------------
;
; CONVERT CHUNKY DEPTH TO SHIFT AMOUNT IN D7
;
LEAROM SHFTTBL,A0 ;TO CONVERT DEPTH TO SHIFT
MOVE CHUNKYDEPTH,D1 ;GET DEPTH
MOVEQ #0,D7 ;DEFAULT SHIFT = 0
MOVE.B 0(A0,D1),D7 ;GET SHIFT AMOUNT IN D7
;-----------------------------------------------
;
; CHECK THE CURSOR TO SEE IF IT HAS CHANGED
; OLD CURSORS: CHECK CURSOR DATA AND DEPTH
; NEW CURSORS: CHECK DEPTH
;
GOTSHFT MOVE.L ([CRSRPTR]),A4 ;GET POINTER TO CURSOR DATA (LOCKED)
CMP #CCRSRPAT,CCTYPE(A4) ;IS IT A COLOR CURSOR?
BNE.S OLDCUR ;=>NO, JUST AN OLD ONE
CMP CCDEPTH(A4),D1 ;HAS DEPTH CHANGED?
BEQ NOEXPAND ;=>NO, DON'T EXPAND
CMP #2,D1 ;IS DEPTH 2 or 1?
BGT.S EXPMASK ;=>NO, JUST EXPAND MASK
BRA.S CPYDATA ;=>ELSE JUST COPY DATA
OLDCUR LEA CCLASTCRSR(A4),A0 ;POINT TO SAVED DATA
MOVE.L A2,A1 ;GET POINTER TO CURSOR
MOVEQ #7,D0 ;CHECK 8 LONGS
@0 CMP.L (A0)+,(A1)+ ;ARE THEY THE SAME?
BNE.S GOEXPAND ;=>NO, EXPAND IT
DBRA D0,@0 ;=>LOOP UNTIL DONE
CMP CCDEPTH(A4),D1 ;HAS DEPTH CHANGED?
BEQ.S NOEXPAND ;=>NO, DON'T EXPAND
GOEXPAND
;-----------------------------------------------
;
; INVALIDATE EXPANDED DATA FOR EACH DEVICE BY CLEARING DEPTH
; THIS MUST BE DONE SO THAT ALL EXPANDED CURSOR IMAGES ARE RENDERED INVALID AFTER
; AN OLD CURSOR HAS BEEN SET. IF THE CURSOR IS NEW, SETCCURSOR ALREADY DID THIS.
MOVE.L DEVICELIST,A0 ;GET FIRST HANDLE IN DEVICE LIST
NXTGD MOVE.L (A0),A0 ;POINT TO FIRST DEVICE
TST GDFLAGS(A0) ;IS IT ACTIVE?
BPL.S NOTACT ;=>NO, SKIP TO NEXT
CLR GDCCDEPTH(A0) ;ELSE INVALIDATE EXPANDED DATA
NOTACT MOVE.L GDNEXTGD(A0),D0 ;GET NEXT GRAFDEVICE
MOVE.L D0,A0 ;GET INTO A0
BNE.S NXTGD ;=>REPEAT FOR ALL DEVICES
; COPY THE CURSOR DATA TO IDENTIFY THIS CURSOR
CPYDATA LEA CCLASTCRSR(A4),A0 ;POINT TO SAVED DATA
MOVE.L A2,A1 ;GET CURSOR
MOVEQ #7,D0 ;MOVE 8 LONGS
@0 MOVE.L (A1)+,(A0)+ ;MOVE A LONG
DBRA D0,@0 ;=>LOOP UNTIL DONE
; UPDATE THE ROWBYTES AND DEPTH FOR THE EXPANDED DATA
MOVE D1,(A0)+ ;COPY THE DEPTH TOO
MOVE D1,CCDEPTH(A4) ;SET DEPTH TO SAY IT'S EXPANDED
ADD D1,D1 ;DOUBLE FOR CURSOR'S ROWBYTES
MOVE D1,CCBYTES(A4) ;AND UPDATE ROWBYTES
;-----------------------------------------------
;
; EXPAND THE CURSOR TO THE CURRENT DEPTH
;
MOVE.L A2,A0 ;SRC = CURSOR
MOVE.L ([CCXDATA,A4]),A1 ;POINT TO EXPANDED DATA (LOCKED)
MOVE.L A1,A2 ;GET START OF DST BUFFER
MOVE #32,D5 ;GET #BYTES OF SOURCE
LSL D7,D5 ;MULTIPLY BY DEPTH
ADD D5,A2 ;POINT TO END OF BUFFER
LEARom EXTBL,A3 ;POINT TO ROUTINE TABLE
ADD 0(A3,D7*2),A3 ;USE DEPTH TO SELECT ROUTINE
MOVEQ #0,D0 ;CLEAR HIGH PART OF D0
JSR (A3) ;EXPAND 32*DEPTH BYTES
;-----------------------------------------------
;
; EXPAND THE MASK TO THE CURRENT DEPTH
;
EXPMASK LEA THECRSR+MASK,A0 ;SRC = CURSOR MASK
MOVE.L ([CCXMASK,A4]),A1 ;POINT TO EXPANDED MASK (LOCKED)
MOVE.L A1,A2 ;GET START OF DST BUFFER
ADD D5,A2 ;POINT TO END OF BUFFER
LEARom EXTBL,A3 ;POINT TO ROUTINE TABLE
ADD 0(A3,D7*2),A3 ;USE DEPTH TO SELECT ROUTINE
MOVEQ #0,D0 ;CLEAR HIGH PART OF D0
JSR (A3) ;EXPAND 32*DEPTH BYTES
;-----------------------------------------------
;
; PREPARE TO BLT THE CURSOR ON THE SCREEN IN ANY DEPTH
; (SUBTITLE: WALTZ OF THE REGISTERS)
;
NOEXPAND MOVE.L ([CCXDATA,A4]),A2 ;A2 = EXPANDED DATA FOR BLT (LOCKED)
MOVE.L ([CCXMASK,A4]),A3 ;A3 = EXPANDED MASK FOR BLT (LOCKED)
MOVEQ #16,D5 ;D5 = 16
;-----------------------------------------------
;
; CLIP THE CURSOR VERTICALLY AND GET THE TOP AND BOTTOM INTO D2 AND D3.
; IF THE TOP IS CLIPPED, UPDATE THE DATA BASE ADDRESSES IN A2 AND A3.
;
MOVE MOUSE+V,D2 ;MOUSE POSITION Y
SUB CRSRPIN+TOP,D2 ;CONVERT TO SCREEN LOCAL COORDS
SUB THECRSR+HOTSPOT+V,D2 ; - HOTSPOT = TOP EDGE
MOVE D2,D3 ;GET CURSOR BOTTOM
ADD D5,D3 ; = TOP + 16
CMP D5,D3 ;AT TOP?
BGE.S CHKBOT ;=>NOT AT TOP
NEG D2 ;GET NUMBER OF CLIPPED ROWS
CMP D5,D2 ;ARE ALL 16 CLIPPED?
BNE.S notClip ; if not, then continue
ShowDown ; <PB560 09Aug88 BAL>
JMPROM DONESHOW ;=>IF SO, NOTHING TO SHOW
notClip MULU CCBYTES(A4),D2 ; * ROWBYTES FOR OFFSET
ADD.L D2,A2 ;ADD VERTICAL OFFSET INTO CURSOR
ADD.L D2,A3 ;ADD VERTICAL OFFSET INTO MASK
MOVEQ #0,D2 ;AND PIN CURSOR TO TOP
CHKBOT MOVE COLLINES,D4 ;GET BOTTOM OF SCREEN
CMP D4,D3 ;PAST BOTTOM?
BLE.S CHKLFT ;=>NO, VERTICAL OK
MOVE D4,D3 ;ELSE PIN TO BOTTOM EDGE
;-----------------------------------------------
;
; CLIP THE CURSOR HORIZONTALLY AND GET THE LEFT AND RIGHT INTO D0 AND D1
; IF THE LEFT OF THE CURSOR IS CLIPPED, ADJUST THE OFFET IN D6.
CHKLFT MOVEQ #0,D6 ;INIT SRC/DST OFFSET TO 0
MOVE MOUSE+H,D0 ;MOUSE POSITION X
SUB CRSRPIN+LEFT,D0 ;CONVERT TO SCREEN LOCAL COORDS
SUB THECRSR+HOTSPOT+H,D0 ; - HOTSPOT = CURSOR LEFT
MOVE D0,D1 ;GET CURSOR RIGHT
ADD D5,D1 ; = LEFT + 16
CMP D5,D1 ;AT LEFT EDGE?
BGE.S CHKRT ;=>NOT AT LEFT EDGE
SUB D0,D6 ;OFFSET = AMOUNT CLIPPED
MOVEQ #0,D0 ;AND PIN TO LEFT EDGE
CHKRT MOVE ROWBITS,D4 ;GET RIGHT EDGE OF SCREEN
CMP D4,D1 ;PAST RIGHT EDGE?
BLE.S RTOK ;=>NO, HORIZONTAL OK
MOVE D4,D1 ;ELSE PIN TO RIGHT EDGE
RTOK
;-----------------------------------------------
;
; USE TOP AND LEFT TO CALCULATE THE LONG ALIGNED SCREEN BASE ADDRESS
MOVE.L CRSRBASE,A5 ;A5 = POINTER TO BASE OF SCREEN
MOVE CRSRROW,A0 ;A0 = SCREEN ROWBYTES
MOVE A0,D4 ;COPY FOR MULU
MULU D2,D4 ;TOP * ROWBYTES
ADD.L D4,A5 ;ADD VERT OFFSET INTO SCREEN
LSL D7,D0 ;CONVERT LEFT PIXELS TO BITS
MOVE D0,D4 ;GET LEFT EDGE
AND #$FFE0,D4 ;LONGWORD ALIGNED
MOVE D4,D5 ;MAKE A COPY
ASR #3,D5 ;CONVERT BITS TO BYTES
ADD D5,A5 ;GET BASE OFFSET IN SCREEN
;-----------------------------------------------
;
; SAVE THE CRSRRECT FOR CURSHIELD
LEA CrsrRect,A1 ;SET UP CRSRRECT
MOVE D2,(A1)+ ;TOP
MOVE D4,D5 ;GET LONG ALIGNED LEFT IN BITS
LSR D7,D5 ;CONVERT TO PIXELS
MOVE D5,(A1)+ ;LONG ALIGNED LEFT
MOVE D3,(A1)+ ;BOTTOM
MOVE D5,(A1) ;RIGHT = LEFT + 32 OR 64
; ADD #32,(A1) ;ASSUME RIGHT,LEFT IN SAME LONG
; EOR D1,D5 ;TURN OFF COMMON BITS
; AND #$FFE0,D5 ;IGNORE LOW 32
; BEQ.S SAMELONG ;=>NOT IN SAME LONG
; ADD #32,(A1) ;ELSE BUMP RIGHT
SAMELONG
;-----------------------------------------------
;
; ADJUST DST/SRC OFFSET IN D6
; GET NUMBER OF ROWS TO DO IN D3
; GET LONGCNT IN D5 AND USE TO ADJUST DSTBUMP IN A0
AND #$1F,D0 ;GET LEFT EDGE MOD 32
LSL D7,D6 ;CONVERT OFFSET TO BITS
SUB D0,D6 ; = NEG OFFSET FROM SOURCE
LSL D7,D1 ;CONVERT RIGHT EDGE TO BITS
MOVE D1,D5 ;MAKE COPY
SUB D4,D5 ;GET WIDTH OF CURSOR
ble.s ShowDown ;bit width <=0, so nothing to draw <PB560 09Aug88 BAL>
subq #1,d5 ;force multiples of 32 to round down
LSR #5,D5 ;GET LONGS-1
SUB D2,D3 ;D3 = # ROWS TO DO
SUBQ #1,D3 ;MAKE IT 0 BASED
MOVE D5,D2 ;GET LONGS
ADDQ #1,D2 ;MAKE ONE BASED
LSL #2,D2 ;CONVERT TO BYTES
SUB D2,A0 ;ADJUST DST BUMP
lsl #3,d2 ;get long aligned bit width
lsr d7,d2 ;get effective cursr pixel width
add d2,(a1) ;adjust crsrRect.right = left+width
;-----------------------------------------------
;
; CONVERT LEFT EDGE AND RIGHT EDGE TO LEFTMASK AND RIGHTMASK IN D4 AND D2
MOVEQ #-1,D4 ;FILL LONG WITH ONES
LSR.L D0,D4 ;AND SHIFT IN 0'S FOR LEFTMASK
MOVEQ #-1,D2 ;FILL LONG WITH ONES
AND #$1F,D1 ;GET RIGHT MOD 32
beq.s @1 ;does right have a real mask? no, flush it
LSR.L D1,D2 ;AND SHIFT 0'S IN FROM RIGHT
NOT.L D2 ;GET RIGHTMASK
;-----------------------------------------------
;
; SAVE DSTLEFT/DSTBUMP/LONGCNT/ROWCNT INTO CRSRPTR SO THAT
; HIDECURSOR KNOWS HOW MUCH SCREEN TO REPLACE.
@1 JMPROM ToShowCrsr
;____________________________________________________________________________________
; PB552 26Jul88 DAF ShieldCursor Patch
;
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 27Jul88 #PB552 (jShieldCursor) (jShieldCursor)
;
; Here is more Leakware. This patch is a companion to PB546 above. Like the other patch, it
; corrects some bounding box problems with one-bit cursors.
MyShieldCursor PROC EXPORT
BackToJShield EQU $1AE58
NoSect EQU $1AE80
ShieldBottom EQU 16
MOVEM.L D0/A0-A1,-(SP) ;SAVE REGISTERS
LEA CrsrRect,A0 ;point to crsr rect
MOVE.L CrsrDevice,A1 ;GET CURSOR DEVICE
MOVE.L (A1),A1 ;POINT TO CURSOR DEVICE
ADD #GDRECT,A1 ;POINT TO DEVICE'S RECT
MOVE ShieldBottom(SP),D0 ;GET SHIELD BOTTOM
SUB TOP(A1),D0 ;CONVERT TO SCREEN LOCAL
CMP (A0)+,D0 ;IS SHIELDBOTTOM < SAVETOP ?
BLT.S @NOSECT ;YES, NO INTERSECTION
JMPROM BackToJShield ; continue in ROM
@NoSect JMPROM NoSect ; here, too
endp
;___________________________________________________________________________
;
; Patch PB586 ABO/BBM
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 15nov88 PB586 MPP Control hook ATP - ReqDupl
;___________________________________________________________________________
ATPDuplPatch proc export
AB EQU $4F ; Offset to DDP argument block in qEl
HB EQU $60 ; Offset to ATP header block in qEl
SaveRtn EQU WDSPointer+24 ; Offset to saved return address in qEl
FromReqDupl EQU $82C08E ; Where called from in ATP
ATPDataSize EQU $ABA ; Size of ATP variables
LookRspCB EQU $4082B7F0 ; Find RspCB routine in ROM
;
; The patch. First see if it looks like we were called from ReqDupl.
;
MOVE.L SaveRtn(A0),D0 ; ATP saves return address here
CMP #($FFFF AND FromReqDupl),D0 ; Does low word match? (quick check)
BEQ.S @20 ; Branch if so
@10 RTS ; Otherwise, no patch
@20 SUB.L #FromReqDupl,D0 ; Subtract address in ReqDupl
AND.L Lo3Bytes,D0 ; Mask high byte
BNE.S @10 ; Branch if not from ReqDupl
;
; Probably from ReqDupl in ATP. So that this patch is less risky, only patch if the
; data pointer looks bad. If the data pointer looks ok (won't cause a bus error), then
; worst case will be we'll write out a garbage reply to an already-completed request.
;
MOVE.L WDSPointer(A0),A3 ; A3 -> WDS
MOVE WDSEntrySz*2+2(A3),D3 ; D3 = high word of third pointer
CMP.B #$90,D3 ; Is pointer above ROM?
BLO.S @10 ; If not, it's good
;
; We need to really be sure this queue element was from ATP (this check should
; really have been done first, but it takes the most time)
;
MOVE.L AbusVars,A2 ; A2 -> MPP variables
MOVE.L ATPVars(A2),A2 ; A2 -> ATP variables
MOVE.L Lo3Bytes,D0 ; D0 = mask
MOVE.L A2,D2 ; D2 -> ATP variables
AND.L D0,D2 ; D2 = masked ATP var pointer
MOVE.L A0,D3 ; D3 -> qEl
AND.L D3,D0 ; D0 = masked qEl pointer
CMP.L D2,D0 ; See if qEl in ATP variables
BLO.S @10 ; If not, wasn't from ATP
ADD.L #ATPDataSize,D2 ; D2 = masked end of ATP vars
CMP.L D2,D0 ; See if qEl in ATP variables
BHI.S @10 ; If not, wasn't from ATP
;
; We're writing out a duplicate response with a potentially bad data pointer.
; Make sure we still own this RspCB.
;
MOVE.L A1,-(SP) ; Save A1
MOVE HB+ATPTransID(A0),D0 ; D0 = TID
MOVE.B Socket(A0),D1 ; D1 = source socket
MOVE.L AB+LAPHdSz+DDPDstNet(A0),D3 ; D3 = destination net (in high word)
MOVE AB+LAPHdSz+DDPDstNode(A0),D3 ; Add in node (high byte of low word)
MOVE.B AB+LAPHdSz+DDPDstSkt(A0),D3 ; D3 = full address
JSR LookRspCB ; Look for the RspCB
MOVE.L (SP)+,A1 ; Restore A1
BEQ.S @10 ; Just return if ok
;
; We no longer own this RspCB. Just return an error to the write call
;
ADDQ #4,SP ; Pop return pointer
MOVEQ #-96,D0 ; Set an error code
MOVE.L jIODone,A2 ; A2 -> ioDone
JMP (A2) ; We're done
ENDP
;#### end of PB586 ####
;____________________________________________________________________________________
; PP332 Cache control trap
;
; This patch adds a new trap to programatically control parameters of the RAMCache.
;
;
; Function: These traps provide an interface to the file system
; caching mechanism.
;
; Cache Trap
; Routines:
; GetCSize Get cache size
; SetCSize Set cache size
; GetApZnSiz Get minimum application zone size
; SetApZnSiz Set minimum application zone size
; GetMaxCXfr Get maximum cached transfer size
; SetMaxCXfr Set maximum cached transfer size
; GetCStatus Get cache status
; SetCStatus Get cache status
;
; Internal
; Routines:
; GetCacSize Get current size of cache
;
; To do:
; Need to completely redefine way cache uses memory. Should be
; a trap here to feed memory to the cache (called by MultiFinder
; or memory manager), also a way to ask for those blocks back
; if they are needed.
; Need some reasonableness checks for parameters.
;
; Modification History:
;
; <20Nov87> JB New today.
; <25Nov87> JB Added get/set cache status
; <02Dec87> JB Changed for ioParamblock interface
; <20Feb89> JB/DNF Moved from BeforePatches.a
;_____________________________________________________________________________
;_____________________________________________________________________________
; Cache trap dispatcher
;
; Supplied:
; D0.W Service selector index
; A0.L New cache parameter value if call is a 'set' call
;
; Returned:
; D0.L Result code
; 'ParamErr' is returned if either the selector
; is invalid or if the value supplied on a 'set'
; call is unreasonable
; A0.L Requested cache parameter value if the
; call was a 'get' call
;_____________________________________________________________________________
CachePatch PROC EXPORT
include 'DiskCachePriv.a' ; P003 <21Feb89><1.9>
ROMFSQSync equ $40807d90 ; Mac SE FSQueueSync address <1.9>
ROMCmdDone equ $40807e48 ; Mac SE CmdDone address <1.9>
ioMisc equ $1C ; old ioMisc mnemonic--need appropriate new name
;_____________________________________________________________________________
; Cache trap dispatch table:
;_____________________________________________________________________________
CTrapTbl dc.w GetCSize-CTrapTbl ; 0 - get cache size
dc.w SetCSize-CTrapTbl ; 1 - set cache size
dc.w GetApZnSiz-CTrapTbl ; 2 - get min application zone size
dc.w SetApZnSiz-CTrapTbl ; 3 - set min application zone size
dc.w GetMaxCXfr-CTrapTbl ; 4 - get max cached transfer size
dc.w SetMaxCXfr-CTrapTbl ; 5 - set max cached transfer size
dc.w GetCStatus-CTrapTbl ; 6 - get cache status
dc.w SetCStatus-CTrapTbl ; 7 - set cache status
maxCacheTrap equ (*-CTrapTbl)/2 ; Number of traps defined
EXPORT CacheTrap
CacheTrap cmp.w #maxCacheTrap,d0 ; Valid trap index?
blo.s @1 ; Xfer if so...
moveq #ParamErr,d0 ; Else, indicate parameter error
rts
@1
lea CTrapTbl,a1 ; Base of dispatch table
add.w d0,d0 ; Trap index into WORD index
add.w (a1,d0),a1 ; Routine to invoke
jmp (a1) ; Go to requested routine...
CTExit
jmp ROMCmdDone ; Exit via the file system...
;_____________________________________________________________________________
; 0 -- Get cache size
;_____________________________________________________________________________
GetCSize
jsr ROMFSQSync ; Synchronize with the file manager
move.l CacheVars,a1 ; Cache vars address
move.l OldBufPtr(a1),d0 ; Pre-cache BufPtr
sub.l NewBufPtr(a1),d0 ; Size of cache = (Pre-cache BufPtr)-current
move.l d0,ioMisc(a0) ; Return in param block
moveq #0,d0 ; Result = SUCCESS
bra.s CTExit
;_____________________________________________________________________________
; 1 -- Set cache size
;_____________________________________________________________________________
SetCSize
jsr ROMFSQSync ; Synchronize with the file manager
move.l ioMisc(a0),d0 ; Get desired cache size
moveq #15,d1 ; Divide by 32K
lsr.l d1,d0 ; ...
move.b d0,CacheConfig ; Set mem config for next launch
moveq #0,d0 ; Result = SUCCESS
bra.s CTExit
;_____________________________________________________________________________
; 2 -- Get minimum application zone size
;_____________________________________________________________________________
GetApZnSiz
jsr ROMFSQSync ; Synchronize with the file manager
move.l CacheVars,a1 ; Cache vars address
move.l CacheMinZn(a1),ioMisc(a0)
moveq #0,d0 ; Result = SUCCESS
bra.s CTExit
;_____________________________________________________________________________
; 3 -- Set minimum application zone size
;
; This value is examined whenever the cache is grown. Cache size will
; not be allowed to exceed this amount. The default value is enough
; space to load and run an application. The value may be set to a
; smaller value to enable use of memory for cacheing when it is known
; that other applications will not be present (MultiFinder).
;_____________________________________________________________________________
SetApZnSiz
jsr ROMFSQSync ; Synchronize with the file manager
move.l CacheVars,a1 ; Cache vars address
move.l ioMisc(a0),CacheMinZn(a1) ; Set new ApplZone size minimum
moveq #0,d0 ; Result = SUCCESS
bra.s CTExit
;_____________________________________________________________________________
; 4 -- Get maximum cached transfer size
;_____________________________________________________________________________
GetMaxCXfr
jsr ROMFSQSync ; Synchronize with the file manager
move.l CacheVars,a1 ; Cache vars address
move.l CacheByteLim(a1),ioMisc(a0)
moveq #0,d0 ; Result = SUCCESS
bra.s CTExit
;_____________________________________________________________________________
; 5 -- Set maximum cached transfer size
;
; This value is examined on each "read/write in place" call. These cache
; calls are used by file system to transfer integral blocks from the
; caller's buffer to/from the disk (possibly) without caching. Setting
; this value to a smaller value will tend to keep reading/writing large
; files from effectively causing a flush of the cache. This might
; make an environment where multiple files are typically open behave
; better (i.e., one application won't tend to cause the cache to be
; flushed).
;_____________________________________________________________________________
SetMaxCXfr
jsr ROMFSQSync ; Synchronize with the file manager
move.l CacheVars,a1 ; Cache vars address
move.l OldBufPtr(a1),d0 ; Pre-cache BufPtr
sub.l NewBufPtr(a1),d0 ; Size of cache = (Pre-cache BufPtr)-current
move.l ioMisc(a0),d1 ; Get caller's parameter
cmp.l d1,d0 ; Cache size >= requested max xfer size?
bhs.s @1 ; Xfer if so...
moveq #ParamErr,d0 ; Else, indicate parameter error
bra CTExit
@1
move.l d1,CacheByteLim(a1) ; Set new max transfer size
moveq #0,d0 ; Result = SUCCESS
bra CTExit
;_____________________________________________________________________________
; 6 -- Get cache status
;_____________________________________________________________________________
GetCStatus
jsr ROMFSQSync ; Synchronize with the file manager
move.l CacheVars,a1 ; Cache vars address
moveq #0,d0 ; Assume cache disabled
tst.b CurEnable(a1) ; Cache currently enabled?
beq.s @1 ; Xfer if currently disabled (error?)
btst #5,CacheEnable ; test enable bit
beq.s @1 ; Xfer if disabled
moveq #1,d0 ; Else, indicate "enabled"
@1
move.l d0,ioMisc(a0) ; Set returned cache status to caller
moveq #0,d0 ; Result = SUCCESS
bra CTExit
;_____________________________________________________________________________
; 7 -- Set cache status
;_____________________________________________________________________________
SetCStatus
jsr ROMFSQSync ; Synchronize with the file manager
tst.l ioMisc(a0) ; Enable or disable?
beq.s @1 ; Xfer if disable...
bset #5,CacheEnable ; Else, ask for enable on next launch
bra.s @2
@1
bclr #5,CacheEnable ; Ask for disable on next launch
@2
moveq #0,d0 ; Result = SUCCESS
bra CTExit
;_____________________________________________________________________________
;********************** End of Cache control trap ****************************
;_____________________________________________________________________________
ENDPROC
;____________________________________________________________________________________
; P005 S118 MapFBlock patch:
;
; This patch fixes a problem in MapFBlock which was trashing the extent file.
; MapFBlock was adding a word value rather than a long word value during the
; calculation of starting logical block number. This resulted in a wrap-
; around of the block number (modulo 64K). Since the extent file resides at
; allocation block zero, it was the first file to be trashed.
;
; This patch applies to ROM76 - ROM78 only. A separate patch in ROM75Fix
; (PM119) is required for ROM75. This is due to the absense of MapFBlock and
; XFSearch vectors in ROM75.
;
; Patched using the "MapFBlock" vector. NOTE, this patch replaces the
; "jMapFBlock" vector without saving the previous contents of that vector!
;
; The corresponding source code modification for this patch were made to
; FXM.a in the "MapFBlock" routine. The required modification was simply
; changing "ADD.W D0,D3" to "ADD.L D0,D3" when calculating the physical
; start block address.
;____________________________________________________________________________________
MapFBPatch: PROC EXPORT
MOVE.L (SP)+,-(A6) ; save return address on A6 stack
MOVEM.L D1-D2/D4-D5/D7/A0-A1/A3-A4,-(A6) ; save registers
SUB #lenFXVars,A6 ; allocate memory for FXM vars <19Mar87>
MOVEA.L A6,A4 ; A4 = pointer to FXM vars <19Mar87>
CLR.B FXVFlags(A4) ; clear all flags <19Mar87>
LEA 0(A1,D1.W),A3 ; A3 = FCB pointer
;
; locate the extent mapping the desired file position
;
MOVE.L D5,D0 ; file position
MOVEA.L jXFSearch,A0 ; call XFSearch via its vector <19Mar87>
JSR (A0) ; <19Mar87>
BNE.S MFExit ; exit on errors
LEA 0(A1,D1.W),A1 ; A1 = ptr to extent entry
MOVE.W D3,D1 ; D1 = beg FABN for extent
SUB.W xdrNumABlks(A1),D1 ;
MOVE.W D3,D2 ; D2 = end FABN in extent + 1
;
; determine end of available space (PEOF or end of extent)
;
MULU VCBAlBlkSiz+2(A2),D2 ; convert end FABN + 1 to file pos
MOVE.L FCBPLen(A3),D0 ; get PEOF
CMP.L D0,D2 ; end of extent > PEOF?
BLE.S @1 ; no, use end of extent ->
MOVE.L D0,D2 ; yes, use PEOF
@1 DIVU VCBAlBlkSiz+2(A2),D2 ; D2 = end of avail space ( end FABN + 1)
;
; set up some constants
;
MOVE.L VCBAlBlkSiz(A2),D6 ; D6 = # blks per alloc blk
DIVU #512,D6 ;
MOVEQ #0,D7 ; D7 = start blk # for alloc blks
MOVE.W VCBAlBlSt(A2),D7 ;
;
; calculate physical start block
;
MOVE.L D5,D3 ; file position / alloc blk size
DIVU VCBAlBlkSiz+2(A2),D3 ; = FABN mapping file position
SWAP D3 ; Get remainder in low word <PWD 26Sep85>
MOVEQ #0,D0 ; Clear top word to get remainder as long <PWD 26Sep85>
MOVE.W D3,D0 ; Compute block offset within alloc block <PWD 26Sep85>
LSR.L #8,D0 ; 'divide' by 256 <PWD 26Sep85>
LSR.L #1,D0 ; and again by 2 to get size in phys. blocks <PWD 26Sep85>
SWAP D3 ; Restore D3 for use <PWD 26Sep85>
SUB.W D1,D3 ; - beg FABN = alloc blk delta
ADD.W xdrStABN(A1),D3 ; + starting ABN = ABN mapping file pos
MULU D6,D3 ; convert to physical block #
ADD.L D0,D3 ; Offset in physical blocks within alloc. blk <19Mar87>
ADD.L D7,D3 ;
;
; calculate number of available bytes
;
MOVE.W D2,D6 ; end FABN + 1 * alloc blk size
MULU VCBAlBlkSiz+2(A2),D6 ; = ending file pos + 1
SUB.L D5,D6 ; - file position = size avail
CMP.L D4,D6 ; compare with desired number
BCS.S mFBlockOK ; < D4 bytes, leave it alone <02Oct85>
MOVE.L D4,D6 ; > D4 bytes, set to D4 bytes
mFBlockOK MOVEQ #0,D0 ; we're ok <01Oct85>
;
; clean up and exit
;
MFExit
ADD #lenFXVars,A6 ; de-allocate memory for FXM vars <02Oct85>
MOVEM.L (A6)+,D1-D2/D4-D5/D7/A0-A1/A3-A4 ; restore registers
MOVE.L (A6)+,-(SP) ; put return address back on stack
TST.W D0 ; set CCR for result <01Oct85>
RTS ; exit MapFBlock
ENDPROC
;____________________________________________________________________________________
; * * * End of MapFBlock patch * * *
;____________________________________________________________________________________
;_______________________________________________________________________
;_______________________________________________________________________
;<3.7> Slot Interrupt/VBL patch
;
; Start of patch code to patch in the new Slot Manager and
; SlotVBL stuff into the MacII (NuMac).
;
; Slot Traps patched: SIntInstall, SIntRemove
; VBL Traps patched:SlotVInstall,SlotVRemove, AttachVBL,DoVBLTask
;
; Also patched: the secondary interrupt handler for slots (SlotInt routine)
; the secondary interrupt handler for slot VBLs (SlotVBLInt routine)
;
; We do this to increase speed with which slot interrupts are handled,
; and to be able to access all slot numbers. Viva la choice.
;
; All the old data structures (pointed to by low mems):
; SlotQDT EQU $0D04 ; ptr to slot Int queue table
; SlotPrTbl EQU $0D08 ; ptr to slot priority table (ROM $78 only)
; SlotVBLQ EQU $0D0C ; ptr to slot VBL queue table (ROM $78 only)
; ScrnVBLPtr EQU $0D10 ; save for ptr to main screen VBL queue
; SlotTICKS EQU $0D14 ; ptr to slot tickcount table (ROM $78 only)
; have been replaced by a single structure (called SlotIntGlobals)
; pointed to by SlotQDT. See SlotMgrEqu.a for details of new structure.
; These low mem's (except for SlotQDT) no longer hold valid values.
;_______________________________________________________________________
SlotPatch proc export
export SIntINSTALL,SIntREMOVE
export SlotInt,Via2SlotInt
export SlotVInstall,SlotVRemove
export AttachVBL,DoVBLTask
with SlotIntQElement,slotIntGlobals,slotVBLInfo
addrDequeue EQU $0602A ;address in MacII ROMS of the Dequeue routine
addrEnqueue EQU $06004 ;address in MacII ROMS of the Enqueue routine
VIA2base EQU $50F02000 ;address of base register of VIA2 on MacII machines
;_______________________________________________________________________
;
; Routine: GetSlotIntQHead
;
; Arguments: D0 (input) : video card slot ($0..$E possible)
; D0 (output): error code
; A1 (output): address of pointer to first SlotIntQElement
;
; Function: Utility routine to do check for valid slot number, and return
; the address of the associated slot slotIntInfo record.
; If the queue type is wrong, or the slot number is out of range,
; an error code will be returned, and the routine will return to
; the callers caller, instead of directly to the caller.
;
; Called by: SIntInstall, SIntRemove
;
; Registers Used: D0,A1
;_______________________________________________________________________
GetSlotIntQHead
cmpi.w #SIQType,SQType(A0) ; is it the proper type?
bne.s @wrongType ; if not, report the error
ext.w d0 ; ignore high byte
cmpi.w #sLastSlot,d0 ; check for valid slot #
bgt.s @slotTooBig ; return error if too big
lea ([SlotQDT],d0.w*4,slotIntQHeads-SQLink),a1 ; get address of queue header
rts ; return with success
@wrongType moveq.l #VTypErr,d0 ; queue element type is wrong
bra.s @error ; report the error
@slotTooBig move.w #smSlotOOBErr,d0 ; return with slot # error
@error addq.w #4,sp ; pop the return address
rts ; return to callers caller
;_______________________________________________________________________
;
; Routine: SIntINSTALL
;
; Arguments: D0 (input) : slot number for routine ($0..$E possible)
; A0 (input) : ptr to queue element
; D0 (output): error code - 0 no error
;
; Function: Installs a slot interrupt poll routine which is called when
; a slot interrupt occurs. The queue element is installed in
; in priority order, $FF highest (first), $00 lowest (last).
; <5.4>
; We reverse the queueing order back to what it was originally on the
; Mac II, which is opposite what's documented in Inside Mac V. $00 is
; now hightest (first) and $$ is lowest (last). For handlers with same
; priority number, the one installed last will be executed first (that
; is, it's closer to front of the queue).
; <28>
; We reverse once more. $FF is highest. equal priorities handled same
; as in <5.4>.
;
; Only low byte of priority word is used (0-255 range).
;
; Registers Used: D0,D1,D2,A0,A1
;_______________________________________________________________________
SIntINSTALL bsr.s GetSlotIntQHead ; a1 := pointer to qheader
move.b SQPrio+1(a0),d0 ; get the priority (low byte of word)
move.w sr,-(sp) ; save interrupt level
ori.w #HiIntMask,sr ; disable interrupts
@PrioritySearch
move.l SQLink(a1),d1 ; get next queue element to check
beq.s @insert ; if end of list, insert before this
exg.l a1,d1 ; swap previous and current pointers
cmp.b SQPrio+1(a1),d0 ; compare priorities
blo.s @PrioritySearch ; loop until lower priority (higher number) found <5.4><28>
exg.l d1,a1 ; a1 points to previous, d1 points to current
@insert ; insert before the lower priority element
move.l d1,SQLink(a0) ; remainder of queue goes after new element
move.l a0,SQLink(a1) ; new element goes after previous element
move.w (sp)+,sr ; restore interrupt level
moveq.l #noErr,d0 ; return success
rts ; all done
;_______________________________________________________________________
;
; Routine: SIntREMOVE
;
; Arguments: D0 (input) : slot number for routine ($0..$E possible)
; A0 (input) : ptr to queue element to remove
; D0 (output): error code - 0 = no error
;
; Function: Removes a poll routine from the slot interrupt queue.
;
; Registers Used: D0,D1,A1
;
;_______________________________________________________________________
SIntREMOVE bsr.s GetSlotIntQHead ; a1 := pointer to qheader
moveq.l #qErr,d0 ; error code in case it's not found
move.w sr,-(sp) ; save interrupt level
ori.w #HiIntMask,sr ; disable interrupts
@search move.l SQLink(a1),d1 ; get next queue element to check
beq.s @notFound ; if end of list, nothing to remove
exg.l a1,d1 ; swap previous and current pointers
cmpa.l a0,a1 ; see if this is the one to remove
bne.s @search ; loop until removee is fount
movea.l d1,a1 ; a1 points to previous
move.l SQLink(a0),SQLink(a1) ; remainder of queue goes after previous element
moveq.l #noErr,d0 ; return success
@notFound move.w (sp)+,sr ; restore interrupt level
rts ; all done
;_______________________________________________________________
;
; Secondary Dispatch routines for slot interrupts
;
; On Entry: A1.L = VIA2/RBV/OSS base address
; D0-D3/A0-A3 have been saved
;
;____________________________________________________________________________
SlotInt
Via2SlotInt
move.b #$02,vIFR(a1) ; reset the VIA any slot interrupt flag
moveq.l #~$3F,d0 ; mask for slot bits (active low)
or.b vBufA(a1),d0 ; read and mask slot interrupt indicators
not.l d0 ; convert to active high bit mask
bne.s SlotIntCommon ; if interrupt pending, service it
rts ; if not, return from the interrupt
SlotIntCommon
subq.l #4,sp ; allocate a long (only a byte is used)
move.b d0,(sp) ; save the interrupt pending bit mask
@loop move.b SlotPriority(d0.w),d0 ; get slot number / bit number
bclr.b d0,(sp) ; clear the bit
lsr.b #4,d0 ; get the slot number
bsr.s RunSlotHandlers ; run the handlers for this slot
bne.s @noHandler ; if couldn't be serviced, die with sys error
move.b (sp),d0 ; see if any other slots were pending
bne.s @loop ; loop until all slots serviced
addq.l #4,sp ; pop the pending bits
; Because AnySlot is edge triggered on some machines, we must make sure that all
; slot interrupts go away, causing AnySlot to go away, so that the next slot interrupt
; will cause an edge transition on AnySlot. We loop back to be start of the handler
; to see if any slot interrupts occurred since we last checked, and only exit when they
; all go away.
movea.l #VIA2base,a1 ; get base address of chip with slot int reg (MacII only!!)
movea.l Via2DT+4*ifCA1,a0 ; get the handler address (in case someone patched it)
jmp (a0) ; loop until no slots interrupting
@noHandler _SysError ; no handler for slot interrupt
RunSlotHandlers
lea ([SlotQDT],d0.w*4,slotIntQHeads-SQLink),a1 ; get address of queue header
@RunNext move.l SQLink(a1),d0 ; get next queue element
beq.s @notFound ; if end of queue reached, return error
movea.l d0,a1 ; setup queue element pointer
move.l a1,-(sp) ; save queue element pointer
movea.l SQAddr(a1),a0 ; get poll routine address
movea.l SQParm(a1),a1 ; stuff optional A1 param
jsr (a0) ; call the handler
movea.l (sp)+,a1 ; restore the queue element pointer
tst.w d0 ; see if the int was serviced
beq.s @RunNext ; if not, try the next handler
moveq.l #noErr,d0 ; if handled, return with success
rts ; all done
@notFound moveq.l #dsBadSlotInt,d0 ; return with an error if no handler
rts ; all done
SlotPriority
dc.b $00 ; 0 0 0 0 0 0 0 0 - no interrupt
dc.b $90 ; 0 0 0 0 0 0 0 1 - Slot 9 (bit 0)
dc.b $A1 ; 0 0 0 0 0 0 1 0 - Slot A (bit 1)
dc.b $90 ; 0 0 0 0 0 0 1 1 - Slot 9 (bit 0)
dc.b $B2 ; 0 0 0 0 0 1 0 0 - Slot B (bit 2)
dc.b $90 ; 0 0 0 0 0 1 0 1 - Slot 9 (bit 0)
dc.b $A1 ; 0 0 0 0 0 1 1 0 - Slot A (bit 1)
dc.b $90 ; 0 0 0 0 0 1 1 1 - Slot 9 (bit 0)
dc.b $C3 ; 0 0 0 0 1 0 0 0 - Slot C (bit 3)
dc.b $90 ; 0 0 0 0 1 0 0 1 - Slot 9 (bit 0)
dc.b $A1 ; 0 0 0 0 1 0 1 0 - Slot A (bit 1)
dc.b $90 ; 0 0 0 0 1 0 1 1 - Slot 9 (bit 0)
dc.b $B2 ; 0 0 0 0 1 1 0 0 - Slot B (bit 2)
dc.b $90 ; 0 0 0 0 1 1 0 1 - Slot 9 (bit 0)
dc.b $A1 ; 0 0 0 0 1 1 1 0 - Slot A (bit 1)
dc.b $90 ; 0 0 0 0 1 1 1 1 - Slot 9 (bit 0)
dc.b $D4 ; 0 0 0 1 0 0 0 0 - Slot D (bit 4)
dc.b $90 ; 0 0 0 1 0 0 0 1 - Slot 9 (bit 0)
dc.b $A1 ; 0 0 0 1 0 0 1 0 - Slot A (bit 1)
dc.b $90 ; 0 0 0 1 0 0 1 1 - Slot 9 (bit 0)
dc.b $B2 ; 0 0 0 1 0 1 0 0 - Slot B (bit 2)
dc.b $90 ; 0 0 0 1 0 1 0 1 - Slot 9 (bit 0)
dc.b $A1 ; 0 0 0 1 0 1 1 0 - Slot A (bit 1)
dc.b $90 ; 0 0 0 1 0 1 1 1 - Slot 9 (bit 0)
dc.b $C3 ; 0 0 0 1 1 0 0 0 - Slot C (bit 3)
dc.b $90 ; 0 0 0 1 1 0 0 1 - Slot 9 (bit 0)
dc.b $A1 ; 0 0 0 1 1 0 1 0 - Slot A (bit 1)
dc.b $90 ; 0 0 0 1 1 0 1 1 - Slot 9 (bit 0)
dc.b $B2 ; 0 0 0 1 1 1 0 0 - Slot B (bit 2)
dc.b $90 ; 0 0 0 1 1 1 0 1 - Slot 9 (bit 0)
dc.b $A1 ; 0 0 0 1 1 1 1 0 - Slot A (bit 1)
dc.b $90 ; 0 0 0 1 1 1 1 1 - Slot 9 (bit 0)
dc.b $E5 ; 0 0 1 0 0 0 0 0 - Slot E (bit 5)
dc.b $90 ; 0 0 1 0 0 0 0 1 - Slot 9 (bit 0)
dc.b $A1 ; 0 0 1 0 0 0 1 0 - Slot A (bit 1)
dc.b $90 ; 0 0 1 0 0 0 1 1 - Slot 9 (bit 0)
dc.b $B2 ; 0 0 1 0 0 1 0 0 - Slot B (bit 2)
dc.b $90 ; 0 0 1 0 0 1 0 1 - Slot 9 (bit 0)
dc.b $A1 ; 0 0 1 0 0 1 1 0 - Slot A (bit 1)
dc.b $90 ; 0 0 1 0 0 1 1 1 - Slot 9 (bit 0)
dc.b $C3 ; 0 0 1 0 1 0 0 0 - Slot C (bit 3)
dc.b $90 ; 0 0 1 0 1 0 0 1 - Slot 9 (bit 0)
dc.b $A1 ; 0 0 1 0 1 0 1 0 - Slot A (bit 1)
dc.b $90 ; 0 0 1 0 1 0 1 1 - Slot 9 (bit 0)
dc.b $B2 ; 0 0 1 0 1 1 0 0 - Slot B (bit 2)
dc.b $90 ; 0 0 1 0 1 1 0 1 - Slot 9 (bit 0)
dc.b $A1 ; 0 0 1 0 1 1 1 0 - Slot A (bit 1)
dc.b $90 ; 0 0 1 0 1 1 1 1 - Slot 9 (bit 0)
dc.b $D4 ; 0 0 1 1 0 0 0 0 - Slot D (bit 4)
dc.b $90 ; 0 0 1 1 0 0 0 1 - Slot 9 (bit 0)
dc.b $A1 ; 0 0 1 1 0 0 1 0 - Slot A (bit 1)
dc.b $90 ; 0 0 1 1 0 0 1 1 - Slot 9 (bit 0)
dc.b $B2 ; 0 0 1 1 0 1 0 0 - Slot B (bit 2)
dc.b $90 ; 0 0 1 1 0 1 0 1 - Slot 9 (bit 0)
dc.b $A1 ; 0 0 1 1 0 1 1 0 - Slot A (bit 1)
dc.b $90 ; 0 0 1 1 0 1 1 1 - Slot 9 (bit 0)
dc.b $C3 ; 0 0 1 1 1 0 0 0 - Slot C (bit 3)
dc.b $90 ; 0 0 1 1 1 0 0 1 - Slot 9 (bit 0)
dc.b $A1 ; 0 0 1 1 1 0 1 0 - Slot A (bit 1)
dc.b $90 ; 0 0 1 1 1 0 1 1 - Slot 9 (bit 0)
dc.b $B2 ; 0 0 1 1 1 1 0 0 - Slot B (bit 2)
dc.b $90 ; 0 0 1 1 1 1 0 1 - Slot 9 (bit 0)
dc.b $A1 ; 0 0 1 1 1 1 1 0 - Slot A (bit 1)
dc.b $90 ; 0 0 1 1 1 1 1 1 - Slot 9 (bit 0)
;_______________________________________________________________________
;
; The following routines handle slot VBL tasks for the NuBus system
;_______________________________________________________________________
; In order to share code, we take advantage of structure of the low memory
; variables associated with the classic VBL manager, and group the queue
; header and tick count in the same way for slots.
_AssumeEq slotTickCount-slotVBLQHdr,Ticks-VBLQueue
;_______________________________________________________________________
;
; Routine: GetSlotVBLQHdr
;
; Arguments: D0 (input) : video card slot ($0..$E possible)
; D0 (output): error code
; A1 (output): address of SlotVBLQHdr for requested slot
;
; Function: Utility routine to do check for valid slot number, and return
; the address of the associated slot VBL queue header.
; If the slot number is out of range, an error code will be
; returned, and the routine will return to the callers caller,
; instead of directly to the caller.
;
; Called by: SlotVInstall, SlotVRemove, AttachVBL, DoVBLTask
;
; Registers Used: D0,A1
;_______________________________________________________________________
GetSlotVBLQHdr
ext.w d0 ; ignore high byte
cmpi.w #sLastSlot,d0 ; check for valid slot #
bgt.s @slotTooBig ; return error if too big
movea.l ([SlotQDT],d0.w*4,slotVBLPtrs),a1 ; point to the VBL queue header
rts ; return with success
@slotTooBig move.w #smSlotOOBErr,d0 ; return with slot # error
addq.w #4,sp ; pop the return address
rts ; return to callers caller
;_______________________________________________________________________
;
; Trap: _SlotVINSTALL
;
; Arguments: A0 (input) : address of vertical retrace control block
; D0 (input) : video card slot ($0..$E possible) <v1.2>
; D0 (output): error code - 0 no error
; -2 invalid queue element type
; -360 invalid slot #
;
; Function: Installs a slot specific vertical retrace routine which is
; called after VBLCOUNT(A0) video frames. The count is treated
; as being in units of the slot's VBL time (e.g. 1/67th sec for
; the standard system monitor). Phase parameter is treated in
; same way as for Mac+ VBL tasks with substitution of a "slot
; tickcount" in place of the global TICKS value.
;
; Registers Used: D0,D1,D2,A0,A1
;_______________________________________________________________________
SlotVInstall
bsr.s GetSlotVBLQHdr ; find the VBL Queue for the slot
*VInstallCommon ; common code shared with SlotVInstall
cmpi.w #vType,VBLType(a0) ; is it the proper type?
bne.s VTypeError ; if not, exit with error <1.4>
move.w vblCount(a0),d1 ; D1.W = Count <30Apr85>
beq.s @QueueIt ; Count=0 is special, one-shot case <30Apr85>
tst.w VBLPhase(a0) ; zero phase is also special <C204>
beq.s @QueueIt ; queue up for count ticks later <C204>
move.w sr,-(sp) ; save current interrupt status <07May85>
ori.w #HiIntMask,sr ; disallow VBL interrupts <07May85>/<24Jul85>
move.l Ticks-VBLQueue(a1),d0; D0 = 2^16*Thi + Tlo <30Apr85>
swap d0 ; <30Apr85>
moveq.l #0,d2 ; <30Apr85>
move.w d0,d2 ; D2 = Thi <30Apr85>
divu d1,d2 ; D2.hi = Thi MOD Count <30Apr85>
swap d2 ; <30Apr85>
move.w d2,d0 ; <30Apr85>
swap d0 ; D0 = 2^16*(Thi MOD Count) + Tlo <30Apr85>
divu d1,d0 ; <30Apr85>
swap d0 ; D0.W = Ticks MOD Count <30Apr85>
sub.w VBLPhase(a0),d0 ; <30Apr85>
neg.w d0 ; D0.W = Phase - (Ticks MOD Count) <30Apr85>
bpl.s @PhaseDone ; <30Apr85>
add.w d1,d0 ; D0.W = Count + (Phase - (...)) <30Apr85>
@PhaseDone ; <30Apr85>
add.w d0,vblCount(a0) ; <30Apr85>
move.w (sp)+,sr ; restore old status <07May85>
@QueueIt jsrROM addrEnqueue ; install it in the queue
moveq.l #noErr,D0 ; indicate success
rts ; and return...
VTypeError moveq.l #VTypErr,d0 ; flag the error
rts ; and return...
;_______________________________________________________________________
;
; Trap: _SlotVRemove
;
; Arguments: A0 (input) : address of vertical retrace control block
; D0 (input) : video card slot ($0..$E possible) <v1.2>
; D0 (output): error code - 0 no error
; -2 invalid queue element type
;
; Function: Removes a slot specific vertical retrace control block from the
; slot's VBL queue.
;
; Registers Used: D0,D1,A1
;_______________________________________________________________________
SlotVRemove bsr.s GetSlotVBLQHdr ; find the VBL Queue for the slot
cmpi.w #vType,VBLType(a0) ; is it the proper type?
bne.s VTypeError ; if not, exit with error
jmpROM addrDequeue ; remove it from the queue, and return
;_______________________________________________________________________
;
; Trap: _AttachVBL
;
; Arguments: D0 (input) : new video card slot for system VBL ($0..$E possible) <v1.2>
; D0 (output): error code
;
; Function: Does setup of ptr in slot VBL table to main system VBL queue.
;
; Registers Used: D0,D1,A1
;_______________________________________________________________________
AttachVBL bsr.s GetSlotVBLQHdr ; find the VBL Queue for the slot
move.l a1,ScrnVBLptr ; save new screen VBL ptr
moveq.l #noErr,d0 ; no error
rts ; and return with success
;_______________________________________________________________________
;
; Trap: _DoVBLTask
;
; Arguments: D0 (input) : video card slot ($0..$E possible) <v1.2>
; D0 (output): error code
;
; Function: Triggers servicing of slot specific VBL queue.
;
; Registers Used: D0,D1,A1
;_______________________________________________________________________
DoVBLTask bsr GetSlotVBLQHdr ; find the VBL Queue for the slot
; first update the slot's "tickcount"
addq.l #1,slotTickCount-slotVBLQHdr(A1) ; increment slot tickcount
; check if main system queue being serviced
cmpa.l ScrnVBLPtr,a1 ; is it the main screen?
bne.s @cursorDone ; skip if not
move.l JCrsrTask,d0 ; else call the cursor task
beq.s @cursorDone ; if there is one installed
movea.l d0,a0 ; there is - go do it
move.l a1,-(sp) ; save queue header ptr
jsr (a0) ; run the cursor task
movea.l (sp)+,a1 ; restore queue ptr
@cursorDone
; now we service the VBL queue . . .
RunVBLs lea qHead-vblink(a1),a0 ; setup to fetch head of list
@VBLloop move.l vblink(a0),d0 ; advance to next block
beq.s @VBLDone ; if queue is empty, exit
; Here we update the counter in the vertical retrace control block and
; call the appropriate routine when it times out. A0 points to the current
; block.
movea.l d0,a0 ; get pointer to next VBL control block
subq.w #1,vblCount(a0) ; decrement the counter
bne.s @VBLloop ; if non-zero, don't bother
move.l a0,-(sp) ; preserve A0 (pointer to VBL ctl block)
move.l a1,-(sp) ; preserve queue header pointer
movea.l vblAddr(a0),a1 ; get address of service routine
jsr (a1) ; call the routine with A0 pointing to the block
movea.L (sp)+,a1 ; restore A1
movea.L (sp)+,a0 ; restore A0
tst.w vblCount(A0) ; did the routine reset count?
bne.s @VBLloop ; if not, leave it in the queue
; unlink the element since it timed out
jsrROM addrDequeue ; unlink it
bra.s @VBLloop ; and search the rest of the queue
@VBLDone bclr.b #inVbl,qFlags(a1) ; remember that we're done!
* moveq.l #noErr,d0 ; no error (d0=0 from code at @VBLloop)
rts ; return with success
;_______________________________________________________________________
;<3.7> Slot Interrupt/VBL patch
;
; End of patch code to patch in the new Slot Manager and
; SlotVBL stuff into the MacII (NuMac).
;_______________________________________________________________________
;_______________________________________________________________________
;############################### END PATCH CODE ##############################################
;
;############################# PATCH INSTALL CODE ############################################
;
;
RAMSysInit PROC EXPORT
IMPORT FixupTbl
IMPORT SysBase,CutBack ;<6.0>
Move.L D1,-(SP) ;save our handle
;############################# PATCH INSTALLS GO HERE ################################
;
; Patches are divided into two groups: Those required for both Mac OS and A/UX, <PB302>
; and those required for the Mac OS Only. <PB302>
; The first group (for both OSs) begins here; Mac OS only patches are <PB302>
; are further down the file. <PB302>
;
; <PB373>
; The Fixing up of addresses generated by the CMPRA, JSRROM & JMPROM Breaks down <PB373>
; as follows: <PB373>
; Addressing High Byte in Instruction Action <PB373>
; 24 bit NZ Do not alter the address in the instruction.<PB373>
; Used with CMPRA to a ROM Resource. <PB373>
; 32 bit NZ Mask out 12 high bits from the address <PB373>
; in the instruction, leaving a ROM offset<PB373>
; Then add in ROMBase.
; either Zero Normal Case. Add ROMBase to the address<PB373>
; in the instruction. <PB373>
; <PB373>
; Registers: <PB373>
; D0: Address Size Flag. Pos: 24 bit mode; Neg: 32 bit Mode <PB373>
; D1: Entry from table of offsets of locations to be fixed up <PB373>
; D2: (RomBase) <PB373>
; A0: Pointer into table of offsets of locations to be fixed up. <PB373>
; A1: Base of fixup table; also location from which offsets are computed.<PB373>
move.l RomBase, D2 ; <PB302> <PB373>
moveq #-1, D0 ; <PB373>
_StripAddress ; <PB373>
lea FixupTbl, A0 ; <PB302>
move.l A0, A1 ; <PB302>
FixUpLooP move.l (A0)+, D1 ; <PB302>
beq.s @1 ; <PB302>
tst.b 0(A1, D1.L) ; <PB373>
beq.s @AddIt ; <PB373>
tst.l D0 ; If Address has any high bits set <PB373>
bpl.s FixUpLoop ; 24 Bit mode; Dont alter this one. <PB373>
and.w #$f, 0(A1, D1.L); 32 Bit Mode; Clear High 12 bits. <PB373>
@AddIt add.l D2, 0(A1, D1.L) ; Normal Case: Add in ROMBase <PB302> <PB373>
bra.s FixUpLoop ; <PB302>
@1
; Initialize some new LowMems <8.3>
move.l #$50F02000,VIA2 ; VIA2 base address <8.3>
move.w #$0310,TimeViaDB; number of VIA accesses per millisecond <8.3>
; PMAB354 07Jan88 EMT Unimplemented Toolbox versions of 12 bisexual traps
INCLUDE 'ToolboxCastration.a'
; PB093 09Mar87 EHB
InstToolTp StdRgn,$D1 ; <PB279/DAF>
; PB136 24Mar87 JTC GetNewControl
InstToolTp MyGetNewControl,$1BE
; PABM150
InstOSTp mySysEnvirons,$90
; PB172 10Apr87 JTC&SMD Pack4 Pack4
InstToolTp MyPack4,$1EB
; PB206 16Jul87 EHB QuickDraw
InstToolTp PatConvert,$313 ; PB206
; PB217 22Jul87 BAL QuickDraw
InstToolTp MyRSect,$321 ; replace RSECT to patch DrawLine
;PMAB270 13Sep87 FJL DrawPicture DrawPicture
InstToolTp FixDisposPixPat,$208 ; <PB292/30Sep87> DAF
InstToolTp FixDisposCCursor,$226 ; <PB292/30Sep87> DAF
InstToolTp FixCloseCPort,$202 ; <PB292/30Sep87> DAF
InstToolTp FixClosePort,$7D ; <PB292/30Sep87> DAF
; <1.7> 2Feb89 CCH Added Gestalt.
; <6.4> <08/19/89 pke> Moved this up here so other 'ptch' files can use Gestalt
; (e.g. TextEdit needs this for 6.0.4 scripts builds and for 7.0)
PtchInst 5
; PB435 Fix for InitWindows memory losing bug
InstToolTp MySetDeskCPat,$247
InstToolTp MyInitWindows,$112
; This patch is for the Get Mgr., so that GetNewCWindow gets 'pltt' resources.
InstToolTp myGetNewCWindow,$246 ; <61>
InstToolTp myPaintRect,$A2 ; PB531
InstToolTp myFrameRect,$A1 ; PB531
;_____________________________________________________________________________
; Install MapFBlock patch (P005,S118)
;_____________________________________________________________________________
IMPORT MapFBPatch
LEA MapFBPatch,A0 ; install patch code
MOVE.L A0,jMapFBlock ;
;_____________________________________________________________________________
; End of MapFBlock patch installation
;_____________________________________________________________________________
;######################### A/UX CONDITIONAL INSTALLATION ********##################### <PBxxx>
; Patches in this group are bypassed when running on A/UX.
MOVE.W HwCfgFlags,D0 ; check em the compulsive way <PBxxx>
BTST #hwCbAUX,D0 ; is it A/UX time? <PBxxx>
BNE skipOSInstalls ; if so skip this OS stuff <PBxxx>
;----------------------------------------------------------------------------------------- <5.7>
; HERE ARE PATCHES THAT WERE FORMERLY INSTALLED FOR A/UX THAT SHOULD NOT HAVE BEEN <5.7>
; PB366 25jan88 bbm
cmp.l #$00002000, SysZone ; is Scruffy installed? <89>
beq.s @hasCleanMemoryManager ; dont install if so <89>
InstOSTp nMaxBlock,$61 ; replace maxblock
@hasCleanMemoryManager ; <89>
; PP332 Install Cache control trap
InstOSTp CacheTrap,$74 ; install the HFS RAM disk cache control trap
; Install patch to fix ATP duplicate request bus-error bug (PB586)
CMP.B #3,CPUFlag ; is this an 030 machine?
BNE.S @noDupl ; dont install if not
LEA ATPDuplPatch,A3 ; A3 -> the patch
MOVE.L A3,ATalkHk1 ; set in LAPWrite hook
; patch loader strips our address before calling us, A3 is full 32-bit address <5.7>
@noDupl
;----------------------------------------------------------------------------------------- <5.7>
; PAB087 06Mar87 CSL JCrsrTask patch ; Moved to Mac OS only <PB302>
LEA JCrsrTask,A0
leaFar CrsrPtch,A1 ; <6.0>
MOVE.L A1,(A0) ;
; PB071 07Mar87 SHF SCSIWrite, SCSIWBlind OS:SCSIMgr.a <PBxxx>
setTrapFar NewSCSIMgr,$A815 ; patched SCSI Manager <1.6> <6.0>
MOVE.L SCSIGlobals,A1 ; ptr to vectors and globals
IF PatchSCSIRead THEN ; not currently used
leaFar mySCSIRead,A0 ; <6.0>
MOVE.L A0,5*4(A1) ; patch the SCSIRead vector
leaFar mySCSIRBlind,A0 ; <1.6> <6.0>
MOVE.L A0,8*4(A1) ; patch the SCSIRBlind vector
ENDIF
leaFar mySCSIWrite,A0 ; <1.6> <6.0>
MOVE.L A0,6*4(A1) ; patch the SCSIWrite vector
leaFar QuantumWBlindII,A0 ; quantum 7.9 rom fix <77> djw
MOVE.L A0,9*4(A1) ; patch the SCSIWBlind vector
leaFar NewSCSIGet,a0 ; point to improved SCSIGet <PMAB466/JWK> <1.6>
move.l a0,1*4(a1) ; patch the SCSIGet vector <PMAB466/JWK>
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 20Oct87 #PMAB295 (SCSILoad) (SCSILoad)
;
; PMAB295 20Oct87 SHF SCSISelect SCSIMgr.a:SCSISelect
; PMAB329 10Dec87 JWK Fixed PMAB295 to avoid 10 sec delay when booting without
; SCSI devices attached. (Retyped PMAB295 -- it was mysteriously deleted!)
; PB336 16Dec87 AGH My apologies for the mysterious disappearance.
ROM78Load EQU $40807AE0 ; Mac II SCSILoad <PMAB295/10Dec87/JWK>
ROM78Select EQU $4082675E ; Select code <PMAB295/10Dec87/JWK>
BSR.S @ClearBus ; clear up bus problems first <PMAB295/10Dec87/JWK>
MOVE.L SCSIGlobals,A0 ; pointer to SCSIMgr variables <PMAB295/10Dec87/JWK>
MOVE.L 2*4(A0),-(SP) ; save old Select vector <PMAB295/10Dec87/JWK>
LEA @Sel78Patch,A1 ; pointer to my patch routine <PMAB295/10Dec87/JWK>
MOVE.L A1,2*4(A0) ; patch out the Select vector <PMAB295/10Dec87/JWK>
MOVE.B #$FF,D0 ; try all drivers <PMAB295/10Dec87/JWK>
MOVEQ.L #7,D1 ; mask for internal drive ID <PMAB295/10Dec87/JWK>
AND.B SCSIPoll,D1 ; bits 0-3: ID of int. drive <PMAB295/10Dec87/JWK>
BCLR.L D1,D0 ; don't try for internal drive <PMAB295/10Dec87/JWK>
MOVEQ.L #SBMac,D3 ; Macintosh OS driver type <PMAB295/10Dec87/JWK>
SWAP D3 ; Mac II SCSILoad needs it here <PMAB295/10Dec87/JWK>
JSR Rom78Load ; take the leap of faith <PMAB295/10Dec87/JWK>
MOVE.L SCSIGlobals,A0 ; pointer to SCSIMgr variables <PMAB295/10Dec87/JWK>
MOVE.L (SP)+,2*4(a0) ; restore the old Select vector <PMAB295/10Dec87/JWK>
BSR.S @ClearBus ; clear up remaining problems <PMAB295/10Dec87/JWK>
BRA.S @SCSIDone
@ClearBus
CLR.W -(SP) ; prepare for return value <PMAB295/10Dec87/JWK>
_SCSIStat ; get current SCSI bus status <PMAB295/10Dec87/JWK>
AND.W #aBSY+aSEL,(SP) ; test BSY&SEL, leave word on stack <PMAB329/10Dec87/JWK>
BEQ.S @ClearRts ; no BSY or SEL, so return <PMAB329/10Dec87/JWK>
@IsBusFloating
AND.W #aSEL,(SP) ; test SEL: floating SCSI bus ? <PMAB329/10Dec87/JWK>
BNE.S @ClearRts ; BSY&SEL true - nothing attached <PMAB329/10Dec87/JWK>
PEA Scratch8 ; address for status byte <PMAB295/10Dec87/JWK>
PEA Scratch8+2 ; address for message byte <PMAB295/10Dec87/JWK>
MOVE.L #OneSecTicks*5,-(SP) ; wait up to five seconds <PMAB295/10Dec87/JWK>
_SCSIComplete ; try to get to Bus Free state <PMAB295/10Dec87/JWK>
@ClearRts
ADDQ.L #2,SP ; pop off return code <PMAB295/10Dec87/JWK>
RTS ; <PMAB295/10Dec87/JWK>
@Sel78Patch
MOVEQ.L #0,D0 ; clear upper bits <PMAB295/10Dec87/JWK>
MOVE.W 8(A6),D0 ; get the target's ID <PMAB295/10Dec87/JWK>
MOVE.W #25,d6 ; select timeout (ms) <PMAB295/10Dec87/JWK>
JMP ROM78Select ; go to rest of the ROM routine <PMAB295/10Dec87/JWK>
@SCSIDone ; <PMAB295/10Dec87/JWK>
; PB073 Cxxx 2Mar87 ABO VInstall atalk:nonres.a <PBxxx>
setTrapFar NewVInstall,$A033 ; replace VInstall <1.6> <6.0>
; PB091 08Mar87 RDC PowerOff OS:InterruptHandlers.a <PBxxx>
leaFar NewPowerOff,A0 ; get address of patch routine <6.0>
MOVE.L A0,AutoInt6 ; and replace poweroff int vector
setTrapFar PowerOff,$A05B ; replace PowerOff trap also <PB541> <6.0>
;____________________________________________________________________________ DAF <PB238> <PB336>
; TFB Video Driver Override
;
INCLUDE 'VideoPatch.a'
; PB231 28Jul87 rwh/rdc Patch for dispatching of deferred tasks
; PB573 22Sep88 jwk Cleaned up for Mac II.
;
; Patch install code - hook into vector for deferred task dispatching
InstOSTp NewDisptch,$B9 ; replace Dispatch vector <PB573>
; PB232 04aug87 bbm WriteXPRam WriteXPRam ; OS trap $52
; Patch to check validity of parameters to WriteXPRam
; Patch install code
InstOSTp NewWriteXPRam,$52 ; replace WriteXPRam trap
; PB236 24Aug87 RDC GenExcps OS:StartErr.a <PB336>
; install new vector only if ROM in control <PB336>
ROMNMIVct EQU $40802114 ; ROM NMI handler routine <PB336>
IMPORT NewNMIExcp ; <PB336>
MOVE.L AutoInt7,D0 ; get current NMI vector <PB336>
CMPI.L #ROMNMIVct,D0 ; ROM in control? <PB336>
BNE.S skipit ; skip if not <PB336>
LEA NewNMIExcp,A0 ; get address of new NMI routine <PB336>
MOVE.L A0,AutoInt7 ; store as new vector <PB336>
skipit
; PB237 19Aug87
LEA FClosePatch,A0 ; Install FClose patch
MOVE.L A0,jFClose
; PB238 19Aug87 DAF Open Open ; OS trap $00
; Add driver version testing to Open for slot devices
InstOSTp MyOpen,$00
; PMAB241 24Aug87 RDC BadTrap BadTrap
IMPORT NewBadTrap
InstToolTp NewBadTrap,$1FF ; replace Debugger trap $A9FF
InstToolTp NewBadTrap,$3FF ; replace Debugger trap $ABFF
; PMAB301 16Nov87 ABO ATP SendRequest
MOVEQ #AGBSize,D0 ; D0 = size of block
_NewHandle ,SYS,CLEAR ; Get it
BNE.S @NoATPPatch ; Error if can't
MOVE.L A0,AGBHandle ; Set in lowmem
MOVE.L (A0),A0 ; A0 -> AppleTalk Global Block
LEA ATPPatch,A1 ; A1 -> patch to SendRequest
MOVE.L A1,ATPHook(A0) ; Set in patch hook
@NoATPPatch
;----------------------------------------------------------------------------------------- <5.7>
; PB337 16dec87 bbm fixed SetOSDef to keep it from trashing PRam.
InstOSTp nSetOSDef,$83
; PMAB372 26Jan88 djw Install async serial driver patch for DTR bug ($BE is assigned vector)
; <80> 17Dec90 eh install new version number for driver
InstOSTp asyncPatch,$BE
SERDVersion equ 5
; install new version number
move.l #5*4,d0 ; first serial DCE is 5th entry in Utbl
moveq #4-1,d1 ; index through 4 dce's (adjusted for dbra)
@next movea.l UTableBase,a0 ; get ptr to the unit table
movea.l 0(a0,d0.w),a0 ; get DCE handle
movea.l (a0),a0 ; get DCE ptr
move.w #SERDVersion,dCtlQueue(a0) ; post new version
addq #4,d0 ; get next DCE
dbra d1,@next
; PB535 12Jul88 BAL/DAF install setccursor wrapper
InstToolTp MySetCCursor,$21c
; PB546 26Jul88 DAF Fix ShowCursor
LEA MyShowCursor,A0 ; get the patch address
MOVE.L A0,JShowCursor ; overwrite lomem vector
; PB552 26Jul88 DAF Fix ShieldCursor
LEA MyShieldCursor,A0 ; get the patch address
MOVE.L A0,JShieldCursor ; overwrite lomem vector
;----------------------------------------------------------------------------------------------------
; PB576 04Oct88 GGD SetupPoll mFmtTrack
;
; Fix File Date Patch# Fix Routine(s) Routine(s) Fixed
;AppleSystemPatch PatchIIROM.a 04Oct88 #PB576 (SetupPoll) (mFmtTrack)
;
; This patch only applies to the Mac IIx ROMs (with superdrive support) The space for the
; patch code is allocated with a NewPtr and the patch is copied in. If this ROM doesn't support
; SuperDrive, no space will be allocated, and no patch will be installed.
; absolute ROM addresses:
mFmtCaller EQU $4082EC74 ;where the MFM format code would have called us from
NoFmtIndex EQU $4082ECDA ;"no index pulse" error branch
mFmtResume EQU $4082EDF0 ;where we'll resume within the ROM
mVerCaller1 EQU $40831BC2 ;where RdAddrSetup calls us from
mVerCaller2 EQU $4082EE68 ;where the MFM verify code calls RdAddrSetup from
; low-memory addresses:
jSetupPoll EQU $23A ;jump vector to Sony driver's SetupPoll routine
; field sizes:
gap4aSize EQU 80 ;Gap between index and index mark
gap1Size EQU 50 ;Gap between index mark and sector 1
gap2Size EQU 22 ;Gap between address and data fields
gap3Sz720K EQU 80 ;Gap between adjacent sectors (720K)
gap3Sz1440K EQU 101 ;Gap between adjacent sectors (1440K)
syncSize EQU 12 ;Sync field size
markSize EQU 4 ;Size of index/address/data marks
; format bytes:
gapByte EQU $4E ;Inter/intra sector gap byte
theSync EQU $00 ;Sync byte preceeding each mark
fmtFillByte EQU $F6-256 ;Format byte to fill sectors with
PatchStart BRA Install ;***** install the patch code *****
;_______________________________________________________________________________
;
; Routine: mFmtPatch
;
; Inputs: D1 -- offset to current drive's variables
; D2 -- sectors/track - 1 (8 or 17); if 17, bit 31 will be set=1
; D4 -- track
; D5 -- side
; A0 -- pointer to IWM/SWIM base address
; A1 -- pointer to Sony driver's variables
;
; Outputs: A3 -- pointer to SWIM write data register
; A4 -- pointer to SWIM handshake register
; A5 -- pointer to SCC A-reg (SCC data available)
; A6 -- pointer to SCC A-reg data (SCC data)
;
; D3,A0,A1,A2 are trashed; all other registers are preserved
;
; Function: Patches SetupPoll so that we can get at the MFM format code. It first
; calls the original SetupPoll to do what it usually does, then checks
; to see if we were called from within the MFM format routine. If not,
; it just jumps back to the caller. If so, it starts up the format and
; then jumps back into the middle of the MFM format code in ROM.
; Also checks to see if MFM format verify code, called RdAddrSetup, which
; calls us at SetupPoll. We adjust the verify code to allow twice as many
; revolutions to find all of the sectors.
;_______________________________________________________________________________
mFmtPatch CMPI.L #mFmtCaller,(SP) ;did we get called from the MFM format code?
BEQ.S mDoFmtPatch ;-> yes, go fix the format
CMPI.L #mVerCaller2,4(SP) ;did RdAddrSetup get called from the verify code
BNE.S oldSetPoll ;-> no, don't fix anything
CMPI.L #mVerCaller1,(SP) ;did SetupPoll get called from RdAddrSetup
BNE.S oldSetPoll ;-> no, don't fix anything
BSET.L #31,D7 ;remember that it has been fixed
BNE.S oldSetPoll ;if already fixed, don't fix it again
ADD.W D7,D7 ;allow twice as many revolutions
oldSetPoll JMP ($53434744).L ;call the original SetupPoll (addr filled in by installer)
mDoFmtPatch MOVEA.L (SP)+,A2 ;pop the return address
BSR.S oldSetPoll ;go setup A5,A6, PollStack
LEA Cylinder,A3 ;setup to fill in address mark template
MOVE.B D4,(A3)+ ;setup track number
MOVE.W D5,(A3)+ ;setup side number (and set byte count to 1-1)
LEA wOnes-1(A0),A4 ;point to the highest write-zeroes address
TST.B rError(A0) ;clear the error register
MOVE.W #$1810,(A4)+ ;clear the write and action bits then set the write bit
MOVEQ #1,D0 ;(A4 now points to wOnes+1)
MOVE.B D0,-(A4) ;toggle the clFIFO bit to clear out
MOVE.B D0,-(A4) ; any data in the FIFO
MOVE.W D0,(A3)+ ;first sector number is 1 (and set byte count to 1-1)
; Write a bunch of gap bytes while waiting for the start of index. We track index
; by waiting for it to go low (if it starts high), then go high (start of index).
MOVEA.L A0,A3 ;point to IWM base address (and write data register)
MOVEQ #gapByte,D1
MOVE.W D1,(A3) ;write two bytes to fill up the FIFO
MOVEQ #8,D0 ;negative of index timeout (in upper word)
MOVE.W D0,(A4) ;turn on the action bit: GO!
LEA rHandshake(A0),A4 ;point to the handshake register for speed
WtIndexLo BSR.S WriteNTest ;write a gap byte (8 the first time) and test for index pulse low
BMI.S WtIndexLo ;-> index is high, so keep waiting
WtIndexHi BSR.S WriteNTest ;write a gap byte and test for index pulse high
BPL.S WtIndexHi ;-> index is low, so keep waiting
; When we get here, we're just after the rising edge of the index pulse.
; First thing we write on the track is a starting gap and sync bytes...
FmtStart LEA TrackTemplate-1,A2 ;point to phase register value
MOVE.B (A2)+,wPhase(A3) ;turn off the index signal while we format
MOVEQ #gap4aSize-1-1,D0 ;setup initial gap size and clear carry
BSR.S WriteBytes ;write out gap 4a (done explicitly, not from TrackTemplate)
;A1 will point here from now on
Fetch MOVEA.L A0,A3 ;restore A3 (points to wData)
MOVEQ.L #0,D0 ;prepare to zero extend
MOVE.B (A2)+,D0 ;fetch the byte count or displacement
BPL.S WriteString ;byte count if positive
ADDQ.B #markSize,D0 ;adjust special byte counts
BPL.S WriteCRC ;positive is CRC or MARK
;negative is NeXTSector
NeXTSect MOVEQ #gap3Sz720K-1,D0 ;get the inter sector gap size
TST.L D2 ;Is it the 1440K format?
BPL.S FmtGap3
MOVEQ #gap3Sz1440K-1,D0 ;Yes, there's a larger inter-sector gap
FmtGap3 MOVEQ.L #gapByte,D1 ;setup the gap data pattern
LEA SectorTemplate,A2 ;resume with NeXT sector
ADDQ.B #1,Sector-SectorTemplate(A2) ;update the sector number
DBRA D2,WriteLoop ;write gap if not the last sector
JMP mFmtResume ;resume after "DBRA D2,FmtNextSect" in mDoFormat (SonyMFM.a)
WriteCRC ADDA.W #wCRC-wData,A3 ;point to the write CRC register temporarily
BEQ.S WriteLoop ;write the byte string
WriteMark ADDA.W #wMark-wCRC,A3 ;point to the write mark register temporarily
WriteString MOVE.B (A2)+,D1 ;fetch the data byte value to write
WriteLoop TST.B (A5) ;SCC data available?
BMI.S @1
MOVE.B (A6),-(SP) ;yes, push it on the stack
@1 MOVE.B (A4),D3 ;wait until there's an opening in the FIFO
BPL.S @1
MOVE.B D1,(A3) ;write a byte
DBRA D0,WriteLoop
LSL.B #7-3,D3 ;test the index pulse level
JMP (A1)
; write D0 bytes and then test the index pulse level (only the index loops need this)
WriteNTest ADDQ.L #1,D0 ;increment loop count toward zero
WriteBytes MOVEA.L (SP)+,A1 ;pop the return address
BCC.S WriteLoop ;-> didn't time out waiting for index
JMP NoFmtIndex-mFmtCaller(A2) ;-> timed out waiting for index
DC.B $F5 ;turn off the index signal while we format
TrackTemplate EQU *
* HardCoded DC.B gap4aSize-1-1,gapByte ;Gap between index and index mark
DC.B syncSize-1,theSync ;write sync before index mark
DC.B markSize-1-1-markSize,$C2 ;write the index mark bytes $C2 $C2 $C2
DC.B 1-1,$FC ;index mark ends with data byte $FC
DC.B gap1Size-1,gapByte ;Gap between index mark and sector 1
SectorTemplate EQU *
DC.B syncSize-1,theSync ;write sync before address mark
DC.B markSize-1-1-markSize,$A1 ;write the addr mark bytes $A1 $A1 $A1
DC.B 1-1,$FE ;addr mark ends with data byte $FE
DC.B 1-1 ;one byte of cylinder number
Cylinder DC.B 0 ;filled in at runtime
DC.B 1-1 ;one byte of side number
Side DC.B 0 ;filled in at runtime
DC.B 1-1 ;one byte of sector number
Sector DC.B 0 ;filled in at runtime
DC.B 1-1,$02 ;one byte of block size (2*256 bytes)
DC.B 1-1-markSize ;write the 2 byte CRC for the address mark
DC.B gap2Size-1,gapByte ;Gap between address and data fields
DC.B syncSize-1,theSync ;write sync before data mark
DC.B markSize-1-1-markSize,$A1 ;write the data mark bytes $A1 $A1 $A1
DC.B 1-1,$FB ;data mark ends with data byte $FB
DC.B 512/4-1,fmtFillByte ;fill the sector data (128 bytes at a time)
DC.B 512/4-1,fmtFillByte ;fill the sector data (128 bytes at a time)
DC.B 512/4-1,fmtFillByte ;fill the sector data (128 bytes at a time)
DC.B 512/4-1,fmtFillByte ;fill the sector data (128 bytes at a time)
DC.B 1-1-markSize ;write the 2 byte CRC for the data mark
DC.B -1-markSize ;if more sectors, write gap and next sect
align 2
;_______________________________________________________________________________
;
; Routine: Install
;
; Inputs: none
;
; Outputs: none
;
; Function: checks if the ROM and Sony driver versions are correct, and if so,
; installs the patch code above into the jSetupPoll lo-mem vector.
;_______________________________________________________________________________
Install MOVEA.L UTableBase,A0 ;get the pointer to the unit table
MOVEA.L 16(A0),A0 ;get the Sony driver's DCE handle
MOVEA.L (A0),A0 ; and de-reference it
CMPI.B #2,DCtlQueue+1(A0) ;is this the correct driver version?
BNE.S DontInstall ;-> no, just exit
MOVEQ.L #(Install-mFmtPatch)/2,D0 ; patch size in words (to fit in a MOVEQ)
ADD.L D0,D0 ; convert word count to byte count
_NewPtr ,SYS ;allocate a block in the system heap for the patch code
BNE.S DontInstall ;-> no space, so we can't install
MOVEA.L A0,A1 ;setup dest ptr
LEA mFmtPatch,A0 ;point to our patch code,
MOVEA.L jSetupPoll,A2 ;get old vector address
MOVE.L A2,oldSetPoll+2-mFmtPatch(A0) ; patch the jump back into the ROM
MOVEQ.L #(Install-mFmtPatch)/2,D0 ; patch size in words (to fit in a MOVEQ)
ADD.L D0,D0 ; convert word count to byte count
_BlockMove ;copy the patch to the system heap
MOVE.L A1,jSetupPoll ; install the patch
DontInstall
; PB576 04Oct88 GGD SetupPoll mFmtTrack
;----------------------------------------------------------------------------------------------------
;#### end install code for PMAB581 <3.2> ####
;
; PB512 -- Install code for UpdAltMDB patch
;
IMPORT svExtBTFile,MyExtBTF,svExtBTCounter
lea svExtBTCounter,a0 ; get the counter <25Sep90>
move.w #-1,(a0) ; initialize to -1 <25Sep90>
lea svExtBTFile,a0 ; Point to save of ROM routine
move.l jExtBTFile,(a0) ; Save addr of ROM routine
lea MyExtBTF,a0 ; Point to the patch
move.l a0,jExtBTFile ; Install ourselves in the vector
;_______________________________________________________________________
;_______________________________________________________________________
;<3.7> Slot Interrupt/VBL patch
;
; Start of install code to patch in the new Slot Manager and
; SlotVBL stuff into the MacII (NuMac).
;_______________________________________________________________________
InitSlotStuff
with SlotIntQElement,slotIntGlobals,slotVBLInfo
move.w sr, -(sp) ; disable interrupts while we patch
ori.w #HiIntMask,sr
movem.l a0-a3/d0-d3,-(sp) ; save some registers
;
; Install the traps FIRST so we can use them to re-install the data structures
;
InstOSTp SIntInstall, $75 ; set new trap address for PrimeTime
InstOSTp SIntRemove, $76 ; set new trap address for PrimeTime
InstOSTp SlotVInstall,$6F ; set new trap address for PrimeTime
InstOSTp SlotVRemove, $70 ; set new trap address for PrimeTime
InstOSTp AttachVBL, $71 ; set new trap address for PrimeTime
InstOSTp DoVBLTask, $72 ; set new trap address for PrimeTime
;stuff lowMem jump vector that's NOT in trap table
lea DoVBLTask,a0 ; move to A0 for SetTrapAddress
move.l a0,d0 ; set up for StripAddress
_StripAddress ; make trap address 32 bit clean
movea.l d0,a0 ; now we're cooking
move.l a0,JVBLTask ; VBL task execute routine
;
; patch in new low memory values for Slot Manager.
; Allocate new memory, initialize it, transfer old values to new data structures,
; dispose of old data structures, and make low mem's point to new data structures.
;
; allocate space for new structures
move.l #sIntGlobalSize,d0 ; alloc space for all possible slots
_NewPtr ,sys,clear ; create table in system heap, cleared
move.l a0,a3 ; save out ptr to new slot manager data structures
; initialize the new structures
lea slotVBLInfos+\
slotVBLQHdr-\
slotVBLInfo(a0),a1 ; setup pointer to first slotVBLInfos record
moveq.l #TotalSlots-1,d0 ; setup loop counter for all possible slots
@init move.l a1,(a0)+ ; point to the slotIntInfo record for this slot
adda.w #sVBLInfoSize,a1 ; point to next slotIntInfo record
dbra d0,@init ; init all possible slots
; copy over data from old structures
; (and YES, to use the new stuff, EVERYTHING must be copied over into place)
; although i guess the SlotVBLPtrs needn't be, since they already point to
; the slotVBLInfos from above.
;Reinstall old slot interrupt handlers
movea.l SlotQDT,a2 ; save ptr to old interrupt handler pointer table
move.l a3, SlotQDT ; point to new structure in lowmem
moveq #sLastSlot,d1 ; start with highest slot
@nextSlot
lea ([-4*sFirstSlot,a2,d1.w *4]),a1 ; get old queue header for this slot
movea.l qHead(a1),a1 ; get ptr to first entry in queue
lea ([SlotQDT],d1.w*4,slotIntQHeads-SQLink),a3 ; get new address of queue head ptr <5.4>
move.l a1,(a3) ; and stuff queue head ptr into it <5.4>
@slotdone subi.w #1,d1 ; next slot number
cmpi.w #sFirstSlot,d1 ; do sLastSlot-sFirstSlot slots
bge.s @nextSlot
movea.l a2, a0 ; get rid of old interrupt handler pointer table
_DisposPtr
;Move the the vbl queue headers into the new structure
moveq #sNumSlots-1,d1 ; move sNumSlots queue headers
lea ([SlotQDT],\ ; point to new first VBL queue header
slotVBLInfos+slotVBLQHdr-\
slotVBLInfo),a1
adda.l #sVBLInfoSize*sLastSlot,a1 ; point to data for last slot
@nxtQhdr
movea.l ([SlotVBLQ],d1.w*4),a0 ; get pointer to old VBLqueue header
moveq #qHeadSize,d0 ; move this many bytes
_BlockMove
suba.l #sVBLInfoSize,a1 ; point to next new queue header
dbra d1,@nxtQhdr
;get the slot of the Main Device and fix the ptr to it's VBL queue header
lea ([ScrnVBLPtr]),a1 ; get pointer to the Main Screen vbl queue
moveq #sNumSlots-1,d0 ;
@nxtScrn
movea.l ([SlotVBLQ],d0.w*4),a0 ; get pointer to old VBLqueue header
cmpa.l a0, a1 ; are we pointing to the Main Screen vbl queue
beq.s @fndScrn ; found it!
dbra d0,@nxtScrn ; didn't find, so check next screen
bra.s @ScrnNotFnd ; we didn't find a pointer at ALL!
@fndScrn
addi.l #sFirstSlot,d0 ; get actual slot number
_AttachVBL ; set ptr to main screen vbl queue
@ScrnNotFnd ; we didn't find a screen; leave ScrnVBLPtr alone
;and dispose the old vbl queue header ptr structure
movea.l SlotVBLQ,a0 ; release storage for old SlotVBLQ
_DisposPtr
move.l #-1,SlotVBLQ ; prevent use-after-free <Sys7.1>
;Copy the tickCounts into the new structures
moveq #sNumSlots-1,d1 ; move sNumSlots queue headers
lea ([SlotQDT],\ ; point to ticks for last slot
slotVBLInfos+slotTickCount-\
slotVBLInfo+sVBLInfoSize*sLastSlot),a1
@nxtTCnt
move.l ([SlotTicks],d1.w*4),(a1) ; move old ticks value to new structure
suba.l #sVBLInfoSize,a1 ; point to next slot info
dbra d1,@nxtTCnt
movea.l SlotTicks,a0 ; release storage for old SlotVBLQ
_DisposPtr
; finally, patch the addresse of the secondary slot interrupt
; handler into the via2 dispatch table
lea SlotInt ,a1 ; addr to patch in
move.l a1,VIA2DT+(4*ifCA1) ; stuff that secondary vector
; restore state
movem.l (sp)+,a0-a3/d0-d3 ; restore saved registers
move.w (sp)+,sr ; disable interrupts while we patch
;_______________________________________________________________________
;<3.7> Slot Interrupt/VBL patch
;
; End of install code to patch in the new Slot Manager and
; SlotVBL stuff into the MacII (NuMac).
;_______________________________________________________________________
;_______________________________________________________________________
skipOSInstalls ; end of the line for OS/hardware <PBxxx> <PB584>
;----------------------------------------------------------------------------------------- <5.7>
; HERE ARE 7.0 FEATURES THAT SHOULD BE PATCHED IN ON A/UX <5.7>
; (There is a separate section for those that are not patched in on A/UX.) <5.7>
;----------------------------------------------------------------------------------------- <5.7>
; <7.2> 09Sep89 BAL 32-Bit QuickDraw ptch for 7.0 and beyond
PtchInst 32
;____________________________________________________________________________ dba <6.0>
; Install default colors 'clut' from System file
; Since the first InitGraf was before the ROvr code, the ROM 'clut' is
; always used. We want to use a better 'clut' from the System file.
; NOTE: This code is straight out of GrafAsm.a.
FixQDColors ; <6.6>
cmp.l #-1,QDColors ; is QDColors initialized? <6.6>
beq.s @done ; no, no need to fix it up <6.6>
SUBQ #4,SP ; make room for function result
MOVE #DefQDColors,-(SP) ; push resource ID
_GetCTable ; get default colors
MOVE.L QDColors,a0 ; get pointer to QDColors
MOVE.L (SP),A1 ; get handle to default colors
MOVE.L (A1),A1 ; point to default colors
ADD #CTTable,A1 ; skip over header
MOVEQ #15,D0 ; need to move 16 longs
@nextLong MOVE.L (A1)+,(A0)+ ; move a long
DBRA D0,@nextLong ; => repeat for all longs
_DisposCTable ; dispose of color table
@done ; <6.6>
;----------------------------------------------------------------------------------------- <6.0>
; HERE ARE PATCHES THAT MUST LOAD AFTER 32-BIT QUICKDRAW, SINCE THEY PATCH QD TRAPS <6.0>
; S497 7June88 med Changed Script Manager to ptch resource <PB??? for 6.0.1 EKH>
PtchInst 4
; Script Manager 7.0 extensions (must be after PtchInst 4 !!) to be included for 6.0.6 builds.
IF installScriptMgrPtch27 THEN ; <6.9> <30>
PtchInst 27 ; <6.9> Must load after ptch 4 !
ENDIF ; <6.9>
;############################### END INSTALL CODE ####################################
;############################# PATCHES CUT BACK CODE #################################
leaFar SysBase,a0 ; start of patch code <6.0>
lea RAMSysInit,a1 ; end of patch code, beginning of install <6.0>
sub.l a0,a1 ; size of patch code <6.0>
move.l a1,d0 ; <6.0>
move.l (sp)+,a0 ; restore the handle passed by SysPatch <6.0>
jmpFar CutBack ; cut us back <6.0>
UsesPtchInst ; PatchInstall Macro code <2.4-4april89-CEL>
Proc
Export FixupTbl
;################## TABLE OF LOCATIONS TO BE OFFSET BY [ROMBase] ########## <PB302>
; <PB302>
; Table contains one entry for each reference to a ROM address from the <PB302>
; JmpROM, JsrROM, and CmpRA macros. &RomFixIndex is a count of the total <PB302>
; number of these references, and is also used to synthesize the label <PB302>
; names for them. The reference labels have the form <PB302>
; RXXX000, RXXX001, RXXX002, ... <PB302>
; See the Macro definitions for JmpROM, JsrROM and CmpRA (near the top of <PB302>
; this file) for more info. <PB302>
; <PB302>
; MkTbl is a macro only because assembler while loops will not work <PB302>
; outside of macros. <PB302>
; <PB302>
MACRO ; <PB302>
MkTbl ; <PB302>
gbla &RomFixIndex ; <PB302>
while &RomFixIndex <> 0 do; <PB302>
&RomFIxIndex seta &RomFixIndex - 1 ; <PB302>
dc.l RXXX&I2S(&ROMFIXINDEX,-3) - FixUpTbl; <PB302>
endwhile ; <PB302>
dc.l 0 ; Zero entry marks end of table. <PB302>
ENDM ; <PB302>
; <PB302>
FixupTbl MkTbl ; <PB302>
; <PB302>
;########################### END PATCHES CUT BACK CODE ################################
EndProc
END