Pure assembly?

Go To Last Post
32 posts / 0 new
Author
Message
#1
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Is it possible to use AVR32 Studio ++ to write and simulate pure assembly language like it is in AVR Studio 4?

I have absolutely no experience programming in C, but plenty experience writing assembly for the 8bit AVRs, and looking at the AVR32 data sheets, the move from 8bit assembly to 32bit assembly looks relatively easy.

I have tried creating an empty project with a test.s file containing

mov r5,r15
main:
rjmp main

but I can't find any "Assemble and run" functions.
Also, I haven't found a way to "Select platform and Device" for my project.

I've been googling for AVR32 Assembly, but all I can find is references to the inline asm("instruction"); function used in C programming.
Searching for ARM assembly, on the other hand, gave lots of informative results, but I'm not ready to move to ARM just because I haven't (yet) figured out how to use pure assembly in AVR32 studio.

Just for laughs I tried creating a C project (which let me define the device) with a test.c containing

asm("
mov 13,r15
main:
rjmp main
");

As you can imagine, this didn't work too well, and the "build" function failed.

Is it even possible to create and simulate a pure assembly program using AVR32 studio?
If so.. What am I missing?

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

As to the C function, try:

void main(void)
{
    asm("
        mov 13,r15
        mymain:
        rjmp mymain
    ");
}

HTH,
--Rich

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

RiJoRi wrote:
As to the C function, try:

void main(void)
{
    asm("
        mov 13,r15
        mymain:
        rjmp mymain
    ");
}


That will not work well either, since the mov instruction will fail in the assembler ;)

AVR32 has 12 general registers for you to play with (+ SP, LR and PC).

The syntax is also wrong, it should be mov , .

;)

Other than that, wrapping it in a C main loop is the way to go. Writing assembler for AVR32 is not strait forward, you have to do everything yourself, even setting things like stack pointer (into SP register).

Hans-Christian

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Interesting stuff!
I know pure assembly is somewhat backwards and complicated compared to C, especially when the target gets as complex as the AVR32 (vs the AVR8).
Just an observation regarding the mov instruction:
mov , would also work.
AVR32 has 16 working registers, but r13,r14 and r15 also serves as stack pointer, link register and program counter respectively. They can still be used like any other register as far as syntax goes.
mov r11,0x8E is just as valid as
mov r15,0x8E

I downloaded the trial version of IAR, just because the advertisement had the word "assembler" in it.
It's quite different from the Studio4 assembler that I'm used to, but at least it lets me write and simulate pure assembly projects.
Still haven't nailed down all the directives and stuff, but as opposed to AVR32 Studio, it comes with sample ASM projects and fairly decent ASM documentation.

Just a final question:
Can someone confirm that AVR32 studio toolchain requires a C style project to work, and assembly can only be used as inline functions and not in stand-alone asm.s source projects, or have I missed something?

edit:
Btw... I tried the C sample provided:

void main(void)
{
    asm("
        mov r13,r15
        mymain:
        rjmp mymain
    ");
} 

but it didn't work:

..\test.c
..\test.c:2: warning: return type of 'main' is not 'int'
..\test.c:3:9: warning: missing terminating " character
..\test.c: In function 'main':
..\test.c:3: error: missing terminating " character
..\test.c:4: error: expected string literal before 'mov'
..\test.c:7:5: warning: missing terminating " character
..\test.c:7: error: missing terminating " character
..\test.c:8:3: warning: no newline at end of file
Build error occurred, build is stopped
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

For sure you can use pure assembly language for AVR32 tool chain.

you can use command line tools "avr32-as" to complie the asm code.

However, I am also looking for an Assembly Language IDE for AVR32 besides IAR. Programming assembly language in a text editor is not fun, but I don't find any better replacement for almost 4 months.

Personaly I like Assembly Language over C for microcontroller development. You get better control
over the hardware.

Good Luck!

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Hi,

there's some mixed C-assembly code in the software framework.
You should look into it.

-sma

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Where can I find documentation specific to the avr32-as.exe?
I'm looking for supported assembler directives (like .db, .equ and .org used in Studio 4) and also formatting.
In IAR assembler, a code line is divided into columns separated by whitespaces, where the 1st column is reserved for labels, the 2nd for instructions and the 3rd for operand(s):

mov r10,0x7FFF //Doesn't work
 mov r10,0x7FF //works (notice the whitespace at the beginning of the line?)

After the code has been assembled using avr32-as.exe, how do I go about loading the output back into avr32 studio to simulate it?

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

The only document I can find is AVR32 RISC instruction set inside document AVR32 Architecture Document.

Oh.. ADS 1.2 IDE I used for Assebmly is : 1st column reserved for labels.

I don't think you can load a asm file and test in AVR 32 Studio. Well, at least I don't know rather it can be done or not.

I just wonder why ATMEL dont even give a choice for customer to use Assembly instead of C.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

What I meant by loading the output in AVR32Studio wasn't loading the assembly text file, but rather the binary output from the assembler. Similar to the way you load the ELF binary generated when building a C project.

The only other way to test the code would be to actually get an evaluation kit and a programmer to try it out live.
The problem then, is I'm so new to the AVR32 I'm not even sure I'd be able to do the classic LED blinker yet. There just seems to be so much stuff that needs to be configured before the I/O pins can be controlled...

That's why I am looking for a way to simulate the ASM code before it is loaded into a real device.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Quote:
The problem then, is I'm so new to the AVR32 I'm not even sure I'd be able to do the classic LED blinker yet.
And that is why there is a free C compiler which makes excellent assembler code ;)

My 0.02 € is to learn to write C, the examples in AVR32 Studio should be quite simple to understand.

Hans-Christian

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

And herein lies the core of the problem.
Historically, I have made a significant effort not to learn C. Perhaps the AVR32 is what makes me bite the bullet.
I suppose I could learn enough C to build the LED blinker, and use the assembled output as a tutorial.
(At this point I was deep into an anti-C rant but then I thought never mind)

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Can you bite harder and jump straight to C# using Micro .NET Framework? It looks interesting and fun, although the range of devices is still limited and there are some limitations in the language compared to real C#, and not all the hardware resources are available (or efficiently implemented).

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Hi DukerX,

I have the same thinking as you do. May be I am an old fashion hardware developer, I learn Assembly and avoid learning C in my job for almost 20 years.

The reason is simple, you know exactly what you are doing with the hardware when using Assembly. Although ATMEL has done a good job in writing the software frame work in C, I rather don't want to spent time to dig into other's function, driver, etc.

Instead of writing MOV R13, 0x18

I have to write

int MyValue;
MyValue = SEE_IF_U_CAN_FIND_ME_OR_NOT;

after searching and searching that MyValue is equal to 0x18, but you have to search trhough all of the included file and might not be able to know the value. or sometime I just thought C_IF_YOU_CAN_FIND_ME_OR_NOT, then this will take me long long time debug. >.<

A simple LED blinker program takes less then 200 bytes is asm code but turn out to be around 66k using C and the software frame work. I know I can strip off lots of unused C code and routine, but it take much more time for me to do that. (maybe my C is not very good)

I know and I understand ATMEL need to develop software for multiple target (portable), but as a hardware developer, I will not change MCU much on my projects, once my company decided to use UC3, it will be years without changing to PIC, portable is not a major concern in this case, we are not writing relocatable program for PC, which might have thousands of different types of display card, we know exactly which hardware we are dealing with, no need a driver or API. I rather spend time to debug my own program instead of studing other's program.

Sorry if I offended anyone in this forum, I do agree C is a good language and ATMEL did a great job in writing the software frame work.

However, I just wonder why ATMEL don't want to give their customer a choice of Language selection like AVR Studio 4 did, which allow Assembly or C.

Sometimes live saving interupt can only be done with Assambly and lots of programming tricks can only be done with Assembly (especially when your code is 130K but you only have 128K flash). But I don't have a choice for writing Assembly in UC3 MCU.

Oh.. by the way, I am trying to see if I can load the object file into the AVR32 Studio for debug purpose, will keep you post if you still interest in that.

^_^

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

This is a quick guide on how to write asm in AVR32 Studio without inlining it.

1. Create a new AVR32 C Project. Use project type AVR32 Standalone.
2. Add a new source file to the project and name it main.s or main.x
3. Write assembly:

.public main

main:
 mov r1, r2
 rjmp main

 .end

4. Build project (Project->Build Project)

This should output something like (I have named the project MyAssemblerProject and used ap7000):
avr32-as -mpart=ap7000 -g3 -omain.o ../main.s
avr32-gcc -mpart=ap7000 -Wl,--gc-sections -oMyAssemblerProject.elf main.o

5. Debug your assembly code with breakpoints single step etc. Open the Registers view and expand the Main section to see the general registers. Open the AVR32 Registers view to see the system registers etc.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

This looks promising!
I did exactly as specified and all is good until I reach step 5.
I jsut couldn't make the AVR32 simulator work using the AP7k MCU...
Tried to change the project to use UC3B0256 and the EVK1101 as "board". This worked just fine, and I am now able to write pure assembly in AVR32 studio!
Jay!!

(If I only could find the manual for the AVR32 assembler to learn about directives an such..)

I still have lots to learn about AVR32 studio, targets, debugger+++ but this is a massive step forward.

@larseven: You're the man! I can't start to express my aprechiation.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

The assembler is GNU assembler, they have quite a lot of documentation; http://sourceware.org/binutils/d...

For details about the instruction set see the AVR32 Architecture Manual at http://www.atmel.com/dyn/product...

Hans-Christian

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

For AVR32 RISC instruction set, read chapter 8 in:
http://www.atmel.com/dyn/resourc...

For GNU assembler doc (should include directives):
http://sourceware.org/binutils/d...

Good luck:)

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Thank you very much larseven, this is a great help!

