• AVR Freaks

AnsweredHot!Set a Special Function Register using #define

Author
tarts
New Member
  • Total Posts : 13
  • Reward points : 0
  • Joined: 2011/06/19 07:41:59
  • Location: 0
  • Status: offline
2020/02/29 02:31:05 (permalink)
0

Set a Special Function Register using #define

Could anyone please explain why this works:
adc.c
#include <xc.h>         /* XC8 General Include File */

void adc_Init(void)
{
    ADCON1bits.ADFM = 1;
}

 
And this does not.
adc.c:33:19: error: (195) expression syntax

 
adc.h
#define ADFM_SETTING = 1; //Result justified: 1-right (ADRESH 0,1 as bit 9, 10)

void adc_Init(void);

adc.c
#include <xc.h> /* XC8 General Include File */
#include "adc.h"

void adc_Init(void)
{
    ADCON1bits.ADFM = ADFM_SETTING;
}

post edited by tarts - 2020/02/29 02:35:17
#1
ric
Super Member
  • Total Posts : 26083
  • Reward points : 0
  • Joined: 2003/11/07 12:41:26
  • Location: Australia, Melbourne
  • Status: online
Re: Set a Special Function Register using #define 2020/02/29 03:17:46 (permalink) ☼ Best Answerby tarts 2020/02/29 03:26:37
+2 (2)
You're using the wrong syntax for #define
Change:
#define ADFM_SETTING = 1; //Result justified: 1-right (ADRESH 0,1 as bit 9, 10)

to:
#define ADFM_SETTING 1 //Result justified: 1-right (ADRESH 0,1 as bit 9, 10)

i.e. do NOT use "=" and do NOT put a ";" on the end.
 
 

I also post at: PicForum
Links to useful PIC information: http://picforum.ric323.co...opic.php?f=59&t=15
NEW USERS: Posting images, links and code - workaround for restrictions.
To get a useful answer, always state which PIC you are using!
#2
tarts
New Member
  • Total Posts : 13
  • Reward points : 0
  • Joined: 2011/06/19 07:41:59
  • Location: 0
  • Status: offline
Re: Set a Special Function Register using #define 2020/02/29 03:26:47 (permalink)
0
Smile: Smile
#3
1and0
Access is Denied
  • Total Posts : 10548
  • Reward points : 0
  • Joined: 2007/05/06 12:03:20
  • Location: Harry's Gray Matter
  • Status: offline
Re: Set a Special Function Register using #define 2020/02/29 03:27:29 (permalink)
+1 (1)
tarts
And this does not.
adc.c:33:19: error: (195) expression syntax

#define ADFM_SETTING = 1; //Result justified: 1-right (ADRESH 0,1 as bit 9, 10)
 
    ADCON1bits.ADFM = ADFM_SETTING;
 


Ric has given you the correct way. 
 
Here's why yours does not work. A #define is basically a text substitution, so this
#define ADFM_SETTING = 1;
 
    ADCON1bits.ADFM = ADFM_SETTING;

expands to this
    ADCON1bits.ADFM = = 1;;

and = = (with a space in between) is not a C operator. The second semicolon is not an issue; it just makes an empty statement.
post edited by 1and0 - 2020/02/29 03:28:41
#4
1and0
Access is Denied
  • Total Posts : 10548
  • Reward points : 0
  • Joined: 2007/05/06 12:03:20
  • Location: Harry's Gray Matter
  • Status: offline
Re: Set a Special Function Register using #define 2020/02/29 03:32:31 (permalink)
+2 (2)
So, if you have done this:
    ADCON1bits.ADFM =ADFM_SETTING;

the compile will be okay with it, since it will expand to this
    ADCON1bits.ADFM == 1;;

which is valid C, even thought that's not what you wanted anyway. ;)
 
 
#5
ric
Super Member
  • Total Posts : 26083
  • Reward points : 0
  • Joined: 2003/11/07 12:41:26
  • Location: Australia, Melbourne
  • Status: online
Re: Set a Special Function Register using #define 2020/02/29 03:36:26 (permalink)
+1 (1)
Meaning it wouldn't give a syntax error, but it would NOT change the value of the ADFM bit either.
 

I also post at: PicForum
Links to useful PIC information: http://picforum.ric323.co...opic.php?f=59&t=15
NEW USERS: Posting images, links and code - workaround for restrictions.
To get a useful answer, always state which PIC you are using!
#6
Mysil
Super Member
  • Total Posts : 3666
  • Reward points : 0
  • Joined: 2012/07/01 04:19:50
  • Location: Norway
  • Status: offline
