Quote:
Good point about signedness - it's a choice that should be made, one way or the other.
After posting my brilliant macros I realized I'd made them unsigned, when something I actually would want to do on occasion is:
Code:
QLY #-1
usually as initialization before entering a loop. "QLA #-1" would be likely prepatory to setting some memory location to $FFFF. So I think I'd vote for sign-extension, and have to re-write the macros accordingly (just replacing "ubyte" by "byte" would be simplest, and result in simply dropping any excess bits of whatever value they may be).
Quote:
Also, I realise that allowing only non-zero quick immediates makes great sense for ADC and a little less sense for LDA. Doesn't hurt for AND or ORA.
In the original 6502 instruction set (and all variants, AFAIK), it's possible to code branch instructions with a zero offset, eg., "BPL 0". Useless except perhaps in some esoteric exercise in timing, but possible. I imagine that was the simplest way to implement the instructions, so there it is.
And don't forget that ADC also involves the carry flag. I've seen "ADC #0" deliberately used for that reason.
Mmm, sign-extended quicks could also be used to make ADC perform subtraction, couldn't they? Making "quick subtracts" redundant. If they weren't sign-extended there could be separate quick ADC and SBC instructions, both with a greater operand magnitude.
And another thing: quick adds of 1 or -1 effectively give us INA and DEA, at least when we know the carry flag is clear. If it's set...quick add zero gives us INA, and quick add -2 give us DEA, I think. That might be useful often enough to forego actual INA and DEA instructions.
Are quick AND, OR and EOR worth it? Sign-extended or not, the high octet has a set value that can't be changed. I'm having trouble envisioning where that would be useful enough to justify the expense. Hmm, BIT also falls in this category. Maybe others as well.
What about a quick NOP? If the signed value is added to the program counter, we get a one-byte BRA (and the true SKP instruction I mentioned earlier). The original NOP behavior remains the same with a high octect value of zero. Getting it to always go in two cycles might be challenge. I wouldn't know where to begin with that, except to point out that there would be no need to fetch a second operand byte (does that help?).
So my initial "quick" list would have sign-extended operands and opcodes for:
QLA or LAQ
QLX or LXQ
QLY or LYQ
QAD or ADQ
QBR or BRQ or SKP or NOP
More as I think of them...
Quote:
Whereas, PHX and so on are really convenient for register-preserving subroutines
I'm all for these. Extremely handy!
Quote:
stack-relative addressing opens up ... something useful to someone. (That's probably a bigger change to the core though.)
I've had some vague thoughts about this sort of thing. It might help with position independence of programs larger than the 32K range of a branch instruction (other approaches: "chained" BRA instructions to reach beyond that range or Real Operating System Loaders).
I've never seen code like this (on a 65C02 or above):
Code:
TSX
JMP ($101,X)
probably because for that to be of any use a correct address has to loaded onto the stack first. Which finally got me to thinking what the 65816's PEA, PEI and PER instructions might actually be useful for. Yeah, have the cpu do the full-address calculations for you at run time...but that's about as far as I've gotten in puzzling it out.