^_^

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

You might feel like screaming RTFM, but I have a few more questions...
What does the ".public main" directive mean? I haven't found it in the GNU assembler docs (which beside this has been very informative).
And...
Why is my program starting at 0x80000114 and not 0x80000000, which is the beginning of the flash?

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

if you disassemble the program (objdump -d ) then you will probably see some trampoline like commands at the start, setting up various stuff. IIRC you have to use --nostdlib to be completely free of all the stuff the toolchain adds.

Hans-Christian

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

This "trampoline" stuff you speak of... Is that somehow related to a bootloader on the EVK1101 (that I set as the build target)?

turning on the --nostdllib caused the assembler to whine about a missing "_start" symbol, so I changed

.public main
main:

into

.public _start
_start:

Now it builds OK, and the program starts at 0x80000000 as expected* but breakpoints seems to be disabled for the first 2 instructions. No big deal, but curious nonetheless.

*In the data sheet, it says: "For AVR32B,
the reset routine entry address is always fixed to 0xA000_0000."
My project is set up to use the UC3B0256, and my simulator target is set up to use EVK1101 and UC3B0256 as well.
I still haven't invested in any hardware, so it's too early to tell if it's just a minor bug, or a real problem.
Any attempts at using .org 0xA0000000 to make things "right" makes the assembler fail, and accuses me of .org-ing backwards.

