]> git.sur5r.net Git - cc65/commitdiff
Load INITBSS segment from disk.
authorOliver Schmidt <ol.sc@web.de>
Sun, 28 Feb 2016 18:29:37 +0000 (19:29 +0100)
committerOliver Schmidt <ol.sc@web.de>
Sun, 28 Feb 2016 18:45:36 +0000 (19:45 +0100)
Conceptually the INITBSS segment is not initialized in any way. Therefore it makes sense to not load it from disk. However the INIT segment has to be loaded from disk and therefore moved to its run location above the INITBSS segment. The necessary move routine increases runtime RAM usage :-(

Therefore we now "unnecessarily" load the INITBSS segment from disk too meaning that the INIT segment is loaded at its run location. Therefore there's no need for the move routine anymore.

After all we trade disk space for (runtime) RAM space - an easy decision ;-)

Notes:

- The code allowing to re-run a program without re-load present so far could not have worked as far as I can see as it only avoided to re-run the move routine but still tried to re-run the code in the INIT segment that was clobbered by zeroing the BSS. Therefore I removed the code in question altogether. I'm personally not into this "dirty re-run" but if someone wants to add an actually working solution I won't block that.

- INITBSS is intentionally not just merged with the DATA segment as ROM-based targets can't reuse the INIT segment for the BSS and therefore have no reason to place the INIT segment above INITBSS.

- Because ROM-based targets don't copy INITBSS from the ROM (like it is done with the DATA segment) all users of INITBSS _MUST_NOT_ presume INITBSS to be initialized with zeros!

cfg/c64-overlay.cfg
cfg/c64.cfg
libsrc/c64/crt0.s
libsrc/common/moveinit.s [deleted file]

