PASM Newbie Questions
Shawna
Posts: 508
Hello everyone,
I am pretty new to the prop, but my first micro controller was a basic stamp, and when that no longer fit my needs I moved to Pics and Pic Basic Pro. I dove into the prop to do some embedded web-server projects and got in way over my head and then dropped the project. Winter is about here and that means I am going to be stuck inside so I decided to jump back into the Prop.
What I want to do, is learn PASM so I can write efficient code for the Prop, but I am having problems finding examples that are simple and small building blocks for learning PASM. Does anyone have any links to sites with tutorials? It is kind of hard for me to wrap my head around multi-tasking with the Prop since there is no interrupts. I know that there is 8 Cogs, but the thought process is still different when planning a project.
My first question is, can one pin be changed to an output and turned on and off without affecting the whole 32 bit outa register? I know it can be in spin but I am not sure about in PASM. I read something in the manual about muxing but I did not understand it.
Thanks
Shawn
I am pretty new to the prop, but my first micro controller was a basic stamp, and when that no longer fit my needs I moved to Pics and Pic Basic Pro. I dove into the prop to do some embedded web-server projects and got in way over my head and then dropped the project. Winter is about here and that means I am going to be stuck inside so I decided to jump back into the Prop.
What I want to do, is learn PASM so I can write efficient code for the Prop, but I am having problems finding examples that are simple and small building blocks for learning PASM. Does anyone have any links to sites with tutorials? It is kind of hard for me to wrap my head around multi-tasking with the Prop since there is no interrupts. I know that there is 8 Cogs, but the thought process is still different when planning a project.
My first question is, can one pin be changed to an output and turned on and off without affecting the whole 32 bit outa register? I know it can be in spin but I am not sure about in PASM. I read something in the manual about muxing but I did not understand it.
Thanks
Shawn
Comments
I always recommend the tutorial Graham Stabler provided.
That looks like a great place to start.
'ASMLED2CogBlink
CON
_clkmode = xtal1 + pll16x
_xinfreq = 5_000_000
PUB Main
cognew(@Blink, 0) 'Launch new cog
cognew(@Blink2,0) 'Launch new cog
DAT
Blink org 0 'Begin at Cog RAM addr 0
mov S1PinMask, #1 'Mask's selected and sets Direction for only
shl S1PinMask, SerPin1 'one pin.
or Dira, S1PinMask
mov Time, cnt 'Sets up waitcnt delay
add Time, Delay
:loop
or Outa, S1PinMask 'Makes Pin 0 High(ON).
waitcnt Time, Delay 'Waits until cnt = Time and then adds Delay to Time
andn Outa, S1PinMask 'Makes Pin 0 Low(OFF).
waitcnt Time, Delay 'Waits until cnt = Time and then adds Delay to Time
jmp #:loop 'Jumps to :loop
SerPin1 long 0
Delay long 2_000_000 'Clock cycles to delay
S1PinMask Res 1
Time Res 1
Blink2 org 0 'Begin at Cog RAM addr 0
mov S2PinMask, #1
shl S2PinMask, SerPin2
or Dira, S2PinMask
mov Time1, cnt
add Time1, Delay1
:loop
or Outa, S2PinMask 'Makes Pin 0 High(ON).
waitcnt Time, Delay
andn Outa, S2PinMask 'Makes Pin 0 Low(OFF).
waitcnt Time1, Delay1
jmp #:loop
SerPin2 long 1
Delay1 long 10_000_000 'Clock cycles to delay
S2PinMask Res 1
Time1 Res 1
Thanks
Shawn
ASMLED2CogBlink.spin
http://www.parallax.com/Portals/0/Downloads/docs/cols/nv/prop/col/nvp10.pdf
Not sure about anyone else, but I would put a second DAT on the line above Blink2. At least in Prop Tool, it aids readability to separate PASM code destined for different COGs. You might also be more generous with tabbing...in anticipation of adding assembly conditions and effects.
PASM tutorial by DeSilva
Assembly Language Primer for the Absolute Beginner by Doug Dingus (potatohead)
The following discussion threads might be helpful as well:
Assembly step by step
Propeller Assembly for Beginners
Propeller Resource Index
Machine Language Tutorial
Assembly Examples for the Beginners
Sandy
{code}
Some Code Here
{/code}
i've used curly brackets above to show the structure. Here it is with the square braces [ and ].
Sandy
{/Edit Oops, did not see it in the listing...... Prop Asm for Beginners is in the list......} which contains some really great contributions with supporting examples from some of the most knowledgeable members of the forum. Just remember to filter out the backscatter behind the initial purpose of the thread. Some of the best parts concerned passing info from hub to cogs and back. Mux and logicals also got good coverage here. Pay special attention to the names Kuroneko, Heater, Jazzed, Jonnymac, potatohead, and others. Some really great explanations are presented.
I am trying to translate this simple spin code into PASM. The prop tool says it is only 7 longs. I cannot for the life of me accomplish this in 7 longs, can someone show me what to do. I only ask because I am sure someone, with experience can do this without even thinking about.
Thanks
Shawn
Actually I can not get your code to work but I am still playing with it. There are allot of little pieces in there that I need to figure out. It is very helpful.
Thanks
Shawn
Does this program have two cogs running? And if it does what are the consequences of me stopping the cog 0. Will the cog running the PASM (ServoInput) still run? I'm not sure why one would do that, but I am just trying to learn. It seems to me that once the DAT portion is running there is no need to run the spin COG.
This program is 11 longs. Still more than the Spin program I posted. Is that because of the overhead to start the second COG?
Thanks
Shawn
If you use BST (Brads Spin Tool) it has a compile-listing window you can pop up to see all the gory details of the compiler output.
Thanks for all of your help, this has been fun learning PASM. I got another question. Is LMM written in PropBasic really 4 to 5 times faster in execution time than spin? I need to do some simple multiplication and division and it just takes to long in spin, so I was kicking around the idea of doing it in PASM. Thats when I discovered PropBasic. If it is really 4 to 5 times faster than Spin, I could probably deal with that. I have this dream though, to write most of this program in PASM. Based on the size of the object library for spin I would assume most people do not use PropBasic. And after reading a few threads on PropBasic I am not sure that it is even finished, but looks very impressive. So what are your guys thoughts. Is PropBasic better than spin? The only disadvantage I can see with PropBasic is that the code may be a little more bloated than spin. Also I am thinking that if I want to write 75 percent of my code in PASM, PropBasic may be a good way of executing my PASM.
Thanks
Shawn
While I'd never try to convince someone NOT to learn PASM (it's really useful), it might not be necessary to learn it just to get your code to go faster. Can you post the code you're referring to here? The Spin compiler makes absolutely no attempt at optimization, so it's possible that you have things in your code that are slowing it down. It's also possible you don't, but it's worth looking at.
muxz-muxc only works if you have a prior test conidtion that sets z or c
even then it may be easier to understand by using two lines to emulate the mux instruction like this
-test something- wz
if_z or outa, pin21
if_nz andn outa, pin21
My brain is stuck in and endless loop.
My ultimate goal is to make a quadcopter controller. I know there is already code out there for this, but I want to try writing the code myself. I want to learn PASM and Spin while I am doing this and I also want to understand every line of code in the program so I can tweak stuff and modify it as needed. I have found that just taking objects from the library doesn't really help me learn much. Also as soon as I run into something that I want to do that is not in the object library I am screwed.
So I am taking one part of the quadcopter program at a time and learning how to write it. I have the rc_input signal and the servo_output signal parts of the code working. I will admit I highjacked the servo32 code for this but not until I fully understood it. Once I figured out how the code functioned then I tore it apart and modified it for what I needed.
I would like my entire control loop for my flight controller to take no more than 2.5mS. This would give me a refresh rate of 400hz. There is no point in the refresh rate being any faster because this is all the faster I can refresh my esc motor controllers. This is why I keep harping on the speed of code execution. There are algorithms for mixing data from the gyros and other sensors that take a little bit of math, and I want to do this as fast as possible.
I am kicking around the Idea of having a cog running all the time just to do math functions but I have not researched this enough to know if this is possible.
Anyways, my brain is still stuck in an endless loop. Maybe I will move to another part of the quadcopter code. I need to get an I2C bus up and running at 400Khz.
I really like the PropBasic, but the code is awfully bloated and the 2k cog space is very limited, but it is fast as hell. LMM is cool but to slow, seems to be slower than spin.
Can anyone hit my reset button?
Thanks
If you want a COG to act as a co-processor for the math, take a look at how Float32 works. It has a Spin interface that sets hub variables for the arguments being passed. A COG routine sees a specific value in a HUB location that triggers a command to execute, it fires the appropriate function and returns the result. You could do something similar where you passed the address of the first of your 8 values to the COG. The PASM code would then read the values from the hub, do the math on them, generate results, then write the results back out to the hub locations (or others, possibly, to avoid problems with other code that might be using those values).
The individual functions in the Float32 code are complicated, but the way it works isn't, and it might give you a head start on how to set up your own code. From there you'd need multiply or divide functions and the glue code to tie it all together. It'll take some time to get right, but working in small pieces will make it much easier.
For I2C stuff, I'd suggest starting with Mike Green's basic I2C driver, as there's a Spin version and a PASM version, both of which are well documented. This is what I started with when writing my gyro / accel code.
http://obex.parallax.com/objects/672/ (Spin)
http://obex.parallax.com/objects/611/ (PASM)
Have fun with it! I'm looking forward to seeing your progress.
If speed rather than size is the primary issue, then it would be worth looking into C, or perhaps using spin2cpp to convert your Spin code to C++ and then compiling it with PropGCC. This is particularly effective for compute intensive code -- for example, Heater's FFT benchmark runs in 1465 ms in Spin, but speeds up to 135 ms when that same Spin code is compiled with "spin2cpp --elf -O2 -o fft.elf fft_bench.spin". (This compares to 47 ms for the pure C version and 25 ms for the PASM version.)
Eric
Should I move my spin questions to another post since the title of this is PASM Newbie Questions?
Thanks
I forgot about the 5mS write time, among other things I have some more questions but not enough time to ask.