blob: 302d7dd4b311a254505949eb9a538611de237203 [file] [log] [blame]
Guido van Rossumea3375d2001-01-09 21:46:50 +00001#include "Python.h"
2
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00003PyDoc_STRVAR(xreadlines_doc,
Guido van Rossumea3375d2001-01-09 21:46:50 +00004"xreadlines(f)\n\
5\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00006Return an xreadlines object for the file f.");
Guido van Rossumea3375d2001-01-09 21:46:50 +00007
8typedef struct {
9 PyObject_HEAD
10 PyObject *file;
11 PyObject *lines;
12 int lineslen;
13 int lineno;
14 int abslineno;
15} PyXReadlinesObject;
16
Jeremy Hylton938ace62002-07-17 16:30:39 +000017static PyTypeObject XReadlinesObject_Type;
Guido van Rossumea3375d2001-01-09 21:46:50 +000018
19static void
Thomas Wouters9fdcf4a2001-01-11 15:40:39 +000020xreadlines_dealloc(PyXReadlinesObject *op)
21{
Guido van Rossumea3375d2001-01-09 21:46:50 +000022 Py_XDECREF(op->file);
23 Py_XDECREF(op->lines);
24 PyObject_DEL(op);
25}
26
27/* A larger chunk size doesn't seem to make a difference */
28#define CHUNKSIZE 8192
29
30static PyXReadlinesObject *
Thomas Wouters9fdcf4a2001-01-11 15:40:39 +000031newreadlinesobject(PyObject *file)
32{
Guido van Rossumea3375d2001-01-09 21:46:50 +000033 PyXReadlinesObject *op;
34 op = PyObject_NEW(PyXReadlinesObject, &XReadlinesObject_Type);
35 if (op == NULL)
36 return NULL;
37 Py_XINCREF(file);
38 op->file = file;
39 op->lines = NULL;
40 op->abslineno = op->lineno = op->lineslen = 0;
41 return op;
42}
43
44static PyObject *
Thomas Wouters9fdcf4a2001-01-11 15:40:39 +000045xreadlines(PyObject *self, PyObject *args)
46{
Guido van Rossumea3375d2001-01-09 21:46:50 +000047 PyObject *file;
48 PyXReadlinesObject *ret;
49
50 if (!PyArg_ParseTuple(args, "O:xreadlines", &file))
51 return NULL;
52 ret = newreadlinesobject(file);
Guido van Rossumea3375d2001-01-09 21:46:50 +000053 return (PyObject*)ret;
54}
55
Thomas Wouters9fdcf4a2001-01-11 15:40:39 +000056static PyObject *
Guido van Rossumc8555b32001-05-22 16:41:32 +000057xreadlines_common(PyXReadlinesObject *a)
Thomas Wouters9fdcf4a2001-01-11 15:40:39 +000058{
Guido van Rossumea3375d2001-01-09 21:46:50 +000059 if (a->lineno >= a->lineslen) {
60 Py_XDECREF(a->lines);
61 a->lines = PyObject_CallMethod(a->file, "readlines", "(i)",
62 CHUNKSIZE);
63 if (a->lines == NULL)
64 return NULL;
65 a->lineno = 0;
66 if ((a->lineslen = PySequence_Size(a->lines)) < 0)
67 return NULL;
68 }
69 a->abslineno++;
70 return PySequence_GetItem(a->lines, a->lineno++);
71}
72
Guido van Rossumc8555b32001-05-22 16:41:32 +000073static PyObject *
74xreadlines_item(PyXReadlinesObject *a, int i)
75{
76 if (i != a->abslineno) {
77 PyErr_SetString(PyExc_RuntimeError,
78 "xreadlines object accessed out of order");
79 return NULL;
80 }
81 return xreadlines_common(a);
82}
83
84static PyObject *
Guido van Rossumc8555b32001-05-22 16:41:32 +000085xreadlines_iternext(PyXReadlinesObject *a)
86{
87 PyObject *res;
88
89 res = xreadlines_common(a);
90 if (res == NULL && PyErr_ExceptionMatches(PyExc_IndexError))
91 PyErr_Clear();
92 return res;
93}
94
95static PyObject *
96xreadlines_next(PyXReadlinesObject *a, PyObject *args)
97{
98 PyObject *res;
99
100 if (!PyArg_ParseTuple(args, ""))
101 return NULL;
102 res = xreadlines_common(a);
103 if (res == NULL && PyErr_ExceptionMatches(PyExc_IndexError))
104 PyErr_SetObject(PyExc_StopIteration, Py_None);
105 return res;
106}
107
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000108PyDoc_STRVAR(next_doc, "x.next() -> the next line or raise StopIteration");
Guido van Rossumc8555b32001-05-22 16:41:32 +0000109
110static PyMethodDef xreadlines_methods[] = {
111 {"next", (PyCFunction)xreadlines_next, METH_VARARGS, next_doc},
112 {NULL, NULL}
113};
114
115static PyObject *
116xreadlines_getattr(PyObject *a, char *name)
117{
118 return Py_FindMethod(xreadlines_methods, a, name);
119}
120
Guido van Rossumea3375d2001-01-09 21:46:50 +0000121static PySequenceMethods xreadlines_as_sequence = {
122 0, /*sq_length*/
123 0, /*sq_concat*/
124 0, /*sq_repeat*/
125 (intargfunc)xreadlines_item, /*sq_item*/
126};
127
128static PyTypeObject XReadlinesObject_Type = {
Guido van Rossum7150a772001-01-19 00:29:06 +0000129 PyObject_HEAD_INIT(NULL)
Guido van Rossumea3375d2001-01-09 21:46:50 +0000130 0,
Guido van Rossum14648392001-12-08 18:02:58 +0000131 "xreadlines.xreadlines",
Neil Schemenauer01b66a82001-08-29 23:50:42 +0000132 sizeof(PyXReadlinesObject),
Guido van Rossumea3375d2001-01-09 21:46:50 +0000133 0,
Guido van Rossumc8555b32001-05-22 16:41:32 +0000134 (destructor)xreadlines_dealloc, /* tp_dealloc */
135 0, /* tp_print */
136 xreadlines_getattr, /* tp_getattr */
137 0, /* tp_setattr */
138 0, /* tp_compare */
139 0, /* tp_repr */
140 0, /* tp_as_number */
141 &xreadlines_as_sequence, /* tp_as_sequence */
142 0, /* tp_as_mapping */
143 0, /* tp_hash */
144 0, /* tp_call */
145 0, /* tp_str */
146 0, /* tp_getattro */
147 0, /* tp_setattro */
148 0, /* tp_as_buffer */
149 Py_TPFLAGS_DEFAULT, /* tp_flags */
150 0, /* tp_doc */
151 0, /* tp_traverse */
152 0, /* tp_clear */
153 0, /* tp_richcompare */
154 0, /* tp_weaklistoffset */
Raymond Hettinger1da1dbf2003-03-17 19:46:11 +0000155 PyObject_SelfIter, /* tp_iter */
Guido van Rossumc8555b32001-05-22 16:41:32 +0000156 (iternextfunc)xreadlines_iternext, /* tp_iternext */
Guido van Rossumea3375d2001-01-09 21:46:50 +0000157};
158
Guido van Rossumc8555b32001-05-22 16:41:32 +0000159static PyMethodDef xreadlines_functions[] = {
Guido van Rossumea3375d2001-01-09 21:46:50 +0000160 {"xreadlines", xreadlines, METH_VARARGS, xreadlines_doc},
161 {NULL, NULL}
162};
163
Mark Hammondfe51c6d2002-08-02 02:27:13 +0000164PyMODINIT_FUNC
Guido van Rossumea3375d2001-01-09 21:46:50 +0000165initxreadlines(void)
166{
Guido van Rossum7150a772001-01-19 00:29:06 +0000167 XReadlinesObject_Type.ob_type = &PyType_Type;
Fred Drakedff3a372001-07-19 21:29:49 +0000168 Py_InitModule("xreadlines", xreadlines_functions);
Guido van Rossum8ee52432002-08-06 17:14:04 +0000169 PyErr_Warn(PyExc_DeprecationWarning,
170 "xreadlines is deprecated; use 'for line in file'.");
Guido van Rossumea3375d2001-01-09 21:46:50 +0000171}