One led per core/thread

All technical discussions and projects around startKIT
dwelch67
Member++
Posts: 22
Joined: Thu Jun 16, 2011 9:01 pm

One led per core/thread

Post by dwelch67 »

I assume XS1_PORT_32A cannot be shared across threads.

There is no (correct/complete) datasheet for the XS1-A8A-64-FB96-C5 part on the startKIT (X0D69, 68, 67, etc are not there). So I cant tell if there are other connections to those led pins such that each thread can have its own resource.

So the next thing I tried was to have one thread manage the port and the other threads send it an xor value, the thread managing the port was listening on its incoming data port (thread to thread communications) but that resource got a RESOURCE_DEP, so in XC or assembly can someone show me how to do this?

thread0:

Code: Select all

while(1)
{
if data from other thread
{
port32a_data^=data_from_one_of_the_other_threads;
port <: port32a_data.
}
}
other threads (more than one)

Code: Select all

while(1)
{  
  delay some thread specific amount of time
  send thread specific xor value to thread 0
}
Not interested in any old way to blink more than one led, I am interested in demonstrating this type of communication between threads (many to one). (well if there are separate connections to those pads then I would also, independently, like to demonstrate separate threads controlling separate leds).

Thanks,
David


User avatar
segher
XCore Expert
Posts: 844
Joined: Sun Jul 11, 2010 1:31 am
Contact:

Post by segher »

It's not an FB96 package, it's an FB217. Have a look at
this one, ignore tile 0 and the USB device.

Port-to-pin mappings are the same on all devices.

You'll need to show us your actual code if you
want us to see what is wrong with it; also the
exact, full exception message.
dwelch67
Member++
Posts: 22
Joined: Thu Jun 16, 2011 9:01 pm

Post by dwelch67 »

Well that is another side topic, the part is marked as 8A6C5DEV, 8A6C5 in the parts list points to XS1-A8A-64-FB96-C5, the FB217 datasheet for the 128 part doesnt describe those pins either, there is a gap just like the 64FB96 datsheet. The schematics say it is a XS1_A8DEV_64_FB217 for which there isnt a datasheet for that combination (64 and FB217).

Also the config directory has a 64 FB96 and 128 FB217 config file but no cross over (no 64 FB217). The config files do describe those pins for both the FB96 and the 128 FB217, well the FB217 pin numbers do not match the schematic but the FB96 does.

This all tends to point at this being the 64 FB96 part that its markings state.

Anyway the datasheet you pointed at (some other part) shows what the 64FB86 (and 128FB217) config files say, that the 32A port is not shared for those pins.

So off to the other question of many to one communications without the one stuck waiting/hanging on one thread why the others are trying to tell it something.

Thanks,
David
dwelch67
Member++
Posts: 22
Joined: Thu Jun 16, 2011 9:01 pm

Post by dwelch67 »

Well there, you go. I had deleted it and given up, hoping for a fresh new example to be pointed to. But since you asked, I pieced together the code again...and now it works so I must have had a bug in the code the last time around.

This code is working as desired. Thread 1 and 2 (core1 core2) both hit thread 0 on the same channel, whichever one comes in thread0 responds to. No hangs...so far.

This is targeted at the simulator right now, later will slow down the code so leds will blink at human speed...

Code: Select all

_start:
    ldc r1, 10
notmain:                # what was this loop for?
    sub r1,r1,1
    bt r1, notmain

    ldc  r11, 0x6       # the I/O ports need a clock
    setc res[r11], 0x8  # setci
    setc res[r11], 0xf  # setci

    # define XS1_PORT_32A 0x200000
    ldc r8,0x2000
    shl r8,r8,8
    setc res[r8],0x8    # turn the port on
    ldc r1,0x6          # give it a clock
    setclk res[r8],r1

    getr r5,2           # allocate a channel end for thread 0
    setd res[r5],r5

    getr r4,0x3         # get a synchronizer

    getst r0,res[r4]    # allocate a thread
    ldap r11,thread1    # get address for the code for new thread
    init t[r0]:pc,r11   # set pc for new thread
    set t[r0]:r5,r5     # fill thread with thread0 channel

    getst r0,res[r4]    # allocate a thread
    ldap r11,thread2    # get address for the code for new thread
    init t[r0]:pc,r11   # set pc for new thread
    set t[r0]:r5,r5     # fill thread with thread0 channel

    msync res[r4]       # start all allocated threads
    bu thread0          # give thread 0, the main thread, a place to go

common_main:

outer:
    mov r2,r3
inner:
    sub r2,r2,1
    bt r2,inner
    out res[r5],r7      # send some data to thread0
    bu outer


thread0:
    ldc r0,0x0
t0loop:
    out res[r8],r0
    in r10,res[r5]      # wait for data
    xor r0,r0,r10
    bu t0loop

thread1:
    ldc r7,0x0010
    ldc r3,0x11
    bu common_main

