Shop OBEX P1 Docs P2 Docs Learn Events
ALTDS replaced with ALTI/ALTR/ALTD/ALTS — Parallax Forums

ALTDS replaced with ALTI/ALTR/ALTD/ALTS

cgraceycgracey Posts: 14,155
edited 2015-11-03 20:45 in Propeller 2
In the next release...

What was ALTDS is now ALTI.

There are three new instructions that share the opcode space with ALTI (no more C/Z writing options, as they were meaningless for these instructions):

ALTR D,S/# - use the sum of D and S/# for the result register in the next instruction
ALTD D,S/# - use the sum of D and S/# for the D register in the next instruction
ALTS D,S/# - use the sum of D and S/# for the S register in the next instruction

The idea is that D is an offset and S/# is a base:

ALTx offset,#base

So, now we'll have simple-to-use instructions for R/D/S alterations.

This cleans up 78rpm's task switcher.

OLD CODE
task_switcher   ' this is the task switcher isr
        ' save current task
                addct1  task_time, ##TASKS_TIMER    
                mov     modify, curr_task_index
                add     modify, #task_ctrl_blk
                altds   modify, #%000_100_000           ' replace D reg
                mov     0-0, IRET1                      ' tcb[ task index]
                add     curr_task_index, #1             ' next task
                and     curr_task_index, #$3            ' in range 0 - 3
        ' set new task
                mov     modify, curr_task_index
                add     modify, #task_ctrl_blk
                altds   modify, #%000_000_100           ' replace S reg
                mov     IRET1, 0-0                      ' tcb[ task index]

                reti1

NEW CODE
task_switcher   addct1  task_time,##TASKS_TIMER         'set next interrupt time

                altd    curr_task_index,#task_ctrl_blk  'save current task
                mov     0,IRET1

                incmod  curr_task_index,#3              'inc/reset task pointer

                alts    curr_task_index,#task_ctrl_blk  'set new task
                mov     IRET1,0

                reti1                                   'execute new task
«1

