M68000 assemblers with patching functionality?
M68000 assemblers with patching functionality?
Are there any M68k assemblers out there that allow for patching of a ROM using "org" like what currently exists for SNES? I have done some searching and cannot find anything like this. Trying my hand at a SFII: Champion Edition hack for CPS1 and it would be way easier to do it this way than manually transcribe my new code into hex. Thanks.
Re: M68000 assemblers with patching functionality?
ORG does normally tell the assembler to assemble the following instructions as if they located at a given memory address. It doesn't actually take care of moving data to that address, and least mixing it with an existing binary.
What you are looking for might be something like "INCBIN filename,fileoffset,length". You could also make a macro for it, where you specify only the end address in memory, and let the macro load data up to that address, with automatically computed fileoffset and length values.
What you are looking for might be something like "INCBIN filename,fileoffset,length". You could also make a macro for it, where you specify only the end address in memory, and let the macro load data up to that address, with automatically computed fileoffset and length values.
Re: M68000 assemblers with patching functionality?
I'm not 68K-savvy, but I'm not aware of anything like this "for the SNES" with one exception: byuu's bass. I literally haven't seen such a feature in any other assembler in my entire life.
Normally what you're expected to do is disassemble existing code, do the modifications, and reassemble it. For stuff unrelated to the disassembled portion, it's easiest to incbin (or whatever the equivalent is in the assembler) those portions, making sure they "properly line up" (address-wise). It's up to you to make sure things work properly (ex. if code in the incbin'd section does something like jmp {some-address-in-the-disassembled-portion}, and you've moved where that code actually is due to your changes, you've now created quite a bad bug).
Normally what you're expected to do is disassemble existing code, do the modifications, and reassemble it. For stuff unrelated to the disassembled portion, it's easiest to incbin (or whatever the equivalent is in the assembler) those portions, making sure they "properly line up" (address-wise). It's up to you to make sure things work properly (ex. if code in the incbin'd section does something like jmp {some-address-in-the-disassembled-portion}, and you've moved where that code actually is due to your changes, you've now created quite a bad bug).
Re: M68000 assemblers with patching functionality?
Normally, the first ORG just sets the address, but subsequent ORGs will pad until the specified addresses.nocash wrote:ORG does normally tell the assembler to assemble the following instructions as if they located at a given memory address. It doesn't actually take care of moving data to that address, and least mixing it with an existing binary.
There are assemblers that allow overlapping though, but I'm not familiar with 68000 tools.What you are looking for might be something like "INCBIN filename,fileoffset,length". You could also make a macro for it, where you specify only the end address in memory, and let the macro load data up to that address, with automatically computed fileoffset and length values.
Re: M68000 assemblers with patching functionality?
Ah ok. It was some variant of xkas that I was using. Didn't realize this wasn't a standard feature. Doing a full disassembly is kinda out of the question because that would probably take me ten years, so I guess I'll do this the hard way. Thanks for the info.
Re: M68000 assemblers with patching functionality?
And bass is the follow-up to xkas.Sverker wrote:Ah ok. It was some variant of xkas that I was using.
rgblink in RGBDS (Game Boy assembler) also supports an overlay file, used to fill regions where nothing got assembled.
The other way is what I did with my mapper hack of Solar Wars: hack something up with offset and length arguments to .incbin.Doing a full disassembly is kinda out of the question because that would probably take me ten years, so I guess I'll do this the hard way. Thanks for the info.
Re: M68000 assemblers with patching functionality?
I'm thinking now I might just rig up a quick and dirty console app to keep track of everything for me on this specific project. Maybe not the most elegant solution but what can you do.
-
- Posts: 1565
- Joined: Tue Feb 07, 2017 2:03 am
Re: M68000 assemblers with patching functionality?
This isn't anything amazing in terms of assembler, any half decent more than 2 pass assembler should do it. The complication you will have with 68K assemblers is they are very much from the linker era, so you might have to get the linker to do the dirty work. But any assembler that has *= for code starting should do what you want. I would just try assemblers to see. Easy68K or sn68k would be my first port of call.
If they really won't do it, you could use TASS64 as a preprocessor.
Assemble your code to a bin file. then you can just do
*=$000000
.binary "yourbinaryhere.bin"
*=$XXXX
.binary "patch.bin"
*=$YYYYY
.binary "patch2.bin"
etc
you will want to set TASS64 to binary output and 65816 mode so you get the full 16MB address space, assuming your bin file is less than 16MB.
64tass -a -x -b -f
if you need to put it to ROM the --s-record format might be useful to you as that is the Motorola S-record used by burners and downloaders.
PS if you want this for SNES 64tass has full 65816 support and if you want it for NES full N6502 support as well.
If they really won't do it, you could use TASS64 as a preprocessor.
Assemble your code to a bin file. then you can just do
*=$000000
.binary "yourbinaryhere.bin"
*=$XXXX
.binary "patch.bin"
*=$YYYYY
.binary "patch2.bin"
etc
you will want to set TASS64 to binary output and 65816 mode so you get the full 16MB address space, assuming your bin file is less than 16MB.
64tass -a -x -b -f
if you need to put it to ROM the --s-record format might be useful to you as that is the Motorola S-record used by burners and downloaders.
PS if you want this for SNES 64tass has full 65816 support and if you want it for NES full N6502 support as well.
- rainwarrior
- Posts: 8732
- Joined: Sun Jan 22, 2012 12:03 pm
- Location: Canada
- Contact:
Re: M68000 assemblers with patching functionality?
I recently learned that cc65 has an overwrite feature for this purpose. (Doesn't help OP of course.)koitsu wrote:I'm not 68K-savvy, but I'm not aware of anything like this "for the SNES" with one exception: byuu's bass. I literally haven't seen such a feature in any other assembler in my entire life.
Re: M68000 assemblers with patching functionality?
Yeah, I`ve also seen source files for some assemblers using "ORG address" or "*=address" for automatic padding. I don't know if that's actually the widespread normal case, or a misconception, or both ; )tokumaru wrote:Normally, the first ORG just sets the address, but subsequent ORGs will pad until the specified addresses.
For padding to address, I would use things like DUP, FILL, DEFS, REPT, with "address-$" or "address-*" as length. Being able to use ORG for padding might seem useful at first glance, but that automated padding does screw up ability to relocate code manually.
For example, for a NES game, if you relocate code from ROM to RAM, you'd have "ORG 8000h" (rom) containing your relocation function, followed by "ORG 200h" (ram) containing the relocated code, plus "ORG reloc_src+reloc_len" to resume ROM addressing for further ROM code & exception vectors. How would that work on assemblers that apply padding on ORG?
-
- Posts: 1565
- Joined: Tue Feb 07, 2017 2:03 am
Re: M68000 assemblers with patching functionality?
that sounds like a crazy system, if ORG sets the address of assembly, what set the PC address?
you haveso Start+5 = $205 however the code will be stored at $8000 in the output file.
To make a standard NES ROM starting at $8000 bin file you would doif you have multiple banks at $8000 and a fixed bank at $c000 store in ram as 16K 8K 8K 8K overlay
However I would recommend using sections and collecting them to form your actual code.
You then have the .virtual case which lets you put a struct or anything else that doesn't actually modify memory at a fixed location. For example you might want to map PPU registers this way.
this way you don't have to actually move the assemble address or logical address and can just place a virtual move so it won't appear in the output memory map. However you can do
STA PPU.MASK and it will put $2001 for you.
The true power of Virtual is it will take an expression solda (p1),y will assemble to lda ($01,s),y
lda (tmp) will assemble to lda $03,s
you have
Code: Select all
*=$8000 ; this set the assembly address to 8000
to change the final target of the assembly, so code that you copy and execute somewhere else you change the assembly PC but not the current PC
.logical $200
start
lda Start+5
sta $d020
rts
.byte 00
.here
To make a standard NES ROM starting at $8000 bin file you would do
Code: Select all
*=$0000 ; assembly set to output $0
.logical $8000 ; assemble as if the code is at $8000
..your code here
.here
Code: Select all
*=$0000
.logical $8000
16K of code here
.here
;Bank1 ; $4000 @$8000
.logical $8000
upto 8K here
.align $c000
.here
;Bank 2 ; $6000 @$8000
.logical $8000
upto 8K here
.align $c000
.here
;Bank 3 ; $8000 @$8000
.logical $8000
upto 8K here
.align $c000
.here
You then have the .virtual case which lets you put a struct or anything else that doesn't actually modify memory at a fixed location. For example you might want to map PPU registers this way.
Code: Select all
.virtual $2000
.block PPU
CTRL .byte ?
MASK .byte ?
STATUS .byte ?
OAMADDR .byte ?
OAMDATA .byte ?
PPUSCROLL .byte ?
PPUADDR .byte ?
PPUDATA .byte ?
OAMDMA .byte ?
.bend
.endv
STA PPU.MASK and it will put $2001 for you.
The true power of Virtual is it will take an expression so
Code: Select all
.virtual #1,s
p1 .addr ?
tmp .byte ?
.endv
lda (tmp) will assemble to lda $03,s