37
37
#define TABSIZE 8
38
38
39
39
#define MAKE_TOKEN (token_type ) token_setup(tok, token, token_type, p_start, p_end)
40
+ #define MAKE_TYPE_COMMENT_TOKEN (token_type , col_offset , end_col_offset ) (\
41
+ type_comment_token_setup(tok, token, token_type, col_offset, end_col_offset, p_start, p_end))
42
+ #define ADVANCE_LINENO () \
43
+ tok->lineno++; \
44
+ tok->col_offset = 0;
40
45
41
46
/* Forward */
42
47
static struct tok_state * tok_new (void );
@@ -73,6 +78,8 @@ tok_new(void)
73
78
tok -> pendin = 0 ;
74
79
tok -> prompt = tok -> nextprompt = NULL ;
75
80
tok -> lineno = 0 ;
81
+ tok -> starting_col_offset = -1 ;
82
+ tok -> col_offset = -1 ;
76
83
tok -> level = 0 ;
77
84
tok -> altindstack [0 ] = 0 ;
78
85
tok -> decoding_state = STATE_INIT ;
@@ -871,7 +878,7 @@ tok_underflow_string(struct tok_state *tok) {
871
878
tok -> buf = tok -> cur ;
872
879
}
873
880
tok -> line_start = tok -> cur ;
874
- tok -> lineno ++ ;
881
+ ADVANCE_LINENO () ;
875
882
tok -> inp = end ;
876
883
return 1 ;
877
884
}
@@ -930,7 +937,7 @@ tok_underflow_interactive(struct tok_state *tok) {
930
937
else if (tok -> start != NULL ) {
931
938
Py_ssize_t cur_multi_line_start = tok -> multi_line_start - tok -> buf ;
932
939
size_t size = strlen (newtok );
933
- tok -> lineno ++ ;
940
+ ADVANCE_LINENO () ;
934
941
if (!tok_reserve_buf (tok , size + 1 )) {
935
942
PyMem_Free (tok -> buf );
936
943
tok -> buf = NULL ;
@@ -943,7 +950,7 @@ tok_underflow_interactive(struct tok_state *tok) {
943
950
tok -> multi_line_start = tok -> buf + cur_multi_line_start ;
944
951
}
945
952
else {
946
- tok -> lineno ++ ;
953
+ ADVANCE_LINENO () ;
947
954
PyMem_Free (tok -> buf );
948
955
tok -> buf = newtok ;
949
956
tok -> cur = tok -> buf ;
@@ -998,7 +1005,7 @@ tok_underflow_file(struct tok_state *tok) {
998
1005
* tok -> inp = '\0' ;
999
1006
}
1000
1007
1001
- tok -> lineno ++ ;
1008
+ ADVANCE_LINENO () ;
1002
1009
if (tok -> decoding_state != STATE_NORMAL ) {
1003
1010
if (tok -> lineno > 2 ) {
1004
1011
tok -> decoding_state = STATE_NORMAL ;
@@ -1056,6 +1063,7 @@ tok_nextc(struct tok_state *tok)
1056
1063
int rc ;
1057
1064
for (;;) {
1058
1065
if (tok -> cur != tok -> inp ) {
1066
+ tok -> col_offset ++ ;
1059
1067
return Py_CHARMASK (* tok -> cur ++ ); /* Fast path */
1060
1068
}
1061
1069
if (tok -> done != E_OK ) {
@@ -1104,6 +1112,7 @@ tok_backup(struct tok_state *tok, int c)
1104
1112
if ((int )(unsigned char )* tok -> cur != c ) {
1105
1113
Py_FatalError ("tok_backup: wrong character" );
1106
1114
}
1115
+ tok -> col_offset -- ;
1107
1116
}
1108
1117
}
1109
1118
@@ -1390,21 +1399,33 @@ tok_continuation_line(struct tok_state *tok) {
1390
1399
return c ;
1391
1400
}
1392
1401
1402
+ static int
1403
+ type_comment_token_setup (struct tok_state * tok , struct token * token , int type , int col_offset ,
1404
+ int end_col_offset , const char * start , const char * end )
1405
+ {
1406
+ token -> level = tok -> level ;
1407
+ token -> lineno = token -> end_lineno = tok -> lineno ;
1408
+ token -> col_offset = col_offset ;
1409
+ token -> end_col_offset = end_col_offset ;
1410
+ token -> start = start ;
1411
+ token -> end = end ;
1412
+ return type ;
1413
+ }
1414
+
1393
1415
static int
1394
1416
token_setup (struct tok_state * tok , struct token * token , int type , const char * start , const char * end )
1395
1417
{
1396
1418
assert ((start == NULL && end == NULL ) || (start != NULL && end != NULL ));
1397
1419
token -> level = tok -> level ;
1398
1420
token -> lineno = type == STRING ? tok -> first_lineno : tok -> lineno ;
1399
1421
token -> end_lineno = tok -> lineno ;
1400
- token -> col_offset = -1 ;
1401
- token -> end_col_offset = -1 ;
1422
+ token -> col_offset = token -> end_col_offset = -1 ;
1402
1423
token -> start = start ;
1403
1424
token -> end = end ;
1425
+
1404
1426
if (start != NULL && end != NULL ) {
1405
- const char * line_start = type == STRING ? tok -> multi_line_start : tok -> line_start ;
1406
- token -> col_offset = (start >= line_start ) ? (int )(start - line_start ) : -1 ;
1407
- token -> end_col_offset = (end >= tok -> line_start ) ? (int )(end - tok -> line_start ) : -1 ;
1427
+ token -> col_offset = tok -> starting_col_offset ;
1428
+ token -> end_col_offset = tok -> col_offset ;
1408
1429
}
1409
1430
return type ;
1410
1431
}
@@ -1419,6 +1440,7 @@ tok_get(struct tok_state *tok, struct token *token)
1419
1440
const char * p_end = NULL ;
1420
1441
nextline :
1421
1442
tok -> start = NULL ;
1443
+ tok -> starting_col_offset = -1 ;
1422
1444
blankline = 0 ;
1423
1445
1424
1446
/* Get indentation level */
@@ -1518,6 +1540,7 @@ tok_get(struct tok_state *tok, struct token *token)
1518
1540
}
1519
1541
1520
1542
tok -> start = tok -> cur ;
1543
+ tok -> starting_col_offset = tok -> col_offset ;
1521
1544
1522
1545
/* Return pending indents/dedents */
1523
1546
if (tok -> pendin != 0 ) {
@@ -1565,25 +1588,30 @@ tok_get(struct tok_state *tok, struct token *token)
1565
1588
1566
1589
/* Set start of current token */
1567
1590
tok -> start = tok -> cur == NULL ? NULL : tok -> cur - 1 ;
1591
+ tok -> starting_col_offset = tok -> col_offset - 1 ;
1568
1592
1569
1593
/* Skip comment, unless it's a type comment */
1570
1594
if (c == '#' ) {
1571
1595
const char * prefix , * p , * type_start ;
1596
+ int current_starting_col_offset ;
1572
1597
1573
1598
while (c != EOF && c != '\n' ) {
1574
1599
c = tok_nextc (tok );
1575
1600
}
1576
1601
1577
1602
if (tok -> type_comments ) {
1578
1603
p = tok -> start ;
1604
+ current_starting_col_offset = tok -> starting_col_offset ;
1579
1605
prefix = type_comment_prefix ;
1580
1606
while (* prefix && p < tok -> cur ) {
1581
1607
if (* prefix == ' ' ) {
1582
1608
while (* p == ' ' || * p == '\t' ) {
1583
1609
p ++ ;
1610
+ current_starting_col_offset ++ ;
1584
1611
}
1585
1612
} else if (* prefix == * p ) {
1586
1613
p ++ ;
1614
+ current_starting_col_offset ++ ;
1587
1615
} else {
1588
1616
break ;
1589
1617
}
@@ -1594,7 +1622,9 @@ tok_get(struct tok_state *tok, struct token *token)
1594
1622
/* This is a type comment if we matched all of type_comment_prefix. */
1595
1623
if (!* prefix ) {
1596
1624
int is_type_ignore = 1 ;
1625
+ // +6 in order to skip the word 'ignore'
1597
1626
const char * ignore_end = p + 6 ;
1627
+ const int ignore_end_col_offset = current_starting_col_offset + 6 ;
1598
1628
tok_backup (tok , c ); /* don't eat the newline or EOF */
1599
1629
1600
1630
type_start = p ;
@@ -1615,11 +1645,11 @@ tok_get(struct tok_state *tok, struct token *token)
1615
1645
tok_nextc (tok );
1616
1646
tok -> atbol = 1 ;
1617
1647
}
1618
- return MAKE_TOKEN (TYPE_IGNORE );
1648
+ return MAKE_TYPE_COMMENT_TOKEN (TYPE_IGNORE , ignore_end_col_offset , tok -> col_offset );
1619
1649
} else {
1620
1650
p_start = type_start ;
1621
1651
p_end = tok -> cur ;
1622
- return MAKE_TOKEN (TYPE_COMMENT );
1652
+ return MAKE_TYPE_COMMENT_TOKEN (TYPE_COMMENT , current_starting_col_offset , tok -> col_offset );
1623
1653
}
1624
1654
}
1625
1655
}
0 commit comments