[Python-checkins] python/nondist/sandbox/pickletools pickletools.py,1.29,1.30

tim_one@users.sourceforge.net tim_one@users.sourceforge.net
Sun, 26 Jan 2003 18:49:42 -0800


Update of /cvsroot/python/python/nondist/sandbox/pickletools
In directory sc8-pr-cvs1:/tmp/cvs-serv20734

Modified Files:
	pickletools.py 
Log Message:
Woo hoo!  Added annotations to the disassembler output so that an opcode
that uses a markobject tells us which MARK opcode created it.  Don't
know about anyone else, but it greatly improves the comprehensibility
for me.


Index: pickletools.py
===================================================================
RCS file: /cvsroot/python/python/nondist/sandbox/pickletools/pickletools.py,v
retrieving revision 1.29
retrieving revision 1.30
diff -C2 -d -r1.29 -r1.30
*** pickletools.py	27 Jan 2003 02:06:04 -0000	1.29
--- pickletools.py	27 Jan 2003 02:49:40 -0000	1.30
***************
*** 978,982 ****
        stack_before=[pylist, markobject, stackslice],
        stack_after=[pylist],
!       proto=0,
        doc="""Extend a list by a slice of stack objects.
  
--- 978,982 ----
        stack_before=[pylist, markobject, stackslice],
        stack_after=[pylist],
!       proto=1,
        doc="""Extend a list by a slice of stack objects.
  
***************
*** 1210,1214 ****
        """),
  
!     # Puah a class object on the stack, via its module and name.
  
      I(name='GLOBAL',
--- 1210,1215 ----
        """),
  
!     # Puah a class object, or module function, on the stack, via its module
!     # and name.
  
      I(name='GLOBAL',
***************
*** 1569,1582 ****
      """
  
      for opcode, arg, pos in genops(pickle):
          if pos is not None:
              print >> out, "%5d:" % pos,
-         print >> out, opcode.code,
-         if arg is None:
-             print >> out, opcode.name
-         else:
-             print >> out, "%-10s %r" % (opcode.name, arg)
  
! _dis_test1 = """
  >>> import pickle
  >>> x = [1, 2, (3, 4), {'abc': u"def"}]
--- 1570,1600 ----
      """
  
+     markstack = []
      for opcode, arg, pos in genops(pickle):
          if pos is not None:
              print >> out, "%5d:" % pos,
  
!         line = opcode.code + " " + opcode.name
! 
!         markmsg = None
!         if markstack and markobject in opcode.stack_before:
!                 markpos = markstack.pop()
!                 if markpos is not None:
!                     markmsg = "(MARK at %d)" % markpos
! 
!         if arg is not None or markmsg:
!             # make a mild effort to align arguments
!             line += (' ' * 10)[len(opcode.name):]
!             if arg is not None:
!                 line += ' ' + repr(arg)
!             if markmsg:
!                 line += ' ' + markmsg
!         print >> out, line
! 
!         if markobject in opcode.stack_after:
!             markstack.append(pos)
! 
! 
! _dis_test = """
  >>> import pickle
  >>> x = [1, 2, (3, 4), {'abc': u"def"}]
***************
*** 1584,1588 ****
  >>> dis(pik)
      0: ( MARK
!     1: l LIST
      2: p PUT        0
      5: I INT        1
--- 1602,1606 ----
  >>> dis(pik)
      0: ( MARK
!     1: l LIST       (MARK at 0)
      2: p PUT        0
      5: I INT        1
***************
*** 1593,1601 ****
     14: I INT        3
     17: I INT        4
!    20: t TUPLE
     21: p PUT        1
     24: a APPEND
     25: ( MARK
!    26: d DICT
     27: p PUT        2
     30: S STRING     'abc'
--- 1611,1619 ----
     14: I INT        3
     17: I INT        4
!    20: t TUPLE      (MARK at 13)
     21: p PUT        1
     24: a APPEND
     25: ( MARK
!    26: d DICT       (MARK at 25)
     27: p PUT        2
     30: S STRING     'abc'
***************
*** 1619,1623 ****
      9: K BININT1    3
     11: K BININT1    4
!    13: t TUPLE
     14: q BINPUT     1
     16: } EMPTY_DICT
--- 1637,1641 ----
      9: K BININT1    3
     11: K BININT1    4
!    13: t TUPLE      (MARK at 8)
     14: q BINPUT     1
     16: } EMPTY_DICT
***************
*** 1628,1636 ****
     34: q BINPUT     4
     36: s SETITEM
!    37: e APPENDS
     38: . STOP
  """
  
! __test__ = {'dissassembler_test1': _dis_test1,
             }
  
--- 1646,1705 ----
     34: q BINPUT     4
     36: s SETITEM
!    37: e APPENDS    (MARK at 3)
     38: . STOP
+ 
+ Exercise the INST/OBJ/BUILD family.
+ 
+ >>> import random
+ >>> dis(pickle.dumps(random.random))
+     0: c GLOBAL     'random.random'
+    15: p PUT        0
+    18: . STOP
+ 
+ >>> x = [pickle.PicklingError()] * 2
+ >>> dis(pickle.dumps(x))
+     0: ( MARK
+     1: l LIST       (MARK at 0)
+     2: p PUT        0
+     5: ( MARK
+     6: i INST       'pickle.PicklingError' (MARK at 5)
+    28: p PUT        1
+    31: ( MARK
+    32: d DICT       (MARK at 31)
+    33: p PUT        2
+    36: S STRING     'args'
+    44: p PUT        3
+    47: ( MARK
+    48: t TUPLE      (MARK at 47)
+    49: p PUT        4
+    52: s SETITEM
+    53: b BUILD
+    54: a APPEND
+    55: g GET        1
+    58: a APPEND
+    59: . STOP
+ 
+ >>> dis(pickle.dumps(x, 1))
+     0: ] EMPTY_LIST
+     1: q BINPUT     0
+     3: ( MARK
+     4: ( MARK
+     5: c GLOBAL     'pickle.PicklingError'
+    27: q BINPUT     1
+    29: o OBJ        (MARK at 4)
+    30: q BINPUT     2
+    32: } EMPTY_DICT
+    33: q BINPUT     3
+    35: U SHORT_BINSTRING 'args'
+    41: q BINPUT     4
+    43: ) EMPTY_TUPLE
+    44: s SETITEM
+    45: b BUILD
+    46: h BINGET     2
+    48: e APPENDS    (MARK at 3)
+    49: . STOP
  """
  
! __test__ = {'dissassembler_test': _dis_test,
             }