# Atari VCS 7800 linker configuration file for cc65
# In order to add the a78 header to the build you can add
# "--force-import __EXEHDR__" to the command line

SYMBOLS {
    __STACKSIZE__:        type = weak, value = $0600; # C stack
    __CARTSIZE__:         type = weak, value = $8000;
    __VEC_BOTTOM__:       value = $fffa, type = export;
    __VEC_SIZE__:         value = $6, type = export;
    __ENCRYPT_BOTTOM__:   value = $ff7a, type = export;
    __ENCRYPT_SIZE__:     value = $80, type = export;
    __MEMORY_TOP__:       value = __ENCRYPT_BOTTOM__, type = export;
    __INIT_SIZE__:        value = 156, type = export;
    __MEMORY_INIT__:      value = __MEMORY_TOP__ - __INIT_SIZE__, type = export;
    __MEMORY_BOTTOM__:    value = $10000 - __CARTSIZE__, type = weak;
    __FREE_ROM_SIZE__:    value = __MEMORY_INIT__ - __MEMORY_BOTTOM__, type = export;
}

MEMORY {
    ZP:     file = "", define = yes, start = $0040, size = $00C0, type = rw;
    SP:     file = "", define = yes, start = $0140, size = $00C0, type = rw;
    RAM1:   file = "", define = yes, start = $1800, size = $0840, type = rw;
    RAM2:   file = "", define = yes, start = $2100, size = $0040, type = rw;
    RAM3:   file = "", define = yes, start = $2200, size = $0600, type = rw;
    # For emulators you also need a header file
    HEADER: file = %O, start = $0000, size = 128;
    # "Normal" cartridge rom. Multiple banks arent supported
    # by this script. You may change the rom size, but keep
    # two things in mind:
    # - start must be a multiple of $1000
    # - ROM must end at $ff79
    ROM:    file = %O, define = yes, start = __MEMORY_BOTTOM__, size = __FREE_ROM_SIZE__, type = ro, fill = yes, fillval = $ff;
    ROMS:   file = %O, define = yes, start = __MEMORY_INIT__, size = __INIT_SIZE__, type = ro, fill = yes, fillval = $ff;
    # Encryption stuff
    ROME:   file = %O, start = __ENCRYPT_BOTTOM__, size = __ENCRYPT_SIZE__, type = ro, fill = yes, fillval = $ff;
    # Interrupt vectors
    ROMV:   file = %O, start = __VEC_BOTTOM__, size = __VEC_SIZE__, type = ro, fill = yes, fillval = $ff;
}

SEGMENTS {
    ZEROPAGE:   load = ZP,              type = zp;
    EXTZP:      load = ZP,              type = zp;
    EXEHDR:     load = HEADER,          type = ro,  optional = yes;
    STARTUP:    load = ROMS,            type = ro,  define = yes;
    ONCE:       load = ROMS,            type = ro,  define = yes;
    CODE:       load = ROM,             type = ro,  define = yes;
    RODATA:     load = ROM,             type = ro,  define = yes, align = 256;
    DATA:       load = ROM, run = RAM1, type = rw,  define = yes;
    BSS:        load = RAM1,            type = bss, define = yes;
    VECTORS:    load = ROMV,            type = ro,  define = yes;
    ENCRYPTION: load = ROME,            type = ro   define = yes;
}

FEATURES {
    CONDES: type    = constructor,
            label   = __CONSTRUCTOR_TABLE__,
            count   = __CONSTRUCTOR_COUNT__,
            segment = ONCE;
    CONDES: type    = destructor,
            label   = __DESTRUCTOR_TABLE__,
            count   = __DESTRUCTOR_COUNT__,
            segment = RODATA;
    CONDES: type    = interruptor,
            label   = __INTERRUPTOR_TABLE__,
            count   = __INTERRUPTOR_COUNT__,
            segment = RODATA,
            import  = __CALLIRQ__;
}
