Parallax Forums
  HomeLog InRegisterCommunity CalendarSearch the ForumHelp
   
Parallax Forums > Public Forums > Propeller Chip > Assembly Code Examples for the Beginner  Forum Quick Jump
 
New Topic Post Reply Printable Version
71 posts in this thread.
Viewing Page :
 1  2  3 
[ << Previous Thread | Next Thread >> ] | Show Newest Post First ]

Mike Green
Registered Member



Email Address Not AvailablePersonal Homepage Not AvailablePrivate Messaging Not AvailableAIM Not AvailableICQ Not AvailableY! Not AvailableMSN Not Available
Date Joined Oct 2004
Total Posts : 15579
 
   Posted 12/4/2006 10:58 AM (GMT -7)    Quote This PostAlert An Admin About This Post.
Brian,
The results (_Num1) are computed in a memory location within the cog's memory space (512 32-bit words). The main memory which
is used by the SPIN interpreter is separate. To the program running in the cog, the main memory looks a bit like an I/O device with
special instructions needed to access it. In particular, the "wrlong <cog address>,<hub address>" instruction writes the contents of
the specified cog location into a main (hub) memory location whose address is in a cog location (in this case, the PAR register). The PAR
register is a read-only cog memory location that contains a hub memory long-word address specified when the cog was started (by the
COGINIT/COGNEW instruction).

You can only "look" at the results of an assembly program by the assembly program itself copying the results into the common hub memory
for other programs (whether in SPIN or assembly) to examine. You could also send the results to an I/O device by manipulating the I/O pins.
Mike
Back to Top
 

Beau Schwabe (Parallax)
IC Layout Engineer



Email Address Not AvailablePersonal Homepage Not AvailablePrivate Messaging Not AvailableAIM Not AvailableICQ Not AvailableY! Not AvailableMSN Not Available
Date Joined Aug 2004
Total Posts : 3967
 
   Posted 12/5/2006 12:02 AM (GMT -7)    Quote This PostAlert An Admin About This Post.
truckwiz,

If you treat 'AddNums(Num1,Num2)' as a function, then when you call it with something like...

Answer := AddNums(Num1,Num2)

Your result will be returned in the variable 'Answer'

To 'look' at them, use any of the other objects available to display them to a TV,VGA,SERIAL,LED's(binary form) etc.


Beau Schwabe

IC Layout Engineer
Parallax, Inc.

Back to Top
 

Beau Schwabe (Parallax)
IC Layout Engineer



Email Address Not AvailablePersonal Homepage Not AvailablePrivate Messaging Not AvailableAIM Not AvailableICQ Not AvailableY! Not AvailableMSN Not Available
Date Joined Aug 2004
Total Posts : 3967
 
   Posted 12/5/2006 12:59 AM (GMT -7)    Quote This PostAlert An Admin About This Post.
Bean,

I've been in Rocklin and Tahoe all of this weekend, and while I was in the Parallax office on Friday and Monday, I was busy going over layout ideas with Chip
and did not have a chance to do any timing tests with the Propeller that would answer your question.


Beau Schwabe

IC Layout Engineer
Parallax, Inc.

Back to Top
 

Bean
Forum Moderator



Email Address Not AvailablePersonal Homepage Not AvailablePrivate Messaging Not AvailableAIM Not AvailableICQ Not AvailableY! Not AvailableMSN Not Available
Date Joined Jul 2004
Total Posts : 6367
 
   Posted 12/5/2006 7:03 AM (GMT -7)    Quote This PostAlert An Admin About This Post.
Beau,
I didn't actually measure the time, but it's pretty fast (much faster than the same code in spin).

I was thinking it had to load the cog from EEPROM, but now that I think about it, I guess it just loads from hub memory into cog memory (which is much faster than pulling the data from the EEPROM).

Bean.


Cheap used 4-digit LED display with driver IC www.hc4led.com
Low power SD Data Logger www.sddatalogger.com
SX-Video Display Modules www.sxvm.com
 
"People who are willing to trade their freedom for security deserve neither and will lose both." Benjamin Franklin
 

Back to Top
 