Last Edited: Thu. Sep 25, 2008 - 12:54 PM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

The "trampoline" stuff is the crt0.o (think it is called that) stuff which is shipped with the compiler. It will setup the SP and do some other stuff.

Do a objdump -d and look for the _start symbol.

Hans-Christian

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0
.public main

makes the label/function main a public symbol so you can specify it as an entry point which will be used by the linker.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Out of pure noobness... How do I "do a objdump -d" ?

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

use the command line:

avr32-objdump your_elf_file_here.elf -d

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Holy moly!

The 0x0114 bytes of "stuff" ahead of my original main: was just the tip of the iceberg.
The last instruction is at 0x7814. That's about 30k of stuff I didn't put there.
I'm sure these functions might be handy at some point (malloc for one) but as a beginner in AVR32, I think I'll just keep it out of there for now so I don't confuse myself even more.

All this new insight has lead me to conclude it's time to get some hardware to work on.
I've been looking at the EVK1100 and EVK1101 boards and a JTAG2. The problem is that the stores that has the JTAG at a reasonable price doesn't have the EVK boards in stock. www.elfa.se seems to have the EVK boards stocked, but the JTAG is about twice as expensive as the same unit from Mouser.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

UC3 devices have a USB bootloader, so you must not have a JTAGICE mkII to begin with. There is an appnote about the USB bootloader on atmel.com/avr32 somewhere.

Hans-Christian

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

My EVK1101 and JTAGICEmkII has arived ! Jay!

the UC has been erased and I'm successfully debugging the unit. Starting simple, I'm just loading, pushing and popping registers and it's all good.
But why is the JTAG writing 4136 bytes when my program is only 22 bytes long?
I have turned on the --nostdlib flag.
Is there some way to read back the data and disassemble it to find out what got written to the UC in adition to my 22 byte program?

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

I wrote a simple helloworld, compiled it with avr32-gcc and here whats inside the .lss (assembler) file:

80000000: bral 80002000 ; Jump always
(nothing in between)
80002000: lddpc pc,80002004 ; Load PC..
80002004: 800020F8 ; ..with this address, ie jump there
80002008: An interrupt handler i didn't write
80002040: An interrupt table i didn't write
80002084: My main and function code
800020F8: Stack pointer, EVBA register init. Loads adresses to memory etc.
80002200: EVBA area, exception handlers (actually infinite loops)
80002304: Default (?) interrupt handlers.
800023A4: ipr_val, whatever that means.

Sum size: 9155 byte. In the same folder as the .lss file I find a .bin file with size 9368, and the .elf which is 49152 byte. Perhaps the USB stuff and bootloader is added to the .elf file? Is it possible to load the .bin file into the evk1100 kit?

IAR EW does not create such big executables when I write helloworld in ASM, the .elf start at 500 bytes and increase with the code i write.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

And you use the -nostdlib ? IIRC there are another option not to add anything except your own code.

But why do you want to write in asm? The C compiler is most likely a lot smart than you will ever be able to write an asm program. And IMHO a C project is a lot more maintainable than a asm project.

0.02 €

Hans-Christian

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

I have no problem with C-programs and the size of the executabe, i just wanted to show what was inside.

ASM is fine for tweaking small applications and learning what is happening inside the microcontroller and the C framework. Then write better C code.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

DukerX wrote:
What does the ".public main" directive mean?

Beats me. I suspect it should be ".global main", which makes the symbol externally visible (i.e. can be called from other modules).
Quote:
Why is my program starting at 0x80000114 and not 0x80000000, which is the beginning of the flash?

Probably because the low-level startup code runs from 0x80000000. If you want to get all the way down to the bare metal, call your entry point "_start" instead of "main" and link with the -nostdlib option. Note that the object that defines _start needs to be linked first unless you want to play around with sections and linker scripts and whatnot.

Note that while it may be fun to write assembly for small projects (or parts of bigger projects), when it gets beyond a certain level of complexity, the compiler is generally going to do a better job of writing assembly than you do. No offense, but people that are able to beat the compiler tend to end up working on improving it :-)