Jump to content
IGNORED

Harmony DPC+ ARM programming


Recommended Posts

As promised, here's the ARM code demo! I didn't finish what I wanted (the 3D projection isn't quite right), but it does show how to call ARM code, which is really all that matters.

 

 

The ARM code is written in C. You'll need to have the appropriate compiler installed. I'm on OS X and used the GCC-3.3 Toolchain found on this page. Here's the direct link to the package.

 

Linux/Windows users should use the one found here. You'll also need to update the Makefile. Specifics on what to change can be found at the top of main.c.

 

 

The C code is found in the custom directory.

 

 

One key thing you need to know about calling ARM Code is that the 6507 is being fed NOPs during the duration of the subroutine. This means the 6507's PC is advancing. If your code takes to long to execute, the 6507 will run past the end of cartridge space. This will crash your program. To maximize subroutine run time, have the STA CALLFUNCTION command towards the start of the 4K bank, this provices plenty of time to run an ARM function for the duration of the vertical blank. At the end of the ARM code, the 6507 is feed a JMP command to pick up after the STA CALLFUNCTION command.

 

NOTE: DPC+ saw numerous revisions since this demo was posted, so this ROM is not compatible with the latest version of Stella. The DPC+ driver is part of the ROM image, so this ROM will work on a Harmony Cartridge.

 

Source

DPCplus ARM code demo.zip

 

Binary

DPC+ ARM Demo.bin

  • Like 2
Link to comment
Share on other sites

  • 11 months later...

As promised, here's the ARM code demo! I didn't finish what I wanted (the 3D projection isn't quite right), but it does show how to call ARM code, which is really all that matters.

 

 

The ARM code is written in C. You'll need to have the appropriate compiler installed. I'm on OS X and used the GCC-3.3 Toolchain found on this page. Here's the direct link to the package.

 

Linux/Windows users should use the one found here. You'll also need to update the Makefile. Specifics on what to change can be found at the top of main.c.

 

 

The C code is found in the custom directory.

 

 

One key thing you need to know about calling ARM Code is that the 6507 is being fed NOPs during the duration of the subroutine. This means the 6507's PC is advancing. If your code takes to long to execute, the 6507 will run past the end of cartridge space. This will crash your program. To maximize subroutine run time, have the STA CALLFUNCTION command towards the start of the 4K bank, this provices plenty of time to run an ARM function for the duration of the vertical blank. At the end of the ARM code, the 6507 is feed a JMP command to pick up after the STA CALLFUNCTION command.

 

Source

DPCplus ARM code demo.zip

 

Binary

DPC+ ARM Demo.bin

 

What happens if you STA CALLFUNCTION from zero page?

Link to comment
Share on other sites

What happens if you STA CALLFUNCTION from zero page?

 

Thinking about it it would probably confuse the harmony about where to feed the nops, but perhaps you could run in zero page for a set time and exit out in time for the harmony to feed the jmp?

 

Also I can't get the demo to work in stella, I'm guessing it doesn't support custom arm code yet?

Edited by eshu
Link to comment
Share on other sites

That does work - but I'd only use it with the $FF version as the 10-15% interrupt overhead of $FE would be wasted since the LDA AMPLITUDE/STA AUDV0 commands it outputs would never be run.

 

I did an experiment of running in ZP last year with a routine that pre-fetched & cached AMPLITUDE data, and the ZP routine would update AUDV0 while the ARM code ran. Turns out you can't pre-fetch AMPLITUDE data though, it resulted in staticy music. That's why we came up with the $FE version for interrupt driven music.

 

The ZP routine I came up with monitors the cartridge space to see when CALLFUNCTION is done as we don't want to hand execution back to cartridge ROM if the ARM is still doing it's thing. This is done by the ldx PosObject instruction. PosObject is a subroutine I put in every single ROM bank, so if I read the first byte of PosObject and don't see #$38 then I know the ARM is still outputting NOP commands. The routine also sets the screen background to a different color if cache data ran out - I was going to use this to let me know if an ARM function ran too long.

; this routine is copied to Zero Page and runs while the ARM is busy.  
       MAC ZP_ROUTINE
       SUBROUTINE
       ; X holds how many Cache values-1
.ZP     ldy #$FF		; 2 67
       sty CALLFUNCTION	; 4 69
.ZPloop
lda CachedAMPLITUDE,x	; 4 73
sta WSYNC		; 3 76/0	
sta AUDV0		; 3  3	
dex			; 2  5	
bpl .ZPloop		; 3  8 - branch taken
.checkARMstate			; 2  7 - branch not taken
ldx PosObject		; 4 11
cpx #$38		; 2 13 - check that we see a SEC command
beq .BCcountdown	; 3 16 - branch taken
ldx #$80		; 2 18 - error color since ARM still running
ERROR_COLOR = * - .ZP - 1	;        offset used to set error color
stx BackgroundColor	; 3 21
ldx #120		; 2 23 - show error color for 2 seconds
stx BCcount		; 3 26
.BCcountdown
ldx BCcount		; 3 29
beq .ZPexit		; 2 31
dex			; 2 33
stx BCcount		; 3 36
bne .ZPexit		; 2 38
ldx #0			; 2 40 - black
stx BackgroundColor	; 3 43
.ZPexit
rts			; 6 49 - 49 = worse case path	
       ENDM    

 

Edit: part of the message was accidentally entered as part of the code's comment. Moved it back to where it belonged.

Source

DPCplus ARM and Music demo 2.zip

Edited by SpiceWare
Link to comment
Share on other sites

Also I can't get the demo to work in stella, I'm guessing it doesn't support custom arm code yet?

I don't think the release build of Stella supports it - you can use the ones that batari posted here.

 

Hmm - the demo crashes Stella on my system. When this demo was written we were still making a lot of changes to DPC+ and ARM support. I'll take a look at it this weekend to see if I can't fix it. In the mean time you can check out other ARM demos like the one I just posted, or follow the development of Frantic in my blog.

Link to comment
Share on other sites

Also I can't get the demo to work in stella, I'm guessing it doesn't support custom arm code yet?

I don't think the release build of Stella supports it - you can use the ones that batari posted here.

 

Hmm - the demo crashes Stella on my system. When this demo was written we were still making a lot of changes to DPC+ and ARM support. I'll take a look at it this weekend to see if I can't fix it. In the mean time you can check out other ARM demos like the one I just posted, or follow the development of Frantic in my blog.

Yes, these older demos will not work. At least two reasons for its failure is that these older demos have ARM code for the setup, and the entry points are different. If you rebuild them with the latest custom.S and lds files, they should work.

Link to comment
Share on other sites

I've replaced those, but it still crashes Stella.

 

There were some compile errors that I fixed, but there's still a bunch of warnings that I don't remember from before. I'm using a different, and newer, compiler than I did when this was originally built.

Link to comment
Share on other sites

I've replaced those, but it still crashes Stella.

 

There were some compile errors that I fixed, but there's still a bunch of warnings that I don't remember from before. I'm using a different, and newer, compiler than I did when this was originally built.

What does the console output look like?

Link to comment
Share on other sites

As I recall, the warnings were mostly about the macros from supercat, as well as a few regarding the matrix functions.

 

My plan when I look at it again this weekend is to revert to the initial, though slower, line drawing routines and see if it works as that would bypass those macros. If that doesn't help, I'd disable the 3D stuff (so the matrix functions aren't used) and test the line drawing routines by themselves.

Link to comment
Share on other sites

Ah - I don't ever run it from command line, so that never crossed my mind.

 

Darrell-Spices-MacBook-Pro:MacOS darrell$ ./Stella 
2011-05-06 14:57:17.448 Stella[940:903] Could not connect the action togglePallette: to target of class Menus
2011-05-06 14:57:17.450 Stella[940:903] Could not connect the action xStartPlus: to target of class Menus
2011-05-06 14:57:17.451 Stella[940:903] Could not connect the action xStartMinus: to target of class Menus
2011-05-06 14:57:17.451 Stella[940:903] Could not connect the action yStartPlus: to target of class Menus
2011-05-06 14:57:17.452 Stella[940:903] Could not connect the action yStartMinus: to target of class Menus
2011-05-06 14:57:17.452 Stella[940:903] Could not connect the action ntscPalMode: to target of class Menus
2011-05-06 14:57:17.452 Stella[940:903] Could not connect the action widthPlus: to target of class Menus
2011-05-06 14:57:17.453 Stella[940:903] Could not connect the action widthMinus: to target of class Menus
2011-05-06 14:57:17.453 Stella[940:903] Could not connect the action heightPlus: to target of class Menus
2011-05-06 14:57:17.454 Stella[940:903] Could not connect the action heightMinus: to target of class Menus
2011-05-06 14:57:17.454 Stella[940:903] Could not connect the action saveProps: to target of class Menus
write16(0x00000048,0x00000880), abort

Link to comment
Share on other sites

Ah - I don't ever run it from command line, so that never crossed my mind.

 

Darrell-Spices-MacBook-Pro:MacOS darrell$ ./Stella 
2011-05-06 14:57:17.448 Stella[940:903] Could not connect the action togglePallette: to target of class Menus
2011-05-06 14:57:17.450 Stella[940:903] Could not connect the action xStartPlus: to target of class Menus
2011-05-06 14:57:17.451 Stella[940:903] Could not connect the action xStartMinus: to target of class Menus
2011-05-06 14:57:17.451 Stella[940:903] Could not connect the action yStartPlus: to target of class Menus
2011-05-06 14:57:17.452 Stella[940:903] Could not connect the action yStartMinus: to target of class Menus
2011-05-06 14:57:17.452 Stella[940:903] Could not connect the action ntscPalMode: to target of class Menus
2011-05-06 14:57:17.452 Stella[940:903] Could not connect the action widthPlus: to target of class Menus
2011-05-06 14:57:17.453 Stella[940:903] Could not connect the action widthMinus: to target of class Menus
2011-05-06 14:57:17.453 Stella[940:903] Could not connect the action heightPlus: to target of class Menus
2011-05-06 14:57:17.454 Stella[940:903] Could not connect the action heightMinus: to target of class Menus
2011-05-06 14:57:17.454 Stella[940:903] Could not connect the action saveProps: to target of class Menus
write16(0x00000048,0x00000880), abort

Not directly related to the topic at hand, but I just committed code that fixes those 'Could not connect the ...' messages.

 

I also plan to add better logging to Stella, so that it's visible from within the application. And I have to fix the problem of errors in ARM code causing Stella to crash. It's OK if your game crashes, but it should never cause the application itself to crash :) I believe it's just an issue of exit() being called, when what should happen is a console pops up showing you the errors.

 

EDIT: could someone post a ROM that caused Stella to crash, and state exactly what error is being printed? I want to get logging support added for the next release, and having a ROM that always crashes would speed things along.

Link to comment
Share on other sites

This is the ROM that's crashing on me.

DPC+ ARM Demo.bin

 

This is what I get from running it in my work computer(when I should be working) :P :

 

post-26314-0-51847200-1304721691_thumb.png

Stella 3.3 doesn't run ARM assembly code, so that's why the app isn't crashing. There's a pre-release of Stella (mentioned above) that you need for ARM support. Or you can wait another 2 weeks, when I release Stella 3.4.

  • Like 1
Link to comment
Share on other sites

This is the ROM that's crashing on me.

DPC+ ARM Demo.bin

 

This is what I get from running it in my work computer(when I should be working) :P :

 

post-26314-0-51847200-1304721691_thumb.png

Stella 3.3 doesn't run ARM assembly code, so that's why the app isn't crashing. There's a pre-release of Stella (mentioned above) that you need for ARM support. Or you can wait another 2 weeks, when I release Stella 3.4.

 

2 WEEKS!?!? Oh alright.. I guess I can handle that. :D

 

Illya

Link to comment
Share on other sites

There was also mention of the DPC+ DataFetchers being set in a HI/LOW fashion causing pointer errors, however in my latest test program build the issue cropped back up and all the DataFetchers are set in a LOW/HI fashion. I'll post the source here that works fine in stella but not on the Harmony cart.

DPCerror.zip

Link to comment
Share on other sites

Ah - I don't ever run it from command line, so that never crossed my mind.

 

Darrell-Spices-MacBook-Pro:MacOS darrell$ ./Stella 
2011-05-06 14:57:17.448 Stella[940:903] Could not connect the action togglePallette: to target of class Menus
2011-05-06 14:57:17.450 Stella[940:903] Could not connect the action xStartPlus: to target of class Menus
2011-05-06 14:57:17.451 Stella[940:903] Could not connect the action xStartMinus: to target of class Menus
2011-05-06 14:57:17.451 Stella[940:903] Could not connect the action yStartPlus: to target of class Menus
2011-05-06 14:57:17.452 Stella[940:903] Could not connect the action yStartMinus: to target of class Menus
2011-05-06 14:57:17.452 Stella[940:903] Could not connect the action ntscPalMode: to target of class Menus
2011-05-06 14:57:17.452 Stella[940:903] Could not connect the action widthPlus: to target of class Menus
2011-05-06 14:57:17.453 Stella[940:903] Could not connect the action widthMinus: to target of class Menus
2011-05-06 14:57:17.453 Stella[940:903] Could not connect the action heightPlus: to target of class Menus
2011-05-06 14:57:17.454 Stella[940:903] Could not connect the action heightMinus: to target of class Menus
2011-05-06 14:57:17.454 Stella[940:903] Could not connect the action saveProps: to target of class Menus
write16(0x00000048,0x00000880), abort

You don't need to run from the command line, just run the console applications in the OSX utilities folder.

 

Anyway, when ARM code crashes, it will always display the offending memory access (and I've since modified it to do a full register dump, and I need to submit that code) but anyway, the problem is there is a write to flash, causing a data abort exception. Not sure why it isn't also happening in Harmony (or is it?)

Link to comment
Share on other sites

I'm working on improving the interaction between Stella and the Thumb emulation right now. The exit()'s are easy enough to fix; I just throw (and catch) an exception instead. But what should we do with it? Here's my opinion, and what I'd like to get done for the next release (in about 2 weeks):

 

1) all exit() in the code are changed to throw an exception, the contents of which will be the text describing the error

 

2) if an exception is caught, the text is shown from within the application, in a window indicating that an error has occurred

 

3) a choice is given to proceed with emulation of the ROM, or exit the ROM

 