parsko
Engineer

Email Address Not AvailablePersonal Homepage Not AvailablePrivate Messaging Not AvailableAIM Not AvailableICQ Not AvailableY! Not AvailableMSN Not Available
Date Joined Mar 2006
Total Posts : 475
 
   Posted 12/9/2006 6:23 PM (GMT -7)    Quote This PostAlert An Admin About This Post.
This is kind of a trap, I suppose. The following pertinent inputs:

VAR
    byte array[100]
PUB
    cognew(@assembly, @second)
DAT
    Assembly
    .
    .
    .



This code is legal. But any new cognew's that occur, must have a PARameter registered to some value of the array/4. Let me say that another way, it's late. I used "@second[4]" for my PARameter. I could have easily used "@second[0]" or "@second[8]". The cognew requeires the start of a long for it's parameter. So, if you want to use "@second[2]" it will still start at second[0]. Subsequently, @second[6] will start at @second[4] {The less obvious concept I'm pointing out}

-Parsko

Post Edited (parsko) : 12/10/2006 1:27:55 AM GMT

Back to Top
 

Mike Green
Registered Member



Email Address Not AvailablePersonal Homepage Not AvailablePrivate Messaging Not AvailableAIM Not AvailableICQ Not AvailableY! Not AvailableMSN Not Available
Date Joined Oct 2004
Total Posts : 15579
 
   Posted 12/9/2006 7:29 PM (GMT -7)    Quote This PostAlert An Admin About This Post.
Because of the way the COGINIT/COGNEW assembly instruction works, there is only a 14 bit field available for initializing the PAR register. Because this value is most likely to be used as the address of a long, it appears in the PAR register shifted left by 2 bits (a multiple of 4). SPIN makes the same assumption and throws away the low order 2 bits of the address supplied. The Propeller Manual says this several times, but it is a trap for the unwary.
Back to Top
 

Wurlitzer
Registered Member

Email Address Not AvailablePersonal Homepage Not AvailablePrivate Messaging Not AvailableAIM Not AvailableICQ Not AvailableY! Not AvailableMSN Not Available
Date Joined Apr 2006
Total Posts : 131
 
   Posted 12/13/2006 12:20 PM (GMT -7)    Quote This PostAlert An Admin About This Post.
Sorry, I'm thick today (well maybe more than today). I have an application which will require 5 or more cogs (some with SPIN others in Assy) to read and write to a common Byte Array[100] in Main RAM.

I cannot get my head around how to assure all cogs know the starting address address of this common array. Does it require the array to be declared in the Top Object then have the Top Object call all the subseqent "CogNew(@SpinOrAssyObjectName,@@ByteArray[0])" and then the PAR register in each cog will contain the proper starting address?

I don't have any worries in this program regarding conflicting writes I just need to be able to read/write to any element in this 100 element ByteArray from any cog.

Thanks
Back to Top
 

SailerMan
Registered Member



Email Address Not AvailablePersonal Homepage Not AvailablePrivate Messaging Not AvailableAIM Not AvailableICQ Not AvailableY! Not AvailableMSN Not Available
Date Joined Sep 2006
Total Posts : 331
 
   Posted 12/14/2006 7:47 AM (GMT -7)    Quote This PostAlert An Admin About This Post.
Hello... I've had my propeller for a few weeks now and am starting to understand SPIN, now for the first time I am ready to begin my quest into ASM... I thought the propeller and it's community would be a great place to start.

Everytime I begin to learn ASM I get discouraged and quit because although I understand what some of the commands do ( MOV, ADD SHR) when I try to combine them to make programs I get lost.

I have been programming in dialects of basic since the days of the commodore pet 1977. but never took it upon myself to dive into ASM, now my mind always thinks in the BASIC way of doing things.

Since this is an ASM beginners thread, can we start from the basics and compare the ASM to SPIN or (BASIC) Equivalents.

Thanks to anyone that is willing to lead me in the right direction.

Regards,
Eric
Back to Top
 

Paul Baker
Registered Member



