[pypy-svn] r13064 - in pypy/dist/pypy: annotation translator/test
pedronis at codespeak.net
pedronis at codespeak.net
Sun Jun 5 00:30:27 CEST 2005
Author: pedronis
Date: Sun Jun 5 00:30:27 2005
New Revision: 13064
Modified:
pypy/dist/pypy/annotation/binaryop.py
pypy/dist/pypy/annotation/model.py
pypy/dist/pypy/translator/test/test_annrpython.py
Log:
more fine tuning, see the new test for the point
Modified: pypy/dist/pypy/annotation/binaryop.py
==============================================================================
--- pypy/dist/pypy/annotation/binaryop.py (original)
+++ pypy/dist/pypy/annotation/binaryop.py Sun Jun 5 00:30:27 2005
@@ -140,10 +140,10 @@
if obj2.is_constant():
if obj1.is_constant():
r.const = obj1.const is obj2.const
- if obj2.const is None and not getattr(obj1, 'can_be_None', True):
+ if obj2.const is None and not obj1.can_be_none():
r.const = False
elif obj1.is_constant():
- if obj1.const is None and not getattr(obj2, 'can_be_None', True):
+ if obj1.const is None and not obj2.can_be_none():
r.const = False
# XXX HACK HACK HACK
# XXX HACK HACK HACK
@@ -151,19 +151,27 @@
bk = getbookkeeper()
if bk is not None: # for testing
knowntypedata = r.knowntypedata = {}
+ fn, block, i = bk.position_key
+
+ annotator = bk.annotator
+ op = block.operations[i]
+ assert op.opname == "is_"
+ assert len(op.args) == 2
+
def bind(src_obj, tgt_obj, tgt_arg):
if hasattr(tgt_obj, 'is_type_of') and src_obj.is_constant():
add_knowntypedata(knowntypedata, True, tgt_obj.is_type_of,
bk.valueoftype(src_obj.const))
- fn, block, i = bk.position_key
- annotator = bk.annotator
- op = block.operations[i]
- assert op.opname == "is_"
- assert len(op.args) == 2
assert annotator.binding(op.args[tgt_arg]) == tgt_obj
add_knowntypedata(knowntypedata, True, [op.args[tgt_arg]], src_obj)
+ nonnone_obj = tgt_obj
+ if src_obj.is_constant() and src_obj.const is None and tgt_obj.can_be_none():
+ nonnone_obj = tgt_obj.nonnoneify()
+
+ add_knowntypedata(knowntypedata, False, [op.args[tgt_arg]], nonnone_obj)
+
bind(obj2, obj1, 0)
bind(obj1, obj2, 1)
Modified: pypy/dist/pypy/annotation/model.py
==============================================================================
--- pypy/dist/pypy/annotation/model.py (original)
+++ pypy/dist/pypy/annotation/model.py Sun Jun 5 00:30:27 2005
@@ -146,12 +146,19 @@
def __setattr__(self, key, value):
object.__setattr__(self, key, value)
+ def can_be_none(self):
+ return True
+
+ def nonnoneify(self):
+ return self
class SomeFloat(SomeObject):
"Stands for a float or an integer."
knowntype = float # if we don't know if it's a float or an int,
# pretend it's a float.
+ def can_be_none(self):
+ return False
class SomeInteger(SomeFloat):
"Stands for an object which is known to be an integer."
@@ -169,13 +176,17 @@
def __init__(self):
pass
-
class SomeString(SomeObject):
"Stands for an object which is known to be a string."
knowntype = str
def __init__(self, can_be_None=False):
self.can_be_None = can_be_None
+ def can_be_none(self):
+ return self.can_be_None
+
+ def nonnoneify(self):
+ return SomeString(can_be_None=False)
class SomeChar(SomeString):
"Stands for an object known to be a string of length 1."
@@ -184,6 +195,9 @@
knowntype = unicode
"Stands for an object known to be a unicode codepoint."
+ def can_be_none(self):
+ return False
+
class SomeList(SomeObject):
"Stands for a homogenous list of any length."
knowntype = list
@@ -193,6 +207,8 @@
return (self.__class__ is other.__class__ and
self.listdef.same_as(other.listdef))
+ def can_be_none(self):
+ return False
class SomeSlice(SomeObject):
knowntype = slice
@@ -201,6 +217,8 @@
self.stop = stop
self.step = step
+ def can_be_none(self):
+ return False
class SomeTuple(SomeObject):
"Stands for a tuple of known length."
@@ -213,6 +231,8 @@
else:
self.const = tuple([i.const for i in items])
+ def can_be_none(self):
+ return False
class SomeDict(SomeObject):
"Stands for a dict."
@@ -223,6 +243,8 @@
return (self.__class__ is other.__class__ and
self.dictdef.same_as(other.dictdef))
+ def can_be_none(self):
+ return False
class SomeIterator(SomeObject):
"Stands for an iterator returning objects from a given container."
@@ -230,6 +252,8 @@
def __init__(self, s_container):
self.s_container = s_container
+ def can_be_none(self):
+ return False
class SomeInstance(SomeObject):
"Stands for an instance of a (user-defined) class."
@@ -242,6 +266,13 @@
def fmt_classdef(self, cd):
return cd.cls.__name__
+ def can_be_none(self):
+ return self.can_be_None
+
+ def nonnoneify(self):
+ return SomeInstance(self.classdef, can_be_None=False)
+
+
def new_or_old_class(c):
if hasattr(c, '__class__'):
return c.__class__
@@ -289,6 +320,17 @@
def isNone(self):
return self.prebuiltinstances == {None:True}
+ def can_be_none(self):
+ return None in self.prebuiltinstances
+
+ def nonnoneify(self):
+ prebuiltinstances = self.prebuiltinstances.copy()
+ del prebuiltinstances[None]
+ if not prebuiltinstances:
+ return SomeImpossibleValue()
+ else:
+ return SomePBC(prebuiltinstances)
+
def fmt_prebuiltinstances(self, pbis):
if hasattr(self, 'const'):
return None
@@ -310,11 +352,16 @@
self.s_self = s_self
self.methodname = methodname
+ def can_be_none(self):
+ return False
class SomeImpossibleValue(SomeObject):
"""The empty set. Instances are placeholders for objects that
will never show up at run-time, e.g. elements of an empty list."""
+ def can_be_none(self):
+ return False
+
#____________________________________________________________
# annotation of low-level types
@@ -322,6 +369,8 @@
def __init__(self, ll_ptrtype):
self.ll_ptrtype = ll_ptrtype
+ def can_be_none(self):
+ return False
from pypy.rpython import lltype
Modified: pypy/dist/pypy/translator/test/test_annrpython.py
==============================================================================
--- pypy/dist/pypy/translator/test/test_annrpython.py (original)
+++ pypy/dist/pypy/translator/test/test_annrpython.py Sun Jun 5 00:30:27 2005
@@ -1188,6 +1188,24 @@
s = a.build_types(f, [int])
assert s == a.bookkeeper.immutablevalue(None)
+ def test_non_None_path(self):
+ class C:
+ pass
+ def g(c):
+ if c is None:
+ return C()
+ return c
+ def f(x):
+ if x:
+ c = None
+ else:
+ c = C()
+ return g(c)
+ a = self.RPythonAnnotator()
+ s = a.build_types(f, [bool])
+ assert s.can_be_none() == False
+
+
def g(n):
return [0,1,2,n]
More information about the Pypy-commit
mailing list