index 1c3b19c09489f1a90b742ba82f36bdea3d186348..522a6d1a6e9c69bc5981dde24f580bc29e1e7f45 100644 (file)
@@ -15,8 +15,7 @@ MEMORY {
     LOADADDR: file = %O,               start = %S - 2,               size = $0002;
     HEADER:   file = %O, define = yes, start = %S,                   size = $000D;
     MAIN:     file = %O, define = yes, start = __HEADER_LAST__,      size = __OVERLAYSTART__ - __STACKSIZE__ - __HEADER_LAST__;
-    MOVE:     file = %O,               start = __INITBSS_LOAD__,     size = __HIMEM__ - __BSS_RUN__;
-    INIT:     file = "",               start = __BSS_RUN__,          size = __HIMEM__ - __BSS_RUN__;
+    INIT:     file = %O,               start = __BSS_RUN__,          size = __HIMEM__ - __BSS_RUN__;
     OVL1ADDR: file = "%O.1",           start = __OVERLAYSTART__ - 2, size = $0002;
     OVL1:     file = "%O.1",           start = __OVERLAYSTART__,     size = __OVERLAYSIZE__;
     OVL2ADDR: file = "%O.2",           start = __OVERLAYSTART__ - 2, size = $0002;
@@ -37,35 +36,35 @@ MEMORY {
     OVL9:     file = "%O.9",           start = __OVERLAYSTART__,     size = __OVERLAYSIZE__;
 }
 SEGMENTS {
-    ZEROPAGE: load = ZP,               type = zp;
-    LOADADDR: load = LOADADDR,         type = ro;
-    EXEHDR:   load = HEADER,           type = ro;
-    STARTUP:  load = MAIN,             type = ro;
-    LOWCODE:  load = MAIN,             type = ro,                optional = yes;
-    CODE:     load = MAIN,             type = ro;
-    RODATA:   load = MAIN,             type = ro;
-    DATA:     load = MAIN,             type = rw;
-    INITBSS:  load = MAIN,             type = bss, define = yes;
-    BSS:      load = MAIN,             type = bss, define = yes;
-    INIT:     load = MOVE, run = INIT, type = ro,  define = yes;
-    OVL1ADDR: load = OVL1ADDR,         type = ro;
-    OVERLAY1: load = OVL1,             type = ro,  define = yes, optional = yes;
-    OVL2ADDR: load = OVL2ADDR,         type = ro;
-    OVERLAY2: load = OVL2,             type = ro,  define = yes, optional = yes;
-    OVL3ADDR: load = OVL3ADDR,         type = ro;
-    OVERLAY3: load = OVL3,             type = ro,  define = yes, optional = yes;
-    OVL4ADDR: load = OVL4ADDR,         type = ro;
-    OVERLAY4: load = OVL4,             type = ro,  define = yes, optional = yes;
-    OVL5ADDR: load = OVL5ADDR,         type = ro;
-    OVERLAY5: load = OVL5,             type = ro,  define = yes, optional = yes;
-    OVL6ADDR: load = OVL6ADDR,         type = ro;
-    OVERLAY6: load = OVL6,             type = ro,  define = yes, optional = yes;
-    OVL7ADDR: load = OVL7ADDR,         type = ro;
-    OVERLAY7: load = OVL7,             type = ro,  define = yes, optional = yes;
-    OVL8ADDR: load = OVL8ADDR,         type = ro;
-    OVERLAY8: load = OVL8,             type = ro,  define = yes, optional = yes;
-    OVL9ADDR: load = OVL9ADDR,         type = ro;
-    OVERLAY9: load = OVL9,             type = ro,  define = yes, optional = yes;
+    ZEROPAGE: load = ZP,       type = zp;
+    LOADADDR: load = LOADADDR, type = ro;
+    EXEHDR:   load = HEADER,   type = ro;
+    STARTUP:  load = MAIN,     type = ro;
+    LOWCODE:  load = MAIN,     type = ro,                optional = yes;
+    CODE:     load = MAIN,     type = ro;
+    RODATA:   load = MAIN,     type = ro;
+    DATA:     load = MAIN,     type = rw;
+    INITBSS:  load = MAIN,     type = rw;
+    BSS:      load = MAIN,     type = bss, define = yes;
+    INIT:     load = INIT,     type = ro;
+    OVL1ADDR: load = OVL1ADDR, type = ro;
+    OVERLAY1: load = OVL1,     type = ro,  define = yes, optional = yes;
+    OVL2ADDR: load = OVL2ADDR, type = ro;
+    OVERLAY2: load = OVL2,     type = ro,  define = yes, optional = yes;
+    OVL3ADDR: load = OVL3ADDR, type = ro;
+    OVERLAY3: load = OVL3,     type = ro,  define = yes, optional = yes;
+    OVL4ADDR: load = OVL4ADDR, type = ro;
+    OVERLAY4: load = OVL4,     type = ro,  define = yes, optional = yes;
+    OVL5ADDR: load = OVL5ADDR, type = ro;
+    OVERLAY5: load = OVL5,     type = ro,  define = yes, optional = yes;
+    OVL6ADDR: load = OVL6ADDR, type = ro;
+    OVERLAY6: load = OVL6,     type = ro,  define = yes, optional = yes;
+    OVL7ADDR: load = OVL7ADDR, type = ro;
+    OVERLAY7: load = OVL7,     type = ro,  define = yes, optional = yes;
+    OVL8ADDR: load = OVL8ADDR, type = ro;
+    OVERLAY8: load = OVL8,     type = ro,  define = yes, optional = yes;
+    OVL9ADDR: load = OVL9ADDR, type = ro;
+    OVERLAY9: load = OVL9,     type = ro,  define = yes, optional = yes;
 }
 FEATURES {
     CONDES: type    = constructor,
index 2a105c7f1cd9a35a1b5dd74b9469b22029865725..8ff7db03cf40bc3a84a5b62928b09b3ce793c4b5 100644 (file)
@@ -12,21 +12,20 @@ MEMORY {
     LOADADDR: file = %O,               start = %S - 2,           size = $0002;
     HEADER:   file = %O, define = yes, start = %S,               size = $000D;
     MAIN:     file = %O, define = yes, start = __HEADER_LAST__,  size = __HIMEM__ - __STACKSIZE__ - __HEADER_LAST__;
-    MOVE:     file = %O,               start = __INITBSS_LOAD__, size = __HIMEM__ - __BSS_RUN__;
-    INIT:     file = "",               start = __BSS_RUN__,      size = __HIMEM__ - __BSS_RUN__;
+    INIT:     file = %O,               start = __BSS_RUN__,      size = __HIMEM__ - __BSS_RUN__;
 }
 SEGMENTS {
-    ZEROPAGE: load = ZP,               type = zp;
-    LOADADDR: load = LOADADDR,         type = ro;
-    EXEHDR:   load = HEADER,           type = ro;
-    STARTUP:  load = MAIN,             type = ro;
-    LOWCODE:  load = MAIN,             type = ro,                optional = yes;
-    CODE:     load = MAIN,             type = ro;
-    RODATA:   load = MAIN,             type = ro;
-    DATA:     load = MAIN,             type = rw;
-    INITBSS:  load = MAIN,             type = bss, define = yes;
-    BSS:      load = MAIN,             type = bss, define = yes;
-    INIT:     load = MOVE, run = INIT, type = ro,  define = yes;
+    ZEROPAGE: load = ZP,       type = zp;
+    LOADADDR: load = LOADADDR, type = ro;
+    EXEHDR:   load = HEADER,   type = ro;
+    STARTUP:  load = MAIN,     type = ro;
+    LOWCODE:  load = MAIN,     type = ro,                optional = yes;
+    CODE:     load = MAIN,     type = ro;
+    RODATA:   load = MAIN,     type = ro;
+    DATA:     load = MAIN,     type = rw;
+    INITBSS:  load = MAIN,     type = rw;
+    BSS:      load = MAIN,     type = bss, define = yes;
+    INIT:     load = INIT,     type = ro,  define = yes;
 }
 FEATURES {
     CONDES: type    = constructor,
index 78268422b0e4f9599597c0c82c80d6939c9e88b5..ea7867925f96fefaa971d941a10dfc5af9d2a9e7 100644 (file)
@@ -6,7 +6,7 @@
         .export         __STARTUP__ : absolute = 1      ; Mark as startup
 
         .import         initlib, donelib
-        .import         moveinit, zerobss, callmain
+        .import         zerobss, callmain
         .import         BSOUT
         .import         __MAIN_START__, __MAIN_SIZE__   ; Linker generated
         .import         __STACKSIZE__                   ; from configure file
 
 Start:
 
-; Switch to the second charset.
-
-        lda     #14
-        jsr     BSOUT
-
 ; Switch off the BASIC ROM.
 
         lda     $01
@@ -39,22 +34,10 @@ Start:
         tsx
         stx     spsave          ; Save the system stack ptr
 
-; Allow some re-entrancy by skipping the next task if it already was done.
-; This sometimes can let us rerun the program without reloading it.
-
-        ldx     move_init
-        beq     L0
-
-; Move the INIT segment from where it was loaded (over the bss segments)
-; into where it must be run (over the BSS segment).
-
-        jsr     moveinit
-        dec     move_init       ; Set to false
-
 ; Save space by putting some of the start-up code in the INIT segment,
 ; which can be re-used by the BSS segment, the heap and the C stack.
 
-L0:     jsr     runinit
+        jsr     init
 
 ; Clear the BSS data.
 
@@ -98,7 +81,7 @@ L2:     lda     zpsave,x
 
 .segment        "INIT"
 
-runinit:
+init:
 
 ; Save the zero-page locations that we need.
 
@@ -115,6 +98,11 @@ L1:     lda     sp,x
         sta     sp
         stx     sp+1            ; Set argument stack ptr
 
+; Switch to the second charset.
+
+        lda     #14
+        jsr     BSOUT
+
 ; Call the module constructors.
 
         jmp     initlib
@@ -123,17 +111,8 @@ L1:     lda     sp,x
 ; ------------------------------------------------------------------------
 ; Data
 
-.data
-
-; These two variables were moved out of the BSS segment, and into DATA, because
-; we need to use them before INIT is moved off of BSS, and before BSS is zeroed.
+.segment        "INITBSS"
 
 mmusave:.res    1
 spsave: .res    1
-
-move_init:
-        .byte   1
-
-.segment        "INITBSS"
-
 zpsave: .res    zpspace
diff --git a/libsrc/common/moveinit.s b/libsrc/common/moveinit.s
deleted file mode 100644 (file)
index 2b22be0..0000000
+++ /dev/null
@@ -1,45 +0,0 @@
-;
-; 2015-10-07, Greg King
-;
-
-        .export         moveinit
-
-        .import         __INIT_LOAD__, __INIT_RUN__, __INIT_SIZE__ ; Linker-generated
-
-        .macpack        cpu
-        .macpack        generic
-
-
-; Put this in the DATA segment because it is self-modifying code.
-
-.data
-
-; Move the INIT segment from where it was loaded (over the bss segments)
-; into where it must be run (over the BSS segment).  The two areas might overlap;
-; and, the segment is moved upwards.  Therefore, this code starts at the highest
-; address, and decrements to the lowest address.  The low bytes of the starting
-; pointers are not sums.  The high bytes are sums; but, they do not include the
-; carry.  Both the low-byte sums and the carries will be done when the pointers
-; are indexed by the .Y register.
-
-moveinit:
-
-; First, move the last, partial page.
-; Then, move all of the full pages.
-
-        ldy     #<__INIT_SIZE__         ; size of partial page
-        ldx     #>__INIT_SIZE__ + (<__INIT_SIZE__ <> 0)  ; number of pages, including partial
-
-L1:     dey
-init_load:
-        lda     __INIT_LOAD__ + (__INIT_SIZE__ & $FF00) - $0100 * (<__INIT_SIZE__ = 0),y
-init_run:
-        sta     __INIT_RUN__  + (__INIT_SIZE__ & $FF00) - $0100 * (<__INIT_SIZE__ = 0),y
-        tya
-        bnz     L1                      ; page not finished
-
-        dec     init_load+2
-        dec     init_run+2
-        dex
-        bnz     L1                      ; move next page
-        rts