Serhiy Storchaka added the comment:
> However, I have no idea how to write that file using Apple's APIs.
Look in CFBinaryPList.c. It have a code for creating 128-bit integers:
CFSInt128Struct val;
val.high = 0;
val.low = bigint;
*plist = CFNumberCreate(allocator, kCFNumberSInt128Type, &val);
And I suppose that you have at least one way to create such file -- just
convert plist file in XML format to binary format.
> Keep in mind that this module is intended for interop with Apple's data
> format.
Apple's tool can read and write integers from 2**63 to 2**64-1.
Here is a patch against current sources.
----------
Added file: http://bugs.python.org/file33481/plistlib_big_ints.patch
_______________________________________
Python tracker <rep...@bugs.python.org>
<http://bugs.python.org/issue14455>
_______________________________________
diff -r 1a8149ba3000 Doc/library/plistlib.rst
--- a/Doc/library/plistlib.rst Wed Jan 15 11:32:35 2014 +0100
+++ b/Doc/library/plistlib.rst Wed Jan 15 15:22:29 2014 +0200
@@ -107,13 +107,6 @@
An :exc:`OverflowError` will be raised for integer values that cannot
be represented in (binary) plist files.
- .. warning::
-
- For compatibility with Apple's libraries it is possible to write
- an integer in the range from 2 ** 63 upto (and including) 2 ** 64
- to binary plists, even though these will be read back as negative
- values.
-
.. versionadded: 3.4
diff -r 1a8149ba3000 Lib/plistlib.py
--- a/Lib/plistlib.py Wed Jan 15 11:32:35 2014 +0100
+++ b/Lib/plistlib.py Wed Jan 15 15:22:29 2014 +0200
@@ -879,18 +879,19 @@
try:
self._fp.write(struct.pack('>Bq', 0x13, value))
except struct.error:
- raise OverflowError(value)
+ raise OverflowError(value) from None
elif value < 1 << 8:
self._fp.write(struct.pack('>BB', 0x10, value))
elif value < 1 << 16:
self._fp.write(struct.pack('>BH', 0x11, value))
elif value < 1 << 32:
self._fp.write(struct.pack('>BL', 0x12, value))
+ elif value < 1 << 63:
+ self._fp.write(struct.pack('>Bq', 0x13, value))
+ elif value < 1 << 64:
+ self._fp.write(b'\x14' + value.to_bytes(16, 'big',
signed=True))
else:
- try:
- self._fp.write(struct.pack('>BQ', 0x13, value))
- except struct.error:
- raise OverflowError(value)
+ raise OverflowError(value)
elif isinstance(value, float):
self._fp.write(struct.pack('>Bd', 0x23, value))
diff -r 1a8149ba3000 Lib/test/test_plistlib.py
--- a/Lib/test/test_plistlib.py Wed Jan 15 11:32:35 2014 +0100
+++ b/Lib/test/test_plistlib.py Wed Jan 15 15:22:29 2014 +0200
@@ -152,7 +152,7 @@
def test_int(self):
for pl in [0, 2**8-1, 2**8, 2**16-1, 2**16, 2**32-1, 2**32,
- 2**63-1, 1, -2**63]:
+ 2**63-1, 2**64-1, 1, -2**63]:
for fmt in ALL_FORMATS:
with self.subTest(pl=pl, fmt=fmt):
data = plistlib.dumps(pl, fmt=fmt)
@@ -163,7 +163,7 @@
self.assertEqual(data, data2)
for fmt in ALL_FORMATS:
- for pl in (2 ** 64 + 1, 2 ** 127-1, -2**64, -2 ** 127):
+ for pl in (2**64, 2**127-1, -2**63-1, -2**127):
with self.subTest(pl=pl, fmt=fmt):
self.assertRaises(OverflowError, plistlib.dumps,
pl, fmt=fmt)
_______________________________________________
Python-bugs-list mailing list
Unsubscribe:
https://mail.python.org/mailman/options/python-bugs-list/archive%40mail-archive.com