- call TOK_GET() as a function only for tokens with values - get rid of 'next_nomacro_spc()' - be sligtly more efficient in next() This made about 4-5%+ speed in my tests.
Unified · Split
| @@ -35,6 +35,7 @@ · 34 unmodified lines | |||
| 35 | #include <time.h> | 35 | #include <time.h> |
| 36 | 36 | ||
| 37 | #ifndef _WIN32 | 37 | #ifndef _WIN32 |
| 38 | # define WIN32_LEAN_AND_MEAN 1 | ||
| 38 | # include <unistd.h> | 39 | # include <unistd.h> |
| 39 | # include <sys/time.h> | 40 | # include <sys/time.h> |
| 40 | # ifndef CONFIG_TCC_STATIC | 41 | # ifndef CONFIG_TCC_STATIC |
| @@ -1009,6 +1010,9 @@ struct filespec { · 968 unmodified lines | |||
| 1009 | 1010 | ||
| 1010 | /* token values */ | 1011 | /* token values */ |
| 1011 | 1012 | ||
| 1013 | /* conditional ops */ | ||
| 1014 | #define TOK_LAND 0x90 | ||
| 1015 | #define TOK_LOR 0x91 | ||
| 1012 | /* warning: the following compare tokens depend on i386 asm code */ | 1016 | /* warning: the following compare tokens depend on i386 asm code */ |
| 1013 | #define TOK_ULT 0x92 | 1017 | #define TOK_ULT 0x92 |
| 1014 | #define TOK_UGE 0x93 | 1018 | #define TOK_UGE 0x93 |
| @@ -1023,62 +1027,65 @@ struct filespec { · 8 unmodified lines | |||
| 1023 | #define TOK_LE 0x9e | 1027 | #define TOK_LE 0x9e |
| 1024 | #define TOK_GT 0x9f | 1028 | #define TOK_GT 0x9f |
| 1025 | 1029 | ||
| 1026 | #define TOK_LAND 0xa0 | 1030 | #define TOK_ISCOND(t) (t >= TOK_LAND && t <= TOK_GT) |
| 1027 | #define TOK_LOR 0xa1 | 1031 | |
| 1028 | #define TOK_DEC 0xa2 | 1032 | #define TOK_DEC 0x80 /* -- */ |
| 1029 | #define TOK_MID 0xa3 /* inc/dec, to void constant */ | 1033 | #define TOK_MID 0x81 /* inc/dec, to void constant */ |
| 1030 | #define TOK_INC 0xa4 | 1034 | #define TOK_INC 0x82 /* ++ */ |
| 1031 | #define TOK_UDIV 0xb0 /* unsigned division */ | 1035 | #define TOK_UDIV 0x83 /* unsigned division */ |
| 1032 | #define TOK_UMOD 0xb1 /* unsigned modulo */ | 1036 | #define TOK_UMOD 0x84 /* unsigned modulo */ |
| 1033 | #define TOK_PDIV 0xb2 /* fast division with undefined rounding for pointers */ | 1037 | #define TOK_PDIV 0x85 /* fast division with undefined rounding for pointers */ |
| 1038 | #define TOK_UMULL 0x86 /* unsigned 32x32 -> 64 mul */ | ||
| 1039 | #define TOK_ADDC1 0x87 /* add with carry generation */ | ||
| 1040 | #define TOK_ADDC2 0x88 /* add with carry use */ | ||
| 1041 | #define TOK_SUBC1 0x89 /* add with carry generation */ | ||
| 1042 | #define TOK_SUBC2 0x8a /* add with carry use */ | ||
| 1043 | #define TOK_SHL '<' /* shift left */ | ||
| 1044 | #define TOK_SAR '>' /* signed shift right */ | ||
| 1045 | #define TOK_SHR 0x8b /* unsigned shift right */ | ||
| 1046 | |||
| 1047 | #define TOK_ARROW 0xa0 /* -> */ | ||
| 1048 | #define TOK_DOTS 0xa1 /* three dots */ | ||
| 1049 | #define TOK_TWODOTS 0xa2 /* C++ token ? */ | ||
| 1050 | #define TOK_TWOSHARPS 0xa3 /* ## preprocessing token */ | ||
| 1051 | #define TOK_PLCHLDR 0xa4 /* placeholder token as defined in C99 */ | ||
| 1052 | #define TOK_NOSUBST 0xa5 /* means following token has already been pp'd */ | ||
| 1053 | #define TOK_PPJOIN 0xa6 /* A '##' in the right position to mean pasting */ | ||
| 1054 | |||
| 1055 | /* assignment operators */ | ||
| 1056 | #define TOK_A_ADD 0xb0 | ||
| 1057 | #define TOK_A_SUB 0xb1 | ||
| 1058 | #define TOK_A_MUL 0xb2 | ||
| 1059 | #define TOK_A_DIV 0xb3 | ||
| 1060 | #define TOK_A_MOD 0xb4 | ||
| 1061 | #define TOK_A_AND 0xb5 | ||
| 1062 | #define TOK_A_OR 0xb6 | ||
| 1063 | #define TOK_A_XOR 0xb7 | ||
| 1064 | #define TOK_A_SHL 0xb8 | ||
| 1065 | #define TOK_A_SAR 0xb9 | ||
| 1066 | |||
| 1067 | #define TOK_ASSIGN(t) (t >= TOK_A_ADD && t <= TOK_A_SAR) | ||
| 1068 | #define TOK_ASSIGN_OP(t) ("+-*/%&|^<>"[t - TOK_A_ADD]) | ||
| 1034 | 1069 | ||
| 1035 | /* tokens that carry values (in additional token string space / tokc) --> */ | 1070 | /* tokens that carry values (in additional token string space / tokc) --> */ |
| 1036 | #define TOK_CCHAR 0xb3 /* char constant in tokc */ | 1071 | #define TOK_CCHAR 0xc0 /* char constant in tokc */ |
| 1037 | #define TOK_LCHAR 0xb4 | 1072 | #define TOK_LCHAR 0xc1 |
| 1038 | #define TOK_CINT 0xb5 /* number in tokc */ | 1073 | #define TOK_CINT 0xc2 /* number in tokc */ |
| 1039 | #define TOK_CUINT 0xb6 /* unsigned int constant */ | 1074 | #define TOK_CUINT 0xc3 /* unsigned int constant */ |
| 1040 | #define TOK_CLLONG 0xb7 /* long long constant */ | 1075 | #define TOK_CLLONG 0xc4 /* long long constant */ |
| 1041 | #define TOK_CULLONG 0xb8 /* unsigned long long constant */ | 1076 | #define TOK_CULLONG 0xc5 /* unsigned long long constant */ |
| 1042 | #define TOK_STR 0xb9 /* pointer to string in tokc */ | 1077 | #define TOK_CLONG 0xc6 /* long constant */ |
| 1043 | #define TOK_LSTR 0xba | 1078 | #define TOK_CULONG 0xc7 /* unsigned long constant */ |
| 1044 | #define TOK_CFLOAT 0xbb /* float constant */ | 1079 | #define TOK_STR 0xc8 /* pointer to string in tokc */ |
| 1045 | #define TOK_CDOUBLE 0xbc /* double constant */ | 1080 | #define TOK_LSTR 0xc9 |
| 1046 | #define TOK_CLDOUBLE 0xbd /* long double constant */ | 1081 | #define TOK_CFLOAT 0xca /* float constant */ |
| 1047 | #define TOK_PPNUM 0xbe /* preprocessor number */ | 1082 | #define TOK_CDOUBLE 0xcb /* double constant */ |
| 1048 | #define TOK_PPSTR 0xbf /* preprocessor string */ | 1083 | #define TOK_CLDOUBLE 0xcc /* long double constant */ |
| 1049 | #define TOK_LINENUM 0xc0 /* line number info */ | 1084 | #define TOK_PPNUM 0xcd /* preprocessor number */ |
| 1050 | #define TOK_TWODOTS 0xa8 /* C++ token ? */ | 1085 | #define TOK_PPSTR 0xce /* preprocessor string */ |
| 1051 | /* <-- */ | 1086 | #define TOK_LINENUM 0xcf /* line number info */ |
| 1052 | 1087 | ||
| 1053 | #define TOK_UMULL 0xc2 /* unsigned 32x32 -> 64 mul */ | 1088 | #define TOK_HAS_VALUE(t) (t >= TOK_CCHAR && t <= TOK_LINENUM) |
| 1054 | #define TOK_ADDC1 0xc3 /* add with carry generation */ | ||
| 1055 | #define TOK_ADDC2 0xc4 /* add with carry use */ | ||
| 1056 | #define TOK_SUBC1 0xc5 /* add with carry generation */ | ||
| 1057 | #define TOK_SUBC2 0xc6 /* add with carry use */ | ||
| 1058 | #define TOK_ARROW 0xc7 | ||
| 1059 | #define TOK_DOTS 0xc8 /* three dots */ | ||
| 1060 | #define TOK_SHR 0xc9 /* unsigned shift right */ | ||
| 1061 | #define TOK_TWOSHARPS 0xca /* ## preprocessing token */ | ||
| 1062 | #define TOK_PLCHLDR 0xcb /* placeholder token as defined in C99 */ | ||
| 1063 | #define TOK_NOSUBST 0xcc /* means following token has already been pp'd */ | ||
| 1064 | #define TOK_PPJOIN 0xcd /* A '##' in the right position to mean pasting */ | ||
| 1065 | #define TOK_CLONG 0xce /* long constant */ | ||
| 1066 | #define TOK_CULONG 0xcf /* unsigned long constant */ | ||
| 1067 | |||
| 1068 | #define TOK_SHL 0x01 /* shift left */ | ||
| 1069 | #define TOK_SAR 0x02 /* signed shift right */ | ||
| 1070 | |||
| 1071 | /* assignment operators : normal operator or 0x80 */ | ||
| 1072 | #define TOK_A_MOD 0xa5 | ||
| 1073 | #define TOK_A_AND 0xa6 | ||
| 1074 | #define TOK_A_MUL 0xaa | ||
| 1075 | #define TOK_A_ADD 0xab | ||
| 1076 | #define TOK_A_SUB 0xad | ||
| 1077 | #define TOK_A_DIV 0xaf | ||
| 1078 | #define TOK_A_XOR 0xde | ||
| 1079 | #define TOK_A_OR 0xfc | ||
| 1080 | #define TOK_A_SHL 0x81 | ||
| 1081 | #define TOK_A_SAR 0x82 | ||
| 1082 | 1089 | ||
| 1083 | #define TOK_EOF (-1) /* end of file */ | 1090 | #define TOK_EOF (-1) /* end of file */ |
| 1084 | #define TOK_LINEFEED 10 /* line feed */ | 1091 | #define TOK_LINEFEED 10 /* line feed */ |
| @@ -1346,7 +1353,6 @@ ST_FUNC Sym *label_push(Sym **ptop, int v, int flags); · 261 unmodified lines | |||
| 1346 | ST_FUNC void label_pop(Sym **ptop, Sym *slast, int keep); | 1353 | ST_FUNC void label_pop(Sym **ptop, Sym *slast, int keep); |
| 1347 | ST_FUNC void parse_define(void); | 1354 | ST_FUNC void parse_define(void); |
| 1348 | ST_FUNC void preprocess(int is_bof); | 1355 | ST_FUNC void preprocess(int is_bof); |
| 1349 | ST_FUNC void next_nomacro(void); | ||
| 1350 | ST_FUNC void next(void); | 1356 | ST_FUNC void next(void); |
| 1351 | ST_INLN void unget_tok(int last_tok); | 1357 | ST_INLN void unget_tok(int last_tok); |
| 1352 | ST_FUNC void preprocess_start(TCCState *s1, int is_asm); | 1358 | ST_FUNC void preprocess_start(TCCState *s1, int is_asm); |
| @@ -3064,7 +3064,7 @@ static int combine_types(CType *dest, SValue *op1, SValue *op2, int op) · 3063 unmodified lines | |||
| 3064 | else if (bt1 != bt2) { | 3064 | else if (bt1 != bt2) { |
| 3065 | /* accept comparison or cond-expr between pointer and integer | 3065 | /* accept comparison or cond-expr between pointer and integer |
| 3066 | with a warning */ | 3066 | with a warning */ |
| 3067 | if ((op == '?' || (op >= TOK_ULT && op <= TOK_LOR)) | 3067 | if ((op == '?' || TOK_ISCOND(op)) |
| 3068 | && (is_integer_btype(bt1) || is_integer_btype(bt2))) | 3068 | && (is_integer_btype(bt1) || is_integer_btype(bt2))) |
| 3069 | tcc_warning("pointer/integer mismatch in %s", | 3069 | tcc_warning("pointer/integer mismatch in %s", |
| 3070 | op == '?' ? "conditional expression" : "comparison"); | 3070 | op == '?' ? "conditional expression" : "comparison"); |
| @@ -3079,7 +3079,7 @@ static int combine_types(CType *dest, SValue *op1, SValue *op2, int op) · 8 unmodified lines | |||
| 3079 | int newquals, copied = 0; | 3079 | int newquals, copied = 0; |
| 3080 | if (pbt1 != VT_VOID && pbt2 != VT_VOID | 3080 | if (pbt1 != VT_VOID && pbt2 != VT_VOID |
| 3081 | && !compare_types(pt1, pt2, 1/*unqualif*/)) { | 3081 | && !compare_types(pt1, pt2, 1/*unqualif*/)) { |
| 3082 | if (op != '?' && (op < TOK_ULT || op > TOK_LOR)) | 3082 | if (op != '?' && !TOK_ISCOND(op)) |
| 3083 | ret = 0; | 3083 | ret = 0; |
| 3084 | else | 3084 | else |
| 3085 | type_incompatibility_warning(type1, type2, | 3085 | type_incompatibility_warning(type1, type2, |
| @@ -3120,7 +3120,7 @@ static int combine_types(CType *dest, SValue *op1, SValue *op2, int op) · 34 unmodified lines | |||
| 3120 | } | 3120 | } |
| 3121 | } | 3121 | } |
| 3122 | } | 3122 | } |
| 3123 | if (op >= TOK_ULT && op <= TOK_LOR) | 3123 | if (TOK_ISCOND(op)) |
| 3124 | type.t = VT_SIZE_T; | 3124 | type.t = VT_SIZE_T; |
| 3125 | } else if (bt1 == VT_STRUCT || bt2 == VT_STRUCT) { | 3125 | } else if (bt1 == VT_STRUCT || bt2 == VT_STRUCT) { |
| 3126 | if (op != '?' || !compare_types(type1, type2, 1)) | 3126 | if (op != '?' || !compare_types(type1, type2, 1)) |
| @@ -3188,7 +3188,7 @@ redo: · 61 unmodified lines | |||
| 3188 | } else if (bt1 == VT_PTR || bt2 == VT_PTR) { | 3188 | } else if (bt1 == VT_PTR || bt2 == VT_PTR) { |
| 3189 | /* at least one operand is a pointer */ | 3189 | /* at least one operand is a pointer */ |
| 3190 | /* relational op: must be both pointers */ | 3190 | /* relational op: must be both pointers */ |
| 3191 | if (op >= TOK_ULT && op <= TOK_LOR) | 3191 | if (TOK_ISCOND(op)) |
| 3192 | goto std_op; | 3192 | goto std_op; |
| 3193 | /* if both pointers, then it must be the '-' op */ | 3193 | /* if both pointers, then it must be the '-' op */ |
| 3194 | if (bt1 == VT_PTR && bt2 == VT_PTR) { | 3194 | if (bt1 == VT_PTR && bt2 == VT_PTR) { |
| @@ -3256,7 +3256,7 @@ redo: · 61 unmodified lines | |||
| 3256 | /* floats can only be used for a few operations */ | 3256 | /* floats can only be used for a few operations */ |
| 3257 | if (is_float(combtype.t) | 3257 | if (is_float(combtype.t) |
| 3258 | && op != '+' && op != '-' && op != '*' && op != '/' | 3258 | && op != '+' && op != '-' && op != '*' && op != '/' |
| 3259 | && (op < TOK_ULT || op > TOK_LOR)) | 3259 | && !TOK_ISCOND(op)) |
| 3260 | tcc_error("invalid operands for binary operation"); | 3260 | tcc_error("invalid operands for binary operation"); |
| 3261 | else if (op == TOK_SHR || op == TOK_SAR || op == TOK_SHL) { | 3261 | else if (op == TOK_SHR || op == TOK_SAR || op == TOK_SHL) { |
| 3262 | t = bt1 == VT_LLONG ? VT_LLONG : VT_INT; | 3262 | t = bt1 == VT_LLONG ? VT_LLONG : VT_INT; |
| @@ -3297,7 +3297,7 @@ redo: · 34 unmodified lines | |||
| 3297 | gen_opif(op); | 3297 | gen_opif(op); |
| 3298 | else | 3298 | else |
| 3299 | gen_opic(op); | 3299 | gen_opic(op); |
| 3300 | if (op >= TOK_ULT && op <= TOK_LOR) { | 3300 | if (TOK_ISCOND(op)) { |
| 3301 | /* relational op: the result is an int */ | 3301 | /* relational op: the result is an int */ |
| 3302 | vtop->type.t = VT_INT; | 3302 | vtop->type.t = VT_INT; |
| 3303 | } else { | 3303 | } else { |
| @@ -4065,13 +4065,8 @@ redo: · 761 unmodified lines | |||
| 4065 | tcc_warning("implicit declaration of function '%s'", | 4065 | tcc_warning("implicit declaration of function '%s'", |
| 4066 | get_tok_str(tok, &tokc)); | 4066 | get_tok_str(tok, &tokc)); |
| 4067 | s = external_global_sym(tok, &func_old_type); | 4067 | s = external_global_sym(tok, &func_old_type); |
| 4068 | } | 4068 | } else if ((s->type.t & VT_BTYPE) != VT_FUNC) |
| 4069 | else if ((s->type.t & VT_BTYPE) == VT_FUNC) { | ||
| 4070 | ad->cleanup_func = s; | ||
| 4071 | } | ||
| 4072 | else { | ||
| 4073 | tcc_error("'%s' is not declared as function", get_tok_str(tok, &tokc)); | 4069 | tcc_error("'%s' is not declared as function", get_tok_str(tok, &tokc)); |
| 4074 | } | ||
| 4075 | ad->cleanup_func = s; | 4070 | ad->cleanup_func = s; |
| 4076 | next(); | 4071 | next(); |
| 4077 | skip(')'); | 4072 | skip(')'); |
| @@ -5937,11 +5932,8 @@ special_math_val: · 1859 unmodified lines | |||
| 5937 | test_lvalue(); | 5932 | test_lvalue(); |
| 5938 | gaddrof(); | 5933 | gaddrof(); |
| 5939 | /* expect pointer on structure */ | 5934 | /* expect pointer on structure */ |
| 5940 | if ((vtop->type.t & VT_BTYPE) != VT_STRUCT) { | 5935 | if ((vtop->type.t & VT_BTYPE) != VT_STRUCT) |
| 5941 | char got[256]; | 5936 | expect("struct or union"); |
| 5942 | type_to_str(got, sizeof got, &vtop->type, NULL); | ||
| 5943 | tcc_error("expected struct or union but not '%s'", got); | ||
| 5944 | } | ||
| 5945 | if (tok == TOK_CDOUBLE) | 5937 | if (tok == TOK_CDOUBLE) |
| 5946 | expect("field name"); | 5938 | expect("field name"); |
| 5947 | next(); | 5939 | next(); |
| @@ -6487,10 +6479,7 @@ static void expr_eq(void) · 539 unmodified lines | |||
| 6487 | int t; | 6479 | int t; |
| 6488 | 6480 | ||
| 6489 | expr_cond(); | 6481 | expr_cond(); |
| 6490 | if ((t = tok) == '=' | 6482 | if ((t = tok) == '=' || TOK_ASSIGN(t)) { |
| 6491 | || (t >= TOK_A_MOD && t <= TOK_A_DIV) | ||
| 6492 | || t == TOK_A_XOR || t == TOK_A_OR | ||
| 6493 | || t == TOK_A_SHL || t == TOK_A_SAR) { | ||
| 6494 | test_lvalue(); | 6483 | test_lvalue(); |
| 6495 | next(); | 6484 | next(); |
| 6496 | if (t == '=') { | 6485 | if (t == '=') { |
| @@ -6498,7 +6487,7 @@ static void expr_eq(void) · 1 unmodified line | |||
| 6498 | } else { | 6487 | } else { |
| 6499 | vdup(); | 6488 | vdup(); |
| 6500 | expr_eq(); | 6489 | expr_eq(); |
| 6501 | gen_op(t & 0x7f); | 6490 | gen_op(TOK_ASSIGN_OP(t)); |
| 6502 | } | 6491 | } |
| 6503 | vstore(); | 6492 | vstore(); |
| 6504 | } | 6493 | } |
| @@ -92,7 +92,7 @@ static const unsigned char tok_two_chars[] = · 91 unmodified lines | |||
| 92 | 0 | 92 | 0 |
| 93 | }; | 93 | }; |
| 94 | 94 | ||
| 95 | static void next_nomacro_spc(void); | 95 | static void next_nomacro(void); |
| 96 | 96 | ||
| 97 | ST_FUNC void skip(int c) | 97 | ST_FUNC void skip(int c) |
| 98 | { | 98 | { |
| @@ -1230,7 +1230,7 @@ ST_FUNC void tok_str_add_tok(TokenString *s) · 1131 unmodified lines | |||
| 1230 | } | 1230 | } |
| 1231 | 1231 | ||
| 1232 | /* get a token from an integer array and increment pointer. */ | 1232 | /* get a token from an integer array and increment pointer. */ |
| 1233 | static inline void TOK_GET(int *t, const int **pp, CValue *cv) | 1233 | static inline void tok_get(int *t, const int **pp, CValue *cv) |
| 1234 | { | 1234 | { |
| 1235 | const int *p = *pp; | 1235 | const int *p = *pp; |
| 1236 | int n, *tab; | 1236 | int n, *tab; |
| @@ -1293,6 +1293,18 @@ static inline void TOK_GET(int *t, const int **pp, CValue *cv) · 56 unmodified lines | |||
| 1293 | *pp = p; | 1293 | *pp = p; |
| 1294 | } | 1294 | } |
| 1295 | 1295 | ||
| 1296 | #if 0 | ||
| 1297 | # define TOK_GET(t,p,c) tok_get(t,p,c) | ||
| 1298 | #else | ||
| 1299 | # define TOK_GET(t,p,c) do { \ | ||
| 1300 | int _t = **(p); \ | ||
| 1301 | if (TOK_HAS_VALUE(_t)) \ | ||
| 1302 | tok_get(t, p, c); \ | ||
| 1303 | else \ | ||
| 1304 | *(t) = _t, ++*(p); \ | ||
| 1305 | } while (0) | ||
| 1306 | #endif | ||
| 1307 | |||
| 1296 | static int macro_is_equal(const int *a, const int *b) | 1308 | static int macro_is_equal(const int *a, const int *b) |
| 1297 | { | 1309 | { |
| 1298 | CValue cv; | 1310 | CValue cv; |
| @@ -1493,7 +1505,8 @@ ST_FUNC void parse_define(void) · 194 unmodified lines | |||
| 1493 | character. */ | 1505 | character. */ |
| 1494 | parse_flags = ((parse_flags & ~PARSE_FLAG_ASM_FILE) | PARSE_FLAG_SPACES); | 1506 | parse_flags = ((parse_flags & ~PARSE_FLAG_ASM_FILE) | PARSE_FLAG_SPACES); |
| 1495 | /* '(' must be just after macro definition for MACRO_FUNC */ | 1507 | /* '(' must be just after macro definition for MACRO_FUNC */ |
| 1496 | next_nomacro_spc(); | 1508 | next_nomacro(); |
| 1509 | parse_flags &= ~PARSE_FLAG_SPACES; | ||
| 1497 | if (tok == '(') { | 1510 | if (tok == '(') { |
| 1498 | int dotid = set_idnum('.', 0); | 1511 | int dotid = set_idnum('.', 0); |
| 1499 | next_nomacro(); | 1512 | next_nomacro(); |
| @@ -1521,7 +1534,8 @@ ST_FUNC void parse_define(void) · 21 unmodified lines | |||
| 1521 | goto bad_list; | 1534 | goto bad_list; |
| 1522 | next_nomacro(); | 1535 | next_nomacro(); |
| 1523 | } | 1536 | } |
| 1524 | next_nomacro_spc(); | 1537 | parse_flags |= PARSE_FLAG_SPACES; |
| 1538 | next_nomacro(); | ||
| 1525 | t = MACRO_FUNC; | 1539 | t = MACRO_FUNC; |
| 1526 | set_idnum('.', dotid); | 1540 | set_idnum('.', dotid); |
| 1527 | } | 1541 | } |
| @@ -1550,7 +1564,7 @@ ST_FUNC void parse_define(void) · 22 unmodified lines | |||
| 1550 | } | 1564 | } |
| 1551 | tok_str_add2(&tokstr_buf, tok, &tokc); | 1565 | tok_str_add2(&tokstr_buf, tok, &tokc); |
| 1552 | skip: | 1566 | skip: |
| 1553 | next_nomacro_spc(); | 1567 | next_nomacro(); |
| 1554 | } | 1568 | } |
| 1555 | 1569 | ||
| 1556 | parse_flags = saved_parse_flags; | 1570 | parse_flags = saved_parse_flags; |
| @@ -2586,6 +2600,7 @@ static inline void next_nomacro1(void) · 1029 unmodified lines | |||
| 2586 | case '\t': | 2600 | case '\t': |
| 2587 | tok = c; | 2601 | tok = c; |
| 2588 | p++; | 2602 | p++; |
| 2603 | maybe_space: | ||
| 2589 | if (parse_flags & PARSE_FLAG_SPACES) | 2604 | if (parse_flags & PARSE_FLAG_SPACES) |
| 2590 | goto keep_tok_flags; | 2605 | goto keep_tok_flags; |
| 2591 | while (isidnum_table[*p - CH_EOF] & IS_SPC) | 2606 | while (isidnum_table[*p - CH_EOF] & IS_SPC) |
| @@ -2932,11 +2947,11 @@ maybe_newline: · 340 unmodified lines | |||
| 2932 | p = parse_comment(p); | 2947 | p = parse_comment(p); |
| 2933 | /* comments replaced by a blank */ | 2948 | /* comments replaced by a blank */ |
| 2934 | tok = ' '; | 2949 | tok = ' '; |
| 2935 | goto keep_tok_flags; | 2950 | goto maybe_space; |
| 2936 | } else if (c == '/') { | 2951 | } else if (c == '/') { |
| 2937 | p = parse_line_comment(p); | 2952 | p = parse_line_comment(p); |
| 2938 | tok = ' '; | 2953 | tok = ' '; |
| 2939 | goto keep_tok_flags; | 2954 | goto maybe_space; |
| 2940 | } else if (c == '=') { | 2955 | } else if (c == '=') { |
| 2941 | p++; | 2956 | p++; |
| 2942 | tok = TOK_A_DIV; | 2957 | tok = TOK_A_DIV; |
| @@ -2978,34 +2993,6 @@ keep_tok_flags: · 35 unmodified lines | |||
| 2978 | #endif | 2993 | #endif |
| 2979 | } | 2994 | } |
| 2980 | 2995 | ||
| 2981 | /* return next token without macro substitution. Can read input from | ||
| 2982 | macro_ptr buffer */ | ||
| 2983 | static void next_nomacro_spc(void) | ||
| 2984 | { | ||
| 2985 | if (macro_ptr) { | ||
| 2986 | redo: | ||
| 2987 | tok = *macro_ptr; | ||
| 2988 | if (tok) { | ||
| 2989 | TOK_GET(&tok, ¯o_ptr, &tokc); | ||
| 2990 | if (tok == TOK_LINENUM) { | ||
| 2991 | file->line_num = tokc.i; | ||
| 2992 | goto redo; | ||
| 2993 | } | ||
| 2994 | } | ||
| 2995 | } else { | ||
| 2996 | next_nomacro1(); | ||
| 2997 | } | ||
| 2998 | //printf("token = %s\n", get_tok_str(tok, &tokc)); | ||
| 2999 | } | ||
| 3000 | |||
| 3001 | ST_FUNC void next_nomacro(void) | ||
| 3002 | { | ||
| 3003 | do { | ||
| 3004 | next_nomacro_spc(); | ||
| 3005 | } while (tok < 256 && (isidnum_table[tok - CH_EOF] & IS_SPC)); | ||
| 3006 | } | ||
| 3007 | |||
| 3008 | |||
| 3009 | static void macro_subst( | 2996 | static void macro_subst( |
| 3010 | TokenString *tok_str, | 2997 | TokenString *tok_str, |
| 3011 | Sym **nested_list, | 2998 | Sym **nested_list, |
| @@ -3281,7 +3268,7 @@ static int next_argstream(Sym **nested_list, TokenString *ws_str) · 269 unmodified lines | |||
| 3281 | 3268 | ||
| 3282 | if (ws_str) | 3269 | if (ws_str) |
| 3283 | return t; | 3270 | return t; |
| 3284 | next_nomacro_spc(); | 3271 | next_nomacro(); |
| 3285 | return tok; | 3272 | return tok; |
| 3286 | } | 3273 | } |
| 3287 | } | 3274 | } |
| @@ -3372,7 +3359,7 @@ static int macro_subst_tok( · 84 unmodified lines | |||
| 3372 | } | 3359 | } |
| 3373 | do { | 3360 | do { |
| 3374 | next_nomacro(); /* eat '(' */ | 3361 | next_nomacro(); /* eat '(' */ |
| 3375 | } while (tok == TOK_PLCHLDR); | 3362 | } while (tok == TOK_PLCHLDR || is_space(tok)); |
| 3376 | 3363 | ||
| 3377 | /* argument macro */ | 3364 | /* argument macro */ |
| 3378 | args = NULL; | 3365 | args = NULL; |
| @@ -3533,29 +3520,59 @@ no_subst: · 154 unmodified lines | |||
| 3533 | } | 3520 | } |
| 3534 | } | 3521 | } |
| 3535 | 3522 | ||
| 3523 | /* return next token without macro substitution. Can read input from | ||
| 3524 | macro_ptr buffer */ | ||
| 3525 | static void next_nomacro(void) | ||
| 3526 | { | ||
| 3527 | int t; | ||
| 3528 | if (macro_ptr) { | ||
| 3529 | redo: | ||
| 3530 | t = *macro_ptr; | ||
| 3531 | if (TOK_HAS_VALUE(t)) { | ||
| 3532 | tok_get(&tok, ¯o_ptr, &tokc); | ||
| 3533 | if (t == TOK_LINENUM) { | ||
| 3534 | file->line_num = tokc.i; | ||
| 3535 | goto redo; | ||
| 3536 | } | ||
| 3537 | } else { | ||
| 3538 | macro_ptr++; | ||
| 3539 | if (t < TOK_IDENT) { | ||
| 3540 | if (!(parse_flags & PARSE_FLAG_SPACES) | ||
| 3541 | && (isidnum_table[t - CH_EOF] & IS_SPC)) | ||
| 3542 | goto redo; | ||
| 3543 | } | ||
| 3544 | tok = t; | ||
| 3545 | } | ||
| 3546 | } else { | ||
| 3547 | next_nomacro1(); | ||
| 3548 | } | ||
| 3549 | } | ||
| 3550 | |||
| 3536 | /* return next token with macro substitution */ | 3551 | /* return next token with macro substitution */ |
| 3537 | ST_FUNC void next(void) | 3552 | ST_FUNC void next(void) |
| 3538 | { | 3553 | { |
| 3554 | int t; | ||
| 3539 | redo: | 3555 | redo: |
| 3540 | if (parse_flags & PARSE_FLAG_SPACES) | 3556 | next_nomacro(); |
| 3541 | next_nomacro_spc(); | 3557 | t = tok; |
| 3542 | else | ||
| 3543 | next_nomacro(); | ||
| 3544 | |||
| 3545 | if (macro_ptr) { | 3558 | if (macro_ptr) { |
| 3546 | if (tok == TOK_NOSUBST || tok == TOK_PLCHLDR) { | 3559 | if (!TOK_HAS_VALUE(t)) { |
| 3547 | /* discard preprocessor markers */ | 3560 | if (t == TOK_NOSUBST || t == TOK_PLCHLDR) { |
| 3548 | goto redo; | 3561 | /* discard preprocessor markers */ |
| 3549 | } else if (tok == 0) { | 3562 | goto redo; |
| 3550 | /* end of macro or unget token string */ | 3563 | } else if (t == 0) { |
| 3551 | end_macro(); | 3564 | /* end of macro or unget token string */ |
| 3552 | goto redo; | 3565 | end_macro(); |
| 3553 | } else if (tok == '\\' && !(parse_flags & PARSE_FLAG_ACCEPT_STRAYS)) | 3566 | goto redo; |
| 3554 | tcc_error("stray '\\' in program"); | 3567 | } else if (t == '\\') { |
| 3555 | } else if (tok >= TOK_IDENT && (parse_flags & PARSE_FLAG_PREPROCESS)) { | 3568 | if (!(parse_flags & PARSE_FLAG_ACCEPT_STRAYS)) |
| 3556 | Sym *s; | 3569 | tcc_error("stray '\\' in program"); |
| 3570 | } | ||
| 3571 | return; | ||
| 3572 | } | ||
| 3573 | } else if (t >= TOK_IDENT && (parse_flags & PARSE_FLAG_PREPROCESS)) { | ||
| 3557 | /* if reading from file, try to substitute macros */ | 3574 | /* if reading from file, try to substitute macros */ |
| 3558 | s = define_find(tok); | 3575 | Sym *s = define_find(t); |
| 3559 | if (s) { | 3576 | if (s) { |
| 3560 | Sym *nested_list = NULL; | 3577 | Sym *nested_list = NULL; |
| 3561 | tokstr_buf.len = 0; | 3578 | tokstr_buf.len = 0; |
| @@ -3564,12 +3581,13 @@ ST_FUNC void next(void) · 2 unmodified lines | |||
| 3564 | begin_macro(&tokstr_buf, 0); | 3581 | begin_macro(&tokstr_buf, 0); |
| 3565 | goto redo; | 3582 | goto redo; |
| 3566 | } | 3583 | } |
| 3584 | return; | ||
| 3567 | } | 3585 | } |
| 3568 | /* convert preprocessor tokens into C tokens */ | 3586 | /* convert preprocessor tokens into C tokens */ |
| 3569 | if (tok == TOK_PPNUM) { | 3587 | if (t == TOK_PPNUM) { |
| 3570 | if (parse_flags & PARSE_FLAG_TOK_NUM) | 3588 | if (parse_flags & PARSE_FLAG_TOK_NUM) |
| 3571 | parse_number((char *)tokc.str.data); | 3589 | parse_number((char *)tokc.str.data); |
| 3572 | } else if (tok == TOK_PPSTR) { | 3590 | } else if (t == TOK_PPSTR) { |
| 3573 | if (parse_flags & PARSE_FLAG_TOK_STR) | 3591 | if (parse_flags & PARSE_FLAG_TOK_STR) |
| 3574 | parse_string((char *)tokc.str.data, tokc.str.size - 1); | 3592 | parse_string((char *)tokc.str.data, tokc.str.size - 1); |
| 3575 | } | 3593 | } |