Macro evaluation order and application order must be opposite
Kerrigan29a opened this issue · comments
The order of application of the macros must be the opposite (I suppose). An example:
#define log(x) puts(x)
#define TOSTR(x) _TOSTR(x)
#define _TOSTR(x) #x
int main(int argc, char const *argv[])
{
printf("hi from line %u\n", __LINE__);
log("hi from line " TOSTR(__LINE__));
puts("hi from line " TOSTR(__LINE__));
return 0;
}
If I precompile this code with Clang (also with gcc and cl.exe) I get:
#1 "test_short.c"
#1 "<built-in>" 1
#1 "<built-in>" 3
#170 "<built-in>" 3
#1 "<command line>" 1
#1 "<built-in>" 2
#1 "test_short.c" 2
int main(int argc, char const *argv[])
{
printf("hi from line %u\n", 11);
puts("hi from line " "12");
puts("hi from line " "13");
return 0;
}
In the puts
line, Clan use this order to evaluate the macros:
TOSTR
_TOSTR
#x
4.__LINE__
BUT applies the macros in the opposite order:
1.__LINE__
2.#x
But if I use lcpp:
../lua/src/lua -e 'lcpp = require("lcpp"); local out = lcpp.compileFile("test_short.c"); print(out);'
I get
int main(int argc, char const *argv[])
{
printf("hi from line %u\n", 10);
puts("hi from line ");
puts("hi from line __LINE__");
return 0;
}
Because the application goes in the same order of the evaluation:
TOSTR
_TOSTR
#x
So, the stringification is applied before the__LINE__
substitution and then__LINE__
is a string, not an identifier
Sorry for my english and thank you for your work.
hmm, I understand the problem, but its not so simple.
consider following example. it evaluate FUNC prior to __ARG.
we are now thinking good way to handle both.
BTW: please do not mind your english. I'm Japanese which has poor english skill :<
and your english is far more better than mine 👍
#include <stdio.h>
#include <stdlib.h>
#define FUNC__ARG 500
#define FUNC100 400
#define __ARG 100
#define FUNC(x) FUNC##x
int main(int argc, char *argv[]) {
printf("%d\n", FUNC(__ARG)); //prints 500, not 400
}
hi, it should be fixed with umegaya/ffiex#20
I will backport this fix to lcpp after CI passed. thanks.
If I understand you correct, you say it must return 400 and not 500, but in fact the it must print 500 and not 400. Examples:
In Ubungu with gcc:
$ echo "#include <stdio.h>
#include <stdlib.h>
#define FUNC__ARG 500
#define FUNC100 400
#define __ARG 100
#define FUNC(x) FUNC##x
int main(int argc, char *argv[]) {
printf("%d\n", FUNC(__ARG)); //prints 500, not 400
}" > test.c
$
$
$ gcc -E test.c | tail -n 3
int main(int argc, char *argv[]) {
printf(%dn, 500);
}
In Mac with Clang:
$ echo "#include <stdio.h>
#include <stdlib.h>
#define FUNC__ARG 500
#define FUNC100 400
#define __ARG 100
#define FUNC(x) FUNC##x
int main(int argc, char *argv[]) {
printf("%d\n", FUNC(__ARG)); //prints 500, not 400
}" > test.c
$
$
$ clang -E test.c | tail -n 3
int main(int argc, char *argv[]) {
printf(%dn, 500);
}
In Windows with cl.exe
> notepad test.c
>
>
> cl.exe -E test.c
[...]
int main(int argc, char *argv[]) {
printf("%d\n", 500);
}
If I understand you correct, you say it must return 400 and not 500
oh, that is misunderstanding :<
what I mean with this sample is,
"if evaluation order is same as the case of #x (stringify operator),
this program should print 400 but actually it prints 500, so evaluation order is different for both (# and ##) case"
and current lcpp is made for processing ## (concat operator) correctly, it causes problem that you report.
anyway, it has been fixed with
https://github.com/umegaya/ffiex/blob/master/ffiex/lcpp.lua (see here)
I will port the fix to this project in a while (sorry for my laziness)
"(sorry for my laziness)"
no problem, im also very lazy :D