@@ -3396,6 +3396,9 @@ generic_pycdata_new(ctypes_state *st,
3396
3396
PyCFuncPtr_Type
3397
3397
*/
3398
3398
3399
+ static int
3400
+ _validate_paramflags (ctypes_state * st , PyTypeObject * type , PyObject * paramflags , PyObject * argtypes );
3401
+
3399
3402
static int
3400
3403
PyCFuncPtr_set_errcheck (PyCFuncPtrObject * self , PyObject * ob , void * Py_UNUSED (ignored ))
3401
3404
{
@@ -3470,21 +3473,26 @@ PyCFuncPtr_get_restype(PyCFuncPtrObject *self, void *Py_UNUSED(ignored))
3470
3473
}
3471
3474
3472
3475
static int
3473
- PyCFuncPtr_set_argtypes (PyCFuncPtrObject * self , PyObject * ob , void * Py_UNUSED (ignored ))
3476
+ PyCFuncPtr_set_argtypes (PyCFuncPtrObject * self , PyObject * value , void * Py_UNUSED (ignored ))
3474
3477
{
3475
- PyObject * converters ;
3476
-
3477
- if (ob == NULL || ob == Py_None ) {
3478
+ if (value == NULL || value == Py_None ) {
3478
3479
Py_CLEAR (self -> converters );
3479
3480
Py_CLEAR (self -> argtypes );
3480
3481
} else {
3481
- ctypes_state * st = get_module_state_by_def (Py_TYPE (Py_TYPE (self )));
3482
- converters = converters_from_argtypes (st , ob );
3482
+ PyTypeObject * type = Py_TYPE (self );
3483
+ ctypes_state * st = get_module_state_by_def (Py_TYPE (type ));
3484
+ PyObject * converters = converters_from_argtypes (st , value );
3483
3485
if (!converters )
3484
3486
return -1 ;
3487
+
3488
+ /* Verify paramflags again due to constraints with argtypes */
3489
+ if (!_validate_paramflags (st , type , self -> paramflags , value )) {
3490
+ Py_DECREF (converters );
3491
+ return -1 ;
3492
+ }
3485
3493
Py_XSETREF (self -> converters , converters );
3486
- Py_INCREF (ob );
3487
- Py_XSETREF (self -> argtypes , ob );
3494
+ Py_INCREF (value );
3495
+ Py_XSETREF (self -> argtypes , value );
3488
3496
}
3489
3497
return 0 ;
3490
3498
}
@@ -3606,10 +3614,9 @@ _check_outarg_type(ctypes_state *st, PyObject *arg, Py_ssize_t index)
3606
3614
3607
3615
/* Returns 1 on success, 0 on error */
3608
3616
static int
3609
- _validate_paramflags (ctypes_state * st , PyTypeObject * type , PyObject * paramflags )
3617
+ _validate_paramflags (ctypes_state * st , PyTypeObject * type , PyObject * paramflags , PyObject * argtypes )
3610
3618
{
3611
3619
Py_ssize_t i , len ;
3612
- PyObject * argtypes ;
3613
3620
3614
3621
StgInfo * info ;
3615
3622
if (PyStgInfo_FromType (st , (PyObject * )type , & info ) < 0 ) {
@@ -3620,10 +3627,13 @@ _validate_paramflags(ctypes_state *st, PyTypeObject *type, PyObject *paramflags)
3620
3627
"abstract class" );
3621
3628
return 0 ;
3622
3629
}
3623
- argtypes = info -> argtypes ;
3630
+ if (argtypes == NULL ) {
3631
+ argtypes = info -> argtypes ;
3632
+ }
3624
3633
3625
- if (paramflags == NULL || info -> argtypes == NULL )
3634
+ if (paramflags == NULL || argtypes == NULL ) {
3626
3635
return 1 ;
3636
+ }
3627
3637
3628
3638
if (!PyTuple_Check (paramflags )) {
3629
3639
PyErr_SetString (PyExc_TypeError ,
@@ -3632,7 +3642,7 @@ _validate_paramflags(ctypes_state *st, PyTypeObject *type, PyObject *paramflags)
3632
3642
}
3633
3643
3634
3644
len = PyTuple_GET_SIZE (paramflags );
3635
- if (len != PyTuple_GET_SIZE (info -> argtypes )) {
3645
+ if (len != PyTuple_GET_SIZE (argtypes )) {
3636
3646
PyErr_SetString (PyExc_ValueError ,
3637
3647
"paramflags must have the same length as argtypes" );
3638
3648
return 0 ;
@@ -3807,7 +3817,7 @@ PyCFuncPtr_FromDll(PyTypeObject *type, PyObject *args, PyObject *kwds)
3807
3817
#endif
3808
3818
#undef USE_DLERROR
3809
3819
ctypes_state * st = get_module_state_by_def (Py_TYPE (type ));
3810
- if (!_validate_paramflags (st , type , paramflags )) {
3820
+ if (!_validate_paramflags (st , type , paramflags , NULL )) {
3811
3821
Py_DECREF (ftuple );
3812
3822
return NULL ;
3813
3823
}
@@ -3849,7 +3859,7 @@ PyCFuncPtr_FromVtblIndex(PyTypeObject *type, PyObject *args, PyObject *kwds)
3849
3859
paramflags = NULL ;
3850
3860
3851
3861
ctypes_state * st = get_module_state_by_def (Py_TYPE (type ));
3852
- if (!_validate_paramflags (st , type , paramflags )) {
3862
+ if (!_validate_paramflags (st , type , paramflags , NULL )) {
3853
3863
return NULL ;
3854
3864
}
3855
3865
self = (PyCFuncPtrObject * )generic_pycdata_new (st , type , args , kwds );
0 commit comments