PDA

View Full Version : Assembly language for a beginner



Ravenkallen
05-19-2010, 11:58 PM
Hey, guys.·I have wanted to learn how to program in assembly for a long time. The only problem i had was not finding a proper micro. Now the propeller is capable of pretty much everything, including assembly. So would any of you know a good starter book/ pdf file/ tutorial, to read over. I know PASM is a little different from regular ASM, but it is the same principle, right. I do have experience in programing(C++, Basic and spin), i just thought it would be nice to put one more under my belt......Thanks again for all the previous help.

DynamoBen
05-20-2010, 12:01 AM
There are a couple of resources in a sticky at the top of this forum, but I will link to them here:

Beginners Tutorial:
http://forums.parallax.com/showthread.php?p=601870

Advanced:
http://forums.parallax.com/showthread.php?p=668559

At UPEC there was a mention that there is a forth coming PASM tutorial from Parallax...no idea on timeline.

JonnyMac
05-20-2010, 12:09 AM
While I don't teach Assembly per se, I do use it and explain what I'm doing in many of my Nuts & Volts columns. You can find them here:

www.parallax.com/Resources/NutsVoltsColumns/TheSpinZone/tabid/781/Default.aspx (http://www.parallax.com/Resources/NutsVoltsColumns/TheSpinZone/tabid/781/Default.aspx)

▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
Jon McPhalen
Hollywood, CA

beazleybub
05-20-2010, 12:39 AM
Hi·Ravenkallen,

If you don't mind me jumping on your train. :)

I'm experimenting with dot matrix displays and will have to learn assembly as well.

Maybe we could·learn together and··share what we learn with each other.
There might be something you or I don't understand along the way that the other does.

Feel free to PM me if you would like.

Cheers

▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
How can there be·nothing? Nothing is something!

rjo_
05-20-2010, 12:53 AM
PASM is pretty simple to learn... the reason most people... such as me... have any trouble with it is that the difference between ASM and PASM is at the level of machine logic... how it works is easy to figure out... what do with it and how it relates to the outside world is far more interesting.

Spend an afternoon sending various kinds of stuff back and forth between Spin and Pasm and you have learned everything that is necessary to get started. There are some tutorials... (that go a little overboard and make it look more complicated than it needs to look) in the sticky threads. After that... don't worry about PASM until you actually need it. When you find that you actually need it... then you can spend another afternoon figuring out exactly what you want it to do and it is all down hill from there.

I am not a PASM wizard... I learned just enough to know that if a problem pops up that requires PASM... it is there... it is pretty simple and there are hundreds of examples available.

Rich

DynamoBen
05-20-2010, 01:14 AM
rjo_ is correct learning the commands is simple part, thinking in PASM is the hard part. It very tedious compared to spin, you have to explicitly do things that are just handled for you in spin. Converting something from spin to PASM is a good idea then you can compare apples to apples.

rjo_
05-20-2010, 01:19 AM
DynamoBen

On the other hand... there is a thrill to rotating bits that is hard to explain. For most people, PASM might seem like a grind... I find it an absolute ball. I just don't know enough about everything else to actually need to use it as often as I would actually like to use it... task oriented and all that stuff:)


Rich

bill190
05-20-2010, 02:41 AM
Assembly is closer to the hardware and circuits. The 1's and 0's.

Helpful to know a bit about logic gates like...

AND gate, OR gate, NOT gate, XOR gate, NAND gate, etc.

Here is a bit on that...

http://en.wikipedia.org/wiki/Logic_gate

For example, an OR gate has two inputs and one output (we're talking 1's and 0's here).

If either input is a 1, you get an output of a 1.

If both inputs are 0, the output is 0.

If both inputs are 1, then you would also get an output of 1.

In assembly,·you might "OR" something to turn it on. Like this...

······· or dira, Pin0
······· or outa, Pin0

But below that you also have to say what Pin0 is...

Like this...

Pin0 long %0000_0000_0000_0000__0000_0000_0000_0001

Or like this...

Pin0 long |< 0


And what exactly are we "OR'ing"?

0000_0000_0000_0000__0000_0000_0000_0001 (Your setting)
0000_0000_0000_0000__0000_0000_0000_0000 (Existing settings)
OR'ed =...
0000_0000_0000_0000__0000_0000_0000_0001 (Turns on pin 0 for dira/outa)

Where the 1 is at the far right is pin 0, next to the left of that is pin 1, and on up.

Basically you do a lot of "ANDing", "ORing", etc. And moving bits around with commands like "MOV".

I would suggest just turning on an LED for starters. You also need to load the assembly program into a cog, that should be explained in the above documents listed.
·

beazleybub
05-20-2010, 02:59 AM
Thanks for the suggestions and links.

Is assembly language unniversal per say or is it chip specfifc?

▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
How can there be·nothing? Nothing is something!

Leon
05-20-2010, 03:19 AM
Manufacturers usually make families of devices with similar architectures and instruction sets.

▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
Leon Heller
Amateur radio callsign: G1HSM

bill190
05-20-2010, 05:26 AM
beazleybub said...
Thanks for the suggestions and links.

Is assembly language unniversal per say or is it chip specfifc?


You pretty much need to know the architecture (building blocks) of the chip and how it is put together.

I suppose you could say this would be like·going·to the grocery store in different cities. The vehicle you take being like the "language" and the cities being like different "chips".

A higher level language would be like a taxi.
Assembly language would be like driving yourself.

So with a higher level language (taxi), you can go to any city (chip) and tell the driver to take you to the grocery store. That's all you need to do. You get to the store.

With assembly (drive yourself), you need to know the·specific directions on how to get to the store. And this would be different for each different city (chip).

So with the highest level things like Microsoft software running on anything, you can say File/Print and your file gets printed on the printer.

If doing the same thing in assembly, you would need to know the exact instructions to use, the design of the chip, what is connected to what, configuration settings, and so forth.

This is quite easy on the Propeller because there is a lot of stuff taken care of for you.

But on other chips the configuration settings - say to use a certain pin for printing - can be quite complex! For example, here is a blurb from a 400 page Pic 18f4550 microcontroller data sheet for how to configure some pins...

"The PBADEN bit in Configuration Register 3H configures PORTB pins to reset as analog or digital pins by controlling how the PCFG0 bits in ADCON1 are reset. Note: On a Power-on Reset, RB4:RB0 are configured as analog inputs by default and read as ‘0’; RB7:RB5 are configured as digital inputs. By programming the Configuration bit, PBADEN (CONFIG3H<1>), RB4:RB0 will alternatively be configured as digital inputs on POR."

And that is only one of about 34 different configuration settings. If you don't have those configuration settings right for the pins you are using, you're not going to print anything!

But again you don't need to worry about that stuff with the Propeller, which is nice!
·

Ravenkallen
05-20-2010, 06:35 AM
Sounds good beazleybub. And thanks to everybody else for the suggestions.

HollyMinkowski
05-20-2010, 07:21 AM
I highly recommend PropBASIC as a PASM learning tool!

You can look over the assembly language code that the compiler
generates. Bean made both a great compiler and a PASM learning
tool http://forums.parallax.com/images/smilies/smile.gif

DynamoBen
05-20-2010, 07:22 AM
bill190, taxi vs driving yourself is a great analogy!!!

DynamoBen
05-20-2010, 07:25 AM
HollyMinkowski said...
I highly recommend PropBASIC as a PASM learning tool!

You can look over the assembly language code that the compiler
generates. Bean made both a great compiler and a PASM learning
tool http://forums.parallax.com/images/smilies/smile.gif


I tried this method when PropBASIC came out and it didn't work for me. Largely because the code produced is fatter than I would like and can be difficult to follow/read.

Call me old fashioned but starting from scratch and learning how to blink an LED is a better way to start. :)

Ravenkallen
05-20-2010, 09:30 AM
Well, i successfully ran the demo assembly program that was included in the propeller manual. it is now blinking a led on and off.....YES. Hey beazleybub, it is on page number 239 if you want to give it a go.

kuroneko
05-20-2010, 09:42 AM
Ravenkallen said...
Well, i successfully ran the demo assembly program that was included in the propeller manual. it is now blinking a led on and off.....YES. Hey beazleybub, it is on page number 239 if you want to give it a go.

Good. As the next exercise get rid of the hardcoded delay and make it a function of the actual clock frequency (i.e. make the LED flash 4 times a second for RCSLOW..80MHz).

Ravenkallen
05-20-2010, 09:47 AM
@Kuroneko....Say what? This is just my first assembly program and i have no idea what you are talking about....please, forgive my stupidity and elaborate a little.

beazleybub
05-20-2010, 09:49 AM
I,m at work right now. I promise I'll get to it by this weekend. http://forums.parallax.com/images/smilies/cool.gif

I work from 4PM till 2AM.

▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
How can there be·nothing? Nothing is something!

Ravenkallen
05-20-2010, 09:53 AM
@beazleybub..... Wow, 4pm to 2am. Tough job.

beazleybub
05-20-2010, 09:59 AM
Yes, a very tough job. I am a truck driver. Gotta hit the road actually right now.
Sent this through my Moto Droid. http://forums.parallax.com/images/smilies/smurf.gif

Good luck on your study. Write to you tomorrow.

▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
How can there be·nothing? Nothing is something!

localroger
05-20-2010, 10:04 AM
Ravenkallen, kuroneko's challenge is actually a bit harsher than he might realize; he wants you to read the system _CLKFREQ and use that to generate the constant for the WAITCNT so that the LED blinks the same rate no matter what speed the Prop is running. It would be easy in Spin, but that's actually kind of hard in PASM, for starters because the Prop has no multiply or divide instructions so you need routines to do those things, plus you need to know how to read _CLKFREQ (which IIRC you have to RDWORD from one of the header locations in Hub RAM).

A better exercise would be to learn how to communicate between your PASM program and the Spin program that starts it up, by using PAR to pass a location where you tell it something -- for example, from the Spin parent to change the LED blink rate or pin or something like that.

I think someone should mention that Propeller assembly isn't like assembly on any other comparable CPU, because just about all other CPU's allow for running "inline" assembly -- that is, you can make an assembly routine and "call" it, where it does its much faster thing while the parent code waits. On the Prop, when you spawn assembly code it inherits its own all-to-itself 80 MHz cog, and runs off to do its own thing regardless of what the mother code wants or thinks. So later synchronization requires the assembly code and the Spin that spawned it to "hook up" by dropping values into vars that each knows to read. It's a little more complicated, sometimes weirdly wasteful, but also far more powerful than the usual method.

The reason the Prop can't run inline assembly is that the Spin interpreter that runs Spin code takes up a whole cog with not a long to spare, so there's no way for that cog to add code in its own memory space and run it. All it can do is start another cog -- a much more complicated deal than what happens when a processor can hold its interpreter or compiled code and some extra stuff in the same memory. It's weird at first if you're not used to it, but like everything about the Prop what at first seems like a weirdness or weakness turns out to also be, at least in certain situations, a surprising strength.

Ravenkallen
05-20-2010, 10:04 AM
Will do.

kuroneko
05-20-2010, 10:24 AM
localroger said...
Ravenkallen, kuroneko's challenge is actually a bit harsher than he might realize; he wants you to read the system _CLKFREQ and use that to generate the constant for the WAITCNT so that the LED blinks the same rate no matter what speed the Prop is running. It would be easy in Spin, but that's actually kind of hard in PASM, for starters because the Prop has no multiply or divide instructions so you need routines to do those things, plus you need to know how to read _CLKFREQ (which IIRC you have to RDWORD from one of the header locations in Hub RAM).

Fair enough. Yes, it implies general knowledge as to how it's done (using clkfreq) but from there it's just a question of figuring out where the value is stored and just read it. Also, I picked 4 for a reason :) What it boils down to is this:



rdlong Delay, #0 ' hub location holding the system frequency
shr Delay, #3 ' equivalent to clkfreq/8, LED on 4 times, LED off 4 times


Keep asking questions!

Post Edited (kuroneko) : 5/20/2010 2:38:56 AM GMT

localroger
05-20-2010, 10:43 AM
kuroneko, you cannot expect a self-professed n00b to find a solution like that. In fact, given the number of tricks like that hidden up the Prop's sleeve, you can probably find quite a few Prop vets who'd do some head scratching over it. (I don't consider myself a prop vet yet, but give me another year.)

My father was a really excellent teacher (of college physics, among other things) and I owe much of what I have become to him. One thing I picked up from him is that while it's true you must challenge the n00bs to find their own solutions, you really must also calibrate the problem to their level of expertise, because giving the n00b a problem yo ucan solve but he can't isn't a good thing, it's just showing off.

If someone has just learned to blink an LED but you don't know their mixed-sign finite math skillz it's a much better idea to go next into moving information around, particularly in an environment like the Prop where the mother program in the higher level language keeps going. There's really no reason at all for a PASM program to ever try to figure out its blink rate constant; if that's an issue, Mom should do that and probably stuff it into the PASM image before the coginit.

Ravenkallen
05-20-2010, 10:56 AM
Uh, wow. Yeah, doing that in spin would be kinda easy, but, as stated above, i have no experience in assembly at all. The reason i choose the propeller to learn assembler, is because parallax always has excellent documentation for their products. So like any other programming language to master, it only takes time and the willingness to learn...

kuroneko
05-20-2010, 10:58 AM
localroger said...
kuroneko, you cannot expect a self-professed n00b to find a solution like that.

I apologise. I admit having trouble scaling down (which works much better in a face-to-face environment).

potatohead
05-20-2010, 11:06 AM
My next moves on the LED program would be:

Blink the pin in a repeatable, short pattern. (create program loops and delays) Your initials in morse code, for example.

Blink it in a longer pattern (use data in loop) Some cool phrase, or maybe fade the LED on a duty cycle)