thread2:
    ldc r7,0x0100
    ldc r3,0x22
    bu common_main

thread3:
    ldc r7,0x1000
    ldc r3,0x33
    bu common_main
dwelch67
Member++
Posts: 22
Joined: Thu Jun 16, 2011 9:01 pm

Post by dwelch67 »

Code: Select all

thread1:
    ldc r7,0x0010
    ldc r3,0x2
    bu common_main

thread2:
    ldc r7,0x0100
    ldc r3,0x3
    bu common_main

thread3:
    ldc r7,0x1000
    ldc r3,0x4
    bu common_main
If I punish it then it does fail...

Code: Select all

stdcore[0]@1- -p-A-p-p-.----.00010040 (inner               +  2) : bt      r2(0x0), -0x2 @300
stdcore[0]@2-*-p-p-A-p-.----..00010042 (inner               +  4) : out     res[r5(0x2)], r7(0x100) @301
stdcore[0]@2 *00010042 : TRAP ET: 9, SPC: 00010042, SSR: 0, ED: 00000002 (RESOURCE_DEP)
stdcore[0]@3- -p-p-p-A-.----...00010044 (inner               +  6) : bu      -0x5 @302
stdcore[0]@0- -A-p-p-p-.----00010048 (t0loop              +  0) : out     res[r8(0x200000)], r0(0x1000) @303
stdcore[0]@1-*-p-A-p-p-.----.00010042 (inner               +  4) : out     res[r5(0x2)], r7(0x10) @304
stdcore[0]@1 *00010042 : TRAP ET: 9, SPC: 00010042, SSR: 0, ED: 00000002 (RESOURCE_DEP)
stdcore[0]@2 *00000000 : TRAP ET: 2, SPC: 00000000, SSR: 10, ED: 00000000

Perhaps I am overflowing a fifo, feeding it faster than it is being pulled?
User avatar
Bianco
XCore Expert
Posts: 754
Joined: Thu Dec 10, 2009 6:56 pm
Contact:

Post by Bianco »

dwelch67 wrote:Well that is another side topic, the part is marked as 8A6C5DEV, 8A6C5 in the parts list points to XS1-A8A-64-FB96-C5, the FB217 datasheet for the 128 part doesnt describe those pins either, there is a gap just like the 64FB96 datsheet. The schematics say it is a XS1_A8DEV_64_FB217 for which there isnt a datasheet for that combination (64 and FB217).

Also the config directory has a 64 FB96 and 128 FB217 config file but no cross over (no 64 FB217). The config files do describe those pins for both the FB96 and the 128 FB217, well the FB217 pin numbers do not match the schematic but the FB96 does.

This all tends to point at this being the 64 FB96 part that its markings state.

Anyway the datasheet you pointed at (some other part) shows what the 64FB86 (and 128FB217) config files say, that the 32A port is not shared for those pins.

So off to the other question of many to one communications without the one stuck waiting/hanging on one thread why the others are trying to tell it something.

Thanks,
David
The A8DEV is a 'non-existing' device just being used in the startKIT.
Segher pointed you to the right device. One of the tiles is dedicated to the onboard debugger just on this board hence they used a different part number to not confuse people (or confuse people more :p)
User avatar
segher
XCore Expert
Posts: 844
Joined: Sun Jul 11, 2010 1:31 am
Contact:

Post by segher »

You are using the same channel end in all threads (even
in the "master" thread). That's a no-no.

When you have fixed this you will find that only one thread
gets its data across; that is because it was the first to send
data, but it never sent an END control token, so the connection
stays open and no one else can send to the master's channel
end. So do send an END after your data, and deal with it
on the master's side (just a CHKCT will do).
dwelch67
Member++
Posts: 22
Joined: Thu Jun 16, 2011 9:01 pm

Post by dwelch67 »

Can you elaborate a wee bit more? Can a thread/task poll without waiting? What about in xc instead of assembly? Is there a simple example of this?

Thanks,
David
dwelch67
Member++
Posts: 22
Joined: Thu Jun 16, 2011 9:01 pm

Post by dwelch67 »

With some more research I am trying to use events. For now just want to see one work then two, etc...

I am doing something wrong though?

Code: Select all

_start:
    ldc r1, 10
notmain:                
    sub r1,r1,1
    bt r1, notmain

    ldc  r11, 0x6       # the I/O ports need a clock
    setc res[r11], 0x8  # setci
    setc res[r11], 0xf  # setci

    # define XS1_PORT_32A 0x200000
    ldc r9,0x2000
    shl r9,r9,8
    setc res[r9],0x8    # turn the port on
    ldc r1,0x6          # give it a clock
    setclk res[r9],r1


    getr r5,2
    getr r6,2
    setd res[r5],r6
    setd res[r6],r5

    getr r4,0x3         # get a synchronizer

    getst r0,res[r4]    # allocate a thread
    ldap r11,thread1    # get address for the code for new thread
    init t[r0]:pc,r11   # set pc for new thread
    set t[r0]:r5,r5
    set t[r0]:r6,r6

    msync res[r4]       # start all allocated threads
    bu thread0          # give thread 0, the main thread, a place to go