Comments

  • jmgjmg Posts: 15,173
    Looks nifty.
    Can you include an ALTI summary, for completeness ?
  • Simple and compact,. Nice one Chip. :)
  • Now that I like. It saves two instructions and thus executes much faster. Both a speed and size optimisation!
  • Cluso99Cluso99 Posts: 18,069
    I like it Chip :)

    Can ALTx D,S/# be chained?
     ALTS D,S/# 'modify S
     ALTD D,S/# 'modify D
     ALTR D,S/# 'modify Result location
     MOV 0-0,0-0 'S, D & R modified
    
  • Cluso99 wrote: »
    I like it Chip :)

    Can ALTx D,S/# be chained?
     ALTS D,S/# 'modify S
     ALTD D,S/# 'modify D
     ALTR D,S/# 'modify Result location
     MOV 0-0,0-0 'S, D & R modified
    
    I think I missed something. What is R? I thought D was where the result went. Is D used when reading that parameter and R used when writing it?

  • cgraceycgracey Posts: 14,155
    edited 2015-11-03 22:47
    Cluso99 wrote: »
    I like it Chip :)

    Can ALTx D,S/# be chained?
     ALTS D,S/# 'modify S
     ALTD D,S/# 'modify D
     ALTR D,S/# 'modify Result location
     MOV 0-0,0-0 'S, D & R modified
    

    Yes. They can be chained.

    Wait! Not like in your example. One ALTx can modify the next ALTx, but you can't wind up with both D and S modified in your final instruction, unless you use ALTI, which is the old ALTDS. ALTI is more complex to use.
  • RaymanRayman Posts: 14,658
    Maybe alti means alternate instruction?
  • cgraceycgracey Posts: 14,155
    David Betz wrote: »
    Cluso99 wrote: »
    I like it Chip :)

    Can ALTx D,S/# be chained?
     ALTS D,S/# 'modify S
     ALTD D,S/# 'modify D
     ALTR D,S/# 'modify Result location
     MOV 0-0,0-0 'S, D & R modified
    
    I think I missed something. What is R? I thought D was where the result went. Is D used when reading that parameter and R used when writing it?

    D normally defines where the result is to be written, ALTI or ALTR can redirect the write, while D remains one of the operands to be read.
  • cgracey wrote: »
    David Betz wrote: »
    Cluso99 wrote: »
    I like it Chip :)

    Can ALTx D,S/# be chained?
     ALTS D,S/# 'modify S
     ALTD D,S/# 'modify D
     ALTR D,S/# 'modify Result location
     MOV 0-0,0-0 'S, D & R modified
    
    I think I missed something. What is R? I thought D was where the result went. Is D used when reading that parameter and R used when writing it?

    D normally defines where the result is to be written, ALTI or ALTR can redirect the write, while D remains one of the operands to be read.
    That's what I guessed. Thanks for confirming.

  • Maybe I'm dense but wouldn't be a lot easier and more compact to just add load/store indirect?
  • evanhevanh Posts: 15,923
    That's the way to do it!
  • evanh wrote: »
    That's the way to do it!
    I understand that but it's a *weird* way to do it. :-)

  • evanhevanh Posts: 15,923
    David, HubRAM fetches already have the PTRA/B indirection handling.
  • evanhevanh Posts: 15,923
    Although, I suspect only two addressing registers will be restrictive.
  • evanh wrote: »
    Although, I suspect only two addressing registers will be restrictive.
    Yes, that's likely.

  • evanhevanh Posts: 15,923
    Ah, ALTS prefixing RDLONG and co. can provide many more I guess. So, there's your load/store indirection without needing any more extensions.

    And ALTS prefixing RDFAST could be used I presume?
  • cgraceycgracey Posts: 14,155
    edited 2015-11-03 23:44
    If you look at the opcodes, there's no more bits to use for something like 'indirect'.

    It either has to be via special registers, or with a prefix instruction like I've done here.

    Special registers would be faster, but we'd probably only have two of them. They would be a pain to save and restore in interrupts or between routines.

    Doing indirection with a prefix instruction takes more time and code, but you can have as many of them as you want, which saves code over special registers. Plus, it's very cheap to do in hardware.
  • I keep looking at the "0" in the D/S field and thinking that there should be some way to still use that. In other words, it would feel more natural for ALTD to alter D of the next instruction instead of replace it. For instance:
            altd    curr_task_index
            mov     task_ctrl_blk, IRET1
    

    In the above code, ALTD adds ("alt" is a misnomer here) the value at curr_task_index to the D address in the next instruction. This might not be exactly right, but you get the idea...
  • Seairth wrote: »
    I keep looking at the "0" in the D/S field and thinking that there should be some way to still use that. In other words, it would feel more natural for ALTD to alter D of the next instruction instead of replace it. For instance:
            altd    curr_task_index
            mov     task_ctrl_blk, IRET1
    

    In the above code, ALTD adds ("alt" is a misnomer here) the value at curr_task_index to the D address in the next instruction. This might not be exactly right, but you get the idea...

    Probably not enough time in the instruction cycle for the add.
  • cgraceycgracey Posts: 14,155
    edited 2015-11-03 23:49
    evanh wrote: »
    Ah, ALTS prefixing RDLONG and co. can provide many more I guess. So, there's your load/store indirection without needing any more extensions.

    And ALTS prefixing RDFAST could be used I presume?

    Yes.
  • cgracey wrote: »
    If you look at the opcodes, there's no more bits to use for something like 'indirect'.

    It either has to be via special registers, or with a prefix instruction like I've done here.

    Special registers would be faster, but we'd probably only have two of them. They would be a pain to save and restore in interrupts or between routines.

    Doing indirection with a prefix instruction takes more time and code, but you can have as many of them as you want, which saves code over special registers. Plus, it's very cheap to do in hardware.
    You could just have LDI and STI for load and store indirect and not try to add an indirect bit to every instruction. Of course, the LDI and STI instructions probably couldn't be done in a single clock cycle.

  • evanhevanh Posts: 15,923
    Seairth wrote: »
            altd    curr_task_index
            mov     task_ctrl_blk, IRET1
    

    Good point, makes sense from an encoding viewpoint but I suspect that would restrict "task_ctrl_blk" to an immediate value only.
  • cgraceycgracey Posts: 14,155
    edited 2015-11-03 23:51
    Seairth wrote: »
    I keep looking at the "0" in the D/S field and thinking that there should be some way to still use that. In other words, it would feel more natural for ALTD to alter D of the next instruction instead of replace it. For instance:
            altd    curr_task_index
            mov     task_ctrl_blk, IRET1
    

    In the above code, ALTD adds ("alt" is a misnomer here) the value at curr_task_index to the D address in the next instruction. This might not be exactly right, but you get the idea...

    Actually, I just made assembler aliases for the unary cases of these instructions:
    ALTI    reg           =       ALTI    reg,#%101_100_100 (substitute reg for next instruction)
    ALTR    reg           =       ALTR    reg,#0
    ALTD    reg           =       ALTD    reg,#0
    ALTS    reg           =       ALTS    reg,#0
    

    Oh, wait! I see what you are proposing. As someone pointed out, there would be no time for that add, as any substitution has to be done before the cog RAM data is latched. There's no time to add anything, only mux something - and nothing can be dependent on the RAM data, as it's arriving very late.
  • David BetzDavid Betz Posts: 14,516
    edited 2015-11-04 00:13
    I guess the assembler could be made to convert this syntax:
       ADD (a), (b), (c)
    

    into a 128 bit instruction with ALTR, ALTD, and ALTS preceeding an ADD instruction. At least that would be more readable.

    Edit: replaced '*' with parens to indicate indirection.
    Edit2: corrected arithmetic
  • cgracey wrote: »
    Oh, wait! I see what you are proposing. As someone pointed out, there would be no time for that add, as any substitution has to be done before the cog RAM data is latched. There's no time to add anything, only mux something - and nothing can be dependent on the RAM data, as it's arriving very late.

    Yeah, I suspected as much also. But I figured I'd throw it out there in case it sparked an idea.
  • David Betz wrote: »
    I guess the assembler could be made to convert this syntax:
       ADD (a), (b), (c)
    

    into a 128 bit instruction with AUGR, AUGD, and AUGS preceeding an ADD instruction. At least that would be more readable.

    Edit: replaced '*' with parens to indicate indirection.
    Edit2: corrected arithmetic

    Did you mean ALT instead of AUG?

  • Seairth wrote: »
    David Betz wrote: »
    I guess the assembler could be made to convert this syntax:
       ADD (a), (b), (c)
    

    into a 128 bit instruction with AUGR, AUGD, and AUGS preceeding an ADD instruction. At least that would be more readable.

    Edit: replaced '*' with parens to indicate indirection.
    Edit2: corrected arithmetic

    Did you mean ALT instead of AUG?
    Yes, of course that is what I meant. Thanks for correcting me. I've edited my post.

  • Seairth wrote: »
    cgracey wrote: »
    Oh, wait! I see what you are proposing. As someone pointed out, there would be no time for that add, as any substitution has to be done before the cog RAM data is latched. There's no time to add anything, only mux something - and nothing can be dependent on the RAM data, as it's arriving very late.

    Yeah, I suspected as much also. But I figured I'd throw it out there in case it sparked an idea.
    Maybe you could use the altered values in the target instruction in the following instruction as if they were also included in an ALTx instruction. Not sure how you'd stop the cascade though. :-)

  • cgracey wrote: »
    If you look at the opcodes, there's no more bits to use for something like 'indirect'.

    It either has to be via special registers, or with a prefix instruction like I've done here.

    I am being very non-serious, but my isr is used as a code example in this thread. Consider changing ram size from 32 to 33-1/3 bits per long, the extra bit and a bit will facilitate long play. :crazy: :clown: :crazy:
  • 78rpm wrote: »
    cgracey wrote: »
    If you look at the opcodes, there's no more bits to use for something like 'indirect'.

    It either has to be via special registers, or with a prefix instruction like I've done here.

    I am being very non-serious, but my isr is used as a code example in this thread. Consider changing ram size from 32 to 33-1/3 bits per long, the extra bit and a bit will facilitate long play. :crazy: :clown: :crazy:

    If we did that wouldn't we have to also switch from digital to analog?

Sign In or Register to comment.