How to get a constant from C to Asm

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

Hello,

I have a constant X defined in main file. I cannot find how to use it in assembler.

/*** file main.c ***/
#define X 120

/*** file asm1.s ***/
.func foo   
foo:
      ldi  r30 , X
      ret
.endfunc

Compiler reports "undefined reference to x".
Especially I would like to use F_CPU in asm code.
But this happens:

//crystal = 10 MHz
     ldi  r30 , F_CPU/60000
../Casm1.s:55: Warning: constant out of 8-bit range: 10000000
../Casm1.s:55: Error: garbage at end of line

Is there some solution?

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

Put the define in the header file, and include it in your ASM file.

- Dean :twisted:

Make Atmel Studio better with my free extensions. Open source and feedback welcome!

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

Dean, thank you for your express answer.
I thought about what you suggest, but I did not like the warning "F_CPU redefined".

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

Then simply do *not* redefine it in the C code.

Jörg Wunsch

Please don't send me PMs, use email if you want to approach me personally.

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

I'm not sure if this is what you want for F_CPU, but I came up with this a while back-

.set MY_FREQ,0    //init to 0
.irpc param,F_CPU //go through all 'characters' in F_CPU
.ifnc \param,U    //if not a 'U'
.ifnc \param,L    //and not an 'L'
.set MY_FREQ,MY_FREQ*10+\param  //left shift,then add
.endif
.endif
.endr 

I did this so I could use the F_CPU value from the makefile in my asm. The 'UL' does not work in asm, so this will strip off the 'UL'. You will end up with MY_FREQ the same value as F_CPU.

There's probably no real 'big' advantage to doing this, but I wanted to keep one F_CPU value in one location (makefile).

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

Btw., there's no real need to tack the `UL' suffix to F_CPU at all.
In C, constants will automatically get a wider type if they don't
fit into the default type. Also, if you can declare it within a
central header file rather than the Makefile, you can use:

#if defined(__ASSEMBLER__)
#  define F_CPU 8000000
#else
#  define F_CPU 8000000UL
#endif

Jörg Wunsch

Please don't send me PMs, use email if you want to approach me personally.

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

I should have added I use Avr Studio to produce the makefile, which does the UL thing (I know, I know, but so far I'm happy to let Studio handle my makefile). So my 'one place' is actually in the Avr Studio project options.

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

Curt,

I'm intrigued - how long did you spend working on that (clever!) macro to strip the UL to get around the limitations and deficiencies of not using a real Makefile? :lol:

Cliff

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

Quote:
how long did you spend working on that (clever!) macro
I had to sorta figure out gcc asm first, but eventually after staring long enough at the list of asm directives, I found what I wanted (but almost gave up). Then to make it work was the other half of the time.

Worth it? Probably not. But I'll never have to do it again, and I did get a good look at those asm directives. I guess I figure solving little problems like that will benefit me sometime, somehow. Probably not.

I'm now 'set in my ways', and will let studio do the makefile work until it can't do it. So you have your work cut out for you to get me to 'convert' to a Real makefile.

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

Gentlemen,
thank you all for your kind replays.
Now I understand why in my code above there is Error: garbage at end of line. It is the "UL" suffix.
I use Studio makefile just as Curt wrote.
Curt, I tested your magic formula successfuly.
But next time when using asm I will try to create an external makefile.
Thanks again

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

Visovian wrote:
But next time when using asm I will try to create an external makefile.

You may already know this but just in case - Mfile in the WinAVR package is your friend - it'll basically write your Makefile for you (as it comes with a well thought out generic template). Find it on Start-Programs-WinAVR