thread0:
    ldc r0,0x0

    clre
    eeu res[r5]

t0outer:
    out res[r9],r0
t0inner:
    ldap r11,t0thread1
    setv res[r5],r11
    waiteu

t0thread1:
    in r10,res[r5]
    xor r0,r0,r10
    outct res[r5],1
    bu t0outer

thread1:
    ldc r9,0x0010
    ldc r3,11
t1outer:
    mov r2,r3
t1inner:
    sub r2,r2,1
    bt r2,t1inner
    out res[r6],r9      # send some data to thread0
    chkct res[r6],1
    bu t1outer
It gets up to the event and then that is it

Code: Select all

stdcore[0]@1- -p-A-.----.00010050 (t1inner             +  0) : sub     r2(0x9), r2(0xa), 0x1 @187
stdcore[0]@0- -A-p-.----0001003c (t0inner             +  2) : setv    res[r5(0x2)], r11(0x10040) @189
stdcore[0]@1- -p-A-.----.00010052 (t1inner             +  2) : bt      r2(0x9), -0x2 @191
stdcore[0]@0-P-A-p-.----0001003e (t0inner             +  4) : waiteu   @193
stdcore[0]@1- -weA-.----.00010050 (t1inner             +  0) : sub     r2(0x8), r2(0x9), 0x1 @195
stdcore[0]@1- -weA-.----.00010052 (t1inner             +  2) : bt      r2(0x8), -0x2 @199
stdcore[0]@1- -weA-.----.00010050 (t1inner             +  0) : sub     r2(0x7), r2(0x8), 0x1 @203
stdcore[0]@1- -weA-.----.00010052 (t1inner             +  2) : bt      r2(0x7), -0x2 @207
stdcore[0]@1- -weA-.----.00010050 (t1inner             +  0) : sub     r2(0x6), r2(0x7), 0x1 @211
stdcore[0]@1- -weA-.----.00010052 (t1inner             +  2) : bt      r2(0x6), -0x2 @215
stdcore[0]@1- -weA-.----.00010050 (t1inner             +  0) : sub     r2(0x5), r2(0x6), 0x1 @219
stdcore[0]@1- -weA-.----.00010052 (t1inner             +  2) : bt      r2(0x5), -0x2 @223
stdcore[0]@1- -weA-.----.00010050 (t1inner             +  0) : sub     r2(0x4), r2(0x5), 0x1 @227
stdcore[0]@1- -weA-.----.00010052 (t1inner             +  2) : bt      r2(0x4), -0x2 @231
stdcore[0]@1- -weA-.----.00010050 (t1inner             +  0) : sub     r2(0x3), r2(0x4), 0x1 @235
stdcore[0]@1- -weA-.----.00010052 (t1inner             +  2) : bt      r2(0x3), -0x2 @239
stdcore[0]@1- -weA-.----.00010050 (t1inner             +  0) : sub     r2(0x2), r2(0x3), 0x1 @243
stdcore[0]@1- -weA-.----.00010052 (t1inner             +  2) : bt      r2(0x2), -0x2 @247
stdcore[0]@1- -weA-.----.00010050 (t1inner             +  0) : sub     r2(0x1), r2(0x2), 0x1 @251
stdcore[0]@1- -weA-.----.00010052 (t1inner             +  2) : bt      r2(0x1), -0x2 @255
stdcore[0]@1- -weA-.----.00010050 (t1inner             +  0) : sub     r2(0x0), r2(0x1), 0x1 @259
stdcore[0]@1- -weA-.----.00010052 (t1inner             +  2) : bt      r2(0x0), -0x2 @263
stdcore[0]@1- -weA-.----.00010054 (t1inner             +  4) : out     res[r6(0x102)], r9(0x10) @267
stdcore[0]@0Event caused by res 0x00000002, V=0x00000040, EV=0x00000002 @271
Thanks,
David
dwelch67
Member++
Posts: 22
Joined: Thu Jun 16, 2011 9:01 pm

Post by dwelch67 »

Code: Select all

stdcore[0]@1- -p-A-p-.----.00010166 (b_port              + 4e) : ldap    r11(0x1012c), -0x1e @3645
stdcore[0]@1- -p-A-p-.----.00010168 (b_port              + 50) : setv    res[r0(0x2)], r11(0x1012c) @3649
...
stdcore[0]@1Event caused by res 0x00000002, V=0x0001012c, EV=0x00000002 @3666
When XC code does the ldap/setv the vector has the 0x10000 set. and goes to the right place, what am I missing?

Thanks,
David
Post Reply