The behavior i want
#define E() E2(k)
#define E2(k) printf("%d", k);
#define A A2(__COUNTER__)
#define A2(k) E()
A
I would like to E() expands FIRTS to E2(k) in the line #define A2(k) E(). Then the result would be printf("%d", some_number);
The real problem
Actually, im working on my college assignment and i need to simulate a language that only accepts:
V = V + 1
V = V - 1
if (V != 0) goto LABEL
We can create as many variables as we want. All the variables have the initial value equal 0. We cant use functions or nothing else. But we should use macros to re-use the code. For example, look what a macro that resets a variable value to zero looks like:
#define L(i, k) L1(i, k, __LINE__)
#define L1(i, k, l) L2(i, k, l)
#define L2(i, k, l) L_##i##k##_##l
#define ZERO(x) ZERO2(x, __COUNTER__)
#define ZERO2(x, k) \
goto L(B, k); \
L(A, k): x = x - 1; \
L(B, k): if (x != 0) goto L(A, k);
Note that this macro looks much more complicated then should be. Right? But all that bunch of thing are necessary. Let me explain. The simplified macro for this should looks like this:
#define ZERO(x) \
goto B; \
A: x = x - 1; \
B: if (x != 0) goto A;
But the problem it won't be possible to call more than one ZERO(v) macro. Because the labels A and B world be declared more than one time. To fix this we have to modify this macro to:
#define L(i) L1(i, __LINE__)
#define L1(i, l) L2(i, l)
#define L2(i, l) L_##i##_##l
#define ZERO(x) \
goto L(B); \
L(A): x = x - 1; \
L(B): if (x != 0) goto L(A);
Now we can call multiple ZERO(v) as long as we don't call more than one ZERO macro per line. But we still have one problem with this code. We cant call multiple ZERO macros inside another macro because the labels would get the same LINE index and would cause conflict. Look:
#define 2ZERO(x, y) \
ZERO(x) \
ZERO(y)
To fix this we need to pass another index for the labels inside each ZERO macro:
#define L(i, k) L1(i, k, __LINE__)
#define L1(i, k, l) L2(i, k, l)
#define L2(i, k, l) L_##i##k##_##l
#define ZERO(x) ZERO2(x, __COUNTER__)
#define ZERO2(x, k) \
goto L(B, k); \
L(A, k): x = x - 1; \
L(B, k): if (x != 0) goto L(A, k);
Now everything works. But the thing is, i dont want to write L(label, k), i would like to write just L(label) and this macro automatically should be changed to L(label, k) and everything should works.
Full Code (if some how helps)
#define L(i, k) L1(i, k, __LINE__)
#define L1(i, k, l) L2(i, k, l)
#define L2(i, k, l) L_##i##k##_##l
#define VARD(v, k) VARD1(v, k)
#define VARD1(v, k) int v##_##k = 0;
#define VAR(v, k) VAR1(v, k)
#define VAR1(v, k) v##_##k
#define END(k) END1(k, __LINE__)
#define END1(k, l) END2(k, l)
#define END2(k, l) L_##k##_##l
#define ZERO(x) ZERO2(x, __COUNTER__)
#define ZERO2(x, k) \
goto L(B, k); \
L(A, k): x = x - 1; \
L(B, k): if (x != 0) goto L(A, k);
#define ASSIGN(y, x) ASSIGN2(y, x, __COUNTER__)
#define ASSIGN2(y, x, k) \
VARD(u1, k) \
ZERO(y); \
L(A, k): if (x != 0) goto L(B, k); \
goto L(C, k); \
L(B, k): x = x - 1; \
y = y + 1; \
VAR(u1, k) = VAR(u1, k) + 1; \
goto L(A, k); \
L(C, k): if (VAR(u1, k) != 0) goto L(D, k); \
goto END(k); \
L(D, k): VAR(u1, k) = VAR(u1, k) - 1; \
x = x + 1; \
goto L(C, k); \
END(k):
#define ADD(y, x) ADD2(y, x, __COUNTER__)
#define ADD2(y, x, k) \
VARD(u1, k) \
ASSIGN(VAR(u1, k), x) \
L(A, k): if (VAR(u1, k) != 0) goto L(B, k); \
goto END(k); \
L(B, k): VAR(u1, k) = VAR(u1, k) - 1; \
y = y + 1; \
goto L(A, k); \
END(k):
I don't know if this behavior that i want is possible using only macros. But i found some interesting links that might help: https://learn.microsoft.com/en-us/cpp/preprocessor/preprocessor-experimental-overview?view=msvc-170