Commit ad263d9b authored by daniloaf@daniloaf-PC's avatar daniloaf@daniloaf-PC

Overloaded functions with reference

parent 38c1b13d
# #
# Pyrex - Parse tree nodes # Pyrex - Parse tree nodes
# #
...@@ -485,7 +486,7 @@ class CReferenceDeclaratorNode(CDeclaratorNode): ...@@ -485,7 +486,7 @@ class CReferenceDeclaratorNode(CDeclaratorNode):
if base_type.is_pyobject: if base_type.is_pyobject:
error(self.pos, error(self.pos,
"Reference base type cannot be a Python object") "Reference base type cannot be a Python object")
ref_type = Pyrextypes.c_ref_type(base_type) ref_type = PyrexTypes.c_ref_type(base_type)
return self.base.analyse(ref_type, env, nonempty = nonempty) return self.base.analyse(ref_type, env, nonempty = nonempty)
class CArrayDeclaratorNode(CDeclaratorNode): class CArrayDeclaratorNode(CDeclaratorNode):
......
# cython: auto_cpdef=True # cython: auto_cpdef=True
# #
# Pyrex Parser # Pyrex Parser
...@@ -1749,9 +1750,6 @@ def p_c_simple_base_type(s, self_flag, nonempty, templates = None): ...@@ -1749,9 +1750,6 @@ def p_c_simple_base_type(s, self_flag, nonempty, templates = None):
if s.sy == 'IDENT' and s.systring in basic_c_type_names: if s.sy == 'IDENT' and s.systring in basic_c_type_names:
name = s.systring name = s.systring
s.next() s.next()
if s.sy == '&':
s.next()
#TODO (Danilo)
else: else:
name = 'int' name = 'int'
if s.sy == 'IDENT' and s.systring == 'complex': if s.sy == 'IDENT' and s.systring == 'complex':
...@@ -1990,6 +1988,12 @@ def p_c_simple_declarator(s, ctx, empty, is_type, cmethod_flag, ...@@ -1990,6 +1988,12 @@ def p_c_simple_declarator(s, ctx, empty, is_type, cmethod_flag,
result = Nodes.CPtrDeclaratorNode(pos, result = Nodes.CPtrDeclaratorNode(pos,
base = Nodes.CPtrDeclaratorNode(pos, base = Nodes.CPtrDeclaratorNode(pos,
base = base)) base = base))
elif s.sy == '&' and Options.cplus:
s.next()
base = p_c_declarator(s, ctx, empty = empty, is_type = is_type,
cmethod_flag = cmethod_flag,
assignable = assignable, nonempty = nonempty)
result = Nodes.CReferenceDeclaratorNode(pos, base = base)
else: else:
rhs = None rhs = None
if s.sy == 'IDENT': if s.sy == 'IDENT':
......
...@@ -91,6 +91,7 @@ class PyrexType(BaseType): ...@@ -91,6 +91,7 @@ class PyrexType(BaseType):
is_array = 0 is_array = 0
is_ptr = 0 is_ptr = 0
is_null_ptr = 0 is_null_ptr = 0
is_reference = 0
is_cfunction = 0 is_cfunction = 0
is_struct_or_union = 0 is_struct_or_union = 0
is_cpp_class = 0 is_cpp_class = 0
...@@ -1031,17 +1032,28 @@ class CReferenceType(CType): ...@@ -1031,17 +1032,28 @@ class CReferenceType(CType):
return "<CReferenceType %s>" % repr(self.base_type) return "<CReferenceType %s>" % repr(self.base_type)
def same_as_resolved_type(self, other_type): def same_as_resolved_type(self, other_type):
return self.base_type.same_as(other_type.base_type) return other_type.is_reference and self.base_type.same_as(other_type.base_type)
def declaration_code(self, entity_code, def declaration_code(self, entity_code,
for_display = 0, dll_linkage = None, pyrex = 0): for_display = 0, dll_linkage = None, pyrex = 0):
#print "CPtrType.declaration_code: pointer to", self.base_type ### #print "CReferenceType.declaration_code: pointer to", self.base_type ###
return self.base_type.declaration_code( return self.base_type.declaration_code(
"&%s" % entity_code, "&%s" % entity_code,
for_display, dll_linkage, pyrex) for_display, dll_linkage, pyrex)
def assignable_from_resolved_type(self, other_type): def assignable_from_resolved_type(self, other_type):
return 0 #TODO (Danilo) implement this if other_type is error_type:
return 1
if other_type.is_ptr:
if other_type.base_type == self.base_type:
return 1
else:
pass
#should send a warning message: initialization from incompatible pointer type (in C/C++)
if other_type == self.base_type:
return 1
else: #for now
return 0
def specialize(self, values): def specialize(self, values):
base_type = self.base_type.specialize(values) base_type = self.base_type.specialize(values)
...@@ -1797,6 +1809,9 @@ def is_promotion(type, other_type): ...@@ -1797,6 +1809,9 @@ def is_promotion(type, other_type):
return False return False
def best_match(args, functions, pos): def best_match(args, functions, pos):
'''Finds the best function to be called
Error if no function fits the call or an ambiguity is find (two or more possible functions)'''
#print functions
actual_nargs = len(args) actual_nargs = len(args)
possibilities = [] possibilities = []
bad_types = 0 bad_types = 0
...@@ -1830,7 +1845,8 @@ def best_match(args, functions, pos): ...@@ -1830,7 +1845,8 @@ def best_match(args, functions, pos):
src_type = args[i].type src_type = args[i].type
dst_type = func_type.args[i].type dst_type = func_type.args[i].type
if dst_type.assignable_from(src_type): if dst_type.assignable_from(src_type):
if src_type == dst_type: #print src_type, src_type.is_pyobject, dst_type, dst_type.is_pyobject
if src_type == dst_type or (dst_type.is_reference and src_type == dst_type.base_type):
pass # score 0 pass # score 0
elif is_promotion(src_type, dst_type): elif is_promotion(src_type, dst_type):
score[2] += 1 score[2] += 1
...@@ -1845,6 +1861,7 @@ def best_match(args, functions, pos): ...@@ -1845,6 +1861,7 @@ def best_match(args, functions, pos):
break break
else: else:
possibilities.append((score, func)) # so we can sort it possibilities.append((score, func)) # so we can sort it
#print score
if len(possibilities): if len(possibilities):
possibilities.sort() possibilities.sort()
if len(possibilities) > 1 and possibilities[0][0] == possibilities[1][0]: if len(possibilities) > 1 and possibilities[0][0] == possibilities[1][0]:
......
# #
# Symbol Table # Symbol Table
# #
...@@ -311,13 +313,16 @@ class Scope(object): ...@@ -311,13 +313,16 @@ class Scope(object):
if visibility == 'extern': if visibility == 'extern':
warning(pos, "'%s' redeclared " % name, 0) warning(pos, "'%s' redeclared " % name, 0)
elif visibility != 'ignore': elif visibility != 'ignore':
pass #pass
#error(pos, "'%s' redeclared " % name) error(pos, "'%s' redeclared " % name)
entry = Entry(name, cname, type, pos = pos) entry = Entry(name, cname, type, pos = pos)
entry.in_cinclude = self.in_cinclude entry.in_cinclude = self.in_cinclude
if name: if name:
entry.qualified_name = self.qualify_name(name) entry.qualified_name = self.qualify_name(name)
if name not in entries:
entries[name] = entry entries[name] = entry
else:
entries[name].overloaded_alternatives.append(entry)
entry.scope = self entry.scope = self
entry.visibility = visibility entry.visibility = visibility
return entry return entry
...@@ -464,14 +469,13 @@ class Scope(object): ...@@ -464,14 +469,13 @@ class Scope(object):
if visibility != 'private' and visibility != entry.visibility: if visibility != 'private' and visibility != entry.visibility:
warning(pos, "Function '%s' previously declared as '%s'" % (name, entry.visibility), 1) warning(pos, "Function '%s' previously declared as '%s'" % (name, entry.visibility), 1)
if not entry.type.same_as(type): if not entry.type.same_as(type):
#if visibility == 'extern' and entry.visibility == 'extern': if visibility == 'extern' and entry.visibility == 'extern':
#warning(pos, "Function signature does not match previous declaration", 1) warning(pos, "Function signature does not match previous declaration", 1)
#entry.type = type #entry.type = type
temp = self.add_cfunction(name, type, pos, cname, visibility, modifiers) entry.overloaded_alternatives.append(
entry.overloaded_alternatives.append(temp) self.add_cfunction(name, type, pos, cname, visibility, modifiers))
entry = temp else:
#else: error(pos, "Function signature does not match previous declaration")
#error(pos, "Function signature does not match previous declaration")
else: else:
entry = self.add_cfunction(name, type, pos, cname, visibility, modifiers) entry = self.add_cfunction(name, type, pos, cname, visibility, modifiers)
entry.func_cname = cname entry.func_cname = cname
...@@ -485,12 +489,6 @@ class Scope(object): ...@@ -485,12 +489,6 @@ class Scope(object):
entry.is_implemented = True entry.is_implemented = True
if modifiers: if modifiers:
entry.func_modifiers = modifiers entry.func_modifiers = modifiers
#try:
# print entry.name, entry.type, entry.overloaded_alternatives
#except:
# pass
#if len(entry.overloaded_alternatives) > 0:
# print entry.name, entry.type, entry.overloaded_alternatives[0].type
return entry return entry
def add_cfunction(self, name, type, pos, cname, visibility, modifiers): def add_cfunction(self, name, type, pos, cname, visibility, modifiers):
......
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