Email Address Not AvailablePersonal Homepage Not AvailablePrivate Messaging Not AvailableAIM Not AvailableICQ Not AvailableY! Not AvailableMSN Not Available
Date Joined Jul 2004
Total Posts : 6323
 
   Posted 12/14/2006 3:09 PM (GMT -7)    Quote This PostAlert An Admin About This Post.
Eric, this discussion is best placed in the non-sticky portion of the forum, first alot of people dont regularly look to see if there are new posts in the sticky section and second we try to keep sticky discussions as on-topic as possible. Fundamentals questions fit here, but comparison/contrast with other languages doesn't.

-Thanks


Paul Baker

Propeller Applications Engineer

Parallax, Inc.

Back to Top
 

SailerMan
Registered Member



Email Address Not AvailablePersonal Homepage Not AvailablePrivate Messaging Not AvailableAIM Not AvailableICQ Not AvailableY! Not AvailableMSN Not Available
Date Joined Sep 2006
Total Posts : 331
 
   Posted 12/14/2006 5:09 PM (GMT -7)    Quote This PostAlert An Admin About This Post.
I guess what I am after is more ASM code examples..... for the Beginner... The only reason I mentioned comparison was because sometimes things are easier to understand when you see ASM code with an Equivalent Spin code. Sorry.
 
 
Back to Top
 

Paul Baker
Registered Member



Email Address Not AvailablePersonal Homepage Not AvailablePrivate Messaging Not AvailableAIM Not AvailableICQ Not AvailableY! Not AvailableMSN Not Available
Date Joined Jul 2004
Total Posts : 6323
 
   Posted 12/14/2006 6:08 PM (GMT -7)    Quote This PostAlert An Admin About This Post.
No problem, I didn't mean to sound harsh.


Paul Baker

Propeller Applications Engineer

Parallax, Inc.

Back to Top
 

Paul Baker
Registered Member



Email Address Not AvailablePersonal Homepage Not AvailablePrivate Messaging Not AvailableAIM Not AvailableICQ Not AvailableY! Not AvailableMSN Not Available
Date Joined Jul 2004
Total Posts : 6323
 
   Posted 12/14/2006 9:16 PM (GMT -7)    Quote This PostAlert An Admin About This Post.
Eric, in an effort to help you, can you name a specific Spin or SX/B command you'd like to see coded into assembly? I just ask you start with something a little simpler than SHIFTIN/OUT or other similarly complex commands.


Paul Baker

Propeller Applications Engineer

Parallax, Inc.

Back to Top
 

SailerMan
Registered Member



Email Address Not AvailablePersonal Homepage Not AvailablePrivate Messaging Not AvailableAIM Not AvailableICQ Not AvailableY! Not AvailableMSN Not Available
Date Joined Sep 2006
Total Posts : 331
 
   Posted 12/15/2006 8:46 AM (GMT -7)    Quote This PostAlert An Admin About This Post.
Thanks... Why don't you move this section of the tread to another post.
In any acount My problem lies in the fact that I have a hard time thinking low level.
Let's start out really small.
 
       
Pub Main|Index,Count
     Repeat Index From 0 to 10
       Count+=1
 
 
    
Back to Top
 

Paul Baker
Registered Member



Email Address Not AvailablePersonal Homepage Not AvailablePrivate Messaging Not AvailableAIM Not AvailableICQ Not AvailableY! Not AvailableMSN Not Available
Date Joined Jul 2004
Total Posts : 6323
 
   Posted 12/15/2006 5:05 PM (GMT -7)    Quote This PostAlert An Admin About This Post.
Here's the thread I started: http://forums.parallax.com/forums/default.aspx?f=25&m=160972


Paul Baker

Propeller Applications Engineer

Parallax, Inc.

Back to Top
 

Karl Smith
Registered Member

Email Address Not AvailablePersonal Homepage Not AvailablePrivate Messaging Not AvailableAIM Not AvailableICQ Not AvailableY! Not AvailableMSN Not Available
Date Joined Jan 2005
Total Posts : 51
 
   Posted 12/29/2006 7:33 PM (GMT -7)    Quote This PostAlert An Admin About This Post.