Re: Set a Special Function Register using #define 2020/02/29 03:52:34 (permalink)
+1 (1)
Hi,
In a preprocessor macro, like you try to do in the header file, 
#define ADFM_SETTING = 1;  
 
specify a symbol and a replacement text to be used where the symbol is encountered.
The macro name is delimited by the first space character after the macro name, Not by a:  '='  operator.
so the macro name is:  'ADFM_SETTING'
and the replacement string is: '= 1;' 
When this is inserted in the adc.c   file, the statement become:
    ADCON1bits.ADFM = = 1;; 

so now you have got 2 '=' operators, and also double semicolon, where there should be only one of each.
You should remove the '=' operator, and the semicolon ';' from the macro definition: #define ... 
Then it will work as you expect.
 
In this case, the extra semicolon doesn't cause a problem,
but if you use such a macro in something like a test or a: if then else   construct,
then an extra semicolon will cause mistakes in the program logic.
Thus the advise is that there should Not be a semicolon at the end  of a #define line.
 
    Mysil
#7
du00000001
Just Some Member
  • Total Posts : 3461
  • Reward points : 0
  • Joined: 2016/05/03 13:52:42
  • Location: Germany
  • Status: offline
Re: Set a Special Function Register using #define 2020/02/29 04:02:20 (permalink)
0
@ ric
Be careful with comments when #defining: your first example wouldn"t work as the ';' would be commented out.
Rule: if you want to comment #defines in the same line, use /* ... */ only.

PEBKAC / EBKAC / POBCAK / PICNIC (eventually see en.wikipedia.org)
#8
ric
Super Member
  • Total Posts : 26083
  • Reward points : 0
  • Joined: 2003/11/07 12:41:26
  • Location: Australia, Melbourne
  • Status: online
Re: Set a Special Function Register using #define 2020/02/29 04:12:09 (permalink)
+1 (1)
du00000001
@ ric
Be careful with comments when #defining: your first example wouldn"t work as the ';' would be commented out.
Rule: if you want to comment #defines in the same line, use /* ... */ only.

That was my original understanding, but one of the compiler authors has commented on this forum that the preprocessor discards the "//" comment BEFORE parsing the #define, so it's perfectly safe to comment a #define line.
The "//" comment does NOT become part of the substitution string.
 

I also post at: PicForum
Links to useful PIC information: http://picforum.ric323.co...opic.php?f=59&t=15
NEW USERS: Posting images, links and code - workaround for restrictions.
To get a useful answer, always state which PIC you are using!
#9
1and0
Access is Denied
  • Total Posts : 10548
  • Reward points : 0
  • Joined: 2007/05/06 12:03:20
  • Location: Harry's Gray Matter
  • Status: offline
Re: Set a Special Function Register using #define 2020/02/29 04:23:33 (permalink)
+1 (1)
As I've understood it, the preprocessor replaces comment with a single space character.
 
#10
1and0
Access is Denied
  • Total Posts : 10548
  • Reward points : 0
  • Joined: 2007/05/06 12:03:20
  • Location: Harry's Gray Matter
  • Status: offline
Re: Set a Special Function Register using #define 2020/02/29 05:05:23 (permalink)
+1 (1)
Mysil
The macro name is delimited by the first space character after the macro name, Not by a:  '='  operator.
so the macro name is:  'ADFM_SETTING'
and the replacement string is: '= 1;' 

Pedantic. I think it's delimited by whitespace(s) after the macro name. That is, the first character of the replacement string is the first non-whitespace character after the macro name.
#11
du00000001
Just Some Member
  • Total Posts : 3461
  • Reward points : 0
  • Joined: 2016/05/03 13:52:42
  • Location: Germany
  • Status: offline
Re: Set a Special Function Register using #define 2020/02/29 09:58:20 (permalink)
+1 (1)
Having hunted down some #define comment issues, my personal experience is that everything following the symbol defined is taken by the preprocessor to replace the symbol's occurrences. Resulting in issues with the // comment style (which I prefer otherwise - where applicable).
Might be XC8 handles this differently, but I won't challenge my luck. I'm working with just too many compilers for different architectures to memorize or use any non-mandatory specifics.

PEBKAC / EBKAC / POBCAK / PICNIC (eventually see en.wikipedia.org)
#12
crosland
Super Member
  • Total Posts : 1872
  • Reward points : 0
  • Joined: 2005/05/10 10:55:05
  • Location: Warks, UK
  • Status: offline
