Commit 391a3837 authored by Mark Florisson's avatar Mark Florisson

branch merge

parents ba464459 7de38ae0
......@@ -315,7 +315,7 @@ class DependencyTree(object):
def immediate_dependencies(self, filename):
all = list(self.cimported_files(filename))
for extern in self.cimports_and_externs(filename):
for extern in sum(self.cimports_and_externs(filename), ()):
all.append(os.path.normpath(os.path.join(os.path.dirname(filename), extern)))
return tuple(all)
......@@ -411,10 +411,15 @@ def create_extension_list(patterns, ctx=None, aliases=None):
raise TypeError(pattern)
for file in glob(filepattern):
pkg = deps.package(file)
if name == '*':
name = deps.fully_qualifeid_name(file)
if name not in seen:
module_list.append(exn_type(name=name, sources=[file], **deps.distutils_info(file, aliases, base).values))
if '*' in name:
module_name = deps.fully_qualifeid_name(file)
else:
module_name = name
if module_name not in seen:
module_list.append(exn_type(
name=module_name,
sources=[file],
**deps.distutils_info(file, aliases, base).values))
seen.add(name)
return module_list
......
......@@ -1076,8 +1076,8 @@ class StringNode(PyConstNode):
# A Python str object, i.e. a byte string in Python 2.x and a
# unicode string in Python 3.x
#
# value BytesLiteral
# unicode_value EncodedString
# value BytesLiteral (or EncodedString with ASCII content)
# unicode_value EncodedString or None
# is_identifier boolean
type = str_type
......@@ -1094,12 +1094,13 @@ class StringNode(PyConstNode):
self.check_for_coercion_error(dst_type, fail=True)
# this will be a unicode string in Py3, so make sure we can decode it
if self.value.encoding:
encoding = self.value.encoding
if self.value.encoding and isinstance(self.value, StringEncoding.BytesLiteral):
try:
self.value.decode(encoding)
self.value.decode(self.value.encoding)
except UnicodeDecodeError:
error(self.pos, "String decoding as '%s' failed. Consider using a byte string or unicode string explicitly, or adjust the source code encoding." % encoding)
error(self.pos, ("Decoding unprefixed string literal from '%s' failed. Consider using"
"a byte string or unicode string explicitly, "
"or adjust the source code encoding.") % self.value.encoding)
return self
......
......@@ -1280,6 +1280,53 @@ class EarlyReplaceBuiltinCalls(Visitor.EnvTransform):
gen_expr_node.pos, loop = loop_node, result_node = result_ref,
expr_scope = gen_expr_node.expr_scope, orig_func = is_any and 'any' or 'all')
def _handle_simple_function_sorted(self, node, pos_args):
"""Transform sorted(genexpr) into [listcomp].sort(). CPython
just reads the iterable into a list and calls .sort() on it.
Expanding the iterable in a listcomp is still faster.
"""
if len(pos_args) != 1:
return node
if not isinstance(pos_args[0], ExprNodes.GeneratorExpressionNode):
return node
gen_expr_node = pos_args[0]
loop_node = gen_expr_node.loop
yield_expression, yield_stat_node = self._find_single_yield_expression(loop_node)
if yield_expression is None:
return node
result_node = UtilNodes.ResultRefNode(
pos = loop_node.pos, type = Builtin.list_type, may_hold_none=False)
target = ExprNodes.ListNode(node.pos, args = [])
append_node = ExprNodes.ComprehensionAppendNode(
yield_expression.pos, expr = yield_expression,
target = ExprNodes.CloneNode(target))
Visitor.recursively_replace_node(loop_node, yield_stat_node, append_node)
listcomp_node = ExprNodes.ComprehensionNode(
gen_expr_node.pos, loop = loop_node, target = target,
append = append_node, type = Builtin.list_type,
expr_scope = gen_expr_node.expr_scope,
has_local_scope = True)
listcomp_assign_node = Nodes.SingleAssignmentNode(
node.pos, lhs = result_node, rhs = listcomp_node, first = True)
sort_method = ExprNodes.AttributeNode(
node.pos, obj = result_node, attribute = EncodedString('sort'),
# entry ? type ?
needs_none_check = False)
sort_node = Nodes.ExprStatNode(
node.pos, expr = ExprNodes.SimpleCallNode(
node.pos, function = sort_method, args = []))
sort_node.analyse_declarations(self.current_env())
return UtilNodes.TempResultFromStatNode(
result_node,
Nodes.StatListNode(node.pos, stats = [ listcomp_assign_node, sort_node ]))
def _handle_simple_function_sum(self, node, pos_args):
"""Transform sum(genexpr) into an equivalent inlined aggregation loop.
"""
......
......@@ -1451,9 +1451,10 @@ class TransformBuiltinMethods(EnvTransform):
error(self.pos, "Builtin 'locals()' called with wrong number of args, expected 0, got %d" % len(node.args))
return node
pos = node.pos
items = [ExprNodes.DictItemNode(pos,
key=ExprNodes.StringNode(pos, value=var),
value=ExprNodes.NameNode(pos, name=var)) for var in lenv.entries]
items = [ ExprNodes.DictItemNode(pos,
key=ExprNodes.StringNode(pos, value=var),
value=ExprNodes.NameNode(pos, name=var))
for var in lenv.entries ]
return ExprNodes.DictNode(pos, key_value_pairs=items)
# cython.foo
......
......@@ -120,9 +120,10 @@ class ResultRefNode(AtomicExprNode):
subexprs = []
lhs_of_first_assignment = False
def __init__(self, expression=None, pos=None, type=None):
def __init__(self, expression=None, pos=None, type=None, may_hold_none=True):
self.expression = expression
self.pos = None
self.may_hold_none = may_hold_none
if expression is not None:
self.pos = expression.pos
if hasattr(expression, "type"):
......@@ -141,6 +142,11 @@ class ResultRefNode(AtomicExprNode):
if self.expression is not None:
return self.expression.infer_type(env)
def may_be_none(self):
if not self.type.is_pyobject:
return False
return self.may_hold_none
def _DISABLED_may_be_none(self):
# not sure if this is safe - the expression may not be the
# only value that gets assigned
......
......@@ -62,6 +62,8 @@ VER_DEP_MODULES = {
]),
(2,4) : (operator.le, lambda x: x in ['run.extern_builtins_T258'
]),
(2,4) : (operator.lt, lambda x: x in ['run.builtin_sorted'
]),
(2,6) : (operator.lt, lambda x: x in ['run.print_function',
'run.cython3',
]),
......@@ -1156,6 +1158,8 @@ def main():
if __name__ == '__main__':
try:
main()
except SystemExit: # <= Py2.4 ...
raise
except Exception:
traceback.print_exc()
try:
......
......@@ -17,7 +17,6 @@ function_as_method_T494
closure_inside_cdef_T554
ipow_crash_T562
pure_mode_cmethod_inheritance_T583
closure_class_T596
# CPython regression tests that don't current work:
pyregr.test_threadsignals
......
cimport cython
@cython.test_fail_if_path_exists("//GeneratorExpressionNode",
"//ComprehensionNode//NoneCheckNode")
@cython.test_assert_path_exists("//ComprehensionNode")
def sorted_genexp():
"""
>>> sorted_genexp()
[1, 4, 9, 16, 25, 36, 49, 64, 81, 100]
"""
return sorted(i*i for i in range(10,0,-1))
@cython.test_assert_path_exists("//SimpleCallNode//SimpleCallNode")
def sorted_list():
"""
>>> sorted_list()
[1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
"""
return sorted(list(range(10,0,-1)))
......@@ -10,6 +10,25 @@ except NameError:
seq.sort()
return seq
__doc__ = """
>>> items = list(locals_function(1).items())
>>> items.sort()
>>> for item in items:
... print('%s = %r' % item)
a = 1
b = 2
x = u'abc'
"""
import sys
if sys.version_info[0] >= 3:
__doc__ = __doc__.replace(" u'", " '")
def locals_function(a, b=2):
x = 'abc'
return locals()
def print_function(*args):
"""
>>> print_function(1,2,3)
......
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