How would I convert this line of spin code to asm, I just can't seem to get it to work, I have tried all different variants of rdbyte and wrbyte one variant listed below:

bytemove(@End,@Start,1)

DAT
                        org
                        mov r0, @Start
                        mov r3, @End
                        rdbyte r1,r0
                        wrbyte r0,r3
                       
                        CogId   CogNum          'Get COG ID
                        CogStop CogNum          'Stop this COG

CogNum               res     1               'Reserved variables
R0                      long
R1                      long
R2                      long
R3                      long
R4                      long
Start                   byte "ABCD"
End                     byte "EFGH"

Back to Top
 

Mike Green
Registered Member



Email Address Not AvailablePersonal Homepage Not AvailablePrivate Messaging Not AvailableAIM Not AvailableICQ Not AvailableY! Not AvailableMSN Not Available
Date Joined Oct 2004
Total Posts : 15579
 
   Posted 12/29/2006 7:45 PM (GMT -7)    Quote This PostAlert An Admin About This Post.
You can't copy bytes individually in assembly the way you might do in SPIN because the cog's memory is not byte addressable. Each location is a long word. If you want to copy bytes in HUB (main - SPIN) memory, you could do it like this:

VAR byte Start, End ' Must be in this order
PUB start
   cognew(@begin,@Start)
   repeat          ' Wait for operation to finish
DAT
         org      0
begin mov     addr,PAR   ' get address of Start
         rdbyte  temp,addr ' get byte value
         add      addr,#1    ' move to next location
         wrbyte temp,addr ' store  byte value
         cogid   temp         ' stop cog
         cogstop temp
addr   res      1
temp  res     1

If what you want to do is to copy bytes from one location in a cog's memory to another,
you will have to use AND/OR and shift instructions and keep track of which byte in a word
that you're copying.
Back to Top
 

Karl Smith
Registered Member

Email Address Not AvailablePersonal Homepage Not AvailablePrivate Messaging Not AvailableAIM Not AvailableICQ Not AvailableY! Not AvailableMSN Not Available
Date Joined Jan 2005
Total Posts : 51
 
   Posted 12/29/2006 8:15 PM (GMT -7)    Quote This PostAlert An Admin About This Post.
Thank Mike, I will give it a try
Back to Top
 

Jello
Registered Member

Email Address Not AvailablePersonal Homepage Not AvailablePrivate Messaging Not AvailableAIM Not AvailableICQ Not AvailableY! Not AvailableMSN Not Available
Date Joined Apr 2007
Total Posts : 9
 
   Posted 4/23/2007 4:37 PM (GMT -7)    Quote This PostAlert An Admin About This Post.
Hi everybody,
Does anyone have a simple example of a case where a spin method calls and asm method tha calls
another asm method?
I need to clear my lcd screen and do other functions fast fast (via SPI).
So I am starting with cls method to get the hang of asm in hopes of eventually
refactoring all of my lcd spin code to asm.
I figure a cls would be a good place to start wrapping my brain around it all.
 
 
such like:
'in spin
 pub CLS(0) 'to clear screen with given color    
    'call asm _CLS method
    _cls(color)
 
 
'in asm
 _cls(color)  
   loop n times (calling asm spi engine shiftout method)
       shiftout(...)  
 
 
I'm sure it's a simple matter (just not simple to me)  :)
 
thanks
j
Back to Top
 

Kaio
Registered Member

Email Address Not AvailablePersonal Homepage Not AvailablePrivate Messaging Not AvailableAIM Not AvailableICQ Not AvailableY! Not AvailableMSN Not Available
Date Joined Jan 2007
Total Posts : 194
 
   Posted 4/24/2007 5:02 AM (GMT -7)    Quote This PostAlert An Admin About This Post.
Jello,

you don't have methods in assembly code. Your assembly code is running in a separate Cog independently from the Cog which is interpreting the Spin code. You could have some functions in your assembly code which are starting with a label and ending with a ret-instruction. Then you can use a call-instruction to perform a function like a method in Spin. When you want to pass arguments to a function you have to declare these as long data.

