[Python-checkins] CVS: python/dist/src/Modules mmapmodule.c,2.12,2.13
A.M. Kuchling
python-dev@python.org
Sat, 17 Jun 2000 21:45:16 -0700
Update of /cvsroot/python/python/dist/src/Modules
In directory slayer.i.sourceforge.net:/tmp/cvs-serv25421
Modified Files:
mmapmodule.c
Log Message:
Patch from Trent Mick:
The seek() method is broken for any 'whence' value (seek from
start, current, orend) other than the default. I have a patch
that fixes that as well as gets mmap'd files working on
Linux64 and Win64.
Index: mmapmodule.c
===================================================================
RCS file: /cvsroot/python/python/dist/src/Modules/mmapmodule.c,v
retrieving revision 2.12
retrieving revision 2.13
diff -C2 -r2.12 -r2.13
*** mmapmodule.c 2000/06/18 04:25:08 2.12
--- mmapmodule.c 2000/06/18 04:45:14 2.13
***************
*** 46,50 ****
#ifdef MS_WIN32
HANDLE map_handle;
! HFILE file_handle;
char * tagname;
#endif
--- 46,50 ----
#ifdef MS_WIN32
HANDLE map_handle;
! INT_PTR file_handle;
char * tagname;
#endif
***************
*** 124,128 ****
if (!PyArg_ParseTuple(args, ":read_byte"))
return NULL;
! if (self->pos >= 0 && self->pos < self->size) {
where = self->data + self->pos;
value = (char) *(where);
--- 124,128 ----
if (!PyArg_ParseTuple(args, ":read_byte"))
return NULL;
! if (self->pos < self->size) {
where = self->data + self->pos;
value = (char) *(where);
***************
*** 154,158 ****
++eol; /* we're interested in the position after the
newline. */
! result = PyString_FromStringAndSize(start, (long) (eol - start));
self->pos += (eol - start);
return (result);
--- 154,158 ----
++eol; /* we're interested in the position after the
newline. */
! result = PyString_FromStringAndSize(start, (eol - start));
self->pos += (eol - start);
return (result);
***************
*** 183,192 ****
PyObject *args)
{
! long start = self->pos;
char * needle;
int len;
CHECK_VALID(NULL);
! if (!PyArg_ParseTuple (args, "s#|l", &needle, &len, &start)) {
return NULL;
} else {
--- 183,192 ----
PyObject *args)
{
! int start = self->pos;
char * needle;
int len;
CHECK_VALID(NULL);
! if (!PyArg_ParseTuple (args, "s#|i", &needle, &len, &start)) {
return NULL;
} else {
***************
*** 201,206 ****
if (!*n) {
return Py_BuildValue (
! "l",
! (long) (p - (self->data + start)));
}
p++;
--- 201,206 ----
if (!*n) {
return Py_BuildValue (
! "i",
! (int) (p - (self->data + start)));
}
p++;
***************
*** 256,260 ****
#ifdef MS_WIN32
! if (self->file_handle != (HFILE) 0xFFFFFFFF) {
return (Py_BuildValue (
"l",
--- 256,260 ----
#ifdef MS_WIN32
! if (self->file_handle != (INT_PTR) -1) {
return (Py_BuildValue (
"l",
***************
*** 402,422 ****
mmap_seek_method (mmap_object * self, PyObject * args)
{
! /* ptrdiff_t dist; */
! long dist;
int how=0;
CHECK_VALID(NULL);
! if (!PyArg_ParseTuple (args, "l|i", &dist, &how)) {
return(NULL);
} else {
! unsigned long where;
switch (how) {
! case 0:
where = dist;
break;
! case 1:
where = self->pos + dist;
break;
! case 2:
! where = self->size - dist;
break;
default:
--- 402,427 ----
mmap_seek_method (mmap_object * self, PyObject * args)
{
! int dist;
int how=0;
CHECK_VALID(NULL);
! if (!PyArg_ParseTuple (args, "i|i", &dist, &how)) {
return(NULL);
} else {
! size_t where;
switch (how) {
! case 0: /* relative to start */
! if (dist < 0)
! goto onoutofrange;
where = dist;
break;
! case 1: /* relative to current position */
! if ((int)self->pos + dist < 0)
! goto onoutofrange;
where = self->pos + dist;
break;
! case 2: /* relative to end */
! if ((int)self->size + dist < 0)
! goto onoutofrange;
! where = self->size + dist;
break;
default:
***************
*** 425,438 ****
return NULL;
}
! if ((where >= 0) && (where < (self->size))) {
! self->pos = where;
! Py_INCREF (Py_None);
! return (Py_None);
! } else {
! PyErr_SetString (PyExc_ValueError,
! "seek out of range");
! return NULL;
! }
}
}
--- 430,443 ----
return NULL;
}
! if (where > self->size)
! goto onoutofrange;
! self->pos = where;
! Py_INCREF (Py_None);
! return (Py_None);
}
+
+ onoutofrange:
+ PyErr_SetString (PyExc_ValueError, "seek out of range");
+ return NULL;
}
***************
*** 705,708 ****
--- 710,770 ----
};
+
+ /* extract the map size from the given PyObject
+
+ The map size is restricted to [0, INT_MAX] because this is the current
+ Python limitation on object sizes. Although the mmap object *could* handle
+ a larger map size, there is no point because all the useful operations
+ (len(), slicing(), sequence indexing) are limited by a C int.
+
+ Returns -1 on error, with an apprpriate Python exception raised. On
+ success, the map size is returned. */
+ static int
+ _GetMapSize(o)
+ PyObject *o;
+ {
+ if (PyInt_Check(o)) {
+ long i = PyInt_AsLong(o);
+ if (PyErr_Occurred())
+ return -1;
+ if (i < 0)
+ goto onnegoverflow;
+ if (i > INT_MAX)
+ goto onposoverflow;
+ return (int)i;
+ }
+ else if (PyLong_Check(o)) {
+ long i = PyLong_AsLong(o);
+ if (PyErr_Occurred()) {
+ /* yes negative overflow is mistaken for positive overflow
+ but not worth the trouble to check sign of 'i' */
+ if (PyErr_ExceptionMatches(PyExc_OverflowError))
+ goto onposoverflow;
+ else
+ return -1;
+ }
+ if (i < 0)
+ goto onnegoverflow;
+ if (i > INT_MAX)
+ goto onposoverflow;
+ return (int)i;
+ }
+ else {
+ PyErr_SetString(PyExc_TypeError,
+ "map size must be an integral value");
+ return -1;
+ }
+
+ onnegoverflow:
+ PyErr_SetString(PyExc_OverflowError,
+ "memory mapped size must be positive");
+ return -1;
+
+ onposoverflow:
+ PyErr_SetString(PyExc_OverflowError,
+ "memory mapped size is too large (limited by C int)");
+ return -1;
+ }
+
#ifdef UNIX
static PyObject *
***************
*** 710,714 ****
{
mmap_object * m_obj;
! unsigned long map_size;
int fd, flags = MAP_SHARED, prot = PROT_WRITE | PROT_READ;
char * filename;
--- 772,777 ----
{
mmap_object * m_obj;
! PyObject *map_size_obj = NULL;
! int map_size;
int fd, flags = MAP_SHARED, prot = PROT_WRITE | PROT_READ;
char * filename;
***************
*** 717,725 ****
if (!PyArg_ParseTupleAndKeywords(args, kwdict,
! "il|ii", keywords,
! &fd, &map_size, &flags, &prot)
)
return NULL;
!
m_obj = PyObject_New (mmap_object, &mmap_object_type);
if (m_obj == NULL) {return NULL;}
--- 780,791 ----
if (!PyArg_ParseTupleAndKeywords(args, kwdict,
! "iO|ii", keywords,
! &fd, &map_size_obj, &flags, &prot)
)
return NULL;
! map_size = _GetMapSize(map_size_obj);
! if (map_size < 0)
! return NULL;
!
m_obj = PyObject_New (mmap_object, &mmap_object_type);
if (m_obj == NULL) {return NULL;}
***************
*** 745,754 ****
{
mmap_object * m_obj;
! unsigned long map_size;
char * tagname = "";
DWORD dwErr = 0;
int fileno;
! HFILE fh = 0;
/* Patch the object type */
--- 811,821 ----
{
mmap_object * m_obj;
! PyObject *map_size_obj = NULL;
! int map_size;
char * tagname = "";
DWORD dwErr = 0;
int fileno;
! INT_PTR fh = 0;
/* Patch the object type */
***************
*** 756,766 ****
if (!PyArg_ParseTuple(args,
! "il|z",
&fileno,
! &map_size,
&tagname)
)
return NULL;
/* if an actual filename has been specified */
if (fileno != 0) {
--- 823,837 ----
if (!PyArg_ParseTuple(args,
! "iO|z",
&fileno,
! &map_size_obj,
&tagname)
)
return NULL;
+ map_size = _GetMapSize(map_size_obj);
+ if (map_size < 0)
+ return NULL;
+
/* if an actual filename has been specified */
if (fileno != 0) {
***************
*** 785,789 ****
}
else {
! m_obj->file_handle = (HFILE) 0xFFFFFFFF;
m_obj->size = map_size;
}
--- 856,860 ----
}
else {
! m_obj->file_handle = (INT_PTR) -1;
m_obj->size = map_size;
}