blob: 55a0dce0df9013e8a92c9c395b164001060bc231 [file] [log] [blame]
Guido van Rossum778983b1993-02-19 15:55:02 +00001/***********************************************************
Guido van Rossumfd71b9e2000-06-30 23:50:40 +00002Copyright (c) 2000, BeOpen.com.
3Copyright (c) 1995-2000, Corporation for National Research Initiatives.
4Copyright (c) 1990-1995, Stichting Mathematisch Centrum.
5All rights reserved.
Guido van Rossum778983b1993-02-19 15:55:02 +00006
Guido van Rossumfd71b9e2000-06-30 23:50:40 +00007See the file "Misc/COPYRIGHT" for information on usage and
8redistribution of this file, and for a DISCLAIMER OF ALL WARRANTIES.
Guido van Rossum778983b1993-02-19 15:55:02 +00009******************************************************************/
10
11/* Array object implementation */
12
13/* An array is a uniform list -- all items have the same type.
14 The item type is restricted to simple C types like int or float */
15
Roger E. Masse2919eaa1996-12-09 20:10:36 +000016#include "Python.h"
Roger E. Masse5817f8f1996-12-09 22:24:19 +000017
Guido van Rossum0c709541994-08-19 12:01:32 +000018#ifdef STDC_HEADERS
19#include <stddef.h>
Guido van Rossum7f1de831999-08-27 20:33:52 +000020#else /* !STDC_HEADERS */
21#ifndef DONT_HAVE_SYS_TYPES_H
Guido van Rossumb6775db1994-08-01 11:34:53 +000022#include <sys/types.h> /* For size_t */
Guido van Rossum7f1de831999-08-27 20:33:52 +000023#endif /* DONT_HAVE_SYS_TYPES_H */
24#endif /* !STDC_HEADERS */
Guido van Rossumdb677392000-07-01 01:09:43 +000025#ifdef HAVE_LIMITS_H
26#include <limits.h>
27#endif /* HAVE_LIMITS_H */
Guido van Rossum778983b1993-02-19 15:55:02 +000028
29struct arrayobject; /* Forward */
30
31struct arraydescr {
32 int typecode;
33 int itemsize;
Tim Petersdbd9ba62000-07-09 03:09:57 +000034 PyObject * (*getitem)(struct arrayobject *, int);
35 int (*setitem)(struct arrayobject *, int, PyObject *);
Guido van Rossum778983b1993-02-19 15:55:02 +000036};
37
38typedef struct arrayobject {
Roger E. Masse2919eaa1996-12-09 20:10:36 +000039 PyObject_VAR_HEAD
Guido van Rossum778983b1993-02-19 15:55:02 +000040 char *ob_item;
41 struct arraydescr *ob_descr;
42} arrayobject;
43
Roger E. Masse2919eaa1996-12-09 20:10:36 +000044staticforward PyTypeObject Arraytype;
Guido van Rossum778983b1993-02-19 15:55:02 +000045
46#define is_arrayobject(op) ((op)->ob_type == &Arraytype)
47
Guido van Rossumb73cc041993-11-01 16:28:59 +000048/* Forward */
Tim Petersdbd9ba62000-07-09 03:09:57 +000049static PyObject *newarrayobject(int, struct arraydescr *);
Guido van Rossuma376cc51996-12-05 23:43:35 +000050#if 0
Tim Petersdbd9ba62000-07-09 03:09:57 +000051static int getarraysize(PyObject *);
Guido van Rossuma376cc51996-12-05 23:43:35 +000052#endif
Tim Petersdbd9ba62000-07-09 03:09:57 +000053static PyObject *getarrayitem(PyObject *, int);
54static int setarrayitem(PyObject *, int, PyObject *);
Guido van Rossuma376cc51996-12-05 23:43:35 +000055#if 0
Tim Petersdbd9ba62000-07-09 03:09:57 +000056static int insarrayitem(PyObject *, int, PyObject *);
57static int addarrayitem(PyObject *, PyObject *);
Guido van Rossuma376cc51996-12-05 23:43:35 +000058#endif
Guido van Rossum778983b1993-02-19 15:55:02 +000059
Roger E. Masse2919eaa1996-12-09 20:10:36 +000060static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +000061c_getitem(arrayobject *ap, int i)
Guido van Rossum778983b1993-02-19 15:55:02 +000062{
Roger E. Masse2919eaa1996-12-09 20:10:36 +000063 return PyString_FromStringAndSize(&((char *)ap->ob_item)[i], 1);
Guido van Rossum778983b1993-02-19 15:55:02 +000064}
65
66static int
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +000067c_setitem(arrayobject *ap, int i, PyObject *v)
Guido van Rossum778983b1993-02-19 15:55:02 +000068{
69 char x;
Roger E. Masse2919eaa1996-12-09 20:10:36 +000070 if (!PyArg_Parse(v, "c;array item must be char", &x))
Guido van Rossum778983b1993-02-19 15:55:02 +000071 return -1;
72 if (i >= 0)
73 ((char *)ap->ob_item)[i] = x;
74 return 0;
75}
76
Roger E. Masse2919eaa1996-12-09 20:10:36 +000077static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +000078b_getitem(arrayobject *ap, int i)
Guido van Rossum778983b1993-02-19 15:55:02 +000079{
80 long x = ((char *)ap->ob_item)[i];
81 if (x >= 128)
82 x -= 256;
Roger E. Masse2919eaa1996-12-09 20:10:36 +000083 return PyInt_FromLong(x);
Guido van Rossum778983b1993-02-19 15:55:02 +000084}
85
86static int
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +000087b_setitem(arrayobject *ap, int i, PyObject *v)
Guido van Rossum778983b1993-02-19 15:55:02 +000088{
Fred Drake541dc3b2000-06-28 17:49:30 +000089 short x;
90 /* PyArg_Parse's 'b' formatter is for an unsigned char, therefore
91 must use the next size up that is signed ('h') and manually do
92 the overflow checking */
93 if (!PyArg_Parse(v, "h;array item must be integer", &x))
Guido van Rossum778983b1993-02-19 15:55:02 +000094 return -1;
Guido van Rossum9f754e02000-07-01 00:38:19 +000095 else if (x < -128) {
Fred Drake541dc3b2000-06-28 17:49:30 +000096 PyErr_SetString(PyExc_OverflowError,
97 "signed char is less than minimum");
98 return -1;
99 }
Guido van Rossum9f754e02000-07-01 00:38:19 +0000100 else if (x > 127) {
Fred Drake541dc3b2000-06-28 17:49:30 +0000101 PyErr_SetString(PyExc_OverflowError,
102 "signed char is greater than maximum");
103 return -1;
104 }
Guido van Rossum778983b1993-02-19 15:55:02 +0000105 if (i >= 0)
Fred Drake541dc3b2000-06-28 17:49:30 +0000106 ((char *)ap->ob_item)[i] = (char)x;
Guido van Rossum778983b1993-02-19 15:55:02 +0000107 return 0;
108}
109
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000110static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000111BB_getitem(arrayobject *ap, int i)
Guido van Rossum549ab711997-01-03 19:09:47 +0000112{
113 long x = ((unsigned char *)ap->ob_item)[i];
114 return PyInt_FromLong(x);
115}
116
Fred Drake541dc3b2000-06-28 17:49:30 +0000117static int
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000118BB_setitem(arrayobject *ap, int i, PyObject *v)
Fred Drake541dc3b2000-06-28 17:49:30 +0000119{
120 unsigned char x;
121 /* 'B' == unsigned char, maps to PyArg_Parse's 'b' formatter */
122 if (!PyArg_Parse(v, "b;array item must be integer", &x))
123 return -1;
124 if (i >= 0)
125 ((char *)ap->ob_item)[i] = x;
126 return 0;
127}
Guido van Rossum549ab711997-01-03 19:09:47 +0000128
129static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000130h_getitem(arrayobject *ap, int i)
Guido van Rossum778983b1993-02-19 15:55:02 +0000131{
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000132 return PyInt_FromLong((long) ((short *)ap->ob_item)[i]);
Guido van Rossum778983b1993-02-19 15:55:02 +0000133}
134
135static int
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000136h_setitem(arrayobject *ap, int i, PyObject *v)
Guido van Rossum778983b1993-02-19 15:55:02 +0000137{
138 short x;
Fred Drake541dc3b2000-06-28 17:49:30 +0000139 /* 'h' == signed short, maps to PyArg_Parse's 'h' formatter */
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000140 if (!PyArg_Parse(v, "h;array item must be integer", &x))
Guido van Rossum778983b1993-02-19 15:55:02 +0000141 return -1;
142 if (i >= 0)
143 ((short *)ap->ob_item)[i] = x;
144 return 0;
145}
146
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000147static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000148HH_getitem(arrayobject *ap, int i)
Guido van Rossum549ab711997-01-03 19:09:47 +0000149{
150 return PyInt_FromLong((long) ((unsigned short *)ap->ob_item)[i]);
151}
152
Fred Drake541dc3b2000-06-28 17:49:30 +0000153static int
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000154HH_setitem(arrayobject *ap, int i, PyObject *v)
Fred Drake541dc3b2000-06-28 17:49:30 +0000155{
156 int x;
157 /* PyArg_Parse's 'h' formatter is for a signed short, therefore
158 must use the next size up and manually do the overflow checking */
159 if (!PyArg_Parse(v, "i;array item must be integer", &x))
160 return -1;
161 else if (x < 0) {
162 PyErr_SetString(PyExc_OverflowError,
163 "unsigned short is less than minimum");
164 return -1;
165 }
166 else if (x > USHRT_MAX) {
167 PyErr_SetString(PyExc_OverflowError,
168 "unsigned short is greater than maximum");
169 return -1;
170 }
171 if (i >= 0)
172 ((short *)ap->ob_item)[i] = (short)x;
173 return 0;
174}
Guido van Rossum549ab711997-01-03 19:09:47 +0000175
176static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000177i_getitem(arrayobject *ap, int i)
Guido van Rossume77a7571993-11-03 15:01:26 +0000178{
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000179 return PyInt_FromLong((long) ((int *)ap->ob_item)[i]);
Guido van Rossume77a7571993-11-03 15:01:26 +0000180}
181
182static int
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000183i_setitem(arrayobject *ap, int i, PyObject *v)
Guido van Rossume77a7571993-11-03 15:01:26 +0000184{
185 int x;
Fred Drake541dc3b2000-06-28 17:49:30 +0000186 /* 'i' == signed int, maps to PyArg_Parse's 'i' formatter */
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000187 if (!PyArg_Parse(v, "i;array item must be integer", &x))
Guido van Rossume77a7571993-11-03 15:01:26 +0000188 return -1;
189 if (i >= 0)
190 ((int *)ap->ob_item)[i] = x;
191 return 0;
192}
193
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000194static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000195II_getitem(arrayobject *ap, int i)
Guido van Rossum549ab711997-01-03 19:09:47 +0000196{
197 return PyLong_FromUnsignedLong(
198 (unsigned long) ((unsigned int *)ap->ob_item)[i]);
199}
200
201static int
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000202II_setitem(arrayobject *ap, int i, PyObject *v)
Guido van Rossum549ab711997-01-03 19:09:47 +0000203{
204 unsigned long x;
205 if (PyLong_Check(v)) {
206 x = PyLong_AsUnsignedLong(v);
207 if (x == (unsigned long) -1 && PyErr_Occurred())
208 return -1;
209 }
210 else {
Fred Drake541dc3b2000-06-28 17:49:30 +0000211 long y;
212 if (!PyArg_Parse(v, "l;array item must be integer", &y))
Guido van Rossum549ab711997-01-03 19:09:47 +0000213 return -1;
Fred Drake541dc3b2000-06-28 17:49:30 +0000214 if (y < 0) {
215 PyErr_SetString(PyExc_OverflowError,
216 "unsigned int is less than minimum");
217 return -1;
218 }
219 x = (unsigned long)y;
220
Guido van Rossum549ab711997-01-03 19:09:47 +0000221 }
Fred Drake541dc3b2000-06-28 17:49:30 +0000222 if (x > UINT_MAX) {
223 PyErr_SetString(PyExc_OverflowError,
224 "unsigned int is greater than maximum");
225 return -1;
226 }
227
Guido van Rossum549ab711997-01-03 19:09:47 +0000228 if (i >= 0)
Fred Drake541dc3b2000-06-28 17:49:30 +0000229 ((unsigned int *)ap->ob_item)[i] = (unsigned int)x;
Guido van Rossum549ab711997-01-03 19:09:47 +0000230 return 0;
231}
232
233static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000234l_getitem(arrayobject *ap, int i)
Guido van Rossum778983b1993-02-19 15:55:02 +0000235{
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000236 return PyInt_FromLong(((long *)ap->ob_item)[i]);
Guido van Rossum778983b1993-02-19 15:55:02 +0000237}
238
239static int
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000240l_setitem(arrayobject *ap, int i, PyObject *v)
Guido van Rossum778983b1993-02-19 15:55:02 +0000241{
242 long x;
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000243 if (!PyArg_Parse(v, "l;array item must be integer", &x))
Guido van Rossum778983b1993-02-19 15:55:02 +0000244 return -1;
245 if (i >= 0)
246 ((long *)ap->ob_item)[i] = x;
247 return 0;
248}
249
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000250static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000251LL_getitem(arrayobject *ap, int i)
Guido van Rossum549ab711997-01-03 19:09:47 +0000252{
253 return PyLong_FromUnsignedLong(((unsigned long *)ap->ob_item)[i]);
254}
255
256static int
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000257LL_setitem(arrayobject *ap, int i, PyObject *v)
Guido van Rossum549ab711997-01-03 19:09:47 +0000258{
259 unsigned long x;
260 if (PyLong_Check(v)) {
261 x = PyLong_AsUnsignedLong(v);
262 if (x == (unsigned long) -1 && PyErr_Occurred())
263 return -1;
264 }
265 else {
Fred Drake541dc3b2000-06-28 17:49:30 +0000266 long y;
267 if (!PyArg_Parse(v, "l;array item must be integer", &y))
Guido van Rossum549ab711997-01-03 19:09:47 +0000268 return -1;
Fred Drake541dc3b2000-06-28 17:49:30 +0000269 if (y < 0) {
270 PyErr_SetString(PyExc_OverflowError,
271 "unsigned long is less than minimum");
272 return -1;
273 }
274 x = (unsigned long)y;
275
Guido van Rossum549ab711997-01-03 19:09:47 +0000276 }
Fred Drake541dc3b2000-06-28 17:49:30 +0000277 if (x > ULONG_MAX) {
278 PyErr_SetString(PyExc_OverflowError,
279 "unsigned long is greater than maximum");
280 return -1;
281 }
282
Guido van Rossum549ab711997-01-03 19:09:47 +0000283 if (i >= 0)
284 ((unsigned long *)ap->ob_item)[i] = x;
285 return 0;
286}
287
288static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000289f_getitem(arrayobject *ap, int i)
Guido van Rossum778983b1993-02-19 15:55:02 +0000290{
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000291 return PyFloat_FromDouble((double) ((float *)ap->ob_item)[i]);
Guido van Rossum778983b1993-02-19 15:55:02 +0000292}
293
294static int
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000295f_setitem(arrayobject *ap, int i, PyObject *v)
Guido van Rossum778983b1993-02-19 15:55:02 +0000296{
297 float x;
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000298 if (!PyArg_Parse(v, "f;array item must be float", &x))
Guido van Rossum778983b1993-02-19 15:55:02 +0000299 return -1;
300 if (i >= 0)
301 ((float *)ap->ob_item)[i] = x;
302 return 0;
303}
304
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000305static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000306d_getitem(arrayobject *ap, int i)
Guido van Rossum778983b1993-02-19 15:55:02 +0000307{
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000308 return PyFloat_FromDouble(((double *)ap->ob_item)[i]);
Guido van Rossum778983b1993-02-19 15:55:02 +0000309}
310
311static int
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000312d_setitem(arrayobject *ap, int i, PyObject *v)
Guido van Rossum778983b1993-02-19 15:55:02 +0000313{
314 double x;
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000315 if (!PyArg_Parse(v, "d;array item must be float", &x))
Guido van Rossum778983b1993-02-19 15:55:02 +0000316 return -1;
317 if (i >= 0)
318 ((double *)ap->ob_item)[i] = x;
319 return 0;
320}
321
322/* Description of types */
Guido van Rossum234f9421993-06-17 12:35:49 +0000323static struct arraydescr descriptors[] = {
Guido van Rossum778983b1993-02-19 15:55:02 +0000324 {'c', sizeof(char), c_getitem, c_setitem},
325 {'b', sizeof(char), b_getitem, b_setitem},
Guido van Rossum1a747f81997-05-16 16:21:38 +0000326 {'B', sizeof(char), BB_getitem, BB_setitem},
Guido van Rossum778983b1993-02-19 15:55:02 +0000327 {'h', sizeof(short), h_getitem, h_setitem},
Guido van Rossum1a747f81997-05-16 16:21:38 +0000328 {'H', sizeof(short), HH_getitem, HH_setitem},
Guido van Rossume77a7571993-11-03 15:01:26 +0000329 {'i', sizeof(int), i_getitem, i_setitem},
Guido van Rossum1a747f81997-05-16 16:21:38 +0000330 {'I', sizeof(int), II_getitem, II_setitem},
Guido van Rossum778983b1993-02-19 15:55:02 +0000331 {'l', sizeof(long), l_getitem, l_setitem},
Guido van Rossum1a747f81997-05-16 16:21:38 +0000332 {'L', sizeof(long), LL_getitem, LL_setitem},
Guido van Rossum778983b1993-02-19 15:55:02 +0000333 {'f', sizeof(float), f_getitem, f_setitem},
334 {'d', sizeof(double), d_getitem, d_setitem},
335 {'\0', 0, 0, 0} /* Sentinel */
336};
Guido van Rossume77a7571993-11-03 15:01:26 +0000337/* If we ever allow items larger than double, we must change reverse()! */
Guido van Rossum778983b1993-02-19 15:55:02 +0000338
339
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000340static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000341newarrayobject(int size, struct arraydescr *descr)
Guido van Rossum778983b1993-02-19 15:55:02 +0000342{
Guido van Rossum778983b1993-02-19 15:55:02 +0000343 arrayobject *op;
Guido van Rossumb6775db1994-08-01 11:34:53 +0000344 size_t nbytes;
Guido van Rossum778983b1993-02-19 15:55:02 +0000345 if (size < 0) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000346 PyErr_BadInternalCall();
Guido van Rossum778983b1993-02-19 15:55:02 +0000347 return NULL;
348 }
349 nbytes = size * descr->itemsize;
350 /* Check for overflow */
Guido van Rossum7844e381997-04-11 20:44:04 +0000351 if (nbytes / descr->itemsize != (size_t)size) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000352 return PyErr_NoMemory();
Guido van Rossum778983b1993-02-19 15:55:02 +0000353 }
Guido van Rossumb18618d2000-05-03 23:44:39 +0000354 op = PyObject_NewVar(arrayobject, &Arraytype, size);
Guido van Rossum778983b1993-02-19 15:55:02 +0000355 if (op == NULL) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000356 return PyErr_NoMemory();
Guido van Rossum778983b1993-02-19 15:55:02 +0000357 }
358 if (size <= 0) {
359 op->ob_item = NULL;
360 }
361 else {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000362 op->ob_item = PyMem_NEW(char, nbytes);
Guido van Rossum778983b1993-02-19 15:55:02 +0000363 if (op->ob_item == NULL) {
Guido van Rossumb18618d2000-05-03 23:44:39 +0000364 PyObject_Del(op);
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000365 return PyErr_NoMemory();
Guido van Rossum778983b1993-02-19 15:55:02 +0000366 }
367 }
Guido van Rossum778983b1993-02-19 15:55:02 +0000368 op->ob_descr = descr;
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000369 return (PyObject *) op;
Guido van Rossum778983b1993-02-19 15:55:02 +0000370}
371
Guido van Rossuma376cc51996-12-05 23:43:35 +0000372#if 0
Guido van Rossum62de97f1995-01-22 00:48:41 +0000373static int
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000374getarraysize(PyObject *op)
Guido van Rossum778983b1993-02-19 15:55:02 +0000375{
376 if (!is_arrayobject(op)) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000377 PyErr_BadInternalCall();
Guido van Rossum778983b1993-02-19 15:55:02 +0000378 return -1;
379 }
380 return ((arrayobject *)op) -> ob_size;
381}
Guido van Rossuma376cc51996-12-05 23:43:35 +0000382#endif
Guido van Rossum778983b1993-02-19 15:55:02 +0000383
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000384static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000385getarrayitem(PyObject *op, int i)
Guido van Rossum778983b1993-02-19 15:55:02 +0000386{
387 register arrayobject *ap;
388 if (!is_arrayobject(op)) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000389 PyErr_BadInternalCall();
Guido van Rossum778983b1993-02-19 15:55:02 +0000390 return NULL;
391 }
392 ap = (arrayobject *)op;
393 if (i < 0 || i >= ap->ob_size) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000394 PyErr_SetString(PyExc_IndexError, "array index out of range");
Guido van Rossum778983b1993-02-19 15:55:02 +0000395 return NULL;
396 }
397 return (*ap->ob_descr->getitem)(ap, i);
398}
399
400static int
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000401ins1(arrayobject *self, int where, PyObject *v)
Guido van Rossum778983b1993-02-19 15:55:02 +0000402{
Guido van Rossum778983b1993-02-19 15:55:02 +0000403 char *items;
404 if (v == NULL) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000405 PyErr_BadInternalCall();
Guido van Rossum778983b1993-02-19 15:55:02 +0000406 return -1;
407 }
408 if ((*self->ob_descr->setitem)(self, -1, v) < 0)
409 return -1;
410 items = self->ob_item;
Roger E. Masse5817f8f1996-12-09 22:24:19 +0000411 PyMem_RESIZE(items, char,
412 (self->ob_size+1) * self->ob_descr->itemsize);
Guido van Rossum778983b1993-02-19 15:55:02 +0000413 if (items == NULL) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000414 PyErr_NoMemory();
Guido van Rossum778983b1993-02-19 15:55:02 +0000415 return -1;
416 }
417 if (where < 0)
418 where = 0;
419 if (where > self->ob_size)
420 where = self->ob_size;
421 memmove(items + (where+1)*self->ob_descr->itemsize,
422 items + where*self->ob_descr->itemsize,
423 (self->ob_size-where)*self->ob_descr->itemsize);
424 self->ob_item = items;
425 self->ob_size++;
426 return (*self->ob_descr->setitem)(self, where, v);
427}
428
Guido van Rossuma376cc51996-12-05 23:43:35 +0000429#if 0
Guido van Rossum62de97f1995-01-22 00:48:41 +0000430static int
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000431insarrayitem(PyObject *op, int where, PyObject *newitem)
Guido van Rossum778983b1993-02-19 15:55:02 +0000432{
433 if (!is_arrayobject(op)) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000434 PyErr_BadInternalCall();
Guido van Rossum778983b1993-02-19 15:55:02 +0000435 return -1;
436 }
437 return ins1((arrayobject *)op, where, newitem);
438}
439
Guido van Rossum62de97f1995-01-22 00:48:41 +0000440static int
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000441addarrayitem(PyObject *op, PyObject *newitem)
Guido van Rossum778983b1993-02-19 15:55:02 +0000442{
443 if (!is_arrayobject(op)) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000444 PyErr_BadInternalCall();
Guido van Rossum778983b1993-02-19 15:55:02 +0000445 return -1;
446 }
447 return ins1((arrayobject *)op,
448 (int) ((arrayobject *)op)->ob_size, newitem);
449}
Guido van Rossuma376cc51996-12-05 23:43:35 +0000450#endif
Guido van Rossum778983b1993-02-19 15:55:02 +0000451
452/* Methods */
453
454static void
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000455array_dealloc(arrayobject *op)
Guido van Rossum778983b1993-02-19 15:55:02 +0000456{
Guido van Rossum778983b1993-02-19 15:55:02 +0000457 if (op->ob_item != NULL)
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000458 PyMem_DEL(op->ob_item);
Guido van Rossumb18618d2000-05-03 23:44:39 +0000459 PyObject_Del(op);
Guido van Rossum778983b1993-02-19 15:55:02 +0000460}
461
462static int
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000463array_compare(arrayobject *v, arrayobject *w)
Guido van Rossum778983b1993-02-19 15:55:02 +0000464{
465 int len = (v->ob_size < w->ob_size) ? v->ob_size : w->ob_size;
466 int i;
467 for (i = 0; i < len; i++) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000468 PyObject *ai, *bi;
Guido van Rossum778983b1993-02-19 15:55:02 +0000469 int cmp;
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000470 ai = getarrayitem((PyObject *)v, i);
471 bi = getarrayitem((PyObject *)w, i);
Guido van Rossum778983b1993-02-19 15:55:02 +0000472 if (ai && bi)
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000473 cmp = PyObject_Compare(ai, bi);
Guido van Rossum778983b1993-02-19 15:55:02 +0000474 else
475 cmp = -1;
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000476 Py_XDECREF(ai);
477 Py_XDECREF(bi);
Guido van Rossumc8b6df91997-05-23 00:06:51 +0000478 if (cmp != 0)
Guido van Rossum778983b1993-02-19 15:55:02 +0000479 return cmp;
Guido van Rossum778983b1993-02-19 15:55:02 +0000480 }
481 return v->ob_size - w->ob_size;
482}
483
484static int
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000485array_length(arrayobject *a)
Guido van Rossum778983b1993-02-19 15:55:02 +0000486{
487 return a->ob_size;
488}
489
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000490static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000491array_item(arrayobject *a, int i)
Guido van Rossum778983b1993-02-19 15:55:02 +0000492{
493 if (i < 0 || i >= a->ob_size) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000494 PyErr_SetString(PyExc_IndexError, "array index out of range");
Guido van Rossum778983b1993-02-19 15:55:02 +0000495 return NULL;
496 }
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000497 return getarrayitem((PyObject *)a, i);
Guido van Rossum778983b1993-02-19 15:55:02 +0000498}
499
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000500static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000501array_slice(arrayobject *a, int ilow, int ihigh)
Guido van Rossum778983b1993-02-19 15:55:02 +0000502{
503 arrayobject *np;
Guido van Rossum778983b1993-02-19 15:55:02 +0000504 if (ilow < 0)
505 ilow = 0;
506 else if (ilow > a->ob_size)
507 ilow = a->ob_size;
508 if (ihigh < 0)
509 ihigh = 0;
510 if (ihigh < ilow)
511 ihigh = ilow;
512 else if (ihigh > a->ob_size)
513 ihigh = a->ob_size;
514 np = (arrayobject *) newarrayobject(ihigh - ilow, a->ob_descr);
515 if (np == NULL)
516 return NULL;
517 memcpy(np->ob_item, a->ob_item + ilow * a->ob_descr->itemsize,
518 (ihigh-ilow) * a->ob_descr->itemsize);
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000519 return (PyObject *)np;
Guido van Rossum778983b1993-02-19 15:55:02 +0000520}
521
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000522static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000523array_concat(arrayobject *a, PyObject *bb)
Guido van Rossum778983b1993-02-19 15:55:02 +0000524{
525 int size;
Guido van Rossum778983b1993-02-19 15:55:02 +0000526 arrayobject *np;
527 if (!is_arrayobject(bb)) {
Fred Drake137507e2000-06-01 02:02:46 +0000528 PyErr_Format(PyExc_TypeError,
529 "can only append array (not \"%.200s\") to array",
530 bb->ob_type->tp_name);
Guido van Rossum778983b1993-02-19 15:55:02 +0000531 return NULL;
532 }
533#define b ((arrayobject *)bb)
534 if (a->ob_descr != b->ob_descr) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000535 PyErr_BadArgument();
Guido van Rossum778983b1993-02-19 15:55:02 +0000536 return NULL;
537 }
538 size = a->ob_size + b->ob_size;
539 np = (arrayobject *) newarrayobject(size, a->ob_descr);
540 if (np == NULL) {
541 return NULL;
542 }
543 memcpy(np->ob_item, a->ob_item, a->ob_size*a->ob_descr->itemsize);
544 memcpy(np->ob_item + a->ob_size*a->ob_descr->itemsize,
Guido van Rossum32be3a71993-11-05 10:16:27 +0000545 b->ob_item, b->ob_size*b->ob_descr->itemsize);
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000546 return (PyObject *)np;
Guido van Rossum778983b1993-02-19 15:55:02 +0000547#undef b
548}
549
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000550static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000551array_repeat(arrayobject *a, int n)
Guido van Rossum778983b1993-02-19 15:55:02 +0000552{
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000553 int i;
Guido van Rossum778983b1993-02-19 15:55:02 +0000554 int size;
555 arrayobject *np;
556 char *p;
557 int nbytes;
558 if (n < 0)
559 n = 0;
560 size = a->ob_size * n;
561 np = (arrayobject *) newarrayobject(size, a->ob_descr);
562 if (np == NULL)
563 return NULL;
564 p = np->ob_item;
565 nbytes = a->ob_size * a->ob_descr->itemsize;
566 for (i = 0; i < n; i++) {
567 memcpy(p, a->ob_item, nbytes);
568 p += nbytes;
569 }
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000570 return (PyObject *) np;
Guido van Rossum778983b1993-02-19 15:55:02 +0000571}
572
573static int
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000574array_ass_slice(arrayobject *a, int ilow, int ihigh, PyObject *v)
Guido van Rossum778983b1993-02-19 15:55:02 +0000575{
576 char *item;
577 int n; /* Size of replacement array */
578 int d; /* Change in size */
Guido van Rossum778983b1993-02-19 15:55:02 +0000579#define b ((arrayobject *)v)
580 if (v == NULL)
581 n = 0;
582 else if (is_arrayobject(v)) {
583 n = b->ob_size;
584 if (a == b) {
585 /* Special case "a[i:j] = a" -- copy b first */
586 int ret;
587 v = array_slice(b, 0, n);
588 ret = array_ass_slice(a, ilow, ihigh, v);
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000589 Py_DECREF(v);
Guido van Rossum778983b1993-02-19 15:55:02 +0000590 return ret;
591 }
592 if (b->ob_descr != a->ob_descr) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000593 PyErr_BadArgument();
Guido van Rossum778983b1993-02-19 15:55:02 +0000594 return -1;
595 }
596 }
597 else {
Fred Drake137507e2000-06-01 02:02:46 +0000598 PyErr_Format(PyExc_TypeError,
599 "can only assign array (not \"%.200s\") to array slice",
600 v->ob_type->tp_name);
Guido van Rossum778983b1993-02-19 15:55:02 +0000601 return -1;
602 }
603 if (ilow < 0)
604 ilow = 0;
605 else if (ilow > a->ob_size)
606 ilow = a->ob_size;
607 if (ihigh < 0)
608 ihigh = 0;
609 if (ihigh < ilow)
610 ihigh = ilow;
611 else if (ihigh > a->ob_size)
612 ihigh = a->ob_size;
613 item = a->ob_item;
614 d = n - (ihigh-ilow);
615 if (d < 0) { /* Delete -d items */
616 memmove(item + (ihigh+d)*a->ob_descr->itemsize,
617 item + ihigh*a->ob_descr->itemsize,
618 (a->ob_size-ihigh)*a->ob_descr->itemsize);
619 a->ob_size += d;
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000620 PyMem_RESIZE(item, char, a->ob_size*a->ob_descr->itemsize);
Guido van Rossum778983b1993-02-19 15:55:02 +0000621 /* Can't fail */
622 a->ob_item = item;
623 }
624 else if (d > 0) { /* Insert d items */
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000625 PyMem_RESIZE(item, char,
626 (a->ob_size + d)*a->ob_descr->itemsize);
Guido van Rossum778983b1993-02-19 15:55:02 +0000627 if (item == NULL) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000628 PyErr_NoMemory();
Guido van Rossum778983b1993-02-19 15:55:02 +0000629 return -1;
630 }
631 memmove(item + (ihigh+d)*a->ob_descr->itemsize,
632 item + ihigh*a->ob_descr->itemsize,
633 (a->ob_size-ihigh)*a->ob_descr->itemsize);
634 a->ob_item = item;
635 a->ob_size += d;
636 }
637 if (n > 0)
638 memcpy(item + ilow*a->ob_descr->itemsize, b->ob_item,
639 n*b->ob_descr->itemsize);
640 return 0;
641#undef b
642}
643
644static int
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000645array_ass_item(arrayobject *a, int i, PyObject *v)
Guido van Rossum778983b1993-02-19 15:55:02 +0000646{
647 if (i < 0 || i >= a->ob_size) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000648 PyErr_SetString(PyExc_IndexError,
649 "array assignment index out of range");
Guido van Rossum778983b1993-02-19 15:55:02 +0000650 return -1;
651 }
652 if (v == NULL)
653 return array_ass_slice(a, i, i+1, v);
654 return (*a->ob_descr->setitem)(a, i, v);
655}
656
657static int
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000658setarrayitem(PyObject *a, int i, PyObject *v)
Guido van Rossum778983b1993-02-19 15:55:02 +0000659{
660 if (!is_arrayobject(a)) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000661 PyErr_BadInternalCall();
Guido van Rossum778983b1993-02-19 15:55:02 +0000662 return -1;
663 }
664 return array_ass_item((arrayobject *)a, i, v);
665}
666
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000667static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000668ins(arrayobject *self, int where, PyObject *v)
Guido van Rossum778983b1993-02-19 15:55:02 +0000669{
670 if (ins1(self, where, v) != 0)
671 return NULL;
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000672 Py_INCREF(Py_None);
673 return Py_None;
Guido van Rossum778983b1993-02-19 15:55:02 +0000674}
675
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000676static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000677array_insert(arrayobject *self, PyObject *args)
Guido van Rossum778983b1993-02-19 15:55:02 +0000678{
679 int i;
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000680 PyObject *v;
681 if (!PyArg_Parse(args, "(iO)", &i, &v))
Guido van Rossum778983b1993-02-19 15:55:02 +0000682 return NULL;
683 return ins(self, i, v);
684}
685
Guido van Rossumb39b90d1998-10-13 14:27:22 +0000686static char insert_doc [] =
687"insert (i,x)\n\
688\n\
689Insert a new item x into the array before position i.";
690
691
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000692static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000693array_buffer_info(arrayobject *self, PyObject *args)
Guido van Rossumde4a4ca1997-08-12 14:55:56 +0000694{
Fred Drake541dc3b2000-06-28 17:49:30 +0000695 PyObject* retval = PyTuple_New(2);
696 if (!retval) return NULL;
697
698 PyTuple_SET_ITEM(retval, 0, PyLong_FromVoidPtr(self->ob_item));
699 PyTuple_SET_ITEM(retval, 1, PyInt_FromLong((long)(self->ob_size)));
700
701 return retval;
Guido van Rossumde4a4ca1997-08-12 14:55:56 +0000702}
703
Guido van Rossumb39b90d1998-10-13 14:27:22 +0000704static char buffer_info_doc [] =
705"buffer_info -> (address, length)\n\
706\n\
707Return a tuple (address, length) giving the current memory address and\n\
708the length in bytes of the buffer used to hold array's contents.";
709
710
Guido van Rossumde4a4ca1997-08-12 14:55:56 +0000711static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000712array_append(arrayobject *self, PyObject *args)
Guido van Rossum778983b1993-02-19 15:55:02 +0000713{
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000714 PyObject *v;
715 if (!PyArg_Parse(args, "O", &v))
Guido van Rossum778983b1993-02-19 15:55:02 +0000716 return NULL;
717 return ins(self, (int) self->ob_size, v);
718}
719
Guido van Rossumb39b90d1998-10-13 14:27:22 +0000720static char append_doc [] =
721"append(x)\n\
722\n\
723Append new value x to the end of the array.";
724
725
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000726static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000727array_byteswap(arrayobject *self, PyObject *args)
Guido van Rossum778983b1993-02-19 15:55:02 +0000728{
729 char *p;
730 int i;
Fred Drakebf272981999-12-03 17:15:30 +0000731
732 if (!PyArg_ParseTuple(args, ":byteswap"))
733 return NULL;
734
Guido van Rossum778983b1993-02-19 15:55:02 +0000735 switch (self->ob_descr->itemsize) {
736 case 1:
737 break;
738 case 2:
739 for (p = self->ob_item, i = self->ob_size; --i >= 0; p += 2) {
740 char p0 = p[0];
741 p[0] = p[1];
742 p[1] = p0;
743 }
744 break;
745 case 4:
746 for (p = self->ob_item, i = self->ob_size; --i >= 0; p += 4) {
747 char p0 = p[0];
748 char p1 = p[1];
749 p[0] = p[3];
750 p[1] = p[2];
751 p[2] = p1;
752 p[3] = p0;
753 }
754 break;
Guido van Rossume77a7571993-11-03 15:01:26 +0000755 case 8:
756 for (p = self->ob_item, i = self->ob_size; --i >= 0; p += 8) {
757 char p0 = p[0];
758 char p1 = p[1];
759 char p2 = p[2];
760 char p3 = p[3];
761 p[0] = p[7];
762 p[1] = p[6];
763 p[2] = p[5];
764 p[3] = p[4];
765 p[4] = p3;
766 p[5] = p2;
767 p[6] = p1;
768 p[7] = p0;
769 }
770 break;
Guido van Rossum778983b1993-02-19 15:55:02 +0000771 default:
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000772 PyErr_SetString(PyExc_RuntimeError,
Guido van Rossum778983b1993-02-19 15:55:02 +0000773 "don't know how to byteswap this array type");
774 return NULL;
775 }
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000776 Py_INCREF(Py_None);
777 return Py_None;
Guido van Rossum778983b1993-02-19 15:55:02 +0000778}
779
Guido van Rossumb39b90d1998-10-13 14:27:22 +0000780static char byteswap_doc [] =
Fred Drakebf272981999-12-03 17:15:30 +0000781"byteswap()\n\
Guido van Rossumb39b90d1998-10-13 14:27:22 +0000782\n\
Fred Drakebf272981999-12-03 17:15:30 +0000783Byteswap all items of the array. If the items in the array are not 1, 2,\n\
7844, or 8 bytes in size, RuntimeError is raised.";
Guido van Rossumb39b90d1998-10-13 14:27:22 +0000785
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000786static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000787array_reverse(arrayobject *self, PyObject *args)
Guido van Rossum778983b1993-02-19 15:55:02 +0000788{
Guido van Rossume77a7571993-11-03 15:01:26 +0000789 register int itemsize = self->ob_descr->itemsize;
790 register char *p, *q;
791 char tmp[sizeof(double)]; /* Assume that's the max item size */
792
Guido van Rossum778983b1993-02-19 15:55:02 +0000793 if (args != NULL) {
Fred Drake137507e2000-06-01 02:02:46 +0000794 PyErr_SetString(PyExc_TypeError,
795 "<array>.reverse requires exactly 0 arguments");
Guido van Rossum778983b1993-02-19 15:55:02 +0000796 return NULL;
797 }
798
799 if (self->ob_size > 1) {
Guido van Rossume77a7571993-11-03 15:01:26 +0000800 for (p = self->ob_item,
801 q = self->ob_item + (self->ob_size - 1)*itemsize;
802 p < q;
803 p += itemsize, q -= itemsize) {
804 memmove(tmp, p, itemsize);
805 memmove(p, q, itemsize);
806 memmove(q, tmp, itemsize);
Guido van Rossum778983b1993-02-19 15:55:02 +0000807 }
808 }
809
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000810 Py_INCREF(Py_None);
811 return Py_None;
Guido van Rossum778983b1993-02-19 15:55:02 +0000812}
Guido van Rossume77a7571993-11-03 15:01:26 +0000813
Guido van Rossumb39b90d1998-10-13 14:27:22 +0000814static char reverse_doc [] =
815"reverse()\n\
816\n\
817Reverse the order of the items in the array.";
818
Guido van Rossume77a7571993-11-03 15:01:26 +0000819/* The following routines were adapted from listobject.c but not converted.
820 To make them work you will have to work! */
Guido van Rossum778983b1993-02-19 15:55:02 +0000821
822#if 0
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000823static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000824array_index(arrayobject *self, PyObject *args)
Guido van Rossum778983b1993-02-19 15:55:02 +0000825{
826 int i;
827
828 if (args == NULL) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000829 PyErr_BadArgument();
Guido van Rossum778983b1993-02-19 15:55:02 +0000830 return NULL;
831 }
832 for (i = 0; i < self->ob_size; i++) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000833 if (PyObject_Compare(self->ob_item[i], args) == 0)
834 return PyInt_FromLong((long)i);
Guido van Rossumc8b6df91997-05-23 00:06:51 +0000835 /* XXX PyErr_Occurred */
Guido van Rossum778983b1993-02-19 15:55:02 +0000836 }
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000837 PyErr_SetString(PyExc_ValueError, "array.index(x): x not in array");
Guido van Rossum778983b1993-02-19 15:55:02 +0000838 return NULL;
839}
840#endif
841
842#if 0
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000843static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000844array_count(arrayobject *self, PyObject *args)
Guido van Rossum778983b1993-02-19 15:55:02 +0000845{
846 int count = 0;
847 int i;
848
849 if (args == NULL) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000850 PyErr_BadArgument();
Guido van Rossum778983b1993-02-19 15:55:02 +0000851 return NULL;
852 }
853 for (i = 0; i < self->ob_size; i++) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000854 if (PyObject_Compare(self->ob_item[i], args) == 0)
Guido van Rossum778983b1993-02-19 15:55:02 +0000855 count++;
Guido van Rossumc8b6df91997-05-23 00:06:51 +0000856 /* XXX PyErr_Occurred */
Guido van Rossum778983b1993-02-19 15:55:02 +0000857 }
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000858 return PyInt_FromLong((long)count);
Guido van Rossum778983b1993-02-19 15:55:02 +0000859}
860#endif
861
862#if 0
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000863static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000864array_remove(arrayobject *self, PyObject *args)
Guido van Rossum778983b1993-02-19 15:55:02 +0000865{
866 int i;
867
868 if (args == NULL) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000869 PyErr_BadArgument();
Guido van Rossum778983b1993-02-19 15:55:02 +0000870 return NULL;
871 }
872 for (i = 0; i < self->ob_size; i++) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000873 if (PyObject_Compare(self->ob_item[i], args) == 0) {
Roger E. Masse5817f8f1996-12-09 22:24:19 +0000874 if (array_ass_slice(self, i, i+1,
875 (PyObject *)NULL) != 0)
Guido van Rossum778983b1993-02-19 15:55:02 +0000876 return NULL;
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000877 Py_INCREF(Py_None);
878 return Py_None;
Guido van Rossum778983b1993-02-19 15:55:02 +0000879 }
Guido van Rossumc8b6df91997-05-23 00:06:51 +0000880 /* XXX PyErr_Occurred */
Guido van Rossum778983b1993-02-19 15:55:02 +0000881 }
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000882 PyErr_SetString(PyExc_ValueError, "array.remove(x): x not in array");
Guido van Rossum778983b1993-02-19 15:55:02 +0000883 return NULL;
884}
885#endif
886
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000887static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000888array_fromfile(arrayobject *self, PyObject *args)
Guido van Rossum778983b1993-02-19 15:55:02 +0000889{
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000890 PyObject *f;
Guido van Rossum778983b1993-02-19 15:55:02 +0000891 int n;
892 FILE *fp;
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000893 if (!PyArg_Parse(args, "(Oi)", &f, &n))
Guido van Rossum778983b1993-02-19 15:55:02 +0000894 return NULL;
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000895 fp = PyFile_AsFile(f);
Guido van Rossum778983b1993-02-19 15:55:02 +0000896 if (fp == NULL) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000897 PyErr_SetString(PyExc_TypeError, "arg1 must be open file");
Guido van Rossum778983b1993-02-19 15:55:02 +0000898 return NULL;
899 }
900 if (n > 0) {
901 char *item = self->ob_item;
902 int itemsize = self->ob_descr->itemsize;
Guido van Rossum7d0ae5e2000-06-28 21:27:21 +0000903 size_t nread;
Guido van Rossum3791b0d1999-02-23 18:05:22 +0000904 int newlength;
905 size_t newbytes;
906 /* Be careful here about overflow */
907 if ((newlength = self->ob_size + n) <= 0 ||
Guido van Rossum481ac881999-03-19 21:50:11 +0000908 (newbytes = newlength * itemsize) / itemsize !=
909 (size_t)newlength)
Guido van Rossum3791b0d1999-02-23 18:05:22 +0000910 goto nomem;
911 PyMem_RESIZE(item, char, newbytes);
Guido van Rossum778983b1993-02-19 15:55:02 +0000912 if (item == NULL) {
Guido van Rossum3791b0d1999-02-23 18:05:22 +0000913 nomem:
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000914 PyErr_NoMemory();
Guido van Rossum778983b1993-02-19 15:55:02 +0000915 return NULL;
916 }
917 self->ob_item = item;
918 self->ob_size += n;
919 nread = fread(item + (self->ob_size - n) * itemsize,
920 itemsize, n, fp);
Guido van Rossum7d0ae5e2000-06-28 21:27:21 +0000921 if (nread < (size_t)n) {
Guido van Rossum778983b1993-02-19 15:55:02 +0000922 self->ob_size -= (n - nread);
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000923 PyMem_RESIZE(item, char, self->ob_size*itemsize);
Guido van Rossum778983b1993-02-19 15:55:02 +0000924 self->ob_item = item;
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000925 PyErr_SetString(PyExc_EOFError,
926 "not enough items in file");
Guido van Rossum778983b1993-02-19 15:55:02 +0000927 return NULL;
928 }
929 }
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000930 Py_INCREF(Py_None);
931 return Py_None;
Guido van Rossum778983b1993-02-19 15:55:02 +0000932}
933
Guido van Rossumb39b90d1998-10-13 14:27:22 +0000934static char fromfile_doc [] =
935"fromfile(f, n)\n\
936\n\
937Read n objects from the file object f and append them to the end of the\n\
938array. Also called as read.";
939
940
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000941static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000942array_tofile(arrayobject *self, PyObject *args)
Guido van Rossum778983b1993-02-19 15:55:02 +0000943{
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000944 PyObject *f;
Guido van Rossum778983b1993-02-19 15:55:02 +0000945 FILE *fp;
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000946 if (!PyArg_Parse(args, "O", &f))
Guido van Rossum778983b1993-02-19 15:55:02 +0000947 return NULL;
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000948 fp = PyFile_AsFile(f);
Guido van Rossum778983b1993-02-19 15:55:02 +0000949 if (fp == NULL) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000950 PyErr_SetString(PyExc_TypeError, "arg must be open file");
Guido van Rossum778983b1993-02-19 15:55:02 +0000951 return NULL;
952 }
953 if (self->ob_size > 0) {
Guido van Rossum7844e381997-04-11 20:44:04 +0000954 if ((int)fwrite(self->ob_item, self->ob_descr->itemsize,
Guido van Rossum778983b1993-02-19 15:55:02 +0000955 self->ob_size, fp) != self->ob_size) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000956 PyErr_SetFromErrno(PyExc_IOError);
Guido van Rossum778983b1993-02-19 15:55:02 +0000957 clearerr(fp);
958 return NULL;
959 }
960 }
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000961 Py_INCREF(Py_None);
962 return Py_None;
Guido van Rossum778983b1993-02-19 15:55:02 +0000963}
964
Guido van Rossumb39b90d1998-10-13 14:27:22 +0000965static char tofile_doc [] =
966"tofile(f)\n\
967\n\
968Write all items (as machine values) to the file object f. Also called as\n\
969write.";
970
971
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000972static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +0000973array_fromlist(arrayobject *self, PyObject *args)
Guido van Rossum778983b1993-02-19 15:55:02 +0000974{
975 int n;
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000976 PyObject *list;
Guido van Rossum778983b1993-02-19 15:55:02 +0000977 int itemsize = self->ob_descr->itemsize;
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000978 if (!PyArg_Parse(args, "O", &list))
Guido van Rossum778983b1993-02-19 15:55:02 +0000979 return NULL;
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000980 if (!PyList_Check(list)) {
981 PyErr_SetString(PyExc_TypeError, "arg must be list");
Guido van Rossum778983b1993-02-19 15:55:02 +0000982 return NULL;
983 }
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000984 n = PyList_Size(list);
Guido van Rossum778983b1993-02-19 15:55:02 +0000985 if (n > 0) {
986 char *item = self->ob_item;
987 int i;
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000988 PyMem_RESIZE(item, char, (self->ob_size + n) * itemsize);
Guido van Rossum778983b1993-02-19 15:55:02 +0000989 if (item == NULL) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000990 PyErr_NoMemory();
Guido van Rossum778983b1993-02-19 15:55:02 +0000991 return NULL;
992 }
993 self->ob_item = item;
994 self->ob_size += n;
995 for (i = 0; i < n; i++) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +0000996 PyObject *v = PyList_GetItem(list, i);
Guido van Rossum778983b1993-02-19 15:55:02 +0000997 if ((*self->ob_descr->setitem)(self,
998 self->ob_size - n + i, v) != 0) {
999 self->ob_size -= n;
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001000 PyMem_RESIZE(item, char,
1001 self->ob_size * itemsize);
Guido van Rossum778983b1993-02-19 15:55:02 +00001002 self->ob_item = item;
1003 return NULL;
1004 }
1005 }
1006 }
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001007 Py_INCREF(Py_None);
1008 return Py_None;
Guido van Rossum778983b1993-02-19 15:55:02 +00001009}
1010
Guido van Rossumb39b90d1998-10-13 14:27:22 +00001011static char fromlist_doc [] =
1012"fromlist(list)\n\
1013\n\
1014Append items to array from list.";
1015
1016
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001017static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +00001018array_tolist(arrayobject *self, PyObject *args)
Guido van Rossum778983b1993-02-19 15:55:02 +00001019{
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001020 PyObject *list = PyList_New(self->ob_size);
Guido van Rossum778983b1993-02-19 15:55:02 +00001021 int i;
1022 if (list == NULL)
1023 return NULL;
1024 for (i = 0; i < self->ob_size; i++) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001025 PyObject *v = getarrayitem((PyObject *)self, i);
Guido van Rossum778983b1993-02-19 15:55:02 +00001026 if (v == NULL) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001027 Py_DECREF(list);
Guido van Rossum778983b1993-02-19 15:55:02 +00001028 return NULL;
1029 }
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001030 PyList_SetItem(list, i, v);
Guido van Rossum778983b1993-02-19 15:55:02 +00001031 }
1032 return list;
1033}
1034
Guido van Rossumb39b90d1998-10-13 14:27:22 +00001035static char tolist_doc [] =
Guido van Rossumfc6aba51998-10-14 02:52:31 +00001036"tolist() -> list\n\
Guido van Rossumb39b90d1998-10-13 14:27:22 +00001037\n\
1038Convert array to an ordinary list with the same items.";
1039
1040
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001041static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +00001042array_fromstring(arrayobject *self, PyObject *args)
Guido van Rossum778983b1993-02-19 15:55:02 +00001043{
1044 char *str;
1045 int n;
1046 int itemsize = self->ob_descr->itemsize;
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001047 if (!PyArg_Parse(args, "s#", &str, &n))
Guido van Rossum778983b1993-02-19 15:55:02 +00001048 return NULL;
1049 if (n % itemsize != 0) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001050 PyErr_SetString(PyExc_ValueError,
Guido van Rossum778983b1993-02-19 15:55:02 +00001051 "string length not a multiple of item size");
1052 return NULL;
1053 }
1054 n = n / itemsize;
1055 if (n > 0) {
1056 char *item = self->ob_item;
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001057 PyMem_RESIZE(item, char, (self->ob_size + n) * itemsize);
Guido van Rossum778983b1993-02-19 15:55:02 +00001058 if (item == NULL) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001059 PyErr_NoMemory();
Guido van Rossum778983b1993-02-19 15:55:02 +00001060 return NULL;
1061 }
1062 self->ob_item = item;
1063 self->ob_size += n;
Roger E. Masse5817f8f1996-12-09 22:24:19 +00001064 memcpy(item + (self->ob_size - n) * itemsize,
1065 str, itemsize*n);
Guido van Rossum778983b1993-02-19 15:55:02 +00001066 }
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001067 Py_INCREF(Py_None);
1068 return Py_None;
Guido van Rossum778983b1993-02-19 15:55:02 +00001069}
1070
Guido van Rossumb39b90d1998-10-13 14:27:22 +00001071static char fromstring_doc [] =
1072"fromstring(string)\n\
1073\n\
1074Appends items from the string, interpreting it as an array of machine\n\
1075values,as if it had been read from a file using the fromfile() method).";
1076
1077
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001078static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +00001079array_tostring(arrayobject *self, PyObject *args)
Guido van Rossum778983b1993-02-19 15:55:02 +00001080{
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001081 if (!PyArg_Parse(args, ""))
Guido van Rossum778983b1993-02-19 15:55:02 +00001082 return NULL;
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001083 return PyString_FromStringAndSize(self->ob_item,
Guido van Rossum778983b1993-02-19 15:55:02 +00001084 self->ob_size * self->ob_descr->itemsize);
1085}
1086
Guido van Rossumb39b90d1998-10-13 14:27:22 +00001087static char tostring_doc [] =
1088"tostring() -> string\n\
1089\n\
1090Convert the array to an array of machine values and return the string\n\
1091representation.";
1092
1093PyMethodDef array_methods[] = {
1094 {"append", (PyCFunction)array_append, 0, append_doc},
1095 {"buffer_info", (PyCFunction)array_buffer_info, 0, buffer_info_doc},
Fred Drakebf272981999-12-03 17:15:30 +00001096 {"byteswap", (PyCFunction)array_byteswap, METH_VARARGS,
1097 byteswap_doc},
Guido van Rossumb6775db1994-08-01 11:34:53 +00001098/* {"count", (method)array_count},*/
Guido van Rossumb39b90d1998-10-13 14:27:22 +00001099 {"fromfile", (PyCFunction)array_fromfile, 0, fromfile_doc},
1100 {"fromlist", (PyCFunction)array_fromlist, 0, fromlist_doc},
1101 {"fromstring", (PyCFunction)array_fromstring, 0, fromstring_doc},
Guido van Rossumb6775db1994-08-01 11:34:53 +00001102/* {"index", (method)array_index},*/
Guido van Rossumb39b90d1998-10-13 14:27:22 +00001103 {"insert", (PyCFunction)array_insert, 0, insert_doc},
1104 {"read", (PyCFunction)array_fromfile, 0, fromfile_doc},
Guido van Rossumb6775db1994-08-01 11:34:53 +00001105/* {"remove", (method)array_remove},*/
Guido van Rossumb39b90d1998-10-13 14:27:22 +00001106 {"reverse", (PyCFunction)array_reverse, 0, reverse_doc},
Guido van Rossumb6775db1994-08-01 11:34:53 +00001107/* {"sort", (method)array_sort},*/
Guido van Rossumb39b90d1998-10-13 14:27:22 +00001108 {"tofile", (PyCFunction)array_tofile, 0, tofile_doc},
1109 {"tolist", (PyCFunction)array_tolist, 0, tolist_doc},
1110 {"tostring", (PyCFunction)array_tostring, 0, tostring_doc},
1111 {"write", (PyCFunction)array_tofile, 0, tofile_doc},
Guido van Rossum778983b1993-02-19 15:55:02 +00001112 {NULL, NULL} /* sentinel */
1113};
1114
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001115static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +00001116array_getattr(arrayobject *a, char *name)
Guido van Rossum778983b1993-02-19 15:55:02 +00001117{
1118 if (strcmp(name, "typecode") == 0) {
1119 char tc = a->ob_descr->typecode;
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001120 return PyString_FromStringAndSize(&tc, 1);
Guido van Rossum778983b1993-02-19 15:55:02 +00001121 }
1122 if (strcmp(name, "itemsize") == 0) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001123 return PyInt_FromLong((long)a->ob_descr->itemsize);
Guido van Rossum778983b1993-02-19 15:55:02 +00001124 }
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00001125 if (strcmp(name, "__members__") == 0) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001126 PyObject *list = PyList_New(2);
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00001127 if (list) {
Roger E. Masse5817f8f1996-12-09 22:24:19 +00001128 PyList_SetItem(list, 0,
1129 PyString_FromString("typecode"));
1130 PyList_SetItem(list, 1,
1131 PyString_FromString("itemsize"));
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001132 if (PyErr_Occurred()) {
1133 Py_DECREF(list);
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00001134 list = NULL;
1135 }
1136 }
1137 return list;
1138 }
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001139 return Py_FindMethod(array_methods, (PyObject *)a, name);
Guido van Rossum778983b1993-02-19 15:55:02 +00001140}
1141
1142static int
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +00001143array_print(arrayobject *a, FILE *fp, int flags)
Guido van Rossum778983b1993-02-19 15:55:02 +00001144{
1145 int ok = 0;
1146 int i, len;
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001147 PyObject *v;
Guido van Rossum778983b1993-02-19 15:55:02 +00001148 len = a->ob_size;
1149 if (len == 0) {
1150 fprintf(fp, "array('%c')", a->ob_descr->typecode);
1151 return ok;
1152 }
1153 if (a->ob_descr->typecode == 'c') {
1154 fprintf(fp, "array('c', ");
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001155 v = array_tostring(a, (PyObject *)NULL);
1156 ok = PyObject_Print(v, fp, 0);
1157 Py_XDECREF(v);
Guido van Rossum778983b1993-02-19 15:55:02 +00001158 fprintf(fp, ")");
1159 return ok;
1160 }
1161 fprintf(fp, "array('%c', [", a->ob_descr->typecode);
1162 for (i = 0; i < len && ok == 0; i++) {
1163 if (i > 0)
1164 fprintf(fp, ", ");
1165 v = (a->ob_descr->getitem)(a, i);
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001166 ok = PyObject_Print(v, fp, 0);
1167 Py_XDECREF(v);
Guido van Rossum778983b1993-02-19 15:55:02 +00001168 }
1169 fprintf(fp, "])");
1170 return ok;
1171}
1172
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001173static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +00001174array_repr(arrayobject *a)
Guido van Rossum778983b1993-02-19 15:55:02 +00001175{
1176 char buf[256];
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001177 PyObject *s, *t, *comma, *v;
Guido van Rossum778983b1993-02-19 15:55:02 +00001178 int i, len;
1179 len = a->ob_size;
1180 if (len == 0) {
1181 sprintf(buf, "array('%c')", a->ob_descr->typecode);
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001182 return PyString_FromString(buf);
Guido van Rossum778983b1993-02-19 15:55:02 +00001183 }
1184 if (a->ob_descr->typecode == 'c') {
1185 sprintf(buf, "array('c', ");
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001186 s = PyString_FromString(buf);
1187 v = array_tostring(a, (PyObject *)NULL);
1188 t = PyObject_Repr(v);
1189 Py_XDECREF(v);
1190 PyString_ConcatAndDel(&s, t);
1191 PyString_ConcatAndDel(&s, PyString_FromString(")"));
Guido van Rossum778983b1993-02-19 15:55:02 +00001192 return s;
1193 }
1194 sprintf(buf, "array('%c', [", a->ob_descr->typecode);
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001195 s = PyString_FromString(buf);
1196 comma = PyString_FromString(", ");
1197 for (i = 0; i < len && !PyErr_Occurred(); i++) {
Guido van Rossumb6775db1994-08-01 11:34:53 +00001198 if (i > 0)
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001199 PyString_Concat(&s, comma);
Guido van Rossum778983b1993-02-19 15:55:02 +00001200 v = (a->ob_descr->getitem)(a, i);
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001201 t = PyObject_Repr(v);
1202 Py_XDECREF(v);
1203 PyString_ConcatAndDel(&s, t);
Guido van Rossum778983b1993-02-19 15:55:02 +00001204 }
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001205 Py_XDECREF(comma);
1206 PyString_ConcatAndDel(&s, PyString_FromString("])"));
Guido van Rossum778983b1993-02-19 15:55:02 +00001207 return s;
1208}
1209
Guido van Rossumfdf95dd1997-05-05 22:15:02 +00001210static int
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +00001211array_buffer_getreadbuf(arrayobject *self, int index, const void **ptr)
Guido van Rossumfdf95dd1997-05-05 22:15:02 +00001212{
1213 if ( index != 0 ) {
Guido van Rossumb39b90d1998-10-13 14:27:22 +00001214 PyErr_SetString(PyExc_SystemError,
1215 "Accessing non-existent array segment");
Guido van Rossumfdf95dd1997-05-05 22:15:02 +00001216 return -1;
1217 }
1218 *ptr = (void *)self->ob_item;
1219 return self->ob_size*self->ob_descr->itemsize;
1220}
1221
1222static int
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +00001223array_buffer_getwritebuf(arrayobject *self, int index, const void **ptr)
Guido van Rossumfdf95dd1997-05-05 22:15:02 +00001224{
1225 if ( index != 0 ) {
Guido van Rossumb39b90d1998-10-13 14:27:22 +00001226 PyErr_SetString(PyExc_SystemError,
1227 "Accessing non-existent array segment");
Guido van Rossumfdf95dd1997-05-05 22:15:02 +00001228 return -1;
1229 }
1230 *ptr = (void *)self->ob_item;
1231 return self->ob_size*self->ob_descr->itemsize;
1232}
1233
1234static int
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +00001235array_buffer_getsegcount(arrayobject *self, int *lenp)
Guido van Rossumfdf95dd1997-05-05 22:15:02 +00001236{
1237 if ( lenp )
1238 *lenp = self->ob_size*self->ob_descr->itemsize;
1239 return 1;
1240}
1241
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001242static PySequenceMethods array_as_sequence = {
Roger E. Masse5817f8f1996-12-09 22:24:19 +00001243 (inquiry)array_length, /*sq_length*/
1244 (binaryfunc)array_concat, /*sq_concat*/
Guido van Rossumb6775db1994-08-01 11:34:53 +00001245 (intargfunc)array_repeat, /*sq_repeat*/
Roger E. Masse5817f8f1996-12-09 22:24:19 +00001246 (intargfunc)array_item, /*sq_item*/
Guido van Rossumb6775db1994-08-01 11:34:53 +00001247 (intintargfunc)array_slice, /*sq_slice*/
1248 (intobjargproc)array_ass_item, /*sq_ass_item*/
1249 (intintobjargproc)array_ass_slice, /*sq_ass_slice*/
Guido van Rossum778983b1993-02-19 15:55:02 +00001250};
1251
Guido van Rossumfdf95dd1997-05-05 22:15:02 +00001252static PyBufferProcs array_as_buffer = {
1253 (getreadbufferproc)array_buffer_getreadbuf,
1254 (getwritebufferproc)array_buffer_getwritebuf,
1255 (getsegcountproc)array_buffer_getsegcount,
1256};
1257
1258
Guido van Rossum778983b1993-02-19 15:55:02 +00001259
1260
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001261static PyObject *
Peter Schneider-Kamp9656abd2000-07-13 21:10:57 +00001262a_array(PyObject *self, PyObject *args)
Guido van Rossum778983b1993-02-19 15:55:02 +00001263{
1264 char c;
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001265 PyObject *initial = NULL;
Guido van Rossum778983b1993-02-19 15:55:02 +00001266 struct arraydescr *descr;
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001267 if (!PyArg_Parse(args, "c", &c)) {
1268 PyErr_Clear();
1269 if (!PyArg_Parse(args, "(cO)", &c, &initial))
Guido van Rossum778983b1993-02-19 15:55:02 +00001270 return NULL;
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001271 if (!PyList_Check(initial) && !PyString_Check(initial)) {
1272 PyErr_SetString(PyExc_TypeError,
Roger E. Masse5817f8f1996-12-09 22:24:19 +00001273 "array initializer must be list or string");
Guido van Rossum778983b1993-02-19 15:55:02 +00001274 return NULL;
1275 }
1276 }
1277 for (descr = descriptors; descr->typecode != '\0'; descr++) {
1278 if (descr->typecode == c) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001279 PyObject *a;
Guido van Rossum778983b1993-02-19 15:55:02 +00001280 int len;
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001281 if (initial == NULL || !PyList_Check(initial))
Guido van Rossum778983b1993-02-19 15:55:02 +00001282 len = 0;
1283 else
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001284 len = PyList_Size(initial);
Guido van Rossum778983b1993-02-19 15:55:02 +00001285 a = newarrayobject(len, descr);
1286 if (a == NULL)
1287 return NULL;
1288 if (len > 0) {
1289 int i;
1290 for (i = 0; i < len; i++) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001291 PyObject *v =
1292 PyList_GetItem(initial, i);
Guido van Rossum778983b1993-02-19 15:55:02 +00001293 if (setarrayitem(a, i, v) != 0) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001294 Py_DECREF(a);
Guido van Rossum778983b1993-02-19 15:55:02 +00001295 return NULL;
1296 }
1297 }
1298 }
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001299 if (initial != NULL && PyString_Check(initial)) {
1300 PyObject *v =
Guido van Rossum778983b1993-02-19 15:55:02 +00001301 array_fromstring((arrayobject *)a, initial);
1302 if (v == NULL) {
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001303 Py_DECREF(a);
Guido van Rossum778983b1993-02-19 15:55:02 +00001304 return NULL;
1305 }
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001306 Py_DECREF(v);
Guido van Rossum778983b1993-02-19 15:55:02 +00001307 }
1308 return a;
1309 }
1310 }
Roger E. Masse5817f8f1996-12-09 22:24:19 +00001311 PyErr_SetString(PyExc_ValueError,
Guido van Rossum549ab711997-01-03 19:09:47 +00001312 "bad typecode (must be c, b, B, h, H, i, I, l, L, f or d)");
Guido van Rossum778983b1993-02-19 15:55:02 +00001313 return NULL;
1314}
1315
Guido van Rossumb39b90d1998-10-13 14:27:22 +00001316static char a_array_doc [] =
1317"array(typecode [, initializer]) -> array\n\
1318\n\
1319Return a new array whose items are restricted by typecode, and\n\
1320initialized from the optional initializer value, which must be a list\n\
1321or a string.";
1322
Roger E. Masse2919eaa1996-12-09 20:10:36 +00001323static PyMethodDef a_methods[] = {
Guido van Rossumb39b90d1998-10-13 14:27:22 +00001324 {"array", a_array, 0, a_array_doc},
Guido van Rossum778983b1993-02-19 15:55:02 +00001325 {NULL, NULL} /* sentinel */
1326};
1327
Guido van Rossumb39b90d1998-10-13 14:27:22 +00001328static char module_doc [] =
1329"This module defines a new object type which can efficiently represent\n\
1330an array of basic values: characters, integers, floating point\n\
1331numbers. Arrays are sequence types and behave very much like lists,\n\
1332except that the type of objects stored in them is constrained. The\n\
1333type is specified at object creation time by using a type code, which\n\
1334is a single character. The following type codes are defined:\n\
1335\n\
1336 Type code C Type Minimum size in bytes \n\
1337 'c' character 1 \n\
1338 'b' signed integer 1 \n\
1339 'B' unsigned integer 1 \n\
1340 'h' signed integer 2 \n\
1341 'H' unsigned integer 2 \n\
1342 'i' signed integer 2 \n\
1343 'I' unsigned integer 2 \n\
1344 'l' signed integer 4 \n\
1345 'L' unsigned integer 4 \n\
1346 'f' floating point 4 \n\
1347 'd' floating point 8 \n\
1348\n\
1349Functions:\n\
1350\n\
1351array(typecode [, initializer]) -- create a new array\n\
1352\n\
1353Special Objects:\n\
1354\n\
1355ArrayType -- type object for array objects\n\
1356";
1357
1358static char arraytype_doc [] =
1359"An array represents basic values and behave very much like lists, except\n\
1360the type of objects stored in them is constrained.\n\
1361\n\
1362Methods:\n\
1363\n\
1364append() -- append a new item to the end of the array\n\
1365buffer_info() -- return information giving the current memory info\n\
1366byteswap() -- byteswap all the items of the array\n\
1367fromfile() -- read items from a file object\n\
1368fromlist() -- append items from the list\n\
1369fromstring() -- append items from the string\n\
1370insert() -- insert a new item into the array at a provided position\n\
1371read() -- DEPRECATED, use fromfile()\n\
1372reverse() -- reverse the order of the items in the array\n\
1373tofile() -- write all items to a file object\n\
1374tolist() -- return the array converted to an ordinary list\n\
1375tostring() -- return the array converted to a string\n\
1376write() -- DEPRECATED, use tofile()\n\
1377\n\
1378Variables:\n\
1379\n\
1380typecode -- the typecode character used to create the array\n\
1381itemsize -- the length in bytes of one array item\n\
1382";
1383
1384statichere PyTypeObject Arraytype = {
Fred Drake0d40ba42000-02-04 20:33:49 +00001385 PyObject_HEAD_INIT(NULL)
Guido van Rossumb39b90d1998-10-13 14:27:22 +00001386 0,
1387 "array",
1388 sizeof(arrayobject),
1389 0,
1390 (destructor)array_dealloc, /*tp_dealloc*/
1391 (printfunc)array_print, /*tp_print*/
1392 (getattrfunc)array_getattr, /*tp_getattr*/
1393 0, /*tp_setattr*/
1394 (cmpfunc)array_compare, /*tp_compare*/
1395 (reprfunc)array_repr, /*tp_repr*/
1396 0, /*tp_as_number*/
1397 &array_as_sequence, /*tp_as_sequence*/
1398 0, /*tp_as_mapping*/
1399 0, /*tp_hash*/
1400 0, /*tp_call*/
1401 0, /*tp_str*/
1402 0, /*tp_getattro*/
1403 0, /*tp_setattro*/
1404 &array_as_buffer, /*tp_as_buffer*/
1405 0, /*tp_xxx4*/
1406 arraytype_doc, /*tp_doc*/
1407};
1408
Guido van Rossum3886bb61998-12-04 18:50:17 +00001409DL_EXPORT(void)
Thomas Woutersf3f33dc2000-07-21 06:00:07 +00001410initarray(void)
Guido van Rossum778983b1993-02-19 15:55:02 +00001411{
Guido van Rossumb6190d31997-05-22 14:56:36 +00001412 PyObject *m, *d;
Fred Drake0d40ba42000-02-04 20:33:49 +00001413
1414 Arraytype.ob_type = &PyType_Type;
Guido van Rossumb39b90d1998-10-13 14:27:22 +00001415 m = Py_InitModule3("array", a_methods, module_doc);
Guido van Rossumb6190d31997-05-22 14:56:36 +00001416 d = PyModule_GetDict(m);
Guido van Rossuma0deb641998-10-14 13:45:06 +00001417 PyDict_SetItemString(d, "ArrayType", (PyObject *)&Arraytype);
1418 /* No need to check the error here, the caller will do that */
Guido van Rossum778983b1993-02-19 15:55:02 +00001419}