Re: Set a Special Function Register using #define 2020/02/29 10:56:45 (permalink)
0
du00000001
Having hunted down some #define comment issues, my personal experience is that everything following the symbol defined is taken by the preprocessor to replace the symbol's occurrences. 



I've never found that, across a range of compilers. Thinking about it most (not Microchips) would have been gcc derived.
#13
du00000001
Just Some Member
  • Total Posts : 3461
  • Reward points : 0
  • Joined: 2016/05/03 13:52:42
  • Location: Germany
  • Status: offline
Re: Set a Special Function Register using #define 2020/02/29 11:32:35 (permalink)
+1 (1)
I've been "playing" with the expensive tools from Diab/Windriver, Green Hills, Metrowerks and alike.
These are really great, and AFAIK none of these is gcc-based.

PEBKAC / EBKAC / POBCAK / PICNIC (eventually see en.wikipedia.org)
#14
jtemples
عُضْوٌ جَدِيد
  • Total Posts : 11673
  • Reward points : 0
  • Joined: 2004/02/13 12:31:19
  • Location: Southern California
  • Status: offline
Re: Set a Special Function Register using #define 2020/02/29 12:19:09 (permalink)
+2 (2)
my personal experience is that everything following the symbol defined is taken by the preprocessor to replace the symbol's occurrences. Resulting in issues with the // comment style

 
Comments are replaced by spaces before preprocessor directives are processed.  This is clearly stated in the standard.
 
I'm working with just too many compilers for different architectures to memorize or use any non-mandatory specifics.

 
It is mandatory.
#15
1and0
Access is Denied
  • Total Posts : 10548
  • Reward points : 0
  • Joined: 2007/05/06 12:03:20
  • Location: Harry's Gray Matter
  • Status: offline
Re: Set a Special Function Register using #define 2020/02/29 14:24:53 (permalink)
+1 (1)
du00000001
Having hunted down some #define comment issues, my personal experience is that everything following the symbol defined is taken by the preprocessor to replace the symbol's occurrences. Resulting in issues with the // comment style (which I prefer otherwise - where applicable).
Might be XC8 handles this differently, but I won't challenge my luck. I'm working with just too many compilers for different architectures to memorize or use any non-mandatory specifics.

Here's the language standard:
C99 5.1.1.2/3
The source file is decomposed into preprocessing tokens6) and sequences of white-space characters (including comments). A source file shall not end in a partial preprocessing token or in a partial comment. Each comment is replaced by one space character. New-line characters are retained. Whether each nonempty sequence of white-space characters other than new-line is retained or replaced by one space character is implementation-defined.

The comments are replaced with a single space character in the translation phase, which happens prior to the preprocessing directive parsing.
 
#16
jtemples
عُضْوٌ جَدِيد
  • Total Posts : 11673
  • Reward points : 0
  • Joined: 2004/02/13 12:31:19
  • Location: Southern California
  • Status: offline
Re: Set a Special Function Register using #define 2020/02/29 15:48:00 (permalink)
+1 (1)
It's hard to imagine event the lamest of C compilers getting this wrong.
#17
mlp
boots too small
  • Total Posts : 881
  • Reward points : 0
  • Joined: 2012/09/10 15:12:07
  • Location: previously Microchip XC8 team
  • Status: offline
Re: Set a Special Function Register using #define 2020/03/01 21:40:05 (permalink)
0
jtemples
It's hard to imagine event the lamest of C compilers getting this wrong.

Oh no it isn't.
 
Or slightly more seriously: if it gets this wrong, it's not actually a C compiler.

Mark (this opinion available for hire)
#18
ric
Super Member
  • Total Posts : 26083
  • Reward points : 0
  • Joined: 2003/11/07 12:41:26
  • Location: Australia, Melbourne
  • Status: online
Re: Set a Special Function Register using #define 2020/03/01 21:47:11 (permalink)
0
du00000001
Having hunted down some #define comment issues, my personal experience is that everything following the symbol defined is taken by the preprocessor to replace the symbol's occurrences. Resulting in issues with the // comment style (which I prefer otherwise - where applicable).
...

Bearing in mind subsequent comments, this appears to be abnormal behaviour.
Can you name and shame the compiler that did it?
 

I also post at: PicForum
Links to useful PIC information: http://picforum.ric323.co...opic.php?f=59&t=15
NEW USERS: Posting images, links and code - workaround for restrictions.
To get a useful answer, always state which PIC you are using!
#19
Jump to:
© 2020 APG vNext Commercial Version 4.5