I'd like some feedback on #2 and #3. Specifically for #2, adding a full trace of the Thumb internals would be nice. Batari mentioned some code to do this; patches are welcome. As for #3, do we even offer a choice to proceed with the ROM, or simply exit it after the first error?

 

Finally, any other lingering patches/bugfixes for ARM stuff should be done in the next week or so, if you want it included in version 3.4.

Link to comment
Share on other sites

I'm working on improving the interaction between Stella and the Thumb emulation right now. The exit()'s are easy enough to fix; I just throw (and catch) an exception instead. But what should we do with it? Here's my opinion, and what I'd like to get done for the next release (in about 2 weeks):

 

1) all exit() in the code are changed to throw an exception, the contents of which will be the text describing the error

 

2) if an exception is caught, the text is shown from within the application, in a window indicating that an error has occurred

 

3) a choice is given to proceed with emulation of the ROM, or exit the ROM

 

I'd like some feedback on #2 and #3. Specifically for #2, adding a full trace of the Thumb internals would be nice. Batari mentioned some code to do this; patches are welcome. As for #3, do we even offer a choice to proceed with the ROM, or simply exit it after the first error?

 

Finally, any other lingering patches/bugfixes for ARM stuff should be done in the next week or so, if you want it included in version 3.4.

I'll get my code to you when I get home (if I remember...) My code shows the register values, the addresses, values, and other things, and I enhanced the "valid" memory regions (currently, it doesn't return exceptions in some cases when it should.)

 