Blink more than one pin. (masking / I/O)

Blink more than one pin in a different pattern. (either use more than one COG, or interleave the loops and fetch data)

etc...

The model for this kind of thing I like best is like the book, "Learning Perl", where you expand some silly simple thing into something quite complex, always adding a bit at a time, and always free to tinker a bit along the way.

▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
Propeller Wiki: Share the coolness! (http://propeller.wikispaces.com/)
8x8 color 80 Column NTSC Text Object (http://obex.parallax.com/objects/550/)
Safety Tip: Life is as good as YOU think it is!

bill190
05-20-2010, 01:29 PM
Ravenkallen said...
Well, i successfully ran the demo assembly program that was included in the propeller manual. it is now blinking a led on and off.....YES. Hey beazleybub, it is on page number 239 if you want to give it a go.
You guys are quick around here! Good work!

It took me two years of reading (and saving money to buy a pc) to get my first assembly program working...
·

Ravenkallen
05-20-2010, 09:37 PM
@potatohead. I wouldn't mind trying all of the things stated above, but i still can't find a tutorial that is easy to understand and yet still presents the important information...


@bill190.... Wow, two years. I am guessing you didn't use a propeller?

@kuroneko... Don't worry about it. No harm done. Sometimes when teaching one can forget that he/she is smarter than the class and then attempts to jump right over some important concepts. It is kind of like teaching a kid to add two numbers and then expect them to multiply a 6 digit number... WE all have to take baby steps

bill190
05-20-2010, 10:42 PM
Ravenkallen said...

@bill190.... Wow, two years. I am guessing you didn't use a propeller?

That was a Zilog Z80 using the CP/M operating system. And you could only get printed documentation or books, no internet!

·

potatohead
05-20-2010, 11:19 PM
@ravenkallen Have you tried reading my beginner document? It can be found here http://forums.parallax.com/forums/attach.aspx?a=28716

It does not have those exact variations on the blinking led, though it does go through the blinker in good detail, and introduces using more than one cog. I will add those. Funny how a thread can trigger the right thing to do. Was wondering where to go with it. Now I know. Anyway, what is there is useful, and complete enough to benefit from.

Hate to plug my own stuff, but it might be useful to you as a kick start. It got written right when I was really thinking on assembly basics. A contributor here, DeSilva, was writing a more advanced and complete document and didn't have that intro that made sense at the time, so we both wrote something.

▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
Propeller Wiki: Share the coolness! (http://propeller.wikispaces.com/)
8x8 color 80 Column NTSC Text Object (http://obex.parallax.com/objects/550/)
Safety Tip: Life is as good as YOU think it is!

tmaynard
05-21-2010, 03:01 AM
potatohead said...
Have you tried reading my beginner document? It can be found here http://forums.parallax.com/forums/attach.aspx?a=28716

I read that material when I first got a Prop -- heck, I read everything I could get my hands on -- and I've got it open in another window as I type this.

Some of the statements there conflict with my own understanding of the Prop's instruction set ... but it could be me, of course! For instance, on Page 23 you show "Adding two unsigned 32 bit numbers" and show the result "(with carry set)". My understanding is that without the "WC" effect specified for the "ADD" the carry flag will be unmodified.

In the intervening text, you explicitly refer to the "WC" and "WZ" effects and how they work ... and then in the 64-bit addition example you don't include the "WC" and then try to add the Carry bit to the result (ADDX).

These are nits. I'm certainly not complaining. That document helped me along.

Tom.

potatohead
05-21-2010, 09:47 AM
Actually good ones. Thanks. Those will get rolled into next version.

▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
Propeller Wiki: Share the coolness! (http://propeller.wikispaces.com/)
8x8 color 80 Column NTSC Text Object (http://obex.parallax.com/objects/550/)
Safety Tip: Life is as good as YOU think it is!

Ravenkallen
05-21-2010, 11:29 AM
@potatohead.... Uh, the link is not working for some reason.

potatohead
05-21-2010, 12:24 PM
Well, I didn't actually make it live with the url tag. Just checked, and it delivered me the PDF.

Try this:

http://forums.parallax.com/attachment.php?attachmentid=58857

▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
Propeller Wiki: Share the coolness! (http://propeller.wikispaces.com/)
8x8 color 80 Column NTSC Text Object (http://obex.parallax.com/objects/550/)
Safety Tip: Life is as good as YOU think it is!

Ravenkallen
05-22-2010, 12:26 AM
I did read most of that one. I think i got some of the concepts down. one thing that i didn't get though.

On the demo program, the first line initializes the pin 16. But what makes the dira turn to a output? Is that what the toggle command does? Is that like the post- set command ~~?

potatohead
05-22-2010, 03:36 AM
Dira is a control register long. All 32 bits are associated with the pins, one bit per pin. When that bit is "1", or set, then that pin is an output pin.

The instruction "mov dira, pin" is all about the labels. "dira" equals the control register COG address. "Pin" refers to the long farther down in the program that holds the value to be put into the control register. In the numbered example, that's long number 6, counting from 0, and you can see the Pin label there.

The "<16" part, means to shift left. It's short hand for this: %00000000_00000001_00000000_00000000.

A mov instruction was used so that all the dira control bit states are known. Essentially, all pins are set to input, but the one we plan on toggling. If two pins were to be toggled, there would need to be two bits set in the dira register, and that long #6 in the program would contain a different value.

Instruction #4, does a logical operation with the outa register, using the same value that was used to set the pin for output. A pin can be high or low in this program, and the "xor" instruction will toggle a bit on and off. If a bit is on, and the xor instruction is used, that bit will be set to off. Another xor instruction will reverse that, and there's your toggle right there.

dira sets the state of the pin, whether it's input or output. outa set the output state, high or low. Both registers associate each of the 32 bits in a long, with the 32 I/O pins. In this case, the same value is handy because it can be used to both set the state and toggle that state.

▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
Propeller Wiki: Share the coolness! (http://propeller.wikispaces.com/)
8x8 color 80 Column NTSC Text Object (http://obex.parallax.com/objects/550/)
Safety Tip: Life is as good as YOU think it is!

Ravenkallen
05-22-2010, 04:51 AM
OH, okay. I know how the dira register works in spin. I was just wondering how one sets the dira register in PASM and now i know, sort of. I think i am getting it, but it still seems very different from a higher level language.

potatohead
05-22-2010, 06:30 AM
Basically, you put a number in the register, and the bits that form the number cause the hardware to do things.

The key thing to understand is how the number gets written to the register! The value written, along with the operator used, impacts the result seen.

If you do a MOV, all the states of all the bits will be exactly as specified in the source portion of the MOV instruction. In other words, MOV impacts all the bits to reflect the 1 and 0 state. MOV is used in the sample program because it's an easy case. Only one pin should be output, with the others all input.

If you do an OR operation, that's different. An OR basically will only flip a bit to an on state, if the source value bit is a one. Where the source value is a zero, the register bit is untouched! Where it's a 1, that particular bit will be set to a 1, or on state. This lets you change, say bits, 1, 15, 23, without impacting the other ones. You set all the bits in the source value to 0, but for those you want to set.

If you do an AND operation, it's different still. And will only result in a 1, if both the source bit and register bit are 1, otherwise it's zero. And could be used as the inverse of OR, in that you might want to set some bits to zero, while leaving the others alone. You set all ones in the source value, but for the bits you want to clear, which would be zero.

In higher level languages, that stuff is abstracted, allowing you to specify things like pin numbers and states. In PASM, there is just the register and values and operations. You combine the register, with the value and operation that suits your needs. A commonly used value is often called a mask, and you think of it like a paint stencil, where the active operation only impacts a portion of the target material. Registers, bits and the operators, MOV, AND, OR... do the same thing.

▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
Propeller Wiki: Share the coolness! (http://propeller.wikispaces.com/)
8x8 color 80 Column NTSC Text Object (http://obex.parallax.com/objects/550/)
Safety Tip: Life is as good as YOU think it is!

Zap-o
05-22-2010, 08:30 AM
I find assembly on the propeller difficult because of the lack of a good book and the way you have to send data over from the hub.

bill190
05-22-2010, 11:18 PM
With the following assembly code, I am setting ctra to NCO mode and to output to pin 22...

mov ctra, CtraNCOp22······· 'Set ctra for NCO single-ended output to Pin 22"

CtraNCOp22·long· %00010000_00000000__00000000_00010110 '%00100 and pin 22



Note: "CtraNCOp22" is my name I have assigned to this. This could be called "Foo" or whatever. And would of course need to be called "Foo" on both lines.

The counters or ctra / ctrb documentation is the *most* difficult part of the Propeller to understand. But basically there is an entire register which can all be set at one time which I have done with my long list of 0's and 1's. Or you can set just portions of that register with "bit manipulation".

I like the 0's and 1's above because I can "see" exactly what is being written/stored/moved to the entire register. I know exactly what every bit in that register is set to.

In spin, you can do the same thing as above with the following which just sets specific areas of the register...

· 'Configure ctra module.
· ctra[30..26] := %00100····· ' Set ctra for "NCO single-ended"
· ctra[5..0] := 22··········· ' Set APIN to P22

One thing which is confusing is how do you set the output? The output is "APIN" and the documentation is not clear on this. So what "APIN" is set to is what pin the output will go to. There are two counters, A and B. Or ctra and ctrb. The output of counter A would be determined by the setting of "APIN". And the output of counter B would be determined by the setting of "BPIN".

EDIT: The above was incorrect, see following posts for correction.



Above in the second line, easy to see it is set to pin 22 because it says 22.

In the line "ctra[30..26] := %00100", the "30..26" part means just set "bits" of the counter register (1's and 0's)·30 through 26.

And that is what this is doing -> 00100

The 0 to the furthest right is bit 26, furthest left is 30. In the middle is bit 28 and is set to a 1.

This does the same thing as well as also setting the pin number...

00010000_00000000__00000000_00010110

This (00100) is on the left side. Bit 28 is the 1. Count from right to left, 0, 1, 2, 3, 4, etc. and·when you get to 28, there is that 1.

The entire "register" is like a filing cabinet drawer. It holds *all* the settings for the counter in that whole drawer. And the individual "files" within that drawer would be like individual settings for mode or the output pin. You can set just one thing, or the entire works all at once.

The entire "register" is shown in the documentation like this...

CTRA and CTRB Registers

31 30..26 25..23 22..15 14..9 8..6 5..0

- CTRMODE PLLDIV - BPIN - APIN

So that register is 31 bits long. Or might like like this...

00010000_00000000__00000000_00010110 (Look familiar?)

There is an additional document on just the Propeller counters. That is called "AN001 - Propeller Counters v1.0" and is here...

http://forums.parallax.com/attachment.php?attachmentid=59613

Another thing which is confusing is the PLLDIV part. This is where in programming microcontrollers you need to understand the hardware. In NCO mode, the output bypasses the PLL part of the counter entirely.

As to the chart·listing settings...

APIN Output - "PHSx[31]" means the direct output of PHSx·bit 31!

APIN Output - "PLLx" means it goes through the PLL first.

APIN Output - "PHSx-Carry" means it is the carry or overflow of PHSx (slower or like a bit 32 or a 33rd bit [32 start counting at 0, 33 start counting at 1]).

APIN Output - "0" means no output.



Post Edited (bill190) : 5/22/2010 7:55:11 PM GMT

BradC
05-22-2010, 11:47 PM
bill190 said...

One thing which is confusing is how do you set the output? The output is "APIN" and the documentation is not clear on this. So what "APIN" is set to is what pin the output will go to. There are two counters, A and B. Or ctra and ctrb. The output of counter A would be determined by the setting of "APIN". And the output of counter B would be determined by the setting of "BPIN".


Not quite correct I'm afraid.

There are two counters in each cog, CTRA & CTRB. Each counter has two pins it can control. APIN and BPIN. So there are ultimately 4 pins per cog that can be used by the counters.

You can set the APIN of a counter with
CTRA |= (Pin No.)
You set the BPIN with
CTRA |= (Pin No.) << 9

.. where (Pin No.) is between 0 & 31.

If you are using these pins as outputs, you also need to set the corresponding bits in the DIRA register or nothing will happen.

Start at page 95 of the Propeller Manual v1.1 for a reasonable explanation of configuring the counters.

▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
"Are you suggesting coconuts migrate?"

JonnyMac
05-22-2010, 11:50 PM
Zap-o said...
I find assembly on the propeller difficult because of the lack of a good book and the way you have to send data over from the hub.


As Holly pointed out -- and I took advantage of this week -- one can use PropBASIC as a tool for quick testing of Assembly segments as the output is native assembly. This saves the trouble of creating an interface and launching a cog.

[ Edit ]· If you don't want to go the PropBASIC route to experiment with PASM, the attached file may help.· I set it up for myself so that I could test small sections of PASM.· The assembly is a command interface where you can set a command value and one or·two parameters (very easy to change).·

▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
Jon McPhalen
Hollywood, CA

Post Edited (JonnyMac) : 5/22/2010 5:43:12 PM GMT

bill190
05-23-2010, 12:32 AM
BradC said...

bill190 said...

One thing which is confusing is how do you set the output? The output is "APIN" and the documentation is not clear on this. So what "APIN" is set to is what pin the output will go to. There are two counters, A and B. Or ctra and ctrb. The output of counter A would be determined by the setting of "APIN". And the output of counter B would be determined by the setting of "BPIN".


Not quite correct I'm afraid.

There are two counters in each cog, CTRA & CTRB. Each counter has two pins it can control. APIN and BPIN. So there are ultimately 4 pins per cog that can be used by the counters.

You can set the APIN of a counter with
CTRA |= (Pin No.)
You set the BPIN with
CTRA |= (Pin No.) << 9


See I've read all this stuff 3 times and I still don't have it right! http://forums.parallax.com/images/smilies/burger.gif

Thanks!
·

Ravenkallen
05-23-2010, 12:46 AM
@Potatohead.....I understand how logic gates work in theory and in some in practice. I bought a bunch of old 74 and 4000 series logic gates and during my first years of experimentation, i learned how they work by themselves. My problem with logic gates comes in whenever Micro controllers are involved. I mean i know that OR gates will produce a one if either input is a one, and i know a NOT gate is just a inverter, and i know that AND gates will only output a one if all inputs are a one.....ect. So about assembly. All that the MOV instruction does is just copy two numbers, right? So for the pin variable thing, instead of saying <16, could you just say something like this?

pin long %00000000_00000001_00000000_00000000

When it comes to pin I/O i always like to visualize the whole port by using raw binary....I guess i am weird, but it just seems eaiser to me


@bill190.... Yeah, The CTRA and CRTB register was the hardest to visualize. And you are right, it is way easier to "see" the register with the long binary list.

@Jonnymac.... I have heard so much about this "PropBASIC". Do you have a link for it?

@BradC.... Good catch. Having two pins for the CTR registers makes a lot more flexiable.

And to all, thank you for the help.

JonnyMac
05-23-2010, 01:17 AM
@RavenKallen

PropBASIC = http://forums.parallax.com/showthread.php?p=755835

Note that PropBASIC only runs in BST.

▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
Jon McPhalen
Hollywood, CA

potatohead
05-23-2010, 01:41 AM
Yes, it's easier for me as well. All mov does is copy the number. The bits in the number, change the states of the gates, and stuff happens. The key thing to understand is that mov will change all the states of all the bits at once.

That's the core of assembly language. All that is really happening at any one time is moving numbers, operating on them (and or, etc..), and adding them together.

So there is understanding of what the instruction literally does. What the impact of that is, depends on how the hardware is built, both the CPU and the stuff connected to it.

I will often evaluate short cut expressions, then plug the binary into the program to see if I got it. If things run the same, I probably did. If not, then I know I've got some stuff to do and learn.

If you understand the gates, then all you really need to do is understand why you use the operators instead of a mov instruction.

Generally, mov impacts the entire destination, no questions asked. Another way to think of this is mov will impact all 32 bits.

There are times when you only want to impact some of the bits, or maybe just one of them. That's what the operators are for. In this case, let's say that some of the pins are connected to other things, like maybe a few leds you want to blink at different times. For simplicity here, and because many people have a demo board, let's say pins 0, 2, 3 have leds on them. So that's three.

Breaking down a few useful instructions might be really helpful:

We need them to all be outputs, right?

mov dira, #%1101

That's a literal, meaning the value %1101 is in the instruction itself. The biggest literal is $1ff, because the rest of the bits detail what the instruction does. What gets written to dira, is 00000000_00000000_00000000_00001101

The impact of that is all pins are set to input, regardless of their prior state, with the pins we want to toggle being set to output. All 32 bits are changed, no matter what.

Let's say we start with all the leds on!

mov outa, #%1101

Again, same process. All pins are pulled low, but for the ones we picked.

Now there is a state we need to be aware of going forward. If we want to turn pin 0 off, we know there is a 0 that needs to get written to outa, bit 0. But, we also want to leave the other pins alone, and do so conditionally.

If all we had was the mov instruction, we would need lots of jmp instructions and stored binary numbers to handle all the combinations! That's impossible to do in a practical way.

Enter the operators!!

To turn pin 0 off, we need the AND instruction. The result of an and is only a 1, if both the source and destination bits are 1. Essentially then, and allows us to turn a single bit off, without impacting the other bits!

and outa, #%1110

Since there is a zero in the bit 0 position, we know that will force the outa bit 0 to be set to the low, or 0 state. The other bits will be either low or high, and be untouched, because of how and works.

To turn pin 0 on, without touching the other ones, we use the or instruction.

or outa, #%0001

It's the opposite of and! Or will set the destination bit to a 1, if either the source or destination bit is a 1.

These three instructions are the core of assembly language, where actually controlling the state of things is concerned. Mov sets the state of all the bits in the destination, erasing the state of them that was there before.

And can turn a single bit, of the 32 we are working with off, without changing the state of the other bits, using a mask. Put ones everywhere, but for the bits to be cleared, and it's a done deal.

Or can turn a single bit on, of the 32 being worked with, using a mask also. Put zeroes everywhere, but for the bits to be set, or turned on, and it's done.

Does that help?

Edit:

To turn the led connected to pin 2 on, without impacting the other leds, connected to the other pins, you would do

or dira, #%0100

off would be and dira, #%1011

etc...

▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
Propeller Wiki: Share the coolness! (http://propeller.wikispaces.com/)
8x8 color 80 Column NTSC Text Object (http://obex.parallax.com/objects/550/)
Safety Tip: Life is as good as YOU think it is!

Post Edited (potatohead) : 5/22/2010 5:54:08 PM GMT

Ravenkallen
05-23-2010, 12:14 PM
OH my gosh, Thank you potatohead for the in-depth teaching. I think i finally get it, maybe.

your first command simply declared some pins as outputs. That is what the MOV instruction does. It copies the %1011 directly to the DIRA register

The second instruction declares a few outputs as a 1 or high. Once again using the MOV instruction. This is also what OUTA will remain as, seeing as the next instructions are not MOV's, but rather bit wise operators

The rest of the commands simply take the OUTA register and the new data and preform logic on them. How does the OR and AND operators not effect the whole register?

And the source is the binary e.g %1110 and the destination is the outa register?

If you still must manipulate the whole OUTA register, Than why not just do a MOV every time?

Thanks again for the patience.

Ravenkallen
05-23-2010, 12:30 PM
Actually the OUTA can't remain the same, seeing as it's value determines the output. So just ignore that·third line.

potatohead
05-23-2010, 02:20 PM
Well, the other bits in outa won't be impacted by the AND and OR instruction, because of how the gates work. What if you need to blink the three LEDs on and off at different times?

If all you use is MOV, then you've got to either calculate or include all the possible values in your program, select the right one, then do the MOV to get it done, right?

For three LEDs, that's the following table of values:

%1101 - All pins on
%1100 - Pins 2 and 3 on, pin 0 off
%1001 - Pin 0 on, pin 2 off, pin three on
%1000 - Pin 0 off, pin 2 off, pin three on
%0101 - Pin 0 on, pin 2 on, pin three off
%0100 - Pin 0 off, pin 2 on, pin three off
%0001 - Pin 0 on, others off
%0000 - All off

What a PITA! A lot of instructions are gonna have to happen to get that all sorted out, and the more instructions you use, the slower things go, the more bugs there are, and the less things you can have the chip do in it's memory space. MOV forces you do deal with the entire problem at one time, because it changes the entire register at one time. The result of a MOV will be according to the table above. For starting out, that's great. But once the program starts doing stuff, it's not practical.

In order to pick the right value for MOV, it is necessary to examine the register, then somehow select the right value from the table above to get the desired result. Frankly, I don't even know how to code this!

When you use OR and AND, it's not necessary to read the outa register at all! All you to is decide which LED, or LED's you want to light up, and perform the operation. Let's look at a similar table for AND first:

%1111 - All pins untouched (useless)
%1110 - Pins 2 and 3 untouched, pin 0 off
%1011 - Pin 2 off, pins 0 and 3 untouched
%1010 - Pin 0 and 2 off, pin 3 untouched
%0111 - Pin 0 and pin 2 untouched, pin 3 off
%0110 - Pin 0 off, pin 2 untouched, pin 3 off
%0011 - Pin 0 untouched, pins 2 and 3 set off
%0010 - All off, for sure.

Notice bit 1. It's always a 1. Why? Because we don't want to mess with bit one at all. There is no LED connected, and maybe it's doing something else important. By putting a 1 there, we've MASKED off that bit, so that it won't be changed by the AND operation. All the possible conditions you might need are there. You can impact any of the bits in any way, without disturbing the ones that are not part of the program purpose at that particular time.

Now, OR

%1101 - All pins on
%1100 - Pins 2 and 3 on, pin 0 untouched
%1001 - Pin 2 untouched, pins 0 and 3 on
%1000 - Pin 0 and 2 untouched, pin 3 on
%0101 - Pin 0 and pin 2 on, pin 3 untouched
%0100 - Pin 0 off, pin 2 on, pin 3 untouched
%0001 - Pin 0 on, pins 2 and 3 untouched
%0000 - All untouched. (useless)

When you program your purpose in PASM, there will be loops and states that change, depending on computations, counters, inputs, etc... At some point your program will make a decision to do something other than what it was doing prior to that decision. The operators allow you to act on those pins that matter, according to the result of the decision, leaving the ones that don't matter, out of the equation, until their time comes.

This happens all the time in graphics, which I find is one of the easiest ways to get the bit operators, and how they are different from MOV.

Look at your computer screen. There are pixels all over the place. And there is your mouse pointer. When you move the mouse pointer around, assembly language instructions are operating on the bits of the screen memory. If we want to see a nice, clean mouse pointer, and have it move at a single pixel position, it's necessary to only write some of the bits and not others, because the bits not written have some meaning outside the mouse pointer part of the program.

The bit operators allow the programmer to only draw the mouse on top of what another programmer, or part of the program has already drawn, like a window with text in it. It's the same thing.

You, the programmer, will very rapidly reach a point where you want to impact one LED, without having to worry about what has been done with the other ones.

Bit operators are good for other things too.

The system counter runs very fast, one tick per clock cycle. Maybe it's a good idea to just take the lower 8 bits of the counter as some kind of simple pseudo random number. The bit operators get us this, very quickly.

Capture the counter value

mov lower_8_bits, cnt

mask off all but the lower 8 bits

and lower_8_bits, #%11111111

Because of how AND works, we know the upper 24 bits will be zero, leaving whatever was in the lower 8 bits at the time to work with elsewhere in the program.

▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
Propeller Wiki: Share the coolness! (http://propeller.wikispaces.com/)
8x8 color 80 Column NTSC Text Object (http://obex.parallax.com/objects/550/)
Safety Tip: Life is as good as YOU think it is!

Ravenkallen
05-24-2010, 01:09 AM
Okay, i think i am getting it. So The MOV instruction is sort of like writing a whole port, but the bit wise operators are kind of like writing a single pin. So If you use the OR and AND commands, other pins will not be affected at all? And i know how XOR gates work in real life, but how does that toggle the pin? And you said that the MOV instruction is one of the only commands used? Then how would one have any conditional looping?

potatohead
05-24-2010, 01:38 AM
Yeah, that's it exactly. You choose which pins, or pin is written with the mask value. If you change the mask, the same code will impact different pins.

The toggle is just how XOR works. The sample program is just a loop that repeatedly XORes the destination port pin, using the same mask value that was used to set it to output in dira. The very first XOR, turns the output pin on, with subsequent ones turning it off, or on, depending on what state it's in when the XOR happens.

It's really helpful to step through that sample program, using just pencil and paper, tracking the state of things. Just mentally run each instruction, and write the contents of the registers. Do this chart style, with a row of addresses and registers across the top, filling everything in, one line at a time for each loop through. After a few, you will get it.

The truth table for XOR is:

source = 0, destination = 0, then destination = 0
source = 0, destination = 1, then destination = 1
source = 1, destination = 1, then destination = 1
source = 1, destination = 1, then destination = 0

With XOR, the state of the destination bits will be toggled from off to on, or on to off, when the source bit is a 1. When the source bit is a 0, the state of the destination bits is untouched.

That's your toggle in the sample program.

I think we ended up in the weeds on conditional looping. If you understand the operators, and how they operate different from MOV, then you can move on to other things, like tests and loops.

Once you understand how the operators allow us to isolate individual bits, or pins with a mask, then it's possible to use those operators for lots of things.

One is to do testing. Let's say pins 0-7 are all input pins, each connected to something. There are 256 on / off state combinations possible. (0-255)

If you want to see whether or not any of the pins, 1, 3, and 4 are on, you need a mask to start with: %00011010

A MOV instruction could capture the ina register, copying it to a working long in the COG for some testing. MOV captures all 32 bits, just as it writes all 32 bits. Let's say that long is just called _input.

To test the pins, you could do:

and _input, #%00011010 NR, WZ

This instruction form is one of the more powerful things about the Propeller. The "NR" effect, means we want the Prop to perform the AND operation, but we don't want the result written to the destination register, because some more tests need to be done. The WZ effect, means we want to set the state of the Z (zero) flag, based on the result of the AND operation.

After this instruction, the Z flag will be 0, if any of the pins were on, and 1, if they were all off. A JMP instruction, with the condition bits set, would change program flow, based on the input pin states.

if_nz JMP #address

If you decide to write the result, all the bits would be cleared in that _input long, but where there was a 1 in both the source or destination. From there, using the CMP instruction, could tell you whether or not the value of the mask is equal to the value of the product of the ANDing the _input register too. That's a simple case for testing for the all on state.

That's the beginnings of conditional looping. Collect the data, operate on it to isolate the bits of interest, compare to known mask values, JMP based on the result of the comparison (Z and C flag).

▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
Propeller Wiki: Share the coolness! (http://propeller.wikispaces.com/)
8x8 color 80 Column NTSC Text Object (http://obex.parallax.com/objects/550/)
Safety Tip: Life is as good as YOU think it is!

Post Edited (potatohead) : 5/23/2010 5:45:16 PM GMT

Ravenkallen
05-24-2010, 02:42 AM
So just for the sake of clarity, which register is the source and which is the destination? And about the ....

and _input, #%00011010 NR, WZ

Was is the _input? Is that a variable?

So conditional looping is not as hard as i thought. the flags determine if the program should jump or not?

Every time i think i got it seems like i lose that reassurance. I really do want to learn this, no matter how many times i mess up. Please, continue.

potatohead
05-24-2010, 02:50 AM
The instructions work [conditions] INSTRUCTION DESTINATION, SOURCE [effects]

_input is just a long in the COG, with a label. I like to use underscores as a purpose marker, that's all.

Yep, you got it! You do operations, which set the flags for the conditionals to do things based on their state.

Let's chip away at it over time. Sometimes I have more, sometimes less, and others will jump in too.

▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
Propeller Wiki: Share the coolness! (http://propeller.wikispaces.com/)
8x8 color 80 Column NTSC Text Object (http://obex.parallax.com/objects/550/)
Safety Tip: Life is as good as YOU think it is!

Ravenkallen
05-24-2010, 05:45 AM
Yeah, your right about taking it slow. Sorry, i tend to get ahead of myself. I will skip right over level 1 and go right to level 30, only to realize i have no idea what i am doing.

potatohead
05-24-2010, 06:43 AM
Are you having fun?

If so, no apology needed.

▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
Propeller Wiki: Share the coolness! (http://propeller.wikispaces.com/)
8x8 color 80 Column NTSC Text Object (http://obex.parallax.com/objects/550/)
Safety Tip: Life is as good as YOU think it is!

Ravenkallen
05-24-2010, 07:30 AM
Well, i don't know about fun....Haha

potatohead
05-25-2010, 01:46 AM
So, where are you at now on PASM?

Should we go through a simple loop?

▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
Propeller Wiki: Share the coolness! (http://propeller.wikispaces.com/)
8x8 color 80 Column NTSC Text Object (http://obex.parallax.com/objects/550/)
Safety Tip: Life is as good as YOU think it is!

Ravenkallen
05-26-2010, 06:52 AM
Actually i just moved, so it might take a while to set me lab back up. I am not very far yet, but i hope to be experimenting tommorrow at the latest. Thanks for staying on board.

potatohead
05-26-2010, 10:33 AM
Ok then. I'm seeing just the kind of thing needed to expand my absolute beginner document. That one takes it really easy, and gets a lot of core basics done, but I wasn't sure where to take it. It's a good thing all around.

▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
Propeller Wiki: Share the coolness! (http://propeller.wikispaces.com/)
8x8 color 80 Column NTSC Text Object (http://obex.parallax.com/objects/550/)
Safety Tip: Life is as good as YOU think it is!