]> git.sesse.net Git - pistorm/blobdiff - platforms/amiga/piscsi/device_driver_amiga/bootrom.s
Some non-working loading of file systems from disk for PiSCSI
[pistorm] / platforms / amiga / piscsi / device_driver_amiga / bootrom.s
index 50c70c19fc2fef2202903cde690b8c55daac2130..18826aa07edee6dd74a98a43fbd810f25f398db2 100644 (file)
-/* ConfigDev passed in a3 */
-/*
-struct ConfigDev {
-    struct Node   cd_Node; // 0  2ptr,2byte,1ptr = 14byte
-    UBYTE   cd_Flags; // 14
-    UBYTE   cd_Pad; // 15
-    struct ExpansionRom cd_Rom; // 16   16bytes
-    APTR    cd_BoardAddr; // 32
-    ...
-*/
-.set SysBase,4
-.set OpenLibrary,-552
-.set CloseLibrary,-414
-.set PutStr,-948
-.set VPrintf,-954
-.set AllocMem,-198
-.set FindResident,-96
-
-start:
-    jmp realstart(pc)
-    handover:
-    jmp trampoline(pc)
-
-.align 4
-realstart:
-    movea.l SysBase,a6 /* allocate RAM for loading ourselves to */
-    move.l #0x40000,d0
-    moveq #0,d1 /* MEMF_ANY */
-    jsr AllocMem(a6)
-    tst.l d0
-    beq allocfail
-
-    move.l d0, a4 /* load addr */
-
-    move.l (a7)+,a3 /* restore configdev address from stack */
-    jmp 0x24(a4) /* jmp to handover at new memory location (0x20+0x04) */
-
-.align 4
-allocfail:  
-    move.l d1,0xdff180
-    add.l #1,d1
-    bra allocfail
-
-/* we will arrive here in our copy in amiga RAM */
-/* a0 contains board addr, a3 contains configdev addr */
-.align 4
-trampoline:
-    lea configdev(pc),a1
-    move.l a3,(a1) /* store configdev pointer */
-
-    move.l a4, a0 /* board addr not needed anymore, keep loadaddr in a0 */
-
-    /* add resident ---------------------- */
-
-    /* mntsd.device is at loadaddr + 0x400 (skip 2 blocks) */
-    move.l  a0,-(a7)
-    add.l   #0x400, a0
-    /* relocate the binary (hunk) */
-    jsr     relocstart(pc)
-    move.l  (a7)+, a0 /* address of loaded mntsd.device */
-    move.l  a0, a4
-    move.l  a4, a1 /* restore board addr */
-
-    add.l   #0x400+0x180, a1 /* start of mntsd.device + $180 = romtag FIXME */
-    move.l  #0, d1 /* no seglist */
-    move.l  4,a6
-    jsr     -102(a6) /* InitResident */
-    /* object = InitResident(resident, segList) */
-    /* D0                    A1        D1 */
-
-    /* make dos node --------------------- */
-
-    jmp initdos(pc)
-
-.align 4
-configdev:
-    .long 0
-
-segtprs:
-    .long 0
-    .long 0
-
-    .align 4
-    relocstart:
-    lea.l  segptrs(pc), a1
-
-    move.l 8(a0), d4 /* number of hunks */
-    move.l #0, d5
-
-    /*
-        a0: executable base addr
-        a1: segptrs
-        a2: addr of hunk0
-
-        d4: numhunks
-        d5: pass#
-        d6: current hunk addr
-    */
-
-    /* hunk 0 address in memory */
-    move.l a0, d6
-    add.l  #0x24, d6
-    move.l d6, a2 /* addr of first hunk */
-    move.l d6, (a1) /* store pointer to this hunk in segptrs[1] */
-
-relocpass:
-    move.l a2, a3
-    move.l 0x14(a0), d0 /* ptr to first hunk size */
-
-    lsl.l  #2, d0 /* firsthunk + first size */
-    add.l  d0, a3 /* end of first hunk, start of reloc table */
-
-    jsr  reloctables(pc)
-
-    add.l  #4, a3 /* skip hunk_end */
-    add.l  #4, a3 /* skip hunk_data */
-    move.l (a3)+, d0 /* size of data hunk */
-    lsl.l  #2, d0
-
-    move.l a3, 4(a1) /* store pointer to this hunk in segptrs[1] */
-    move.l a3, d6 /* save current hunk ptr for patching CHECKME */
-    add.l  d0, a3 /* arrive at reloc tables of data hunk */
-
-    jsr   reloctables(pc)
-
-    cmp #1, d5
-    bge rcomplete
-
-    /* start pass 1 */
-    move.l #1, d5
-    move.l a2, d6 /* addr of first hunk */
-    bra relocpass
-
-rcomplete:
-    rts
-
-.align 4
-reloctables:
-    move.l (a3)+, d2 /* skip 0000 03ec marker */
-    reloctable:
-    move.l (a3)+, d2 /* number of relocs to process */
-
-    tst.w  d2
-    beq    relocdone /* done if zero */
-
-    move.l (a3)+, d1  /* segment number to point to */
-
-    lsl.l #2, d1
-    move.l (a1,d1), d1 /* offset to add to target slots */
-
-    bra rloop
-relocloop:
-    move.l (a3)+, a4
-
-    tst.w d5 /* pass = 0? */
-    beq rloop
-
-    /* pass = 1, so patch */
-    add.l  d6, a4 /* add current hunk address */
-    add.l  d1, (a4) /* the actual patching */
-
-    move.l d1, 0xdff180
-    rloop:
-    dbra   d2, relocloop
-    jmp reloctable(pc)
-    relocdone:
-    rts
-
-.align 4
-initdos:  
-    move.l  4,a6
-    lea     expansionname(pc),a1
-
-    moveq   #37, d0
-    jsr     OpenLibrary(a6) /* open expansion.library */
-    tst.l   d0
-    beq.s   nodos
-    move.l  d0,a6
-
-        /*movem.l a0-a6/d0-d6,-(a7)
-        move.l #0xbeef,d2
-        lea.l fmtdebug(pc),a1
-        jsr printf(pc)
-        movem.l (a7)+,a0-a6/d0-d6*/
-
-    lea     dosnode(pc),a0
-    lea     diskname(pc),a1
-    move.l  a1,(a0) /* store in parmpkt */
-    lea     devicename(pc),a1
-    move.l  a1,4(a0) /* store in parmpkt */
-
-    jsr     -144(a6) /* MakeDosNode */
-    move.l  d0, a0 /* fresh device node */
-
-    /* add boot node --------------------- */
-
-    move.l  #0, d0
-    move.l  #0, d1
-    move.l configdev(pc),a1
-    /*move.l  #0, a1*/ /* later put ConfigDev here (a3) */
-    jsr     -36(a6) /* AddBootNode */
-
-    move.l  a6,a1 /* close expansion library */
-    move.l  4,a6
-    jsr     CloseLibrary(a6)
-    moveq   #1,d0
-    move.l  (a7)+,a6
-    rts
-
-nodos:
-    move.l d1,0xdff180
-    add.l #1,d1
-    bra nodos
-
-    moveq   #1,d0
-    move.l  (a7)+,a6
-    rts
-
-.align 4
-diskname:
-    .asciz "PDH0"
-    .align 4
-devicename:
-    .asciz "pi-scsi.device"
-    .align 4
-expansionname:
-    .asciz "expansion.library"
-    .align 4
-dosnode:
-    .long 0 /* dos disk name */
-    .long 0 /* device file name */
-    .long 0 /* unit */
-    .long 0 /* flags */
-    .long 16 /* length of node? */
-    .long 128 /* longs in a block */
-    .long 0
-    .long 4 /* surfaces */
-    .long 1 /* sectors per block */
-    .long 256 /* blocks per track */
-    .long 2 /* reserved bootblocks 256 = 128KB */
-    .long 0
-    .long 0
-    .long 2  /* lowcyl FIXME */
-    /*.long 2047*/ /* hicyl */
-    .long 1023
-    .long 10 /* buffers */
-    .long 0 /* MEMF_ANY */
-    .long 0x0001fe00 /* MAXTRANS */
-    .long 0x7ffffffe /* Mask */
-    .long -1 /* boot prio */
-    .long 0x444f5303 /* dostype: DOS3 */
+**
+** Sample autoboot code fragment
+**
+** These are the calling conventions for the Diag routine
+**
+** A7 -- points to at least 2K of stack
+** A6 -- ExecBase
+** A5 -- ExpansionBase
+** A3 -- your board's ConfigDev structure
+** A2 -- Base of diag/init area that was copied
+** A0 -- Base of your board
+**
+** Your Diag routine should return a non-zero value in D0 for success.
+** If this value is NULL, then the diag/init area that was copied
+** will be returned to the free memory pool.
+**
+
+    INCLUDE "exec/types.i"
+    INCLUDE "exec/nodes.i"
+    INCLUDE "exec/resident.i"
+    INCLUDE "libraries/configvars.i"
+    INCLUDE "libraries/expansionbase.i"
+
+    ; LVO's resolved by linking with library amiga.lib
+    XREF   _LVOFindResident
+
+ROMINFO     EQU      0
+ROMOFFS     EQU     $4000
+
+* ROMINFO defines whether you want the AUTOCONFIG information in
+* the beginning of your ROM (set to 0 if you instead have PALS
+* providing the AUTOCONFIG information instead)
+*
+* ROMOFFS is the offset from your board base where your ROMs appear.
+* Your ROMs might appear at offset 0 and contain your AUTOCONFIG
+* information in the high nibbles of the first $40 words ($80 bytes).
+* Or, your autoconfig ID information may be in a PAL, with your
+* ROMs possibly being addressed at some offset (for example $2000)
+* from your board base.  This ROMOFFS constant will be used as an
+* additional offset from your configured board address when patching
+* structures which require absolute pointers to ROM code or data.
+
+*----- We'll store Version and Revision in serial number
+VERSION            EQU 37              ; also the high word of serial number
+REVISION           EQU 1               ; also the low word of serial number
+
+* See the Addison-Wesley Amiga Hardware Manual for more info.
+    
+MANUF_ID           EQU 2011            ; CBM assigned (2011 for hackers only)
+PRODUCT_ID         EQU 1               ; Manufacturer picks product ID
+
+BOARDSIZE          EQU $10000          ; How much address space board decodes
+SIZE_FLAG          EQU 3               ; Autoconfig 3-bit flag for BOARDSIZE
+                                       ;   0=$800000(8meg)  4=$80000(512K)
+                                       ;   1=$10000(64K)    5=$100000(1meg)
+                                       ;   2=$20000(128K)   6=$200000(2meg)
+                                       ;   3=$40000(256K)   7=$400000(4meg)
+                CODE
+
+; Exec stuff
+AllocMem        EQU -198
+InitResident    EQU -102
+FindResident    EQU -96
+OpenLibrary     EQU -552
+CloseLibrary    EQU -414
+OpenResource    EQU -$1F2
+AddResource     EQU -$1E6
+Enqueue         EQU -$10E
+AddMemList      EQU -$26A
+
+; Expansion stuff
+MakeDosNode     EQU -144
+AddDosNode      EQU -150
+AddBootNode     EQU -36
+
+; PiSCSI stuff
+PiSCSIAddr1     EQU $80000010
+PiSCSIAddr2     EQU $80000014
+PiSCSIAddr3     EQU $80000018
+PiSCSIAddr4     EQU $8000001C
+PiSCSIDebugMe   EQU $80000020
+PiSCSIDriver    EQU $80000040
+PiSCSINextPart  EQU $80000044
+PiSCSIGetPart   EQU $80000048
+PiSCSIGetPrio   EQU $8000004C
+PiSCSIGetFS     EQU $80000060
+PiSCSINextFS    EQU $80000064
+PiSCSICopyFS    EQU $80000068
+PiSCSIFSSize    EQU $8000006C
+PiSCSISetFSH    EQU $80000070
+PiSCSILoadFS    EQU $80000084
+PiSCSIGetFSInfo EQU $80000088
+PiSCSIDbg1      EQU $80001010
+PiSCSIDbg2      EQU $80001014
+PiSCSIDbg3      EQU $80001018
+PiSCSIDbg4      EQU $8000101C
+PiSCSIDbg5      EQU $80001020
+PiSCSIDbg6      EQU $80001024
+PiSCSIDbg7      EQU $80001028
+PiSCSIDbg8      EQU $8000102C
+PiSCSIDbgMsg    EQU $80001000
+
+*******  RomStart  ***************************************************
+**********************************************************************
+
+RomStart:
+
+*******  DiagStart  **************************************************
+DiagStart:  ; This is the DiagArea structure whose relative offset from
+            ; your board base appears as the Init Diag vector in your
+            ; autoconfig ID information.  This structure is designed
+            ; to use all relative pointers (no patching needed).
+            dc.b    DAC_WORDWIDE+DAC_CONFIGTIME    ; da_Config
+            dc.b    0                              ; da_Flags
+            dc.w    $4000              ; da_Size
+            dc.w    DiagEntry-DiagStart            ; da_DiagPoint
+            dc.w    BootEntry-DiagStart            ; da_BootPoint
+            dc.w    DevName-DiagStart              ; da_Name
+            dc.w    0                              ; da_Reserved01
+            dc.w    0                              ; da_Reserved02
+
+*******  Resident Structure  *****************************************
+Romtag:
+            dc.w    RTC_MATCHWORD      ; UWORD RT_MATCHWORD
+rt_Match:   dc.l    Romtag-DiagStart   ; APTR  RT_MATCHTAG
+rt_End:     dc.l    EndCopy-DiagStart  ; APTR  RT_ENDSKIP
+            dc.b    RTW_COLDSTART      ; UBYTE RT_FLAGS
+            dc.b    VERSION            ; UBYTE RT_VERSION
+            dc.b    NT_DEVICE          ; UBYTE RT_TYPE
+            dc.b    20                 ; BYTE  RT_PRI
+rt_Name:    dc.l    DevName-DiagStart  ; APTR  RT_NAME
+rt_Id:      dc.l    IdString-DiagStart ; APTR  RT_IDSTRING
+rt_Init:    dc.l    Init-RomStart      ; APTR  RT_INIT
+
+
+******* Strings referenced in Diag Copy area  ************************
+DevName:    dc.b    'pi-scsi.device',0,0                      ; Name string
+IdString    dc.b    'PISCSI v0.8',0   ; Id string
+
+DosName:        dc.b    'dos.library',0                ; DOS library name
+ExpansionName:  dc.b    "expansion.library",0
+LibName:        dc.b    "pi-scsi.device",0,0
+
+DosDevName: dc.b    'ABC',0        ; dos device name for MakeDosNode()
+                                   ;   (dos device will be ABC:)
+
+            ds.w    0              ; word align
+
+*******  DiagEntry  **************************************************
+**********************************************************************
+*
+*   success = DiagEntry(BoardBase,DiagCopy, configDev)
+*   d0                  a0         a2                  a3
+*
+*   Called by expansion architecture to relocate any pointers
+*   in the copied diagnostic area.   We will patch the romtag.
+*   If you have pre-coded your MakeDosNode packet, BootNode,
+*   or device initialization structures, they would also need
+*   to be within this copy area, and patched by this routine.
+*
+**********************************************************************
+
+DiagEntry:
+            align 2
+            nop
+            nop
+            nop
+            move.l #1,PiSCSIDebugMe
+            move.l a3,PiSCSIAddr1
+            nop
+            nop
+            nop
+            nop
+            nop
+            nop
+
+            lea      patchTable-RomStart(a0),a1   ; find patch table
+            adda.l   #ROMOFFS,a1                  ; adjusting for ROMOFFS
+
+* Patch relative pointers to labels within DiagCopy area
+* by adding Diag RAM copy address.  These pointers were coded as
+* long relative offsets from base of the DiagArea structure.
+*
+dpatches:
+            move.l   a2,d1           ;d1=base of ram Diag copy
+dloop:
+            move.w   (a1)+,d0        ;d0=word offs. into Diag needing patch
+            bmi.s    bpatches        ;-1 is end of word patch offset table
+            add.l    d1,0(a2,d0.w)   ;add DiagCopy addr to coded rel. offset
+            bra.s    dloop
+
+* Patches relative pointers to labels within the ROM by adding
+* the board base address + ROMOFFS.  These pointers were coded as
+* long relative offsets from RomStart.
+*
+bpatches:
+            move.l   a0,d1           ;d1 = board base address
+            add.l    #ROMOFFS,d1     ;add offset to where your ROMs are
+rloop:
+            move.w   (a1)+,d0        ;d0=word offs. into Diag needing patch
+            bmi.s   endpatches       ;-1 is end of patch offset table
+            add.l   d1,0(a2,d0.w)    ;add ROM address to coded relative offset
+            bra.s   rloop
+
+endpatches:
+            moveq.l #1,d0           ; indicate "success"
+            rts
+
+
+*******  BootEntry  **************************************************
+**********************************************************************
+
+BootEntry:
+            align 2
+            move.l #2,PiSCSIDebugMe
+            lea DosName(pc),a1
+            jsr FindResident(a6)
+            tst.l d0
+            beq.b .End
+            move.l d0,a0
+            move.l RT_INIT(a0),a0
+            jmp (a0)
+.End
+            moveq.l #1,d0           ; indicate "success"
+            rts
+
+*
+* End of the Diag copy area which is copied to RAM
+*
+EndCopy:
+*************************************************************************
+
+*************************************************************************
+*
+*   Beginning of ROM driver code and data that is accessed only in
+*   the ROM space.  This must all be position-independent.
+*
+
+patchTable:
+* Word offsets into Diag area where pointers need Diag copy address added
+            dc.w   rt_Match-DiagStart
+            dc.w   rt_End-DiagStart
+            dc.w   rt_Name-DiagStart
+            dc.w   rt_Id-DiagStart
+            dc.w   -1
+
+* Word offsets into Diag area where pointers need boardbase+ROMOFFS added
+            dc.w   rt_Init-DiagStart
+            dc.w   -1
+
+*******  Romtag InitEntry  **********************************************
+*************************************************************************
+
+Init:       ; After Diag patching, our romtag will point to this
+            ; routine in ROM so that it can be called at Resident
+            ; initialization time.
+            ; This routine will be similar to a normal expansion device
+            ; initialization routine, but will MakeDosNode then set up a
+            ; BootNode, and Enqueue() on eb_MountList.
+            ;
+            align 2
+            move.l a6,-(a7)             ; Push A6 to stack
+            move.w #$00B8,$dff09a       ; Disable interrupts during init
+            move.l  #3,PiSCSIDebugMe
+            move.l a3,PiSCSIAddr4
+
+            movea.l 4,a6
+
+            move.l $10000040,d1
+            move.l #$feffeeff,$10000040
+            move.l $10000040,d0
+            cmp.l #$feffeeff,d0
+            bne.s NoZ3
+            move.l d1,$10000040
+
+            move.l #$8000000,d0         ; Add some Z3 fast RAM if it hasn't been moved (Kick 1.3)
+            move.l #$405,d1
+            move.l #10,d2
+            move.l #$10000000,a0
+            move.l #0,a1
+            jsr AddMemList(a6)
+
+NoZ3:
+            move.l  #11,PiSCSIDebugMe
+            lea LibName(pc),a1
+            jsr FindResident(a6)
+            move.l  #10,PiSCSIDebugMe
+            cmp.l #0,d0
+            bne.s SkipDriverLoad        ; Library is already loaded, jump straight to partitions
+
+            move.l  #4,PiSCSIDebugMe
+            movea.l 4,a6
+            move.l #$40000,d0
+            moveq #0,d1
+            jsr AllocMem(a6)            ; Allocate memory for the PiStorm to copy the driver to
+
+            move.l  d0,PiSCSIDriver     ; Copy the PiSCSI driver to allocated memory and patch offsets
+
+            move.l  #5,PiSCSIDebugMe
+            move.l  d0,a1
+            move.l  #0,d1
+            movea.l  4,a6
+            add.l #$02c,a1
+            jsr InitResident(a6)        ; Initialize the PiSCSI driver
+
+SkipDriverLoad:
+            move.l  #9,PiSCSIDebugMe
+            jsr LoadFileSystems(pc)
+
+FSLoadExit:
+            lea ExpansionName(pc),a1
+            moveq #0,d0
+            jsr OpenLibrary(a6)         ; Open expansion.library to make this work, somehow
+            move.l a6,a4
+            move.l d0,a6
+
+            move.l  #7,PiSCSIDebugMe
+PartitionLoop:
+            move.l PiSCSIGetPart,d0     ; Get the available partition in the current slot
+            beq.w EndPartitions         ; If the next partition returns 0, there's no additional partitions
+            move.l d0,a0
+            jsr MakeDosNode(a6)
+            ;cmp.l #0,PiSCSIGetFSInfo      ; This does not work for some reason... not massively surprising...
+            ;beq.s SkipLoadFS
+
+            ;move.l d0,PiSCSILoadFS        ; Attempt to load the file system driver from data/fs
+            ;cmp.l #$FFFFFFFF,PiSCSIAddr4
+            ;beq SkipLoadFS
+
+            ;jsr LoadFileSystems(pc)
+
+SkipLoadFS:
+            move.l d0,PiSCSISetFSH
+            move.l d0,PiSCSIAddr2       ; Put DeviceNode address in PiSCSIAddr2, because I'm useless
+            move.l d0,a0
+            move.l PiSCSIGetPrio,d0
+            move.l #0,d1
+            move.l PiSCSIAddr1,a1
+
+* Uncomment these lines to test AddDosNode/Enqueue stuff
+* Or comment them out all the way down to and including SkipEnqueue: to use the AddBootNode method instead.
+            cmp.l   #-128,d0
+            bne.s   EnqueueNode
+
+* BOOL AddDosNode( LONG bootPri, ULONG flags, struct DeviceNode *deviceNode );
+* amicall(ExpansionBase, 0x96, AddDosNode(d0,d1,a0))
+            move.l #38,PiSCSIDebugMe
+            jsr AddDosNode(a6)
+            bra.w SkipEnqueue
+* VOID Enqueue( struct List *list, struct Node *node );
+* amicall(SysBase, 0x10e, Enqueue(a0,a1))
+
+EnqueueNode:
+            exg a6,a4
+            ;move.l #35,PiSCSIDebugMe
+            ;move.l #BootNode_SIZEOF,PiSCSIDebugMe
+            ;move.l #NT_BOOTNODE,PiSCSIDebugMe
+            ;move.l #LN_TYPE,PiSCSIDebugMe
+            ;move.l #LN_PRI,PiSCSIDebugMe
+            ;move.l #LN_NAME,PiSCSIDebugMe
+            ;move.l #eb_MountList,PiSCSIDebugMe
+            ;move.l #35,PiSCSIDebugMe
+
+            move.l #BootNode_SIZEOF,d0
+            move.l #$10001,d1
+            jsr AllocMem(a6)            ; Allocate memory for the BootNode
+
+            move.l d0,PiSCSIAddr3
+            move.l #36,PiSCSIDebugMe
+
+            move.l d0,a1
+            move.b #NT_BOOTNODE,LN_TYPE(a1)
+            move.l PiSCSIGetPrio,d0
+            move.b d0,LN_PRI(a1)
+            move.l PiSCSIAddr2,bn_DeviceNode(a1)
+            move.l PiSCSIAddr1,LN_NAME(a1)
+
+            lea eb_MountList(a4),a0
+            jsr Enqueue(a6)
+            exg a6,a4
+
+SkipEnqueue:
+
+* BOOL AddBootNode( LONG bootPri, ULONG flags, struct DeviceNode *deviceNode, struct ConfigDev *configDev );
+* amicall(ExpansionBase, 0x24, AddBootNode(d0,d1,a0,a1))
+* Comment out the line below to test AddDosNode/Enqueue stuff
+*            jsr AddBootNode(a6)
+            move.l #1,PiSCSINextPart    ; Switch to the next partition
+            bra.w PartitionLoop
+
+
+EndPartitions:
+            move.l #8,PiSCSIDebugMe
+            move.l a6,a1
+            move.l #800,PiSCSIDebugMe
+            movea.l 4,a6
+            move.l #801,PiSCSIDebugMe
+            jsr CloseLibrary(a6)
+            move.l #802,PiSCSIDebugMe
+
+            move.l (a7)+,a6             ; Pop A6 from stack
+            move.l #803,PiSCSIDebugMe
+
+            move.w #$80B8,$dff09a       ; Re-enable interrupts
+            move.l #804,PiSCSIDebugMe
+            moveq.l #1,d0               ; indicate "success"
+            move.l #805,PiSCSIDebugMe
+            rts
+
+            align 4
+FileSysName     dc.b    'FileSystem.resource',0
+FileSysCreator  dc.b    'PiStorm',0
+
+CurFS:          dc.l    $0
+FSResource:     dc.l    $0
+
+            align 2
+LoadFileSystems:
+            movem.l d0-d7/a0-a6,-(sp)       ; Push registers to stack
+            move.l #30,PiSCSIDebugMe
+            movea.l 4,a6
+ReloadResource:
+            lea FileSysName(pc),a1
+            jsr OpenResource(a6)
+            tst.l d0
+            bne FSRExists
+
+            move.l #33,PiSCSIDebugMe        ; FileSystem.resource isn't open, create it
+                                            ; Code based on WinUAE filesys.asm
+
+            moveq #32,d0                    ; sizeof(FileSysResource)
+            move.l #$10001,d1
+            jsr AllocMem(a6)
+            move.l d0,a2
+            move.b #8,8(a2)                 ; NT_RESOURCE
+            lea FileSysName(pc),a0
+            move.l a0,10(a2)                ; node name
+            lea FileSysCreator(pc),a0
+            move.l a0,14(a2)                ; fsr_Creator
+            lea 18(a2),a0
+            move.l a0,(a0)                  ; NewList() fsr_FileSysEntries
+            addq.l #4,(a0)
+            move.l a0,8(a0)
+            lea $150(a6),a0                 ; ResourceList
+            move.l a2,a1
+            jsr -$f6(a6)                    ; AddTail
+            move.l a2,a0
+            move.l a0,d0
+
+FSRExists:  
+            move.l d0,PiSCSIAddr2             ; PiSCSIAddr2 is now FileSystem.resource
+            move.l #31,PiSCSIDebugMe
+            move.l PiSCSIAddr2,a0
+            move.l PiSCSIGetFS,d0
+            cmp.l #0,d0
+            beq.w FSDone
+
+FSNext:     
+            move.l #45,PiSCSIDebugMe
+            lea fsr_FileSysEntries(a0),a0
+            move.l a0,d2
+            move.l LH_HEAD(a0),d0
+            beq.w NoEntries
+
+FSLoop:     
+            move.l #34,PiSCSIDebugMe
+            move.l d0,a1
+            move.l #35,PiSCSIDebugMe
+            cmp.l fse_DosType(a1),d7
+            move.l #36,PiSCSIDebugMe
+            beq.w AlreadyLoaded
+            move.l #37,PiSCSIDebugMe
+            move.l LN_SUCC(a1),d0
+            bne.w FSLoop
+            move.l #390,PiSCSIDebugMe
+            bra.w NoEntries
+
+            align 2
+NoEntries:  
+            move.l #39,PiSCSIDebugMe
+            move.l PiSCSIFSSize,d0
+            move.l #40,PiSCSIDebugMe
+            move.l #$10001,d1
+            move.l #41,PiSCSIDebugMe
+            jsr AllocMem(a6)
+            move.l d0,PiSCSIAddr3
+            move.l d0,a0
+            move.l #1,PiSCSICopyFS
+            move.b #NT_RESOURCE,LN_TYPE(a0)
+
+AlreadyLoaded:
+            move.l #480,PiSCSIDebugMe
+            move.l PiSCSIAddr2,a0
+            move.l #1,PiSCSINextFS
+            move.l PiSCSIGetFS,d0
+            cmp.l #0,d0
+            bne.w FSNext
+
+FSDone:     move.l #37,PiSCSIDebugMe
+            move.l #32,PiSCSIDebugMe    ; Couldn't open FileSystem.resource, Kick 1.2/1.3?
+
+            movem.l (sp)+,d0-d7/a0-a6   ; Pop registers from stack
+            rts
+
+FSRes
+    dc.l    0
+    dc.l    0
+    dc.b    NT_RESOURCE
+    dc.b    0
+    dc.l    FileSysName
+    dc.l    FileSysCreator
+.Head
+    dc.l    .Tail
+.Tail
+    dc.l    0
+    dc.l    .Head
+    dc.b    NT_RESOURCE
+    dc.b    0