Commit 9c048f9f authored by Jeremy Hylton's avatar Jeremy Hylton

Now supports entire Python 2.0 language and still supports Python

1.5.2.  The compiler generates code for the version of the interpreter
it is run under.

ast.py:
    Print and Printnl add dest attr for extended print
    new node AugAssign for augmented assignments
    new nodes ListComp, ListCompFor, and ListCompIf for list
        comprehensions

pyassem.py:
    add work around for string-Unicode comparison raising UnicodeError
        on comparison of two objects in code object's const table

pycodegen.py:
    define VERSION, the Python major version number
    get magic number using imp.get_magic() instead of hard coding
    implement list comprehensions, extended print, and augmented
        assignment; augmented assignment uses Delegator classes (see
        doc string)
    fix import and tuple unpacking for 1.5.2

transformer.py:
    various changes to support new 2.0 grammar and old 1.5 grammar
    add debug_tree helper than converts and symbol and token numbers
    to their names
parent 5bad5a4b
......@@ -279,22 +279,24 @@ class Const(Node):
class Print(Node):
nodes['print'] = 'Print'
def __init__(self, nodes):
def __init__(self, nodes, dest):
self.nodes = nodes
self._children = ('print', nodes)
self.dest = dest
self._children = ('print', nodes, dest)
def __repr__(self):
return "Print(%s)" % self._children[1:]
return "Print(%s, %s)" % (self._children[1:-1], self._children[-1])
class Printnl(Node):
nodes['printnl'] = 'Printnl'
def __init__(self, nodes):
def __init__(self, nodes, dest):
self.nodes = nodes
self._children = ('printnl', nodes)
self.dest = dest
self._children = ('printnl', nodes, dest)
def __repr__(self):
return "Printnl(%s)" % self._children[1:]
return "Printnl(%s, %s)" % (self._children[1:-1], self._children[-1])
class Discard(Node):
nodes['discard'] = 'Discard'
......@@ -306,6 +308,18 @@ class Discard(Node):
def __repr__(self):
return "Discard(%s)" % self._children[1:]
class AugAssign(Node):
nodes['augassign'] = 'AugAssign'
def __init__(self, node, op, expr):
self.node = node
self.op = op
self.expr = expr
self._children = ('augassign', node, op, expr)
def __repr__(self):
return "AugAssign(%s)" % str(self._children[1:])
class Assign(Node):
nodes['assign'] = 'Assign'
......@@ -360,6 +374,41 @@ class AssAttr(Node):
def __repr__(self):
return "AssAttr(%s,%s,%s)" % self._children[1:]
class ListComp(Node):
nodes['listcomp'] = 'ListComp'
def __init__(self, expr, quals):
self.expr = expr
self.quals = quals
self._children = ('listcomp', expr, quals)
def __repr__(self):
return "ListComp(%s, %s)" % self._children[1:]
class ListCompFor(Node):
nodes['listcomp_for'] = 'ListCompFor'
# transformer fills in ifs after node is created
def __init__(self, assign, list, ifs):
self.assign = assign
self.list = list
self.ifs = ifs
self._children = ('listcomp_for', assign, list, ifs)
def __repr__(self):
return "ListCompFor(%s, %s, %s)" % self._children[1:]
class ListCompIf(Node):
nodes['listcomp_if'] = 'ListCompIf'
def __init__(self, test):
self.test = test
self._children = ('listcomp_if', test)
def __repr__(self):
return "ListCompIf(%s)" % self._children[1:]
class List(Node):
nodes['list'] = 'List'
......
......@@ -253,8 +253,14 @@ class PyFlowGraph(FlowGraph):
def _lookupName(self, name, list):
"""Return index of name in list, appending if necessary"""
if name in list:
i = list.index(name)
found = None
t = type(name)
for i in range(len(list)):
# must do a comparison on type first to prevent UnicodeErrors
if t == type(list[i]) and list[i] == name:
found = 1
break
if found:
# this is cheap, but incorrect in some cases, e.g 2 vs. 2L
if type(name) == type(list[i]):
return i
......
This diff is collapsed.
This diff is collapsed.
......@@ -279,22 +279,24 @@ class Const(Node):
class Print(Node):
nodes['print'] = 'Print'
def __init__(self, nodes):
def __init__(self, nodes, dest):
self.nodes = nodes
self._children = ('print', nodes)
self.dest = dest
self._children = ('print', nodes, dest)
def __repr__(self):
return "Print(%s)" % self._children[1:]
return "Print(%s, %s)" % (self._children[1:-1], self._children[-1])
class Printnl(Node):
nodes['printnl'] = 'Printnl'
def __init__(self, nodes):
def __init__(self, nodes, dest):
self.nodes = nodes
self._children = ('printnl', nodes)
self.dest = dest
self._children = ('printnl', nodes, dest)
def __repr__(self):
return "Printnl(%s)" % self._children[1:]
return "Printnl(%s, %s)" % (self._children[1:-1], self._children[-1])
class Discard(Node):
nodes['discard'] = 'Discard'
......@@ -306,6 +308,18 @@ class Discard(Node):
def __repr__(self):
return "Discard(%s)" % self._children[1:]
class AugAssign(Node):
nodes['augassign'] = 'AugAssign'
def __init__(self, node, op, expr):
self.node = node
self.op = op
self.expr = expr
self._children = ('augassign', node, op, expr)
def __repr__(self):
return "AugAssign(%s)" % str(self._children[1:])
class Assign(Node):
nodes['assign'] = 'Assign'
......@@ -360,6 +374,41 @@ class AssAttr(Node):
def __repr__(self):
return "AssAttr(%s,%s,%s)" % self._children[1:]
class ListComp(Node):
nodes['listcomp'] = 'ListComp'
def __init__(self, expr, quals):
self.expr = expr
self.quals = quals
self._children = ('listcomp', expr, quals)
def __repr__(self):
return "ListComp(%s, %s)" % self._children[1:]
class ListCompFor(Node):
nodes['listcomp_for'] = 'ListCompFor'
# transformer fills in ifs after node is created
def __init__(self, assign, list, ifs):
self.assign = assign
self.list = list
self.ifs = ifs
self._children = ('listcomp_for', assign, list, ifs)
def __repr__(self):
return "ListCompFor(%s, %s, %s)" % self._children[1:]
class ListCompIf(Node):
nodes['listcomp_if'] = 'ListCompIf'
def __init__(self, test):
self.test = test
self._children = ('listcomp_if', test)
def __repr__(self):
return "ListCompIf(%s)" % self._children[1:]
class List(Node):
nodes['list'] = 'List'
......
......@@ -253,8 +253,14 @@ class PyFlowGraph(FlowGraph):
def _lookupName(self, name, list):
"""Return index of name in list, appending if necessary"""
if name in list:
i = list.index(name)
found = None
t = type(name)
for i in range(len(list)):
# must do a comparison on type first to prevent UnicodeErrors
if t == type(list[i]) and list[i] == name:
found = 1
break
if found:
# this is cheap, but incorrect in some cases, e.g 2 vs. 2L
if type(name) == type(list[i]):
return i
......
This diff is collapsed.
This diff is collapsed.
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