[Python-checkins] r68026 - sandbox/trunk/io-c/_textio.c

amaury.forgeotdarc python-checkins at python.org
Mon Dec 29 21:32:01 CET 2008


Author: amaury.forgeotdarc
Date: Mon Dec 29 21:32:00 2008
New Revision: 68026

Log:
Try a clever implementation of the TextIOWrapper.seek() cookie.
Not used, not even tested yet.


Modified:
   sandbox/trunk/io-c/_textio.c

Modified: sandbox/trunk/io-c/_textio.c
==============================================================================
--- sandbox/trunk/io-c/_textio.c	(original)
+++ sandbox/trunk/io-c/_textio.c	Mon Dec 29 21:32:00 2008
@@ -975,6 +975,116 @@
 
 /* Seek and Tell */
 
+#if defined(MS_WIN64) || defined(MS_WINDOWS)
+typedef PY_LONG_LONG Py_off_t;
+#else
+typedef off_t Py_off_t;
+#endif
+
+typedef struct {
+    Py_off_t start_pos;
+    int dec_flags;
+    int bytes_to_feed;
+    int chars_to_skip;
+    char need_eof;
+} CookieStruct;
+
+/* Same structure as before, with fields in reversed order. Only used for
+ * offsetof().
+ *
+ * This trick allows the copy of fields between the structure and the bytes
+ * buffer, while respecting both the machine's endianness and the fact that
+ * start_pos should be the least significant part of the packed value.
+ */
+typedef struct {
+    char need_eof;
+    int chars_to_skip;
+    int bytes_to_feed;
+    int dec_flags;
+    Py_off_t start_pos;
+} _CookieStruct_LE;
+
+#define IS_LITTLE_ENDIAN (int)*(unsigned char*)&one
+
+static int
+TextIOWrapper_parseCookie(CookieStruct *cookie, PyObject *cookieObj)
+{
+    char buffer[sizeof(CookieStruct)];
+    static int one = 1;
+    PyLongObject *cookieLong = (PyLongObject *)PyNumber_Long(cookieObj);
+    if (cookieLong == NULL)
+        return -1;
+
+    if (_PyLong_AsByteArray(cookieLong, buffer, sizeof(buffer),
+                            IS_LITTLE_ENDIAN, 0) < 0) {
+        Py_DECREF(cookieLong);
+        return -1;
+    }
+    Py_DECREF(cookieLong);
+
+    if (!IS_LITTLE_ENDIAN) {
+        cookie->start_pos     = *(Py_off_t*)(buffer +
+                                             offsetof(CookieStruct, start_pos));
+        cookie->dec_flags     = *(int*)     (buffer +
+                                             offsetof(CookieStruct, dec_flags));
+        cookie->bytes_to_feed = *(int*)     (buffer +
+                                             offsetof(CookieStruct, bytes_to_feed));
+        cookie->chars_to_skip = *(int*)     (buffer +
+                                             offsetof(CookieStruct, chars_to_skip));
+        cookie->need_eof      = *(char*)    (buffer +
+                                             offsetof(CookieStruct, need_eof));
+    }
+    else {
+        cookie->start_pos     = *(Py_off_t*)(buffer +
+                                             offsetof(_CookieStruct_LE, start_pos));
+        cookie->dec_flags     = *(int*)     (buffer +
+                                             offsetof(_CookieStruct_LE, dec_flags));
+        cookie->bytes_to_feed = *(int*)     (buffer +
+                                             offsetof(_CookieStruct_LE, bytes_to_feed));
+        cookie->chars_to_skip = *(int*)     (buffer +
+                                             offsetof(_CookieStruct_LE, chars_to_skip));
+        cookie->need_eof      = *(char*)    (buffer +
+                                             offsetof(_CookieStruct_LE, need_eof));
+    }
+
+    return 0;
+}
+
+static int
+TextIOWrapper_buildCookie(CookieStruct *cookie, PyObject *cookieObj)
+{
+    char buffer[sizeof(CookieStruct)];
+    static int one = 1;
+
+    if (!IS_LITTLE_ENDIAN) {
+        *(Py_off_t*)(buffer +
+                     offsetof(CookieStruct, start_pos))     = cookie->start_pos;
+        *(int*)     (buffer +
+                     offsetof(CookieStruct, dec_flags))     = cookie->dec_flags;
+        *(int*)     (buffer +
+                     offsetof(CookieStruct, bytes_to_feed)) = cookie->bytes_to_feed;
+        *(int*)     (buffer +
+                     offsetof(CookieStruct, chars_to_skip)) = cookie->chars_to_skip;
+        *(char*)    (buffer +
+                     offsetof(CookieStruct, need_eof))      = cookie->need_eof;
+    }
+    else {
+        *(Py_off_t*)(buffer +
+                     offsetof(_CookieStruct_LE, start_pos))     = cookie->start_pos;
+        *(int*)     (buffer +
+                     offsetof(_CookieStruct_LE, dec_flags))     = cookie->dec_flags;
+        *(int*)     (buffer +
+                     offsetof(_CookieStruct_LE, bytes_to_feed)) = cookie->bytes_to_feed;
+        *(int*)     (buffer +
+                     offsetof(_CookieStruct_LE, chars_to_skip)) = cookie->chars_to_skip;
+        *(char*)    (buffer +
+                     offsetof(_CookieStruct_LE, need_eof))      = cookie->need_eof;
+    }
+
+    return _PyLong_FromByteArray(buffer, sizeof(buffer), IS_LITTLE_ENDIAN, 0);
+}
+#undef IS_LITTLE_ENDIAN
+
 static PyObject *
 TextIOWrapper_seek(PyTextIOWrapperObject *self, PyObject *args)
 {


More information about the Python-checkins mailing list