A trace of the instructions leading up to the error would be fairly simple. Each instruction includes optional text that is printed when DBUG and DISP are set to 1. You could modify these somehow to show a disassembly backward from the PC if needed, or just create a new method that returns the appropriate text.

 

#3 sounds like a good idea. While the ROM may not run right from there, it might be useful for debugging.

Link to comment
Share on other sites

Okay I've figured out why LOW/HI works and yet the demo I posted doesn't.

 

On the Harmony cart you cannot just update the LOW DataFetcher pointer over and over like I do before updating the HI on Carry set, both have to be written to consecutively in the LOW/HI order.

 

So to patch this for now, I just rewrite the HI pointer after updating the LOW. This adds cycle overhead to my loops which update the sprites since I have to update the pointers to the next scanline in ScreenRAM space.

 

But at least this mystery has been solved for now :D

 

@batari, would this be correctable in a firmware update? I am guessing once DFxLOW is written to, the next write expects the HI value? I would much rather update the LOW pointer a few times and retain the HI pointer values till I need them updated, rather than having to write LOW/HI every time LOW needs updated.

Edited by ScumSoft
Link to comment
Share on other sites

Okay I've figured out why LOW/HI works and yet the demo I posted doesn't.

 

On the Harmony cart you cannot just update the LOW DataFetcher pointer over and over like I do before updating the HI on Carry set, both have to be written to consecutively in the LOW/HI order.

 

So to patch this for now, I just rewrite the HI pointer after updating the LOW. This adds cycle overhead to my loops which update the sprites since I have to update the pointers to the next scanline in ScreenRAM space.

 

But at least this mystery has been solved for now :D

 

@batari, would this be correctable in a firmware update? I am guessing once DFxLOW is written to, the next write expects the HI value? I would much rather update the LOW pointer a few times and retain the HI pointer values till I need them updated, rather than having to write LOW/HI every time LOW needs updated.

So, looking at DPC+ code, it definitely clears the HI bits when low is written. I don't remember why I did it this way but there must have been a reason at the time.

 

DPC+ is not in the firmware, but in the binary itself (and for things like this, I'm glad I did it this way.) So, all you need is a new DPC+.arm file to fix any issues. Here's a DPC+.arm that does not clear these bits. Let me know if there are any issues.

DPC+.zip

Link to comment
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

Loading...
  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...