LCOV - code coverage report
Current view: | top level - Objects - abstract.c (source / functions) |  |  | Hit | Total | Coverage
Test: | CPython 3.12 LCOV report [commit 5e6661bce9] |  | Lines: | 589 | 1454 | 40.5 %
Date: | 2023-03-20 08:15:36 |  | Functions: | 84 | 131 | 64.1 %
|  |  | Branches: | 338 | 984 | 34.3 %

               Branch data     Line data    Source code
           1                 :            : /* Abstract Object Interface (many thanks to Jim Fulton) */
           2                 :            :
           3                 :            : #include "Python.h"
           4                 :            : #include "pycore_abstract.h"      // _PyIndex_Check()
           5                 :            : #include "pycore_call.h"          // _PyObject_CallNoArgs()
           6                 :            : #include "pycore_ceval.h"         // _Py_EnterRecursiveCallTstate()
           7                 :            : #include "pycore_object.h"        // _Py_CheckSlotResult()
           8                 :            : #include "pycore_pyerrors.h"      // _PyErr_Occurred()
           9                 :            : #include "pycore_pystate.h"       // _PyThreadState_GET()
          10                 :            : #include "pycore_unionobject.h"   // _PyUnion_Check()
          11                 :            : #include <ctype.h>
          12                 :            : #include <stddef.h>               // offsetof()
          13                 :            :
          14                 :            :
          15                 :            :
          16                 :            : /* Shorthands to return certain errors */
          17                 :            :
          18                 :            : static PyObject *
          19                 :         88 : type_error(const char *msg, PyObject *obj)
          20                 :            : {
          21                 :         88 :     PyErr_Format(PyExc_TypeError, msg, Py_TYPE(obj)->tp_name);
          22                 :         88 :     return NULL;
          23                 :            : }
          24                 :            :
          25                 :            : static PyObject *
          26                 :          0 : null_error(void)
          27                 :            : {
          28                 :          0 :     PyThreadState *tstate = _PyThreadState_GET();
          29         [ #  # ]:          0 :     if (!_PyErr_Occurred(tstate)) {
          30                 :          0 :         _PyErr_SetString(tstate, PyExc_SystemError,
          31                 :            :                          "null argument to internal routine");
          32                 :            :     }
          33                 :          0 :     return NULL;
          34                 :            : }
          35                 :            :
          36                 :            : /* Operations on any object */
          37                 :            :
          38                 :            : PyObject *
          39                 :         81 : PyObject_Type(PyObject *o)
          40                 :            : {
          41                 :            :     PyObject *v;
          42                 :            :
          43         [ -  + ]:         81 :     if (o == NULL) {
          44                 :          0 :         return null_error();
          45                 :            :     }
          46                 :            :
          47                 :         81 :     v = (PyObject *)Py_TYPE(o);
          48                 :         81 :     return Py_NewRef(v);
          49                 :            : }
          50                 :            :
          51                 :            : Py_ssize_t
          52                 :      47322 : PyObject_Size(PyObject *o)
          53                 :            : {
          54         [ -  + ]:      47322 :     if (o == NULL) {
          55                 :          0 :         null_error();
          56                 :          0 :         return -1;
          57                 :            :     }
          58                 :            :
          59                 :      47322 :     PySequenceMethods *m = Py_TYPE(o)->tp_as_sequence;
          60   [ +  -  +  + ]:      47322 :     if (m && m->sq_length) {
          61                 :      46948 :         Py_ssize_t len = m->sq_length(o);
          62                 :            :         assert(_Py_CheckSlotResult(o, "__len__", len >= 0));
          63                 :      46948 :         return len;
          64                 :            :     }
          65                 :            :
          66                 :        374 :     return PyMapping_Size(o);
          67                 :            : }
          68                 :            :
          69                 :            : #undef PyObject_Length
          70                 :            : Py_ssize_t
          71                 :          0 : PyObject_Length(PyObject *o)
          72                 :            : {
          73                 :          0 :     return PyObject_Size(o);
          74                 :            : }
          75                 :            : #define PyObject_Length PyObject_Size
          76                 :            :
          77                 :            : int
          78                 :      24012 : _PyObject_HasLen(PyObject *o) {
          79   [ +  +  +  + ]:      46238 :     return (Py_TYPE(o)->tp_as_sequence && Py_TYPE(o)->tp_as_sequence->sq_length) ||
          80   [ +  +  +  + ]:      22226 :         (Py_TYPE(o)->tp_as_mapping && Py_TYPE(o)->tp_as_mapping->mp_length);
          81                 :            : }
          82                 :            :
          83                 :            : /* The length hint function returns a non-negative value from o.__len__()
          84                 :            :    or o.__length_hint__(). If those methods aren't found the defaultvalue is
          85                 :            :    returned.  If one of the calls fails with an exception other than TypeError
          86                 :            :    this function returns -1.
          87                 :            : */
          88                 :            :
          89                 :            : Py_ssize_t
          90                 :      23997 : PyObject_LengthHint(PyObject *o, Py_ssize_t defaultvalue)
          91                 :            : {
          92                 :            :     PyObject *hint, *result;
          93                 :            :     Py_ssize_t res;
          94         [ +  + ]:      23997 :     if (_PyObject_HasLen(o)) {
          95                 :       1928 :         res = PyObject_Length(o);
          96         [ -  + ]:       1928 :         if (res < 0) {
          97                 :          0 :             PyThreadState *tstate = _PyThreadState_GET();
          98                 :            :             assert(_PyErr_Occurred(tstate));
          99         [ #  # ]:          0 :             if (!_PyErr_ExceptionMatches(tstate, PyExc_TypeError)) {
         100                 :          0 :                 return -1;
         101                 :            :             }
         102                 :          0 :             _PyErr_Clear(tstate);
         103                 :            :         }
         104                 :            :         else {
         105                 :       1928 :             return res;
         106                 :            :         }
         107                 :            :     }
         108                 :      22069 :     hint = _PyObject_LookupSpecial(o, &_Py_ID(__length_hint__));
         109         [ +  + ]:      22069 :     if (hint == NULL) {
         110         [ -  + ]:      19031 :         if (PyErr_Occurred()) {
         111                 :          0 :             return -1;
         112                 :            :         }
         113                 :      19031 :         return defaultvalue;
         114                 :            :     }
         115                 :       3038 :     result = _PyObject_CallNoArgs(hint);
         116                 :       3038 :     Py_DECREF(hint);
         117         [ -  + ]:       3038 :     if (result == NULL) {
         118                 :          0 :         PyThreadState *tstate = _PyThreadState_GET();
         119         [ #  # ]:          0 :         if (_PyErr_ExceptionMatches(tstate, PyExc_TypeError)) {
         120                 :          0 :             _PyErr_Clear(tstate);
         121                 :          0 :             return defaultvalue;
         122                 :            :         }
         123                 :          0 :         return -1;
         124                 :            :     }
         125         [ -  + ]:       3038 :     else if (result == Py_NotImplemented) {
         126                 :          0 :         Py_DECREF(result);
         127                 :          0 :         return defaultvalue;
         128                 :            :     }
         129         [ -  + ]:       3038 :     if (!PyLong_Check(result)) {
         130                 :          0 :         PyErr_Format(PyExc_TypeError, "__length_hint__ must be an integer, not %.100s",
         131                 :          0 :             Py_TYPE(result)->tp_name);
         132                 :          0 :         Py_DECREF(result);
         133                 :          0 :         return -1;
         134                 :            :     }
         135                 :       3038 :     res = PyLong_AsSsize_t(result);
         136                 :       3038 :     Py_DECREF(result);
         137   [ -  +  -  - ]:       3038 :     if (res < 0 && PyErr_Occurred()) {
         138                 :          0 :         return -1;
         139                 :            :     }
         140         [ -  + ]:       3038 :     if (res < 0) {
         141                 :          0 :         PyErr_Format(PyExc_ValueError, "__length_hint__() should return >= 0");
         142                 :          0 :         return -1;
         143                 :            :     }
         144                 :       3038 :     return res;
         145                 :            : }
         146                 :            :
         147                 :            : PyObject *
         148                 :     200351 : PyObject_GetItem(PyObject *o, PyObject *key)
         149                 :            : {
         150   [ +  -  -  + ]:     200351 :     if (o == NULL || key == NULL) {
         151                 :          0 :         return null_error();
         152                 :            :     }
         153                 :            :
         154                 :     200351 :     PyMappingMethods *m = Py_TYPE(o)->tp_as_mapping;
         155   [ +  +  +  + ]:     200351 :     if (m && m->mp_subscript) {
         156                 :     200266 :         PyObject *item = m->mp_subscript(o, key);
         157                 :            :         assert(_Py_CheckSlotResult(o, "__getitem__", item != NULL));
         158                 :     200266 :         return item;
         159                 :            :     }
         160                 :            :
         161                 :         85 :     PySequenceMethods *ms = Py_TYPE(o)->tp_as_sequence;
         162   [ +  +  -  + ]:         85 :     if (ms && ms->sq_item) {
         163         [ #  # ]:          0 :         if (_PyIndex_Check(key)) {
         164                 :            :             Py_ssize_t key_value;
         165                 :          0 :             key_value = PyNumber_AsSsize_t(key, PyExc_IndexError);
         166   [ #  #  #  # ]:          0 :             if (key_value == -1 && PyErr_Occurred())
         167                 :          0 :                 return NULL;
         168                 :          0 :             return PySequence_GetItem(o, key_value);
         169                 :            :         }
         170                 :            :         else {
         171                 :          0 :             return type_error("sequence index must "
         172                 :            :                               "be integer, not '%.200s'", key);
         173                 :            :         }
         174                 :            :     }
         175                 :            :
         176         [ +  - ]:         85 :     if (PyType_Check(o)) {
         177                 :            :         PyObject *meth, *result;
         178                 :            :
         179                 :            :         // Special case type[int], but disallow other types so str[int] fails
         180         [ +  + ]:         85 :         if ((PyTypeObject*)o == &PyType_Type) {
         181                 :          3 :             return Py_GenericAlias(o, key);
         182                 :            :         }
         183                 :            :
         184         [ -  + ]:         82 :         if (_PyObject_LookupAttr(o, &_Py_ID(__class_getitem__), &meth) < 0) {
         185                 :          0 :             return NULL;
         186                 :            :         }
         187   [ +  -  +  - ]:         82 :         if (meth && meth != Py_None) {
         188                 :         82 :             result = PyObject_CallOneArg(meth, key);
         189                 :         82 :             Py_DECREF(meth);
         190                 :         82 :             return result;
         191                 :            :         }
         192                 :          0 :         Py_XDECREF(meth);
         193                 :          0 :         PyErr_Format(PyExc_TypeError, "type '%.200s' is not subscriptable",
         194                 :            :                      ((PyTypeObject *)o)->tp_name);
         195                 :          0 :         return NULL;
         196                 :            :     }
         197                 :            :
         198                 :          0 :     return type_error("'%.200s' object is not subscriptable", o);
         199                 :            : }
         200                 :            :
         201                 :            : int
         202                 :      10336 : PyObject_SetItem(PyObject *o, PyObject *key, PyObject *value)
         203                 :            : {
         204   [ +  -  +  -  :      10336 :     if (o == NULL || key == NULL || value == NULL) {
                       -  + ]
         205                 :          0 :         null_error();
         206                 :          0 :         return -1;
         207                 :            :     }
         208                 :            :
         209                 :      10336 :     PyMappingMethods *m = Py_TYPE(o)->tp_as_mapping;
         210   [ +  -  +  - ]:      10336 :     if (m && m->mp_ass_subscript) {
         211                 :      10336 :         int res = m->mp_ass_subscript(o, key, value);
         212                 :            :         assert(_Py_CheckSlotResult(o, "__setitem__", res >= 0));
         213                 :      10336 :         return res;
         214                 :            :     }
         215                 :            :
         216         [ #  # ]:          0 :     if (Py_TYPE(o)->tp_as_sequence) {
         217         [ #  # ]:          0 :         if (_PyIndex_Check(key)) {
         218                 :            :             Py_ssize_t key_value;
         219                 :          0 :             key_value = PyNumber_AsSsize_t(key, PyExc_IndexError);
         220   [ #  #  #  # ]:          0 :             if (key_value == -1 && PyErr_Occurred())
         221                 :          0 :                 return -1;
         222                 :          0 :             return PySequence_SetItem(o, key_value, value);
         223                 :            :         }
         224         [ #  # ]:          0 :         else if (Py_TYPE(o)->tp_as_sequence->sq_ass_item) {
         225                 :          0 :             type_error("sequence index must be "
         226                 :            :                        "integer, not '%.200s'", key);
         227                 :          0 :             return -1;
         228                 :            :         }
         229                 :            :     }
         230                 :            :
         231                 :          0 :     type_error("'%.200s' object does not support item assignment", o);
         232                 :          0 :     return -1;
         233                 :            : }
         234                 :            :
         235                 :            : int
         236                 :       1753 : PyObject_DelItem(PyObject *o, PyObject *key)
         237                 :            : {
         238   [ +  -  -  + ]:       1753 :     if (o == NULL || key == NULL) {
         239                 :          0 :         null_error();
         240                 :          0 :         return -1;
         241                 :            :     }
         242                 :            :
         243                 :       1753 :     PyMappingMethods *m = Py_TYPE(o)->tp_as_mapping;
         244   [ +  -  +  - ]:       1753 :     if (m && m->mp_ass_subscript) {
         245                 :       1753 :         int res = m->mp_ass_subscript(o, key, (PyObject*)NULL);
         246                 :            :         assert(_Py_CheckSlotResult(o, "__delitem__", res >= 0));
         247                 :       1753 :         return res;
         248                 :            :     }
         249                 :            :
         250         [ #  # ]:          0 :     if (Py_TYPE(o)->tp_as_sequence) {
         251         [ #  # ]:          0 :         if (_PyIndex_Check(key)) {
         252                 :            :             Py_ssize_t key_value;
         253                 :          0 :             key_value = PyNumber_AsSsize_t(key, PyExc_IndexError);
         254   [ #  #  #  # ]:          0 :             if (key_value == -1 && PyErr_Occurred())
         255                 :          0 :                 return -1;
         256                 :          0 :             return PySequence_DelItem(o, key_value);
         257                 :            :         }
         258         [ #  # ]:          0 :         else if (Py_TYPE(o)->tp_as_sequence->sq_ass_item) {
         259                 :          0 :             type_error("sequence index must be "
         260                 :            :                        "integer, not '%.200s'", key);
         261                 :          0 :             return -1;
         262                 :            :         }
         263                 :            :     }
         264                 :            :
         265                 :          0 :     type_error("'%.200s' object does not support item deletion", o);
         266                 :          0 :     return -1;
         267                 :            : }
         268                 :            :
         269                 :            : int
         270                 :          0 : PyObject_DelItemString(PyObject *o, const char *key)
         271                 :            : {
         272                 :            :     PyObject *okey;
         273                 :            :     int ret;
         274                 :            :
         275   [ #  #  #  # ]:          0 :     if (o == NULL || key == NULL) {
         276                 :          0 :         null_error();
         277                 :          0 :         return -1;
         278                 :            :     }
         279                 :          0 :     okey = PyUnicode_FromString(key);
         280         [ #  # ]:          0 :     if (okey == NULL)
         281                 :          0 :         return -1;
         282                 :          0 :     ret = PyObject_DelItem(o, okey);
         283                 :          0 :     Py_DECREF(okey);
         284                 :          0 :     return ret;
         285                 :            : }
         286                 :            :
         287                 :            :
         288                 :            : /* Return 1 if the getbuffer function is available, otherwise return 0. */
         289                 :            : int
         290                 :       2795 : PyObject_CheckBuffer(PyObject *obj)
         291                 :            : {
         292                 :       2795 :     PyBufferProcs *tp_as_buffer = Py_TYPE(obj)->tp_as_buffer;
         293   [ +  +  +  - ]:       2795 :     return (tp_as_buffer != NULL && tp_as_buffer->bf_getbuffer != NULL);
         294                 :            : }
         295                 :            :
         296                 :            :
         297                 :            : /* We release the buffer right after use of this function which could
         298                 :            :    cause issues later on.  Don't use these functions in new code.
         299                 :            :  */
         300                 :            : int
         301                 :          0 : PyObject_CheckReadBuffer(PyObject *obj)
         302                 :            : {
         303                 :          0 :     PyBufferProcs *pb = Py_TYPE(obj)->tp_as_buffer;
         304                 :            :     Py_buffer view;
         305                 :            :
         306         [ #  # ]:          0 :     if (pb == NULL ||
         307         [ #  # ]:          0 :         pb->bf_getbuffer == NULL)
         308                 :          0 :         return 0;
         309         [ #  # ]:          0 :     if ((*pb->bf_getbuffer)(obj, &view, PyBUF_SIMPLE) == -1) {
         310                 :          0 :         PyErr_Clear();
         311                 :          0 :         return 0;
         312                 :            :     }
         313                 :          0 :     PyBuffer_Release(&view);
         314                 :          0 :     return 1;
         315                 :            : }
         316                 :            :
         317                 :            : static int
         318                 :          0 : as_read_buffer(PyObject *obj, const void **buffer, Py_ssize_t *buffer_len)
         319                 :            : {
         320                 :            :     Py_buffer view;
         321                 :            :
         322   [ #  #  #  #  :          0 :     if (obj == NULL || buffer == NULL || buffer_len == NULL) {
                       #  # ]
         323                 :          0 :         null_error();
         324                 :          0 :         return -1;
         325                 :            :     }
         326         [ #  # ]:          0 :     if (PyObject_GetBuffer(obj, &view, PyBUF_SIMPLE) != 0)
         327                 :          0 :         return -1;
         328                 :            :
         329                 :          0 :     *buffer = view.buf;
         330                 :          0 :     *buffer_len = view.len;
         331                 :          0 :     PyBuffer_Release(&view);
         332                 :          0 :     return 0;
         333                 :            : }
         334                 :            :
         335                 :            : int
         336                 :          0 : PyObject_AsCharBuffer(PyObject *obj,
         337                 :            :                       const char **buffer,
         338                 :            :                       Py_ssize_t *buffer_len)
         339                 :            : {
         340                 :          0 :     return as_read_buffer(obj, (const void **)buffer, buffer_len);
         341                 :            : }
         342                 :            :
         343                 :          0 : int PyObject_AsReadBuffer(PyObject *obj,
         344                 :            :                           const void **buffer,
         345                 :            :                           Py_ssize_t *buffer_len)
         346                 :            : {
         347                 :          0 :     return as_read_buffer(obj, buffer, buffer_len);
         348                 :            : }
         349                 :            :
         350                 :          0 : int PyObject_AsWriteBuffer(PyObject *obj,
         351                 :            :                            void **buffer,
         352                 :            :                            Py_ssize_t *buffer_len)
         353                 :            : {
         354                 :            :     PyBufferProcs *pb;
         355                 :            :     Py_buffer view;
         356                 :            :
         357   [ #  #  #  #  :          0 :     if (obj == NULL || buffer == NULL || buffer_len == NULL) {
                       #  # ]
         358                 :          0 :         null_error();
         359                 :          0 :         return -1;
         360                 :            :     }
         361                 :          0 :     pb = Py_TYPE(obj)->tp_as_buffer;
         362         [ #  # ]:          0 :     if (pb == NULL ||
         363   [ #  #  #  # ]:          0 :         pb->bf_getbuffer == NULL ||
         364                 :          0 :         ((*pb->bf_getbuffer)(obj, &view, PyBUF_WRITABLE) != 0)) {
         365                 :          0 :         PyErr_SetString(PyExc_TypeError,
         366                 :            :                         "expected a writable bytes-like object");
         367                 :          0 :         return -1;
         368                 :            :     }
         369                 :            :
         370                 :          0 :     *buffer = view.buf;
         371                 :          0 :     *buffer_len = view.len;
         372                 :          0 :     PyBuffer_Release(&view);
         373                 :          0 :     return 0;
         374                 :            : }
         375                 :            :
         376                 :            : /* Buffer C-API for Python 3.0 */
         377                 :            :
         378                 :            : int
         379                 :      24304 : PyObject_GetBuffer(PyObject *obj, Py_buffer *view, int flags)
         380                 :            : {
         381                 :      24304 :     PyBufferProcs *pb = Py_TYPE(obj)->tp_as_buffer;
         382                 :            :
         383   [ +  -  -  + ]:      24304 :     if (pb == NULL || pb->bf_getbuffer == NULL) {
         384                 :          0 :         PyErr_Format(PyExc_TypeError,
         385                 :            :                      "a bytes-like object is required, not '%.100s'",
         386                 :          0 :                      Py_TYPE(obj)->tp_name);
         387                 :          0 :         return -1;
         388                 :            :     }
         389                 :      24304 :     int res = (*pb->bf_getbuffer)(obj, view, flags);
         390                 :            :     assert(_Py_CheckSlotResult(obj, "getbuffer", res >= 0));
         391                 :      24304 :     return res;
         392                 :            : }
         393                 :            :
         394                 :            : static int
         395                 :          0 : _IsFortranContiguous(const Py_buffer *view)
         396                 :            : {
         397                 :            :     Py_ssize_t sd, dim;
         398                 :            :     int i;
         399                 :            :
         400                 :            :     /* 1) len = product(shape) * itemsize
         401                 :            :        2) itemsize > 0
         402                 :            :        3) len = 0 <==> exists i: shape[i] = 0 */
         403         [ #  # ]:          0 :     if (view->len == 0) return 1;
         404         [ #  # ]:          0 :     if (view->strides == NULL) {  /* C-contiguous by definition */
         405                 :            :         /* Trivially F-contiguous */
         406         [ #  # ]:          0 :         if (view->ndim <= 1) return 1;
         407                 :            :
         408                 :            :         /* ndim > 1 implies shape != NULL */
         409                 :            :         assert(view->shape != NULL);
         410                 :            :
         411                 :            :         /* Effectively 1-d */
         412                 :          0 :         sd = 0;
         413         [ #  # ]:          0 :         for (i=0; i<view->ndim; i++) {
         414         [ #  # ]:          0 :             if (view->shape[i] > 1) sd += 1;
         415                 :            :         }
         416                 :          0 :         return sd <= 1;
         417                 :            :     }
         418                 :            :
         419                 :            :     /* strides != NULL implies both of these */
         420                 :            :     assert(view->ndim > 0);
         421                 :            :     assert(view->shape != NULL);
         422                 :            :
         423                 :          0 :     sd = view->itemsize;
         424         [ #  # ]:          0 :     for (i=0; i<view->ndim; i++) {
         425                 :          0 :         dim = view->shape[i];
         426   [ #  #  #  # ]:          0 :         if (dim > 1 && view->strides[i] != sd) {
         427                 :          0 :             return 0;
         428                 :            :         }
         429                 :          0 :         sd *= dim;
         430                 :            :     }
         431                 :          0 :     return 1;
         432                 :            : }
         433                 :            :
         434                 :            : static int
         435                 :      10846 : _IsCContiguous(const Py_buffer *view)
         436                 :            : {
         437                 :            :     Py_ssize_t sd, dim;
         438                 :            :     int i;
         439                 :            :
         440                 :            :     /* 1) len = product(shape) * itemsize
         441                 :            :        2) itemsize > 0
         442                 :            :        3) len = 0 <==> exists i: shape[i] = 0 */
         443         [ +  + ]:      10846 :     if (view->len == 0) return 1;
         444         [ +  + ]:      10214 :     if (view->strides == NULL) return 1; /* C-contiguous by definition */
         445                 :            :
         446                 :            :     /* strides != NULL implies both of these */
         447                 :            :     assert(view->ndim > 0);
         448                 :            :     assert(view->shape != NULL);
         449                 :            :
         450                 :        164 :     sd = view->itemsize;
         451         [ +  + ]:        328 :     for (i=view->ndim-1; i>=0; i--) {
         452                 :        164 :         dim = view->shape[i];
         453   [ +  +  -  + ]:        164 :         if (dim > 1 && view->strides[i] != sd) {
         454                 :          0 :             return 0;
         455                 :            :         }
         456                 :        164 :         sd *= dim;
         457                 :            :     }
         458                 :        164 :     return 1;
         459                 :            : }
         460                 :            :
         461                 :            : int
         462                 :      10846 : PyBuffer_IsContiguous(const Py_buffer *view, char order)
         463                 :            : {
         464                 :            :
         465         [ -  + ]:      10846 :     if (view->suboffsets != NULL) return 0;
         466                 :            :
         467         [ +  - ]:      10846 :     if (order == 'C')
         468                 :      10846 :         return _IsCContiguous(view);
         469         [ #  # ]:          0 :     else if (order == 'F')
         470                 :          0 :         return _IsFortranContiguous(view);
         471         [ #  # ]:          0 :     else if (order == 'A')
         472   [ #  #  #  # ]:          0 :         return (_IsCContiguous(view) || _IsFortranContiguous(view));
         473                 :          0 :     return 0;
         474                 :            : }
         475                 :            :
         476                 :            :
         477                 :            : void*
         478                 :          0 : PyBuffer_GetPointer(const Py_buffer *view, const Py_ssize_t *indices)
         479                 :            : {
         480                 :            :     char* pointer;
         481                 :            :     int i;
         482                 :          0 :     pointer = (char *)view->buf;
         483         [ #  # ]:          0 :     for (i = 0; i < view->ndim; i++) {
         484                 :          0 :         pointer += view->strides[i]*indices[i];
         485   [ #  #  #  # ]:          0 :         if ((view->suboffsets != NULL) && (view->suboffsets[i] >= 0)) {
         486                 :          0 :             pointer = *((char**)pointer) + view->suboffsets[i];
         487                 :            :         }
         488                 :            :     }
         489                 :          0 :     return (void*)pointer;
         490                 :            : }
         491                 :            :
         492                 :            :
         493                 :            : void
         494                 :          0 : _Py_add_one_to_index_F(int nd, Py_ssize_t *index, const Py_ssize_t *shape)
         495                 :            : {
         496                 :            :     int k;
         497                 :            :
         498         [ #  # ]:          0 :     for (k=0; k<nd; k++) {
         499         [ #  # ]:          0 :         if (index[k] < shape[k]-1) {
         500                 :          0 :             index[k]++;
         501                 :          0 :             break;
         502                 :            :         }
         503                 :            :         else {
         504                 :          0 :             index[k] = 0;
         505                 :            :         }
         506                 :            :     }
         507                 :          0 : }
         508                 :            :
         509                 :            : void
         510                 :          0 : _Py_add_one_to_index_C(int nd, Py_ssize_t *index, const Py_ssize_t *shape)
         511                 :            : {
         512                 :            :     int k;
         513                 :            :
         514         [ #  # ]:          0 :     for (k=nd-1; k>=0; k--) {
         515         [ #  # ]:          0 :         if (index[k] < shape[k]-1) {
         516                 :          0 :             index[k]++;
         517                 :          0 :             break;
         518                 :            :         }
         519                 :            :         else {
         520                 :          0 :             index[k] = 0;
         521                 :            :         }
         522                 :            :     }
         523                 :          0 : }
         524                 :            :
         525                 :            : Py_ssize_t
         526                 :          0 : PyBuffer_SizeFromFormat(const char *format)
         527                 :            : {
         528                 :          0 :     PyObject *calcsize = NULL;
         529                 :          0 :     PyObject *res = NULL;
         530                 :          0 :     PyObject *fmt = NULL;
         531                 :          0 :     Py_ssize_t itemsize = -1;
         532                 :            :
         533                 :          0 :     calcsize = _PyImport_GetModuleAttrString("struct", "calcsize");
         534         [ #  # ]:          0 :     if (calcsize == NULL) {
         535                 :          0 :         goto done;
         536                 :            :     }
         537                 :            :
         538                 :          0 :     fmt = PyUnicode_FromString(format);
         539         [ #  # ]:          0 :     if (fmt == NULL) {
         540                 :          0 :         goto done;
         541                 :            :     }
         542                 :            :
         543                 :          0 :     res = PyObject_CallFunctionObjArgs(calcsize, fmt, NULL);
         544         [ #  # ]:          0 :     if (res == NULL) {
         545                 :          0 :         goto done;
         546                 :            :     }
         547                 :            :
         548                 :          0 :     itemsize = PyLong_AsSsize_t(res);
         549         [ #  # ]:          0 :     if (itemsize < 0) {
         550                 :          0 :         goto done;
         551                 :            :     }
         552                 :            :
         553                 :          0 : done:
         554                 :          0 :     Py_XDECREF(calcsize);
         555                 :          0 :     Py_XDECREF(fmt);
         556                 :          0 :     Py_XDECREF(res);
         557                 :          0 :     return itemsize;
         558                 :            : }
         559                 :            :
         560                 :            : int
         561                 :          0 : PyBuffer_FromContiguous(const Py_buffer *view, const void *buf, Py_ssize_t len, char fort)
         562                 :            : {
         563                 :            :     int k;
         564                 :            :     void (*addone)(int, Py_ssize_t *, const Py_ssize_t *);
         565                 :            :     Py_ssize_t *indices, elements;
         566                 :            :     char *ptr;
         567                 :            :     const char *src;
         568                 :            :
         569         [ #  # ]:          0 :     if (len > view->len) {
         570                 :          0 :         len = view->len;
         571                 :            :     }
         572                 :            :
         573         [ #  # ]:          0 :     if (PyBuffer_IsContiguous(view, fort)) {
         574                 :            :         /* simplest copy is all that is needed */
         575                 :          0 :         memcpy(view->buf, buf, len);
         576                 :          0 :         return 0;
         577                 :            :     }
         578                 :            :
         579                 :            :     /* Otherwise a more elaborate scheme is needed */
         580                 :            :
         581                 :            :     /* view->ndim <= 64 */
         582                 :          0 :     indices = (Py_ssize_t *)PyMem_Malloc(sizeof(Py_ssize_t)*(view->ndim));
         583         [ #  # ]:          0 :     if (indices == NULL) {
         584                 :          0 :         PyErr_NoMemory();
         585                 :          0 :         return -1;
         586                 :            :     }
         587         [ #  # ]:          0 :     for (k=0; k<view->ndim;k++) {
         588                 :          0 :         indices[k] = 0;
         589                 :            :     }
         590                 :            :
         591         [ #  # ]:          0 :     if (fort == 'F') {
         592                 :          0 :         addone = _Py_add_one_to_index_F;
         593                 :            :     }
         594                 :            :     else {
         595                 :          0 :         addone = _Py_add_one_to_index_C;
         596                 :            :     }
         597                 :          0 :     src = buf;
         598                 :            :     /* XXX : This is not going to be the fastest code in the world
         599                 :            :              several optimizations are possible.
         600                 :            :      */
         601                 :          0 :     elements = len / view->itemsize;
         602         [ #  # ]:          0 :     while (elements--) {
         603                 :          0 :         ptr = PyBuffer_GetPointer(view, indices);
         604                 :          0 :         memcpy(ptr, src, view->itemsize);
         605                 :          0 :         src += view->itemsize;
         606                 :          0 :         addone(view->ndim, indices, view->shape);
         607                 :            :     }
         608                 :            :
         609                 :          0 :     PyMem_Free(indices);
         610                 :          0 :     return 0;
         611                 :            : }
         612                 :            :
         613                 :          0 : int PyObject_CopyData(PyObject *dest, PyObject *src)
         614                 :            : {
         615                 :            :     Py_buffer view_dest, view_src;
         616                 :            :     int k;
         617                 :            :     Py_ssize_t *indices, elements;
         618                 :            :     char *dptr, *sptr;
         619                 :            :
         620   [ #  #  #  # ]:          0 :     if (!PyObject_CheckBuffer(dest) ||
         621                 :          0 :         !PyObject_CheckBuffer(src)) {
         622                 :          0 :         PyErr_SetString(PyExc_TypeError,
         623                 :            :                         "both destination and source must be "\
         624                 :            :                         "bytes-like objects");
         625                 :          0 :         return -1;
         626                 :            :     }
         627                 :            :
         628         [ #  # ]:          0 :     if (PyObject_GetBuffer(dest, &view_dest, PyBUF_FULL) != 0) return -1;
         629         [ #  # ]:          0 :     if (PyObject_GetBuffer(src, &view_src, PyBUF_FULL_RO) != 0) {
         630                 :          0 :         PyBuffer_Release(&view_dest);
         631                 :          0 :         return -1;
         632                 :            :     }
         633                 :            :
         634         [ #  # ]:          0 :     if (view_dest.len < view_src.len) {
         635                 :          0 :         PyErr_SetString(PyExc_BufferError,
         636                 :            :                         "destination is too small to receive data from source");
         637                 :          0 :         PyBuffer_Release(&view_dest);
         638                 :          0 :         PyBuffer_Release(&view_src);
         639                 :          0 :         return -1;
         640                 :            :     }
         641                 :            :
         642   [ #  #  #  # ]:          0 :     if ((PyBuffer_IsContiguous(&view_dest, 'C') &&
         643         [ #  # ]:          0 :          PyBuffer_IsContiguous(&view_src, 'C')) ||
         644         [ #  # ]:          0 :         (PyBuffer_IsContiguous(&view_dest, 'F') &&
         645                 :          0 :          PyBuffer_IsContiguous(&view_src, 'F'))) {
         646                 :            :         /* simplest copy is all that is needed */
         647                 :          0 :         memcpy(view_dest.buf, view_src.buf, view_src.len);
         648                 :          0 :         PyBuffer_Release(&view_dest);
         649                 :          0 :         PyBuffer_Release(&view_src);
         650                 :          0 :         return 0;
         651                 :            :     }
         652                 :            :
         653                 :            :     /* Otherwise a more elaborate copy scheme is needed */
         654                 :            :
         655                 :            :     /* XXX(nnorwitz): need to check for overflow! */
         656                 :          0 :     indices = (Py_ssize_t *)PyMem_Malloc(sizeof(Py_ssize_t)*view_src.ndim);
         657         [ #  # ]:          0 :     if (indices == NULL) {
         658                 :          0 :         PyErr_NoMemory();
         659                 :          0 :         PyBuffer_Release(&view_dest);
         660                 :          0 :         PyBuffer_Release(&view_src);
         661                 :          0 :         return -1;
         662                 :            :     }
         663         [ #  # ]:          0 :     for (k=0; k<view_src.ndim;k++) {
         664                 :          0 :         indices[k] = 0;
         665                 :            :     }
         666                 :          0 :     elements = 1;
         667         [ #  # ]:          0 :     for (k=0; k<view_src.ndim; k++) {
         668                 :            :         /* XXX(nnorwitz): can this overflow? */
         669                 :          0 :         elements *= view_src.shape[k];
         670                 :            :     }
         671         [ #  # ]:          0 :     while (elements--) {
         672                 :          0 :         _Py_add_one_to_index_C(view_src.ndim, indices, view_src.shape);
         673                 :          0 :         dptr = PyBuffer_GetPointer(&view_dest, indices);
         674                 :          0 :         sptr = PyBuffer_GetPointer(&view_src, indices);
         675                 :          0 :         memcpy(dptr, sptr, view_src.itemsize);
         676                 :            :     }
         677                 :          0 :     PyMem_Free(indices);
         678                 :          0 :     PyBuffer_Release(&view_dest);
         679                 :          0 :     PyBuffer_Release(&view_src);
         680                 :          0 :     return 0;
         681                 :            : }
         682                 :            :
         683                 :            : void
         684                 :          0 : PyBuffer_FillContiguousStrides(int nd, Py_ssize_t *shape,
         685                 :            :                                Py_ssize_t *strides, int itemsize,
         686                 :            :                                char fort)
         687                 :            : {
         688                 :            :     int k;
         689                 :            :     Py_ssize_t sd;
         690                 :            :
         691                 :          0 :     sd = itemsize;
         692         [ #  # ]:          0 :     if (fort == 'F') {
         693         [ #  # ]:          0 :         for (k=0; k<nd; k++) {
         694                 :          0 :             strides[k] = sd;
         695                 :          0 :             sd *= shape[k];
         696                 :            :         }
         697                 :            :     }
         698                 :            :     else {
         699         [ #  # ]:          0 :         for (k=nd-1; k>=0; k--) {
         700                 :          0 :             strides[k] = sd;
         701                 :          0 :             sd *= shape[k];
         702                 :            :         }
         703                 :            :     }
         704                 :          0 :     return;
         705                 :            : }
         706                 :            :
         707                 :            : int
         708                 :      23918 : PyBuffer_FillInfo(Py_buffer *view, PyObject *obj, void *buf, Py_ssize_t len,
         709                 :            :                   int readonly, int flags)
         710                 :            : {
         711         [ -  + ]:      23918 :     if (view == NULL) {
         712                 :          0 :         PyErr_SetString(PyExc_BufferError,
         713                 :            :                         "PyBuffer_FillInfo: view==NULL argument is obsolete");
         714                 :          0 :         return -1;
         715                 :            :     }
         716                 :            :
         717   [ +  +  -  + ]:      23918 :     if (((flags & PyBUF_WRITABLE) == PyBUF_WRITABLE) &&
         718                 :            :         (readonly == 1)) {
         719                 :          0 :         PyErr_SetString(PyExc_BufferError,
         720                 :            :                         "Object is not writable.");
         721                 :          0 :         return -1;
         722                 :            :     }
         723                 :            :
         724                 :      23918 :     view->obj = Py_XNewRef(obj);
         725                 :      23918 :     view->buf = buf;
         726                 :      23918 :     view->len = len;
         727                 :      23918 :     view->readonly = readonly;
         728                 :      23918 :     view->itemsize = 1;
         729                 :      23918 :     view->format = NULL;
         730         [ +  + ]:      23918 :     if ((flags & PyBUF_FORMAT) == PyBUF_FORMAT)
         731                 :        554 :         view->format = "B";
         732                 :      23918 :     view->ndim = 1;
         733                 :      23918 :     view->shape = NULL;
         734         [ +  + ]:      23918 :     if ((flags & PyBUF_ND) == PyBUF_ND)
         735                 :       5406 :         view->shape = &(view->len);
         736                 :      23918 :     view->strides = NULL;
         737         [ +  + ]:      23918 :     if ((flags & PyBUF_STRIDES) == PyBUF_STRIDES)
         738                 :        554 :         view->strides = &(view->itemsize);
         739                 :      23918 :     view->suboffsets = NULL;
         740                 :      23918 :     view->internal = NULL;
         741                 :      23918 :     return 0;
         742                 :            : }
         743                 :            :
         744                 :            : void
         745                 :      38500 : PyBuffer_Release(Py_buffer *view)
         746                 :            : {
         747                 :      38500 :     PyObject *obj = view->obj;
         748                 :            :     PyBufferProcs *pb;
         749         [ +  + ]:      38500 :     if (obj == NULL)
         750                 :      14196 :         return;
         751                 :      24304 :     pb = Py_TYPE(obj)->tp_as_buffer;
         752   [ +  -  +  + ]:      24304 :     if (pb && pb->bf_releasebuffer) {
         753                 :       5403 :         pb->bf_releasebuffer(obj, view);
         754                 :            :     }
         755                 :      24304 :     view->obj = NULL;
         756                 :      24304 :     Py_DECREF(obj);
         757                 :            : }
         758                 :            :
         759                 :            : PyObject *
         760                 :     304040 : PyObject_Format(PyObject *obj, PyObject *format_spec)
         761                 :            : {
         762                 :            :     PyObject *meth;
         763                 :     304040 :     PyObject *empty = NULL;
         764                 :     304040 :     PyObject *result = NULL;
         765                 :            :
         766   [ +  +  -  + ]:     304040 :     if (format_spec != NULL && !PyUnicode_Check(format_spec)) {
         767                 :          0 :         PyErr_Format(PyExc_SystemError,
         768                 :            :                      "Format specifier must be a string, not %.200s",
         769                 :          0 :                      Py_TYPE(format_spec)->tp_name);
         770                 :          0 :         return NULL;
         771                 :            :     }
         772                 :            :
         773                 :            :     /* Fast path for common types. */
         774   [ +  +  -  + ]:     304040 :     if (format_spec == NULL || PyUnicode_GET_LENGTH(format_spec) == 0) {
         775         [ -  + ]:      35767 :         if (PyUnicode_CheckExact(obj)) {
         776                 :          0 :             return Py_NewRef(obj);
         777                 :            :         }
         778         [ +  + ]:      35767 :         if (PyLong_CheckExact(obj)) {
         779                 :      32635 :             return PyObject_Str(obj);
         780                 :            :         }
         781                 :            :     }
         782                 :            :
         783                 :            :     /* If no format_spec is provided, use an empty string */
         784         [ +  + ]:     271405 :     if (format_spec == NULL) {
         785                 :       3132 :         empty = PyUnicode_New(0, 0);
         786                 :       3132 :         format_spec = empty;
         787                 :            :     }
         788                 :            :
         789                 :            :     /* Find the (unbound!) __format__ method */
         790                 :     271405 :     meth = _PyObject_LookupSpecial(obj, &_Py_ID(__format__));
         791         [ -  + ]:     271405 :     if (meth == NULL) {
         792                 :          0 :         PyThreadState *tstate = _PyThreadState_GET();
         793         [ #  # ]:          0 :         if (!_PyErr_Occurred(tstate)) {
         794                 :          0 :             _PyErr_Format(tstate, PyExc_TypeError,
         795                 :            :                           "Type %.100s doesn't define __format__",
         796                 :          0 :                           Py_TYPE(obj)->tp_name);
         797                 :            :         }
         798                 :          0 :         goto done;
         799                 :            :     }
         800                 :            :
         801                 :            :     /* And call it. */
         802                 :     271405 :     result = PyObject_CallOneArg(meth, format_spec);
         803                 :     271405 :     Py_DECREF(meth);
         804                 :            :
         805   [ -  +  +  - ]:     271405 :     if (result && !PyUnicode_Check(result)) {
         806                 :          0 :         PyErr_Format(PyExc_TypeError,
         807                 :            :                      "__format__ must return a str, not %.200s",
         808                 :          0 :                      Py_TYPE(result)->tp_name);
         809                 :          0 :         Py_SETREF(result, NULL);
         810                 :          0 :         goto done;
         811                 :            :     }
         812                 :            :
         813                 :     271405 : done:
         814                 :     271405 :     Py_XDECREF(empty);
         815                 :     271405 :     return result;
         816                 :            : }
         817                 :            : /* Operations on numbers */
         818                 :            :
         819                 :            : int
         820                 :       1619 : PyNumber_Check(PyObject *o)
         821                 :            : {
         822         [ -  + ]:       1619 :     if (o == NULL)
         823                 :          0 :         return 0;
         824                 :       1619 :     PyNumberMethods *nb = Py_TYPE(o)->tp_as_number;
         825   [ +  -  +  +  :       1619 :     return nb && (nb->nb_index || nb->nb_int || nb->nb_float || PyComplex_Check(o));
              +  -  +  -  -
                          + ]
         826                 :            : }
         827                 :            :
         828                 :            : /* Binary operators */
         829                 :            :
         830                 :            : #define NB_SLOT(x) offsetof(PyNumberMethods, x)
         831                 :            : #define NB_BINOP(nb_methods, slot) \
         832                 :            :         (*(binaryfunc*)(& ((char*)nb_methods)[slot]))
         833                 :            : #define NB_TERNOP(nb_methods, slot) \
         834                 :            :         (*(ternaryfunc*)(& ((char*)nb_methods)[slot]))
         835                 :            :
         836                 :            : /*
         837                 :            :   Calling scheme used for binary operations:
         838                 :            :
         839                 :            :   Order operations are tried until either a valid result or error:
         840                 :            :     w.op(v,w)[*], v.op(v,w), w.op(v,w)
         841                 :            :
         842                 :            :   [*] only when Py_TYPE(v) != Py_TYPE(w) && Py_TYPE(w) is a subclass of
         843                 :            :       Py_TYPE(v)
         844                 :            :  */
         845                 :            :
         846                 :            : static PyObject *
         847                 :    3178178 : binary_op1(PyObject *v, PyObject *w, const int op_slot
         848                 :            : #ifndef NDEBUG
         849                 :            :            , const char *op_name
         850                 :            : #endif
         851                 :            :            )
         852                 :            : {
         853                 :            :     binaryfunc slotv;
         854         [ +  + ]:    3178178 :     if (Py_TYPE(v)->tp_as_number != NULL) {
         855                 :    3176110 :         slotv = NB_BINOP(Py_TYPE(v)->tp_as_number, op_slot);
         856                 :            :     }
         857                 :            :     else {
         858                 :       2068 :         slotv = NULL;
         859                 :            :     }
         860                 :            :
         861                 :            :     binaryfunc slotw;
         862   [ +  +  +  + ]:    3178178 :     if (!Py_IS_TYPE(w, Py_TYPE(v)) && Py_TYPE(w)->tp_as_number != NULL) {
         863                 :     382394 :         slotw = NB_BINOP(Py_TYPE(w)->tp_as_number, op_slot);
         864         [ +  + ]:     382394 :         if (slotw == slotv) {
         865                 :       2846 :             slotw = NULL;
         866                 :            :         }
         867                 :            :     }
         868                 :            :     else {
         869                 :    2795784 :         slotw = NULL;
         870                 :            :     }
         871                 :            :
         872         [ +  + ]:    3178178 :     if (slotv) {
         873                 :            :         PyObject *x;
         874   [ +  +  +  + ]:    3024457 :         if (slotw && PyType_IsSubtype(Py_TYPE(w), Py_TYPE(v))) {
         875                 :        144 :             x = slotw(v, w);
         876         [ +  - ]:        144 :             if (x != Py_NotImplemented)
         877                 :        144 :                 return x;
         878                 :          0 :             Py_DECREF(x); /* can't do it */
         879                 :          0 :             slotw = NULL;
         880                 :            :         }
         881                 :    3024313 :         x = slotv(v, w);
         882                 :            :         assert(_Py_CheckSlotResult(v, op_name, x != NULL));
         883         [ +  + ]:    3024313 :         if (x != Py_NotImplemented) {
         884                 :    2817249 :             return x;
         885                 :            :         }
         886                 :     207064 :         Py_DECREF(x); /* can't do it */
         887                 :            :     }
         888         [ +  + ]:     360785 :     if (slotw) {
         889                 :     355194 :         PyObject *x = slotw(v, w);
         890                 :            :         assert(_Py_CheckSlotResult(w, op_name, x != NULL));
         891         [ +  + ]:     355194 :         if (x != Py_NotImplemented) {
         892                 :     207048 :             return x;
         893                 :            :         }
         894                 :     148146 :         Py_DECREF(x); /* can't do it */
         895                 :            :     }
         896                 :     153737 :     Py_RETURN_NOTIMPLEMENTED;
         897                 :            : }
         898                 :            :
         899                 :            : #ifdef NDEBUG
         900                 :            : #  define BINARY_OP1(v, w, op_slot, op_name) binary_op1(v, w, op_slot)
         901                 :            : #else
         902                 :            : #  define BINARY_OP1(v, w, op_slot, op_name) binary_op1(v, w, op_slot, op_name)
         903                 :            : #endif
         904                 :            :
         905                 :            : static PyObject *
         906                 :          4 : binop_type_error(PyObject *v, PyObject *w, const char *op_name)
         907                 :            : {
         908                 :          4 :     PyErr_Format(PyExc_TypeError,
         909                 :            :                  "unsupported operand type(s) for %.100s: "
         910                 :            :                  "'%.100s' and '%.100s'",
         911                 :            :                  op_name,
         912                 :          4 :                  Py_TYPE(v)->tp_name,
         913                 :          4 :                  Py_TYPE(w)->tp_name);
         914                 :          4 :     return NULL;
         915                 :            : }
         916                 :            :
         917                 :            : static PyObject *
         918                 :    1049317 : binary_op(PyObject *v, PyObject *w, const int op_slot, const char *op_name)
         919                 :            : {
         920                 :    1049317 :     PyObject *result = BINARY_OP1(v, w, op_slot, op_name);
         921         [ -  + ]:    1049317 :     if (result == Py_NotImplemented) {
         922                 :          0 :         Py_DECREF(result);
         923                 :            :
         924   [ #  #  #  # ]:          0 :         if (op_slot == NB_SLOT(nb_rshift) &&
         925                 :          0 :             PyCFunction_CheckExact(v) &&
         926         [ #  # ]:          0 :             strcmp(((PyCFunctionObject *)v)->m_ml->ml_name, "print") == 0)
         927                 :            :         {
         928                 :          0 :             PyErr_Format(PyExc_TypeError,
         929                 :            :                 "unsupported operand type(s) for %.100s: "
         930                 :            :                 "'%.100s' and '%.100s'. Did you mean \"print(<message>, "
         931                 :            :                 "file=<output_stream>)\"?",
         932                 :            :                 op_name,
         933                 :          0 :                 Py_TYPE(v)->tp_name,
         934                 :          0 :                 Py_TYPE(w)->tp_name);
         935                 :          0 :             return NULL;
         936                 :            :         }
         937                 :          0 :         return binop_type_error(v, w, op_name);
         938                 :            :     }
         939                 :    1049317 :     return result;
         940                 :            : }
         941                 :            :
         942                 :            :
         943                 :            : /*
         944                 :            :   Calling scheme used for ternary operations:
         945                 :            :
         946                 :            :   Order operations are tried until either a valid result or error:
         947                 :            :     v.op(v,w,z), w.op(v,w,z), z.op(v,w,z)
         948                 :            :  */
         949                 :            :
         950                 :            : static PyObject *
         951                 :     216773 : ternary_op(PyObject *v,
         952                 :            :            PyObject *w,
         953                 :            :            PyObject *z,
         954                 :            :            const int op_slot,
         955                 :            :            const char *op_name
         956                 :            :            )
         957                 :            : {
         958                 :     216773 :     PyNumberMethods *mv = Py_TYPE(v)->tp_as_number;
         959                 :     216773 :     PyNumberMethods *mw = Py_TYPE(w)->tp_as_number;
         960                 :            :
         961                 :            :     ternaryfunc slotv;
         962         [ +  - ]:     216773 :     if (mv != NULL) {
         963                 :     216773 :         slotv = NB_TERNOP(mv, op_slot);
         964                 :            :     }
         965                 :            :     else {
         966                 :          0 :         slotv = NULL;
         967                 :            :     }
         968                 :            :
         969                 :            :     ternaryfunc slotw;
         970   [ +  +  +  - ]:     216773 :     if (!Py_IS_TYPE(w, Py_TYPE(v)) && mw != NULL) {
         971                 :     205233 :         slotw = NB_TERNOP(mw, op_slot);
         972         [ -  + ]:     205233 :         if (slotw == slotv) {
         973                 :          0 :             slotw = NULL;
         974                 :            :         }
         975                 :            :     }
         976                 :            :     else {
         977                 :      11540 :         slotw = NULL;
         978                 :            :     }
         979                 :            :
         980         [ +  - ]:     216773 :     if (slotv) {
         981                 :            :         PyObject *x;
         982   [ +  +  -  + ]:     216773 :         if (slotw && PyType_IsSubtype(Py_TYPE(w), Py_TYPE(v))) {
         983                 :          0 :             x = slotw(v, w, z);
         984         [ #  # ]:          0 :             if (x != Py_NotImplemented) {
         985                 :          0 :                 return x;
         986                 :            :             }
         987                 :          0 :             Py_DECREF(x); /* can't do it */
         988                 :          0 :             slotw = NULL;
         989                 :            :         }
         990                 :     216773 :         x = slotv(v, w, z);
         991                 :            :         assert(_Py_CheckSlotResult(v, op_name, x != NULL));
         992         [ +  + ]:     216773 :         if (x != Py_NotImplemented) {
         993                 :     216771 :             return x;
         994                 :            :         }
         995                 :          2 :         Py_DECREF(x); /* can't do it */
         996                 :            :     }
         997         [ +  - ]:          2 :     if (slotw) {
         998                 :          2 :         PyObject *x = slotw(v, w, z);
         999                 :            :         assert(_Py_CheckSlotResult(w, op_name, x != NULL));
        1000         [ +  - ]:          2 :         if (x != Py_NotImplemented) {
        1001                 :          2 :             return x;
        1002                 :            :         }
        1003                 :          0 :         Py_DECREF(x); /* can't do it */
        1004                 :            :     }
        1005                 :            :
        1006                 :          0 :     PyNumberMethods *mz = Py_TYPE(z)->tp_as_number;
        1007         [ #  # ]:          0 :     if (mz != NULL) {
        1008                 :          0 :         ternaryfunc slotz = NB_TERNOP(mz, op_slot);
        1009   [ #  #  #  # ]:          0 :         if (slotz == slotv || slotz == slotw) {
        1010                 :          0 :             slotz = NULL;
        1011                 :            :         }
        1012         [ #  # ]:          0 :         if (slotz) {
        1013                 :          0 :             PyObject *x = slotz(v, w, z);
        1014                 :            :             assert(_Py_CheckSlotResult(z, op_name, x != NULL));
        1015         [ #  # ]:          0 :             if (x != Py_NotImplemented) {
        1016                 :          0 :                 return x;
        1017                 :            :             }
        1018                 :          0 :             Py_DECREF(x); /* can't do it */
        1019                 :            :         }
        1020                 :            :     }
        1021                 :            :
        1022         [ #  # ]:          0 :     if (z == Py_None) {
        1023                 :          0 :         PyErr_Format(
        1024                 :            :             PyExc_TypeError,
        1025                 :            :             "unsupported operand type(s) for %.100s: "
        1026                 :            :             "'%.100s' and '%.100s'",
        1027                 :            :             op_name,
        1028                 :          0 :             Py_TYPE(v)->tp_name,
        1029                 :          0 :             Py_TYPE(w)->tp_name);
        1030                 :            :     }
        1031                 :            :     else {
        1032                 :          0 :         PyErr_Format(
        1033                 :            :             PyExc_TypeError,
        1034                 :            :             "unsupported operand type(s) for %.100s: "
        1035                 :            :             "'%.100s', '%.100s', '%.100s'",
        1036                 :            :             op_name,
        1037                 :          0 :             Py_TYPE(v)->tp_name,
        1038                 :          0 :             Py_TYPE(w)->tp_name,
        1039                 :          0 :             Py_TYPE(z)->tp_name);
        1040                 :            :     }
        1041                 :          0 :     return NULL;
        1042                 :            : }
        1043                 :            :
        1044                 :            : #define BINARY_FUNC(func, op, op_name) \
        1045                 :            :     PyObject * \
        1046                 :            :     func(PyObject *v, PyObject *w) { \
        1047                 :            :         return binary_op(v, w, NB_SLOT(op), op_name); \
        1048                 :            :     }
        1049                 :            :
        1050                 :     260308 : BINARY_FUNC(PyNumber_Or, nb_or, "|")
        1051                 :          7 : BINARY_FUNC(PyNumber_Xor, nb_xor, "^")
        1052                 :      92656 : BINARY_FUNC(PyNumber_And, nb_and, "&")
        1053                 :      49126 : BINARY_FUNC(PyNumber_Lshift, nb_lshift, "<<")
        1054                 :     509999 : BINARY_FUNC(PyNumber_Rshift, nb_rshift, ">>")
        1055                 :      14458 : BINARY_FUNC(PyNumber_Subtract, nb_subtract, "-")
        1056                 :        148 : BINARY_FUNC(PyNumber_Divmod, nb_divmod, "divmod()")
        1057                 :            :
        1058                 :            : PyObject *
        1059                 :     233885 : PyNumber_Add(PyObject *v, PyObject *w)
        1060                 :            : {
        1061                 :     233885 :     PyObject *result = BINARY_OP1(v, w, NB_SLOT(nb_add), "+");
        1062         [ +  + ]:     233885 :     if (result != Py_NotImplemented) {
        1063                 :     228798 :         return result;
        1064                 :            :     }
        1065                 :       5087 :     Py_DECREF(result);
        1066                 :            :
        1067                 :       5087 :     PySequenceMethods *m = Py_TYPE(v)->tp_as_sequence;
        1068   [ +  +  +  - ]:       5087 :     if (m && m->sq_concat) {
        1069                 :       5085 :         result = (*m->sq_concat)(v, w);
        1070                 :            :         assert(_Py_CheckSlotResult(v, "+", result != NULL));
        1071                 :       5085 :         return result;
        1072                 :            :     }
        1073                 :            :
        1074                 :          2 :     return binop_type_error(v, w, "+");
        1075                 :            : }
        1076                 :            :
        1077                 :            : static PyObject *
        1078                 :     148165 : sequence_repeat(ssizeargfunc repeatfunc, PyObject *seq, PyObject *n)
        1079                 :            : {
        1080                 :            :     Py_ssize_t count;
        1081         [ +  + ]:     148165 :     if (_PyIndex_Check(n)) {
        1082                 :     148159 :         count = PyNumber_AsSsize_t(n, PyExc_OverflowError);
        1083   [ -  +  -  - ]:     148159 :         if (count == -1 && PyErr_Occurred()) {
        1084                 :          0 :             return NULL;
        1085                 :            :         }
        1086                 :            :     }
        1087                 :            :     else {
        1088                 :          6 :         return type_error("can't multiply sequence by "
        1089                 :            :                           "non-int of type '%.200s'", n);
        1090                 :            :     }
        1091                 :     148159 :     PyObject *res = (*repeatfunc)(seq, count);
        1092                 :            :     assert(_Py_CheckSlotResult(seq, "*", res != NULL));
        1093                 :     148159 :     return res;
        1094                 :            : }
        1095                 :            :
        1096                 :            : PyObject *
        1097                 :    1272786 : PyNumber_Multiply(PyObject *v, PyObject *w)
        1098                 :            : {
        1099                 :    1272786 :     PyObject *result = BINARY_OP1(v, w, NB_SLOT(nb_multiply), "*");
        1100         [ +  + ]:    1272786 :     if (result == Py_NotImplemented) {
        1101                 :     148167 :         PySequenceMethods *mv = Py_TYPE(v)->tp_as_sequence;
        1102                 :     148167 :         PySequenceMethods *mw = Py_TYPE(w)->tp_as_sequence;
        1103                 :     148167 :         Py_DECREF(result);
        1104   [ +  +  +  + ]:     148167 :         if  (mv && mv->sq_repeat) {
        1105                 :     148152 :             return sequence_repeat(mv->sq_repeat, v, w);
        1106                 :            :         }
        1107   [ +  -  +  + ]:         15 :         else if (mw && mw->sq_repeat) {
        1108                 :         13 :             return sequence_repeat(mw->sq_repeat, w, v);
        1109                 :            :         }
        1110                 :          2 :         result = binop_type_error(v, w, "*");
        1111                 :            :     }
        1112                 :    1124621 :     return result;
        1113                 :            : }
        1114                 :            :
        1115                 :            : PyObject *
        1116                 :          0 : PyNumber_MatrixMultiply(PyObject *v, PyObject *w)
        1117                 :            : {
        1118                 :          0 :     return binary_op(v, w, NB_SLOT(nb_matrix_multiply), "@");
        1119                 :            : }
        1120                 :            :
        1121                 :            : PyObject *
        1122                 :      89275 : PyNumber_FloorDivide(PyObject *v, PyObject *w)
        1123                 :            : {
        1124                 :      89275 :     return binary_op(v, w, NB_SLOT(nb_floor_divide), "//");
        1125                 :            : }
        1126                 :            :
        1127                 :            : PyObject *
        1128                 :      33110 : PyNumber_TrueDivide(PyObject *v, PyObject *w)
        1129                 :            : {
        1130                 :      33110 :     return binary_op(v, w, NB_SLOT(nb_true_divide), "/");
        1131                 :            : }
        1132                 :            :
        1133                 :            : PyObject *
        1134                 :        230 : PyNumber_Remainder(PyObject *v, PyObject *w)
        1135                 :            : {
        1136                 :        230 :     return binary_op(v, w, NB_SLOT(nb_remainder), "%");
        1137                 :            : }
        1138                 :            :
        1139                 :            : PyObject *
        1140                 :     216773 : PyNumber_Power(PyObject *v, PyObject *w, PyObject *z)
        1141                 :            : {
        1142                 :     216773 :     return ternary_op(v, w, z, NB_SLOT(nb_power), "** or pow()");
        1143                 :            : }
        1144                 :            :
        1145                 :            : PyObject *
        1146                 :     216707 : _PyNumber_PowerNoMod(PyObject *lhs, PyObject *rhs)
        1147                 :            : {
        1148                 :     216707 :     return PyNumber_Power(lhs, rhs, Py_None);
        1149                 :            : }
        1150                 :            :
        1151                 :            : /* Binary in-place operators */
        1152                 :            :
        1153                 :            : /* The in-place operators are defined to fall back to the 'normal',
        1154                 :            :    non in-place operations, if the in-place methods are not in place.
        1155                 :            :
        1156                 :            :    - If the left hand object has the appropriate struct members, and
        1157                 :            :      they are filled, call the appropriate function and return the
        1158                 :            :      result.  No coercion is done on the arguments; the left-hand object
        1159                 :            :      is the one the operation is performed on, and it's up to the
        1160                 :            :      function to deal with the right-hand object.
        1161                 :            :
        1162                 :            :    - Otherwise, in-place modification is not supported. Handle it exactly as
        1163                 :            :      a non in-place operation of the same kind.
        1164                 :            :
        1165                 :            :    */
        1166                 :            :
        1167                 :            : static PyObject *
        1168                 :     668726 : binary_iop1(PyObject *v, PyObject *w, const int iop_slot, const int op_slot
        1169                 :            : #ifndef NDEBUG
        1170                 :            :             , const char *op_name
        1171                 :            : #endif
        1172                 :            :             )
        1173                 :            : {
        1174                 :     668726 :     PyNumberMethods *mv = Py_TYPE(v)->tp_as_number;
        1175         [ +  + ]:     668726 :     if (mv != NULL) {
        1176                 :     668331 :         binaryfunc slot = NB_BINOP(mv, iop_slot);
        1177         [ +  + ]:     668331 :         if (slot) {
        1178                 :      46536 :             PyObject *x = (slot)(v, w);
        1179                 :            :             assert(_Py_CheckSlotResult(v, op_name, x != NULL));
        1180         [ +  - ]:      46536 :             if (x != Py_NotImplemented) {
        1181                 :      46536 :                 return x;
        1182                 :            :             }
        1183                 :          0 :             Py_DECREF(x);
        1184                 :            :         }
        1185                 :            :     }
        1186                 :            : #ifdef NDEBUG
        1187                 :     622190 :     return binary_op1(v, w, op_slot);
        1188                 :            : #else
        1189                 :            :     return binary_op1(v, w, op_slot, op_name);
        1190                 :            : #endif
        1191                 :            : }
        1192                 :            :
        1193                 :            : #ifdef NDEBUG
        1194                 :            : #  define BINARY_IOP1(v, w, iop_slot, op_slot, op_name) binary_iop1(v, w, iop_slot, op_slot)
        1195                 :            : #else
        1196                 :            : #  define BINARY_IOP1(v, w, iop_slot, op_slot, op_name) binary_iop1(v, w, iop_slot, op_slot, op_name)
        1197                 :            : #endif
        1198                 :            :
        1199                 :            : static PyObject *
        1200                 :     667145 : binary_iop(PyObject *v, PyObject *w, const int iop_slot, const int op_slot,
        1201                 :            :                 const char *op_name)
        1202                 :            : {
        1203                 :     667145 :     PyObject *result = BINARY_IOP1(v, w, iop_slot, op_slot, op_name);
        1204         [ -  + ]:     667145 :     if (result == Py_NotImplemented) {
        1205                 :          0 :         Py_DECREF(result);
        1206                 :          0 :         return binop_type_error(v, w, op_name);
        1207                 :            :     }
        1208                 :     667145 :     return result;
        1209                 :            : }
        1210                 :            :
        1211                 :            : static PyObject *
        1212                 :          0 : ternary_iop(PyObject *v, PyObject *w, PyObject *z, const int iop_slot, const int op_slot,
        1213                 :            :                 const char *op_name)
        1214                 :            : {
        1215                 :          0 :     PyNumberMethods *mv = Py_TYPE(v)->tp_as_number;
        1216         [ #  # ]:          0 :     if (mv != NULL) {
        1217                 :          0 :         ternaryfunc slot = NB_TERNOP(mv, iop_slot);
        1218         [ #  # ]:          0 :         if (slot) {
        1219                 :          0 :             PyObject *x = (slot)(v, w, z);
        1220         [ #  # ]:          0 :             if (x != Py_NotImplemented) {
        1221                 :          0 :                 return x;
        1222                 :            :             }
        1223                 :          0 :             Py_DECREF(x);
        1224                 :            :         }
        1225                 :            :     }
        1226                 :          0 :     return ternary_op(v, w, z, op_slot, op_name);
        1227                 :            : }
        1228                 :            :
        1229                 :            : #define INPLACE_BINOP(func, iop, op, op_name) \
        1230                 :            :     PyObject * \
        1231                 :            :     func(PyObject *v, PyObject *w) { \
        1232                 :            :         return binary_iop(v, w, NB_SLOT(iop), NB_SLOT(op), op_name); \
        1233                 :            :     }
        1234                 :            :
        1235                 :     110559 : INPLACE_BINOP(PyNumber_InPlaceOr, nb_inplace_or, nb_or, "|=")
        1236                 :         15 : INPLACE_BINOP(PyNumber_InPlaceXor, nb_inplace_xor, nb_xor, "^=")
        1237                 :         79 : INPLACE_BINOP(PyNumber_InPlaceAnd, nb_inplace_and, nb_and, "&=")
        1238                 :     520000 : INPLACE_BINOP(PyNumber_InPlaceLshift, nb_inplace_lshift, nb_lshift, "<<=")
        1239                 :          0 : INPLACE_BINOP(PyNumber_InPlaceRshift, nb_inplace_rshift, nb_rshift, ">>=")
        1240                 :          4 : INPLACE_BINOP(PyNumber_InPlaceSubtract, nb_inplace_subtract, nb_subtract, "-=")
        1241                 :          0 : INPLACE_BINOP(PyNumber_InPlaceMatrixMultiply, nb_inplace_matrix_multiply, nb_matrix_multiply, "@=")
        1242                 :      36488 : INPLACE_BINOP(PyNumber_InPlaceFloorDivide, nb_inplace_floor_divide, nb_floor_divide, "//=")
        1243                 :          0 : INPLACE_BINOP(PyNumber_InPlaceTrueDivide, nb_inplace_true_divide, nb_true_divide,  "/=")
        1244                 :          0 : INPLACE_BINOP(PyNumber_InPlaceRemainder, nb_inplace_remainder, nb_remainder, "%=")
        1245                 :            :
        1246                 :            : PyObject *
        1247                 :       1524 : PyNumber_InPlaceAdd(PyObject *v, PyObject *w)
        1248                 :            : {
        1249                 :       1524 :     PyObject *result = BINARY_IOP1(v, w, NB_SLOT(nb_inplace_add),
        1250                 :            :                                    NB_SLOT(nb_add), "+=");
        1251         [ +  + ]:       1524 :     if (result == Py_NotImplemented) {
        1252                 :        483 :         PySequenceMethods *m = Py_TYPE(v)->tp_as_sequence;
        1253                 :        483 :         Py_DECREF(result);
        1254         [ +  - ]:        483 :         if (m != NULL) {
        1255                 :        483 :             binaryfunc func = m->sq_inplace_concat;
        1256         [ +  + ]:        483 :             if (func == NULL)
        1257                 :        247 :                 func = m->sq_concat;
        1258         [ +  - ]:        483 :             if (func != NULL) {
        1259                 :        483 :                 result = func(v, w);
        1260                 :            :                 assert(_Py_CheckSlotResult(v, "+=", result != NULL));
        1261                 :        483 :                 return result;
        1262                 :            :             }
        1263                 :            :         }
        1264                 :          0 :         result = binop_type_error(v, w, "+=");
        1265                 :            :     }
        1266                 :       1041 :     return result;
        1267                 :            : }
        1268                 :            :
        1269                 :            : PyObject *
        1270                 :         57 : PyNumber_InPlaceMultiply(PyObject *v, PyObject *w)
        1271                 :            : {
        1272                 :         57 :     PyObject *result = BINARY_IOP1(v, w, NB_SLOT(nb_inplace_multiply),
        1273                 :            :                                    NB_SLOT(nb_multiply), "*=");
        1274         [ -  + ]:         57 :     if (result == Py_NotImplemented) {
        1275                 :          0 :         ssizeargfunc f = NULL;
        1276                 :          0 :         PySequenceMethods *mv = Py_TYPE(v)->tp_as_sequence;
        1277                 :          0 :         PySequenceMethods *mw = Py_TYPE(w)->tp_as_sequence;
        1278                 :          0 :         Py_DECREF(result);
        1279         [ #  # ]:          0 :         if (mv != NULL) {
        1280                 :          0 :             f = mv->sq_inplace_repeat;
        1281         [ #  # ]:          0 :             if (f == NULL)
        1282                 :          0 :                 f = mv->sq_repeat;
        1283         [ #  # ]:          0 :             if (f != NULL)
        1284                 :          0 :                 return sequence_repeat(f, v, w);
        1285                 :            :         }
        1286         [ #  # ]:          0 :         else if (mw != NULL) {
        1287                 :            :             /* Note that the right hand operand should not be
        1288                 :            :              * mutated in this case so sq_inplace_repeat is not
        1289                 :            :              * used. */
        1290         [ #  # ]:          0 :             if (mw->sq_repeat)
        1291                 :          0 :                 return sequence_repeat(mw->sq_repeat, w, v);
        1292                 :            :         }
        1293                 :          0 :         result = binop_type_error(v, w, "*=");
        1294                 :            :     }
        1295                 :         57 :     return result;
        1296                 :            : }
        1297                 :            :
        1298                 :            : PyObject *
        1299                 :          0 : PyNumber_InPlacePower(PyObject *v, PyObject *w, PyObject *z)
        1300                 :            : {
        1301                 :          0 :     return ternary_iop(v, w, z, NB_SLOT(nb_inplace_power),
        1302                 :            :                                 NB_SLOT(nb_power), "**=");
        1303                 :            : }
        1304                 :            :
        1305                 :            : PyObject *
        1306                 :          0 : _PyNumber_InPlacePowerNoMod(PyObject *lhs, PyObject *rhs)
        1307                 :            : {
        1308                 :          0 :     return PyNumber_InPlacePower(lhs, rhs, Py_None);
        1309                 :            : }
        1310                 :            :
        1311                 :            :
        1312                 :            : /* Unary operators and functions */
        1313                 :            :
        1314                 :            : PyObject *
        1315                 :      45933 : PyNumber_Negative(PyObject *o)
        1316                 :            : {
        1317         [ -  + ]:      45933 :     if (o == NULL) {
        1318                 :          0 :         return null_error();
        1319                 :            :     }
        1320                 :            :
        1321                 :      45933 :     PyNumberMethods *m = Py_TYPE(o)->tp_as_number;
        1322   [ +  -  +  - ]:      45933 :     if (m && m->nb_negative) {
        1323                 :      45933 :         PyObject *res = (*m->nb_negative)(o);
        1324                 :            :         assert(_Py_CheckSlotResult(o, "__neg__", res != NULL));
        1325                 :      45933 :         return res;
        1326                 :            :     }
        1327                 :            :
        1328                 :          0 :     return type_error("bad operand type for unary -: '%.200s'", o);
        1329                 :            : }
        1330                 :            :
        1331                 :            : PyObject *
        1332                 :         10 : PyNumber_Positive(PyObject *o)
        1333                 :            : {
        1334         [ -  + ]:         10 :     if (o == NULL) {
        1335                 :          0 :         return null_error();
        1336                 :            :     }
        1337                 :            :
        1338                 :         10 :     PyNumberMethods *m = Py_TYPE(o)->tp_as_number;
        1339   [ +  -  +  - ]:         10 :     if (m && m->nb_positive) {
        1340                 :         10 :         PyObject *res = (*m->nb_positive)(o);
        1341                 :            :         assert(_Py_CheckSlotResult(o, "__pos__", res != NULL));
        1342                 :         10 :         return res;
        1343                 :            :     }
        1344                 :            :
        1345                 :          0 :     return type_error("bad operand type for unary +: '%.200s'", o);
        1346                 :            : }
        1347                 :            :
        1348                 :            : PyObject *
        1349                 :      18212 : PyNumber_Invert(PyObject *o)
        1350                 :            : {
        1351         [ -  + ]:      18212 :     if (o == NULL) {
        1352                 :          0 :         return null_error();
        1353                 :            :     }
        1354                 :            :
        1355                 :      18212 :     PyNumberMethods *m = Py_TYPE(o)->tp_as_number;
        1356   [ +  -  +  - ]:      18212 :     if (m && m->nb_invert) {
        1357                 :      18212 :         PyObject *res = (*m->nb_invert)(o);
        1358                 :            :         assert(_Py_CheckSlotResult(o, "__invert__", res != NULL));
        1359                 :      18212 :         return res;
        1360                 :            :     }
        1361                 :            :
        1362                 :          0 :     return type_error("bad operand type for unary ~: '%.200s'", o);
        1363                 :            : }
        1364                 :            :
        1365                 :            : PyObject *
        1366                 :      81240 : PyNumber_Absolute(PyObject *o)
        1367                 :            : {
        1368         [ -  + ]:      81240 :     if (o == NULL) {
        1369                 :          0 :         return null_error();
        1370                 :            :     }
        1371                 :            :
        1372                 :      81240 :     PyNumberMethods *m = Py_TYPE(o)->tp_as_number;
        1373   [ +  -  +  - ]:      81240 :     if (m && m->nb_absolute) {
        1374                 :      81240 :         PyObject *res = m->nb_absolute(o);
        1375                 :            :         assert(_Py_CheckSlotResult(o, "__abs__", res != NULL));
        1376                 :      81240 :         return res;
        1377                 :            :     }
        1378                 :            :
        1379                 :          0 :     return type_error("bad operand type for abs(): '%.200s'", o);
        1380                 :            : }
        1381                 :            :
        1382                 :            :
        1383                 :            : int
        1384                 :       5731 : PyIndex_Check(PyObject *obj)
        1385                 :            : {
        1386                 :       5731 :     return _PyIndex_Check(obj);
        1387                 :            : }
        1388                 :            :
        1389                 :            :
        1390                 :            : /* Return a Python int from the object item.
        1391                 :            :    Can return an instance of int subclass.
        1392                 :            :    Raise TypeError if the result is not an int
        1393                 :            :    or if the object cannot be interpreted as an index.
        1394                 :            : */
        1395                 :            : PyObject *
        1396                 :    1147679 : _PyNumber_Index(PyObject *item)
        1397                 :            : {
        1398         [ -  + ]:    1147679 :     if (item == NULL) {
        1399                 :          0 :         return null_error();
        1400                 :            :     }
        1401                 :            :
        1402         [ +  + ]:    1147679 :     if (PyLong_Check(item)) {
        1403                 :    1146198 :         return Py_NewRef(item);
        1404                 :            :     }
        1405         [ +  + ]:       1481 :     if (!_PyIndex_Check(item)) {
        1406                 :       1459 :         PyErr_Format(PyExc_TypeError,
        1407                 :            :                      "'%.200s' object cannot be interpreted "
        1408                 :       1459 :                      "as an integer", Py_TYPE(item)->tp_name);
        1409                 :       1459 :         return NULL;
        1410                 :            :     }
        1411                 :            :
        1412                 :         22 :     PyObject *result = Py_TYPE(item)->tp_as_number->nb_index(item);
        1413                 :            :     assert(_Py_CheckSlotResult(item, "__index__", result != NULL));
        1414   [ +  -  +  - ]:         22 :     if (!result || PyLong_CheckExact(result)) {
        1415                 :         22 :         return result;
        1416                 :            :     }
        1417                 :            :
        1418         [ #  # ]:          0 :     if (!PyLong_Check(result)) {
        1419                 :          0 :         PyErr_Format(PyExc_TypeError,
        1420                 :            :                      "__index__ returned non-int (type %.200s)",
        1421                 :          0 :                      Py_TYPE(result)->tp_name);
        1422                 :          0 :         Py_DECREF(result);
        1423                 :          0 :         return NULL;
        1424                 :            :     }
        1425                 :            :     /* Issue #17576: warn if 'result' not of exact type int. */
        1426         [ #  # ]:          0 :     if (PyErr_WarnFormat(PyExc_DeprecationWarning, 1,
        1427                 :            :             "__index__ returned non-int (type %.200s).  "
        1428                 :            :             "The ability to return an instance of a strict subclass of int "
        1429                 :            :             "is deprecated, and may be removed in a future version of Python.",
        1430                 :          0 :             Py_TYPE(result)->tp_name)) {
        1431                 :          0 :         Py_DECREF(result);
        1432                 :          0 :         return NULL;
        1433                 :            :     }
        1434                 :          0 :     return result;
        1435                 :            : }
        1436                 :            :
        1437                 :            : /* Return an exact Python int from the object item.
        1438                 :            :    Raise TypeError if the result is not an int
        1439                 :            :    or if the object cannot be interpreted as an index.
        1440                 :            : */
        1441                 :            : PyObject *
        1442                 :     213811 : PyNumber_Index(PyObject *item)
        1443                 :            : {
        1444                 :     213811 :     PyObject *result = _PyNumber_Index(item);
        1445   [ +  +  +  + ]:     213811 :     if (result != NULL && !PyLong_CheckExact(result)) {
        1446                 :         40 :         Py_SETREF(result, _PyLong_Copy((PyLongObject *)result));
        1447                 :            :     }
        1448                 :     213811 :     return result;
        1449                 :            : }
        1450                 :            :
        1451                 :            : /* Return an error on Overflow only if err is not NULL*/
        1452                 :            :
        1453                 :            : Py_ssize_t
        1454                 :     826810 : PyNumber_AsSsize_t(PyObject *item, PyObject *err)
        1455                 :            : {
        1456                 :            :     Py_ssize_t result;
        1457                 :            :     PyObject *runerr;
        1458                 :     826810 :     PyObject *value = _PyNumber_Index(item);
        1459         [ -  + ]:     826810 :     if (value == NULL)
        1460                 :          0 :         return -1;
        1461                 :            :
        1462                 :            :     /* We're done if PyLong_AsSsize_t() returns without error. */
        1463                 :     826810 :     result = PyLong_AsSsize_t(value);
        1464         [ +  + ]:     826810 :     if (result != -1)
        1465                 :     824865 :         goto finish;
        1466                 :            :
        1467                 :       1945 :     PyThreadState *tstate = _PyThreadState_GET();
        1468                 :       1945 :     runerr = _PyErr_Occurred(tstate);
        1469         [ +  - ]:       1945 :     if (!runerr) {
        1470                 :       1945 :         goto finish;
        1471                 :            :     }
        1472                 :            :
        1473                 :            :     /* Error handling code -- only manage OverflowError differently */
        1474         [ #  # ]:          0 :     if (!PyErr_GivenExceptionMatches(runerr, PyExc_OverflowError)) {
        1475                 :          0 :         goto finish;
        1476                 :            :     }
        1477                 :          0 :     _PyErr_Clear(tstate);
        1478                 :            :
        1479                 :            :     /* If no error-handling desired then the default clipping
        1480                 :            :        is sufficient. */
        1481         [ #  # ]:          0 :     if (!err) {
        1482                 :            :         assert(PyLong_Check(value));
        1483                 :            :         /* Whether or not it is less than or equal to
        1484                 :            :            zero is determined by the sign of ob_size
        1485                 :            :         */
        1486         [ #  # ]:          0 :         if (_PyLong_Sign(value) < 0)
        1487                 :          0 :             result = PY_SSIZE_T_MIN;
        1488                 :            :         else
        1489                 :          0 :             result = PY_SSIZE_T_MAX;
        1490                 :            :     }
        1491                 :            :     else {
        1492                 :            :         /* Otherwise replace the error with caller's error object. */
        1493                 :          0 :         _PyErr_Format(tstate, err,
        1494                 :            :                       "cannot fit '%.200s' into an index-sized integer",
        1495                 :          0 :                       Py_TYPE(item)->tp_name);
        1496                 :            :     }
        1497                 :            :
        1498                 :     826810 :  finish:
        1499                 :     826810 :     Py_DECREF(value);
        1500                 :     826810 :     return result;
        1501                 :            : }
        1502                 :            :
        1503                 :            :
        1504                 :            : PyObject *
        1505                 :     533142 : PyNumber_Long(PyObject *o)
        1506                 :            : {
        1507                 :            :     PyObject *result;
        1508                 :            :     PyNumberMethods *m;
        1509                 :            :     PyObject *trunc_func;
        1510                 :            :     Py_buffer view;
        1511                 :            :
        1512         [ -  + ]:     533142 :     if (o == NULL) {
        1513                 :          0 :         return null_error();
        1514                 :            :     }
        1515                 :            :
        1516         [ +  + ]:     533142 :     if (PyLong_CheckExact(o)) {
        1517                 :       1274 :         return Py_NewRef(o);
        1518                 :            :     }
        1519                 :     531868 :     m = Py_TYPE(o)->tp_as_number;
        1520   [ +  -  +  + ]:     531868 :     if (m && m->nb_int) { /* This should include subclasses of int */
        1521                 :            :         /* Convert using the nb_int slot, which should return something
        1522                 :            :            of exact type int. */
        1523                 :     531027 :         result = m->nb_int(o);
        1524                 :            :         assert(_Py_CheckSlotResult(o, "__int__", result != NULL));
        1525   [ +  -  +  - ]:     531027 :         if (!result || PyLong_CheckExact(result)) {
        1526                 :     531027 :             return result;
        1527                 :            :         }
        1528                 :            :
        1529         [ #  # ]:          0 :         if (!PyLong_Check(result)) {
        1530                 :          0 :             PyErr_Format(PyExc_TypeError,
        1531                 :            :                          "__int__ returned non-int (type %.200s)",
        1532                 :          0 :                          Py_TYPE(result)->tp_name);
        1533                 :          0 :             Py_DECREF(result);
        1534                 :          0 :             return NULL;
        1535                 :            :         }
        1536                 :            :         /* Issue #17576: warn if 'result' not of exact type int. */
        1537         [ #  # ]:          0 :         if (PyErr_WarnFormat(PyExc_DeprecationWarning, 1,
        1538                 :            :                 "__int__ returned non-int (type %.200s).  "
        1539                 :            :                 "The ability to return an instance of a strict subclass of int "
        1540                 :            :                 "is deprecated, and may be removed in a future version of Python.",
        1541                 :          0 :                 Py_TYPE(result)->tp_name)) {
        1542                 :          0 :             Py_DECREF(result);
        1543                 :          0 :             return NULL;
        1544                 :            :         }
        1545                 :          0 :         Py_SETREF(result, _PyLong_Copy((PyLongObject *)result));
        1546                 :          0 :         return result;
        1547                 :            :     }
        1548   [ +  -  -  + ]:        841 :     if (m && m->nb_index) {
        1549                 :          0 :         return PyNumber_Index(o);
        1550                 :            :     }
        1551                 :        841 :     trunc_func = _PyObject_LookupSpecial(o, &_Py_ID(__trunc__));
        1552         [ -  + ]:        841 :     if (trunc_func) {
        1553         [ #  # ]:          0 :         if (PyErr_WarnEx(PyExc_DeprecationWarning,
        1554                 :            :                 "The delegation of int() to __trunc__ is deprecated.", 1)) {
        1555                 :          0 :             Py_DECREF(trunc_func);
        1556                 :          0 :             return NULL;
        1557                 :            :         }
        1558                 :          0 :         result = _PyObject_CallNoArgs(trunc_func);
        1559                 :          0 :         Py_DECREF(trunc_func);
        1560   [ #  #  #  # ]:          0 :         if (result == NULL || PyLong_CheckExact(result)) {
        1561                 :          0 :             return result;
        1562                 :            :         }
        1563         [ #  # ]:          0 :         if (PyLong_Check(result)) {
        1564                 :          0 :             Py_SETREF(result, _PyLong_Copy((PyLongObject *)result));
        1565                 :          0 :             return result;
        1566                 :            :         }
        1567                 :            :         /* __trunc__ is specified to return an Integral type,
        1568                 :            :            but int() needs to return an int. */
        1569         [ #  # ]:          0 :         if (!PyIndex_Check(result)) {
        1570                 :          0 :             PyErr_Format(
        1571                 :            :                 PyExc_TypeError,
        1572                 :            :                 "__trunc__ returned non-Integral (type %.200s)",
        1573                 :          0 :                 Py_TYPE(result)->tp_name);
        1574                 :          0 :             Py_DECREF(result);
        1575                 :          0 :             return NULL;
        1576                 :            :         }
        1577                 :          0 :         Py_SETREF(result, PyNumber_Index(result));
        1578                 :          0 :         return result;
        1579                 :            :     }
        1580         [ -  + ]:        841 :     if (PyErr_Occurred())
        1581                 :          0 :         return NULL;
        1582                 :            :
        1583         [ +  - ]:        841 :     if (PyUnicode_Check(o))
        1584                 :            :         /* The below check is done in PyLong_FromUnicodeObject(). */
        1585                 :        841 :         return PyLong_FromUnicodeObject(o, 10);
        1586                 :            :
        1587         [ #  # ]:          0 :     if (PyBytes_Check(o))
        1588                 :            :         /* need to do extra error checking that PyLong_FromString()
        1589                 :            :          * doesn't do.  In particular int('9\x005') must raise an
        1590                 :            :          * exception, not truncate at the null.
        1591                 :            :          */
        1592                 :          0 :         return _PyLong_FromBytes(PyBytes_AS_STRING(o),
        1593                 :            :                                  PyBytes_GET_SIZE(o), 10);
        1594                 :            :
        1595         [ #  # ]:          0 :     if (PyByteArray_Check(o))
        1596                 :          0 :         return _PyLong_FromBytes(PyByteArray_AS_STRING(o),
        1597                 :            :                                  PyByteArray_GET_SIZE(o), 10);
        1598                 :            :
        1599         [ #  # ]:          0 :     if (PyObject_GetBuffer(o, &view, PyBUF_SIMPLE) == 0) {
        1600                 :            :         PyObject *bytes;
        1601                 :            :
        1602                 :            :         /* Copy to NUL-terminated buffer. */
        1603                 :          0 :         bytes = PyBytes_FromStringAndSize((const char *)view.buf, view.len);
        1604         [ #  # ]:          0 :         if (bytes == NULL) {
        1605                 :          0 :             PyBuffer_Release(&view);
        1606                 :          0 :             return NULL;
        1607                 :            :         }
        1608                 :          0 :         result = _PyLong_FromBytes(PyBytes_AS_STRING(bytes),
        1609                 :            :                                    PyBytes_GET_SIZE(bytes), 10);
        1610                 :          0 :         Py_DECREF(bytes);
        1611                 :          0 :         PyBuffer_Release(&view);
        1612                 :          0 :         return result;
        1613                 :            :     }
        1614                 :            :
        1615                 :          0 :     return type_error("int() argument must be a string, a bytes-like object "
        1616                 :            :                       "or a real number, not '%.200s'", o);
        1617                 :            : }
        1618                 :            :
        1619                 :            : PyObject *
        1620                 :       6150 : PyNumber_Float(PyObject *o)
        1621                 :            : {
        1622         [ -  + ]:       6150 :     if (o == NULL) {
        1623                 :          0 :         return null_error();
        1624                 :            :     }
        1625                 :            :
        1626         [ +  + ]:       6150 :     if (PyFloat_CheckExact(o)) {
        1627                 :          4 :         return Py_NewRef(o);
        1628                 :            :     }
        1629                 :            :
        1630                 :       6146 :     PyNumberMethods *m = Py_TYPE(o)->tp_as_number;
        1631   [ +  -  +  - ]:       6146 :     if (m && m->nb_float) { /* This should include subclasses of float */
        1632                 :       6146 :         PyObject *res = m->nb_float(o);
        1633                 :            :         assert(_Py_CheckSlotResult(o, "__float__", res != NULL));
        1634   [ +  -  +  - ]:       6146 :         if (!res || PyFloat_CheckExact(res)) {
        1635                 :       6146 :             return res;
        1636                 :            :         }
        1637                 :            :
        1638         [ #  # ]:          0 :         if (!PyFloat_Check(res)) {
        1639                 :          0 :             PyErr_Format(PyExc_TypeError,
        1640                 :            :                          "%.50s.__float__ returned non-float (type %.50s)",
        1641                 :          0 :                          Py_TYPE(o)->tp_name, Py_TYPE(res)->tp_name);
        1642                 :          0 :             Py_DECREF(res);
        1643                 :          0 :             return NULL;
        1644                 :            :         }
        1645                 :            :         /* Issue #26983: warn if 'res' not of exact type float. */
        1646         [ #  # ]:          0 :         if (PyErr_WarnFormat(PyExc_DeprecationWarning, 1,
        1647                 :            :                 "%.50s.__float__ returned non-float (type %.50s).  "
        1648                 :            :                 "The ability to return an instance of a strict subclass of float "
        1649                 :            :                 "is deprecated, and may be removed in a future version of Python.",
        1650                 :          0 :                 Py_TYPE(o)->tp_name, Py_TYPE(res)->tp_name)) {
        1651                 :          0 :             Py_DECREF(res);
        1652                 :          0 :             return NULL;
        1653                 :            :         }
        1654                 :          0 :         double val = PyFloat_AS_DOUBLE(res);
        1655                 :          0 :         Py_DECREF(res);
        1656                 :          0 :         return PyFloat_FromDouble(val);
        1657                 :            :     }
        1658                 :            :
        1659   [ #  #  #  # ]:          0 :     if (m && m->nb_index) {
        1660                 :          0 :         PyObject *res = _PyNumber_Index(o);
        1661         [ #  # ]:          0 :         if (!res) {
        1662                 :          0 :             return NULL;
        1663                 :            :         }
        1664                 :          0 :         double val = PyLong_AsDouble(res);
        1665                 :          0 :         Py_DECREF(res);
        1666   [ #  #  #  # ]:          0 :         if (val == -1.0 && PyErr_Occurred()) {
        1667                 :          0 :             return NULL;
        1668                 :            :         }
        1669                 :          0 :         return PyFloat_FromDouble(val);
        1670                 :            :     }
        1671                 :            :
        1672                 :            :     /* A float subclass with nb_float == NULL */
        1673         [ #  # ]:          0 :     if (PyFloat_Check(o)) {
        1674                 :          0 :         return PyFloat_FromDouble(PyFloat_AS_DOUBLE(o));
        1675                 :            :     }
        1676                 :          0 :     return PyFloat_FromString(o);
        1677                 :            : }
        1678                 :            :
        1679                 :            :
        1680                 :            : PyObject *
        1681                 :       2004 : PyNumber_ToBase(PyObject *n, int base)
        1682                 :            : {
        1683   [ +  +  +  -  :       2004 :     if (!(base == 2 || base == 8 || base == 10 || base == 16)) {
                 -  +  -  - ]
        1684                 :          0 :         PyErr_SetString(PyExc_SystemError,
        1685                 :            :                         "PyNumber_ToBase: base must be 2, 8, 10 or 16");
        1686                 :          0 :         return NULL;
        1687                 :            :     }
        1688                 :       2004 :     PyObject *index = _PyNumber_Index(n);
        1689         [ -  + ]:       2004 :     if (!index)
        1690                 :          0 :         return NULL;
        1691                 :       2004 :     PyObject *res = _PyLong_Format(index, base);
        1692                 :       2004 :     Py_DECREF(index);
        1693                 :       2004 :     return res;
        1694                 :            : }
        1695                 :            :
        1696                 :            :
        1697                 :            : /* Operations on sequences */
        1698                 :            :
        1699                 :            : int
        1700                 :       1144 : PySequence_Check(PyObject *s)
        1701                 :            : {
        1702         [ -  + ]:       1144 :     if (PyDict_Check(s))
        1703                 :          0 :         return 0;
        1704         [ +  + ]:       2284 :     return Py_TYPE(s)->tp_as_sequence &&
        1705         [ +  + ]:       1140 :         Py_TYPE(s)->tp_as_sequence->sq_item != NULL;
        1706                 :            : }
        1707                 :            :
        1708                 :            : Py_ssize_t
        1709                 :         29 : PySequence_Size(PyObject *s)
        1710                 :            : {
        1711         [ -  + ]:         29 :     if (s == NULL) {
        1712                 :          0 :         null_error();
        1713                 :          0 :         return -1;
        1714                 :            :     }
        1715                 :            :
        1716                 :         29 :     PySequenceMethods *m = Py_TYPE(s)->tp_as_sequence;
        1717   [ +  -  +  - ]:         29 :     if (m && m->sq_length) {
        1718                 :         29 :         Py_ssize_t len = m->sq_length(s);
        1719                 :            :         assert(_Py_CheckSlotResult(s, "__len__", len >= 0));
        1720                 :         29 :         return len;
        1721                 :            :     }
        1722                 :            :
        1723   [ #  #  #  # ]:          0 :     if (Py_TYPE(s)->tp_as_mapping && Py_TYPE(s)->tp_as_mapping->mp_length) {
        1724                 :          0 :         type_error("%.200s is not a sequence", s);
        1725                 :          0 :         return -1;
        1726                 :            :     }
        1727                 :          0 :     type_error("object of type '%.200s' has no len()", s);
        1728                 :          0 :     return -1;
        1729                 :            : }
        1730                 :            :
        1731                 :            : #undef PySequence_Length
        1732                 :            : Py_ssize_t
        1733                 :          0 : PySequence_Length(PyObject *s)
        1734                 :            : {
        1735                 :          0 :     return PySequence_Size(s);
        1736                 :            : }
        1737                 :            : #define PySequence_Length PySequence_Size
        1738                 :            :
        1739                 :            : PyObject *
        1740                 :         73 : PySequence_Concat(PyObject *s, PyObject *o)
        1741                 :            : {
        1742   [ +  -  -  + ]:         73 :     if (s == NULL || o == NULL) {
        1743                 :          0 :         return null_error();
        1744                 :            :     }
        1745                 :            :
        1746                 :         73 :     PySequenceMethods *m = Py_TYPE(s)->tp_as_sequence;
        1747   [ +  -  +  - ]:         73 :     if (m && m->sq_concat) {
        1748                 :         73 :         PyObject *res = m->sq_concat(s, o);
        1749                 :            :         assert(_Py_CheckSlotResult(s, "+", res != NULL));
        1750                 :         73 :         return res;
        1751                 :            :     }
        1752                 :            :
        1753                 :            :     /* Instances of user classes defining an __add__() method only
        1754                 :            :        have an nb_add slot, not an sq_concat slot.      So we fall back
        1755                 :            :        to nb_add if both arguments appear to be sequences. */
        1756   [ #  #  #  # ]:          0 :     if (PySequence_Check(s) && PySequence_Check(o)) {
        1757                 :          0 :         PyObject *result = BINARY_OP1(s, o, NB_SLOT(nb_add), "+");
        1758         [ #  # ]:          0 :         if (result != Py_NotImplemented)
        1759                 :          0 :             return result;
        1760                 :          0 :         Py_DECREF(result);
        1761                 :            :     }
        1762                 :          0 :     return type_error("'%.200s' object can't be concatenated", s);
        1763                 :            : }
        1764                 :            :
        1765                 :            : PyObject *
        1766                 :          0 : PySequence_Repeat(PyObject *o, Py_ssize_t count)
        1767                 :            : {
        1768         [ #  # ]:          0 :     if (o == NULL) {
        1769                 :          0 :         return null_error();
        1770                 :            :     }
        1771                 :            :
        1772                 :          0 :     PySequenceMethods *m = Py_TYPE(o)->tp_as_sequence;
        1773   [ #  #  #  # ]:          0 :     if (m && m->sq_repeat) {
        1774                 :          0 :         PyObject *res = m->sq_repeat(o, count);
        1775                 :            :         assert(_Py_CheckSlotResult(o, "*", res != NULL));
        1776                 :          0 :         return res;
        1777                 :            :     }
        1778                 :            :
        1779                 :            :     /* Instances of user classes defining a __mul__() method only
        1780                 :            :        have an nb_multiply slot, not an sq_repeat slot. so we fall back
        1781                 :            :        to nb_multiply if o appears to be a sequence. */
        1782         [ #  # ]:          0 :     if (PySequence_Check(o)) {
        1783                 :            :         PyObject *n, *result;
        1784                 :          0 :         n = PyLong_FromSsize_t(count);
        1785         [ #  # ]:          0 :         if (n == NULL)
        1786                 :          0 :             return NULL;
        1787                 :          0 :         result = BINARY_OP1(o, n, NB_SLOT(nb_multiply), "*");
        1788                 :          0 :         Py_DECREF(n);
        1789         [ #  # ]:          0 :         if (result != Py_NotImplemented)
        1790                 :          0 :             return result;
        1791                 :          0 :         Py_DECREF(result);
        1792                 :            :     }
        1793                 :          0 :     return type_error("'%.200s' object can't be repeated", o);
        1794                 :            : }
        1795                 :            :
        1796                 :            : PyObject *
        1797                 :          0 : PySequence_InPlaceConcat(PyObject *s, PyObject *o)
        1798                 :            : {
        1799   [ #  #  #  # ]:          0 :     if (s == NULL || o == NULL) {
        1800                 :          0 :         return null_error();
        1801                 :            :     }
        1802                 :            :
        1803                 :          0 :     PySequenceMethods *m = Py_TYPE(s)->tp_as_sequence;
        1804   [ #  #  #  # ]:          0 :     if (m && m->sq_inplace_concat) {
        1805                 :          0 :         PyObject *res = m->sq_inplace_concat(s, o);
        1806                 :            :         assert(_Py_CheckSlotResult(s, "+=", res != NULL));
        1807                 :          0 :         return res;
        1808                 :            :     }
        1809   [ #  #  #  # ]:          0 :     if (m && m->sq_concat) {
        1810                 :          0 :         PyObject *res = m->sq_concat(s, o);
        1811                 :            :         assert(_Py_CheckSlotResult(s, "+", res != NULL));
        1812                 :          0 :         return res;
        1813                 :            :     }
        1814                 :            :
        1815   [ #  #  #  # ]:          0 :     if (PySequence_Check(s) && PySequence_Check(o)) {
        1816                 :          0 :         PyObject *result = BINARY_IOP1(s, o, NB_SLOT(nb_inplace_add),
        1817                 :            :                                        NB_SLOT(nb_add), "+=");
        1818         [ #  # ]:          0 :         if (result != Py_NotImplemented)
        1819                 :          0 :             return result;
        1820                 :          0 :         Py_DECREF(result);
        1821                 :            :     }
        1822                 :          0 :     return type_error("'%.200s' object can't be concatenated", s);
        1823                 :            : }
        1824                 :            :
        1825                 :            : PyObject *
        1826                 :          0 : PySequence_InPlaceRepeat(PyObject *o, Py_ssize_t count)
        1827                 :            : {
        1828         [ #  # ]:          0 :     if (o == NULL) {
        1829                 :          0 :         return null_error();
        1830                 :            :     }
        1831                 :            :
        1832                 :          0 :     PySequenceMethods *m = Py_TYPE(o)->tp_as_sequence;
        1833   [ #  #  #  # ]:          0 :     if (m && m->sq_inplace_repeat) {
        1834                 :          0 :         PyObject *res = m->sq_inplace_repeat(o, count);
        1835                 :            :         assert(_Py_CheckSlotResult(o, "*=", res != NULL));
        1836                 :          0 :         return res;
        1837                 :            :     }
        1838   [ #  #  #  # ]:          0 :     if (m && m->sq_repeat) {
        1839                 :          0 :         PyObject *res = m->sq_repeat(o, count);
        1840                 :            :         assert(_Py_CheckSlotResult(o, "*", res != NULL));
        1841                 :          0 :         return res;
        1842                 :            :     }
        1843                 :            :
        1844         [ #  # ]:          0 :     if (PySequence_Check(o)) {
        1845                 :            :         PyObject *n, *result;
        1846                 :          0 :         n = PyLong_FromSsize_t(count);
        1847         [ #  # ]:          0 :         if (n == NULL)
        1848                 :          0 :             return NULL;
        1849                 :          0 :         result = BINARY_IOP1(o, n, NB_SLOT(nb_inplace_multiply),
        1850                 :            :                              NB_SLOT(nb_multiply), "*=");
        1851                 :          0 :         Py_DECREF(n);
        1852         [ #  # ]:          0 :         if (result != Py_NotImplemented)
        1853                 :          0 :             return result;
        1854                 :          0 :         Py_DECREF(result);
        1855                 :            :     }
        1856                 :          0 :     return type_error("'%.200s' object can't be repeated", o);
        1857                 :            : }
        1858                 :            :
        1859                 :            : PyObject *
        1860                 :      16394 : PySequence_GetItem(PyObject *s, Py_ssize_t i)
        1861                 :            : {
        1862         [ -  + ]:      16394 :     if (s == NULL) {
        1863                 :          0 :         return null_error();
        1864                 :            :     }
        1865                 :            :
        1866                 :      16394 :     PySequenceMethods *m = Py_TYPE(s)->tp_as_sequence;
        1867   [ +  -  +  - ]:      16394 :     if (m && m->sq_item) {
        1868         [ -  + ]:      16394 :         if (i < 0) {
        1869         [ #  # ]:          0 :             if (m->sq_length) {
        1870                 :          0 :                 Py_ssize_t l = (*m->sq_length)(s);
        1871                 :            :                 assert(_Py_CheckSlotResult(s, "__len__", l >= 0));
        1872         [ #  # ]:          0 :                 if (l < 0) {
        1873                 :          0 :                     return NULL;
        1874                 :            :                 }
        1875                 :          0 :                 i += l;
        1876                 :            :             }
        1877                 :            :         }
        1878                 :      16394 :         PyObject *res = m->sq_item(s, i);
        1879                 :            :         assert(_Py_CheckSlotResult(s, "__getitem__", res != NULL));
        1880                 :      16394 :         return res;
        1881                 :            :     }
        1882                 :            :
        1883   [ #  #  #  # ]:          0 :     if (Py_TYPE(s)->tp_as_mapping && Py_TYPE(s)->tp_as_mapping->mp_subscript) {
        1884                 :          0 :         return type_error("%.200s is not a sequence", s);
        1885                 :            :     }
        1886                 :          0 :     return type_error("'%.200s' object does not support indexing", s);
        1887                 :            : }
        1888                 :            :
        1889                 :            : PyObject *
        1890                 :        775 : PySequence_GetSlice(PyObject *s, Py_ssize_t i1, Py_ssize_t i2)
        1891                 :            : {
        1892         [ -  + ]:        775 :     if (!s) {
        1893                 :          0 :         return null_error();
        1894                 :            :     }
        1895                 :            :
        1896                 :        775 :     PyMappingMethods *mp = Py_TYPE(s)->tp_as_mapping;
        1897   [ +  -  +  - ]:        775 :     if (mp && mp->mp_subscript) {
        1898                 :        775 :         PyObject *slice = _PySlice_FromIndices(i1, i2);
        1899         [ -  + ]:        775 :         if (!slice) {
        1900                 :          0 :             return NULL;
        1901                 :            :         }
        1902                 :        775 :         PyObject *res = mp->mp_subscript(s, slice);
        1903                 :            :         assert(_Py_CheckSlotResult(s, "__getitem__", res != NULL));
        1904                 :        775 :         Py_DECREF(slice);
        1905                 :        775 :         return res;
        1906                 :            :     }
        1907                 :            :
        1908                 :          0 :     return type_error("'%.200s' object is unsliceable", s);
        1909                 :            : }
        1910                 :            :
        1911                 :            : int
        1912                 :          0 : PySequence_SetItem(PyObject *s, Py_ssize_t i, PyObject *o)
        1913                 :            : {
        1914         [ #  # ]:          0 :     if (s == NULL) {
        1915                 :          0 :         null_error();
        1916                 :          0 :         return -1;
        1917                 :            :     }
        1918                 :            :
        1919                 :          0 :     PySequenceMethods *m = Py_TYPE(s)->tp_as_sequence;
        1920   [ #  #  #  # ]:          0 :     if (m && m->sq_ass_item) {
        1921         [ #  # ]:          0 :         if (i < 0) {
        1922         [ #  # ]:          0 :             if (m->sq_length) {
        1923                 :          0 :                 Py_ssize_t l = (*m->sq_length)(s);
        1924                 :            :                 assert(_Py_CheckSlotResult(s, "__len__", l >= 0));
        1925         [ #  # ]:          0 :                 if (l < 0) {
        1926                 :          0 :                     return -1;
        1927                 :            :                 }
        1928                 :          0 :                 i += l;
        1929                 :            :             }
        1930                 :            :         }
        1931                 :          0 :         int res = m->sq_ass_item(s, i, o);
        1932                 :            :         assert(_Py_CheckSlotResult(s, "__setitem__", res >= 0));
        1933                 :          0 :         return res;
        1934                 :            :     }
        1935                 :            :
        1936   [ #  #  #  # ]:          0 :     if (Py_TYPE(s)->tp_as_mapping && Py_TYPE(s)->tp_as_mapping->mp_ass_subscript) {
        1937                 :          0 :         type_error("%.200s is not a sequence", s);
        1938                 :          0 :         return -1;
        1939                 :            :     }
        1940                 :          0 :     type_error("'%.200s' object does not support item assignment", s);
        1941                 :          0 :     return -1;
        1942                 :            : }
        1943                 :            :
        1944                 :            : int
        1945                 :       7722 : PySequence_DelItem(PyObject *s, Py_ssize_t i)
        1946                 :            : {
        1947         [ -  + ]:       7722 :     if (s == NULL) {
        1948                 :          0 :         null_error();
        1949                 :          0 :         return -1;
        1950                 :            :     }
        1951                 :            :
        1952                 :       7722 :     PySequenceMethods *m = Py_TYPE(s)->tp_as_sequence;
        1953   [ +  -  +  - ]:       7722 :     if (m && m->sq_ass_item) {
        1954         [ -  + ]:       7722 :         if (i < 0) {
        1955         [ #  # ]:          0 :             if (m->sq_length) {
        1956                 :          0 :                 Py_ssize_t l = (*m->sq_length)(s);
        1957                 :            :                 assert(_Py_CheckSlotResult(s, "__len__", l >= 0));
        1958         [ #  # ]:          0 :                 if (l < 0) {
        1959                 :          0 :                     return -1;
        1960                 :            :                 }
        1961                 :          0 :                 i += l;
        1962                 :            :             }
        1963                 :            :         }
        1964                 :       7722 :         int res = m->sq_ass_item(s, i, (PyObject *)NULL);
        1965                 :            :         assert(_Py_CheckSlotResult(s, "__delitem__", res >= 0));
        1966                 :       7722 :         return res;
        1967                 :            :     }
        1968                 :            :
        1969   [ #  #  #  # ]:          0 :     if (Py_TYPE(s)->tp_as_mapping && Py_TYPE(s)->tp_as_mapping->mp_ass_subscript) {
        1970                 :          0 :         type_error("%.200s is not a sequence", s);
        1971                 :          0 :         return -1;
        1972                 :            :     }
        1973                 :          0 :     type_error("'%.200s' object doesn't support item deletion", s);
        1974                 :          0 :     return -1;
        1975                 :            : }
        1976                 :            :
        1977                 :            : int
        1978                 :          0 : PySequence_SetSlice(PyObject *s, Py_ssize_t i1, Py_ssize_t i2, PyObject *o)
        1979                 :            : {
        1980         [ #  # ]:          0 :     if (s == NULL) {
        1981                 :          0 :         null_error();
        1982                 :          0 :         return -1;
        1983                 :            :     }
        1984                 :            :
        1985                 :          0 :     PyMappingMethods *mp = Py_TYPE(s)->tp_as_mapping;
        1986   [ #  #  #  # ]:          0 :     if (mp && mp->mp_ass_subscript) {
        1987                 :          0 :         PyObject *slice = _PySlice_FromIndices(i1, i2);
        1988         [ #  # ]:          0 :         if (!slice)
        1989                 :          0 :             return -1;
        1990                 :          0 :         int res = mp->mp_ass_subscript(s, slice, o);
        1991                 :            :         assert(_Py_CheckSlotResult(s, "__setitem__", res >= 0));
        1992                 :          0 :         Py_DECREF(slice);
        1993                 :          0 :         return res;
        1994                 :            :     }
        1995                 :            :
        1996                 :          0 :     type_error("'%.200s' object doesn't support slice assignment", s);
        1997                 :          0 :     return -1;
        1998                 :            : }
        1999                 :            :
        2000                 :            : int
        2001                 :          0 : PySequence_DelSlice(PyObject *s, Py_ssize_t i1, Py_ssize_t i2)
        2002                 :            : {
        2003         [ #  # ]:          0 :     if (s == NULL) {
        2004                 :          0 :         null_error();
        2005                 :          0 :         return -1;
        2006                 :            :     }
        2007                 :            :
        2008                 :          0 :     PyMappingMethods *mp = Py_TYPE(s)->tp_as_mapping;
        2009   [ #  #  #  # ]:          0 :     if (mp && mp->mp_ass_subscript) {
        2010                 :          0 :         PyObject *slice = _PySlice_FromIndices(i1, i2);
        2011         [ #  # ]:          0 :         if (!slice) {
        2012                 :          0 :             return -1;
        2013                 :            :         }
        2014                 :          0 :         int res = mp->mp_ass_subscript(s, slice, NULL);
        2015                 :            :         assert(_Py_CheckSlotResult(s, "__delitem__", res >= 0));
        2016                 :          0 :         Py_DECREF(slice);
        2017                 :          0 :         return res;
        2018                 :            :     }
        2019                 :          0 :     type_error("'%.200s' object doesn't support slice deletion", s);
        2020                 :          0 :     return -1;
        2021                 :            : }
        2022                 :            :
        2023                 :            : PyObject *
        2024                 :      25192 : PySequence_Tuple(PyObject *v)
        2025                 :            : {
        2026                 :            :     PyObject *it;  /* iter(v) */
        2027                 :            :     Py_ssize_t n;             /* guess for result tuple size */
        2028                 :      25192 :     PyObject *result = NULL;
        2029                 :            :     Py_ssize_t j;
        2030                 :            :
        2031         [ -  + ]:      25192 :     if (v == NULL) {
        2032                 :          0 :         return null_error();
        2033                 :            :     }
        2034                 :            :
        2035                 :            :     /* Special-case the common tuple and list cases, for efficiency. */
        2036         [ +  + ]:      25192 :     if (PyTuple_CheckExact(v)) {
        2037                 :            :         /* Note that we can't know whether it's safe to return
        2038                 :            :            a tuple *subclass* instance as-is, hence the restriction
        2039                 :            :            to exact tuples here.  In contrast, lists always make
        2040                 :            :            a copy, so there's no need for exactness below. */
        2041                 :      12746 :         return Py_NewRef(v);
        2042                 :            :     }
        2043         [ +  + ]:      12446 :     if (PyList_CheckExact(v))
        2044                 :       9341 :         return PyList_AsTuple(v);
        2045                 :            :
        2046                 :            :     /* Get iterator. */
        2047                 :       3105 :     it = PyObject_GetIter(v);
        2048         [ +  + ]:       3105 :     if (it == NULL)
        2049                 :          1 :         return NULL;
        2050                 :            :
        2051                 :            :     /* Guess result size and allocate space. */
        2052                 :       3104 :     n = PyObject_LengthHint(v, 10);
        2053         [ -  + ]:       3104 :     if (n == -1)
        2054                 :          0 :         goto Fail;
        2055                 :       3104 :     result = PyTuple_New(n);
        2056         [ -  + ]:       3104 :     if (result == NULL)
        2057                 :          0 :         goto Fail;
        2058                 :            :
        2059                 :            :     /* Fill the tuple. */
        2060                 :     423109 :     for (j = 0; ; ++j) {
        2061                 :     423109 :         PyObject *item = PyIter_Next(it);
        2062         [ +  + ]:     423109 :         if (item == NULL) {
        2063         [ -  + ]:       3104 :             if (PyErr_Occurred())
        2064                 :          0 :                 goto Fail;
        2065                 :       3104 :             break;
        2066                 :            :         }
        2067         [ +  + ]:     420005 :         if (j >= n) {
        2068                 :        763 :             size_t newn = (size_t)n;
        2069                 :            :             /* The over-allocation strategy can grow a bit faster
        2070                 :            :                than for lists because unlike lists the
        2071                 :            :                over-allocation isn't permanent -- we reclaim
        2072                 :            :                the excess before the end of this routine.
        2073                 :            :                So, grow by ten and then add 25%.
        2074                 :            :             */
        2075                 :        763 :             newn += 10u;
        2076                 :        763 :             newn += newn >> 2;
        2077         [ -  + ]:        763 :             if (newn > PY_SSIZE_T_MAX) {
        2078                 :            :                 /* Check for overflow */
        2079                 :          0 :                 PyErr_NoMemory();
        2080                 :          0 :                 Py_DECREF(item);
        2081                 :          0 :                 goto Fail;
        2082                 :            :             }
        2083                 :        763 :             n = (Py_ssize_t)newn;
        2084         [ -  + ]:        763 :             if (_PyTuple_Resize(&result, n) != 0) {
        2085                 :          0 :                 Py_DECREF(item);
        2086                 :          0 :                 goto Fail;
        2087                 :            :             }
        2088                 :            :         }
        2089                 :     420005 :         PyTuple_SET_ITEM(result, j, item);
        2090                 :            :     }
        2091                 :            :
        2092                 :            :     /* Cut tuple back if guess was too large. */
        2093   [ +  +  -  + ]:       5198 :     if (j < n &&
        2094                 :       2094 :         _PyTuple_Resize(&result, j) != 0)
        2095                 :          0 :         goto Fail;
        2096                 :            :
        2097                 :       3104 :     Py_DECREF(it);
        2098                 :       3104 :     return result;
        2099                 :            :
        2100                 :          0 : Fail:
        2101                 :          0 :     Py_XDECREF(result);
        2102                 :          0 :     Py_DECREF(it);
        2103                 :          0 :     return NULL;
        2104                 :            : }
        2105                 :            :
        2106                 :            : PyObject *
        2107                 :      20546 : PySequence_List(PyObject *v)
        2108                 :            : {
        2109                 :            :     PyObject *result;  /* result list */
        2110                 :            :     PyObject *rv;          /* return value from PyList_Extend */
        2111                 :            :
        2112         [ -  + ]:      20546 :     if (v == NULL) {
        2113                 :          0 :         return null_error();
        2114                 :            :     }
        2115                 :            :
        2116                 :      20546 :     result = PyList_New(0);
        2117         [ -  + ]:      20546 :     if (result == NULL)
        2118                 :          0 :         return NULL;
        2119                 :            :
        2120                 :      20546 :     rv = _PyList_Extend((PyListObject *)result, v);
        2121         [ -  + ]:      20546 :     if (rv == NULL) {
        2122                 :          0 :         Py_DECREF(result);
        2123                 :          0 :         return NULL;
        2124                 :            :     }
        2125                 :      20546 :     Py_DECREF(rv);
        2126                 :      20546 :     return result;
        2127                 :            : }
        2128                 :            :
        2129                 :            : PyObject *
        2130                 :      57161 : PySequence_Fast(PyObject *v, const char *m)
        2131                 :            : {
        2132                 :            :     PyObject *it;
        2133                 :            :
        2134         [ -  + ]:      57161 :     if (v == NULL) {
        2135                 :          0 :         return null_error();
        2136                 :            :     }
        2137                 :            :
        2138   [ +  +  +  + ]:      57161 :     if (PyList_CheckExact(v) || PyTuple_CheckExact(v)) {
        2139                 :      40603 :         return Py_NewRef(v);
        2140                 :            :     }
        2141                 :            :
        2142                 :      16558 :     it = PyObject_GetIter(v);
        2143         [ -  + ]:      16558 :     if (it == NULL) {
        2144                 :          0 :         PyThreadState *tstate = _PyThreadState_GET();
        2145         [ #  # ]:          0 :         if (_PyErr_ExceptionMatches(tstate, PyExc_TypeError)) {
        2146                 :          0 :             _PyErr_SetString(tstate, PyExc_TypeError, m);
        2147                 :            :         }
        2148                 :          0 :         return NULL;
        2149                 :            :     }
        2150                 :            :
        2151                 :      16558 :     v = PySequence_List(it);
        2152                 :      16558 :     Py_DECREF(it);
        2153                 :            :
        2154                 :      16558 :     return v;
        2155                 :            : }
        2156                 :            :
        2157                 :            : /* Iterate over seq.  Result depends on the operation:
        2158                 :            :    PY_ITERSEARCH_COUNT:  -1 if error, else # of times obj appears in seq.
        2159                 :            :    PY_ITERSEARCH_INDEX:  0-based index of first occurrence of obj in seq;
        2160                 :            :     set ValueError and return -1 if none found; also return -1 on error.
        2161                 :            :    Py_ITERSEARCH_CONTAINS:  return 1 if obj in seq, else 0; -1 on error.
        2162                 :            : */
        2163                 :            : Py_ssize_t
        2164                 :          0 : _PySequence_IterSearch(PyObject *seq, PyObject *obj, int operation)
        2165                 :            : {
        2166                 :            :     Py_ssize_t n;
        2167                 :            :     int wrapped;  /* for PY_ITERSEARCH_INDEX, true iff n wrapped around */
        2168                 :            :     PyObject *it;  /* iter(seq) */
        2169                 :            :
        2170   [ #  #  #  # ]:          0 :     if (seq == NULL || obj == NULL) {
        2171                 :          0 :         null_error();
        2172                 :          0 :         return -1;
        2173                 :            :     }
        2174                 :            :
        2175                 :          0 :     it = PyObject_GetIter(seq);
        2176         [ #  # ]:          0 :     if (it == NULL) {
        2177         [ #  # ]:          0 :         if (PyErr_ExceptionMatches(PyExc_TypeError)) {
        2178                 :          0 :             type_error("argument of type '%.200s' is not iterable", seq);
        2179                 :            :         }
        2180                 :          0 :         return -1;
        2181                 :            :     }
        2182                 :            :
        2183                 :          0 :     n = wrapped = 0;
        2184                 :          0 :     for (;;) {
        2185                 :            :         int cmp;
        2186                 :          0 :         PyObject *item = PyIter_Next(it);
        2187         [ #  # ]:          0 :         if (item == NULL) {
        2188         [ #  # ]:          0 :             if (PyErr_Occurred())
        2189                 :          0 :                 goto Fail;
        2190                 :          0 :             break;
        2191                 :            :         }
        2192                 :            :
        2193                 :          0 :         cmp = PyObject_RichCompareBool(item, obj, Py_EQ);
        2194                 :          0 :         Py_DECREF(item);
        2195         [ #  # ]:          0 :         if (cmp < 0)
        2196                 :          0 :             goto Fail;
        2197         [ #  # ]:          0 :         if (cmp > 0) {
        2198   [ #  #  #  # ]:          0 :             switch (operation) {
        2199                 :          0 :             case PY_ITERSEARCH_COUNT:
        2200         [ #  # ]:          0 :                 if (n == PY_SSIZE_T_MAX) {
        2201                 :          0 :                     PyErr_SetString(PyExc_OverflowError,
        2202                 :            :                            "count exceeds C integer size");
        2203                 :          0 :                     goto Fail;
        2204                 :            :                 }
        2205                 :          0 :                 ++n;
        2206                 :          0 :                 break;
        2207                 :            :
        2208                 :          0 :             case PY_ITERSEARCH_INDEX:
        2209         [ #  # ]:          0 :                 if (wrapped) {
        2210                 :          0 :                     PyErr_SetString(PyExc_OverflowError,
        2211                 :            :                            "index exceeds C integer size");
        2212                 :          0 :                     goto Fail;
        2213                 :            :                 }
        2214                 :          0 :                 goto Done;
        2215                 :            :
        2216                 :          0 :             case PY_ITERSEARCH_CONTAINS:
        2217                 :          0 :                 n = 1;
        2218                 :          0 :                 goto Done;
        2219                 :            :
        2220                 :          0 :             default:
        2221                 :          0 :                 Py_UNREACHABLE();
        2222                 :            :             }
        2223                 :          0 :         }
        2224                 :            :
        2225         [ #  # ]:          0 :         if (operation == PY_ITERSEARCH_INDEX) {
        2226         [ #  # ]:          0 :             if (n == PY_SSIZE_T_MAX)
        2227                 :          0 :                 wrapped = 1;
        2228                 :          0 :             ++n;
        2229                 :            :         }
        2230                 :            :     }
        2231                 :            :
        2232         [ #  # ]:          0 :     if (operation != PY_ITERSEARCH_INDEX)
        2233                 :          0 :         goto Done;
        2234                 :            :
        2235                 :          0 :     PyErr_SetString(PyExc_ValueError,
        2236                 :            :                     "sequence.index(x): x not in sequence");
        2237                 :            :     /* fall into failure code */
        2238                 :          0 : Fail:
        2239                 :          0 :     n = -1;
        2240                 :            :     /* fall through */
        2241                 :          0 : Done:
        2242                 :          0 :     Py_DECREF(it);
        2243                 :          0 :     return n;
        2244                 :            :
        2245                 :            : }
        2246                 :            :
        2247                 :            : /* Return # of times o appears in s. */
        2248                 :            : Py_ssize_t
        2249                 :          0 : PySequence_Count(PyObject *s, PyObject *o)
        2250                 :            : {
        2251                 :          0 :     return _PySequence_IterSearch(s, o, PY_ITERSEARCH_COUNT);
        2252                 :            : }
        2253                 :            :
        2254                 :            : /* Return -1 if error; 1 if ob in seq; 0 if ob not in seq.
        2255                 :            :  * Use sq_contains if possible, else defer to _PySequence_IterSearch().
        2256                 :            :  */
        2257                 :            : int
        2258                 :      71080 : PySequence_Contains(PyObject *seq, PyObject *ob)
        2259                 :            : {
        2260                 :      71080 :     PySequenceMethods *sqm = Py_TYPE(seq)->tp_as_sequence;
        2261   [ +  -  +  - ]:      71080 :     if (sqm != NULL && sqm->sq_contains != NULL) {
        2262                 :      71080 :         int res = (*sqm->sq_contains)(seq, ob);
        2263                 :            :         assert(_Py_CheckSlotResult(seq, "__contains__", res >= 0));
        2264                 :      71080 :         return res;
        2265                 :            :     }
        2266                 :          0 :     Py_ssize_t result = _PySequence_IterSearch(seq, ob, PY_ITERSEARCH_CONTAINS);
        2267                 :          0 :     return Py_SAFE_DOWNCAST(result, Py_ssize_t, int);
        2268                 :            : }
        2269                 :            :
        2270                 :            : /* Backwards compatibility */
        2271                 :            : #undef PySequence_In
        2272                 :            : int
        2273                 :          0 : PySequence_In(PyObject *w, PyObject *v)
        2274                 :            : {
        2275                 :          0 :     return PySequence_Contains(w, v);
        2276                 :            : }
        2277                 :            :
        2278                 :            : Py_ssize_t
        2279                 :          0 : PySequence_Index(PyObject *s, PyObject *o)
        2280                 :            : {
        2281                 :          0 :     return _PySequence_IterSearch(s, o, PY_ITERSEARCH_INDEX);
        2282                 :            : }
        2283                 :            :
        2284                 :            : /* Operations on mappings */
        2285                 :            :
        2286                 :            : int
        2287                 :       8390 : PyMapping_Check(PyObject *o)
        2288                 :            : {
        2289   [ +  -  +  + ]:      16776 :     return o && Py_TYPE(o)->tp_as_mapping &&
        2290         [ +  - ]:       8386 :         Py_TYPE(o)->tp_as_mapping->mp_subscript;
        2291                 :            : }
        2292                 :            :
        2293                 :            : Py_ssize_t
        2294                 :        374 : PyMapping_Size(PyObject *o)
        2295                 :            : {
        2296         [ -  + ]:        374 :     if (o == NULL) {
        2297                 :          0 :         null_error();
        2298                 :          0 :         return -1;
        2299                 :            :     }
        2300                 :            :
        2301                 :        374 :     PyMappingMethods *m = Py_TYPE(o)->tp_as_mapping;
        2302   [ +  -  +  - ]:        374 :     if (m && m->mp_length) {
        2303                 :        374 :         Py_ssize_t len = m->mp_length(o);
        2304                 :            :         assert(_Py_CheckSlotResult(o, "__len__", len >= 0));
        2305                 :        374 :         return len;
        2306                 :            :     }
        2307                 :            :
        2308   [ #  #  #  # ]:          0 :     if (Py_TYPE(o)->tp_as_sequence && Py_TYPE(o)->tp_as_sequence->sq_length) {
        2309                 :          0 :         type_error("%.200s is not a mapping", o);
        2310                 :          0 :         return -1;
        2311                 :            :     }
        2312                 :            :     /* PyMapping_Size() can be called from PyObject_Size(). */
        2313                 :          0 :     type_error("object of type '%.200s' has no len()", o);
        2314                 :          0 :     return -1;
        2315                 :            : }
        2316                 :            :
        2317                 :            : #undef PyMapping_Length
        2318                 :            : Py_ssize_t
        2319                 :          0 : PyMapping_Length(PyObject *o)
        2320                 :            : {
        2321                 :          0 :     return PyMapping_Size(o);
        2322                 :            : }
        2323                 :            : #define PyMapping_Length PyMapping_Size
        2324                 :            :
        2325                 :            : PyObject *
        2326                 :        120 : PyMapping_GetItemString(PyObject *o, const char *key)
        2327                 :            : {
        2328                 :            :     PyObject *okey, *r;
        2329                 :            :
        2330         [ -  + ]:        120 :     if (key == NULL) {
        2331                 :          0 :         return null_error();
        2332                 :            :     }
        2333                 :            :
        2334                 :        120 :     okey = PyUnicode_FromString(key);
        2335         [ -  + ]:        120 :     if (okey == NULL)
        2336                 :          0 :         return NULL;
        2337                 :        120 :     r = PyObject_GetItem(o, okey);
        2338                 :        120 :     Py_DECREF(okey);
        2339                 :        120 :     return r;
        2340                 :            : }
        2341                 :            :
        2342                 :            : int
        2343                 :         40 : PyMapping_SetItemString(PyObject *o, const char *key, PyObject *value)
        2344                 :            : {
        2345                 :            :     PyObject *okey;
        2346                 :            :     int r;
        2347                 :            :
        2348         [ -  + ]:         40 :     if (key == NULL) {
        2349                 :          0 :         null_error();
        2350                 :          0 :         return -1;
        2351                 :            :     }
        2352                 :            :
        2353                 :         40 :     okey = PyUnicode_FromString(key);
        2354         [ -  + ]:         40 :     if (okey == NULL)
        2355                 :          0 :         return -1;
        2356                 :         40 :     r = PyObject_SetItem(o, okey, value);
        2357                 :         40 :     Py_DECREF(okey);
        2358                 :         40 :     return r;
        2359                 :            : }
        2360                 :            :
        2361                 :            : int
        2362                 :          0 : PyMapping_HasKeyString(PyObject *o, const char *key)
        2363                 :            : {
        2364                 :            :     PyObject *v;
        2365                 :            :
        2366                 :          0 :     v = PyMapping_GetItemString(o, key);
        2367         [ #  # ]:          0 :     if (v) {
        2368                 :          0 :         Py_DECREF(v);
        2369                 :          0 :         return 1;
        2370                 :            :     }
        2371                 :          0 :     PyErr_Clear();
        2372                 :          0 :     return 0;
        2373                 :            : }
        2374                 :            :
        2375                 :            : int
        2376                 :          0 : PyMapping_HasKey(PyObject *o, PyObject *key)
        2377                 :            : {
        2378                 :            :     PyObject *v;
        2379                 :            :
        2380                 :          0 :     v = PyObject_GetItem(o, key);
        2381         [ #  # ]:          0 :     if (v) {
        2382                 :          0 :         Py_DECREF(v);
        2383                 :          0 :         return 1;
        2384                 :            :     }
        2385                 :          0 :     PyErr_Clear();
        2386                 :          0 :     return 0;
        2387                 :            : }
        2388                 :            :
        2389                 :            : /* This function is quite similar to PySequence_Fast(), but specialized to be
        2390                 :            :    a helper for PyMapping_Keys(), PyMapping_Items() and PyMapping_Values().
        2391                 :            :  */
        2392                 :            : static PyObject *
        2393                 :       1031 : method_output_as_list(PyObject *o, PyObject *meth)
        2394                 :            : {
        2395                 :            :     PyObject *it, *result, *meth_output;
        2396                 :            :
        2397                 :            :     assert(o != NULL);
        2398                 :       1031 :     meth_output = PyObject_CallMethodNoArgs(o, meth);
        2399   [ +  -  -  + ]:       1031 :     if (meth_output == NULL || PyList_CheckExact(meth_output)) {
        2400                 :          0 :         return meth_output;
        2401                 :            :     }
        2402                 :       1031 :     it = PyObject_GetIter(meth_output);
        2403         [ -  + ]:       1031 :     if (it == NULL) {
        2404                 :          0 :         PyThreadState *tstate = _PyThreadState_GET();
        2405         [ #  # ]:          0 :         if (_PyErr_ExceptionMatches(tstate, PyExc_TypeError)) {
        2406                 :          0 :             _PyErr_Format(tstate, PyExc_TypeError,
        2407                 :            :                           "%.200s.%U() returned a non-iterable (type %.200s)",
        2408                 :          0 :                           Py_TYPE(o)->tp_name,
        2409                 :            :                           meth,
        2410                 :          0 :                           Py_TYPE(meth_output)->tp_name);
        2411                 :            :         }
        2412                 :          0 :         Py_DECREF(meth_output);
        2413                 :          0 :         return NULL;
        2414                 :            :     }
        2415                 :       1031 :     Py_DECREF(meth_output);
        2416                 :       1031 :     result = PySequence_List(it);
        2417                 :       1031 :     Py_DECREF(it);
        2418                 :       1031 :     return result;
        2419                 :            : }
        2420                 :            :
        2421                 :            : PyObject *
        2422                 :        178 : PyMapping_Keys(PyObject *o)
        2423                 :            : {
        2424         [ -  + ]:        178 :     if (o == NULL) {
        2425                 :          0 :         return null_error();
        2426                 :            :     }
        2427         [ +  + ]:        178 :     if (PyDict_CheckExact(o)) {
        2428                 :        109 :         return PyDict_Keys(o);
        2429                 :            :     }
        2430                 :         69 :     return method_output_as_list(o, &_Py_ID(keys));
        2431                 :            : }
        2432                 :            :
        2433                 :            : PyObject *
        2434                 :        962 : PyMapping_Items(PyObject *o)
        2435                 :            : {
        2436         [ -  + ]:        962 :     if (o == NULL) {
        2437                 :          0 :         return null_error();
        2438                 :            :     }
        2439         [ -  + ]:        962 :     if (PyDict_CheckExact(o)) {
        2440                 :          0 :         return PyDict_Items(o);
        2441                 :            :     }
        2442                 :        962 :     return method_output_as_list(o, &_Py_ID(items));
        2443                 :            : }
        2444                 :            :
        2445                 :            : PyObject *
        2446                 :          0 : PyMapping_Values(PyObject *o)
        2447                 :            : {
        2448         [ #  # ]:          0 :     if (o == NULL) {
        2449                 :          0 :         return null_error();
        2450                 :            :     }
        2451         [ #  # ]:          0 :     if (PyDict_CheckExact(o)) {
        2452                 :          0 :         return PyDict_Values(o);
        2453                 :            :     }
        2454                 :          0 :     return method_output_as_list(o, &_Py_ID(values));
        2455                 :            : }
        2456                 :            :
        2457                 :            : /* isinstance(), issubclass() */
        2458                 :            :
        2459                 :            : /* abstract_get_bases() has logically 4 return states:
        2460                 :            :  *
        2461                 :            :  * 1. getattr(cls, '__bases__') could raise an AttributeError
        2462                 :            :  * 2. getattr(cls, '__bases__') could raise some other exception
        2463                 :            :  * 3. getattr(cls, '__bases__') could return a tuple
        2464                 :            :  * 4. getattr(cls, '__bases__') could return something other than a tuple
        2465                 :            :  *
        2466                 :            :  * Only state #3 is a non-error state and only it returns a non-NULL object
        2467                 :            :  * (it returns the retrieved tuple).
        2468                 :            :  *
        2469                 :            :  * Any raised AttributeErrors are masked by clearing the exception and
        2470                 :            :  * returning NULL.  If an object other than a tuple comes out of __bases__,
        2471                 :            :  * then again, the return value is NULL.  So yes, these two situations
        2472                 :            :  * produce exactly the same results: NULL is returned and no error is set.
        2473                 :            :  *
        2474                 :            :  * If some exception other than AttributeError is raised, then NULL is also
        2475                 :            :  * returned, but the exception is not cleared.  That's because we want the
        2476                 :            :  * exception to be propagated along.
        2477                 :            :  *
        2478                 :            :  * Callers are expected to test for PyErr_Occurred() when the return value
        2479                 :            :  * is NULL to decide whether a valid exception should be propagated or not.
        2480                 :            :  * When there's no exception to propagate, it's customary for the caller to
        2481                 :            :  * set a TypeError.
        2482                 :            :  */
        2483                 :            : static PyObject *
        2484                 :          0 : abstract_get_bases(PyObject *cls)
        2485                 :            : {
        2486                 :            :     PyObject *bases;
        2487                 :            :
        2488                 :          0 :     (void)_PyObject_LookupAttr(cls, &_Py_ID(__bases__), &bases);
        2489   [ #  #  #  # ]:          0 :     if (bases != NULL && !PyTuple_Check(bases)) {
        2490                 :          0 :         Py_DECREF(bases);
        2491                 :          0 :         return NULL;
        2492                 :            :     }
        2493                 :          0 :     return bases;
        2494                 :            : }
        2495                 :            :
        2496                 :            :
        2497                 :            : static int
        2498                 :          0 : abstract_issubclass(PyObject *derived, PyObject *cls)
        2499                 :            : {
        2500                 :          0 :     PyObject *bases = NULL;
        2501                 :            :     Py_ssize_t i, n;
        2502                 :          0 :     int r = 0;
        2503                 :            :
        2504                 :            :     while (1) {
        2505         [ #  # ]:          0 :         if (derived == cls) {
        2506                 :          0 :             Py_XDECREF(bases); /* See below comment */
        2507                 :          0 :             return 1;
        2508                 :            :         }
        2509                 :            :         /* Use XSETREF to drop bases reference *after* finishing with
        2510                 :            :            derived; bases might be the only reference to it.
        2511                 :            :            XSETREF is used instead of SETREF, because bases is NULL on the
        2512                 :            :            first iteration of the loop.
        2513                 :            :         */
        2514                 :          0 :         Py_XSETREF(bases, abstract_get_bases(derived));
        2515         [ #  # ]:          0 :         if (bases == NULL) {
        2516         [ #  # ]:          0 :             if (PyErr_Occurred())
        2517                 :          0 :                 return -1;
        2518                 :          0 :             return 0;
        2519                 :            :         }
        2520                 :          0 :         n = PyTuple_GET_SIZE(bases);
        2521         [ #  # ]:          0 :         if (n == 0) {
        2522                 :          0 :             Py_DECREF(bases);
        2523                 :          0 :             return 0;
        2524                 :            :         }
        2525                 :            :         /* Avoid recursivity in the single inheritance case */
        2526         [ #  # ]:          0 :         if (n == 1) {
        2527                 :          0 :             derived = PyTuple_GET_ITEM(bases, 0);
        2528                 :          0 :             continue;
        2529                 :            :         }
        2530                 :          0 :         break;
        2531                 :            :     }
        2532                 :            :     assert(n >= 2);
        2533         [ #  # ]:          0 :     if (_Py_EnterRecursiveCall(" in __issubclass__")) {
        2534                 :          0 :         Py_DECREF(bases);
        2535                 :          0 :         return -1;
        2536                 :            :     }
        2537         [ #  # ]:          0 :     for (i = 0; i < n; i++) {
        2538                 :          0 :         r = abstract_issubclass(PyTuple_GET_ITEM(bases, i), cls);
        2539         [ #  # ]:          0 :         if (r != 0) {
        2540                 :          0 :             break;
        2541                 :            :         }
        2542                 :            :     }
        2543                 :          0 :     _Py_LeaveRecursiveCall();
        2544                 :          0 :     Py_DECREF(bases);
        2545                 :          0 :     return r;
        2546                 :            : }
        2547                 :            :
        2548                 :            : static int
        2549                 :          0 : check_class(PyObject *cls, const char *error)
        2550                 :            : {
        2551                 :          0 :     PyObject *bases = abstract_get_bases(cls);
        2552         [ #  # ]:          0 :     if (bases == NULL) {
        2553                 :            :         /* Do not mask errors. */
        2554                 :          0 :         PyThreadState *tstate = _PyThreadState_GET();
        2555         [ #  # ]:          0 :         if (!_PyErr_Occurred(tstate)) {
        2556                 :          0 :             _PyErr_SetString(tstate, PyExc_TypeError, error);
        2557                 :            :         }
        2558                 :          0 :         return 0;
        2559                 :            :     }
        2560                 :          0 :     Py_DECREF(bases);
        2561                 :          0 :     return -1;
        2562                 :            : }
        2563                 :            :
        2564                 :            : static int
        2565                 :      36972 : object_isinstance(PyObject *inst, PyObject *cls)
        2566                 :            : {
        2567                 :            :     PyObject *icls;
        2568                 :            :     int retval;
        2569         [ +  - ]:      36972 :     if (PyType_Check(cls)) {
        2570                 :      36972 :         retval = PyObject_TypeCheck(inst, (PyTypeObject *)cls);
        2571         [ +  + ]:      36972 :         if (retval == 0) {
        2572                 :      36252 :             retval = _PyObject_LookupAttr(inst, &_Py_ID(__class__), &icls);
        2573         [ +  - ]:      36252 :             if (icls != NULL) {
        2574   [ -  +  -  - ]:      36252 :                 if (icls != (PyObject *)(Py_TYPE(inst)) && PyType_Check(icls)) {
        2575                 :          0 :                     retval = PyType_IsSubtype(
        2576                 :            :                         (PyTypeObject *)icls,
        2577                 :            :                         (PyTypeObject *)cls);
        2578                 :            :                 }
        2579                 :            :                 else {
        2580                 :      36252 :                     retval = 0;
        2581                 :            :                 }
        2582                 :      36252 :                 Py_DECREF(icls);
        2583                 :            :             }
        2584                 :            :         }
        2585                 :            :     }
        2586                 :            :     else {
        2587         [ #  # ]:          0 :         if (!check_class(cls,
        2588                 :            :             "isinstance() arg 2 must be a type, a tuple of types, or a union"))
        2589                 :          0 :             return -1;
        2590                 :          0 :         retval = _PyObject_LookupAttr(inst, &_Py_ID(__class__), &icls);
        2591         [ #  # ]:          0 :         if (icls != NULL) {
        2592                 :          0 :             retval = abstract_issubclass(icls, cls);
        2593                 :          0 :             Py_DECREF(icls);
        2594                 :            :         }
        2595                 :            :     }
        2596                 :            :
        2597                 :      36972 :     return retval;
        2598                 :            : }
        2599                 :            :
        2600                 :            : static int
        2601                 :     633245 : object_recursive_isinstance(PyThreadState *tstate, PyObject *inst, PyObject *cls)
        2602                 :            : {
        2603                 :            :     /* Quick test for an exact match */
        2604         [ +  + ]:     633245 :     if (Py_IS_TYPE(inst, (PyTypeObject *)cls)) {
        2605                 :     488792 :         return 1;
        2606                 :            :     }
        2607                 :            :
        2608                 :            :     /* We know what type's __instancecheck__ does. */
        2609         [ +  + ]:     144453 :     if (PyType_CheckExact(cls)) {
        2610                 :      30829 :         return object_isinstance(inst, cls);
        2611                 :            :     }
        2612                 :            :
        2613         [ -  + ]:     113624 :     if (_PyUnion_Check(cls)) {
        2614                 :          0 :         cls = _Py_union_args(cls);
        2615                 :            :     }
        2616                 :            :
        2617         [ +  + ]:     113624 :     if (PyTuple_Check(cls)) {
        2618                 :            :         /* Not a general sequence -- that opens up the road to
        2619                 :            :            recursion and stack overflow. */
        2620         [ -  + ]:      37228 :         if (_Py_EnterRecursiveCallTstate(tstate, " in __instancecheck__")) {
        2621                 :          0 :             return -1;
        2622                 :            :         }
        2623                 :      37228 :         Py_ssize_t n = PyTuple_GET_SIZE(cls);
        2624                 :      37228 :         int r = 0;
        2625         [ +  + ]:      50105 :         for (Py_ssize_t i = 0; i < n; ++i) {
        2626                 :      44058 :             PyObject *item = PyTuple_GET_ITEM(cls, i);
        2627                 :      44058 :             r = object_recursive_isinstance(tstate, inst, item);
        2628         [ +  + ]:      44058 :             if (r != 0) {
        2629                 :            :                 /* either found it, or got an error */
        2630                 :      31181 :                 break;
        2631                 :            :             }
        2632                 :            :         }
        2633                 :      37228 :         _Py_LeaveRecursiveCallTstate(tstate);
        2634                 :      37228 :         return r;
        2635                 :            :     }
        2636                 :            :
        2637                 :      76396 :     PyObject *checker = _PyObject_LookupSpecial(cls, &_Py_ID(__instancecheck__));
        2638         [ +  - ]:      76396 :     if (checker != NULL) {
        2639         [ -  + ]:      76396 :         if (_Py_EnterRecursiveCallTstate(tstate, " in __instancecheck__")) {
        2640                 :          0 :             Py_DECREF(checker);
        2641                 :          0 :             return -1;
        2642                 :            :         }
        2643                 :            :
        2644                 :      76396 :         PyObject *res = PyObject_CallOneArg(checker, inst);
        2645                 :      76396 :         _Py_LeaveRecursiveCallTstate(tstate);
        2646                 :      76396 :         Py_DECREF(checker);
        2647                 :            :
        2648         [ -  + ]:      76396 :         if (res == NULL) {
        2649                 :          0 :             return -1;
        2650                 :            :         }
        2651                 :      76396 :         int ok = PyObject_IsTrue(res);
        2652                 :      76396 :         Py_DECREF(res);
        2653                 :            :
        2654                 :      76396 :         return ok;
        2655                 :            :     }
        2656         [ #  # ]:          0 :     else if (_PyErr_Occurred(tstate)) {
        2657                 :          0 :         return -1;
        2658                 :            :     }
        2659                 :            :
        2660                 :            :     /* cls has no __instancecheck__() method */
        2661                 :          0 :     return object_isinstance(inst, cls);
        2662                 :            : }
        2663                 :            :
        2664                 :            :
        2665                 :            : int
        2666                 :     589187 : PyObject_IsInstance(PyObject *inst, PyObject *cls)
        2667                 :            : {
        2668                 :     589187 :     PyThreadState *tstate = _PyThreadState_GET();
        2669                 :     589187 :     return object_recursive_isinstance(tstate, inst, cls);
        2670                 :            : }
        2671                 :            :
        2672                 :            :
        2673                 :            : static  int
        2674                 :      17673 : recursive_issubclass(PyObject *derived, PyObject *cls)
        2675                 :            : {
        2676   [ +  -  +  - ]:      17673 :     if (PyType_Check(cls) && PyType_Check(derived)) {
        2677                 :            :         /* Fast path (non-recursive) */
        2678                 :      17673 :         return PyType_IsSubtype((PyTypeObject *)derived, (PyTypeObject *)cls);
        2679                 :            :     }
        2680         [ #  # ]:          0 :     if (!check_class(derived,
        2681                 :            :                      "issubclass() arg 1 must be a class"))
        2682                 :          0 :         return -1;
        2683                 :            :
        2684   [ #  #  #  # ]:          0 :     if (!_PyUnion_Check(cls) && !check_class(cls,
        2685                 :            :                             "issubclass() arg 2 must be a class,"
        2686                 :            :                             " a tuple of classes, or a union")) {
        2687                 :          0 :         return -1;
        2688                 :            :     }
        2689                 :            :
        2690                 :          0 :     return abstract_issubclass(derived, cls);
        2691                 :            : }
        2692                 :            :
        2693                 :            : static int
        2694                 :       5687 : object_issubclass(PyThreadState *tstate, PyObject *derived, PyObject *cls)
        2695                 :            : {
        2696                 :            :     PyObject *checker;
        2697                 :            :
        2698                 :            :     /* We know what type's __subclasscheck__ does. */
        2699         [ +  + ]:       5687 :     if (PyType_CheckExact(cls)) {
        2700                 :            :         /* Quick test for an exact match */
        2701         [ +  + ]:       4090 :         if (derived == cls)
        2702                 :       2615 :             return 1;
        2703                 :       1475 :         return recursive_issubclass(derived, cls);
        2704                 :            :     }
        2705                 :            :
        2706         [ -  + ]:       1597 :     if (_PyUnion_Check(cls)) {
        2707                 :          0 :         cls = _Py_union_args(cls);
        2708                 :            :     }
        2709                 :            :
        2710         [ +  + ]:       1597 :     if (PyTuple_Check(cls)) {
        2711                 :            :
        2712         [ -  + ]:         21 :         if (_Py_EnterRecursiveCallTstate(tstate, " in __subclasscheck__")) {
        2713                 :          0 :             return -1;
        2714                 :            :         }
        2715                 :         21 :         Py_ssize_t n = PyTuple_GET_SIZE(cls);
        2716                 :         21 :         int r = 0;
        2717         [ +  + ]:         60 :         for (Py_ssize_t i = 0; i < n; ++i) {
        2718                 :         42 :             PyObject *item = PyTuple_GET_ITEM(cls, i);
        2719                 :         42 :             r = object_issubclass(tstate, derived, item);
        2720         [ +  + ]:         42 :             if (r != 0)
        2721                 :            :                 /* either found it, or got an error */
        2722                 :          3 :                 break;
        2723                 :            :         }
        2724                 :         21 :         _Py_LeaveRecursiveCallTstate(tstate);
        2725                 :         21 :         return r;
        2726                 :            :     }
        2727                 :            :
        2728                 :       1576 :     checker = _PyObject_LookupSpecial(cls, &_Py_ID(__subclasscheck__));
        2729         [ +  - ]:       1576 :     if (checker != NULL) {
        2730                 :       1576 :         int ok = -1;
        2731         [ -  + ]:       1576 :         if (_Py_EnterRecursiveCallTstate(tstate, " in __subclasscheck__")) {
        2732                 :          0 :             Py_DECREF(checker);
        2733                 :          0 :             return ok;
        2734                 :            :         }
        2735                 :       1576 :         PyObject *res = PyObject_CallOneArg(checker, derived);
        2736                 :       1576 :         _Py_LeaveRecursiveCallTstate(tstate);
        2737                 :       1576 :         Py_DECREF(checker);
        2738         [ +  - ]:       1576 :         if (res != NULL) {
        2739                 :       1576 :             ok = PyObject_IsTrue(res);
        2740                 :       1576 :             Py_DECREF(res);
        2741                 :            :         }
        2742                 :       1576 :         return ok;
        2743                 :            :     }
        2744         [ #  # ]:          0 :     else if (_PyErr_Occurred(tstate)) {
        2745                 :          0 :         return -1;
        2746                 :            :     }
        2747                 :            :
        2748                 :            :     /* Probably never reached anymore. */
        2749                 :          0 :     return recursive_issubclass(derived, cls);
        2750                 :            : }
        2751                 :            :
        2752                 :            :
        2753                 :            : int
        2754                 :       5645 : PyObject_IsSubclass(PyObject *derived, PyObject *cls)
        2755                 :            : {
        2756                 :       5645 :     PyThreadState *tstate = _PyThreadState_GET();
        2757                 :       5645 :     return object_issubclass(tstate, derived, cls);
        2758                 :            : }
        2759                 :            :
        2760                 :            :
        2761                 :            : int
        2762                 :       6143 : _PyObject_RealIsInstance(PyObject *inst, PyObject *cls)
        2763                 :            : {
        2764                 :       6143 :     return object_isinstance(inst, cls);
        2765                 :            : }
        2766                 :            :
        2767                 :            : int
        2768                 :      16198 : _PyObject_RealIsSubclass(PyObject *derived, PyObject *cls)
        2769                 :            : {
        2770                 :      16198 :     return recursive_issubclass(derived, cls);
        2771                 :            : }
        2772                 :            :
        2773                 :            :
        2774                 :            : PyObject *
        2775                 :    2499224 : PyObject_GetIter(PyObject *o)
        2776                 :            : {
        2777                 :    2499224 :     PyTypeObject *t = Py_TYPE(o);
        2778                 :            :     getiterfunc f;
        2779                 :            :
        2780                 :    2499224 :     f = t->tp_iter;
        2781         [ +  + ]:    2499224 :     if (f == NULL) {
        2782         [ +  + ]:        609 :         if (PySequence_Check(o))
        2783                 :        527 :             return PySeqIter_New(o);
        2784                 :         82 :         return type_error("'%.200s' object is not iterable", o);
        2785                 :            :     }
        2786                 :            :     else {
        2787                 :    2498615 :         PyObject *res = (*f)(o);
        2788   [ +  -  -  + ]:    2498615 :         if (res != NULL && !PyIter_Check(res)) {
        2789                 :          0 :             PyErr_Format(PyExc_TypeError,
        2790                 :            :                          "iter() returned non-iterator "
        2791                 :            :                          "of type '%.100s'",
        2792                 :          0 :                          Py_TYPE(res)->tp_name);
        2793                 :          0 :             Py_SETREF(res, NULL);
        2794                 :            :         }
        2795                 :    2498615 :         return res;
        2796                 :            :     }
        2797                 :            : }
        2798                 :            :
        2799                 :            : PyObject *
        2800                 :          0 : PyObject_GetAIter(PyObject *o) {
        2801                 :          0 :     PyTypeObject *t = Py_TYPE(o);
        2802                 :            :     unaryfunc f;
        2803                 :            :
        2804   [ #  #  #  # ]:          0 :     if (t->tp_as_async == NULL || t->tp_as_async->am_aiter == NULL) {
        2805                 :          0 :         return type_error("'%.200s' object is not an async iterable", o);
        2806                 :            :     }
        2807                 :          0 :     f = t->tp_as_async->am_aiter;
        2808                 :          0 :     PyObject *it = (*f)(o);
        2809   [ #  #  #  # ]:          0 :     if (it != NULL && !PyAIter_Check(it)) {
        2810                 :          0 :         PyErr_Format(PyExc_TypeError,
        2811                 :            :                      "aiter() returned not an async iterator of type '%.100s'",
        2812                 :          0 :                      Py_TYPE(it)->tp_name);
        2813                 :          0 :         Py_SETREF(it, NULL);
        2814                 :            :     }
        2815                 :          0 :     return it;
        2816                 :            : }
        2817                 :            :
        2818                 :            : int
        2819                 :    2695476 : PyIter_Check(PyObject *obj)
        2820                 :            : {
        2821                 :    2695476 :     PyTypeObject *tp = Py_TYPE(obj);
        2822         [ +  - ]:    5390952 :     return (tp->tp_iternext != NULL &&
        2823         [ +  - ]:    2695476 :             tp->tp_iternext != &_PyObject_NextNotImplemented);
        2824                 :            : }
        2825                 :            :
        2826                 :            : int
        2827                 :          0 : PyAIter_Check(PyObject *obj)
        2828                 :            : {
        2829                 :          0 :     PyTypeObject *tp = Py_TYPE(obj);
        2830                 :          0 :     return (tp->tp_as_async != NULL &&
        2831   [ #  #  #  # ]:          0 :             tp->tp_as_async->am_anext != NULL &&
        2832         [ #  # ]:          0 :             tp->tp_as_async->am_anext != &_PyObject_NextNotImplemented);
        2833                 :            : }
        2834                 :            :
        2835                 :            : /* Return next item.
        2836                 :            :  * If an error occurs, return NULL.  PyErr_Occurred() will be true.
        2837                 :            :  * If the iteration terminates normally, return NULL and clear the
        2838                 :            :  * PyExc_StopIteration exception (if it was set).  PyErr_Occurred()
        2839                 :            :  * will be false.
        2840                 :            :  * Else return the next object.  PyErr_Occurred() will be false.
        2841                 :            :  */
        2842                 :            : PyObject *
        2843                 :    1702468 : PyIter_Next(PyObject *iter)
        2844                 :            : {
        2845                 :            :     PyObject *result;
        2846                 :    1702468 :     result = (*Py_TYPE(iter)->tp_iternext)(iter);
        2847         [ +  + ]:    1702468 :     if (result == NULL) {
        2848                 :     276009 :         PyThreadState *tstate = _PyThreadState_GET();
        2849         [ -  + ]:     276009 :         if (_PyErr_Occurred(tstate)
        2850         [ #  # ]:          0 :             && _PyErr_ExceptionMatches(tstate, PyExc_StopIteration))
        2851                 :            :         {
        2852                 :          0 :             _PyErr_Clear(tstate);
        2853                 :            :         }
        2854                 :            :     }
        2855                 :    1702468 :     return result;
        2856                 :            : }
        2857                 :            :
        2858                 :            : PySendResult
        2859                 :          0 : PyIter_Send(PyObject *iter, PyObject *arg, PyObject **result)
        2860                 :            : {
        2861                 :            :     assert(arg != NULL);
        2862                 :            :     assert(result != NULL);
        2863   [ #  #  #  # ]:          0 :     if (Py_TYPE(iter)->tp_as_async && Py_TYPE(iter)->tp_as_async->am_send) {
        2864                 :          0 :         PySendResult res = Py_TYPE(iter)->tp_as_async->am_send(iter, arg, result);
        2865                 :            :         assert(_Py_CheckSlotResult(iter, "am_send", res != PYGEN_ERROR));
        2866                 :          0 :         return res;
        2867                 :            :     }
        2868   [ #  #  #  # ]:          0 :     if (arg == Py_None && PyIter_Check(iter)) {
        2869                 :          0 :         *result = Py_TYPE(iter)->tp_iternext(iter);
        2870                 :            :     }
        2871                 :            :     else {
        2872                 :          0 :         *result = PyObject_CallMethodOneArg(iter, &_Py_ID(send), arg);
        2873                 :            :     }
        2874         [ #  # ]:          0 :     if (*result != NULL) {
        2875                 :          0 :         return PYGEN_NEXT;
        2876                 :            :     }
        2877         [ #  # ]:          0 :     if (_PyGen_FetchStopIterationValue(result) == 0) {
        2878                 :          0 :         return PYGEN_RETURN;
        2879                 :            :     }
        2880                 :          0 :     return PYGEN_ERROR;
        2881                 :            : }
        2882                 :            :
        2883                 :            : /*
        2884                 :            :  * Flatten a sequence of bytes() objects into a C array of
        2885                 :            :  * NULL terminated string pointers with a NULL char* terminating the array.
        2886                 :            :  * (ie: an argv or env list)
        2887                 :            :  *
        2888                 :            :  * Memory allocated for the returned list is allocated using PyMem_Malloc()
        2889                 :            :  * and MUST be freed by _Py_FreeCharPArray().
        2890                 :            :  */
        2891                 :            : char *const *
        2892                 :          0 : _PySequence_BytesToCharpArray(PyObject* self)
        2893                 :            : {
        2894                 :            :     char **array;
        2895                 :            :     Py_ssize_t i, argc;
        2896                 :          0 :     PyObject *item = NULL;
        2897                 :            :     Py_ssize_t size;
        2898                 :            :
        2899                 :          0 :     argc = PySequence_Size(self);
        2900         [ #  # ]:          0 :     if (argc == -1)
        2901                 :          0 :         return NULL;
        2902                 :            :
        2903                 :            :     assert(argc >= 0);
        2904                 :            :
        2905         [ #  # ]:          0 :     if ((size_t)argc > (PY_SSIZE_T_MAX-sizeof(char *)) / sizeof(char *)) {
        2906                 :          0 :         PyErr_NoMemory();
        2907                 :          0 :         return NULL;
        2908                 :            :     }
        2909                 :            :
        2910                 :          0 :     array = PyMem_Malloc((argc + 1) * sizeof(char *));
        2911         [ #  # ]:          0 :     if (array == NULL) {
        2912                 :          0 :         PyErr_NoMemory();
        2913                 :          0 :         return NULL;
        2914                 :            :     }
        2915         [ #  # ]:          0 :     for (i = 0; i < argc; ++i) {
        2916                 :            :         char *data;
        2917                 :          0 :         item = PySequence_GetItem(self, i);
        2918         [ #  # ]:          0 :         if (item == NULL) {
        2919                 :            :             /* NULL terminate before freeing. */
        2920                 :          0 :             array[i] = NULL;
        2921                 :          0 :             goto fail;
        2922                 :            :         }
        2923                 :            :         /* check for embedded null bytes */
        2924         [ #  # ]:          0 :         if (PyBytes_AsStringAndSize(item, &data, NULL) < 0) {
        2925                 :            :             /* NULL terminate before freeing. */
        2926                 :          0 :             array[i] = NULL;
        2927                 :          0 :             goto fail;
        2928                 :            :         }
        2929                 :          0 :         size = PyBytes_GET_SIZE(item) + 1;
        2930                 :          0 :         array[i] = PyMem_Malloc(size);
        2931         [ #  # ]:          0 :         if (!array[i]) {
        2932                 :          0 :             PyErr_NoMemory();
        2933                 :          0 :             goto fail;
        2934                 :            :         }
        2935                 :          0 :         memcpy(array[i], data, size);
        2936                 :          0 :         Py_DECREF(item);
        2937                 :            :     }
        2938                 :          0 :     array[argc] = NULL;
        2939                 :            :
        2940                 :          0 :     return array;
        2941                 :            :
        2942                 :          0 : fail:
        2943                 :          0 :     Py_XDECREF(item);
        2944                 :          0 :     _Py_FreeCharPArray(array);
        2945                 :          0 :     return NULL;
        2946                 :            : }
        2947                 :            :
        2948                 :            :
        2949                 :            : /* Free's a NULL terminated char** array of C strings. */
        2950                 :            : void
        2951                 :          0 : _Py_FreeCharPArray(char *const array[])
        2952                 :            : {
        2953                 :            :     Py_ssize_t i;
        2954         [ #  # ]:          0 :     for (i = 0; array[i] != NULL; ++i) {
        2955                 :          0 :         PyMem_Free(array[i]);
        2956                 :            :     }
        2957                 :          0 :     PyMem_Free((void*)array);
        2958                 :          0 : }

Generated by: LCOV version 1.14