News:

Printed Amstrad Addict magazine announced, check it out here!

Main Menu
avatar_pmeier

Game overwrites AMSDOS. Can I re-enable it?

Started by pmeier, 14:20, 27 November 22

Previous topic - Next topic

0 Members and 1 Guest are viewing this topic.

pmeier

I'm trying to add a level loader to Boulder Dash, so that BDCK levels can be re-loaded from the game.
The game overwrites AMSDOS. AFAIK it does not use mc_start_program.

Is it possible to re-enable AMSDOS again? I have studied various threads with this topic, but none covered an overwritten AMSDOS.

In particular my level loader overwrites the original code at: #16AF

BSC

You can safely enable Amsdos again, but keep in mind that some memory will be overwritten, starting at &a700 normally. You should backup what's there if BD needs it, so you can restore after loading your levels. I don't remember the exacts calls right now, but I am sure you can find it online or maybe a fellow from here will provide it :) 

Why does your loader have to be at &16af, though? 
** My website ** Some music

My hardware: ** Schneider CPC 464 with colour screen, 64k extension, 3" and 5,25 drives and more ** Amstrad CPC 6128 with M4 board, GreaseWeazle.

pmeier

Quote from: BSC on 16:14, 27 November 22Why does your loader have to be at &16af, though?
Thanks, I'll try! &16af is the default level decrunching routine. In case anyone will have a look at it ;D

Nich

Quote from: pmeier on 14:20, 27 November 22Is it possible to re-enable AMSDOS again? I have studied various threads with this topic, but none covered an overwritten AMSDOS.
The following code will reinitialise the AMSDOS ROM:

initialise_amsdos:
    ld hl,(&be7d)       ;Get address where current drive number is stored
    inc hl              ;Move forward 2 bytes to the address where the drive
    inc hl              ;number of the most recently loaded file is stored
    ld a,(hl)           ;Get drive number (A = 0, B = 1)
    push af             ;Store drive number on the stack

    ld de,&40
    ld hl,&b0ff         ;Highest usable byte of memory
    ld c,7              ;AMSDOS ROM is located in slot 7
    call &bcce          ;Initialise the selected ROM

    pop af              ;Get drive number
    ld hl,(&be7d)       ;Get new address where drive number is stored
    ld (hl),a           ;Set drive number
    ret

This, of course, relies on the firmware still being in use. If it isn't, then I can provide additional code to reinitialise the firmware as well (although it gets a bit more complicated as you have to modify the code slightly depending on the model of CPC being used).

pmeier

Quote from: Nich on 20:36, 27 November 22This, of course, relies on the firmware still being in use. If it isn't, then I can provide additional code to reinitialise the firmware as well (although it gets a bit more complicated as you have to modify the code slightly depending on the model of CPC being used).
Indeed the firmware was overwritten, too. I'd love to see your solution.

Nevertheless, your initialise_amsdos routine is very helpful. I'll keep it safe.

tronic


pmeier

@tronic This looks promising! Thank you! It does restore firmware in my artificial tests, but unfortunately within the game it crashes... I guess I'm going to play with this example for some hours...

Nich

Quote from: pmeier on 09:03, 28 November 22Indeed the firmware was overwritten, too. I'd love to see your solution.

Nevertheless, your initialise_amsdos routine is very helpful. I'll keep it safe.

I know @tronic has posted a link to some code, but here is the code I use (which is quite similar):

;This initialisation routine must not be located in the lower ROM area
;i.e. 0-&3FFF)

himem   equ &b0ff       ;Highest usable byte of memory when initialising
                        ;AMSDOS

initialise_amsdos:
    ld bc,&7f88         ;Set the screen to Mode 0 and enable the lower ROM;
    out (c),c           ;change BC to &7F89 for Mode 1, &7F8A for Mode 2
    exx
    xor a
    ex af,af'

    call &0044          ;Initialise the firmware
initialise_firmware_call:
    call &08bd          ;Change address to &0888 for CPC464 machines and &08BB
                        ;for CPC664 machines
    call &bb00
    call &b909          ;Disable the lower ROM

    ld a,&c9            ;&C9 = RET instruction
    ld (&bb5a),a        ;Disable printing of text to the screen

;Initialise all ROMs, including AMSDOS
    ld de,&40
    ld hl,himem         ;Highest usable byte of memory
    ld c,7              ;AMSDOS ROM is located in slot 7
    call &bcce          ;Initialise the selected ROM

    ld a,&ff
    ld (&be78),a        ;Disable disc error message prompts

;Set the drive number to use when loading files

set_drive_number:
    ld a,0              ;0 = drive A, 1 = drive B
    ld (himem-&04ff),a  ;Set the drive number
    ret

And to find out what address you need to use to initialise the firmware, and to set the drive to use (A or B), use this code:

    ld hl,(&bd38)           ;Get the address in the lower ROM that CALL &BD37
                            ;(which initialises the firmware) jumps to
    res 7,h                 ;Set bit 7 of H to zero
    ld (initialise_firmware_call+1),hl  ;Store the address in the
                            ;initialisation routine

    ld hl,(&be7d)           ;Get address where current drive number is stored
    inc hl                  ;Move forward 2 bytes to the address where the drive
    inc hl                  ;number of the most recently loaded file is stored
    ld a,(hl)               ;Get drive number (A = 0, B = 1)
    ld (set_drive_number+1),a   ;Store it in the initialisation routine

pmeier


Powered by SMFPacks Menu Editor Mod