summaryrefslogtreecommitdiff
path: root/lang/python/wiredtiger/fpacking.py
diff options
context:
space:
mode:
authorMichael Cahill <michael.cahill@wiredtiger.com>2013-07-17 10:13:11 +1000
committerMichael Cahill <michael.cahill@wiredtiger.com>2013-07-17 10:13:11 +1000
commit1fb70757f2e7d5a783b389249a3bcd3149eb6fcf (patch)
tree9c84590ae3456273596f5de205efb1df19cb1ea8 /lang/python/wiredtiger/fpacking.py
parentba05f74e0d5c868b6b3b346d03c57d050305f88d (diff)
downloadmongo-1fb70757f2e7d5a783b389249a3bcd3149eb6fcf.tar.gz
Fix "make install" of Python. Remove old code and restructure the Python sources under lang/python to simplify the installation step.
--HG-- rename : lang/python/fpacking.py => lang/python/wiredtiger/fpacking.py rename : lang/python/intpack-test.py => lang/python/wiredtiger/intpack-test.py rename : lang/python/intpacking.py => lang/python/wiredtiger/intpacking.py rename : lang/python/packing-test.py => lang/python/wiredtiger/packing-test.py rename : lang/python/packing.py => lang/python/wiredtiger/packing.py
Diffstat (limited to 'lang/python/wiredtiger/fpacking.py')
-rw-r--r--lang/python/wiredtiger/fpacking.py98
1 files changed, 98 insertions, 0 deletions
diff --git a/lang/python/wiredtiger/fpacking.py b/lang/python/wiredtiger/fpacking.py
new file mode 100644
index 00000000000..1922047edde
--- /dev/null
+++ b/lang/python/wiredtiger/fpacking.py
@@ -0,0 +1,98 @@
+#!/usr/bin/env python
+#
+# Copyright (c) 2008-2013 WiredTiger, Inc.
+# All rights reserved.
+#
+# See the file LICENSE for redistribution information.
+#
+# WiredTiger fixed-size packing and unpacking functions, using the Python
+# struct library.
+
+import struct
+
+def __wt2struct(fmt):
+ if not fmt:
+ return None, fmt
+ # Big endian with no alignment is the default
+ if fmt[0] in '@=<>!':
+ tfmt = fmt[0]
+ fmt = fmt[1:]
+ else:
+ tfmt = '>'
+ return tfmt, fmt.replace('r', 'Q')
+
+def unpack(fmt, s):
+ tfmt, fmt = __wt2struct(fmt)
+ if not fmt:
+ return ()
+ result = ()
+ pfmt = tfmt
+ sizebytes = 0
+ for offset, f in enumerate(fmt):
+ if f.isdigit():
+ sizebytes += 1
+ # With a fixed size, everything is encoded as a string
+ if f in 'Su' and sizebytes > 0:
+ f = 's'
+ if f not in 'Su':
+ pfmt += f
+ sizebytes = 0
+ continue
+
+ # We've hit something that needs special handling, split any fixed-size
+ # values we've already passed
+ if len(pfmt) > 1:
+ size = struct.calcsize(pfmt)
+ result += struct.unpack_from(pfmt, s)
+ s = s[size:]
+ if f == 'S':
+ l = s.find('\0')
+ result += (s[:l],)
+ s = s[l+1:]
+ if f == 'u':
+ if offset == len(fmt) - 1:
+ result += (s,)
+ else:
+ l = struct.unpack_from(tfmt + 'l', s)[0]
+ s = s[struct.calcsize(tfmt + 'l'):]
+ result += (s[:l],)
+ s = s[l:]
+ pfmt = tfmt
+ sizebytes = 0
+
+ if len(pfmt) > 1:
+ result += struct.unpack(pfmt, s)
+ return result
+
+def pack(fmt, *values):
+ pfmt, fmt = __wt2struct(fmt)
+ if not fmt:
+ return ''
+ i = sizebytes = 0
+ for offset, f in enumerate(fmt):
+ if f == 'S':
+ # Note: this code is being careful about embedded NUL characters
+ if sizebytes == 0:
+ l = values[i].find('\0') + 1
+ if not l:
+ l = len(values[i]) + 1
+ pfmt += str(l)
+ sizebytes = len(str(l))
+ f = 's'
+ elif f == 'u':
+ if sizebytes == 0 and offset != len(fmt) - 1:
+ l = len(values[i])
+ pfmt += 'l' + str(l)
+ values = values[:i] + (l,) + values[i:]
+ sizebytes = len(str(l))
+ f = 's'
+ pfmt += f
+ if f.isdigit():
+ sizebytes += 1
+ continue
+ if f != 's' and sizebytes > 0:
+ i += int(pfmt[-sizebytes:])
+ else:
+ i += 1
+ sizebytes = 0
+ return struct.pack(pfmt, *values)