@@ -187,45 +187,74 @@ PyMember_SetOne(char *addr, PyMemberDef *l, PyObject *v)
187
187
WARN ("Truncation of value to int" );
188
188
break ;
189
189
}
190
- case T_UINT :{
191
- unsigned long ulong_val = PyLong_AsUnsignedLong (v );
192
- if ((ulong_val == (unsigned long )-1 ) && PyErr_Occurred ()) {
193
- /* XXX: For compatibility, accept negative int values
194
- as well. */
195
- PyErr_Clear ();
196
- ulong_val = PyLong_AsLong (v );
197
- if ((ulong_val == (unsigned long )-1 ) &&
198
- PyErr_Occurred ())
190
+ case T_UINT : {
191
+ /* XXX: For compatibility, accept negative int values
192
+ as well. */
193
+ int overflow ;
194
+ long long_val = PyLong_AsLongAndOverflow (v , & overflow );
195
+ if (long_val == -1 && PyErr_Occurred ()) {
196
+ return -1 ;
197
+ }
198
+ if (overflow < 0 ) {
199
+ PyErr_SetString (PyExc_OverflowError ,
200
+ "Python int too large to convert to C long" );
201
+ return -1 ;
202
+ }
203
+ else if (!overflow ) {
204
+ * (unsigned int * )addr = (unsigned int )(unsigned long )long_val ;
205
+ if (long_val < 0 ) {
206
+ WARN ("Writing negative value into unsigned field" );
207
+ }
208
+ else if ((unsigned long )long_val > UINT_MAX ) {
209
+ WARN ("Truncation of value to unsigned short" );
210
+ }
211
+ }
212
+ else {
213
+ unsigned long ulong_val = PyLong_AsUnsignedLong (v );
214
+ if (ulong_val == (unsigned long )-1 && PyErr_Occurred ()) {
199
215
return -1 ;
200
- * (unsigned int * )addr = (unsigned int )ulong_val ;
201
- WARN ("Writing negative value into unsigned field" );
202
- } else
203
- * (unsigned int * )addr = (unsigned int )ulong_val ;
204
- if (ulong_val > UINT_MAX )
205
- WARN ("Truncation of value to unsigned int" );
206
- break ;
216
+ }
217
+ * (unsigned int * )addr = (unsigned int )ulong_val ;
218
+ if (ulong_val > UINT_MAX ) {
219
+ WARN ("Truncation of value to unsigned int" );
220
+ }
207
221
}
222
+ break ;
223
+ }
208
224
case T_LONG :{
209
225
* (long * )addr = PyLong_AsLong (v );
210
226
if ((* (long * )addr == -1 ) && PyErr_Occurred ())
211
227
return -1 ;
212
228
break ;
213
229
}
214
- case T_ULONG :{
215
- * (unsigned long * )addr = PyLong_AsUnsignedLong (v );
216
- if ((* (unsigned long * )addr == (unsigned long )-1 )
217
- && PyErr_Occurred ()) {
218
- /* XXX: For compatibility, accept negative int values
219
- as well. */
220
- PyErr_Clear ();
221
- * (unsigned long * )addr = PyLong_AsLong (v );
222
- if ((* (unsigned long * )addr == (unsigned long )-1 )
223
- && PyErr_Occurred ())
230
+ case T_ULONG : {
231
+ /* XXX: For compatibility, accept negative int values
232
+ as well. */
233
+ int overflow ;
234
+ long long_val = PyLong_AsLongAndOverflow (v , & overflow );
235
+ if (long_val == -1 && PyErr_Occurred ()) {
236
+ return -1 ;
237
+ }
238
+ if (overflow < 0 ) {
239
+ PyErr_SetString (PyExc_OverflowError ,
240
+ "Python int too large to convert to C long" );
241
+ return -1 ;
242
+ }
243
+ else if (!overflow ) {
244
+ * (unsigned long * )addr = (unsigned long )long_val ;
245
+ if (long_val < 0 ) {
246
+ WARN ("Writing negative value into unsigned field" );
247
+ }
248
+ }
249
+ else {
250
+ unsigned long ulong_val = PyLong_AsUnsignedLong (v );
251
+ if (ulong_val == (unsigned long )-1 && PyErr_Occurred ()) {
224
252
return -1 ;
225
- WARN ("Writing negative value into unsigned field" );
253
+ }
254
+ * (unsigned long * )addr = ulong_val ;
226
255
}
227
256
break ;
228
- }
257
+ }
229
258
case T_PYSSIZET :{
230
259
* (Py_ssize_t * )addr = PyLong_AsSsize_t (v );
231
260
if ((* (Py_ssize_t * )addr == (Py_ssize_t )- 1 )
0 commit comments