1 /***********************************************************
2 Copyright (c) 2000, BeOpen.com.
3 Copyright (c) 1995-2000, Corporation for National Research Initiatives.
4 Copyright (c) 1990-1995, Stichting Mathematisch Centrum.
7 See the file "Misc/COPYRIGHT" for information on usage and
8 redistribution of this file, and for a DISCLAIMER OF ALL WARRANTIES.
9 ******************************************************************/
11 /* Map C struct members to Python object attributes */
15 #include "structmember.h"
18 listmembers(struct memberlist
*mlist
)
22 for (n
= 0; mlist
[n
].name
!= NULL
; n
++)
26 for (i
= 0; i
< n
; i
++)
28 PyString_FromString(mlist
[i
].name
));
29 if (PyErr_Occurred()) {
41 PyMember_Get(char *addr
, struct memberlist
*mlist
, char *name
)
45 if (strcmp(name
, "__members__") == 0)
46 return listmembers(mlist
);
47 for (l
= mlist
; l
->name
!= NULL
; l
++) {
48 if (strcmp(l
->name
, name
) == 0) {
53 v
= PyInt_FromLong((long)
54 (((*(char*)addr
& 0xff)
58 v
= PyInt_FromLong((long) *(char*)addr
& 0xff);
61 v
= PyInt_FromLong((long) *(short*)addr
);
64 v
= PyInt_FromLong((long)
65 *(unsigned short*)addr
);
68 v
= PyInt_FromLong((long) *(int*)addr
);
71 v
= PyInt_FromLong((long)
72 *(unsigned int*)addr
);
75 v
= PyInt_FromLong(*(long*)addr
);
78 v
= PyLong_FromDouble((double)
79 *(unsigned long*)addr
);
82 v
= PyFloat_FromDouble((double)*(float*)addr
);
85 v
= PyFloat_FromDouble(*(double*)addr
);
88 if (*(char**)addr
== NULL
) {
93 v
= PyString_FromString(*(char**)addr
);
95 case T_STRING_INPLACE
:
96 v
= PyString_FromString((char*)addr
);
100 if (*(char**)addr
== NULL
) {
105 v
= PyString_FromStringAndSize(
107 **(unsigned char**)addr
);
109 case T_PSTRING_INPLACE
:
110 v
= PyString_FromStringAndSize(
112 *(unsigned char*)addr
);
114 #endif /* macintosh */
116 v
= PyString_FromStringAndSize((char*)addr
, 1);
119 v
= *(PyObject
**)addr
;
125 PyErr_SetString(PyExc_SystemError
,
126 "bad memberlist type");
133 PyErr_SetString(PyExc_AttributeError
, name
);
138 PyMember_Set(char *addr
, struct memberlist
*mlist
, char *name
, PyObject
*v
)
140 struct memberlist
*l
;
143 for (l
= mlist
; l
->name
!= NULL
; l
++) {
144 if (strcmp(l
->name
, name
) == 0) {
146 if (l
->readonly
|| l
->type
== T_STRING
||
147 l
->type
== T_PSTRING
)
150 if (l
->readonly
|| l
->type
== T_STRING
) {
151 #endif /* macintosh */
152 PyErr_SetString(PyExc_TypeError
,
153 "readonly attribute");
156 if (v
== NULL
&& l
->type
!= T_OBJECT
) {
157 PyErr_SetString(PyExc_TypeError
,
158 "can't delete numeric/char attribute");
165 if (!PyInt_Check(v
)) {
169 *(char*)addr
= (char) PyInt_AsLong(v
);
173 if (!PyInt_Check(v
)) {
177 *(short*)addr
= (short) PyInt_AsLong(v
);
181 if (!PyInt_Check(v
)) {
185 *(int*)addr
= (int) PyInt_AsLong(v
);
188 if (!PyInt_Check(v
)) {
192 *(long*)addr
= PyInt_AsLong(v
);
196 *(long*)addr
= PyInt_AsLong(v
);
197 else if (PyLong_Check(v
))
198 *(long*)addr
= PyLong_AsLong(v
);
207 (float) PyInt_AsLong(v
);
208 else if (PyFloat_Check(v
))
210 (float) PyFloat_AsDouble(v
);
219 (double) PyInt_AsLong(v
);
220 else if (PyFloat_Check(v
))
221 *(double*)addr
= PyFloat_AsDouble(v
);
229 oldv
= *(PyObject
**)addr
;
230 *(PyObject
**)addr
= v
;
234 if (PyString_Check(v
) &&
235 PyString_Size(v
) == 1) {
237 PyString_AsString(v
)[0];
244 PyErr_SetString(PyExc_SystemError
,
245 "bad memberlist type");
252 PyErr_SetString(PyExc_AttributeError
, name
);