@@ -3466,6 +3466,195 @@ test_weakref_capi(PyObject *Py_UNUSED(module), PyObject *Py_UNUSED(args))
3466
3466
}
3467
3467
3468
3468
3469
+ static PyObject *
3470
+ test_dict_capi (PyObject * Py_UNUSED (module ), PyObject * Py_UNUSED (args ))
3471
+ {
3472
+ assert (!PyErr_Occurred ());
3473
+
3474
+ PyObject * dict = NULL , * key = NULL , * missing_key = NULL , * value = NULL ;
3475
+ PyObject * invalid_key = NULL ;
3476
+
3477
+ // test PyDict_New()
3478
+ dict = PyDict_New ();
3479
+ if (dict == NULL ) {
3480
+ goto error ;
3481
+ }
3482
+
3483
+ key = PyUnicode_FromString ("key" );
3484
+ if (key == NULL ) {
3485
+ goto error ;
3486
+ }
3487
+
3488
+ missing_key = PyUnicode_FromString ("missing_key" );
3489
+ if (missing_key == NULL ) {
3490
+ goto error ;
3491
+ }
3492
+
3493
+ value = PyUnicode_FromString ("value" );
3494
+ if (value == NULL ) {
3495
+ goto error ;
3496
+ }
3497
+
3498
+ // test PyDict_SetItem()
3499
+ Py_ssize_t key_refcnt = Py_REFCNT (key );
3500
+ Py_ssize_t value_refcnt = Py_REFCNT (value );
3501
+ if (PyDict_SetItem (dict , key , value ) < 0 ) {
3502
+ goto error ;
3503
+ }
3504
+ assert (Py_REFCNT (key ) == (key_refcnt + 1 ));
3505
+ assert (Py_REFCNT (value ) == (value_refcnt + 1 ));
3506
+
3507
+ // test PyDict_SetItemString()
3508
+ if (PyDict_SetItemString (dict , "key" , value ) < 0 ) {
3509
+ goto error ;
3510
+ }
3511
+ assert (Py_REFCNT (key ) == (key_refcnt + 1 ));
3512
+ assert (Py_REFCNT (value ) == (value_refcnt + 1 ));
3513
+
3514
+ // test PyDict_Size()
3515
+ assert (PyDict_Size (dict ) == 1 );
3516
+
3517
+ // test PyDict_Contains(), key is present
3518
+ assert (PyDict_Contains (dict , key ) == 1 );
3519
+
3520
+ // test PyDict_GetItem(), key is present
3521
+ assert (PyDict_GetItem (dict , key ) == value );
3522
+
3523
+ // test PyDict_GetItemString(), key is present
3524
+ assert (PyDict_GetItemString (dict , "key" ) == value );
3525
+
3526
+ // test PyDict_GetItemWithError(), key is present
3527
+ assert (PyDict_GetItemWithError (dict , key ) == value );
3528
+ assert (!PyErr_Occurred ());
3529
+
3530
+ // test PyDict_GetItemRef(), key is present
3531
+ PyObject * get_value = Py_Ellipsis ; // marker value
3532
+ if (PyDict_GetItemRef (dict , key , & get_value ) < 0 ) {
3533
+ goto error ;
3534
+ }
3535
+ assert (get_value == value );
3536
+ Py_DECREF (get_value );
3537
+
3538
+ // test PyDict_GetItemStringRef(), key is present
3539
+ get_value = Py_Ellipsis ; // marker value
3540
+ if (PyDict_GetItemStringRef (dict , "key" , & get_value ) < 0 ) {
3541
+ goto error ;
3542
+ }
3543
+ assert (get_value == value );
3544
+ Py_DECREF (get_value );
3545
+
3546
+ // test PyDict_Contains(), missing key
3547
+ assert (PyDict_Contains (dict , missing_key ) == 0 );
3548
+
3549
+ // test PyDict_GetItem(), missing key
3550
+ assert (PyDict_GetItem (dict , missing_key ) == NULL );
3551
+ assert (!PyErr_Occurred ());
3552
+
3553
+ // test PyDict_GetItemString(), missing key
3554
+ assert (PyDict_GetItemString (dict , "missing_key" ) == NULL );
3555
+ assert (!PyErr_Occurred ());
3556
+
3557
+ // test PyDict_GetItemWithError(), missing key
3558
+ assert (PyDict_GetItem (dict , missing_key ) == NULL );
3559
+ assert (!PyErr_Occurred ());
3560
+
3561
+ // test PyDict_GetItemRef(), missing key
3562
+ get_value = Py_Ellipsis ; // marker value
3563
+ assert (PyDict_GetItemRef (dict , missing_key , & get_value ) == 0 );
3564
+ assert (!PyErr_Occurred ());
3565
+ assert (get_value == NULL );
3566
+
3567
+ // test PyDict_GetItemStringRef(), missing key
3568
+ get_value = Py_Ellipsis ; // marker value
3569
+ assert (PyDict_GetItemStringRef (dict , "missing_key" , & get_value ) == 0 );
3570
+ assert (!PyErr_Occurred ());
3571
+ assert (get_value == NULL );
3572
+
3573
+ // test PyDict_GetItem(), invalid dict
3574
+ PyObject * invalid_dict = key ; // borrowed reference
3575
+ assert (PyDict_GetItem (invalid_dict , key ) == NULL );
3576
+ assert (!PyErr_Occurred ());
3577
+
3578
+ // test PyDict_GetItemWithError(), invalid dict
3579
+ assert (PyDict_GetItemWithError (invalid_dict , key ) == NULL );
3580
+ assert (PyErr_ExceptionMatches (PyExc_SystemError ));
3581
+ PyErr_Clear ();
3582
+
3583
+ // test PyDict_GetItemRef(), invalid dict
3584
+ get_value = Py_Ellipsis ; // marker value
3585
+ assert (PyDict_GetItemRef (invalid_dict , key , & get_value ) == -1 );
3586
+ assert (PyErr_ExceptionMatches (PyExc_SystemError ));
3587
+ PyErr_Clear ();
3588
+ assert (get_value == NULL );
3589
+
3590
+ // test PyDict_GetItemStringRef(), invalid dict
3591
+ get_value = Py_Ellipsis ; // marker value
3592
+ assert (PyDict_GetItemStringRef (invalid_dict , "key" , & get_value ) == -1 );
3593
+ assert (PyErr_ExceptionMatches (PyExc_SystemError ));
3594
+ PyErr_Clear ();
3595
+ assert (get_value == NULL );
3596
+
3597
+ invalid_key = PyList_New (0 );
3598
+ if (invalid_key == NULL ) {
3599
+ goto error ;
3600
+ }
3601
+
3602
+ // test PyDict_Contains(), invalid key
3603
+ assert (PyDict_Contains (dict , invalid_key ) == -1 );
3604
+ assert (PyErr_ExceptionMatches (PyExc_TypeError ));
3605
+ PyErr_Clear ();
3606
+
3607
+ // test PyDict_GetItem(), invalid key
3608
+ assert (PyDict_GetItem (dict , invalid_key ) == NULL );
3609
+ assert (!PyErr_Occurred ());
3610
+
3611
+ // test PyDict_GetItemWithError(), invalid key
3612
+ assert (PyDict_GetItemWithError (dict , invalid_key ) == NULL );
3613
+ assert (PyErr_ExceptionMatches (PyExc_TypeError ));
3614
+ PyErr_Clear ();
3615
+
3616
+ // test PyDict_GetItemRef(), invalid key
3617
+ get_value = Py_Ellipsis ; // marker value
3618
+ assert (PyDict_GetItemRef (dict , invalid_key , & get_value ) == -1 );
3619
+ assert (PyErr_ExceptionMatches (PyExc_TypeError ));
3620
+ PyErr_Clear ();
3621
+ assert (get_value == NULL );
3622
+
3623
+ // test PyDict_DelItem(), key is present
3624
+ assert (PyDict_DelItem (dict , key ) == 0 );
3625
+ assert (PyDict_Size (dict ) == 0 );
3626
+
3627
+ // test PyDict_DelItem(), missing key
3628
+ assert (PyDict_DelItem (dict , missing_key ) == -1 );
3629
+ assert (PyErr_ExceptionMatches (PyExc_KeyError ));
3630
+ PyErr_Clear ();
3631
+
3632
+ // test PyDict_DelItem(), invalid key
3633
+ assert (PyDict_DelItem (dict , invalid_key ) == -1 );
3634
+ assert (PyErr_ExceptionMatches (PyExc_TypeError ));
3635
+ PyErr_Clear ();
3636
+
3637
+ // test PyDict_Clear()
3638
+ PyDict_Clear (dict );
3639
+
3640
+ Py_DECREF (dict );
3641
+ Py_DECREF (key );
3642
+ Py_DECREF (missing_key );
3643
+ Py_DECREF (value );
3644
+ Py_DECREF (invalid_key );
3645
+
3646
+ Py_RETURN_NONE ;
3647
+
3648
+ error :
3649
+ Py_XDECREF (dict );
3650
+ Py_XDECREF (key );
3651
+ Py_XDECREF (missing_key );
3652
+ Py_XDECREF (value );
3653
+ Py_XDECREF (invalid_key );
3654
+ return NULL ;
3655
+ }
3656
+
3657
+
3469
3658
static PyMethodDef TestMethods [] = {
3470
3659
{"set_errno" , set_errno , METH_VARARGS },
3471
3660
{"test_config" , test_config , METH_NOARGS },
@@ -3611,6 +3800,7 @@ static PyMethodDef TestMethods[] = {
3611
3800
{"test_atexit" , test_atexit , METH_NOARGS },
3612
3801
{"check_pyimport_addmodule" , check_pyimport_addmodule , METH_VARARGS },
3613
3802
{"test_weakref_capi" , test_weakref_capi , METH_NOARGS },
3803
+ {"test_dict_capi" , test_dict_capi , METH_NOARGS },
3614
3804
{NULL , NULL } /* sentinel */
3615
3805
};
3616
3806
0 commit comments