Macros

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

I don't normally use macros but others seem to use them to make configurating botloaders etc. easier.

So I tried and failed. Is there any hope for me?

In the following simple code I want to specify the port with the "#define Switch (E)" statement. When I try to use Switch in a macro, the result is, I get Switch instead of the desired E.

This is code for the Xmega. Should this post be in the Xmega forum?

/*   Test macros   */

#include 


#define Switch  (E)           // Specify the switch port here
#define Port(a) (PORT ## a)


int main (void)
{

Port(E).PIN3CTRL      = PORT_OPC_PULLUP_gc;   // okay, I get PORTE.PIN3CTRL
Port(Switch).PIN3CTRL = PORT_OPC_PULLUP_gc;   // bad, I get PORTSwitch.PIN3CTRL

}

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0
#define xCAT2(a,b) a##b
#define CAT2(a,b) xCAT2(a,b)

#define Switch  E
#define Port(a) CAT2(PORT,a)

Stefan Ernst

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

Thanks Stefan.

I don't understand it but it works.

It's just as I suspected. You have to be crazy to understand macros. ;)

Well the port is the easy part. I'll see if I can get the pin working also.

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

Quote:
I don't understand it but it works.
The "trick" is that you have to "delay" the concatenation until all text replacements have taken place. In your version the concatenation happens before Switch is replaced by E. And after the concatenation Switch can not be replaced because it is now part of a bigger token and no longer a token on its own.

Stefan Ernst

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

sternst wrote:
The "trick" is that you have to "delay" the concatenation until all text replacements have taken place. In your version the concatenation happens before Switch is replaced by E. And after the concatenation Switch can not be replaced because it is now part of a bigger token and no longer a token on its own.
Thanks for the explanation. Maybe that will sink into my brain someday. In the meanwhile, I detected a pattern and I extended it.

I found someone on the web that defined the port and pin with one #define. His code didn't look anything like this though.

Anyway I followed your scheme and I got it to work.

/*   Test macros   */

#include 

#define SwitchPin  E,3            // specify switch pin here


#define xCAT2(a,b) a##b
#define CAT2(a,b) xCAT2(a,b)

#define xCAT3(a,b,c) a##b##c
#define CAT3(a,b,c) xCAT3(a,b,c)


#define CAT3a(a,b,c) xCAT2(a,b)
#define Port(a) CAT3a(PORT,a)

#define CAT4a(a,b,c,d) xCAT3(a,c,d)
#define Pin_control(a)  CAT4a(PIN,a,CTRL)


int main (void)
{

   Port(SwitchPin).Pin_control(SwitchPin) = PORT_OPC_PULLUP_gc;   // YES, it really works!

}

Thanks again for your help.