15f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# cython: auto_cpdef=True, infer_types=True, language_level=3, py2_import=True
25f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#
35f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#   Parser
45f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#
55f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
65f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# This should be done automatically
75f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)import cython
85f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cython.declare(Nodes=object, ExprNodes=object, EncodedString=object,
95f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)               BytesLiteral=object, StringEncoding=object,
105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)               FileSourceDescriptor=object, lookup_unicodechar=object,
115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)               Future=object, Options=object, error=object, warning=object,
125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)               Builtin=object, ModuleNode=object, Utils=object,
135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)               re=object, _unicode=object, _bytes=object)
145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)import re
165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)from unicodedata import lookup as lookup_unicodechar
175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)from Cython.Compiler.Scanning import PyrexScanner, FileSourceDescriptor
195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)import Nodes
205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)import ExprNodes
215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)import Builtin
225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)import StringEncoding
235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)from StringEncoding import EncodedString, BytesLiteral, _unicode, _bytes
245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)from ModuleNode import ModuleNode
255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)from Errors import error, warning
265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)from Cython import Utils
275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)import Future
285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)import Options
295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)class Ctx(object):
315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    #  Parsing context
325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    level = 'other'
335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    visibility = 'private'
345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    cdef_flag = 0
355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    typedef_flag = 0
365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    api = 0
375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    overridable = 0
385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    nogil = 0
395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    namespace = None
405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    templates = None
415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    allow_struct_enum_decorator = False
425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    def __init__(self, **kwds):
445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        self.__dict__.update(kwds)
455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    def __call__(self, **kwds):
475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        ctx = Ctx()
485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        d = ctx.__dict__
495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        d.update(self.__dict__)
505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        d.update(kwds)
515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ctx
525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_ident(s, message = "Expected an identifier"):
545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'IDENT':
555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        name = s.systring
565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return name
585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.error(message)
605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_ident_list(s):
625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    names = []
635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while s.sy == 'IDENT':
645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        names.append(s.systring)
655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy != ',':
675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            break
685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return names
705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#------------------------------------------
725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#
735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#   Expressions
745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#
755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#------------------------------------------
765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_binop_operator(s):
785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    op = s.sy
805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return op, pos
825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_binop_expr(s, ops, p_sub_expr):
845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    n1 = p_sub_expr(s)
855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while s.sy in ops:
865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        op, pos = p_binop_operator(s)
875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        n2 = p_sub_expr(s)
885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        n1 = ExprNodes.binop_node(pos, op, n1, n2)
895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if op == '/':
905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if Future.division in s.context.future_directives:
915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                n1.truedivision = True
925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            else:
935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                n1.truedivision = None # unknown
945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return n1
955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#lambdef: 'lambda' [varargslist] ':' test
975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_lambdef(s, allow_conditional=True):
995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == 'lambda'
1005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
1015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
1025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == ':':
1035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        args = []
1045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        star_arg = starstar_arg = None
1055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
1065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        args, star_arg, starstar_arg = p_varargslist(
1075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s, terminator=':', annotated=False)
1085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect(':')
1095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if allow_conditional:
1105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        expr = p_test(s)
1115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
1125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        expr = p_test_nocond(s)
1135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return ExprNodes.LambdaNode(
1145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        pos, args = args,
1155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        star_arg = star_arg, starstar_arg = starstar_arg,
1165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        result_expr = expr)
1175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#lambdef_nocond: 'lambda' [varargslist] ':' test_nocond
1195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_lambdef_nocond(s):
1215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return p_lambdef(s, allow_conditional=False)
1225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#test: or_test ['if' or_test 'else' test] | lambdef
1245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_test(s):
1265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'lambda':
1275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_lambdef(s)
1285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
1295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    expr = p_or_test(s)
1305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'if':
1315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
1325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        test = p_or_test(s)
1335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect('else')
1345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        other = p_test(s)
1355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.CondExprNode(pos, test=test, true_val=expr, false_val=other)
1365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
1375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return expr
1385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#test_nocond: or_test | lambdef_nocond
1405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_test_nocond(s):
1425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'lambda':
1435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_lambdef_nocond(s)
1445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
1455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_or_test(s)
1465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#or_test: and_test ('or' and_test)*
1485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_or_test(s):
1505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return p_rassoc_binop_expr(s, ('or',), p_and_test)
1515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_rassoc_binop_expr(s, ops, p_subexpr):
1535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    n1 = p_subexpr(s)
1545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy in ops:
1555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        pos = s.position()
1565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        op = s.sy
1575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
1585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        n2 = p_rassoc_binop_expr(s, ops, p_subexpr)
1595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        n1 = ExprNodes.binop_node(pos, op, n1, n2)
1605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return n1
1615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#and_test: not_test ('and' not_test)*
1635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_and_test(s):
1655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    #return p_binop_expr(s, ('and',), p_not_test)
1665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return p_rassoc_binop_expr(s, ('and',), p_not_test)
1675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#not_test: 'not' not_test | comparison
1695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_not_test(s):
1715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'not':
1725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        pos = s.position()
1735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
1745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.NotNode(pos, operand = p_not_test(s))
1755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
1765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_comparison(s)
1775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#comparison: expr (comp_op expr)*
1795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#comp_op: '<'|'>'|'=='|'>='|'<='|'<>'|'!='|'in'|'not' 'in'|'is'|'is' 'not'
1805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_comparison(s):
1825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    n1 = p_starred_expr(s)
1835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy in comparison_ops:
1845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        pos = s.position()
1855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        op = p_cmp_op(s)
1865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        n2 = p_starred_expr(s)
1875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        n1 = ExprNodes.PrimaryCmpNode(pos,
1885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            operator = op, operand1 = n1, operand2 = n2)
1895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy in comparison_ops:
1905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            n1.cascade = p_cascaded_cmp(s)
1915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return n1
1925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_test_or_starred_expr(s):
1945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '*':
1955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_starred_expr(s)
1965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
1975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_test(s)
1985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
1995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_starred_expr(s):
2005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
2015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '*':
2025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        starred = True
2035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
2045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
2055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        starred = False
2065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    expr = p_bit_expr(s)
2075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if starred:
2085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        expr = ExprNodes.StarredTargetNode(pos, expr)
2095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return expr
2105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_cascaded_cmp(s):
2125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
2135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    op = p_cmp_op(s)
2145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    n2 = p_starred_expr(s)
2155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    result = ExprNodes.CascadedCmpNode(pos,
2165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        operator = op, operand2 = n2)
2175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy in comparison_ops:
2185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        result.cascade = p_cascaded_cmp(s)
2195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return result
2205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_cmp_op(s):
2225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'not':
2235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
2245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect('in')
2255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        op = 'not_in'
2265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'is':
2275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
2285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == 'not':
2295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
2305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            op = 'is_not'
2315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
2325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            op = 'is'
2335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
2345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        op = s.sy
2355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
2365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if op == '<>':
2375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        op = '!='
2385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return op
2395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)comparison_ops = cython.declare(set, set([
2415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    '<', '>', '==', '>=', '<=', '<>', '!=',
2425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    'in', 'is', 'not'
2435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)]))
2445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#expr: xor_expr ('|' xor_expr)*
2465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_bit_expr(s):
2485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return p_binop_expr(s, ('|',), p_xor_expr)
2495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#xor_expr: and_expr ('^' and_expr)*
2515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_xor_expr(s):
2535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return p_binop_expr(s, ('^',), p_and_expr)
2545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#and_expr: shift_expr ('&' shift_expr)*
2565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_and_expr(s):
2585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return p_binop_expr(s, ('&',), p_shift_expr)
2595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#shift_expr: arith_expr (('<<'|'>>') arith_expr)*
2615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_shift_expr(s):
2635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return p_binop_expr(s, ('<<', '>>'), p_arith_expr)
2645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#arith_expr: term (('+'|'-') term)*
2665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_arith_expr(s):
2685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return p_binop_expr(s, ('+', '-'), p_term)
2695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#term: factor (('*'|'/'|'%') factor)*
2715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_term(s):
2735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return p_binop_expr(s, ('*', '/', '%', '//'), p_factor)
2745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#factor: ('+'|'-'|'~'|'&'|typecast|sizeof) factor | power
2765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_factor(s):
2785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # little indirection for C-ification purposes
2795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return _p_factor(s)
2805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
2815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def _p_factor(s):
2825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    sy = s.sy
2835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if sy in ('+', '-', '~'):
2845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        op = s.sy
2855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        pos = s.position()
2865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
2875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.unop_node(pos, op, p_factor(s))
2885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif not s.in_python_file:
2895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if sy == '&':
2905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            pos = s.position()
2915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
2925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            arg = p_factor(s)
2935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return ExprNodes.AmpersandNode(pos, operand = arg)
2945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif sy == "<":
2955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return p_typecast(s)
2965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif sy == 'IDENT' and s.systring == "sizeof":
2975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return p_sizeof(s)
2985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return p_power(s)
2995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
3005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_typecast(s):
3015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == "<"
3025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
3035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
3045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    base_type = p_c_base_type(s)
3055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    is_memslice = isinstance(base_type, Nodes.MemoryViewSliceTypeNode)
3065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    is_template = isinstance(base_type, Nodes.TemplatedTypeNode)
3075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    is_const = isinstance(base_type, Nodes.CConstTypeNode)
3085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if (not is_memslice and not is_template and not is_const
3095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        and base_type.name is None):
3105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.error("Unknown type")
3115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    declarator = p_c_declarator(s, empty = 1)
3125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '?':
3135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
3145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        typecheck = 1
3155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
3165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        typecheck = 0
3175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect(">")
3185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    operand = p_factor(s)
3195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if is_memslice:
3205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.CythonArrayNode(pos, base_type_node=base_type,
3215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                                         operand=operand)
3225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
3235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return ExprNodes.TypecastNode(pos,
3245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        base_type = base_type,
3255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        declarator = declarator,
3265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        operand = operand,
3275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        typecheck = typecheck)
3285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
3295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_sizeof(s):
3305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == ident "sizeof"
3315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
3325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
3335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect('(')
3345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # Here we decide if we are looking at an expression or type
3355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # If it is actually a type, but parsable as an expression,
3365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # we treat it as an expression here.
3375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if looking_at_expr(s):
3385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        operand = p_test(s)
3395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        node = ExprNodes.SizeofVarNode(pos, operand = operand)
3405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
3415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        base_type = p_c_base_type(s)
3425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        declarator = p_c_declarator(s, empty = 1)
3435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        node = ExprNodes.SizeofTypeNode(pos,
3445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            base_type = base_type, declarator = declarator)
3455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect(')')
3465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return node
3475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
3485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_yield_expression(s):
3495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == "yield"
3505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
3515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
3525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    is_yield_from = False
3535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'from':
3545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        is_yield_from = True
3555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
3565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy != ')' and s.sy not in statement_terminators:
3575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        arg = p_testlist(s)
3585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
3595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if is_yield_from:
3605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.error("'yield from' requires a source argument",
3615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    pos=pos, fatal=False)
3625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        arg = None
3635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if is_yield_from:
3645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.YieldFromExprNode(pos, arg=arg)
3655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
3665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.YieldExprNode(pos, arg=arg)
3675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
3685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_yield_statement(s):
3695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == "yield"
3705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    yield_expr = p_yield_expression(s)
3715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.ExprStatNode(yield_expr.pos, expr=yield_expr)
3725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
3735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#power: atom trailer* ('**' factor)*
3745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
3755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_power(s):
3765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.systring == 'new' and s.peek()[0] == 'IDENT':
3775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_new_expr(s)
3785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    n1 = p_atom(s)
3795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while s.sy in ('(', '[', '.'):
3805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        n1 = p_trailer(s, n1)
3815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '**':
3825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        pos = s.position()
3835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
3845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        n2 = p_factor(s)
3855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        n1 = ExprNodes.binop_node(pos, '**', n1, n2)
3865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return n1
3875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
3885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_new_expr(s):
3895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.systring == 'new'.
3905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
3915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
3925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    cppclass = p_c_base_type(s)
3935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return p_call(s, ExprNodes.NewExprNode(pos, cppclass = cppclass))
3945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
3955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#trailer: '(' [arglist] ')' | '[' subscriptlist ']' | '.' NAME
3965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
3975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_trailer(s, node1):
3985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
3995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '(':
4005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_call(s, node1)
4015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == '[':
4025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_index(s, node1)
4035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else: # s.sy == '.'
4045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
4055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        name = EncodedString( p_ident(s) )
4065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.AttributeNode(pos,
4075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            obj = node1, attribute = name)
4085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
4095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# arglist:  argument (',' argument)* [',']
4105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# argument: [test '='] test       # Really [keyword '='] test
4115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
4125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_call_parse_args(s, allow_genexp = True):
4135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == '('
4145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
4155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
4165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    positional_args = []
4175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    keyword_args = []
4185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    star_arg = None
4195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    starstar_arg = None
4205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while s.sy not in ('**', ')'):
4215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == '*':
4225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if star_arg:
4235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                s.error("only one star-arg parameter allowed",
4245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                        pos=s.position())
4255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
4265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            star_arg = p_test(s)
4275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
4285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            arg = p_test(s)
4295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if s.sy == '=':
4305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                s.next()
4315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                if not arg.is_name:
4325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    s.error("Expected an identifier before '='",
4335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                            pos=arg.pos)
4345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                encoded_name = EncodedString(arg.name)
4355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                keyword = ExprNodes.IdentifierStringNode(
4365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    arg.pos, value=encoded_name)
4375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                arg = p_test(s)
4385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                keyword_args.append((keyword, arg))
4395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            else:
4405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                if keyword_args:
4415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    s.error("Non-keyword arg following keyword arg",
4425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                            pos=arg.pos)
4435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                if star_arg:
4445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    s.error("Non-keyword arg following star-arg",
4455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                            pos=arg.pos)
4465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                positional_args.append(arg)
4475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy != ',':
4485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            break
4495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
4505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
4515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'for':
4525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if len(positional_args) == 1 and not star_arg:
4535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            positional_args = [ p_genexp(s, positional_args[0]) ]
4545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == '**':
4555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
4565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        starstar_arg = p_test(s)
4575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == ',':
4585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
4595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect(')')
4605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return positional_args, keyword_args, star_arg, starstar_arg
4615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
4625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_call_build_packed_args(pos, positional_args, keyword_args,
4635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                             star_arg, starstar_arg):
4645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    arg_tuple = None
4655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    keyword_dict = None
4665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if positional_args or not star_arg:
4675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        arg_tuple = ExprNodes.TupleNode(pos,
4685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            args = positional_args)
4695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if star_arg:
4705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        star_arg_tuple = ExprNodes.AsTupleNode(pos, arg = star_arg)
4715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if arg_tuple:
4725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            arg_tuple = ExprNodes.binop_node(pos,
4735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                operator = '+', operand1 = arg_tuple,
4745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                operand2 = star_arg_tuple)
4755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
4765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            arg_tuple = star_arg_tuple
4775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if keyword_args or starstar_arg:
4785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        keyword_args = [ExprNodes.DictItemNode(pos=key.pos, key=key, value=value)
4795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                          for key, value in keyword_args]
4805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if starstar_arg:
4815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            keyword_dict = ExprNodes.KeywordArgsNode(
4825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                pos,
4835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                starstar_arg = starstar_arg,
4845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                keyword_args = keyword_args)
4855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
4865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            keyword_dict = ExprNodes.DictNode(
4875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                pos, key_value_pairs = keyword_args)
4885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return arg_tuple, keyword_dict
4895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
4905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_call(s, function):
4915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == '('
4925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
4935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
4945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    positional_args, keyword_args, star_arg, starstar_arg = \
4955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                     p_call_parse_args(s)
4965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
4975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if not (keyword_args or star_arg or starstar_arg):
4985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.SimpleCallNode(pos,
4995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            function = function,
5005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            args = positional_args)
5015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
5025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        arg_tuple, keyword_dict = p_call_build_packed_args(
5035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            pos, positional_args, keyword_args, star_arg, starstar_arg)
5045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.GeneralCallNode(pos,
5055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            function = function,
5065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            positional_args = arg_tuple,
5075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            keyword_args = keyword_dict)
5085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
5095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#lambdef: 'lambda' [varargslist] ':' test
5105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
5115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#subscriptlist: subscript (',' subscript)* [',']
5125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
5135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_index(s, base):
5145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == '['
5155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
5165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
5175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    subscripts, is_single_value = p_subscript_list(s)
5185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if is_single_value and len(subscripts[0]) == 2:
5195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        start, stop = subscripts[0]
5205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        result = ExprNodes.SliceIndexNode(pos,
5215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            base = base, start = start, stop = stop)
5225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
5235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        indexes = make_slice_nodes(pos, subscripts)
5245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if is_single_value:
5255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            index = indexes[0]
5265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
5275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            index = ExprNodes.TupleNode(pos, args = indexes)
5285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        result = ExprNodes.IndexNode(pos,
5295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            base = base, index = index)
5305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect(']')
5315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return result
5325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
5335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_subscript_list(s):
5345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    is_single_value = True
5355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    items = [p_subscript(s)]
5365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while s.sy == ',':
5375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        is_single_value = False
5385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
5395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == ']':
5405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            break
5415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        items.append(p_subscript(s))
5425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return items, is_single_value
5435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
5445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#subscript: '.' '.' '.' | test | [test] ':' [test] [':' [test]]
5455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
5465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_subscript(s):
5475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # Parse a subscript and return a list of
5485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # 1, 2 or 3 ExprNodes, depending on how
5495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # many slice elements were encountered.
5505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
5515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    start = p_slice_element(s, (':',))
5525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy != ':':
5535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return [start]
5545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
5555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    stop = p_slice_element(s, (':', ',', ']'))
5565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy != ':':
5575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return [start, stop]
5585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
5595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    step = p_slice_element(s, (':', ',', ']'))
5605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return [start, stop, step]
5615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
5625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_slice_element(s, follow_set):
5635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # Simple expression which may be missing iff
5645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # it is followed by something in follow_set.
5655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy not in follow_set:
5665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_test(s)
5675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
5685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return None
5695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
5705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def expect_ellipsis(s):
5715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect('.')
5725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect('.')
5735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect('.')
5745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
5755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def make_slice_nodes(pos, subscripts):
5765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # Convert a list of subscripts as returned
5775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # by p_subscript_list into a list of ExprNodes,
5785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # creating SliceNodes for elements with 2 or
5795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # more components.
5805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    result = []
5815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    for subscript in subscripts:
5825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if len(subscript) == 1:
5835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            result.append(subscript[0])
5845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
5855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            result.append(make_slice_node(pos, *subscript))
5865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return result
5875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
5885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def make_slice_node(pos, start, stop = None, step = None):
5895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if not start:
5905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        start = ExprNodes.NoneNode(pos)
5915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if not stop:
5925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        stop = ExprNodes.NoneNode(pos)
5935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if not step:
5945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        step = ExprNodes.NoneNode(pos)
5955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return ExprNodes.SliceNode(pos,
5965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        start = start, stop = stop, step = step)
5975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
5985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#atom: '(' [yield_expr|testlist_comp] ')' | '[' [listmaker] ']' | '{' [dict_or_set_maker] '}' | '`' testlist '`' | NAME | NUMBER | STRING+
5995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
6005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_atom(s):
6015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
6025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    sy = s.sy
6035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if sy == '(':
6045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
6055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == ')':
6065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            result = ExprNodes.TupleNode(pos, args = [])
6075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif s.sy == 'yield':
6085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            result = p_yield_expression(s)
6095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
6105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            result = p_testlist_comp(s)
6115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect(')')
6125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return result
6135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif sy == '[':
6145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_list_maker(s)
6155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif sy == '{':
6165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_dict_or_set_maker(s)
6175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif sy == '`':
6185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_backquote_expr(s)
6195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif sy == '.':
6205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        expect_ellipsis(s)
6215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.EllipsisNode(pos)
6225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif sy == 'INT':
6235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_int_literal(s)
6245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif sy == 'FLOAT':
6255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        value = s.systring
6265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
6275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.FloatNode(pos, value = value)
6285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif sy == 'IMAG':
6295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        value = s.systring[:-1]
6305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
6315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.ImagNode(pos, value = value)
6325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif sy == 'BEGIN_STRING':
6335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        kind, bytes_value, unicode_value = p_cat_string_literal(s)
6345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if kind == 'c':
6355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return ExprNodes.CharNode(pos, value = bytes_value)
6365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif kind == 'u':
6375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return ExprNodes.UnicodeNode(pos, value = unicode_value, bytes_value = bytes_value)
6385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif kind == 'b':
6395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return ExprNodes.BytesNode(pos, value = bytes_value)
6405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
6415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return ExprNodes.StringNode(pos, value = bytes_value, unicode_value = unicode_value)
6425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif sy == 'IDENT':
6435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        name = EncodedString( s.systring )
6445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
6455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if name == "None":
6465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return ExprNodes.NoneNode(pos)
6475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif name == "True":
6485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return ExprNodes.BoolNode(pos, value=True)
6495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif name == "False":
6505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return ExprNodes.BoolNode(pos, value=False)
6515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif name == "NULL" and not s.in_python_file:
6525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return ExprNodes.NullNode(pos)
6535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
6545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return p_name(s, name)
6555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
6565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.error("Expected an identifier or literal")
6575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
6585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_int_literal(s):
6595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
6605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    value = s.systring
6615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
6625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    unsigned = ""
6635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    longness = ""
6645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while value[-1] in u"UuLl":
6655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if value[-1] in u"Ll":
6665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            longness += "L"
6675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
6685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            unsigned += "U"
6695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        value = value[:-1]
6705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # '3L' is ambiguous in Py2 but not in Py3.  '3U' and '3LL' are
6715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # illegal in Py2 Python files.  All suffixes are illegal in Py3
6725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # Python files.
6735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    is_c_literal = None
6745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if unsigned:
6755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        is_c_literal = True
6765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif longness:
6775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if longness == 'LL' or s.context.language_level >= 3:
6785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            is_c_literal = True
6795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.in_python_file:
6805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if is_c_literal:
6815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            error(pos, "illegal integer literal syntax in Python source file")
6825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        is_c_literal = False
6835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return ExprNodes.IntNode(pos,
6845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                             is_c_literal = is_c_literal,
6855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                             value = value,
6865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                             unsigned = unsigned,
6875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                             longness = longness)
6885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
6895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
6905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_name(s, name):
6915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
6925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if not s.compile_time_expr and name in s.compile_time_env:
6935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        value = s.compile_time_env.lookup_here(name)
6945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        node = wrap_compile_time_constant(pos, value)
6955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if node is not None:
6965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return node
6975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return ExprNodes.NameNode(pos, name=name)
6985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
6995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
7005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def wrap_compile_time_constant(pos, value):
7015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    rep = repr(value)
7025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if value is None:
7035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.NoneNode(pos)
7045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif value is Ellipsis:
7055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.EllipsisNode(pos)
7065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif isinstance(value, bool):
7075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.BoolNode(pos, value=value)
7085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif isinstance(value, int):
7095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.IntNode(pos, value=rep)
7105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif isinstance(value, long):
7115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.IntNode(pos, value=rep, longness="L")
7125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif isinstance(value, float):
7135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.FloatNode(pos, value=rep)
7145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif isinstance(value, _unicode):
7155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.UnicodeNode(pos, value=EncodedString(value))
7165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif isinstance(value, _bytes):
7175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.BytesNode(pos, value=BytesLiteral(value))
7185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif isinstance(value, tuple):
7195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        args = [wrap_compile_time_constant(pos, arg)
7205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                for arg in value]
7215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if None not in args:
7225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return ExprNodes.TupleNode(pos, args=args)
7235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
7245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            # error already reported
7255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return None
7265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    error(pos, "Invalid type for compile-time constant: %r (type %s)"
7275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)               % (value, value.__class__.__name__))
7285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return None
7295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
7305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
7315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_cat_string_literal(s):
7325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # A sequence of one or more adjacent string literals.
7335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # Returns (kind, bytes_value, unicode_value)
7345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # where kind in ('b', 'c', 'u', '')
7355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    kind, bytes_value, unicode_value = p_string_literal(s)
7365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if kind == 'c' or s.sy != 'BEGIN_STRING':
7375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return kind, bytes_value, unicode_value
7385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    bstrings, ustrings = [bytes_value], [unicode_value]
7395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    bytes_value = unicode_value = None
7405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while s.sy == 'BEGIN_STRING':
7415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        pos = s.position()
7425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        next_kind, next_bytes_value, next_unicode_value = p_string_literal(s)
7435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if next_kind == 'c':
7445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            error(pos, "Cannot concatenate char literal with another string or char literal")
7455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif next_kind != kind:
7465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            error(pos, "Cannot mix string literals of different types, expected %s'', got %s''" %
7475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                  (kind, next_kind))
7485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
7495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            bstrings.append(next_bytes_value)
7505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            ustrings.append(next_unicode_value)
7515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # join and rewrap the partial literals
7525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if kind in ('b', 'c', '') or kind == 'u' and None not in bstrings:
7535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        # Py3 enforced unicode literals are parsed as bytes/unicode combination
7545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        bytes_value = BytesLiteral( StringEncoding.join_bytes(bstrings) )
7555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        bytes_value.encoding = s.source_encoding
7565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if kind in ('u', ''):
7575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        unicode_value = EncodedString( u''.join([ u for u in ustrings if u is not None ]) )
7585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return kind, bytes_value, unicode_value
7595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
7605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_opt_string_literal(s, required_type='u'):
7615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'BEGIN_STRING':
7625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        kind, bytes_value, unicode_value = p_string_literal(s, required_type)
7635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if required_type == 'u':
7645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return unicode_value
7655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif required_type == 'b':
7665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return bytes_value
7675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
7685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.error("internal parser configuration error")
7695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
7705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return None
7715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
7725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def check_for_non_ascii_characters(string):
7735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    for c in string:
7745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if c >= u'\x80':
7755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return True
7765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return False
7775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
7785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_string_literal(s, kind_override=None):
7795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # A single string or char literal.  Returns (kind, bvalue, uvalue)
7805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # where kind in ('b', 'c', 'u', '').  The 'bvalue' is the source
7815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # code byte sequence of the string literal, 'uvalue' is the
7825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # decoded Unicode string.  Either of the two may be None depending
7835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # on the 'kind' of string, only unprefixed strings have both
7845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # representations.
7855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
7865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == 'BEGIN_STRING'
7875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
7885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    is_raw = False
7895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    is_python3_source = s.context.language_level >= 3
7905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    has_non_ASCII_literal_characters = False
7915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    kind = s.systring[:1].lower()
7925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if kind == 'r':
7935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        # Py3 allows both 'br' and 'rb' as prefix
7945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.systring[1:2].lower() == 'b':
7955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            kind = 'b'
7965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
7975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            kind = ''
7985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        is_raw = True
7995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif kind in 'ub':
8005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        is_raw = s.systring[1:2].lower() == 'r'
8015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif kind != 'c':
8025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        kind = ''
8035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if kind == '' and kind_override is None and Future.unicode_literals in s.context.future_directives:
8045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        chars = StringEncoding.StrLiteralBuilder(s.source_encoding)
8055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        kind = 'u'
8065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
8075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if kind_override is not None and kind_override in 'ub':
8085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            kind = kind_override
8095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if kind == 'u':
8105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            chars = StringEncoding.UnicodeLiteralBuilder()
8115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif kind == '':
8125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            chars = StringEncoding.StrLiteralBuilder(s.source_encoding)
8135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
8145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            chars = StringEncoding.BytesLiteralBuilder(s.source_encoding)
8155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
8165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while 1:
8175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
8185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        sy = s.sy
8195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        systr = s.systring
8205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        #print "p_string_literal: sy =", sy, repr(s.systring) ###
8215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if sy == 'CHARS':
8225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            chars.append(systr)
8235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if is_python3_source and not has_non_ASCII_literal_characters and check_for_non_ascii_characters(systr):
8245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                has_non_ASCII_literal_characters = True
8255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif sy == 'ESCAPE':
8265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if is_raw:
8275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                chars.append(systr)
8285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                if is_python3_source and not has_non_ASCII_literal_characters \
8295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                       and check_for_non_ascii_characters(systr):
8305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    has_non_ASCII_literal_characters = True
8315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            else:
8325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                c = systr[1]
8335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                if c in u"01234567":
8345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    chars.append_charval( int(systr[1:], 8) )
8355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                elif c in u"'\"\\":
8365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    chars.append(c)
8375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                elif c in u"abfnrtv":
8385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    chars.append(
8395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                        StringEncoding.char_from_escape_sequence(systr))
8405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                elif c == u'\n':
8415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    pass
8425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                elif c == u'x':   # \xXX
8435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    if len(systr) == 4:
8445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                        chars.append_charval( int(systr[2:], 16) )
8455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    else:
8465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                        s.error("Invalid hex escape '%s'" % systr,
8475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                                fatal=False)
8485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                elif c in u'NUu' and kind in ('u', ''):   # \uxxxx, \Uxxxxxxxx, \N{...}
8495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    chrval = -1
8505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    if c == u'N':
8515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                        try:
8525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                            chrval = ord(lookup_unicodechar(systr[3:-1]))
8535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                        except KeyError:
8545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                            s.error("Unknown Unicode character name %s" %
8555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                                    repr(systr[3:-1]).lstrip('u'))
8565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    elif len(systr) in (6,10):
8575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                        chrval = int(systr[2:], 16)
8585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                        if chrval > 1114111: # sys.maxunicode:
8595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                            s.error("Invalid unicode escape '%s'" % systr)
8605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                            chrval = -1
8615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    else:
8625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                        s.error("Invalid unicode escape '%s'" % systr,
8635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                                fatal=False)
8645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    if chrval >= 0:
8655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                        chars.append_uescape(chrval, systr)
8665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                else:
8675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    chars.append(u'\\' + systr[1:])
8685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    if is_python3_source and not has_non_ASCII_literal_characters \
8695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                           and check_for_non_ascii_characters(systr):
8705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                        has_non_ASCII_literal_characters = True
8715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif sy == 'NEWLINE':
8725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            chars.append(u'\n')
8735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif sy == 'END_STRING':
8745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            break
8755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif sy == 'EOF':
8765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.error("Unclosed string literal", pos=pos)
8775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
8785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.error("Unexpected token %r:%r in string literal" %
8795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    (sy, s.systring))
8805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
8815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if kind == 'c':
8825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        unicode_value = None
8835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        bytes_value = chars.getchar()
8845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if len(bytes_value) != 1:
8855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            error(pos, u"invalid character literal: %r" % bytes_value)
8865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
8875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        bytes_value, unicode_value = chars.getstrings()
8885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if is_python3_source and has_non_ASCII_literal_characters:
8895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            # Python 3 forbids literal non-ASCII characters in byte strings
8905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if kind != 'u':
8915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                s.error("bytes can only contain ASCII literal characters.",
8925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                        pos=pos, fatal=False)
8935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            bytes_value = None
8945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
8955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return (kind, bytes_value, unicode_value)
8965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
8975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# list_display      ::=      "[" [listmaker] "]"
8985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# listmaker     ::=     expression ( comp_for | ( "," expression )* [","] )
8995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# comp_iter     ::=     comp_for | comp_if
9005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# comp_for     ::=     "for" expression_list "in" testlist [comp_iter]
9015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# comp_if     ::=     "if" test [comp_iter]
9025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
9035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_list_maker(s):
9045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == '['
9055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
9065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
9075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == ']':
9085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect(']')
9095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.ListNode(pos, args = [])
9105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    expr = p_test(s)
9115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'for':
9125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        append = ExprNodes.ComprehensionAppendNode(pos, expr=expr)
9135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        loop = p_comp_for(s, append)
9145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect(']')
9155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.ComprehensionNode(
9165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            pos, loop=loop, append=append, type = Builtin.list_type,
9175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            # list comprehensions leak their loop variable in Py2
9185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            has_local_scope = s.context.language_level >= 3)
9195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
9205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == ',':
9215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
9225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            exprs = p_simple_expr_list(s, expr)
9235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
9245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            exprs = [expr]
9255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect(']')
9265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.ListNode(pos, args = exprs)
9275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
9285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_comp_iter(s, body):
9295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'for':
9305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_comp_for(s, body)
9315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'if':
9325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_comp_if(s, body)
9335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
9345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        # insert the 'append' operation into the loop
9355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return body
9365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
9375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_comp_for(s, body):
9385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == 'for'
9395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
9405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
9415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    kw = p_for_bounds(s, allow_testlist=False)
9425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    kw.update(else_clause = None, body = p_comp_iter(s, body))
9435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.ForStatNode(pos, **kw)
9445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
9455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_comp_if(s, body):
9465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == 'if'
9475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
9485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
9495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    test = p_test_nocond(s)
9505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.IfStatNode(pos,
9515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if_clauses = [Nodes.IfClauseNode(pos, condition = test,
9525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                                         body = p_comp_iter(s, body))],
9535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else_clause = None )
9545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
9555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#dictmaker: test ':' test (',' test ':' test)* [',']
9565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
9575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_dict_or_set_maker(s):
9585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == '{'
9595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
9605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
9615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '}':
9625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
9635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.DictNode(pos, key_value_pairs = [])
9645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    item = p_test(s)
9655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == ',' or s.sy == '}':
9665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        # set literal
9675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        values = [item]
9685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        while s.sy == ',':
9695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
9705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if s.sy == '}':
9715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                break
9725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            values.append( p_test(s) )
9735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect('}')
9745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.SetNode(pos, args=values)
9755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'for':
9765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        # set comprehension
9775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        append = ExprNodes.ComprehensionAppendNode(
9785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            item.pos, expr=item)
9795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        loop = p_comp_for(s, append)
9805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect('}')
9815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.ComprehensionNode(
9825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            pos, loop=loop, append=append, type=Builtin.set_type)
9835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == ':':
9845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        # dict literal or comprehension
9855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        key = item
9865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
9875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        value = p_test(s)
9885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == 'for':
9895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            # dict comprehension
9905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            append = ExprNodes.DictComprehensionAppendNode(
9915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                item.pos, key_expr=key, value_expr=value)
9925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            loop = p_comp_for(s, append)
9935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.expect('}')
9945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return ExprNodes.ComprehensionNode(
9955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                pos, loop=loop, append=append, type=Builtin.dict_type)
9965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
9975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            # dict literal
9985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            items = [ExprNodes.DictItemNode(key.pos, key=key, value=value)]
9995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            while s.sy == ',':
10005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                s.next()
10015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                if s.sy == '}':
10025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    break
10035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                key = p_test(s)
10045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                s.expect(':')
10055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                value = p_test(s)
10065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                items.append(
10075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    ExprNodes.DictItemNode(key.pos, key=key, value=value))
10085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.expect('}')
10095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return ExprNodes.DictNode(pos, key_value_pairs=items)
10105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
10115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        # raise an error
10125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect('}')
10135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return ExprNodes.DictNode(pos, key_value_pairs = [])
10145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
10155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# NOTE: no longer in Py3 :)
10165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_backquote_expr(s):
10175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == '`'
10185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
10195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
10205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    args = [p_test(s)]
10215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while s.sy == ',':
10225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
10235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        args.append(p_test(s))
10245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect('`')
10255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if len(args) == 1:
10265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        arg = args[0]
10275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
10285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        arg = ExprNodes.TupleNode(pos, args = args)
10295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return ExprNodes.BackquoteNode(pos, arg = arg)
10305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
10315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_simple_expr_list(s, expr=None):
10325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    exprs = expr is not None and [expr] or []
10335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while s.sy not in expr_terminators:
10345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        exprs.append( p_test(s) )
10355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy != ',':
10365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            break
10375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
10385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return exprs
10395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
10405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_test_or_starred_expr_list(s, expr=None):
10415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    exprs = expr is not None and [expr] or []
10425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while s.sy not in expr_terminators:
10435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        exprs.append( p_test_or_starred_expr(s) )
10445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy != ',':
10455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            break
10465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
10475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return exprs
10485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
10495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
10505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#testlist: test (',' test)* [',']
10515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
10525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_testlist(s):
10535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
10545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    expr = p_test(s)
10555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == ',':
10565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
10575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        exprs = p_simple_expr_list(s, expr)
10585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.TupleNode(pos, args = exprs)
10595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
10605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return expr
10615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
10625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# testlist_star_expr: (test|star_expr) ( comp_for | (',' (test|star_expr))* [','] )
10635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
10645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_testlist_star_expr(s):
10655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
10665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    expr = p_test_or_starred_expr(s)
10675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == ',':
10685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
10695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        exprs = p_test_or_starred_expr_list(s, expr)
10705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.TupleNode(pos, args = exprs)
10715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
10725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return expr
10735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
10745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# testlist_comp: (test|star_expr) ( comp_for | (',' (test|star_expr))* [','] )
10755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
10765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_testlist_comp(s):
10775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
10785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    expr = p_test_or_starred_expr(s)
10795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == ',':
10805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
10815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        exprs = p_test_or_starred_expr_list(s, expr)
10825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.TupleNode(pos, args = exprs)
10835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'for':
10845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_genexp(s, expr)
10855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
10865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return expr
10875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
10885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_genexp(s, expr):
10895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == 'for'
10905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    loop = p_comp_for(s, Nodes.ExprStatNode(
10915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        expr.pos, expr = ExprNodes.YieldExprNode(expr.pos, arg=expr)))
10925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return ExprNodes.GeneratorExpressionNode(expr.pos, loop=loop)
10935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
10945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)expr_terminators = cython.declare(set, set([
10955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    ')', ']', '}', ':', '=', 'NEWLINE']))
10965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
10975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#-------------------------------------------------------
10985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#
10995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#   Statements
11005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#
11015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#-------------------------------------------------------
11025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
11035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_global_statement(s):
11045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # assume s.sy == 'global'
11055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
11065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
11075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    names = p_ident_list(s)
11085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.GlobalNode(pos, names = names)
11095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
11105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_nonlocal_statement(s):
11115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
11125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
11135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    names = p_ident_list(s)
11145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.NonlocalNode(pos, names = names)
11155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
11165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_expression_or_assignment(s):
11175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    expr_list = [p_testlist_star_expr(s)]
11185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '=' and expr_list[0].is_starred:
11195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        # This is a common enough error to make when learning Cython to let
11205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        # it fail as early as possible and give a very clear error message.
11215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.error("a starred assignment target must be in a list or tuple"
11225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                " - maybe you meant to use an index assignment: var[0] = ...",
11235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                pos=expr_list[0].pos)
11245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while s.sy == '=':
11255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
11265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == 'yield':
11275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            expr = p_yield_expression(s)
11285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
11295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            expr = p_testlist_star_expr(s)
11305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        expr_list.append(expr)
11315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if len(expr_list) == 1:
11325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if re.match(r"([+*/\%^\&|-]|<<|>>|\*\*|//)=", s.sy):
11335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            lhs = expr_list[0]
11345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if isinstance(lhs, ExprNodes.SliceIndexNode):
11355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                # implementation requires IndexNode
11365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                lhs = ExprNodes.IndexNode(
11375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    lhs.pos,
11385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    base=lhs.base,
11395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    index=make_slice_node(lhs.pos, lhs.start, lhs.stop))
11405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            elif not isinstance(lhs, (ExprNodes.AttributeNode, ExprNodes.IndexNode, ExprNodes.NameNode) ):
11415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                error(lhs.pos, "Illegal operand for inplace operation.")
11425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            operator = s.sy[:-1]
11435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
11445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if s.sy == 'yield':
11455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                rhs = p_yield_expression(s)
11465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            else:
11475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                rhs = p_testlist(s)
11485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return Nodes.InPlaceAssignmentNode(lhs.pos, operator = operator, lhs = lhs, rhs = rhs)
11495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        expr = expr_list[0]
11505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return Nodes.ExprStatNode(expr.pos, expr=expr)
11515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
11525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    rhs = expr_list[-1]
11535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if len(expr_list) == 2:
11545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return Nodes.SingleAssignmentNode(rhs.pos,
11555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            lhs = expr_list[0], rhs = rhs)
11565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
11575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return Nodes.CascadedAssignmentNode(rhs.pos,
11585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            lhs_list = expr_list[:-1], rhs = rhs)
11595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
11605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_print_statement(s):
11615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == 'print'
11625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
11635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    ends_with_comma = 0
11645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
11655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '>>':
11665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
11675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        stream = p_test(s)
11685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == ',':
11695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
11705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            ends_with_comma = s.sy in ('NEWLINE', 'EOF')
11715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
11725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        stream = None
11735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    args = []
11745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy not in ('NEWLINE', 'EOF'):
11755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        args.append(p_test(s))
11765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        while s.sy == ',':
11775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
11785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if s.sy in ('NEWLINE', 'EOF'):
11795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                ends_with_comma = 1
11805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                break
11815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            args.append(p_test(s))
11825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    arg_tuple = ExprNodes.TupleNode(pos, args = args)
11835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.PrintStatNode(pos,
11845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        arg_tuple = arg_tuple, stream = stream,
11855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        append_newline = not ends_with_comma)
11865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
11875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_exec_statement(s):
11885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == 'exec'
11895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
11905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
11915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    code = p_bit_expr(s)
11925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if isinstance(code, ExprNodes.TupleNode):
11935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        # Py3 compatibility syntax
11945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        tuple_variant = True
11955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        args = code.args
11965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if len(args) not in (2, 3):
11975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.error("expected tuple of length 2 or 3, got length %d" % len(args),
11985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    pos=pos, fatal=False)
11995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            args = [code]
12005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
12015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        tuple_variant = False
12025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        args = [code]
12035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'in':
12045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if tuple_variant:
12055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.error("tuple variant of exec does not support additional 'in' arguments",
12065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    fatal=False)
12075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
12085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        args.append(p_test(s))
12095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == ',':
12105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
12115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            args.append(p_test(s))
12125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.ExecStatNode(pos, args=args)
12135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
12145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_del_statement(s):
12155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == 'del'
12165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
12175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
12185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # FIXME: 'exprlist' in Python
12195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    args = p_simple_expr_list(s)
12205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.DelStatNode(pos, args = args)
12215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
12225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_pass_statement(s, with_newline = 0):
12235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
12245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect('pass')
12255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if with_newline:
12265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect_newline("Expected a newline")
12275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.PassStatNode(pos)
12285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
12295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_break_statement(s):
12305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == 'break'
12315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
12325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
12335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.BreakStatNode(pos)
12345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
12355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_continue_statement(s):
12365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == 'continue'
12375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
12385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
12395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.ContinueStatNode(pos)
12405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
12415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_return_statement(s):
12425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == 'return'
12435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
12445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
12455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy not in statement_terminators:
12465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        value = p_testlist(s)
12475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
12485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        value = None
12495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.ReturnStatNode(pos, value = value)
12505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
12515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_raise_statement(s):
12525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == 'raise'
12535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
12545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
12555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    exc_type = None
12565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    exc_value = None
12575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    exc_tb = None
12585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    cause = None
12595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy not in statement_terminators:
12605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        exc_type = p_test(s)
12615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == ',':
12625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
12635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            exc_value = p_test(s)
12645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if s.sy == ',':
12655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                s.next()
12665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                exc_tb = p_test(s)
12675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif s.sy == 'from':
12685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
12695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            cause = p_test(s)
12705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if exc_type or exc_value or exc_tb:
12715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return Nodes.RaiseStatNode(pos,
12725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            exc_type = exc_type,
12735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            exc_value = exc_value,
12745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            exc_tb = exc_tb,
12755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            cause = cause)
12765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
12775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return Nodes.ReraiseStatNode(pos)
12785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
12795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_import_statement(s):
12805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy in ('import', 'cimport')
12815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
12825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    kind = s.sy
12835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
12845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    items = [p_dotted_name(s, as_allowed = 1)]
12855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while s.sy == ',':
12865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
12875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        items.append(p_dotted_name(s, as_allowed = 1))
12885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    stats = []
12895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    for pos, target_name, dotted_name, as_name in items:
12905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        dotted_name = EncodedString(dotted_name)
12915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if kind == 'cimport':
12925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            stat = Nodes.CImportStatNode(pos,
12935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                module_name = dotted_name,
12945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                as_name = as_name)
12955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
12965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if as_name and "." in dotted_name:
12975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                name_list = ExprNodes.ListNode(pos, args = [
12985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                        ExprNodes.IdentifierStringNode(pos, value = EncodedString("*"))])
12995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            else:
13005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                name_list = None
13015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            stat = Nodes.SingleAssignmentNode(pos,
13025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                lhs = ExprNodes.NameNode(pos,
13035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    name = as_name or target_name),
13045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                rhs = ExprNodes.ImportNode(pos,
13055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    module_name = ExprNodes.IdentifierStringNode(
13065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                        pos, value = dotted_name),
13075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    level = None,
13085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    name_list = name_list))
13095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        stats.append(stat)
13105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.StatListNode(pos, stats = stats)
13115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
13125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_from_import_statement(s, first_statement = 0):
13135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == 'from'
13145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
13155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
13165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '.':
13175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        # count relative import level
13185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        level = 0
13195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        while s.sy == '.':
13205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            level += 1
13215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
13225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == 'cimport':
13235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.error("Relative cimport is not supported yet")
13245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
13255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        level = None
13265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if level is not None and s.sy == 'import':
13275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        # we are dealing with "from .. import foo, bar"
13285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        dotted_name_pos, dotted_name = s.position(), ''
13295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif level is not None and s.sy == 'cimport':
13305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        # "from .. cimport"
13315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.error("Relative cimport is not supported yet")
13325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
13335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        (dotted_name_pos, _, dotted_name, _) = \
13345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            p_dotted_name(s, as_allowed = 0)
13355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy in ('import', 'cimport'):
13365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        kind = s.sy
13375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
13385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
13395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.error("Expected 'import' or 'cimport'")
13405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
13415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    is_cimport = kind == 'cimport'
13425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    is_parenthesized = False
13435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '*':
13445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        imported_names = [(s.position(), "*", None, None)]
13455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
13465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
13475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == '(':
13485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            is_parenthesized = True
13495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
13505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        imported_names = [p_imported_name(s, is_cimport)]
13515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while s.sy == ',':
13525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
13535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if is_parenthesized and s.sy == ')':
13545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            break
13555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        imported_names.append(p_imported_name(s, is_cimport))
13565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if is_parenthesized:
13575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect(')')
13585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    dotted_name = EncodedString(dotted_name)
13595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if dotted_name == '__future__':
13605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if not first_statement:
13615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.error("from __future__ imports must occur at the beginning of the file")
13625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif level is not None:
13635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.error("invalid syntax")
13645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
13655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            for (name_pos, name, as_name, kind) in imported_names:
13665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                if name == "braces":
13675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    s.error("not a chance", name_pos)
13685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    break
13695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                try:
13705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    directive = getattr(Future, name)
13715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                except AttributeError:
13725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    s.error("future feature %s is not defined" % name, name_pos)
13735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    break
13745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                s.context.future_directives.add(directive)
13755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return Nodes.PassStatNode(pos)
13765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif kind == 'cimport':
13775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return Nodes.FromCImportStatNode(pos,
13785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            module_name = dotted_name,
13795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            imported_names = imported_names)
13805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
13815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        imported_name_strings = []
13825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        items = []
13835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        for (name_pos, name, as_name, kind) in imported_names:
13845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            encoded_name = EncodedString(name)
13855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            imported_name_strings.append(
13865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                ExprNodes.IdentifierStringNode(name_pos, value = encoded_name))
13875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            items.append(
13885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                (name,
13895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                 ExprNodes.NameNode(name_pos,
13905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                                    name = as_name or name)))
13915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        import_list = ExprNodes.ListNode(
13925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            imported_names[0][0], args = imported_name_strings)
13935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        dotted_name = EncodedString(dotted_name)
13945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return Nodes.FromImportStatNode(pos,
13955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            module = ExprNodes.ImportNode(dotted_name_pos,
13965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                module_name = ExprNodes.IdentifierStringNode(pos, value = dotted_name),
13975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                level = level,
13985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                name_list = import_list),
13995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            items = items)
14005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
14015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)imported_name_kinds = cython.declare(
14025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    set, set(['class', 'struct', 'union']))
14035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
14045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_imported_name(s, is_cimport):
14055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
14065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    kind = None
14075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if is_cimport and s.systring in imported_name_kinds:
14085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        kind = s.systring
14095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
14105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    name = p_ident(s)
14115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    as_name = p_as_name(s)
14125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return (pos, name, as_name, kind)
14135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
14145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_dotted_name(s, as_allowed):
14155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
14165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    target_name = p_ident(s)
14175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    as_name = None
14185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    names = [target_name]
14195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while s.sy == '.':
14205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
14215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        names.append(p_ident(s))
14225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if as_allowed:
14235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        as_name = p_as_name(s)
14245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return (pos, target_name, u'.'.join(names), as_name)
14255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
14265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_as_name(s):
14275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'IDENT' and s.systring == 'as':
14285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
14295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_ident(s)
14305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
14315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return None
14325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
14335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_assert_statement(s):
14345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == 'assert'
14355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
14365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
14375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    cond = p_test(s)
14385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == ',':
14395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
14405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        value = p_test(s)
14415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
14425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        value = None
14435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.AssertStatNode(pos, cond = cond, value = value)
14445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
14455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)statement_terminators = cython.declare(set, set([';', 'NEWLINE', 'EOF']))
14465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
14475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_if_statement(s):
14485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == 'if'
14495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
14505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
14515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if_clauses = [p_if_clause(s)]
14525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while s.sy == 'elif':
14535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
14545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if_clauses.append(p_if_clause(s))
14555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else_clause = p_else_clause(s)
14565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.IfStatNode(pos,
14575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if_clauses = if_clauses, else_clause = else_clause)
14585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
14595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_if_clause(s):
14605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
14615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    test = p_test(s)
14625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    body = p_suite(s)
14635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.IfClauseNode(pos,
14645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        condition = test, body = body)
14655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
14665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_else_clause(s):
14675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'else':
14685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
14695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_suite(s)
14705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
14715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return None
14725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
14735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_while_statement(s):
14745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == 'while'
14755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
14765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
14775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    test = p_test(s)
14785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    body = p_suite(s)
14795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else_clause = p_else_clause(s)
14805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.WhileStatNode(pos,
14815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        condition = test, body = body,
14825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else_clause = else_clause)
14835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
14845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_for_statement(s):
14855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == 'for'
14865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
14875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
14885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    kw = p_for_bounds(s, allow_testlist=True)
14895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    body = p_suite(s)
14905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else_clause = p_else_clause(s)
14915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    kw.update(body = body, else_clause = else_clause)
14925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.ForStatNode(pos, **kw)
14935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
14945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_for_bounds(s, allow_testlist=True):
14955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    target = p_for_target(s)
14965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'in':
14975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
14985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        iterator = p_for_iterator(s, allow_testlist)
14995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return dict( target = target, iterator = iterator )
15005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif not s.in_python_file:
15015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == 'from':
15025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
15035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            bound1 = p_bit_expr(s)
15045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
15055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            # Support shorter "for a <= x < b" syntax
15065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            bound1, target = target, None
15075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        rel1 = p_for_from_relation(s)
15085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        name2_pos = s.position()
15095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        name2 = p_ident(s)
15105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        rel2_pos = s.position()
15115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        rel2 = p_for_from_relation(s)
15125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        bound2 = p_bit_expr(s)
15135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        step = p_for_from_step(s)
15145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if target is None:
15155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            target = ExprNodes.NameNode(name2_pos, name = name2)
15165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
15175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if not target.is_name:
15185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                error(target.pos,
15195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    "Target of for-from statement must be a variable name")
15205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            elif name2 != target.name:
15215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                error(name2_pos,
15225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    "Variable name in for-from range does not match target")
15235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if rel1[0] != rel2[0]:
15245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            error(rel2_pos,
15255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                "Relation directions in for-from do not match")
15265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return dict(target = target,
15275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    bound1 = bound1,
15285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    relation1 = rel1,
15295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    relation2 = rel2,
15305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    bound2 = bound2,
15315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    step = step,
15325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    )
15335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
15345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect('in')
15355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return {}
15365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
15375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_for_from_relation(s):
15385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy in inequality_relations:
15395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        op = s.sy
15405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
15415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return op
15425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
15435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.error("Expected one of '<', '<=', '>' '>='")
15445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
15455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_for_from_step(s):
15465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'IDENT' and s.systring == 'by':
15475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
15485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        step = p_bit_expr(s)
15495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return step
15505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
15515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return None
15525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
15535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)inequality_relations = cython.declare(set, set(['<', '<=', '>', '>=']))
15545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
15555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_target(s, terminator):
15565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
15575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    expr = p_starred_expr(s)
15585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == ',':
15595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
15605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        exprs = [expr]
15615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        while s.sy != terminator:
15625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            exprs.append(p_starred_expr(s))
15635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if s.sy != ',':
15645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                break
15655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
15665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ExprNodes.TupleNode(pos, args = exprs)
15675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
15685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return expr
15695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
15705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_for_target(s):
15715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return p_target(s, 'in')
15725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
15735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_for_iterator(s, allow_testlist=True):
15745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
15755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if allow_testlist:
15765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        expr = p_testlist(s)
15775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
15785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        expr = p_or_test(s)
15795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return ExprNodes.IteratorNode(pos, sequence = expr)
15805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
15815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_try_statement(s):
15825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == 'try'
15835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
15845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
15855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    body = p_suite(s)
15865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    except_clauses = []
15875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else_clause = None
15885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy in ('except', 'else'):
15895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        while s.sy == 'except':
15905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            except_clauses.append(p_except_clause(s))
15915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == 'else':
15925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
15935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            else_clause = p_suite(s)
15945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        body = Nodes.TryExceptStatNode(pos,
15955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            body = body, except_clauses = except_clauses,
15965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            else_clause = else_clause)
15975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy != 'finally':
15985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return body
15995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        # try-except-finally is equivalent to nested try-except/try-finally
16005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'finally':
16015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
16025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        finally_clause = p_suite(s)
16035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return Nodes.TryFinallyStatNode(pos,
16045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            body = body, finally_clause = finally_clause)
16055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
16065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.error("Expected 'except' or 'finally'")
16075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
16085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_except_clause(s):
16095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == 'except'
16105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
16115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
16125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    exc_type = None
16135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    exc_value = None
16145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    is_except_as = False
16155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy != ':':
16165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        exc_type = p_test(s)
16175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        # normalise into list of single exception tests
16185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if isinstance(exc_type, ExprNodes.TupleNode):
16195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            exc_type = exc_type.args
16205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
16215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            exc_type = [exc_type]
16225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == ',' or (s.sy == 'IDENT' and s.systring == 'as'
16235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                           and s.context.language_level == 2):
16245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
16255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            exc_value = p_test(s)
16265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif s.sy == 'IDENT' and s.systring == 'as':
16275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            # Py3 syntax requires a name here
16285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
16295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            pos2 = s.position()
16305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            name = p_ident(s)
16315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            exc_value = ExprNodes.NameNode(pos2, name = name)
16325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            is_except_as = True
16335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    body = p_suite(s)
16345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.ExceptClauseNode(pos,
16355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        pattern = exc_type, target = exc_value,
16365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        body = body, is_except_as=is_except_as)
16375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
16385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_include_statement(s, ctx):
16395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
16405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next() # 'include'
16415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    unicode_include_file_name = p_string_literal(s, 'u')[2]
16425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect_newline("Syntax error in include statement")
16435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.compile_time_eval:
16445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        include_file_name = unicode_include_file_name
16455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        include_file_path = s.context.find_include_file(include_file_name, pos)
16465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if include_file_path:
16475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.included_files.append(include_file_name)
16485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            f = Utils.open_source_file(include_file_path, mode="rU")
16495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            source_desc = FileSourceDescriptor(include_file_path)
16505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s2 = PyrexScanner(f, source_desc, s, source_encoding=f.encoding, parse_comments=s.parse_comments)
16515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            try:
16525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                tree = p_statement_list(s2, ctx)
16535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            finally:
16545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                f.close()
16555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return tree
16565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
16575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return None
16585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
16595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return Nodes.PassStatNode(pos)
16605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
16615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_with_statement(s):
16625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next() # 'with'
16635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.systring == 'template' and not s.in_python_file:
16645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        node = p_with_template(s)
16655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
16665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        node = p_with_items(s)
16675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return node
16685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
16695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_with_items(s):
16705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
16715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if not s.in_python_file and s.sy == 'IDENT' and s.systring in ('nogil', 'gil'):
16725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        state = s.systring
16735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
16745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == ',':
16755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
16765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            body = p_with_items(s)
16775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
16785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            body = p_suite(s)
16795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return Nodes.GILStatNode(pos, state = state, body = body)
16805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
16815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        manager = p_test(s)
16825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        target = None
16835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == 'IDENT' and s.systring == 'as':
16845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
16855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            target = p_starred_expr(s)
16865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == ',':
16875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
16885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            body = p_with_items(s)
16895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
16905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            body = p_suite(s)
16915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.WithStatNode(pos, manager = manager,
16925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                              target = target, body = body)
16935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
16945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_with_template(s):
16955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
16965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    templates = []
16975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
16985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect('[')
16995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    templates.append(s.systring)
17005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
17015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while s.systring == ',':
17025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
17035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        templates.append(s.systring)
17045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
17055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect(']')
17065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == ':':
17075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
17085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect_newline("Syntax error in template function declaration")
17095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect_indent()
17105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        body_ctx = Ctx()
17115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        body_ctx.templates = templates
17125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        func_or_var = p_c_func_or_var_declaration(s, pos, body_ctx)
17135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect_dedent()
17145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return func_or_var
17155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
17165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        error(pos, "Syntax error in template function declaration")
17175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
17185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_simple_statement(s, first_statement = 0):
17195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    #print "p_simple_statement:", s.sy, s.systring ###
17205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'global':
17215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        node = p_global_statement(s)
17225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'nonlocal':
17235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        node = p_nonlocal_statement(s)
17245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'print':
17255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        node = p_print_statement(s)
17265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'exec':
17275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        node = p_exec_statement(s)
17285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'del':
17295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        node = p_del_statement(s)
17305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'break':
17315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        node = p_break_statement(s)
17325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'continue':
17335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        node = p_continue_statement(s)
17345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'return':
17355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        node = p_return_statement(s)
17365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'raise':
17375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        node = p_raise_statement(s)
17385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy in ('import', 'cimport'):
17395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        node = p_import_statement(s)
17405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'from':
17415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        node = p_from_import_statement(s, first_statement = first_statement)
17425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'yield':
17435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        node = p_yield_statement(s)
17445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'assert':
17455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        node = p_assert_statement(s)
17465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'pass':
17475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        node = p_pass_statement(s)
17485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
17495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        node = p_expression_or_assignment(s)
17505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return node
17515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
17525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_simple_statement_list(s, ctx, first_statement = 0):
17535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # Parse a series of simple statements on one line
17545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # separated by semicolons.
17555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    stat = p_simple_statement(s, first_statement = first_statement)
17565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = stat.pos
17575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    stats = []
17585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if not isinstance(stat, Nodes.PassStatNode):
17595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        stats.append(stat)
17605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while s.sy == ';':
17615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        #print "p_simple_statement_list: maybe more to follow" ###
17625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
17635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy in ('NEWLINE', 'EOF'):
17645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            break
17655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        stat = p_simple_statement(s, first_statement = first_statement)
17665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if isinstance(stat, Nodes.PassStatNode):
17675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            continue
17685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        stats.append(stat)
17695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        first_statement = False
17705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
17715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if not stats:
17725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        stat = Nodes.PassStatNode(pos)
17735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif len(stats) == 1:
17745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        stat = stats[0]
17755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
17765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        stat = Nodes.StatListNode(pos, stats = stats)
17775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect_newline("Syntax error in simple statement list")
17785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return stat
17795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
17805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_compile_time_expr(s):
17815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    old = s.compile_time_expr
17825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.compile_time_expr = 1
17835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    expr = p_testlist(s)
17845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.compile_time_expr = old
17855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return expr
17865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
17875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_DEF_statement(s):
17885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
17895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    denv = s.compile_time_env
17905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next() # 'DEF'
17915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    name = p_ident(s)
17925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect('=')
17935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    expr = p_compile_time_expr(s)
17945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    value = expr.compile_time_value(denv)
17955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    #print "p_DEF_statement: %s = %r" % (name, value) ###
17965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    denv.declare(name, value)
17975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect_newline()
17985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.PassStatNode(pos)
17995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
18005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_IF_statement(s, ctx):
18015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
18025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    saved_eval = s.compile_time_eval
18035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    current_eval = saved_eval
18045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    denv = s.compile_time_env
18055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    result = None
18065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while 1:
18075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next() # 'IF' or 'ELIF'
18085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        expr = p_compile_time_expr(s)
18095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.compile_time_eval = current_eval and bool(expr.compile_time_value(denv))
18105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        body = p_suite(s, ctx)
18115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.compile_time_eval:
18125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            result = body
18135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            current_eval = 0
18145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy != 'ELIF':
18155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            break
18165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'ELSE':
18175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
18185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.compile_time_eval = current_eval
18195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        body = p_suite(s, ctx)
18205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if current_eval:
18215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            result = body
18225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if not result:
18235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        result = Nodes.PassStatNode(pos)
18245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.compile_time_eval = saved_eval
18255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return result
18265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
18275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_statement(s, ctx, first_statement = 0):
18285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    cdef_flag = ctx.cdef_flag
18295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    decorators = None
18305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'ctypedef':
18315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if ctx.level not in ('module', 'module_pxd'):
18325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.error("ctypedef statement not allowed here")
18335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        #if ctx.api:
18345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        #    error(s.position(), "'api' not allowed with 'ctypedef'")
18355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_ctypedef_statement(s, ctx)
18365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'DEF':
18375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_DEF_statement(s)
18385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'IF':
18395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_IF_statement(s, ctx)
18405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'DECORATOR':
18415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if ctx.level not in ('module', 'class', 'c_class', 'function', 'property', 'module_pxd', 'c_class_pxd', 'other'):
18425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.error('decorator not allowed here')
18435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.level = ctx.level
18445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        decorators = p_decorators(s)
18455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        bad_toks =  'def', 'cdef', 'cpdef', 'class'
18465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if not ctx.allow_struct_enum_decorator and s.sy not in bad_toks:
18475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.error("Decorators can only be followed by functions or classes")
18485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'pass' and cdef_flag:
18495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        # empty cdef block
18505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_pass_statement(s, with_newline = 1)
18515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
18525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    overridable = 0
18535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'cdef':
18545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        cdef_flag = 1
18555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
18565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'cpdef':
18575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        cdef_flag = 1
18585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        overridable = 1
18595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
18605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if cdef_flag:
18615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if ctx.level not in ('module', 'module_pxd', 'function', 'c_class', 'c_class_pxd'):
18625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.error('cdef statement not allowed here')
18635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.level = ctx.level
18645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        node = p_cdef_statement(s, ctx(overridable = overridable))
18655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if decorators is not None:
18665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            tup = Nodes.CFuncDefNode, Nodes.CVarDefNode, Nodes.CClassDefNode
18675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if ctx.allow_struct_enum_decorator:
18685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                tup += Nodes.CStructOrUnionDefNode, Nodes.CEnumDefNode
18695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if not isinstance(node, tup):
18705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                s.error("Decorators can only be followed by functions or classes")
18715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            node.decorators = decorators
18725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return node
18735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
18745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if ctx.api:
18755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.error("'api' not allowed with this statement", fatal=False)
18765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif s.sy == 'def':
18775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            # def statements aren't allowed in pxd files, except
18785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            # as part of a cdef class
18795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if ('pxd' in ctx.level) and (ctx.level != 'c_class_pxd'):
18805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                s.error('def statement not allowed here')
18815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.level = ctx.level
18825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return p_def_statement(s, decorators)
18835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif s.sy == 'class':
18845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if ctx.level not in ('module', 'function', 'class', 'other'):
18855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                s.error("class definition not allowed here")
18865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return p_class_statement(s, decorators)
18875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif s.sy == 'include':
18885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if ctx.level not in ('module', 'module_pxd'):
18895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                s.error("include statement not allowed here")
18905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return p_include_statement(s, ctx)
18915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif ctx.level == 'c_class' and s.sy == 'IDENT' and s.systring == 'property':
18925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return p_property_decl(s)
18935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif s.sy == 'pass' and ctx.level != 'property':
18945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return p_pass_statement(s, with_newline=True)
18955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
18965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if ctx.level in ('c_class_pxd', 'property'):
18975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                node = p_ignorable_statement(s)
18985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                if node is not None:
18995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    return node
19005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                s.error("Executable statement not allowed here")
19015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if s.sy == 'if':
19025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                return p_if_statement(s)
19035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            elif s.sy == 'while':
19045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                return p_while_statement(s)
19055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            elif s.sy == 'for':
19065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                return p_for_statement(s)
19075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            elif s.sy == 'try':
19085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                return p_try_statement(s)
19095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            elif s.sy == 'with':
19105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                return p_with_statement(s)
19115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            else:
19125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                return p_simple_statement_list(
19135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    s, ctx, first_statement = first_statement)
19145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
19155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_statement_list(s, ctx, first_statement = 0):
19165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # Parse a series of statements separated by newlines.
19175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
19185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    stats = []
19195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while s.sy not in ('DEDENT', 'EOF'):
19205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        stat = p_statement(s, ctx, first_statement = first_statement)
19215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if isinstance(stat, Nodes.PassStatNode):
19225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            continue
19235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        stats.append(stat)
19245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        first_statement = False
19255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if not stats:
19265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return Nodes.PassStatNode(pos)
19275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif len(stats) == 1:
19285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return stats[0]
19295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
19305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return Nodes.StatListNode(pos, stats = stats)
19315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
19325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
19335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_suite(s, ctx=Ctx()):
19345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return p_suite_with_docstring(s, ctx, with_doc_only=False)[1]
19355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
19365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
19375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_suite_with_docstring(s, ctx, with_doc_only=False):
19385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect(':')
19395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    doc = None
19405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'NEWLINE':
19415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
19425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect_indent()
19435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if with_doc_only:
19445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            doc = p_doc_string(s)
19455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        body = p_statement_list(s, ctx)
19465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect_dedent()
19475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
19485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if ctx.api:
19495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.error("'api' not allowed with this statement", fatal=False)
19505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if ctx.level in ('module', 'class', 'function', 'other'):
19515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            body = p_simple_statement_list(s, ctx)
19525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
19535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            body = p_pass_statement(s)
19545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.expect_newline("Syntax error in declarations")
19555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if not with_doc_only:
19565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        doc, body = _extract_docstring(body)
19575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return doc, body
19585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
19595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
19605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_positional_and_keyword_args(s, end_sy_set, templates = None):
19615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    """
19625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    Parses positional and keyword arguments. end_sy_set
19635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    should contain any s.sy that terminate the argument list.
19645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    Argument expansion (* and **) are not allowed.
19655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
19665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    Returns: (positional_args, keyword_args)
19675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    """
19685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    positional_args = []
19695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    keyword_args = []
19705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos_idx = 0
19715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
19725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while s.sy not in end_sy_set:
19735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == '*' or s.sy == '**':
19745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.error('Argument expansion not allowed here.', fatal=False)
19755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
19765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        parsed_type = False
19775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == 'IDENT' and s.peek()[0] == '=':
19785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            ident = s.systring
19795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next() # s.sy is '='
19805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
19815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if looking_at_expr(s):
19825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                arg = p_test(s)
19835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            else:
19845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                base_type = p_c_base_type(s, templates = templates)
19855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                declarator = p_c_declarator(s, empty = 1)
19865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                arg = Nodes.CComplexBaseTypeNode(base_type.pos,
19875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    base_type = base_type, declarator = declarator)
19885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                parsed_type = True
19895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            keyword_node = ExprNodes.IdentifierStringNode(
19905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                arg.pos, value = EncodedString(ident))
19915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            keyword_args.append((keyword_node, arg))
19925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            was_keyword = True
19935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
19945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
19955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if looking_at_expr(s):
19965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                arg = p_test(s)
19975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            else:
19985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                base_type = p_c_base_type(s, templates = templates)
19995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                declarator = p_c_declarator(s, empty = 1)
20005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                arg = Nodes.CComplexBaseTypeNode(base_type.pos,
20015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    base_type = base_type, declarator = declarator)
20025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                parsed_type = True
20035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            positional_args.append(arg)
20045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            pos_idx += 1
20055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if len(keyword_args) > 0:
20065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                s.error("Non-keyword arg following keyword arg",
20075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                        pos=arg.pos)
20085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
20095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy != ',':
20105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if s.sy not in end_sy_set:
20115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                if parsed_type:
20125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    s.error("Unmatched %s" % " or ".join(end_sy_set))
20135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            break
20145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
20155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return positional_args, keyword_args
20165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
20175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_c_base_type(s, self_flag = 0, nonempty = 0, templates = None):
20185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # If self_flag is true, this is the base type for the
20195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # self argument of a C method of an extension type.
20205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '(':
20215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_c_complex_base_type(s, templates = templates)
20225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
20235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_c_simple_base_type(s, self_flag, nonempty = nonempty, templates = templates)
20245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
20255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_calling_convention(s):
20265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'IDENT' and s.systring in calling_convention_words:
20275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        result = s.systring
20285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
20295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return result
20305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
20315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return ""
20325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
20335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)calling_convention_words = cython.declare(
20345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    set, set(["__stdcall", "__cdecl", "__fastcall"]))
20355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
20365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_c_complex_base_type(s, templates = None):
20375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == '('
20385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
20395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
20405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    base_type = p_c_base_type(s, templates = templates)
20415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    declarator = p_c_declarator(s, empty = 1)
20425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect(')')
20435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    type_node = Nodes.CComplexBaseTypeNode(pos,
20445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            base_type = base_type, declarator = declarator)
20455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '[':
20465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if is_memoryviewslice_access(s):
20475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            type_node = p_memoryviewslice_access(s, type_node)
20485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
20495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            type_node = p_buffer_or_template(s, type_node, templates)
20505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return type_node
20515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
20525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
20535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_c_simple_base_type(s, self_flag, nonempty, templates = None):
20545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    #print "p_c_simple_base_type: self_flag =", self_flag, nonempty
20555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    is_basic = 0
20565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    signed = 1
20575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    longness = 0
20585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    complex = 0
20595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    module_path = []
20605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
20615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if not s.sy == 'IDENT':
20625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        error(pos, "Expected an identifier, found '%s'" % s.sy)
20635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.systring == 'const':
20645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
20655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        base_type = p_c_base_type(s,
20665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            self_flag = self_flag, nonempty = nonempty, templates = templates)
20675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return Nodes.CConstTypeNode(pos, base_type = base_type)
20685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if looking_at_base_type(s):
20695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        #print "p_c_simple_base_type: looking_at_base_type at", s.position()
20705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        is_basic = 1
20715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == 'IDENT' and s.systring in special_basic_c_types:
20725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            signed, longness = special_basic_c_types[s.systring]
20735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            name = s.systring
20745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
20755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
20765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            signed, longness = p_sign_and_longness(s)
20775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if s.sy == 'IDENT' and s.systring in basic_c_type_names:
20785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                name = s.systring
20795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                s.next()
20805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            else:
20815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                name = 'int'  # long [int], short [int], long [int] complex, etc.
20825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == 'IDENT' and s.systring == 'complex':
20835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            complex = 1
20845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
20855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif looking_at_dotted_name(s):
20865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        #print "p_c_simple_base_type: looking_at_type_name at", s.position()
20875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        name = s.systring
20885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
20895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        while s.sy == '.':
20905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            module_path.append(name)
20915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
20925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            name = p_ident(s)
20935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
20945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        name = s.systring
20955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
20965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if nonempty and s.sy != 'IDENT':
20975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            # Make sure this is not a declaration of a variable or function.
20985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if s.sy == '(':
20995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                s.next()
21005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                if (s.sy == '*' or s.sy == '**' or s.sy == '&'
21015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                        or (s.sy == 'IDENT' and s.systring in calling_convention_words)):
21025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    s.put_back('(', '(')
21035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                else:
21045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    s.put_back('(', '(')
21055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    s.put_back('IDENT', name)
21065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    name = None
21075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            elif s.sy not in ('*', '**', '[', '&'):
21085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                s.put_back('IDENT', name)
21095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                name = None
21105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
21115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    type_node = Nodes.CSimpleBaseTypeNode(pos,
21125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        name = name, module_path = module_path,
21135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        is_basic_c_type = is_basic, signed = signed,
21145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        complex = complex, longness = longness,
21155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        is_self_arg = self_flag, templates = templates)
21165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
21175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    #    declarations here.
21185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '[':
21195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if is_memoryviewslice_access(s):
21205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            type_node = p_memoryviewslice_access(s, type_node)
21215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
21225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            type_node = p_buffer_or_template(s, type_node, templates)
21235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
21245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '.':
21255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
21265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        name = p_ident(s)
21275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        type_node = Nodes.CNestedBaseTypeNode(pos, base_type = type_node, name = name)
21285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
21295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return type_node
21305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
21315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_buffer_or_template(s, base_type_node, templates):
21325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == '['
21335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
21345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
21355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # Note that buffer_positional_options_count=1, so the only positional argument is dtype.
21365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # For templated types, all parameters are types.
21375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    positional_args, keyword_args = (
21385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        p_positional_and_keyword_args(s, (']',), templates)
21395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    )
21405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect(']')
21415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
21425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '[':
21435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        base_type_node = p_buffer_or_template(s, base_type_node, templates)
21445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
21455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    keyword_dict = ExprNodes.DictNode(pos,
21465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        key_value_pairs = [
21475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            ExprNodes.DictItemNode(pos=key.pos, key=key, value=value)
21485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            for key, value in keyword_args
21495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        ])
21505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    result = Nodes.TemplatedTypeNode(pos,
21515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        positional_args = positional_args,
21525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        keyword_args = keyword_dict,
21535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        base_type_node = base_type_node)
21545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return result
21555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
21565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_bracketed_base_type(s, base_type_node, nonempty, empty):
21575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == '['
21585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if empty and not nonempty:
21595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        # sizeof-like thing.  Only anonymous C arrays allowed (int[SIZE]).
21605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return base_type_node
21615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif not empty and nonempty:
21625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        # declaration of either memoryview slice or buffer.
21635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if is_memoryviewslice_access(s):
21645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return p_memoryviewslice_access(s, base_type_node)
21655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
21665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return p_buffer_or_template(s, base_type_node, None)
21675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            # return p_buffer_access(s, base_type_node)
21685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif not empty and not nonempty:
21695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        # only anonymous C arrays and memoryview slice arrays here.  We
21705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        # disallow buffer declarations for now, due to ambiguity with anonymous
21715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        # C arrays.
21725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if is_memoryviewslice_access(s):
21735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return p_memoryviewslice_access(s, base_type_node)
21745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
21755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return base_type_node
21765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
21775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def is_memoryviewslice_access(s):
21785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == '['
21795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # a memoryview slice declaration is distinguishable from a buffer access
21805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # declaration by the first entry in the bracketed list.  The buffer will
21815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # not have an unnested colon in the first entry; the memoryview slice will.
21825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    saved = [(s.sy, s.systring)]
21835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
21845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    retval = False
21855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.systring == ':':
21865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        retval = True
21875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'INT':
21885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        saved.append((s.sy, s.systring))
21895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
21905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == ':':
21915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            retval = True
21925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
21935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    for sv in saved[::-1]:
21945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.put_back(*sv)
21955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
21965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return retval
21975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
21985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_memoryviewslice_access(s, base_type_node):
21995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == '['
22005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
22015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
22025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    subscripts, _ = p_subscript_list(s)
22035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # make sure each entry in subscripts is a slice
22045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    for subscript in subscripts:
22055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if len(subscript) < 2:
22065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.error("An axis specification in memoryview declaration does not have a ':'.")
22075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect(']')
22085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    indexes = make_slice_nodes(pos, subscripts)
22095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    result = Nodes.MemoryViewSliceTypeNode(pos,
22105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            base_type_node = base_type_node,
22115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            axes = indexes)
22125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return result
22135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
22145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def looking_at_name(s):
22155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return s.sy == 'IDENT' and not s.systring in calling_convention_words
22165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
22175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def looking_at_expr(s):
22185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.systring in base_type_start_words:
22195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return False
22205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'IDENT':
22215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        is_type = False
22225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        name = s.systring
22235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        dotted_path = []
22245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
22255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
22265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        while s.sy == '.':
22275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
22285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            dotted_path.append(s.systring)
22295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.expect('IDENT')
22305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
22315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        saved = s.sy, s.systring
22325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == 'IDENT':
22335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            is_type = True
22345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif s.sy == '*' or s.sy == '**':
22355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
22365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            is_type = s.sy in (')', ']')
22375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.put_back(*saved)
22385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif s.sy == '(':
22395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
22405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            is_type = s.sy == '*'
22415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.put_back(*saved)
22425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif s.sy == '[':
22435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
22445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            is_type = s.sy == ']'
22455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.put_back(*saved)
22465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
22475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        dotted_path.reverse()
22485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        for p in dotted_path:
22495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.put_back('IDENT', p)
22505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.put_back('.', '.')
22515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
22525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.put_back('IDENT', name)
22535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return not is_type and saved[0]
22545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
22555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return True
22565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
22575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def looking_at_base_type(s):
22585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    #print "looking_at_base_type?", s.sy, s.systring, s.position()
22595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return s.sy == 'IDENT' and s.systring in base_type_start_words
22605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
22615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def looking_at_dotted_name(s):
22625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'IDENT':
22635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        name = s.systring
22645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
22655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        result = s.sy == '.'
22665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.put_back('IDENT', name)
22675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return result
22685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
22695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return 0
22705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
22715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def looking_at_call(s):
22725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    "See if we're looking at a.b.c("
22735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # Don't mess up the original position, so save and restore it.
22745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # Unfortunately there's no good way to handle this, as a subsequent call
22755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # to next() will not advance the position until it reads a new token.
22765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    position = s.start_line, s.start_col
22775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    result = looking_at_expr(s) == u'('
22785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if not result:
22795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.start_line, s.start_col = position
22805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return result
22815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
22825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)basic_c_type_names = cython.declare(
22835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    set, set(["void", "char", "int", "float", "double", "bint"]))
22845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
22855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)special_basic_c_types = cython.declare(dict, {
22865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # name : (signed, longness)
22875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    "Py_UNICODE" : (0, 0),
22885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    "Py_UCS4"    : (0, 0),
22895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    "Py_ssize_t" : (2, 0),
22905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    "ssize_t"    : (2, 0),
22915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    "size_t"     : (0, 0),
22925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    "ptrdiff_t"  : (2, 0),
22935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)})
22945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
22955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)sign_and_longness_words = cython.declare(
22965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    set, set(["short", "long", "signed", "unsigned"]))
22975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
22985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)base_type_start_words = cython.declare(
22995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    set,
23005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    basic_c_type_names
23015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    | sign_and_longness_words
23025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    | set(special_basic_c_types))
23035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
23045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)struct_enum_union = cython.declare(
23055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    set, set(["struct", "union", "enum", "packed"]))
23065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
23075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_sign_and_longness(s):
23085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    signed = 1
23095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    longness = 0
23105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while s.sy == 'IDENT' and s.systring in sign_and_longness_words:
23115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.systring == 'unsigned':
23125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            signed = 0
23135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif s.systring == 'signed':
23145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            signed = 2
23155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif s.systring == 'short':
23165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            longness = -1
23175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif s.systring == 'long':
23185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            longness += 1
23195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
23205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return signed, longness
23215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
23225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_opt_cname(s):
23235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    literal = p_opt_string_literal(s, 'u')
23245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if literal is not None:
23255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        cname = EncodedString(literal)
23265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        cname.encoding = s.source_encoding
23275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
23285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        cname = None
23295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return cname
23305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
23315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_c_declarator(s, ctx = Ctx(), empty = 0, is_type = 0, cmethod_flag = 0,
23325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                   assignable = 0, nonempty = 0,
23335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                   calling_convention_allowed = 0):
23345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # If empty is true, the declarator must be empty. If nonempty is true,
23355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # the declarator must be nonempty. Otherwise we don't care.
23365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # If cmethod_flag is true, then if this declarator declares
23375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # a function, it's a C method of an extension type.
23385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
23395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '(':
23405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
23415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == ')' or looking_at_name(s):
23425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            base = Nodes.CNameDeclaratorNode(pos, name = EncodedString(u""), cname = None)
23435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            result = p_c_func_declarator(s, pos, ctx, base, cmethod_flag)
23445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
23455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            result = p_c_declarator(s, ctx, empty = empty, is_type = is_type,
23465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                                    cmethod_flag = cmethod_flag,
23475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                                    nonempty = nonempty,
23485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                                    calling_convention_allowed = 1)
23495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.expect(')')
23505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
23515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        result = p_c_simple_declarator(s, ctx, empty, is_type, cmethod_flag,
23525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                                       assignable, nonempty)
23535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if not calling_convention_allowed and result.calling_convention and s.sy != '(':
23545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        error(s.position(), "%s on something that is not a function"
23555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            % result.calling_convention)
23565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while s.sy in ('[', '('):
23575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        pos = s.position()
23585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == '[':
23595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            result = p_c_array_declarator(s, result)
23605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else: # sy == '('
23615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
23625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            result = p_c_func_declarator(s, pos, ctx, result, cmethod_flag)
23635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        cmethod_flag = 0
23645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return result
23655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
23665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_c_array_declarator(s, base):
23675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
23685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next() # '['
23695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy != ']':
23705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        dim = p_testlist(s)
23715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
23725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        dim = None
23735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect(']')
23745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.CArrayDeclaratorNode(pos, base = base, dimension = dim)
23755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
23765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_c_func_declarator(s, pos, ctx, base, cmethod_flag):
23775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    #  Opening paren has already been skipped
23785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    args = p_c_arg_list(s, ctx, cmethod_flag = cmethod_flag,
23795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                        nonempty_declarators = 0)
23805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    ellipsis = p_optional_ellipsis(s)
23815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect(')')
23825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    nogil = p_nogil(s)
23835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    exc_val, exc_check = p_exception_value_clause(s)
23845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    with_gil = p_with_gil(s)
23855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.CFuncDeclaratorNode(pos,
23865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        base = base, args = args, has_varargs = ellipsis,
23875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        exception_value = exc_val, exception_check = exc_check,
23885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        nogil = nogil or ctx.nogil or with_gil, with_gil = with_gil)
23895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
23905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)supported_overloaded_operators = cython.declare(set, set([
23915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    '+', '-', '*', '/', '%',
23925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    '++', '--', '~', '|', '&', '^', '<<', '>>', ',',
23935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    '==', '!=', '>=', '>', '<=', '<',
23945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    '[]', '()', '!',
23955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)]))
23965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
23975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_c_simple_declarator(s, ctx, empty, is_type, cmethod_flag,
23985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                          assignable, nonempty):
23995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
24005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    calling_convention = p_calling_convention(s)
24015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '*':
24025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
24035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.systring == 'const':
24045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            const_pos = s.position()
24055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
24065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            const_base = p_c_declarator(s, ctx, empty = empty,
24075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                                       is_type = is_type,
24085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                                       cmethod_flag = cmethod_flag,
24095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                                       assignable = assignable,
24105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                                       nonempty = nonempty)
24115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            base = Nodes.CConstDeclaratorNode(const_pos, base = const_base)
24125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
24135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            base = p_c_declarator(s, ctx, empty = empty, is_type = is_type,
24145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                                  cmethod_flag = cmethod_flag,
24155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                                  assignable = assignable, nonempty = nonempty)
24165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        result = Nodes.CPtrDeclaratorNode(pos,
24175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            base = base)
24185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == '**': # scanner returns this as a single token
24195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
24205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        base = p_c_declarator(s, ctx, empty = empty, is_type = is_type,
24215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                              cmethod_flag = cmethod_flag,
24225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                              assignable = assignable, nonempty = nonempty)
24235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        result = Nodes.CPtrDeclaratorNode(pos,
24245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            base = Nodes.CPtrDeclaratorNode(pos,
24255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                base = base))
24265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == '&':
24275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
24285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        base = p_c_declarator(s, ctx, empty = empty, is_type = is_type,
24295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                              cmethod_flag = cmethod_flag,
24305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                              assignable = assignable, nonempty = nonempty)
24315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        result = Nodes.CReferenceDeclaratorNode(pos, base = base)
24325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
24335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        rhs = None
24345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == 'IDENT':
24355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            name = EncodedString(s.systring)
24365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if empty:
24375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                error(s.position(), "Declarator should be empty")
24385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
24395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            cname = p_opt_cname(s)
24405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if name != 'operator' and s.sy == '=' and assignable:
24415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                s.next()
24425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                rhs = p_test(s)
24435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
24445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if nonempty:
24455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                error(s.position(), "Empty declarator")
24465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            name = ""
24475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            cname = None
24485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if cname is None and ctx.namespace is not None and nonempty:
24495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            cname = ctx.namespace + "::" + name
24505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if name == 'operator' and ctx.visibility == 'extern' and nonempty:
24515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            op = s.sy
24525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if [1 for c in op if c in '+-*/<=>!%&|([^~,']:
24535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                s.next()
24545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                # Handle diphthong operators.
24555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                if op == '(':
24565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    s.expect(')')
24575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    op = '()'
24585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                elif op == '[':
24595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    s.expect(']')
24605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    op = '[]'
24615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                elif op in ('-', '+', '|', '&') and s.sy == op:
24625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    op *= 2       # ++, --, ...
24635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    s.next()
24645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                elif s.sy == '=':
24655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    op += s.sy    # +=, -=, ...
24665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    s.next()
24675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                if op not in supported_overloaded_operators:
24685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    s.error("Overloading operator '%s' not yet supported." % op,
24695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                            fatal=False)
24705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                name += op
24715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        result = Nodes.CNameDeclaratorNode(pos,
24725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            name = name, cname = cname, default = rhs)
24735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    result.calling_convention = calling_convention
24745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return result
24755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
24765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_nogil(s):
24775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'IDENT' and s.systring == 'nogil':
24785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
24795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return 1
24805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
24815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return 0
24825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
24835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_with_gil(s):
24845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'with':
24855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
24865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect_keyword('gil')
24875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return 1
24885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
24895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return 0
24905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
24915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_exception_value_clause(s):
24925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    exc_val = None
24935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    exc_check = 0
24945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'except':
24955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
24965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == '*':
24975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            exc_check = 1
24985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
24995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif s.sy == '+':
25005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            exc_check = '+'
25015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
25025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if s.sy == 'IDENT':
25035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                name = s.systring
25045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                s.next()
25055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                exc_val = p_name(s, name)
25065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
25075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if s.sy == '?':
25085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                exc_check = 1
25095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                s.next()
25105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            exc_val = p_test(s)
25115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return exc_val, exc_check
25125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
25135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)c_arg_list_terminators = cython.declare(set, set(['*', '**', '.', ')']))
25145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
25155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_c_arg_list(s, ctx = Ctx(), in_pyfunc = 0, cmethod_flag = 0,
25165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                 nonempty_declarators = 0, kw_only = 0, annotated = 1):
25175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    #  Comma-separated list of C argument declarations, possibly empty.
25185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    #  May have a trailing comma.
25195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    args = []
25205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    is_self_arg = cmethod_flag
25215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while s.sy not in c_arg_list_terminators:
25225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        args.append(p_c_arg_decl(s, ctx, in_pyfunc, is_self_arg,
25235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            nonempty = nonempty_declarators, kw_only = kw_only,
25245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            annotated = annotated))
25255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy != ',':
25265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            break
25275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
25285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        is_self_arg = 0
25295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return args
25305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
25315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_optional_ellipsis(s):
25325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '.':
25335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        expect_ellipsis(s)
25345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return 1
25355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
25365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return 0
25375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
25385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_c_arg_decl(s, ctx, in_pyfunc, cmethod_flag = 0, nonempty = 0,
25395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                 kw_only = 0, annotated = 1):
25405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
25415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    not_none = or_none = 0
25425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    default = None
25435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    annotation = None
25445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.in_python_file:
25455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        # empty type declaration
25465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        base_type = Nodes.CSimpleBaseTypeNode(pos,
25475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            name = None, module_path = [],
25485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            is_basic_c_type = 0, signed = 0,
25495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            complex = 0, longness = 0,
25505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            is_self_arg = cmethod_flag, templates = None)
25515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
25525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        base_type = p_c_base_type(s, cmethod_flag, nonempty = nonempty)
25535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    declarator = p_c_declarator(s, ctx, nonempty = nonempty)
25545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy in ('not', 'or') and not s.in_python_file:
25555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        kind = s.sy
25565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
25575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == 'IDENT' and s.systring == 'None':
25585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
25595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
25605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.error("Expected 'None'")
25615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if not in_pyfunc:
25625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            error(pos, "'%s None' only allowed in Python functions" % kind)
25635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        or_none = kind == 'or'
25645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        not_none = kind == 'not'
25655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if annotated and s.sy == ':':
25665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
25675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        annotation = p_test(s)
25685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '=':
25695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
25705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if 'pxd' in ctx.level:
25715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if s.sy not in ['*', '?']:
25725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                error(pos, "default values cannot be specified in pxd files, use ? or *")
25735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            default = ExprNodes.BoolNode(1)
25745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
25755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
25765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            default = p_test(s)
25775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.CArgDeclNode(pos,
25785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        base_type = base_type,
25795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        declarator = declarator,
25805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        not_none = not_none,
25815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        or_none = or_none,
25825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        default = default,
25835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        annotation = annotation,
25845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        kw_only = kw_only)
25855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
25865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_api(s):
25875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'IDENT' and s.systring == 'api':
25885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
25895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return 1
25905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
25915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return 0
25925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
25935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_cdef_statement(s, ctx):
25945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
25955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    ctx.visibility = p_visibility(s, ctx.visibility)
25965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    ctx.api = ctx.api or p_api(s)
25975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if ctx.api:
25985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if ctx.visibility not in ('private', 'public'):
25995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            error(pos, "Cannot combine 'api' with '%s'" % ctx.visibility)
26005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if (ctx.visibility == 'extern') and s.sy == 'from':
26015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_cdef_extern_block(s, pos, ctx)
26025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'import':
26035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
26045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_cdef_extern_block(s, pos, ctx)
26055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif p_nogil(s):
26065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        ctx.nogil = 1
26075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if ctx.overridable:
26085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            error(pos, "cdef blocks cannot be declared cpdef")
26095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_cdef_block(s, ctx)
26105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == ':':
26115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if ctx.overridable:
26125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            error(pos, "cdef blocks cannot be declared cpdef")
26135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_cdef_block(s, ctx)
26145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'class':
26155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if ctx.level not in ('module', 'module_pxd'):
26165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            error(pos, "Extension type definition not allowed here")
26175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if ctx.overridable:
26185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            error(pos, "Extension types cannot be declared cpdef")
26195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_c_class_definition(s, pos, ctx)
26205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'IDENT' and s.systring == 'cppclass':
26215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_cpp_class_definition(s, pos, ctx)
26225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'IDENT' and s.systring in struct_enum_union:
26235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if ctx.level not in ('module', 'module_pxd'):
26245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            error(pos, "C struct/union/enum definition not allowed here")
26255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if ctx.overridable:
26265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            error(pos, "C struct/union/enum cannot be declared cpdef")
26275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_struct_enum(s, pos, ctx)
26285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'IDENT' and s.systring == 'fused':
26295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_fused_definition(s, pos, ctx)
26305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
26315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_c_func_or_var_declaration(s, pos, ctx)
26325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
26335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_cdef_block(s, ctx):
26345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return p_suite(s, ctx(cdef_flag = 1))
26355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
26365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_cdef_extern_block(s, pos, ctx):
26375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if ctx.overridable:
26385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        error(pos, "cdef extern blocks cannot be declared cpdef")
26395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    include_file = None
26405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect('from')
26415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '*':
26425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
26435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
26445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        include_file = p_string_literal(s, 'u')[2]
26455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    ctx = ctx(cdef_flag = 1, visibility = 'extern')
26465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.systring == "namespace":
26475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
26485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        ctx.namespace = p_string_literal(s, 'u')[2]
26495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if p_nogil(s):
26505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        ctx.nogil = 1
26515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    body = p_suite(s, ctx)
26525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.CDefExternNode(pos,
26535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        include_file = include_file,
26545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        body = body,
26555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        namespace = ctx.namespace)
26565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
26575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_c_enum_definition(s, pos, ctx):
26585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == ident 'enum'
26595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
26605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'IDENT':
26615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        name = s.systring
26625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
26635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        cname = p_opt_cname(s)
26645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if cname is None and ctx.namespace is not None:
26655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            cname = ctx.namespace + "::" + name
26665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
26675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        name = None
26685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        cname = None
26695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    items = None
26705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect(':')
26715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    items = []
26725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy != 'NEWLINE':
26735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        p_c_enum_line(s, ctx, items)
26745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
26755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next() # 'NEWLINE'
26765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect_indent()
26775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        while s.sy not in ('DEDENT', 'EOF'):
26785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            p_c_enum_line(s, ctx, items)
26795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect_dedent()
26805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.CEnumDefNode(
26815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        pos, name = name, cname = cname, items = items,
26825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        typedef_flag = ctx.typedef_flag, visibility = ctx.visibility,
26835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        api = ctx.api, in_pxd = ctx.level == 'module_pxd')
26845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
26855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_c_enum_line(s, ctx, items):
26865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy != 'pass':
26875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        p_c_enum_item(s, ctx, items)
26885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        while s.sy == ',':
26895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
26905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if s.sy in ('NEWLINE', 'EOF'):
26915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                break
26925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            p_c_enum_item(s, ctx, items)
26935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
26945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
26955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect_newline("Syntax error in enum item list")
26965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
26975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_c_enum_item(s, ctx, items):
26985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
26995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    name = p_ident(s)
27005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    cname = p_opt_cname(s)
27015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if cname is None and ctx.namespace is not None:
27025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        cname = ctx.namespace + "::" + name
27035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    value = None
27045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '=':
27055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
27065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        value = p_test(s)
27075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    items.append(Nodes.CEnumDefItemNode(pos,
27085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        name = name, cname = cname, value = value))
27095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
27105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_c_struct_or_union_definition(s, pos, ctx):
27115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    packed = False
27125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.systring == 'packed':
27135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        packed = True
27145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
27155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy != 'IDENT' or s.systring != 'struct':
27165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.expected('struct')
27175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == ident 'struct' or 'union'
27185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    kind = s.systring
27195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
27205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    name = p_ident(s)
27215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    cname = p_opt_cname(s)
27225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if cname is None and ctx.namespace is not None:
27235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        cname = ctx.namespace + "::" + name
27245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    attributes = None
27255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == ':':
27265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
27275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect('NEWLINE')
27285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect_indent()
27295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        attributes = []
27305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        body_ctx = Ctx()
27315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        while s.sy != 'DEDENT':
27325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if s.sy != 'pass':
27335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                attributes.append(
27345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    p_c_func_or_var_declaration(s, s.position(), body_ctx))
27355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            else:
27365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                s.next()
27375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                s.expect_newline("Expected a newline")
27385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect_dedent()
27395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
27405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect_newline("Syntax error in struct or union definition")
27415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.CStructOrUnionDefNode(pos,
27425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        name = name, cname = cname, kind = kind, attributes = attributes,
27435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        typedef_flag = ctx.typedef_flag, visibility = ctx.visibility,
27445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        api = ctx.api, in_pxd = ctx.level == 'module_pxd', packed = packed)
27455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
27465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_fused_definition(s, pos, ctx):
27475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    """
27485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    c(type)def fused my_fused_type:
27495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        ...
27505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    """
27515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.systring == 'fused'
27525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
27535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if ctx.level not in ('module', 'module_pxd'):
27545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        error(pos, "Fused type definition not allowed here")
27555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
27565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
27575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    name = p_ident(s)
27585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
27595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect(":")
27605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect_newline()
27615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect_indent()
27625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
27635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    types = []
27645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while s.sy != 'DEDENT':
27655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy != 'pass':
27665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            #types.append(p_c_declarator(s))
27675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            types.append(p_c_base_type(s)) #, nonempty=1))
27685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
27695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
27705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
27715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect_newline()
27725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
27735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect_dedent()
27745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
27755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if not types:
27765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        error(pos, "Need at least one type")
27775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
27785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.FusedTypeNode(pos, name=name, types=types)
27795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
27805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_struct_enum(s, pos, ctx):
27815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.systring == 'enum':
27825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_c_enum_definition(s, pos, ctx)
27835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
27845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_c_struct_or_union_definition(s, pos, ctx)
27855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
27865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_visibility(s, prev_visibility):
27875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
27885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    visibility = prev_visibility
27895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'IDENT' and s.systring in ('extern', 'public', 'readonly'):
27905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        visibility = s.systring
27915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if prev_visibility != 'private' and visibility != prev_visibility:
27925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.error("Conflicting visibility options '%s' and '%s'"
27935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                % (prev_visibility, visibility), fatal=False)
27945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
27955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return visibility
27965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
27975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_c_modifiers(s):
27985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'IDENT' and s.systring in ('inline',):
27995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        modifier = s.systring
28005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
28015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return [modifier] + p_c_modifiers(s)
28025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return []
28035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
28045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_c_func_or_var_declaration(s, pos, ctx):
28055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    cmethod_flag = ctx.level in ('c_class', 'c_class_pxd')
28065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    modifiers = p_c_modifiers(s)
28075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    base_type = p_c_base_type(s, nonempty = 1, templates = ctx.templates)
28085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    declarator = p_c_declarator(s, ctx, cmethod_flag = cmethod_flag,
28095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                                assignable = 1, nonempty = 1)
28105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    declarator.overridable = ctx.overridable
28115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'IDENT' and s.systring == 'const' and ctx.level == 'cpp_class':
28125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
28135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        is_const_method = 1
28145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
28155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        is_const_method = 0
28165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == ':':
28175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if ctx.level not in ('module', 'c_class', 'module_pxd', 'c_class_pxd', 'cpp_class') and not ctx.templates:
28185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.error("C function definition not allowed here")
28195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        doc, suite = p_suite_with_docstring(s, Ctx(level='function'))
28205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        result = Nodes.CFuncDefNode(pos,
28215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            visibility = ctx.visibility,
28225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            base_type = base_type,
28235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            declarator = declarator,
28245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            body = suite,
28255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            doc = doc,
28265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            modifiers = modifiers,
28275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            api = ctx.api,
28285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            overridable = ctx.overridable,
28295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            is_const_method = is_const_method)
28305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
28315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        #if api:
28325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        #    s.error("'api' not allowed with variable declaration")
28335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if is_const_method:
28345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            declarator.is_const_method = is_const_method
28355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        declarators = [declarator]
28365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        while s.sy == ',':
28375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
28385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if s.sy == 'NEWLINE':
28395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                break
28405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            declarator = p_c_declarator(s, ctx, cmethod_flag = cmethod_flag,
28415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                                        assignable = 1, nonempty = 1)
28425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            declarators.append(declarator)
28435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        doc_line = s.start_line + 1
28445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect_newline("Syntax error in C variable declaration")
28455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if ctx.level in ('c_class', 'c_class_pxd') and s.start_line == doc_line:
28465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            doc = p_doc_string(s)
28475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
28485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            doc = None
28495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        result = Nodes.CVarDefNode(pos,
28505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            visibility = ctx.visibility,
28515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            base_type = base_type,
28525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            declarators = declarators,
28535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            in_pxd = ctx.level in ('module_pxd', 'c_class_pxd'),
28545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            doc = doc,
28555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            api = ctx.api,
28565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            modifiers = modifiers,
28575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            overridable = ctx.overridable)
28585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return result
28595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
28605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_ctypedef_statement(s, ctx):
28615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == 'ctypedef'
28625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
28635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
28645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    visibility = p_visibility(s, ctx.visibility)
28655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    api = p_api(s)
28665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    ctx = ctx(typedef_flag = 1, visibility = visibility)
28675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if api:
28685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        ctx.api = 1
28695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'class':
28705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_c_class_definition(s, pos, ctx)
28715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'IDENT' and s.systring in struct_enum_union:
28725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_struct_enum(s, pos, ctx)
28735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif s.sy == 'IDENT' and s.systring == 'fused':
28745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return p_fused_definition(s, pos, ctx)
28755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
28765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        base_type = p_c_base_type(s, nonempty = 1)
28775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        declarator = p_c_declarator(s, ctx, is_type = 1, nonempty = 1)
28785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect_newline("Syntax error in ctypedef statement")
28795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return Nodes.CTypeDefNode(
28805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            pos, base_type = base_type,
28815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            declarator = declarator,
28825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            visibility = visibility, api = api,
28835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            in_pxd = ctx.level == 'module_pxd')
28845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
28855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_decorators(s):
28865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    decorators = []
28875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while s.sy == 'DECORATOR':
28885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        pos = s.position()
28895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
28905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        decstring = p_dotted_name(s, as_allowed=0)[2]
28915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        names = decstring.split('.')
28925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        decorator = ExprNodes.NameNode(pos, name=EncodedString(names[0]))
28935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        for name in names[1:]:
28945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            decorator = ExprNodes.AttributeNode(pos,
28955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                                           attribute=EncodedString(name),
28965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                                           obj=decorator)
28975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == '(':
28985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            decorator = p_call(s, decorator)
28995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        decorators.append(Nodes.DecoratorNode(pos, decorator=decorator))
29005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect_newline("Expected a newline after decorator")
29015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return decorators
29025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
29035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_def_statement(s, decorators=None):
29045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == 'def'
29055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
29065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
29075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    name = EncodedString( p_ident(s) )
29085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect('(')
29095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    args, star_arg, starstar_arg = p_varargslist(s, terminator=')')
29105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect(')')
29115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if p_nogil(s):
29125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        error(pos, "Python function cannot be declared nogil")
29135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return_type_annotation = None
29145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '->':
29155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
29165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return_type_annotation = p_test(s)
29175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    doc, body = p_suite_with_docstring(s, Ctx(level='function'))
29185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.DefNode(pos, name = name, args = args,
29195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        star_arg = star_arg, starstar_arg = starstar_arg,
29205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        doc = doc, body = body, decorators = decorators,
29215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return_type_annotation = return_type_annotation)
29225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
29235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_varargslist(s, terminator=')', annotated=1):
29245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    args = p_c_arg_list(s, in_pyfunc = 1, nonempty_declarators = 1,
29255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                        annotated = annotated)
29265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    star_arg = None
29275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    starstar_arg = None
29285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '*':
29295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
29305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == 'IDENT':
29315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            star_arg = p_py_arg_decl(s, annotated=annotated)
29325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == ',':
29335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
29345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            args.extend(p_c_arg_list(s, in_pyfunc = 1,
29355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                nonempty_declarators = 1, kw_only = 1, annotated = annotated))
29365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif s.sy != terminator:
29375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.error("Syntax error in Python function argument list")
29385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '**':
29395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
29405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        starstar_arg = p_py_arg_decl(s, annotated=annotated)
29415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return (args, star_arg, starstar_arg)
29425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
29435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_py_arg_decl(s, annotated = 1):
29445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
29455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    name = p_ident(s)
29465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    annotation = None
29475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if annotated and s.sy == ':':
29485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
29495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        annotation = p_test(s)
29505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.PyArgDeclNode(pos, name = name, annotation = annotation)
29515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
29525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_class_statement(s, decorators):
29535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == 'class'
29545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
29555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
29565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    class_name = EncodedString( p_ident(s) )
29575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    class_name.encoding = s.source_encoding
29585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    arg_tuple = None
29595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    keyword_dict = None
29605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    starstar_arg = None
29615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '(':
29625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        positional_args, keyword_args, star_arg, starstar_arg = \
29635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                            p_call_parse_args(s, allow_genexp = False)
29645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        arg_tuple, keyword_dict = p_call_build_packed_args(
29655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            pos, positional_args, keyword_args, star_arg, None)
29665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if arg_tuple is None:
29675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        # XXX: empty arg_tuple
29685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        arg_tuple = ExprNodes.TupleNode(pos, args=[])
29695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    doc, body = p_suite_with_docstring(s, Ctx(level='class'))
29705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.PyClassDefNode(
29715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        pos, name=class_name,
29725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        bases=arg_tuple,
29735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        keyword_args=keyword_dict,
29745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        starstar_arg=starstar_arg,
29755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        doc=doc, body=body, decorators=decorators,
29765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        force_py3_semantics=s.context.language_level >= 3)
29775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
29785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_c_class_definition(s, pos,  ctx):
29795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == 'class'
29805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
29815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    module_path = []
29825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    class_name = p_ident(s)
29835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while s.sy == '.':
29845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
29855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        module_path.append(class_name)
29865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        class_name = p_ident(s)
29875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if module_path and ctx.visibility != 'extern':
29885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        error(pos, "Qualified class name only allowed for 'extern' C class")
29895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if module_path and s.sy == 'IDENT' and s.systring == 'as':
29905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
29915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        as_name = p_ident(s)
29925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
29935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        as_name = class_name
29945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    objstruct_name = None
29955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    typeobj_name = None
29965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    base_class_module = None
29975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    base_class_name = None
29985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '(':
29995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
30005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        base_class_path = [p_ident(s)]
30015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        while s.sy == '.':
30025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
30035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            base_class_path.append(p_ident(s))
30045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy == ',':
30055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.error("C class may only have one base class", fatal=False)
30065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect(')')
30075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        base_class_module = ".".join(base_class_path[:-1])
30085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        base_class_name = base_class_path[-1]
30095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '[':
30105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if ctx.visibility not in ('public', 'extern') and not ctx.api:
30115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            error(s.position(), "Name options only allowed for 'public', 'api', or 'extern' C class")
30125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        objstruct_name, typeobj_name = p_c_class_options(s)
30135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == ':':
30145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if ctx.level == 'module_pxd':
30155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            body_level = 'c_class_pxd'
30165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        else:
30175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            body_level = 'c_class'
30185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        doc, body = p_suite_with_docstring(s, Ctx(level=body_level))
30195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
30205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect_newline("Syntax error in C class definition")
30215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        doc = None
30225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        body = None
30235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if ctx.visibility == 'extern':
30245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if not module_path:
30255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            error(pos, "Module name required for 'extern' C class")
30265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if typeobj_name:
30275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            error(pos, "Type object name specification not allowed for 'extern' C class")
30285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif ctx.visibility == 'public':
30295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if not objstruct_name:
30305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            error(pos, "Object struct name specification required for 'public' C class")
30315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if not typeobj_name:
30325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            error(pos, "Type object name specification required for 'public' C class")
30335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif ctx.visibility == 'private':
30345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if ctx.api:
30355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if not objstruct_name:
30365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                error(pos, "Object struct name specification required for 'api' C class")
30375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if not typeobj_name:
30385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                error(pos, "Type object name specification required for 'api' C class")
30395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
30405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        error(pos, "Invalid class visibility '%s'" % ctx.visibility)
30415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.CClassDefNode(pos,
30425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        visibility = ctx.visibility,
30435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        typedef_flag = ctx.typedef_flag,
30445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        api = ctx.api,
30455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        module_name = ".".join(module_path),
30465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        class_name = class_name,
30475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        as_name = as_name,
30485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        base_class_module = base_class_module,
30495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        base_class_name = base_class_name,
30505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        objstruct_name = objstruct_name,
30515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        typeobj_name = typeobj_name,
30525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        in_pxd = ctx.level == 'module_pxd',
30535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        doc = doc,
30545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        body = body)
30555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
30565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_c_class_options(s):
30575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    objstruct_name = None
30585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    typeobj_name = None
30595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect('[')
30605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while 1:
30615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy != 'IDENT':
30625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            break
30635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.systring == 'object':
30645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
30655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            objstruct_name = p_ident(s)
30665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif s.systring == 'type':
30675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
30685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            typeobj_name = p_ident(s)
30695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy != ',':
30705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            break
30715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
30725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.expect(']', "Expected 'object' or 'type'")
30735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return objstruct_name, typeobj_name
30745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
30755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
30765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_property_decl(s):
30775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
30785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()  # 'property'
30795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    name = p_ident(s)
30805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    doc, body = p_suite_with_docstring(
30815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s, Ctx(level='property'), with_doc_only=True)
30825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.PropertyNode(pos, name=name, doc=doc, body=body)
30835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
30845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
30855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_ignorable_statement(s):
30865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    """
30875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    Parses any kind of ignorable statement that is allowed in .pxd files.
30885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    """
30895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'BEGIN_STRING':
30905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        pos = s.position()
30915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        string_node = p_atom(s)
30925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy != 'EOF':
30935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.expect_newline("Syntax error in string")
30945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return Nodes.ExprStatNode(pos, expr=string_node)
30955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return None
30965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
30975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
30985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_doc_string(s):
30995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == 'BEGIN_STRING':
31005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        pos = s.position()
31015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        kind, bytes_result, unicode_result = p_cat_string_literal(s)
31025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if s.sy != 'EOF':
31035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.expect_newline("Syntax error in doc string")
31045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if kind in ('u', ''):
31055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return unicode_result
31065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        warning(pos, "Python 3 requires docstrings to be unicode strings")
31075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return bytes_result
31085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
31095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        return None
31105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
31115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
31125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def _extract_docstring(node):
31135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    """
31145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    Extract a docstring from a statement or from the first statement
31155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    in a list.  Remove the statement if found.  Return a tuple
31165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    (plain-docstring or None, node).
31175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    """
31185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    doc_node = None
31195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if node is None:
31205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        pass
31215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif isinstance(node, Nodes.ExprStatNode):
31225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if node.expr.is_string_literal:
31235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            doc_node = node.expr
31245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            node = Nodes.StatListNode(node.pos, stats=[])
31255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif isinstance(node, Nodes.StatListNode) and node.stats:
31265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        stats = node.stats
31275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if isinstance(stats[0], Nodes.ExprStatNode):
31285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if stats[0].expr.is_string_literal:
31295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                doc_node = stats[0].expr
31305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                del stats[0]
31315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
31325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if doc_node is None:
31335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        doc = None
31345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif isinstance(doc_node, ExprNodes.BytesNode):
31355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        warning(node.pos,
31365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                "Python 3 requires docstrings to be unicode strings")
31375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        doc = doc_node.value
31385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    elif isinstance(doc_node, ExprNodes.StringNode):
31395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        doc = doc_node.unicode_value
31405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if doc is None:
31415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            doc = doc_node.value
31425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
31435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        doc = doc_node.value
31445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return doc, node
31455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
31465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
31475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_code(s, level=None, ctx=Ctx):
31485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    body = p_statement_list(s, ctx(level = level), first_statement = 1)
31495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy != 'EOF':
31505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.error("Syntax error in statement [%s,%s]" % (
31515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            repr(s.sy), repr(s.systring)))
31525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return body
31535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
31545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)_match_compiler_directive_comment = cython.declare(object, re.compile(
31555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    r"^#\s*cython\s*:\s*((\w|[.])+\s*=.*)$").match)
31565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
31575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_compiler_directive_comments(s):
31585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    result = {}
31595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    while s.sy == 'commentline':
31605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        m = _match_compiler_directive_comment(s.systring)
31615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if m:
31625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            directives = m.group(1).strip()
31635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            try:
31645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                result.update(Options.parse_directive_list(
31655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    directives, ignore_unknown=True))
31665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            except ValueError, e:
31675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                s.error(e.args[0], fatal=False)
31685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
31695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return result
31705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
31715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_module(s, pxd, full_module_name, ctx=Ctx):
31725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    pos = s.position()
31735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
31745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    directive_comments = p_compiler_directive_comments(s)
31755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.parse_comments = False
31765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
31775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if 'language_level' in directive_comments:
31785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.context.set_language_level(directive_comments['language_level'])
31795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
31805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    doc = p_doc_string(s)
31815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if pxd:
31825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        level = 'module_pxd'
31835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
31845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        level = 'module'
31855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
31865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    body = p_statement_list(s, ctx(level=level), first_statement = 1)
31875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy != 'EOF':
31885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.error("Syntax error in statement [%s,%s]" % (
31895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            repr(s.sy), repr(s.systring)))
31905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return ModuleNode(pos, doc = doc, body = body,
31915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                      full_module_name = full_module_name,
31925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                      directive_comments = directive_comments)
31935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
31945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def p_cpp_class_definition(s, pos,  ctx):
31955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    # s.sy == 'cppclass'
31965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    s.next()
31975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    module_path = []
31985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    class_name = p_ident(s)
31995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    cname = p_opt_cname(s)
32005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if cname is None and ctx.namespace is not None:
32015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        cname = ctx.namespace + "::" + class_name
32025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '.':
32035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        error(pos, "Qualified class name not allowed C++ class")
32045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '[':
32055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
32065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        templates = [p_ident(s)]
32075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        while s.sy == ',':
32085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
32095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            templates.append(p_ident(s))
32105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect(']')
32115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
32125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        templates = None
32135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '(':
32145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
32155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        base_classes = [p_c_base_type(s, templates = templates)]
32165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        while s.sy == ',':
32175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            s.next()
32185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            base_classes.append(p_c_base_type(s, templates = templates))
32195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect(')')
32205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
32215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        base_classes = []
32225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == '[':
32235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        error(s.position(), "Name options not allowed for C++ class")
32245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    nogil = p_nogil(s)
32255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if s.sy == ':':
32265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.next()
32275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect('NEWLINE')
32285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect_indent()
32295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        attributes = []
32305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        body_ctx = Ctx(visibility = ctx.visibility, level='cpp_class', nogil=nogil or ctx.nogil)
32315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        body_ctx.templates = templates
32325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        while s.sy != 'DEDENT':
32335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            if s.systring == 'cppclass':
32345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                attributes.append(
32355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    p_cpp_class_definition(s, s.position(), body_ctx))
32365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            elif s.sy != 'pass':
32375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                attributes.append(
32385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    p_c_func_or_var_declaration(s, s.position(), body_ctx))
32395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            else:
32405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                s.next()
32415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                s.expect_newline("Expected a newline")
32425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect_dedent()
32435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    else:
32445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        attributes = None
32455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        s.expect_newline("Syntax error in C++ class definition")
32465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    return Nodes.CppClassNode(pos,
32475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        name = class_name,
32485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        cname = cname,
32495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        base_classes = base_classes,
32505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        visibility = ctx.visibility,
32515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        in_pxd = ctx.level == 'module_pxd',
32525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        attributes = attributes,
32535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        templates = templates)
32545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
32555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
32565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
32575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#----------------------------------------------
32585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#
32595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#   Debugging
32605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#
32615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#----------------------------------------------
32625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
32635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)def print_parse_tree(f, node, level, key = None):
32645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    from types import ListType, TupleType
32655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    from Nodes import Node
32665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    ind = "  " * level
32675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    if node:
32685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        f.write(ind)
32695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if key:
32705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            f.write("%s: " % key)
32715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        t = type(node)
32725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        if t is tuple:
32735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            f.write("(%s @ %s\n" % (node[0], node[1]))
32745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            for i in xrange(2, len(node)):
32755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                print_parse_tree(f, node[i], level+1)
32765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            f.write("%s)\n" % ind)
32775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return
32785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif isinstance(node, Node):
32795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            try:
32805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                tag = node.tag
32815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            except AttributeError:
32825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                tag = node.__class__.__name__
32835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            f.write("%s @ %s\n" % (tag, node.pos))
32845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            for name, value in node.__dict__.items():
32855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                if name != 'tag' and name != 'pos':
32865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                    print_parse_tree(f, value, level+1, name)
32875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return
32885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)        elif t is list:
32895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            f.write("[\n")
32905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            for i in xrange(len(node)):
32915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)                print_parse_tree(f, node[i], level+1)
32925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            f.write("%s]\n" % ind)
32935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)            return
32945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)    f.write("%s%s\n" % (ind, node))
3295