Skip to content

Commit 351a058

Browse files
authored
Merge pull request #224 from sysprog21/parse-macro
Implement macro parameter substitution in statement contexts
2 parents 1fb9fa5 + 607a19b commit 351a058

File tree

2 files changed

+73
-0
lines changed

2 files changed

+73
-0
lines changed

src/parser.c

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2671,6 +2671,36 @@ basic_block_t *read_body_statement(block_t *parent, basic_block_t *bb)
26712671
if (!lex_peek(T_identifier, token))
26722672
error("Unexpected token");
26732673

2674+
/* handle macro parameter substitution for statements */
2675+
int macro_param_idx = find_macro_param_src_idx(token, parent);
2676+
if (macro_param_idx && parent->macro) {
2677+
/* save current state */
2678+
int saved_size = SOURCE->size;
2679+
char saved_char = next_char;
2680+
int saved_token = next_token;
2681+
2682+
/* jump to parameter value */
2683+
SOURCE->size = macro_param_idx;
2684+
next_char = SOURCE->elements[SOURCE->size];
2685+
next_token = lex_token();
2686+
2687+
/* extract the parameter value as identifier token */
2688+
if (lex_peek(T_identifier, token)) {
2689+
lex_expect(T_identifier);
2690+
} else {
2691+
/* parameter is not a simple identifier, restore state and continue
2692+
*/
2693+
SOURCE->size = saved_size;
2694+
next_char = saved_char;
2695+
next_token = saved_token;
2696+
}
2697+
2698+
/* restore source position */
2699+
SOURCE->size = saved_size;
2700+
next_char = saved_char;
2701+
next_token = saved_token;
2702+
}
2703+
26742704
/* is it a variable declaration? */
26752705
int find_type_flag = lex_accept(T_struct) ? 2 : 1;
26762706
type = find_type(token, find_type_flag);

tests/driver.sh

Lines changed: 43 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -942,6 +942,49 @@ int main()
942942
}
943943
EOF
944944

945+
# macro parameter substitution works in expression contexts
946+
try_ 15 << EOF
947+
#define ADD_PARAMS(a, b) ((a) + (b))
948+
int main()
949+
{
950+
int x = 5, y = 10;
951+
return ADD_PARAMS(x, y);
952+
}
953+
EOF
954+
955+
# macro with assignment operators
956+
try_ 18 << EOF
957+
#define ASSIGN_MACRO(variable, val) \
958+
variable = variable + val + 10
959+
int main()
960+
{
961+
int x = 5;
962+
ASSIGN_MACRO(x, 3);
963+
return x;
964+
}
965+
EOF
966+
967+
try_ 27 << EOF
968+
#define COMPOUND_ASSIGN(variable, val) \
969+
variable += val + 10
970+
int main()
971+
{
972+
int y = 10;
973+
COMPOUND_ASSIGN(y, 7);
974+
return y;
975+
}
976+
EOF
977+
978+
try_ 42 << EOF
979+
#define SET_VAR(var, value) var = value
980+
int main()
981+
{
982+
int z = 0;
983+
SET_VAR(z, 42);
984+
return z;
985+
}
986+
EOF
987+
945988
try_output 0 "Wrapper: Hello World!" << EOF
946989
#define WRAPPER(...) \
947990
do { \

0 commit comments

Comments
 (0)