But you can't call such a function directly from Spin. Therefore you must use some assembly code that will communicate over the main memory with the Spin code. It's waiting for a command and can use also arguments which must be passed over the main memory. If a command is received it calls accordingly the function.

DAT
                        org     0
                        
entry                   mov     Arg1,#$20
                        call    #cout
                        jmp     #entry                  'endless loop only for this example

cout                    mov     Temp,Arg1               'get argument
                        'do something
cout_ret                ret

Arg1                    res     1                       'or long    0
Temp                    res     1                       'or long    0                                               


For an example of such a communication routine in assembly please have a look at file AsmDebug.spin from POD. This routine can also have a return value for some functions. To see how easy it is to call from Spin have a look at file PropDebugger.spin and there at method getFlags.
http://forums.parallax.com/forums/default.aspx?f=25&m=178997

Post Edited (Kaio) : 4/24/2007 4:44:58 PM GMT

Back to Top
 

Jello
Registered Member

Email Address Not AvailablePersonal Homepage Not AvailablePrivate Messaging Not AvailableAIM Not AvailableICQ Not AvailableY! Not AvailableMSN Not Available
Date Joined Apr 2007
Total Posts : 9
 
   Posted 4/24/2007 7:44 AM (GMT -7)    Quote This PostAlert An Admin About This Post.
Kaio,
What you said makes sense and the examples you sited are helpful.
I haven't quite digested it all yet :) but working on it. I have a lot to learn.
Thanks for the help Kaio!
J
Back to Top
 

ericball
Registered Member

Email Address Not AvailablePersonal Homepage Not AvailablePrivate Messaging Not AvailableAIM Not AvailableICQ Not AvailableY! Not AvailableMSN Not Available
Date Joined May 2007
Total Posts : 335
 
   Posted 6/13/2007 6:31 AM (GMT -7)    Quote This PostAlert An Admin About This Post.
Bean (Hitt Consulting) said...
Beau,
How long does it take to start/stop a new cog with an assembly program ?
If I have a routine that isn't fast enough in spin, I know it would be faster in assembly, but I don't know what the time delay is to launch a new cog.

Bean.

CogInit/CogNew forces the cog to execute a RDLONG for each word of cog RAM.  So the startup delay will be 512*16 = 8192 cycles (probably a few more for the initial HUB access and other startup delays).
 
Back to Top
 

ErNa
Registered Member



Email Address Not AvailablePersonal Homepage Not AvailablePrivate Messaging Not AvailableAIM Not AvailableICQ Not AvailableY! Not AvailableMSN Not Available
Date Joined May 2007
Total Posts : 250
 
   Posted 6/23/2007 11:32 AM (GMT -7)    Quote This PostAlert An Admin About This Post.
Does this also mean, that all other cogs are blocked for global access during this time?
Back to Top
 

Paul Baker
Registered Member



Email Address Not AvailablePersonal Homepage Not AvailablePrivate Messaging Not AvailableAIM Not AvailableICQ Not AvailableY! Not AvailableMSN Not Available
Date Joined Jul 2004
Total Posts : 6323
 
   Posted 6/23/2007 1:08 PM (GMT -7)    Quote This PostAlert An Admin About This Post.
