Commit 0a77df1d authored by Robert Bradshaw's avatar Robert Bradshaw

Extract last of type list dependance from parser.

parent 231240e1
...@@ -411,8 +411,10 @@ class CNameDeclaratorNode(CDeclaratorNode): ...@@ -411,8 +411,10 @@ class CNameDeclaratorNode(CDeclaratorNode):
error(self.pos, "Missing argument name") error(self.pos, "Missing argument name")
elif base_type.is_void: elif base_type.is_void:
error(self.pos, "Use spam() rather than spam(void) to declare a function with no arguments.") error(self.pos, "Use spam() rather than spam(void) to declare a function with no arguments.")
self.name = base_type.declaration_code("", for_display=1, pyrex=1) else:
base_type = py_object_type print "here"
self.name = base_type.declaration_code("", for_display=1, pyrex=1)
base_type = py_object_type
self.type = base_type self.type = base_type
return self, base_type return self, base_type
...@@ -570,7 +572,19 @@ class CArgDeclNode(Node): ...@@ -570,7 +572,19 @@ class CArgDeclNode(Node):
def analyse(self, env, nonempty = 0): def analyse(self, env, nonempty = 0):
#print "CArgDeclNode.analyse: is_self_arg =", self.is_self_arg ### #print "CArgDeclNode.analyse: is_self_arg =", self.is_self_arg ###
base_type = self.base_type.analyse(env) # The parser may missinterpret names as types...
# We fix that here.
if isinstance(self.declarator, CNameDeclaratorNode) and self.declarator.name == '':
if nonempty:
self.declarator.name = self.base_type.name
self.base_type.name = None
self.base_type.is_basic_c_type = False
could_be_name = True
else:
could_be_name = False
base_type = self.base_type.analyse(env, could_be_name = could_be_name)
if self.base_type.arg_name:
self.declarator.name = self.base_type.arg_name
return self.declarator.analyse(base_type, env, nonempty = nonempty) return self.declarator.analyse(base_type, env, nonempty = nonempty)
def annotate(self, code): def annotate(self, code):
...@@ -597,8 +611,9 @@ class CSimpleBaseTypeNode(CBaseTypeNode): ...@@ -597,8 +611,9 @@ class CSimpleBaseTypeNode(CBaseTypeNode):
# is_self_arg boolean Is self argument of C method # is_self_arg boolean Is self argument of C method
child_attrs = [] child_attrs = []
arg_name = None # in case the argument name was interpreted as a type
def analyse(self, env): def analyse(self, env, could_be_name = False):
# Return type descriptor. # Return type descriptor.
#print "CSimpleBaseTypeNode.analyse: is_self_arg =", self.is_self_arg ### #print "CSimpleBaseTypeNode.analyse: is_self_arg =", self.is_self_arg ###
type = None type = None
...@@ -615,13 +630,22 @@ class CSimpleBaseTypeNode(CBaseTypeNode): ...@@ -615,13 +630,22 @@ class CSimpleBaseTypeNode(CBaseTypeNode):
else: else:
type = py_object_type type = py_object_type
else: else:
scope = env.find_imported_module(self.module_path, self.pos) if self.module_path:
scope = env.find_imported_module(self.module_path, self.pos)
else:
scope = env
if scope: if scope:
if scope.is_c_class_scope: if scope.is_c_class_scope:
scope = scope.global_scope() scope = scope.global_scope()
entry = scope.find(self.name, self.pos) entry = scope.lookup(self.name)
if entry and entry.is_type: if entry and entry.is_type:
type = entry.type type = entry.type
elif could_be_name:
if self.is_self_arg and env.is_c_class_scope:
type = env.parent_type
else:
type = py_object_type
self.arg_name = self.name
else: else:
error(self.pos, "'%s' is not a type identifier" % self.name) error(self.pos, "'%s' is not a type identifier" % self.name)
if type: if type:
...@@ -644,7 +668,7 @@ class CBufferAccessTypeNode(CBaseTypeNode): ...@@ -644,7 +668,7 @@ class CBufferAccessTypeNode(CBaseTypeNode):
dtype_node = None dtype_node = None
def analyse(self, env): def analyse(self, env, could_be_name = False):
base_type = self.base_type_node.analyse(env) base_type = self.base_type_node.analyse(env)
if base_type.is_error: return base_type if base_type.is_error: return base_type
import Buffer import Buffer
...@@ -665,8 +689,8 @@ class CComplexBaseTypeNode(CBaseTypeNode): ...@@ -665,8 +689,8 @@ class CComplexBaseTypeNode(CBaseTypeNode):
child_attrs = ["base_type", "declarator"] child_attrs = ["base_type", "declarator"]
def analyse(self, env): def analyse(self, env, could_be_name = False):
base = self.base_type.analyse(env) base = self.base_type.analyse(env, could_be_name)
_, type = self.declarator.analyse(base, env) _, type = self.declarator.analyse(base, env)
return type return type
......
...@@ -253,14 +253,14 @@ def p_sizeof(s): ...@@ -253,14 +253,14 @@ def p_sizeof(s):
# Here we decide if we are looking at an expression or type # Here we decide if we are looking at an expression or type
# If it is actually a type, but parsable as an expression, # If it is actually a type, but parsable as an expression,
# we treat it as an expression here. # we treat it as an expression here.
if looking_at_type(s): if looking_at_expr(s):
operand = p_simple_expr(s)
node = ExprNodes.SizeofVarNode(pos, operand = operand)
else:
base_type = p_c_base_type(s) base_type = p_c_base_type(s)
declarator = p_c_declarator(s, empty = 1) declarator = p_c_declarator(s, empty = 1)
node = ExprNodes.SizeofTypeNode(pos, node = ExprNodes.SizeofTypeNode(pos,
base_type = base_type, declarator = declarator) base_type = base_type, declarator = declarator)
else:
operand = p_simple_expr(s)
node = ExprNodes.SizeofVarNode(pos, operand = operand)
s.expect(')') s.expect(')')
return node return node
...@@ -1034,7 +1034,6 @@ def p_from_import_statement(s, first_statement = 0): ...@@ -1034,7 +1034,6 @@ def p_from_import_statement(s, first_statement = 0):
for (name_pos, name, as_name, kind) in imported_names: for (name_pos, name, as_name, kind) in imported_names:
local_name = as_name or name local_name = as_name or name
if local_name == "*" and False: if local_name == "*" and False:
print s.__dict__.keys()
module = s.context.find_module(dotted_name) module = s.context.find_module(dotted_name)
for type in module.type_entries: for type in module.type_entries:
s.add_type_name(type.name) s.add_type_name(type.name)
...@@ -1613,7 +1612,7 @@ def p_c_complex_base_type(s): ...@@ -1613,7 +1612,7 @@ def p_c_complex_base_type(s):
base_type = base_type, declarator = declarator) base_type = base_type, declarator = declarator)
def p_c_simple_base_type(s, self_flag, nonempty): def p_c_simple_base_type(s, self_flag, nonempty):
#print "p_c_simple_base_type: self_flag =", self_flag #print "p_c_simple_base_type: self_flag =", self_flag, nonempty
is_basic = 0 is_basic = 0
signed = 1 signed = 1
longness = 0 longness = 0
...@@ -1636,12 +1635,11 @@ def p_c_simple_base_type(s, self_flag, nonempty): ...@@ -1636,12 +1635,11 @@ def p_c_simple_base_type(s, self_flag, nonempty):
module_path.append(name) module_path.append(name)
s.next() s.next()
name = p_ident(s) name = p_ident(s)
elif s.looking_at_type_name(): # looking_at_type(s): else:
name = s.systring name = s.systring
s.next() s.next()
if nonempty and s.sy != 'IDENT': if nonempty and s.sy != 'IDENT':
# Make sure this is not a declaration of a variable or # Make sure this is not a declaration of a variable or function.
# function with the same name as a type.
if s.sy == '(': if s.sy == '(':
s.next() s.next()
if s.sy == '*' or s.sy == '**': if s.sy == '*' or s.sy == '**':
...@@ -1653,10 +1651,7 @@ def p_c_simple_base_type(s, self_flag, nonempty): ...@@ -1653,10 +1651,7 @@ def p_c_simple_base_type(s, self_flag, nonempty):
elif s.sy not in ('*', '**', '['): elif s.sy not in ('*', '**', '['):
s.put_back('IDENT', name) s.put_back('IDENT', name)
name = None name = None
else:
#print "p_c_simple_base_type: not looking at type at", s.position()
name = None
type_node = Nodes.CSimpleBaseTypeNode(pos, type_node = Nodes.CSimpleBaseTypeNode(pos,
name = name, module_path = module_path, name = name, module_path = module_path,
is_basic_c_type = is_basic, signed = signed, is_basic_c_type = is_basic, signed = signed,
...@@ -1696,13 +1691,12 @@ def p_buffer_access(s, base_type_node): ...@@ -1696,13 +1691,12 @@ def p_buffer_access(s, base_type_node):
return result return result
def looking_at_possible_type(s): def looking_at_name(s):
return s.sy == 'IDENT' and not s.systring in calling_convention_words return s.sy == 'IDENT' and not s.systring in calling_convention_words
# return looking_at_base_type(s) or s.looking_at_type_name()
def looking_at_type(s): def looking_at_expr(s):
if s.systring in base_type_start_words: if s.systring in base_type_start_words:
return True return False
elif s.sy == 'IDENT': elif s.sy == 'IDENT':
is_type = False is_type = False
name = s.systring name = s.systring
...@@ -1713,7 +1707,9 @@ def looking_at_type(s): ...@@ -1713,7 +1707,9 @@ def looking_at_type(s):
dotted_path.append(s.systring) dotted_path.append(s.systring)
s.expect('IDENT') s.expect('IDENT')
saved = s.sy, s.systring saved = s.sy, s.systring
if s.sy == '*' or s.sy == '**': if s.sy == 'IDENT':
is_type = True
elif s.sy == '*' or s.sy == '**':
s.next() s.next()
is_type = s.sy == ')' is_type = s.sy == ')'
s.put_back(*saved) s.put_back(*saved)
...@@ -1725,16 +1721,14 @@ def looking_at_type(s): ...@@ -1725,16 +1721,14 @@ def looking_at_type(s):
s.next() s.next()
is_type = s.sy == ']' is_type = s.sy == ']'
s.put_back(*saved) s.put_back(*saved)
elif s.sy == 'IDENT':
is_type = True
dotted_path.reverse() dotted_path.reverse()
for p in dotted_path: for p in dotted_path:
s.put_back('IDENT', p) s.put_back('IDENT', p)
s.put_back('.', '.') s.put_back('.', '.')
s.put_back('IDENT', name) s.put_back('IDENT', name)
return is_type return not is_type
else: else:
return False return True
def looking_at_base_type(s): def looking_at_base_type(s):
#print "looking_at_base_type?", s.sy, s.systring, s.position() #print "looking_at_base_type?", s.sy, s.systring, s.position()
...@@ -1790,7 +1784,7 @@ def p_c_declarator(s, ctx = Ctx(), empty = 0, is_type = 0, cmethod_flag = 0, ...@@ -1790,7 +1784,7 @@ def p_c_declarator(s, ctx = Ctx(), empty = 0, is_type = 0, cmethod_flag = 0,
pos = s.position() pos = s.position()
if s.sy == '(': if s.sy == '(':
s.next() s.next()
if s.sy == ')' or looking_at_possible_type(s): if s.sy == ')' or looking_at_name(s):
base = Nodes.CNameDeclaratorNode(pos, name = EncodedString(u""), cname = None) base = Nodes.CNameDeclaratorNode(pos, name = EncodedString(u""), cname = None)
result = p_c_func_declarator(s, pos, ctx, base, cmethod_flag) result = p_c_func_declarator(s, pos, ctx, base, cmethod_flag)
else: else:
...@@ -2195,6 +2189,8 @@ def p_ctypedef_statement(s, ctx): ...@@ -2195,6 +2189,8 @@ def p_ctypedef_statement(s, ctx):
return p_c_struct_or_union_definition(s, pos, ctx) return p_c_struct_or_union_definition(s, pos, ctx)
else: else:
base_type = p_c_base_type(s, nonempty = 1) base_type = p_c_base_type(s, nonempty = 1)
if base_type.name is None:
s.error("Syntax error in ctypedef statement")
declarator = p_c_declarator(s, ctx, is_type = 1, nonempty = 1) declarator = p_c_declarator(s, ctx, is_type = 1, nonempty = 1)
s.expect_newline("Syntax error in ctypedef statement") s.expect_newline("Syntax error in ctypedef statement")
return Nodes.CTypeDefNode( return Nodes.CTypeDefNode(
......
...@@ -280,7 +280,6 @@ class BuiltinObjectType(PyObjectType): ...@@ -280,7 +280,6 @@ class BuiltinObjectType(PyObjectType):
return "<%s>"% self.cname return "<%s>"% self.cname
def assignable_from(self, src_type): def assignable_from(self, src_type):
if isinstance(src_type, BuiltinObjectType): if isinstance(src_type, BuiltinObjectType):
return src_type.name == self.name return src_type.name == self.name
else: else:
......
cdef struct point:
double x
double y
double z
print sizeof(point*)
cdef extern from *:
cdef foo(int, int i,
list, list L,
point, point p, point* ps)
cdef class A:
cdef list
cdef list L
cdef point(self, int, int i, list, list L, point, point p, point* ps):
pass
cdef class B(A):
cdef point(self, o, int i, oo, list L, ooo, point p, point* ps):
pass
cdef point P
cdef point *Ps
cdef A a
foo(2, 3, [], [], P, P, &P)
a.point("something", 3, "anything", [], "an object", P, &P)
...@@ -10,7 +10,7 @@ cdef class Grail: ...@@ -10,7 +10,7 @@ cdef class Grail:
pass pass
_ERRORS = u""" _ERRORS = u"""
1:9: Non-default argument follows default argument 1:10: Non-default argument follows default argument
9:16: This argument cannot have a default value 9:16: This argument cannot have a default value
4:23: Non-default argument following default argument 4:23: Non-default argument following default argument
""" """
...@@ -4,7 +4,5 @@ def f(): ...@@ -4,7 +4,5 @@ def f():
cdef object[e_bufaccess_pxd.T] buf cdef object[e_bufaccess_pxd.T] buf
_ERRORS = u""" _ERRORS = u"""
3:17: Syntax error in ctypedef statement 3:9: 'nothing' is not a type identifier
4:31: 'T' is not a type identifier
4:31: 'T' is not declared
""" """
def f(): def f():
a = <foao>x a = <foao>True
_ERRORS = """ _ERRORS = """
2:13: Unknown type 2:9: 'foao' is not a type identifier
""" """
\ No newline at end of file
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment