Skip to content

Commit 9cecc09

Browse files
authored
Accept empty 'case' or 'default' labels (#564)
1 parent 7ae671d commit 9cecc09

File tree

2 files changed

+42
-0
lines changed

2 files changed

+42
-0
lines changed

pycparser/c_parser.py

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1584,6 +1584,14 @@ def p_labeled_statement_4(self, p):
15841584
""" labeled_statement : ID COLON """
15851585
p[0] = c_ast.Label(p[1], c_ast.EmptyStatement(self._token_coord(p, 1)), self._token_coord(p, 1))
15861586

1587+
def p_labeled_statement_5(self, p):
1588+
""" labeled_statement : CASE constant_expression COLON """
1589+
p[0] = c_ast.Case(p[2], [c_ast.EmptyStatement(self._token_coord(p, 2))], self._token_coord(p, 1))
1590+
1591+
def p_labeled_statement_6(self, p):
1592+
""" labeled_statement : DEFAULT COLON """
1593+
p[0] = c_ast.Default([c_ast.EmptyStatement(self._token_coord(p, 1))], self._token_coord(p, 1))
1594+
15871595
def p_selection_statement_1(self, p):
15881596
""" selection_statement : IF LPAREN expression RPAREN pragmacomp_or_statement """
15891597
p[0] = c_ast.If(p[3], p[5], None, self._token_coord(p, 1))

tests/test_c_parser.py

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2504,6 +2504,40 @@ def test_label_empty_statement(self):
25042504
self.assertIsInstance(s1_ast.ext[0].body.block_items[2], Label)
25052505
self.assertIsInstance(s1_ast.ext[0].body.block_items[2].stmt, EmptyStatement)
25062506

2507+
def test_case_empty_statement(self):
2508+
# Labels with empty statements and no semicolon should be parsed correctly
2509+
s1 = r'''
2510+
int main() {
2511+
int i = 0;
2512+
switch (i) {
2513+
case 0:
2514+
i = 1;
2515+
case 1:
2516+
}
2517+
return i;
2518+
}
2519+
'''
2520+
s2 = r'''
2521+
int main() {
2522+
int i = 0;
2523+
switch (i) {
2524+
case 0:
2525+
i = 1;
2526+
default:
2527+
}
2528+
return i;
2529+
}
2530+
'''
2531+
s1_ast : FileAST = self.parse(s1)
2532+
s2_ast : FileAST = self.parse(s2)
2533+
self.assertIsInstance(s1_ast.ext[0].body.block_items[1], Switch)
2534+
self.assertIsInstance(s1_ast.ext[0].body.block_items[1].stmt, Compound)
2535+
self.assertIsInstance(s1_ast.ext[0].body.block_items[1].stmt.block_items[0], Case)
2536+
self.assertIsInstance(s1_ast.ext[0].body.block_items[1].stmt.block_items[0].stmts[0], Assignment)
2537+
self.assertIsInstance(s1_ast.ext[0].body.block_items[1].stmt.block_items[1], Case)
2538+
self.assertIsInstance(s1_ast.ext[0].body.block_items[1].stmt.block_items[1].stmts[0], EmptyStatement)
2539+
self.assertIsInstance(s2_ast.ext[0].body.block_items[1].stmt.block_items[1].stmts[0], EmptyStatement)
2540+
25072541
if __name__ == '__main__':
25082542
#~ suite = unittest.TestLoader().loadTestsFromNames(
25092543
#~ ['test_c_parser.TestCParser_fundamentals.test_typedef'])

0 commit comments

Comments
 (0)