No, hub accesses are performed in round-robin non-blocking style (thats why theres the *16 factor in ericball's equation).


Paul Baker

Propeller Applications Engineer

Parallax, Inc.

Back to Top
 

deSilva
Registered Member



Email Address Not AvailablePersonal Homepage Not AvailablePrivate Messaging Not AvailableAIM Not AvailableICQ Not AvailableY! Not AvailableMSN Not Available
Date Joined Jun 2007
Total Posts : 2972
 
   Posted 7/5/2007 3:20 AM (GMT -7)    Quote This PostAlert An Admin About This Post.
Well, not strictly for the beginner... However....
It is not widely known that SPIN allows full recursion of calls! This can be emulated within an assembly program by installing an ad-hoc stack mechanism.
It will be instructive anyhow to have a look at the many "patches". Note that you never shall "patch" crossing JMPRETs (aka CALLs), as the code has to stay re-entrant!

The speed-up is about 40, which is not so overwhelming compared to the general speed-up from SPIN to handmade assembly (about 80 according to my experience) which discloses a very efficient stack management within SPIN!

This innocent looking piece of SPIN.....
PUB spinFibo(n)
  if n>2
     return spinFibo(n-1)+ spinFibo(n-2)
  else
     return 1

... has thus created this "assembly-monster":
DAT
fiboasm
' PAR shall contain a reference to 2 longs
'  [ 0 ] Argument for fibo (0: result ready)
'  [ 1 ] Result
 
    mov a, #$1ff
    add a, cnt
    waitcnt a,#0    ' save energy while idling
    rdlong a, par
    tjz a,#fiboasm
  ' organize a stack
    mov stackP, #stack
    
    jmpret retaddr, #fibo   ' result = fibo(a)

   ' result available
    mov a, par
    add a, #4
    wrlong result, a
    mov a,#0
    wrlong a, par
    jmp #fiboasm

fibo
' if a<3 return 1
    cmps a, #3   wc
    mov resultat, #1
    if_c jmp retaddr

    
    add stackP, #1   ' points to the LAST USED entry
    movd :f1, stackP
    add stackP, #1       
    movd :f2, stackP  
:f1 mov 0-0, retaddr ' push return address 
:f2 mov 0-0, a       ' push argument

    sub a, #1 
    jmpret retaddr, #fibo ' call fibo(a-1)

    movs :f3, stackP 
    movd :f4, stackP 
:f3 mov a, 0-0      ' get argument
                    '... and substitute by result
:f4 mov 0-0, result                    

    sub a, #2
    jmpret retaddr, #fibo  ' call fibo(a-2)         

' add both reults
    movs :f5, stackP
    sub stackP, #1
:f5 add result, 0-0  
    movs :f6, stackP   ' return to caller
    sub stackP, #1     ' adjust stack
:f6 jmp 0-0    


retaddr  res 1
result res 1
a  res 1

' The stack runs from lower to higher addresses; stackP always points to the last used entry!
stackP res 0    ' a litte bit over-optimized 
stack res 100     ' ... or as long as it will go




----
If you are interested in the general timing without trying yourself:
fibo(29) needed:
26 sec with SPIN
1.8 sec with PHP on my mid-range Windows Notebook
800 ms with the above posted piece of code
30 ms with a very efficient FORTH Implementation on my mid-range Windows Notebook
----
BTW: I am well aware that there are simple algorithms to compute the n-th Fibonacci number in o(1) - this is obviously not the point :-)

---
Edit a long time later:
1,1 sec PureBasic in Interpreter/Debugger Mode (on same Notebook)
15 ms PureBasic compiled to 16kB EXE-file on same Notebook

Post Edited (deSilva) : 12/28/2007 6:12:59 PM GMT

Back to Top
 

mirror
Registered Member

Email Address Not AvailablePersonal Homepage Not AvailablePrivate Messaging Not AvailableAIM Not AvailableICQ Not AvailableY! Not AvailableMSN Not Available
Date Joined Apr 2007
Total Posts : 322
 
   Posted 7/5/2007 4:39 PM (GMT -7)    Quote This PostAlert An Admin About This Post.
Just out of curiosity - which Spin to assembler compiler did you use?

Spin to bytecodes I understand. Spin to handcoded assembler I understand.

Are you saying that you have manually handcoded the Spin to assembler, and simulated a stack type machine in the process?


 

Back to Top
 
[ << Previous Thread | Next Thread >> ]
New Topic Post Reply Printable Version
71 posts in this thread.
Viewing Page :
 1  2  3 
 
Forum Information
Currently it is Thursday, July 29, 2010 5:15 PM (GMT -7)
There are a total of 462,439 posts in 62,066 threads.
In the last 3 days there were 90 new threads and 802 reply posts. View Active Threads
Who's Online
This forum has 20143 registered members. Please welcome our newest member, ME01.
50 Guest(s), 9 Registered Member(s) are currently online.  Details
John Abshier, kf4ixm, BradC, Sapieha, Timmoore, Gene Bonin, laser-vector, localroger, Nick McClick