Shop OBEX P1 Docs P2 Docs Learn Events
Loading multiple cogs with ASM — Parallax Forums

Loading multiple cogs with ASM

crcordillcrcordill Posts: 29
edited 2008-05-18 18:19 in Propeller 1
Quick question. I've been working on learning ASM for a few weeks with the help of the Forums and some of the tutorials. They've helped me a bunch. I've been able to use some of the power of ASM and its been great. However, I've only been able to run one cog at once.

My question is how to launch multiple cogs with ASM. Lets say that I have two entries and I am launching them onto seperate cogs with totally different code. Do I need to use the ORG and FIT functions? Here's how I think it should go:
PUB Main
cognew(@entry1, @stack)
cognew(@entry2, @stack[noparse][[/noparse]10])

DAT
entry1          ORG
code in here
entry1_end    FIT

entry2           ORG
code in here
entry2_end    FIT



Is this the way that I should load up the different cogs?

Another quick question. I'll be using all of the cogs. When I start my code I've already started my first cog, correct? Let me explain:
PUB  Main
cognew(Cog1, @stack)
cognew(Cog2, @stack)
cognew(Cog3, @stack)
cognew(Cog4, @stack)
cognew(Cog5, @stack)
cognew(Cog6, @stack[noparse][[/noparse]6])
cognew(Cog7, @stack[noparse][[/noparse]7])
Cog0



where Cog# is an object to run
This one makes sense, where the next one doesn't I think. I'll run out of cogs if I try the next one, right?
PUB  Main
cognew(Cog1, @stack)
cognew(Cog2, @stack)
cognew(Cog3, @stack)
cognew(Cog4, @stack)
cognew(Cog5, @stack)
cognew(Cog6, @stack[noparse][[/noparse]6])
cognew(Cog7, @stack[noparse][[/noparse]7])
cognew(Cog0, @stack[noparse][[/noparse]8])


Post Edited (crcordill) : 5/17/2008 4:19:44 PM GMT

Comments

  • Mike GreenMike Green Posts: 23,101
    edited 2008-05-17 15:49
    Please use the [noparse][[/noparse] code ] and [noparse][[/noparse] /code ] tags for formatting (and please look at what you've posted to see if it's formatted the way you want it to be).
  • hippyhippy Posts: 1,981
    edited 2008-05-17 17:22
    Your first example is the right way to go, but note that using @stack[noparse][[/noparse]10] sets the second Cog's stack 10 up from the start of the stack used by the first. If the first Cog uses more than 10 stack entries it will start to corrupt the stack of the second Cog, and operations on the second Cog's stack will affect the operation of the first Cog.

    This is even more problematic in your second and third examples, where each Cog is only given one stack entry each.

    You're right that one Cog is always used ( Cog 0, the one running the Spin program launching the others ). To re-use the Cog 0, do a CogInit(0,methodName,@stack).
  • Mike GreenMike Green Posts: 23,101
    edited 2008-05-17 17:53
    Please note that assembly routines do not need or use a stack. The last parameter to COGNEW or COGINIT is copied into the PAR register where it's available as a general purpose parameter to the assembly routine. The PAR register's two least significant bits are always set to zero, so this parameter is usually a long address.
  • crcordillcrcordill Posts: 29
    edited 2008-05-17 18:45
    Right, I'm clear on the stack system. More my question was how does the chip get my ASM code onto the cog? Lets say that my two ASM cogs use the same subroutine. I understand that one cog cannot ask another cog the instructions on how to do a subroutine easily (I've know that you can do some self modifying code stuff, but that scares me). Basically I'm asking how do I partition my DAT section so that it goes into two different cogs?

    Here's an example of how I think you can partition the code.

    PUB Main
    cognew(@entry1, @stack)
    cognew(@entry2, @stack[noparse][[/noparse]10])
    
    DAT
    entry1          ORG
    code in here
    Subroutine 1
    Subroutine 2
    etc
    entry1_end    FIT
    
    entry2           ORG
    code in here
    Subroutine 1
    Subroutine 4
    etc
    entry2_end    FIT
    
    



    I think that if I use the ORG and FIT commands, that would send the code between the ORG and FIT into two separate cogs. So the first cog is only loaded with code that it needs, and not stuff for needed for the second entry. Though I'm not sure. Here's another example and what I think will happen.

    PUB Main
    cognew(@entry1, @stack)
    cognew(@entry2, @stack[noparse][[/noparse]10])
    
    DAT
    entry1          ORG
    code in here
    Subroutine 1
    Subroutine 2
    etc
    
    entry2           
    code in here
    Subroutine 1
    Subroutine 4
    etc
    end              FIT
    
    



    With this example, I think that each cog will load up everything in between the ORG and the FIT for each cog. I'm sure that that is clear as mud. Please ask question for clarification. Thanks
  • Mike GreenMike Green Posts: 23,101
    edited 2008-05-17 19:07
    Please look at the description of the COGINIT/COGNEW assembly instruction in the Propeller manual because that's what the Spin interpreter executes to actually start up the new cog. The COGNEW doesn't know anything about what you actually have in your DAT section, neither the ORG nor the FIT. It just copies a block of 512 longs from hub memory to the cog's memory and starts it all going at location zero after zeroing the 16 special locations at the end of the cog's memory. The purpose of the ORG and FIT directives is to help you make a valid assembly program in that block of 512 longs.
  • AleAle Posts: 2,363
    edited 2008-05-18 12:43
    crcordill:

    In your last code listing you have two entry points and just one ORG directive: That is a bad idea, because the address for the second entry point will not be at 0, it does need to be, because the cognew instruction will load 496 long starting at that point but the symbols will start at entry1. I'd recommend you keep every assembly block in its own DAT section with its own ORG, for clarity and to avoid messing up the symbols. (You can test what I told you, just put the cursos over a symbol and it will tell you the address, you will see that it is the ORG directive the one that fixes that address to 0).
  • Ken PetersonKen Peterson Posts: 806
    edited 2008-05-18 13:28
    COGNEW and COGINIT copy 496 longs starting at whatever symbol name you pass to the function. So if you use @entry2 for the first parameter, it copies 496 longs starting at that point.

    ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
  • AleAle Posts: 2,363
    edited 2008-05-18 13:32
    Ken:

    That's what I said, but any label will not have the correct address as I explained above.
  • crcordillcrcordill Posts: 29
    edited 2008-05-18 14:28
    Great, those last two comments answered my question. Thanks a bunch.
  • Ken PetersonKen Peterson Posts: 806
    edited 2008-05-18 18:19
    @Ale: I know that's what you said and none of it was incorrect, but I thought it might help to be more clear on what exactly gets copied and from where. crcordill seemed a little confused on that point in particular so I thought I'd get to the root of the question. Your point about the org statments and dividing among different DAT sections is also very good advice.

    ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
Sign In or Register to comment.