Coverage Report

Created: 2022-07-08 09:39

/home/mdboom/Work/builds/cpython/Python/getargs.c
Line
Count
Source (jump to first uncovered line)
1
2
/* New getargs implementation */
3
4
#include "Python.h"
5
#include "pycore_tuple.h"         // _PyTuple_ITEMS()
6
#include "pycore_pylifecycle.h"   // _PyArg_Fini
7
8
#include <ctype.h>
9
#include <float.h>
10
11
12
#ifdef __cplusplus
13
extern "C" {
14
#endif
15
int PyArg_Parse(PyObject *, const char *, ...);
16
int PyArg_ParseTuple(PyObject *, const char *, ...);
17
int PyArg_VaParse(PyObject *, const char *, va_list);
18
19
int PyArg_ParseTupleAndKeywords(PyObject *, PyObject *,
20
                                const char *, char **, ...);
21
int PyArg_VaParseTupleAndKeywords(PyObject *, PyObject *,
22
                                const char *, char **, va_list);
23
24
int _PyArg_ParseTupleAndKeywordsFast(PyObject *, PyObject *,
25
                                            struct _PyArg_Parser *, ...);
26
int _PyArg_VaParseTupleAndKeywordsFast(PyObject *, PyObject *,
27
                                            struct _PyArg_Parser *, va_list);
28
29
#ifdef HAVE_DECLSPEC_DLL
30
/* Export functions */
31
PyAPI_FUNC(int) _PyArg_Parse_SizeT(PyObject *, const char *, ...);
32
PyAPI_FUNC(int) _PyArg_ParseStack_SizeT(PyObject *const *args, Py_ssize_t nargs,
33
                                        const char *format, ...);
34
PyAPI_FUNC(int) _PyArg_ParseStackAndKeywords_SizeT(PyObject *const *args, Py_ssize_t nargs,
35
                                        PyObject *kwnames,
36
                                        struct _PyArg_Parser *parser, ...);
37
PyAPI_FUNC(int) _PyArg_ParseTuple_SizeT(PyObject *, const char *, ...);
38
PyAPI_FUNC(int) _PyArg_ParseTupleAndKeywords_SizeT(PyObject *, PyObject *,
39
                                                  const char *, char **, ...);
40
PyAPI_FUNC(PyObject *) _Py_BuildValue_SizeT(const char *, ...);
41
PyAPI_FUNC(int) _PyArg_VaParse_SizeT(PyObject *, const char *, va_list);
42
PyAPI_FUNC(int) _PyArg_VaParseTupleAndKeywords_SizeT(PyObject *, PyObject *,
43
                                              const char *, char **, va_list);
44
45
PyAPI_FUNC(int) _PyArg_ParseTupleAndKeywordsFast_SizeT(PyObject *, PyObject *,
46
                                            struct _PyArg_Parser *, ...);
47
PyAPI_FUNC(int) _PyArg_VaParseTupleAndKeywordsFast_SizeT(PyObject *, PyObject *,
48
                                            struct _PyArg_Parser *, va_list);
49
#endif
50
51
#define FLAG_COMPAT 1
52
#define FLAG_SIZE_T 2
53
54
typedef int (*destr_t)(PyObject *, void *);
55
56
57
/* Keep track of "objects" that have been allocated or initialized and
58
   which will need to be deallocated or cleaned up somehow if overall
59
   parsing fails.
60
*/
61
typedef struct {
62
  void *item;
63
  destr_t destructor;
64
} freelistentry_t;
65
66
typedef struct {
67
  freelistentry_t *entries;
68
  int first_available;
69
  int entries_malloced;
70
} freelist_t;
71
72
#define STATIC_FREELIST_ENTRIES 8
73
74
/* Forward */
75
static int vgetargs1_impl(PyObject *args, PyObject *const *stack, Py_ssize_t nargs,
76
                          const char *format, va_list *p_va, int flags);
77
static int vgetargs1(PyObject *, const char *, va_list *, int);
78
static void seterror(Py_ssize_t, const char *, int *, const char *, const char *);
79
static const char *convertitem(PyObject *, const char **, va_list *, int, int *,
80
                               char *, size_t, freelist_t *);
81
static const char *converttuple(PyObject *, const char **, va_list *, int,
82
                                int *, char *, size_t, int, freelist_t *);
83
static const char *convertsimple(PyObject *, const char **, va_list *, int,
84
                                 char *, size_t, freelist_t *);
85
static Py_ssize_t convertbuffer(PyObject *, const void **p, const char **);
86
static int getbuffer(PyObject *, Py_buffer *, const char**);
87
88
static int vgetargskeywords(PyObject *, PyObject *,
89
                            const char *, char **, va_list *, int);
90
static int vgetargskeywordsfast(PyObject *, PyObject *,
91
                            struct _PyArg_Parser *, va_list *, int);
92
static int vgetargskeywordsfast_impl(PyObject *const *args, Py_ssize_t nargs,
93
                          PyObject *keywords, PyObject *kwnames,
94
                          struct _PyArg_Parser *parser,
95
                          va_list *p_va, int flags);
96
static const char *skipitem(const char **, va_list *, int);
97
98
int
99
PyArg_Parse(PyObject *args, const char *format, ...)
100
{
101
    int retval;
102
    va_list va;
103
104
    va_start(va, format);
105
    retval = vgetargs1(args, format, &va, FLAG_COMPAT);
106
    va_end(va);
107
    return retval;
108
}
109
110
PyAPI_FUNC(int)
111
_PyArg_Parse_SizeT(PyObject *args, const char *format, ...)
112
{
113
    int retval;
114
    va_list va;
115
116
    va_start(va, format);
117
    retval = vgetargs1(args, format, &va, FLAG_COMPAT|FLAG_SIZE_T);
118
    va_end(va);
119
    return retval;
120
}
121
122
123
int
124
PyArg_ParseTuple(PyObject *args, const char *format, ...)
125
{
126
    int retval;
127
    va_list va;
128
129
    va_start(va, format);
130
    retval = vgetargs1(args, format, &va, 0);
131
    va_end(va);
132
    return retval;
133
}
134
135
PyAPI_FUNC(int)
136
_PyArg_ParseTuple_SizeT(PyObject *args, const char *format, ...)
137
{
138
    int retval;
139
    va_list va;
140
141
    va_start(va, format);
142
    retval = vgetargs1(args, format, &va, FLAG_SIZE_T);
143
    va_end(va);
144
    return retval;
145
}
146
147
148
int
149
_PyArg_ParseStack(PyObject *const *args, Py_ssize_t nargs, const char *format, ...)
150
{
151
    int retval;
152
    va_list va;
153
154
    va_start(va, format);
155
    retval = vgetargs1_impl(NULL, args, nargs, format, &va, 0);
156
    va_end(va);
157
    return retval;
158
}
159
160
PyAPI_FUNC(int)
161
_PyArg_ParseStack_SizeT(PyObject *const *args, Py_ssize_t nargs, const char *format, ...)
162
{
163
    int retval;
164
    va_list va;
165
166
    va_start(va, format);
167
    retval = vgetargs1_impl(NULL, args, nargs, format, &va, FLAG_SIZE_T);
168
    va_end(va);
169
    return retval;
170
}
171
172
173
int
174
PyArg_VaParse(PyObject *args, const char *format, va_list va)
175
{
176
    va_list lva;
177
    int retval;
178
179
    va_copy(lva, va);
180
181
    retval = vgetargs1(args, format, &lva, 0);
182
    va_end(lva);
183
    return retval;
184
}
185
186
PyAPI_FUNC(int)
187
_PyArg_VaParse_SizeT(PyObject *args, const char *format, va_list va)
188
{
189
    va_list lva;
190
    int retval;
191
192
    va_copy(lva, va);
193
194
    retval = vgetargs1(args, format, &lva, FLAG_SIZE_T);
195
    va_end(lva);
196
    return retval;
197
}
198
199
200
/* Handle cleanup of allocated memory in case of exception */
201
202
static int
203
cleanup_ptr(PyObject *self, void *ptr)
204
{
205
    if (ptr) {
  Branch (205:9): [True: 0, False: 0]
206
        PyMem_Free(ptr);
207
    }
208
    return 0;
209
}
210
211
static int
212
cleanup_buffer(PyObject *self, void *ptr)
213
{
214
    Py_buffer *buf = (Py_buffer *)ptr;
215
    if (buf) {
  Branch (215:9): [True: 2, False: 0]
216
        PyBuffer_Release(buf);
217
    }
218
    return 0;
219
}
220
221
static int
222
addcleanup(void *ptr, freelist_t *freelist, destr_t destructor)
223
{
224
    int index;
225
226
    index = freelist->first_available;
227
    freelist->first_available += 1;
228
229
    freelist->entries[index].item = ptr;
230
    freelist->entries[index].destructor = destructor;
231
232
    return 0;
233
}
234
235
static int
236
cleanreturn(int retval, freelist_t *freelist)
237
{
238
    int index;
239
240
    if (retval == 0) {
  Branch (240:9): [True: 1.69k, False: 22.5M]
241
      /* A failure occurred, therefore execute all of the cleanup
242
         functions.
243
      */
244
      for (index = 0; index < freelist->first_available; 
++index3
) {
  Branch (244:23): [True: 3, False: 1.69k]
245
          freelist->entries[index].destructor(NULL,
246
                                              freelist->entries[index].item);
247
      }
248
    }
249
    if (freelist->entries_malloced)
  Branch (249:9): [True: 88.9k, False: 22.4M]
250
        PyMem_Free(freelist->entries);
251
    return retval;
252
}
253
254
255
static int
256
vgetargs1_impl(PyObject *compat_args, PyObject *const *stack, Py_ssize_t nargs, const char *format,
257
               va_list *p_va, int flags)
258
{
259
    char msgbuf[256];
260
    int levels[32];
261
    const char *fname = NULL;
262
    const char *message = NULL;
263
    int min = -1;
264
    int max = 0;
265
    int level = 0;
266
    int endfmt = 0;
267
    const char *formatsave = format;
268
    Py_ssize_t i;
269
    const char *msg;
270
    int compat = flags & FLAG_COMPAT;
271
    freelistentry_t static_entries[STATIC_FREELIST_ENTRIES];
272
    freelist_t freelist;
273
274
    assert(nargs == 0 || stack != NULL);
275
276
    freelist.entries = static_entries;
277
    freelist.first_available = 0;
278
    freelist.entries_malloced = 0;
279
280
    flags = flags & ~FLAG_COMPAT;
281
282
    while (endfmt == 0) {
  Branch (282:12): [True: 64.5M, False: 14.4M]
283
        int c = *format++;
284
        switch (c) {
285
        case '(':
  Branch (285:9): [True: 1.10k, False: 64.5M]
286
            if (level == 0)
  Branch (286:17): [True: 1.10k, False: 0]
287
                max++;
288
            level++;
289
            if (level >= 30)
  Branch (289:17): [True: 0, False: 1.10k]
290
                Py_FatalError("too many tuple nesting levels "
291
                              "in argument format string");
292
            break;
293
        case ')':
  Branch (293:9): [True: 1.10k, False: 64.5M]
294
            if (level == 0)
  Branch (294:17): [True: 0, False: 1.10k]
295
                Py_FatalError("excess ')' in getargs format");
296
            else
297
                level--;
298
            break;
299
        case '\0':
  Branch (299:9): [True: 2.49M, False: 62.0M]
300
            endfmt = 1;
301
            break;
302
        case ':':
  Branch (302:9): [True: 11.4M, False: 53.0M]
303
            fname = format;
304
            endfmt = 1;
305
            break;
306
        case ';':
  Branch (306:9): [True: 447k, False: 64.1M]
307
            message = format;
308
            endfmt = 1;
309
            break;
310
        case '|':
  Branch (310:9): [True: 10.6M, False: 53.9M]
311
            if (level == 0)
  Branch (311:17): [True: 10.6M, False: 0]
312
                min = max;
313
            break;
314
        default:
  Branch (314:9): [True: 39.5M, False: 25.0M]
315
            if (level == 0) {
  Branch (315:17): [True: 39.5M, False: 3.80k]
316
                if (Py_ISALPHA(c))
317
                    if (c != 'e') /* skip encoded */
  Branch (317:25): [True: 36.5M, False: 617]
318
                        max++;
319
            }
320
            break;
321
        }
322
    }
323
324
    if (level != 0)
  Branch (324:9): [True: 0, False: 14.4M]
325
        Py_FatalError(/* '(' */ "missing ')' in getargs format");
326
327
    if (min < 0)
  Branch (327:9): [True: 3.80M, False: 10.6M]
328
        min = max;
329
330
    format = formatsave;
331
332
    if (max > STATIC_FREELIST_ENTRIES) {
  Branch (332:9): [True: 19.9k, False: 14.4M]
333
        freelist.entries = PyMem_NEW(freelistentry_t, max);
334
        if (freelist.entries == NULL) {
  Branch (334:13): [True: 0, False: 19.9k]
335
            PyErr_NoMemory();
336
            return 0;
337
        }
338
        freelist.entries_malloced = 1;
339
    }
340
341
    if (compat) {
  Branch (341:9): [True: 2.53M, False: 11.8M]
342
        if (max == 0) {
  Branch (342:13): [True: 0, False: 2.53M]
343
            if (compat_args == NULL)
  Branch (343:17): [True: 0, False: 0]
344
                return 1;
345
            PyErr_Format(PyExc_TypeError,
346
                         "%.200s%s takes no arguments",
347
                         fname==NULL ? "function" : fname,
  Branch (347:26): [True: 0, False: 0]
348
                         fname==NULL ? "" : "()");
  Branch (348:26): [True: 0, False: 0]
349
            return cleanreturn(0, &freelist);
350
        }
351
        else if (min == 1 && max == 1) {
  Branch (351:18): [True: 2.53M, False: 0]
  Branch (351:30): [True: 2.53M, False: 0]
352
            if (compat_args == NULL) {
  Branch (352:17): [True: 0, False: 2.53M]
353
                PyErr_Format(PyExc_TypeError,
354
                             "%.200s%s takes at least one argument",
355
                             fname==NULL ? "function" : fname,
  Branch (355:30): [True: 0, False: 0]
356
                             fname==NULL ? "" : "()");
  Branch (356:30): [True: 0, False: 0]
357
                return cleanreturn(0, &freelist);
358
            }
359
            msg = convertitem(compat_args, &format, p_va, flags, levels,
360
                              msgbuf, sizeof(msgbuf), &freelist);
361
            if (msg == NULL)
  Branch (361:17): [True: 2.53M, False: 274]
362
                return cleanreturn(1, &freelist);
363
            seterror(levels[0], msg, levels+1, fname, message);
364
            return cleanreturn(0, &freelist);
365
        }
366
        else {
367
            PyErr_SetString(PyExc_SystemError,
368
                "old style getargs format uses new features");
369
            return cleanreturn(0, &freelist);
370
        }
371
    }
372
373
    if (nargs < min || 
max < nargs11.8M
) {
  Branch (373:9): [True: 97, False: 11.8M]
  Branch (373:24): [True: 80, False: 11.8M]
374
        if (message == NULL)
  Branch (374:13): [True: 133, False: 44]
375
            PyErr_Format(PyExc_TypeError,
376
                         "%.150s%s takes %s %d argument%s (%zd given)",
377
                         fname==NULL ? 
"function"48
:
fname85
,
  Branch (377:26): [True: 48, False: 85]
378
                         fname==NULL ? 
""48
:
"()"85
,
  Branch (378:26): [True: 48, False: 85]
379
                         min==max ? 
"exactly"58
  Branch (379:26): [True: 58, False: 75]
380
                         : 
nargs < min75
?
"at least"43
:
"at most"32
,
  Branch (380:28): [True: 43, False: 32]
381
                         nargs < min ? 
min77
:
max56
,
  Branch (381:26): [True: 77, False: 56]
382
                         (nargs < min ? 
min77
:
max56
) == 1 ?
""46
:
"s"87
,
  Branch (382:26): [True: 46, False: 87]
  Branch (382:27): [True: 77, False: 56]
383
                         nargs);
384
        else
385
            PyErr_SetString(PyExc_TypeError, message);
386
        return cleanreturn(0, &freelist);
387
    }
388
389
    
for (i = 0; 11.8M
i < nargs;
i++17.9M
) {
  Branch (389:17): [True: 17.9M, False: 11.8M]
390
        if (*format == '|')
  Branch (390:13): [True: 4.31M, False: 13.6M]
391
            format++;
392
        msg = convertitem(stack[i], &format, p_va,
393
                          flags, levels, msgbuf,
394
                          sizeof(msgbuf), &freelist);
395
        if (msg) {
  Branch (395:13): [True: 575, False: 17.9M]
396
            seterror(i+1, msg, levels, fname, message);
397
            return cleanreturn(0, &freelist);
398
        }
399
    }
400
401
    if (*format != '\0' && 
!11.5M
Py_ISALPHA11.5M
(*format) &&
  Branch (401:9): [True: 11.5M, False: 354k]
  Branch (401:28): [True: 7.80M, False: 3.72M]
402
        
*format != '('7.80M
&&
  Branch (402:9): [True: 7.80M, False: 0]
403
        
*format != '|'7.80M
&&
*format != ':'1.50M
&&
*format != ';'101k
) {
  Branch (403:9): [True: 1.50M, False: 6.30M]
  Branch (403:27): [True: 101k, False: 1.40M]
  Branch (403:45): [True: 1, False: 101k]
404
        PyErr_Format(PyExc_SystemError,
405
                     "bad format string: %.200s", formatsave);
406
        return cleanreturn(0, &freelist);
407
    }
408
409
    return cleanreturn(1, &freelist);
410
}
411
412
static int
413
vgetargs1(PyObject *args, const char *format, va_list *p_va, int flags)
414
{
415
    PyObject **stack;
416
    Py_ssize_t nargs;
417
418
    if (!(flags & FLAG_COMPAT)) {
  Branch (418:9): [True: 11.7M, False: 2.53M]
419
        assert(args != NULL);
420
421
        if (!PyTuple_Check(args)) {
  Branch (421:13): [True: 0, False: 11.7M]
422
            PyErr_SetString(PyExc_SystemError,
423
                "new style getargs format but argument is not a tuple");
424
            return 0;
425
        }
426
427
        stack = _PyTuple_ITEMS(args);
428
        nargs = PyTuple_GET_SIZE(args);
429
    }
430
    else {
431
        stack = NULL;
432
        nargs = 0;
433
    }
434
435
    return vgetargs1_impl(args, stack, nargs, format, p_va, flags);
436
}
437
438
439
static void
440
seterror(Py_ssize_t iarg, const char *msg, int *levels, const char *fname,
441
         const char *message)
442
{
443
    char buf[512];
444
    int i;
445
    char *p = buf;
446
447
    if (PyErr_Occurred())
  Branch (447:9): [True: 594, False: 561]
448
        return;
449
    else if (message == NULL) {
  Branch (449:14): [True: 528, False: 33]
450
        if (fname != NULL) {
  Branch (450:13): [True: 100, False: 428]
451
            PyOS_snprintf(p, sizeof(buf), "%.200s() ", fname);
452
            p += strlen(p);
453
        }
454
        if (iarg != 0) {
  Branch (454:13): [True: 458, False: 70]
455
            PyOS_snprintf(p, sizeof(buf) - (p - buf),
456
                          "argument %zd", iarg);
457
            i = 0;
458
            p += strlen(p);
459
            while (i < 32 && levels[i] > 0 && 
(int)(p-buf) < 2201
) {
  Branch (459:20): [True: 459, False: 0]
  Branch (459:30): [True: 1, False: 458]
  Branch (459:47): [True: 1, False: 0]
460
                PyOS_snprintf(p, sizeof(buf) - (p - buf),
461
                              ", item %d", levels[i]-1);
462
                p += strlen(p);
463
                i++;
464
            }
465
        }
466
        else {
467
            PyOS_snprintf(p, sizeof(buf) - (p - buf), "argument");
468
            p += strlen(p);
469
        }
470
        PyOS_snprintf(p, sizeof(buf) - (p - buf), " %.256s", msg);
471
        message = buf;
472
    }
473
    if (msg[0] == '(') {
  Branch (473:9): [True: 110, False: 451]
474
        PyErr_SetString(PyExc_SystemError, message);
475
    }
476
    else {
477
        PyErr_SetString(PyExc_TypeError, message);
478
    }
479
}
480
481
482
/* Convert a tuple argument.
483
   On entry, *p_format points to the character _after_ the opening '('.
484
   On successful exit, *p_format points to the closing ')'.
485
   If successful:
486
      *p_format and *p_va are updated,
487
      *levels and *msgbuf are untouched,
488
      and NULL is returned.
489
   If the argument is invalid:
490
      *p_format is unchanged,
491
      *p_va is undefined,
492
      *levels is a 0-terminated list of item numbers,
493
      *msgbuf contains an error message, whose format is:
494
     "must be <typename1>, not <typename2>", where:
495
        <typename1> is the name of the expected type, and
496
        <typename2> is the name of the actual type,
497
      and msgbuf is returned.
498
*/
499
500
static const char *
501
converttuple(PyObject *arg, const char **p_format, va_list *p_va, int flags,
502
             int *levels, char *msgbuf, size_t bufsize, int toplevel,
503
             freelist_t *freelist)
504
{
505
    int level = 0;
506
    int n = 0;
507
    const char *format = *p_format;
508
    int i;
509
    Py_ssize_t len;
510
511
    for (;;) {
512
        int c = *format++;
513
        if (c == '(') {
  Branch (513:13): [True: 4, False: 4.98k]
514
            if (level == 0)
  Branch (514:17): [True: 4, False: 0]
515
                n++;
516
            level++;
517
        }
518
        else if (c == ')') {
  Branch (518:18): [True: 1.13k, False: 3.84k]
519
            if (level == 0)
  Branch (519:17): [True: 1.12k, False: 4]
520
                break;
521
            level--;
522
        }
523
        else if (c == ':' || c == ';' || c == '\0')
  Branch (523:18): [True: 0, False: 3.84k]
  Branch (523:30): [True: 0, False: 3.84k]
  Branch (523:42): [True: 0, False: 3.84k]
524
            break;
525
        else if (level == 0 && 
Py_ISALPHA3.84k
(c))
  Branch (525:18): [True: 3.84k, False: 8]
526
            n++;
527
    }
528
529
    if (!PySequence_Check(arg) || 
PyBytes_Check1.10k
(arg)) {
  Branch (529:9): [True: 21, False: 1.10k]
530
        levels[0] = 0;
531
        PyOS_snprintf(msgbuf, bufsize,
532
                      toplevel ? 
"expected %d arguments, not %.50s"0
:
  Branch (532:23): [True: 0, False: 21]
533
                      "must be %d-item sequence, not %.50s",
534
                  n,
535
                  arg == Py_None ? 
"None"0
: Py_TYPE(arg)->tp_name);
  Branch (535:19): [True: 0, False: 21]
536
        return msgbuf;
537
    }
538
539
    len = PySequence_Size(arg);
540
    if (len != n) {
  Branch (540:9): [True: 14, False: 1.09k]
541
        levels[0] = 0;
542
        if (toplevel) {
  Branch (542:13): [True: 0, False: 14]
543
            PyOS_snprintf(msgbuf, bufsize,
544
                          "expected %d argument%s, not %zd",
545
                          n,
546
                          n == 1 ? "" : "s",
  Branch (546:27): [True: 0, False: 0]
547
                          len);
548
        }
549
        else {
550
            PyOS_snprintf(msgbuf, bufsize,
551
                          "must be sequence of length %d, not %zd",
552
                          n, len);
553
        }
554
        return msgbuf;
555
    }
556
557
    format = *p_format;
558
    for (i = 0; i < n; 
i++2.90k
) {
  Branch (558:17): [True: 2.92k, False: 1.07k]
559
        const char *msg;
560
        PyObject *item;
561
        item = PySequence_GetItem(arg, i);
562
        if (item == NULL) {
  Branch (562:13): [True: 1, False: 2.92k]
563
            PyErr_Clear();
564
            levels[0] = i+1;
565
            levels[1] = 0;
566
            strncpy(msgbuf, "is not retrievable", bufsize);
567
            return msgbuf;
568
        }
569
        msg = convertitem(item, &format, p_va, flags, levels+1,
570
                          msgbuf, bufsize, freelist);
571
        /* PySequence_GetItem calls tp->sq_item, which INCREFs */
572
        Py_XDECREF(item);
573
        if (msg != NULL) {
  Branch (573:13): [True: 21, False: 2.90k]
574
            levels[0] = i+1;
575
            return msg;
576
        }
577
    }
578
579
    *p_format = format;
580
    return NULL;
581
}
582
583
584
/* Convert a single item. */
585
586
static const char *
587
convertitem(PyObject *arg, const char **p_format, va_list *p_va, int flags,
588
            int *levels, char *msgbuf, size_t bufsize, freelist_t *freelist)
589
{
590
    const char *msg;
591
    const char *format = *p_format;
592
593
    if (*format == '(' /* ')' */) {
  Branch (593:9): [True: 1.12k, False: 22.9M]
594
        format++;
595
        msg = converttuple(arg, &format, p_va, flags, levels, msgbuf,
596
                           bufsize, 0, freelist);
597
        if (msg == NULL)
  Branch (597:13): [True: 1.07k, False: 57]
598
            format++;
599
    }
600
    else {
601
        msg = convertsimple(arg, &format, p_va, flags,
602
                            msgbuf, bufsize, freelist);
603
        if (msg != NULL)
  Branch (603:13): [True: 1.11k, False: 22.9M]
604
            levels[0] = 0;
605
    }
606
    if (msg == NULL)
  Branch (606:9): [True: 22.9M, False: 1.17k]
607
        *p_format = format;
608
    return msg;
609
}
610
611
612
613
/* Format an error message generated by convertsimple().
614
   displayname must be UTF-8 encoded.
615
*/
616
617
void
618
_PyArg_BadArgument(const char *fname, const char *displayname,
619
                   const char *expected, PyObject *arg)
620
{
621
    PyErr_Format(PyExc_TypeError,
622
                 "%.200s() %.200s must be %.50s, not %.50s",
623
                 fname, displayname, expected,
624
                 arg == Py_None ? 
"None"14
:
Py_TYPE112
(arg)->tp_name112
);
  Branch (624:18): [True: 14, False: 112]
625
}
626
627
static const char *
628
converterr(const char *expected, PyObject *arg, char *msgbuf, size_t bufsize)
629
{
630
    assert(expected != NULL);
631
    assert(arg != NULL);
632
    if (expected[0] == '(') {
  Branch (632:9): [True: 144, False: 488]
633
        PyOS_snprintf(msgbuf, bufsize,
634
                      "%.100s", expected);
635
    }
636
    else {
637
        PyOS_snprintf(msgbuf, bufsize,
638
                      "must be %.50s, not %.50s", expected,
639
                      arg == Py_None ? 
"None"47
:
Py_TYPE441
(arg)->tp_name441
);
  Branch (639:23): [True: 47, False: 441]
640
    }
641
    return msgbuf;
642
}
643
644
#define CONV_UNICODE "(unicode conversion error)"
645
646
/* Convert a non-tuple argument.  Return NULL if conversion went OK,
647
   or a string with a message describing the failure.  The message is
648
   formatted as "must be <desired type>, not <actual type>".
649
   When failing, an exception may or may not have been raised.
650
   Don't call if a tuple is expected.
651
652
   When you add new format codes, please don't forget poor skipitem() below.
653
*/
654
655
static const char *
656
convertsimple(PyObject *arg, const char **p_format, va_list *p_va, int flags,
657
              char *msgbuf, size_t bufsize, freelist_t *freelist)
658
{
659
#define RETURN_ERR_OCCURRED 
return msgbuf487
660
    /* For # codes */
661
#define REQUIRE_PY_SSIZE_T_CLEAN \
662
    
if (57.2k
!(flags & 57.2k
FLAG_SIZE_T57.2k
)) { \
663
        PyErr_SetString(PyExc_SystemError, \
664
                        "PY_SSIZE_T_CLEAN macro must be defined for '#' formats"); \
665
        RETURN_ERR_OCCURRED; \
666
    }
667
668
    const char *format = *p_format;
669
    char c = *format++;
670
    const char *sarg;
671
672
    switch (c) {
673
674
    case 'b': { /* unsigned byte -- very short int */
  Branch (674:5): [True: 70.3k, False: 22.8M]
675
        char *p = va_arg(*p_va, char *);
676
        long ival = PyLong_AsLong(arg);
677
        if (ival == -1 && 
PyErr_Occurred()17
)
  Branch (677:13): [True: 17, False: 70.3k]
  Branch (677:27): [True: 12, False: 5]
678
            RETURN_ERR_OCCURRED;
679
        else if (ival < 0) {
  Branch (679:18): [True: 5, False: 70.3k]
680
            PyErr_SetString(PyExc_OverflowError,
681
                            "unsigned byte integer is less than minimum");
682
            RETURN_ERR_OCCURRED;
683
        }
684
        else if (ival > UCHAR_MAX) {
  Branch (684:18): [True: 5, False: 70.3k]
685
            PyErr_SetString(PyExc_OverflowError,
686
                            "unsigned byte integer is greater than maximum");
687
            RETURN_ERR_OCCURRED;
688
        }
689
        else
690
            *p = (unsigned char) ival;
691
        break;
692
    }
693
694
    case 'B': {/* byte sized bitfield - both signed and unsigned
  Branch (694:5): [True: 73, False: 22.9M]
695
                  values allowed */
696
        char *p = va_arg(*p_va, char *);
697
        unsigned long ival = PyLong_AsUnsignedLongMask(arg);
698
        if (ival == (unsigned long)-1 && 
PyErr_Occurred()6
)
  Branch (698:13): [True: 6, False: 67]
  Branch (698:42): [True: 5, False: 1]
699
            RETURN_ERR_OCCURRED;
700
        else
701
            *p = (unsigned char) ival;
702
        break;
703
    }
704
705
    case 'h': {/* signed short int */
  Branch (705:5): [True: 42.4k, False: 22.8M]
706
        short *p = va_arg(*p_va, short *);
707
        long ival = PyLong_AsLong(arg);
708
        if (ival == -1 && 
PyErr_Occurred()7.79k
)
  Branch (708:13): [True: 7.79k, False: 34.6k]
  Branch (708:27): [True: 16, False: 7.78k]
709
            RETURN_ERR_OCCURRED;
710
        else if (ival < SHRT_MIN) {
  Branch (710:18): [True: 5, False: 42.4k]
711
            PyErr_SetString(PyExc_OverflowError,
712
                            "signed short integer is less than minimum");
713
            RETURN_ERR_OCCURRED;
714
        }
715
        else if (ival > SHRT_MAX) {
  Branch (715:18): [True: 5, False: 42.4k]
716
            PyErr_SetString(PyExc_OverflowError,
717
                            "signed short integer is greater than maximum");
718
            RETURN_ERR_OCCURRED;
719
        }
720
        else
721
            *p = (short) ival;
722
        break;
723
    }
724
725
    case 'H': { /* short int sized bitfield, both signed and
  Branch (725:5): [True: 19, False: 22.9M]
726
                   unsigned allowed */
727
        unsigned short *p = va_arg(*p_va, unsigned short *);
728
        unsigned long ival = PyLong_AsUnsignedLongMask(arg);
729
        if (ival == (unsigned long)-1 && 
PyErr_Occurred()6
)
  Branch (729:13): [True: 6, False: 13]
  Branch (729:42): [True: 5, False: 1]
730
            RETURN_ERR_OCCURRED;
731
        else
732
            *p = (unsigned short) ival;
733
        break;
734
    }
735
736
    case 'i': {/* signed int */
  Branch (736:5): [True: 1.94M, False: 20.9M]
737
        int *p = va_arg(*p_va, int *);
738
        long ival = PyLong_AsLong(arg);
739
        if (ival == -1 && 
PyErr_Occurred()33.0k
)
  Branch (739:13): [True: 33.0k, False: 1.91M]
  Branch (739:27): [True: 189, False: 32.8k]
740
            RETURN_ERR_OCCURRED;
741
        else if (ival > INT_MAX) {
  Branch (741:18): [True: 26, False: 1.94M]
742
            PyErr_SetString(PyExc_OverflowError,
743
                            "signed integer is greater than maximum");
744
            RETURN_ERR_OCCURRED;
745
        }
746
        else if (ival < INT_MIN) {
  Branch (746:18): [True: 7, False: 1.94M]
747
            PyErr_SetString(PyExc_OverflowError,
748
                            "signed integer is less than minimum");
749
            RETURN_ERR_OCCURRED;
750
        }
751
        else
752
            *p = ival;
753
        break;
754
    }
755
756
    case 'I': { /* int sized bitfield, both signed and
  Branch (756:5): [True: 522, False: 22.9M]
757
                   unsigned allowed */
758
        unsigned int *p = va_arg(*p_va, unsigned int *);
759
        unsigned long ival = PyLong_AsUnsignedLongMask(arg);
760
        if (ival == (unsigned long)-1 && 
PyErr_Occurred()6
)
  Branch (760:13): [True: 6, False: 516]
  Branch (760:42): [True: 5, False: 1]
761
            RETURN_ERR_OCCURRED;
762
        else
763
            *p = (unsigned int) ival;
764
        break;
765
    }
766
767
    case 'n': /* Py_ssize_t */
  Branch (767:5): [True: 228k, False: 22.6M]
768
    {
769
        PyObject *iobj;
770
        Py_ssize_t *p = va_arg(*p_va, Py_ssize_t *);
771
        Py_ssize_t ival = -1;
772
        iobj = _PyNumber_Index(arg);
773
        if (iobj != NULL) {
  Branch (773:13): [True: 228k, False: 121]
774
            ival = PyLong_AsSsize_t(iobj);
775
            Py_DECREF(iobj);
776
        }
777
        if (ival == -1 && 
PyErr_Occurred()275
)
  Branch (777:13): [True: 275, False: 228k]
  Branch (777:27): [True: 125, False: 150]
778
            RETURN_ERR_OCCURRED;
779
        *p = ival;
780
        break;
781
    }
782
    case 'l': {/* long int */
  Branch (782:5): [True: 21.2k, False: 22.9M]
783
        long *p = va_arg(*p_va, long *);
784
        long ival = PyLong_AsLong(arg);
785
        if (ival == -1 && 
PyErr_Occurred()3.91k
)
  Branch (785:13): [True: 3.91k, False: 17.3k]
  Branch (785:27): [True: 23, False: 3.89k]
786
            RETURN_ERR_OCCURRED;
787
        else
788
            *p = ival;
789
        break;
790
    }
791
792
    case 'k': { /* long sized bitfield */
  Branch (792:5): [True: 663, False: 22.9M]
793
        unsigned long *p = va_arg(*p_va, unsigned long *);
794
        unsigned long ival;
795
        if (PyLong_Check(arg))
796
            ival = PyLong_AsUnsignedLongMask(arg);
797
        else
798
            return converterr("int", arg, msgbuf, bufsize);
799
        *p = ival;
800
        break;
801
    }
802
803
    case 'L': {/* long long */
  Branch (803:5): [True: 27.8k, False: 22.8M]
804
        long long *p = va_arg( *p_va, long long * );
805
        long long ival = PyLong_AsLongLong(arg);
806
        if (ival == (long long)-1 && 
PyErr_Occurred()3.91k
)
  Branch (806:13): [True: 3.91k, False: 23.8k]
  Branch (806:38): [True: 22, False: 3.89k]
807
            RETURN_ERR_OCCURRED;
808
        else
809
            *p = ival;
810
        break;
811
    }
812
813
    case 'K': { /* long long sized bitfield */
  Branch (813:5): [True: 37.1k, False: 22.8M]
814
        unsigned long long *p = va_arg(*p_va, unsigned long long *);
815
        unsigned long long ival;
816
        if (PyLong_Check(arg))
817
            ival = PyLong_AsUnsignedLongLongMask(arg);
818
        else
819
            return converterr("int", arg, msgbuf, bufsize);
820
        *p = ival;
821
        break;
822
    }
823
824
    case 'f': {/* float */
  Branch (824:5): [True: 21.0k, False: 22.9M]
825
        float *p = va_arg(*p_va, float *);
826
        double dval = PyFloat_AsDouble(arg);
827
        if (dval == -1.0 && 
PyErr_Occurred()6
)
  Branch (827:13): [True: 6, False: 21.0k]
  Branch (827:29): [True: 6, False: 0]
828
            RETURN_ERR_OCCURRED;
829
        else
830
            *p = (float) dval;
831
        break;
832
    }
833
834
    case 'd': {/* double */
  Branch (834:5): [True: 86.6k, False: 22.8M]
835
        double *p = va_arg(*p_va, double *);
836
        double dval = PyFloat_AsDouble(arg);
837
        if (dval == -1.0 && 
PyErr_Occurred()65.5k
)
  Branch (837:13): [True: 65.5k, False: 21.0k]
  Branch (837:29): [True: 8, False: 65.5k]
838
            RETURN_ERR_OCCURRED;
839
        else
840
            *p = dval;
841
        break;
842
    }
843
844
    case 'D': {/* complex double */
  Branch (844:5): [True: 28, False: 22.9M]
845
        Py_complex *p = va_arg(*p_va, Py_complex *);
846
        Py_complex cval;
847
        cval = PyComplex_AsCComplex(arg);
848
        if (PyErr_Occurred())
  Branch (848:13): [True: 2, False: 26]
849
            RETURN_ERR_OCCURRED;
850
        else
851
            *p = cval;
852
        break;
853
    }
854
855
    case 'c': {/* char */
  Branch (855:5): [True: 8, False: 22.9M]
856
        char *p = va_arg(*p_va, char *);
857
        if (PyBytes_Check(arg) && 
PyBytes_Size(arg) == 12
)
  Branch (857:35): [True: 1, False: 1]
858
            *p = PyBytes_AS_STRING(arg)[0];
859
        else if (PyByteArray_Check(arg) && 
PyByteArray_Size(arg) == 11
)
  Branch (859:44): [True: 1, False: 0]
860
            *p = PyByteArray_AS_STRING(arg)[0];
861
        else
862
            return converterr("a byte string of length 1", arg, msgbuf, bufsize);
863
        break;
864
    }
865
866
    case 'C': {/* unicode char */
  Branch (866:5): [True: 71.7k, False: 22.8M]
867
        int *p = va_arg(*p_va, int *);
868
        int kind;
869
        const void *data;
870
871
        if (!PyUnicode_Check(arg))
  Branch (871:13): [True: 6, False: 71.7k]
872
            return converterr("a unicode character", arg, msgbuf, bufsize);
873
874
        if (PyUnicode_READY(arg))
875
            RETURN_ERR_OCCURRED;
876
877
        if (PyUnicode_GET_LENGTH(arg) != 1)
  Branch (877:13): [True: 2, False: 71.7k]
878
            return converterr("a unicode character", arg, msgbuf, bufsize);
879
880
        kind = PyUnicode_KIND(arg);
881
        data = PyUnicode_DATA(arg);
882
        *p = PyUnicode_READ(kind, data, 0);
883
        break;
884
    }
885
886
    case 'p': {/* boolean *p*redicate */
  Branch (886:5): [True: 53.8k, False: 22.8M]
887
        int *p = va_arg(*p_va, int *);
888
        int val = PyObject_IsTrue(arg);
889
        if (val > 0)
  Branch (889:13): [True: 52.3k, False: 1.48k]
890
            *p = 1;
891
        else if (val == 0)
  Branch (891:18): [True: 1.47k, False: 4]
892
            *p = 0;
893
        else
894
            RETURN_ERR_OCCURRED;
895
        break;
896
    }
897
898
    /* XXX WAAAAH!  's', 'y', 'z', 'u', 'Z', 'e', 'w' codes all
899
       need to be cleaned up! */
900
901
    case 'y': {/* any bytes-like object */
  Branch (901:5): [True: 42.2k, False: 22.8M]
902
        void **p = (void **)va_arg(*p_va, char **);
903
        const char *buf;
904
        Py_ssize_t count;
905
        if (*format == '*') {
  Branch (905:13): [True: 42.2k, False: 77]
906
            if (getbuffer(arg, (Py_buffer*)p, &buf) < 0)
  Branch (906:17): [True: 37, False: 42.1k]
907
                return converterr(buf, arg, msgbuf, bufsize);
908
            format++;
909
            if (addcleanup(p, freelist, cleanup_buffer)) {
  Branch (909:17): [True: 0, False: 42.1k]
910
                return converterr(
911
                    "(cleanup problem)",
912
                    arg, msgbuf, bufsize);
913
            }
914
            break;
915
        }
916
        count = convertbuffer(arg, (const void **)p, &buf);
917
        if (count < 0)
  Branch (917:13): [True: 9, False: 68]
918
            return converterr(buf, arg, msgbuf, bufsize);
919
        if (*format == '#') {
  Branch (919:13): [True: 48, False: 20]
920
            REQUIRE_PY_SSIZE_T_CLEAN;
921
            Py_ssize_t *psize = va_arg(*p_va, Py_ssize_t*);
922
            *psize = count;
923
            format++;
924
        } else {
925
            if (strlen(*p) != (size_t)count) {
  Branch (925:17): [True: 1, False: 19]
926
                PyErr_SetString(PyExc_ValueError, "embedded null byte");
927
                RETURN_ERR_OCCURRED;
928
            }
929
        }
930
        break;
931
    }
932
933
    case 's': /* text string or bytes-like object */
  Branch (933:5): [True: 63.8k, False: 22.8M]
934
    case 'z': /* text string, bytes-like object or None */
  Branch (934:5): [True: 20, False: 22.9M]
935
    {
936
        if (*format == '*') {
  Branch (936:13): [True: 22, False: 63.8k]
937
            /* "s*" or "z*" */
938
            Py_buffer *p = (Py_buffer *)va_arg(*p_va, Py_buffer *);
939
940
            if (c == 'z' && 
arg == 6
Py_None6
)
  Branch (940:17): [True: 6, False: 16]
  Branch (940:29): [True: 1, False: 5]
941
                PyBuffer_FillInfo(p, NULL, NULL, 0, 1, 0);
942
            else if (PyUnicode_Check(arg)) {
943
                Py_ssize_t len;
944
                sarg = PyUnicode_AsUTF8AndSize(arg, &len);
945
                if (sarg == NULL)
  Branch (945:21): [True: 0, False: 6]
946
                    return converterr(CONV_UNICODE,
947
                                      arg, msgbuf, bufsize);
948
                PyBuffer_FillInfo(p, arg, (void *)sarg, len, 1, 0);
949
            }
950
            else { /* any bytes-like object */
951
                const char *buf;
952
                if (getbuffer(arg, p, &buf) < 0)
  Branch (952:21): [True: 1, False: 14]
953
                    return converterr(buf, arg, msgbuf, bufsize);
954
            }
955
            if (addcleanup(p, freelist, cleanup_buffer)) {
  Branch (955:17): [True: 0, False: 21]
956
                return converterr(
957
                    "(cleanup problem)",
958
                    arg, msgbuf, bufsize);
959
            }
960
            format++;
961
        } else if (*format == '#') { /* a string or read-only bytes-like object */
  Branch (961:20): [True: 57.2k, False: 6.67k]
962
            /* "s#" or "z#" */
963
            const void **p = (const void **)va_arg(*p_va, const char **);
964
            REQUIRE_PY_SSIZE_T_CLEAN;
965
            Py_ssize_t *psize = va_arg(*p_va, Py_ssize_t*);
966
967
            if (c == 'z' && 
arg == 6
Py_None6
) {
  Branch (967:17): [True: 6, False: 57.2k]
  Branch (967:29): [True: 1, False: 5]
968
                *p = NULL;
969
                *psize = 0;
970
            }
971
            else if (PyUnicode_Check(arg)) {
972
                Py_ssize_t len;
973
                sarg = PyUnicode_AsUTF8AndSize(arg, &len);
974
                if (sarg == NULL)
  Branch (974:21): [True: 0, False: 55.7k]
975
                    return converterr(CONV_UNICODE,
976
                                      arg, msgbuf, bufsize);
977
                *p = sarg;
978
                *psize = len;
979
            }
980
            else { /* read-only bytes-like object */
981
                /* XXX Really? */
982
                const char *buf;
983
                Py_ssize_t count = convertbuffer(arg, p, &buf);
984
                if (count < 0)
  Branch (984:21): [True: 34, False: 1.45k]
985
                    return converterr(buf, arg, msgbuf, bufsize);
986
                *psize = count;
987
            }
988
            format++;
989
        } else {
990
            /* "s" or "z" */
991
            const char **p = va_arg(*p_va, const char **);
992
            Py_ssize_t len;
993
            sarg = NULL;
994
995
            if (c == 'z' && 
arg == 8
Py_None8
)
  Branch (995:17): [True: 8, False: 6.66k]
  Branch (995:29): [True: 1, False: 7]
996
                *p = NULL;
997
            else if (PyUnicode_Check(arg)) {
998
                sarg = PyUnicode_AsUTF8AndSize(arg, &len);
999
                if (sarg == NULL)
  Branch (999:21): [True: 8, False: 6.65k]
1000
                    return converterr(CONV_UNICODE,
1001
                                      arg, msgbuf, bufsize);
1002
                if (strlen(sarg) != (size_t)len) {
  Branch (1002:21): [True: 5, False: 6.64k]
1003
                    PyErr_SetString(PyExc_ValueError, "embedded null character");
1004
                    RETURN_ERR_OCCURRED;
1005
                }
1006
                *p = sarg;
1007
            }
1008
            else
1009
                return converterr(c == 'z' ? 
"str or None"4
:
"str"12
,
  Branch (1009:35): [True: 4, False: 12]
1010
                                  arg, msgbuf, bufsize);
1011
        }
1012
        break;
1013
    }
1014
1015
    case 'e': {/* encoded string */
  Branch (1015:5): [True: 617, False: 22.9M]
1016
        char **buffer;
1017
        const char *encoding;
1018
        PyObject *s;
1019
        int recode_strings;
1020
        Py_ssize_t size;
1021
        const char *ptr;
1022
1023
        /* Get 'e' parameter: the encoding name */
1024
        encoding = (const char *)va_arg(*p_va, const char *);
1025
        if (encoding == NULL)
  Branch (1025:13): [True: 4, False: 613]
1026
            encoding = PyUnicode_GetDefaultEncoding();
1027
1028
        /* Get output buffer parameter:
1029
           's' (recode all objects via Unicode) or
1030
           't' (only recode non-string objects)
1031
        */
1032
        if (*format == 's')
  Branch (1032:13): [True: 402, False: 215]
1033
            recode_strings = 1;
1034
        else if (*format == 't')
  Branch (1034:18): [True: 215, False: 0]
1035
            recode_strings = 0;
1036
        else
1037
            return converterr(
1038
                "(unknown parser marker combination)",
1039
                arg, msgbuf, bufsize);
1040
        buffer = (char **)va_arg(*p_va, char **);
1041
        format++;
1042
        if (buffer == NULL)
  Branch (1042:13): [True: 0, False: 617]
1043
            return converterr("(buffer is NULL)",
1044
                              arg, msgbuf, bufsize);
1045
1046
        /* Encode object */
1047
        if (!recode_strings &&
  Branch (1047:13): [True: 215, False: 402]
1048
            
(215
PyBytes_Check215
(arg) ||
PyByteArray_Check215
(arg))) {
1049
            s = arg;
1050
            Py_INCREF(s);
1051
            if (PyBytes_Check(arg)) {
1052
                size = PyBytes_GET_SIZE(s);
1053
                ptr = PyBytes_AS_STRING(s);
1054
            }
1055
            else {
1056
                size = PyByteArray_GET_SIZE(s);
1057
                ptr = PyByteArray_AS_STRING(s);
1058
            }
1059
        }
1060
        else if (PyUnicode_Check(arg)) {
1061
            /* Encode object; use default error handling */
1062
            s = PyUnicode_AsEncodedString(arg,
1063
                                          encoding,
1064
                                          NULL);
1065
            if (s == NULL)
  Branch (1065:17): [True: 8, False: 583]
1066
                return converterr("(encoding failed)",
1067
                                  arg, msgbuf, bufsize);
1068
            assert(PyBytes_Check(s));
1069
            size = PyBytes_GET_SIZE(s);
1070
            ptr = PyBytes_AS_STRING(s);
1071
            if (ptr == NULL)
  Branch (1071:17): [True: 0, False: 583]
1072
                ptr = "";
1073
        }
1074
        else {
1075
            return converterr(
1076
                recode_strings ? 
"str"8
:
"str, bytes or bytearray"5
,
  Branch (1076:17): [True: 8, False: 5]
1077
                arg, msgbuf, bufsize);
1078
        }
1079
1080
        /* Write output; output is guaranteed to be 0-terminated */
1081
        if (*format == '#') {
  Branch (1081:13): [True: 18, False: 578]
1082
            /* Using buffer length parameter '#':
1083
1084
               - if *buffer is NULL, a new buffer of the
1085
               needed size is allocated and the data
1086
               copied into it; *buffer is updated to point
1087
               to the new buffer; the caller is
1088
               responsible for PyMem_Free()ing it after
1089
               usage
1090
1091
               - if *buffer is not NULL, the data is
1092
               copied to *buffer; *buffer_len has to be
1093
               set to the size of the buffer on input;
1094
               buffer overflow is signalled with an error;
1095
               buffer has to provide enough room for the
1096
               encoded string plus the trailing 0-byte
1097
1098
               - in both cases, *buffer_len is updated to
1099
               the size of the buffer /excluding/ the
1100
               trailing 0-byte
1101
1102
            */
1103
            REQUIRE_PY_SSIZE_T_CLEAN;
1104
            Py_ssize_t *psize = va_arg(*p_va, Py_ssize_t*);
1105
1106
            format++;
1107
            if (psize == NULL) {
  Branch (1107:17): [True: 0, False: 18]
1108
                Py_DECREF(s);
1109
                return converterr(
1110
                    "(buffer_len is NULL)",
1111
                    arg, msgbuf, bufsize);
1112
            }
1113
            if (*buffer == NULL) {
  Branch (1113:17): [True: 10, False: 8]
1114
                *buffer = PyMem_NEW(char, size + 1);
1115
                if (*buffer == NULL) {
  Branch (1115:21): [True: 0, False: 10]
1116
                    Py_DECREF(s);
1117
                    PyErr_NoMemory();
1118
                    RETURN_ERR_OCCURRED;
1119
                }
1120
                if (addcleanup(*buffer, freelist, cleanup_ptr)) {
  Branch (1120:21): [True: 0, False: 10]
1121
                    Py_DECREF(s);
1122
                    return converterr(
1123
                        "(cleanup problem)",
1124
                        arg, msgbuf, bufsize);
1125
                }
1126
            } else {
1127
                if (size + 1 > *psize) {
  Branch (1127:21): [True: 4, False: 4]
1128
                    Py_DECREF(s);
1129
                    PyErr_Format(PyExc_ValueError,
1130
                                 "encoded string too long "
1131
                                 "(%zd, maximum length %zd)",
1132
                                 (Py_ssize_t)size, (Py_ssize_t)(*psize - 1));
1133
                    RETURN_ERR_OCCURRED;
1134
                }
1135
            }
1136
            memcpy(*buffer, ptr, size+1);
1137
1138
            *psize = size;
1139
        }
1140
        else {
1141
            /* Using a 0-terminated buffer:
1142
1143
               - the encoded string has to be 0-terminated
1144
               for this variant to work; if it is not, an
1145
               error raised
1146
1147
               - a new buffer of the needed size is
1148
               allocated and the data copied into it;
1149
               *buffer is updated to point to the new
1150
               buffer; the caller is responsible for
1151
               PyMem_Free()ing it after usage
1152
1153
            */
1154
            if ((Py_ssize_t)strlen(ptr) != size) {
  Branch (1154:17): [True: 5, False: 573]
1155
                Py_DECREF(s);
1156
                return converterr(
1157
                    "encoded string without null bytes",
1158
                    arg, msgbuf, bufsize);
1159
            }
1160
            *buffer = PyMem_NEW(char, size + 1);
1161
            if (*buffer == NULL) {
  Branch (1161:17): [True: 0, False: 573]
1162
                Py_DECREF(s);
1163
                PyErr_NoMemory();
1164
                RETURN_ERR_OCCURRED;
1165
            }
1166
            if (addcleanup(*buffer, freelist, cleanup_ptr)) {
  Branch (1166:17): [True: 0, False: 573]
1167
                Py_DECREF(s);
1168
                return converterr("(cleanup problem)",
1169
                                arg, msgbuf, bufsize);
1170
            }
1171
            memcpy(*buffer, ptr, size+1);
1172
        }
1173
        Py_DECREF(s);
1174
        break;
1175
    }
1176
1177
    case 'S': { /* PyBytes object */
  Branch (1177:5): [True: 312, False: 22.9M]
1178
        PyObject **p = va_arg(*p_va, PyObject **);
1179
        if (PyBytes_Check(arg))
1180
            *p = arg;
1181
        else
1182
            return converterr("bytes", arg, msgbuf, bufsize);
1183
        break;
1184
    }
1185
1186
    case 'Y': { /* PyByteArray object */
  Branch (1186:5): [True: 14, False: 22.9M]
1187
        PyObject **p = va_arg(*p_va, PyObject **);
1188
        if (PyByteArray_Check(arg))
1189
            *p = arg;
1190
        else
1191
            return converterr("bytearray", arg, msgbuf, bufsize);
1192
        break;
1193
    }
1194
1195
    case 'U': { /* PyUnicode object */
  Branch (1195:5): [True: 145k, False: 22.7M]
1196
        PyObject **p = va_arg(*p_va, PyObject **);
1197
        if (PyUnicode_Check(arg)) {
1198
            if (PyUnicode_READY(arg) == -1)
  Branch (1198:17): [True: 0, False: 145k]
1199
                RETURN_ERR_OCCURRED;
1200
            *p = arg;
1201
        }
1202
        else
1203
            return converterr("str", arg, msgbuf, bufsize);
1204
        break;
1205
    }
1206
1207
    case 'O': { /* object */
  Branch (1207:5): [True: 17.9M, False: 5.00M]
1208
        PyTypeObject *type;
1209
        PyObject **p;
1210
        if (*format == '!') {
  Branch (1210:13): [True: 381k, False: 17.5M]
1211
            type = va_arg(*p_va, PyTypeObject*);
1212
            p = va_arg(*p_va, PyObject **);
1213
            format++;
1214
            if (PyType_IsSubtype(Py_TYPE(arg), type))
  Branch (1214:17): [True: 381k, False: 17]
1215
                *p = arg;
1216
            else
1217
                return converterr(type->tp_name, arg, msgbuf, bufsize);
1218
1219
        }
1220
        else if (*format == '&') {
  Branch (1220:18): [True: 145k, False: 17.3M]
1221
            typedef int (*converter)(PyObject *, void *);
1222
            converter convert = va_arg(*p_va, converter);
1223
            void *addr = va_arg(*p_va, void *);
1224
            int res;
1225
            format++;
1226
            if (! (res = (*convert)(arg, addr)))
  Branch (1226:17): [True: 19, False: 145k]
1227
                return converterr("(unspecified)",
1228
                                  arg, msgbuf, bufsize);
1229
            if (res == Py_CLEANUP_SUPPORTED &&
  Branch (1229:17): [True: 7.24k, False: 138k]
1230
                
addcleanup(addr, freelist, convert) == -17.24k
)
  Branch (1230:17): [True: 0, False: 7.24k]
1231
                return converterr("(cleanup problem)",
1232
                                arg, msgbuf, bufsize);
1233
        }
1234
        else {
1235
            p = va_arg(*p_va, PyObject **);
1236
            *p = arg;
1237
        }
1238
        break;
1239
    }
1240
1241
1242
    case 'w': { /* "w*": memory buffer, read-write access */
  Branch (1242:5): [True: 2.14M, False: 20.7M]
1243
        void **p = va_arg(*p_va, void **);
1244
1245
        if (*format != '*')
  Branch (1245:13): [True: 1, False: 2.14M]
1246
            return converterr(
1247
                "(invalid use of 'w' format character)",
1248
                arg, msgbuf, bufsize);
1249
        format++;
1250
1251
        /* Caller is interested in Py_buffer, and the object
1252
           supports it directly. */
1253
        if (PyObject_GetBuffer(arg, (Py_buffer*)p, PyBUF_WRITABLE) < 0) {
  Branch (1253:13): [True: 43, False: 2.14M]
1254
            PyErr_Clear();
1255
            return converterr("read-write bytes-like object",
1256
                              arg, msgbuf, bufsize);
1257
        }
1258
        if (!PyBuffer_IsContiguous((Py_buffer*)p, 'C')) {
  Branch (1258:13): [True: 0, False: 2.14M]
1259
            PyBuffer_Release((Py_buffer*)p);
1260
            return converterr("contiguous buffer", arg, msgbuf, bufsize);
1261
        }
1262
        if (addcleanup(p, freelist, cleanup_buffer)) {
  Branch (1262:13): [True: 0, False: 2.14M]
1263
            return converterr(
1264
                "(cleanup problem)",
1265
                arg, msgbuf, bufsize);
1266
        }
1267
        break;
1268
    }
1269
1270
    default:
  Branch (1270:5): [True: 108, False: 22.9M]
1271
        return converterr("(impossible<bad format char>)", arg, msgbuf, bufsize);
1272
1273
    }
1274
1275
    *p_format = format;
1276
    return NULL;
1277
1278
#undef REQUIRE_PY_SSIZE_T_CLEAN
1279
#undef RETURN_ERR_OCCURRED
1280
}
1281
1282
static Py_ssize_t
1283
convertbuffer(PyObject *arg, const void **p, const char **errmsg)
1284
{
1285
    PyBufferProcs *pb = Py_TYPE(arg)->tp_as_buffer;
1286
    Py_ssize_t count;
1287
    Py_buffer view;
1288
1289
    *errmsg = NULL;
1290
    *p = NULL;
1291
    if (pb != NULL && 
pb->bf_releasebuffer != NULL1.52k
) {
  Branch (1291:9): [True: 1.52k, False: 35]
  Branch (1291:23): [True: 8, False: 1.52k]
1292
        *errmsg = "read-only bytes-like object";
1293
        return -1;
1294
    }
1295
1296
    if (getbuffer(arg, &view, errmsg) < 0)
  Branch (1296:9): [True: 35, False: 1.52k]
1297
        return -1;
1298
    count = view.len;
1299
    *p = view.buf;
1300
    PyBuffer_Release(&view);
1301
    return count;
1302
}
1303
1304
static int
1305
getbuffer(PyObject *arg, Py_buffer *view, const char **errmsg)
1306
{
1307
    if (PyObject_GetBuffer(arg, view, PyBUF_SIMPLE) != 0) {
  Branch (1307:9): [True: 73, False: 43.7k]
1308
        *errmsg = "bytes-like object";
1309
        return -1;
1310
    }
1311
    if (!PyBuffer_IsContiguous(view, 'C')) {
  Branch (1311:9): [True: 0, False: 43.7k]
1312
        PyBuffer_Release(view);
1313
        *errmsg = "contiguous buffer";
1314
        return -1;
1315
    }
1316
    return 0;
1317
}
1318
1319
/* Support for keyword arguments donated by
1320
   Geoff Philbrick <philbric@delphi.hks.com> */
1321
1322
/* Return false (0) for error, else true. */
1323
int
1324
PyArg_ParseTupleAndKeywords(PyObject *args,
1325
                            PyObject *keywords,
1326
                            const char *format,
1327
                            char **kwlist, ...)
1328
{
1329
    int retval;
1330
    va_list va;
1331
1332
    if ((args == NULL || !PyTuple_Check(args)) ||
  Branch (1332:10): [True: 0, False: 7.34M]
  Branch (1332:26): [True: 0, False: 7.34M]
1333
        (keywords != NULL && 
!90.9k
PyDict_Check90.9k
(keywords)) ||
  Branch (1333:10): [True: 90.9k, False: 7.25M]
  Branch (1333:30): [True: 0, False: 90.9k]
1334
        format == NULL ||
  Branch (1334:9): [True: 0, False: 7.34M]
1335
        kwlist == NULL)
  Branch (1335:9): [True: 0, False: 7.34M]
1336
    {
1337
        PyErr_BadInternalCall();
1338
        return 0;
1339
    }
1340
1341
    va_start(va, kwlist);
1342
    retval = vgetargskeywords(args, keywords, format, kwlist, &va, 0);
1343
    va_end(va);
1344
    return retval;
1345
}
1346
1347
PyAPI_FUNC(int)
1348
_PyArg_ParseTupleAndKeywords_SizeT(PyObject *args,
1349
                                  PyObject *keywords,
1350
                                  const char *format,
1351
                                  char **kwlist, ...)
1352
{
1353
    int retval;
1354
    va_list va;
1355
1356
    if ((args == NULL || !PyTuple_Check(args)) ||
  Branch (1356:10): [True: 0, False: 753k]
  Branch (1356:26): [True: 0, False: 753k]
1357
        (keywords != NULL && 
!199k
PyDict_Check199k
(keywords)) ||
  Branch (1357:10): [True: 199k, False: 553k]
  Branch (1357:30): [True: 0, False: 199k]
1358
        format == NULL ||
  Branch (1358:9): [True: 0, False: 753k]
1359
        kwlist == NULL)
  Branch (1359:9): [True: 0, False: 753k]
1360
    {
1361
        PyErr_BadInternalCall();
1362
        return 0;
1363
    }
1364
1365
    va_start(va, kwlist);
1366
    retval = vgetargskeywords(args, keywords, format,
1367
                              kwlist, &va, FLAG_SIZE_T);
1368
    va_end(va);
1369
    return retval;
1370
}
1371
1372
1373
int
1374
PyArg_VaParseTupleAndKeywords(PyObject *args,
1375
                              PyObject *keywords,
1376
                              const char *format,
1377
                              char **kwlist, va_list va)
1378
{
1379
    int retval;
1380
    va_list lva;
1381
1382
    if ((args == NULL || !PyTuple_Check(args)) ||
  Branch (1382:10): [True: 0, False: 0]
  Branch (1382:26): [True: 0, False: 0]
1383
        (keywords != NULL && !PyDict_Check(keywords)) ||
  Branch (1383:10): [True: 0, False: 0]
  Branch (1383:30): [True: 0, False: 0]
1384
        format == NULL ||
  Branch (1384:9): [True: 0, False: 0]
1385
        kwlist == NULL)
  Branch (1385:9): [True: 0, False: 0]
1386
    {
1387
        PyErr_BadInternalCall();
1388
        return 0;
1389
    }
1390
1391
    va_copy(lva, va);
1392
1393
    retval = vgetargskeywords(args, keywords, format, kwlist, &lva, 0);
1394
    va_end(lva);
1395
    return retval;
1396
}
1397
1398
PyAPI_FUNC(int)
1399
_PyArg_VaParseTupleAndKeywords_SizeT(PyObject *args,
1400
                                    PyObject *keywords,
1401
                                    const char *format,
1402
                                    char **kwlist, va_list va)
1403
{
1404
    int retval;
1405
    va_list lva;
1406
1407
    if ((args == NULL || !PyTuple_Check(args)) ||
  Branch (1407:10): [True: 0, False: 0]
  Branch (1407:26): [True: 0, False: 0]
1408
        (keywords != NULL && !PyDict_Check(keywords)) ||
  Branch (1408:10): [True: 0, False: 0]
  Branch (1408:30): [True: 0, False: 0]
1409
        format == NULL ||
  Branch (1409:9): [True: 0, False: 0]
1410
        kwlist == NULL)
  Branch (1410:9): [True: 0, False: 0]
1411
    {
1412
        PyErr_BadInternalCall();
1413
        return 0;
1414
    }
1415
1416
    va_copy(lva, va);
1417
1418
    retval = vgetargskeywords(args, keywords, format,
1419
                              kwlist, &lva, FLAG_SIZE_T);
1420
    va_end(lva);
1421
    return retval;
1422
}
1423
1424
PyAPI_FUNC(int)
1425
_PyArg_ParseTupleAndKeywordsFast(PyObject *args, PyObject *keywords,
1426
                            struct _PyArg_Parser *parser, ...)
1427
{
1428
    int retval;
1429
    va_list va;
1430
1431
    va_start(va, parser);
1432
    retval = vgetargskeywordsfast(args, keywords, parser, &va, 0);
1433
    va_end(va);
1434
    return retval;
1435
}
1436
1437
PyAPI_FUNC(int)
1438
_PyArg_ParseTupleAndKeywordsFast_SizeT(PyObject *args, PyObject *keywords,
1439
                            struct _PyArg_Parser *parser, ...)
1440
{
1441
    int retval;
1442
    va_list va;
1443
1444
    va_start(va, parser);
1445
    retval = vgetargskeywordsfast(args, keywords, parser, &va, FLAG_SIZE_T);
1446
    va_end(va);
1447
    return retval;
1448
}
1449
1450
PyAPI_FUNC(int)
1451
_PyArg_ParseStackAndKeywords(PyObject *const *args, Py_ssize_t nargs, PyObject *kwnames,
1452
                  struct _PyArg_Parser *parser, ...)
1453
{
1454
    int retval;
1455
    va_list va;
1456
1457
    va_start(va, parser);
1458
    retval = vgetargskeywordsfast_impl(args, nargs, NULL, kwnames, parser, &va, 0);
1459
    va_end(va);
1460
    return retval;
1461
}
1462
1463
PyAPI_FUNC(int)
1464
_PyArg_ParseStackAndKeywords_SizeT(PyObject *const *args, Py_ssize_t nargs, PyObject *kwnames,
1465
                        struct _PyArg_Parser *parser, ...)
1466
{
1467
    int retval;
1468
    va_list va;
1469
1470
    va_start(va, parser);
1471
    retval = vgetargskeywordsfast_impl(args, nargs, NULL, kwnames, parser, &va, FLAG_SIZE_T);
1472
    va_end(va);
1473
    return retval;
1474
}
1475
1476
1477
PyAPI_FUNC(int)
1478
_PyArg_VaParseTupleAndKeywordsFast(PyObject *args, PyObject *keywords,
1479
                            struct _PyArg_Parser *parser, va_list va)
1480
{
1481
    int retval;
1482
    va_list lva;
1483
1484
    va_copy(lva, va);
1485
1486
    retval = vgetargskeywordsfast(args, keywords, parser, &lva, 0);
1487
    va_end(lva);
1488
    return retval;
1489
}
1490
1491
PyAPI_FUNC(int)
1492
_PyArg_VaParseTupleAndKeywordsFast_SizeT(PyObject *args, PyObject *keywords,
1493
                            struct _PyArg_Parser *parser, va_list va)
1494
{
1495
    int retval;
1496
    va_list lva;
1497
1498
    va_copy(lva, va);
1499
1500
    retval = vgetargskeywordsfast(args, keywords, parser, &lva, FLAG_SIZE_T);
1501
    va_end(lva);
1502
    return retval;
1503
}
1504
1505
int
1506
PyArg_ValidateKeywordArguments(PyObject *kwargs)
1507
{
1508
    if (!PyDict_Check(kwargs)) {
  Branch (1508:9): [True: 0, False: 6.17k]
1509
        PyErr_BadInternalCall();
1510
        return 0;
1511
    }
1512
    if (!_PyDict_HasOnlyStringKeys(kwargs)) {
  Branch (1512:9): [True: 3, False: 6.17k]
1513
        PyErr_SetString(PyExc_TypeError,
1514
                        "keywords must be strings");
1515
        return 0;
1516
    }
1517
    return 1;
1518
}
1519
1520
#define IS_END_OF_FORMAT(c) (
c == '\0'11.1M
||
c == ';'11.0M
||
c == ':'11.0M
)
1521
1522
static int
1523
vgetargskeywords(PyObject *args, PyObject *kwargs, const char *format,
1524
                 char **kwlist, va_list *p_va, int flags)
1525
{
1526
    char msgbuf[512];
1527
    int levels[32];
1528
    const char *fname, *msg, *custom_msg;
1529
    int min = INT_MAX;
1530
    int max = INT_MAX;
1531
    int i, pos, len;
1532
    int skip = 0;
1533
    Py_ssize_t nargs, nkwargs;
1534
    PyObject *current_arg;
1535
    freelistentry_t static_entries[STATIC_FREELIST_ENTRIES];
1536
    freelist_t freelist;
1537
1538
    freelist.entries = static_entries;
1539
    freelist.first_available = 0;
1540
    freelist.entries_malloced = 0;
1541
1542
    assert(args != NULL && PyTuple_Check(args));
1543
    assert(kwargs == NULL || PyDict_Check(kwargs));
1544
    assert(format != NULL);
1545
    assert(kwlist != NULL);
1546
    assert(p_va != NULL);
1547
1548
    /* grab the function name or custom error msg first (mutually exclusive) */
1549
    fname = strchr(format, ':');
1550
    if (fname) {
  Branch (1550:9): [True: 7.72M, False: 381k]
1551
        fname++;
1552
        custom_msg = NULL;
1553
    }
1554
    else {
1555
        custom_msg = strchr(format,';');
1556
        if (custom_msg)
  Branch (1556:13): [True: 3, False: 381k]
1557
            custom_msg++;
1558
    }
1559
1560
    /* scan kwlist and count the number of positional-only parameters */
1561
    for (pos = 0; kwlist[pos] && 
!*kwlist[pos]8.10M
;
pos++1.16k
) {
  Branch (1561:19): [True: 8.10M, False: 373]
  Branch (1561:34): [True: 1.16k, False: 8.10M]
1562
    }
1563
    /* scan kwlist and get greatest possible nbr of args */
1564
    for (len = pos; kwlist[len]; 
len++17.7M
) {
  Branch (1564:21): [True: 17.7M, False: 8.10M]
1565
        if (!*kwlist[len]) {
  Branch (1565:13): [True: 2, False: 17.7M]
1566
            PyErr_SetString(PyExc_SystemError,
1567
                            "Empty keyword parameter name");
1568
            return cleanreturn(0, &freelist);
1569
        }
1570
    }
1571
1572
    if (len > STATIC_FREELIST_ENTRIES) {
  Branch (1572:9): [True: 68.9k, False: 8.03M]
1573
        freelist.entries = PyMem_NEW(freelistentry_t, len);
1574
        if (freelist.entries == NULL) {
  Branch (1574:13): [True: 0, False: 68.9k]
1575
            PyErr_NoMemory();
1576
            return 0;
1577
        }
1578
        freelist.entries_malloced = 1;
1579
    }
1580
1581
    nargs = PyTuple_GET_SIZE(args);
1582
    nkwargs = (kwargs == NULL) ? 
07.81M
:
PyDict_GET_SIZE290k
(kwargs);
  Branch (1582:15): [True: 7.81M, False: 290k]
1583
    if (nargs + nkwargs > len) {
  Branch (1583:9): [True: 39, False: 8.10M]
1584
        /* Adding "keyword" (when nargs == 0) prevents producing wrong error
1585
           messages in some special cases (see bpo-31229). */
1586
        PyErr_Format(PyExc_TypeError,
1587
                     "%.200s%s takes at most %d %sargument%s (%zd given)",
1588
                     (fname == NULL) ? 
"function"20
:
fname19
,
  Branch (1588:22): [True: 20, False: 19]
1589
                     (fname == NULL) ? 
""20
:
"()"19
,
  Branch (1589:22): [True: 20, False: 19]
1590
                     len,
1591
                     (nargs == 0) ? 
"keyword "3
:
""36
,
  Branch (1591:22): [True: 3, False: 36]
1592
                     (len == 1) ? 
""25
:
"s"14
,
  Branch (1592:22): [True: 25, False: 14]
1593
                     nargs + nkwargs);
1594
        return cleanreturn(0, &freelist);
1595
    }
1596
1597
    /* convert tuple args and keyword args in same loop, using kwlist to drive process */
1598
    
for (i = 0; 8.10M
i < len;
i++3.08M
) {
  Branch (1598:17): [True: 10.8M, False: 337k]
1599
        if (*format == '|') {
  Branch (1599:13): [True: 7.96M, False: 2.88M]
1600
            if (min != INT_MAX) {
  Branch (1600:17): [True: 1, False: 7.96M]
1601
                PyErr_SetString(PyExc_SystemError,
1602
                                "Invalid format string (| specified twice)");
1603
                return cleanreturn(0, &freelist);
1604
            }
1605
1606
            min = i;
1607
            format++;
1608
1609
            if (max != INT_MAX) {
  Branch (1609:17): [True: 1, False: 7.96M]
1610
                PyErr_SetString(PyExc_SystemError,
1611
                                "Invalid format string ($ before |)");
1612
                return cleanreturn(0, &freelist);
1613
            }
1614
        }
1615
        if (*format == '$') {
  Branch (1615:13): [True: 2.13M, False: 8.71M]
1616
            if (max != INT_MAX) {
  Branch (1616:17): [True: 1, False: 2.13M]
1617
                PyErr_SetString(PyExc_SystemError,
1618
                                "Invalid format string ($ specified twice)");
1619
                return cleanreturn(0, &freelist);
1620
            }
1621
1622
            max = i;
1623
            format++;
1624
1625
            if (max < pos) {
  Branch (1625:17): [True: 2, False: 2.13M]
1626
                PyErr_SetString(PyExc_SystemError,
1627
                                "Empty parameter name after $");
1628
                return cleanreturn(0, &freelist);
1629
            }
1630
            if (skip) {
  Branch (1630:17): [True: 4, False: 2.13M]
1631
                /* Now we know the minimal and the maximal numbers of
1632
                 * positional arguments and can raise an exception with
1633
                 * informative message (see below). */
1634
                break;
1635
            }
1636
            if (max < nargs) {
  Branch (1636:17): [True: 8, False: 2.13M]
1637
                if (max == 0) {
  Branch (1637:21): [True: 1, False: 7]
1638
                    PyErr_Format(PyExc_TypeError,
1639
                                 "%.200s%s takes no positional arguments",
1640
                                 (fname == NULL) ? "function" : 
fname0
,
  Branch (1640:34): [True: 1, False: 0]
1641
                                 (fname == NULL) ? "" : 
"()"0
);
  Branch (1641:34): [True: 1, False: 0]
1642
                }
1643
                else {
1644
                    PyErr_Format(PyExc_TypeError,
1645
                                 "%.200s%s takes %s %d positional argument%s"
1646
                                 " (%zd given)",
1647
                                 (fname == NULL) ? 
"function"5
:
fname2
,
  Branch (1647:34): [True: 5, False: 2]
1648
                                 (fname == NULL) ? 
""5
:
"()"2
,
  Branch (1648:34): [True: 5, False: 2]
1649
                                 (min != INT_MAX) ? "at most" : 
"exactly"0
,
  Branch (1649:34): [True: 7, False: 0]
1650
                                 max,
1651
                                 max == 1 ? 
""1
:
"s"6
,
  Branch (1651:34): [True: 1, False: 6]
1652
                                 nargs);
1653
                }
1654
                return cleanreturn(0, &freelist);
1655
            }
1656
        }
1657
        if (IS_END_OF_FORMAT(*format)) {
1658
            PyErr_Format(PyExc_SystemError,
1659
                         "More keyword list entries (%d) than "
1660
                         "format specifiers (%d)", len, i);
1661
            return cleanreturn(0, &freelist);
1662
        }
1663
        if (!skip) {
  Branch (1663:13): [True: 10.8M, False: 9]
1664
            if (i < nargs) {
  Branch (1664:17): [True: 1.79M, False: 9.04M]
1665
                current_arg = PyTuple_GET_ITEM(args, i);
1666
            }
1667
            else if (nkwargs && 
i >= pos1.28M
) {
  Branch (1667:22): [True: 1.28M, False: 7.76M]
  Branch (1667:33): [True: 1.28M, False: 7]
1668
                current_arg = _PyDict_GetItemStringWithError(kwargs, kwlist[i]);
1669
                if (current_arg) {
  Branch (1669:21): [True: 631k, False: 652k]
1670
                    --nkwargs;
1671
                }
1672
                else if (PyErr_Occurred()) {
  Branch (1672:26): [True: 0, False: 652k]
1673
                    return cleanreturn(0, &freelist);
1674
                }
1675
            }
1676
            else {
1677
                current_arg = NULL;
1678
            }
1679
1680
            if (current_arg) {
  Branch (1680:17): [True: 2.43M, False: 8.41M]
1681
                msg = convertitem(current_arg, &format, p_va, flags,
1682
                    levels, msgbuf, sizeof(msgbuf), &freelist);
1683
                if (msg) {
  Branch (1683:21): [True: 306, False: 2.43M]
1684
                    seterror(i+1, msg, levels, fname, custom_msg);
1685
                    return cleanreturn(0, &freelist);
1686
                }
1687
                continue;
1688
            }
1689
1690
            if (i < min) {
  Branch (1690:17): [True: 49, False: 8.41M]
1691
                if (i < pos) {
  Branch (1691:21): [True: 10, False: 39]
1692
                    assert (min == INT_MAX);
1693
                    assert (max == INT_MAX);
1694
                    skip = 1;
1695
                    /* At that moment we still don't know the minimal and
1696
                     * the maximal numbers of positional arguments.  Raising
1697
                     * an exception is deferred until we encounter | and $
1698
                     * or the end of the format. */
1699
                }
1700
                else {
1701
                    PyErr_Format(PyExc_TypeError,  "%.200s%s missing required "
1702
                                 "argument '%s' (pos %d)",
1703
                                 (fname == NULL) ? 
"function"25
:
fname14
,
  Branch (1703:34): [True: 25, False: 14]
1704
                                 (fname == NULL) ? 
""25
:
"()"14
,
  Branch (1704:34): [True: 25, False: 14]
1705
                                 kwlist[i], i+1);
1706
                    return cleanreturn(0, &freelist);
1707
                }
1708
            }
1709
            /* current code reports success when all required args
1710
             * fulfilled and no keyword args left, with no further
1711
             * validation. XXX Maybe skip this in debug build ?
1712
             */
1713
            if (!nkwargs && 
!skip7.76M
) {
  Branch (1713:17): [True: 7.76M, False: 652k]
  Branch (1713:29): [True: 7.76M, False: 5]
1714
                return cleanreturn(1, &freelist);
1715
            }
1716
        }
1717
1718
        /* We are into optional args, skip through to any remaining
1719
         * keyword args */
1720
        msg = skipitem(&format, p_va, flags);
1721
        if (msg) {
  Branch (1721:13): [True: 211, False: 652k]
1722
            PyErr_Format(PyExc_SystemError, "%s: '%s'", msg,
1723
                         format);
1724
            return cleanreturn(0, &freelist);
1725
        }
1726
    }
1727
1728
    if (skip) {
  Branch (1728:9): [True: 10, False: 337k]
1729
        PyErr_Format(PyExc_TypeError,
1730
                     "%.200s%s takes %s %d positional argument%s"
1731
                     " (%zd given)",
1732
                     (fname == NULL) ? 
"function"7
:
fname3
,
  Branch (1732:22): [True: 7, False: 3]
1733
                     (fname == NULL) ? 
""7
:
"()"3
,
  Branch (1733:22): [True: 7, False: 3]
1734
                     (Py_MIN(pos, min) < i) ? 
"at least"6
:
"exactly"4
,
  Branch (1734:22): [True: 6, False: 4]
1735
                     Py_MIN(pos, min),
1736
                     Py_MIN(pos, min) == 1 ? 
""8
:
"s"2
,
  Branch (1736:22): [True: 8, False: 2]
1737
                     nargs);
1738
        return cleanreturn(0, &freelist);
1739
    }
1740
1741
    if (!IS_END_OF_FORMAT(*format) && 
(*format != '|')2
&&
(*format != '$')1
) {
  Branch (1741:39): [True: 1, False: 1]
  Branch (1741:59): [True: 1, False: 0]
1742
        PyErr_Format(PyExc_SystemError,
1743
            "more argument specifiers than keyword list entries "
1744
            "(remaining format:'%s')", format);
1745
        return cleanreturn(0, &freelist);
1746
    }
1747
1748
    if (nkwargs > 0) {
  Branch (1748:9): [True: 41, False: 337k]
1749
        PyObject *key;
1750
        Py_ssize_t j;
1751
        /* make sure there are no arguments given by name and position */
1752
        for (i = pos; i < nargs; 
i++23
) {
  Branch (1752:23): [True: 24, False: 40]
1753
            current_arg = _PyDict_GetItemStringWithError(kwargs, kwlist[i]);
1754
            if (current_arg) {
  Branch (1754:17): [True: 1, False: 23]
1755
                /* arg present in tuple and in dict */
1756
                PyErr_Format(PyExc_TypeError,
1757
                             "argument for %.200s%s given by name ('%s') "
1758
                             "and position (%d)",
1759
                             (fname == NULL) ? "function" : 
fname0
,
  Branch (1759:30): [True: 1, False: 0]
1760
                             (fname == NULL) ? "" : 
"()"0
,
  Branch (1760:30): [True: 1, False: 0]
1761
                             kwlist[i], i+1);
1762
                return cleanreturn(0, &freelist);
1763
            }
1764
            else if (PyErr_Occurred()) {
  Branch (1764:22): [True: 0, False: 23]
1765
                return cleanreturn(0, &freelist);
1766
            }
1767
        }
1768
        /* make sure there are no extraneous keyword arguments */
1769
        j = 0;
1770
        while (PyDict_Next(kwargs, &j, &key, NULL)) {
  Branch (1770:16): [True: 56, False: 0]
1771
            int match = 0;
1772
            if (!PyUnicode_Check(key)) {
  Branch (1772:17): [True: 0, False: 56]
1773
                PyErr_SetString(PyExc_TypeError,
1774
                                "keywords must be strings");
1775
                return cleanreturn(0, &freelist);
1776
            }
1777
            
for (i = pos; 56
i < len;
i++178
) {
  Branch (1777:27): [True: 194, False: 40]
1778
                if (_PyUnicode_EqualToASCIIString(key, kwlist[i])) {
  Branch (1778:21): [True: 16, False: 178]
1779
                    match = 1;
1780
                    break;
1781
                }
1782
            }
1783
            if (!match) {
  Branch (1783:17): [True: 40, False: 16]
1784
                PyErr_Format(PyExc_TypeError,
1785
                             "'%U' is an invalid keyword "
1786
                             "argument for %.200s%s",
1787
                             key,
1788
                             (fname == NULL) ? 
"this function"25
:
fname15
,
  Branch (1788:30): [True: 25, False: 15]
1789
                             (fname == NULL) ? 
""25
:
"()"15
);
  Branch (1789:30): [True: 25, False: 15]
1790
                return cleanreturn(0, &freelist);
1791
            }
1792
        }
1793
    }
1794
1795
    return cleanreturn(1, &freelist);
1796
}
1797
1798
1799
/* List of static parsers. */
1800
static struct _PyArg_Parser *static_arg_parsers = NULL;
1801
1802
static int
1803
parser_init(struct _PyArg_Parser *parser)
1804
{
1805
    const char * const *keywords;
1806
    const char *format, *msg;
1807
    int i, len, min, max, nkw;
1808
    PyObject *kwtuple;
1809
1810
    assert(parser->keywords != NULL);
1811
    if (parser->kwtuple != NULL) {
  Branch (1811:9): [True: 1.34M, False: 447]
1812
        return 1;
1813
    }
1814
1815
    keywords = parser->keywords;
1816
    /* scan keywords and count the number of positional-only parameters */
1817
    for (i = 0; keywords[i] && 
!*keywords[i]480
;
i++40
) {
  Branch (1817:17): [True: 480, False: 7]
  Branch (1817:32): [True: 40, False: 440]
1818
    }
1819
    parser->pos = i;
1820
    /* scan keywords and get greatest possible nbr of args */
1821
    for (; keywords[i]; 
i++1.53k
) {
  Branch (1821:12): [True: 1.53k, False: 447]
1822
        if (!*keywords[i]) {
  Branch (1822:13): [True: 0, False: 1.53k]
1823
            PyErr_SetString(PyExc_SystemError,
1824
                            "Empty keyword parameter name");
1825
            return 0;
1826
        }
1827
    }
1828
    len = i;
1829
1830
    format = parser->format;
1831
    if (format) {
  Branch (1831:9): [True: 6, False: 441]
1832
        /* grab the function name or custom error msg first (mutually exclusive) */
1833
        parser->fname = strchr(parser->format, ':');
1834
        if (parser->fname) {
  Branch (1834:13): [True: 6, False: 0]
1835
            parser->fname++;
1836
            parser->custom_msg = NULL;
1837
        }
1838
        else {
1839
            parser->custom_msg = strchr(parser->format,';');
1840
            if (parser->custom_msg)
  Branch (1840:17): [True: 0, False: 0]
1841
                parser->custom_msg++;
1842
        }
1843
1844
        min = max = INT_MAX;
1845
        for (i = 0; i < len; 
i++10
) {
  Branch (1845:21): [True: 10, False: 6]
1846
            if (*format == '|') {
  Branch (1846:17): [True: 3, False: 7]
1847
                if (min != INT_MAX) {
  Branch (1847:21): [True: 0, False: 3]
1848
                    PyErr_SetString(PyExc_SystemError,
1849
                                    "Invalid format string (| specified twice)");
1850
                    return 0;
1851
                }
1852
                if (max != INT_MAX) {
  Branch (1852:21): [True: 0, False: 3]
1853
                    PyErr_SetString(PyExc_SystemError,
1854
                                    "Invalid format string ($ before |)");
1855
                    return 0;
1856
                }
1857
                min = i;
1858
                format++;
1859
            }
1860
            if (*format == '$') {
  Branch (1860:17): [True: 0, False: 10]
1861
                if (max != INT_MAX) {
  Branch (1861:21): [True: 0, False: 0]
1862
                    PyErr_SetString(PyExc_SystemError,
1863
                                    "Invalid format string ($ specified twice)");
1864
                    return 0;
1865
                }
1866
                if (i < parser->pos) {
  Branch (1866:21): [True: 0, False: 0]
1867
                    PyErr_SetString(PyExc_SystemError,
1868
                                    "Empty parameter name after $");
1869
                    return 0;
1870
                }
1871
                max = i;
1872
                format++;
1873
            }
1874
            if (IS_END_OF_FORMAT(*format)) {
1875
                PyErr_Format(PyExc_SystemError,
1876
                            "More keyword list entries (%d) than "
1877
                            "format specifiers (%d)", len, i);
1878
                return 0;
1879
            }
1880
1881
            msg = skipitem(&format, NULL, 0);
1882
            if (msg) {
  Branch (1882:17): [True: 0, False: 10]
1883
                PyErr_Format(PyExc_SystemError, "%s: '%s'", msg,
1884
                            format);
1885
                return 0;
1886
            }
1887
        }
1888
        parser->min = Py_MIN(min, len);
1889
        parser->max = Py_MIN(max, len);
1890
1891
        if (!IS_END_OF_FORMAT(*format) && 
(*format != '|')0
&&
(*format != '$')0
) {
  Branch (1891:43): [True: 0, False: 0]
  Branch (1891:63): [True: 0, False: 0]
1892
            PyErr_Format(PyExc_SystemError,
1893
                "more argument specifiers than keyword list entries "
1894
                "(remaining format:'%s')", format);
1895
            return 0;
1896
        }
1897
    }
1898
1899
    nkw = len - parser->pos;
1900
    kwtuple = PyTuple_New(nkw);
1901
    if (kwtuple == NULL) {
  Branch (1901:9): [True: 0, False: 447]
1902
        return 0;
1903
    }
1904
    keywords = parser->keywords + parser->pos;
1905
    for (i = 0; i < nkw; 
i++1.53k
) {
  Branch (1905:17): [True: 1.53k, False: 447]
1906
        PyObject *str = PyUnicode_FromString(keywords[i]);
1907
        if (str == NULL) {
  Branch (1907:13): [True: 0, False: 1.53k]
1908
            Py_DECREF(kwtuple);
1909
            return 0;
1910
        }
1911
        PyUnicode_InternInPlace(&str);
1912
        PyTuple_SET_ITEM(kwtuple, i, str);
1913
    }
1914
    parser->kwtuple = kwtuple;
1915
1916
    assert(parser->next == NULL);
1917
    parser->next = static_arg_parsers;
1918
    static_arg_parsers = parser;
1919
    return 1;
1920
}
1921
1922
static void
1923
parser_clear(struct _PyArg_Parser *parser)
1924
{
1925
    Py_CLEAR(parser->kwtuple);
1926
}
1927
1928
static PyObject*
1929
find_keyword(PyObject *kwnames, PyObject *const *kwstack, PyObject *key)
1930
{
1931
    Py_ssize_t i, nkwargs;
1932
1933
    nkwargs = PyTuple_GET_SIZE(kwnames);
1934
    for (i = 0; i < nkwargs; 
i++330k
) {
  Branch (1934:17): [True: 1.63M, False: 236k]
1935
        PyObject *kwname = PyTuple_GET_ITEM(kwnames, i);
1936
1937
        /* kwname == key will normally find a match in since keyword keys
1938
           should be interned strings; if not retry below in a new loop. */
1939
        if (kwname == key) {
  Branch (1939:13): [True: 1.30M, False: 330k]
1940
            return kwstack[i];
1941
        }
1942
    }
1943
1944
    
for (i = 0; 236k
i < nkwargs;
i++276k
) {
  Branch (1944:17): [True: 277k, False: 236k]
1945
        PyObject *kwname = PyTuple_GET_ITEM(kwnames, i);
1946
        assert(PyUnicode_Check(kwname));
1947
        if (_PyUnicode_EQ(kwname, key)) {
  Branch (1947:13): [True: 255, False: 276k]
1948
            return kwstack[i];
1949
        }
1950
    }
1951
    return NULL;
1952
}
1953
1954
static int
1955
vgetargskeywordsfast_impl(PyObject *const *args, Py_ssize_t nargs,
1956
                          PyObject *kwargs, PyObject *kwnames,
1957
                          struct _PyArg_Parser *parser,
1958
                          va_list *p_va, int flags)
1959
{
1960
    PyObject *kwtuple;
1961
    char msgbuf[512];
1962
    int levels[32];
1963
    const char *format;
1964
    const char *msg;
1965
    PyObject *keyword;
1966
    int i, pos, len;
1967
    Py_ssize_t nkwargs;
1968
    PyObject *current_arg;
1969
    freelistentry_t static_entries[STATIC_FREELIST_ENTRIES];
1970
    freelist_t freelist;
1971
    PyObject *const *kwstack = NULL;
1972
1973
    freelist.entries = static_entries;
1974
    freelist.first_available = 0;
1975
    freelist.entries_malloced = 0;
1976
1977
    assert(kwargs == NULL || PyDict_Check(kwargs));
1978
    assert(kwargs == NULL || kwnames == NULL);
1979
    assert(p_va != NULL);
1980
1981
    if (parser == NULL) {
  Branch (1981:9): [True: 0, False: 51]
1982
        PyErr_BadInternalCall();
1983
        return 0;
1984
    }
1985
1986
    if (kwnames != NULL && 
!0
PyTuple_Check0
(kwnames)) {
  Branch (1986:9): [True: 0, False: 51]
  Branch (1986:28): [True: 0, False: 0]
1987
        PyErr_BadInternalCall();
1988
        return 0;
1989
    }
1990
1991
    if (!parser_init(parser)) {
  Branch (1991:9): [True: 0, False: 51]
1992
        return 0;
1993
    }
1994
1995
    kwtuple = parser->kwtuple;
1996
    pos = parser->pos;
1997
    len = pos + (int)PyTuple_GET_SIZE(kwtuple);
1998
1999
    if (len > STATIC_FREELIST_ENTRIES) {
  Branch (1999:9): [True: 0, False: 51]
2000
        freelist.entries = PyMem_NEW(freelistentry_t, len);
2001
        if (freelist.entries == NULL) {
  Branch (2001:13): [True: 0, False: 0]
2002
            PyErr_NoMemory();
2003
            return 0;
2004
        }
2005
        freelist.entries_malloced = 1;
2006
    }
2007
2008
    if (kwargs != NULL) {
  Branch (2008:9): [True: 0, False: 51]
2009
        nkwargs = PyDict_GET_SIZE(kwargs);
2010
    }
2011
    else if (kwnames != NULL) {
  Branch (2011:14): [True: 0, False: 51]
2012
        nkwargs = PyTuple_GET_SIZE(kwnames);
2013
        kwstack = args + nargs;
2014
    }
2015
    else {
2016
        nkwargs = 0;
2017
    }
2018
    if (nargs + nkwargs > len) {
  Branch (2018:9): [True: 0, False: 51]
2019
        /* Adding "keyword" (when nargs == 0) prevents producing wrong error
2020
           messages in some special cases (see bpo-31229). */
2021
        PyErr_Format(PyExc_TypeError,
2022
                     "%.200s%s takes at most %d %sargument%s (%zd given)",
2023
                     (parser->fname == NULL) ? "function" : parser->fname,
  Branch (2023:22): [True: 0, False: 0]
2024
                     (parser->fname == NULL) ? "" : "()",
  Branch (2024:22): [True: 0, False: 0]
2025
                     len,
2026
                     (nargs == 0) ? "keyword " : "",
  Branch (2026:22): [True: 0, False: 0]
2027
                     (len == 1) ? "" : "s",
  Branch (2027:22): [True: 0, False: 0]
2028
                     nargs + nkwargs);
2029
        return cleanreturn(0, &freelist);
2030
    }
2031
    if (parser->max < nargs) {
  Branch (2031:9): [True: 0, False: 51]
2032
        if (parser->max == 0) {
  Branch (2032:13): [True: 0, False: 0]
2033
            PyErr_Format(PyExc_TypeError,
2034
                         "%.200s%s takes no positional arguments",
2035
                         (parser->fname == NULL) ? "function" : parser->fname,
  Branch (2035:26): [True: 0, False: 0]
2036
                         (parser->fname == NULL) ? "" : "()");
  Branch (2036:26): [True: 0, False: 0]
2037
        }
2038
        else {
2039
            PyErr_Format(PyExc_TypeError,
2040
                         "%.200s%s takes %s %d positional argument%s (%zd given)",
2041
                         (parser->fname == NULL) ? "function" : parser->fname,
  Branch (2041:26): [True: 0, False: 0]
2042
                         (parser->fname == NULL) ? "" : "()",
  Branch (2042:26): [True: 0, False: 0]
2043
                         (parser->min < parser->max) ? "at most" : "exactly",
  Branch (2043:26): [True: 0, False: 0]
2044
                         parser->max,
2045
                         parser->max == 1 ? "" : "s",
  Branch (2045:26): [True: 0, False: 0]
2046
                         nargs);
2047
        }
2048
        return cleanreturn(0, &freelist);
2049
    }
2050
2051
    format = parser->format;
2052
    /* convert tuple args and keyword args in same loop, using kwtuple to drive process */
2053
    for (i = 0; i < len; 
i++65
) {
  Branch (2053:17): [True: 98, False: 18]
2054
        if (*format == '|') {
  Branch (2054:13): [True: 38, False: 60]
2055
            format++;
2056
        }
2057
        if (*format == '$') {
  Branch (2057:13): [True: 0, False: 98]
2058
            format++;
2059
        }
2060
        assert(!IS_END_OF_FORMAT(*format));
2061
2062
        if (i < nargs) {
  Branch (2062:13): [True: 65, False: 33]
2063
            current_arg = args[i];
2064
        }
2065
        else if (nkwargs && 
i >= pos0
) {
  Branch (2065:18): [True: 0, False: 33]
  Branch (2065:29): [True: 0, False: 0]
2066
            keyword = PyTuple_GET_ITEM(kwtuple, i - pos);
2067
            if (kwargs != NULL) {
  Branch (2067:17): [True: 0, False: 0]
2068
                current_arg = PyDict_GetItemWithError(kwargs, keyword);
2069
                if (!current_arg && PyErr_Occurred()) {
  Branch (2069:21): [True: 0, False: 0]
  Branch (2069:37): [True: 0, False: 0]
2070
                    return cleanreturn(0, &freelist);
2071
                }
2072
            }
2073
            else {
2074
                current_arg = find_keyword(kwnames, kwstack, keyword);
2075
            }
2076
            if (current_arg) {
  Branch (2076:17): [True: 0, False: 0]
2077
                --nkwargs;
2078
            }
2079
        }
2080
        else {
2081
            current_arg = NULL;
2082
        }
2083
2084
        if (current_arg) {
  Branch (2084:13): [True: 65, False: 33]
2085
            msg = convertitem(current_arg, &format, p_va, flags,
2086
                levels, msgbuf, sizeof(msgbuf), &freelist);
2087
            if (msg) {
  Branch (2087:17): [True: 0, False: 65]
2088
                seterror(i+1, msg, levels, parser->fname, parser->custom_msg);
2089
                return cleanreturn(0, &freelist);
2090
            }
2091
            continue;
2092
        }
2093
2094
        if (i < parser->min) {
  Branch (2094:13): [True: 0, False: 33]
2095
            /* Less arguments than required */
2096
            if (i < pos) {
  Branch (2096:17): [True: 0, False: 0]
2097
                Py_ssize_t min = Py_MIN(pos, parser->min);
2098
                PyErr_Format(PyExc_TypeError,
2099
                             "%.200s%s takes %s %d positional argument%s"
2100
                             " (%zd given)",
2101
                             (parser->fname == NULL) ? "function" : parser->fname,
  Branch (2101:30): [True: 0, False: 0]
2102
                             (parser->fname == NULL) ? "" : "()",
  Branch (2102:30): [True: 0, False: 0]
2103
                             min < parser->max ? "at least" : "exactly",
  Branch (2103:30): [True: 0, False: 0]
2104
                             min,
2105
                             min == 1 ? "" : "s",
  Branch (2105:30): [True: 0, False: 0]
2106
                             nargs);
2107
            }
2108
            else {
2109
                keyword = PyTuple_GET_ITEM(kwtuple, i - pos);
2110
                PyErr_Format(PyExc_TypeError,  "%.200s%s missing required "
2111
                             "argument '%U' (pos %d)",
2112
                             (parser->fname == NULL) ? "function" : parser->fname,
  Branch (2112:30): [True: 0, False: 0]
2113
                             (parser->fname == NULL) ? "" : "()",
  Branch (2113:30): [True: 0, False: 0]
2114
                             keyword, i+1);
2115
            }
2116
            return cleanreturn(0, &freelist);
2117
        }
2118
        /* current code reports success when all required args
2119
         * fulfilled and no keyword args left, with no further
2120
         * validation. XXX Maybe skip this in debug build ?
2121
         */
2122
        if (!nkwargs) {
  Branch (2122:13): [True: 33, False: 0]
2123
            return cleanreturn(1, &freelist);
2124
        }
2125
2126
        /* We are into optional args, skip through to any remaining
2127
         * keyword args */
2128
        msg = skipitem(&format, p_va, flags);
2129
        assert(msg == NULL);
2130
    }
2131
2132
    assert(IS_END_OF_FORMAT(*format) || (*format == '|') || (*format == '$'));
2133
2134
    if (nkwargs > 0) {
  Branch (2134:9): [True: 0, False: 18]
2135
        Py_ssize_t j;
2136
        /* make sure there are no arguments given by name and position */
2137
        for (i = pos; i < nargs; i++) {
  Branch (2137:23): [True: 0, False: 0]
2138
            keyword = PyTuple_GET_ITEM(kwtuple, i - pos);
2139
            if (kwargs != NULL) {
  Branch (2139:17): [True: 0, False: 0]
2140
                current_arg = PyDict_GetItemWithError(kwargs, keyword);
2141
                if (!current_arg && PyErr_Occurred()) {
  Branch (2141:21): [True: 0, False: 0]
  Branch (2141:37): [True: 0, False: 0]
2142
                    return cleanreturn(0, &freelist);
2143
                }
2144
            }
2145
            else {
2146
                current_arg = find_keyword(kwnames, kwstack, keyword);
2147
            }
2148
            if (current_arg) {
  Branch (2148:17): [True: 0, False: 0]
2149
                /* arg present in tuple and in dict */
2150
                PyErr_Format(PyExc_TypeError,
2151
                             "argument for %.200s%s given by name ('%U') "
2152
                             "and position (%d)",
2153
                             (parser->fname == NULL) ? "function" : parser->fname,
  Branch (2153:30): [True: 0, False: 0]
2154
                             (parser->fname == NULL) ? "" : "()",
  Branch (2154:30): [True: 0, False: 0]
2155
                             keyword, i+1);
2156
                return cleanreturn(0, &freelist);
2157
            }
2158
        }
2159
        /* make sure there are no extraneous keyword arguments */
2160
        j = 0;
2161
        while (1) {
  Branch (2161:16): [Folded - Ignored]
2162
            int match;
2163
            if (kwargs != NULL) {
  Branch (2163:17): [True: 0, False: 0]
2164
                if (!PyDict_Next(kwargs, &j, &keyword, NULL))
  Branch (2164:21): [True: 0, False: 0]
2165
                    break;
2166
            }
2167
            else {
2168
                if (j >= PyTuple_GET_SIZE(kwnames))
  Branch (2168:21): [True: 0, False: 0]
2169
                    break;
2170
                keyword = PyTuple_GET_ITEM(kwnames, j);
2171
                j++;
2172
            }
2173
2174
            match = PySequence_Contains(kwtuple, keyword);
2175
            if (match <= 0) {
  Branch (2175:17): [True: 0, False: 0]
2176
                if (!match) {
  Branch (2176:21): [True: 0, False: 0]
2177
                    PyErr_Format(PyExc_TypeError,
2178
                                 "'%S' is an invalid keyword "
2179
                                 "argument for %.200s%s",
2180
                                 keyword,
2181
                                 (parser->fname == NULL) ? "this function" : parser->fname,
  Branch (2181:34): [True: 0, False: 0]
2182
                                 (parser->fname == NULL) ? "" : "()");
  Branch (2182:34): [True: 0, False: 0]
2183
                }
2184
                return cleanreturn(0, &freelist);
2185
            }
2186
        }
2187
    }
2188
2189
    return cleanreturn(1, &freelist);
2190
}
2191
2192
static int
2193
vgetargskeywordsfast(PyObject *args, PyObject *keywords,
2194
                     struct _PyArg_Parser *parser, va_list *p_va, int flags)
2195
{
2196
    PyObject **stack;
2197
    Py_ssize_t nargs;
2198
2199
    if (args == NULL
  Branch (2199:9): [True: 0, False: 0]
2200
        || !PyTuple_Check(args)
  Branch (2200:12): [True: 0, False: 0]
2201
        || (keywords != NULL && !PyDict_Check(keywords)))
  Branch (2201:13): [True: 0, False: 0]
  Branch (2201:33): [True: 0, False: 0]
2202
    {
2203
        PyErr_BadInternalCall();
2204
        return 0;
2205
    }
2206
2207
    stack = _PyTuple_ITEMS(args);
2208
    nargs = PyTuple_GET_SIZE(args);
2209
    return vgetargskeywordsfast_impl(stack, nargs, keywords, NULL,
2210
                                     parser, p_va, flags);
2211
}
2212
2213
2214
#undef _PyArg_UnpackKeywords
2215
2216
PyObject * const *
2217
_PyArg_UnpackKeywords(PyObject *const *args, Py_ssize_t nargs,
2218
                      PyObject *kwargs, PyObject *kwnames,
2219
                      struct _PyArg_Parser *parser,
2220
                      int minpos, int maxpos, int minkw,
2221
                      PyObject **buf)
2222
{
2223
    PyObject *kwtuple;
2224
    PyObject *keyword;
2225
    int i, posonly, minposonly, maxargs;
2226
    int reqlimit = minkw ? 
maxpos + minkw0
: minpos;
  Branch (2226:20): [True: 0, False: 1.28M]
2227
    Py_ssize_t nkwargs;
2228
    PyObject *current_arg;
2229
    PyObject * const *kwstack = NULL;
2230
2231
    assert(kwargs == NULL || PyDict_Check(kwargs));
2232
    assert(kwargs == NULL || kwnames == NULL);
2233
2234
    if (parser == NULL) {
  Branch (2234:9): [True: 0, False: 1.28M]
2235
        PyErr_BadInternalCall();
2236
        return NULL;
2237
    }
2238
2239
    if (kwnames != NULL && 
!1.20M
PyTuple_Check1.20M
(kwnames)) {
  Branch (2239:9): [True: 1.20M, False: 85.7k]
  Branch (2239:28): [True: 0, False: 1.20M]
2240
        PyErr_BadInternalCall();
2241
        return NULL;
2242
    }
2243
2244
    if (args == NULL && 
nargs == 0672
) {
  Branch (2244:9): [True: 672, False: 1.28M]
  Branch (2244:25): [True: 672, False: 0]
2245
        args = buf;
2246
    }
2247
2248
    if (!parser_init(parser)) {
  Branch (2248:9): [True: 0, False: 1.28M]
2249
        return NULL;
2250
    }
2251
2252
    kwtuple = parser->kwtuple;
2253
    posonly = parser->pos;
2254
    minposonly = Py_MIN(posonly, minpos);
2255
    maxargs = posonly + (int)PyTuple_GET_SIZE(kwtuple);
2256
2257
    if (kwargs != NULL) {
  Branch (2257:9): [True: 84.8k, False: 1.20M]
2258
        nkwargs = PyDict_GET_SIZE(kwargs);
2259
    }
2260
    else if (kwnames != NULL) {
  Branch (2260:14): [True: 1.20M, False: 854]
2261
        nkwargs = PyTuple_GET_SIZE(kwnames);
2262
        kwstack = args + nargs;
2263
    }
2264
    else {
2265
        nkwargs = 0;
2266
    }
2267
    if (nkwargs == 0 && 
minkw == 043.9k
&&
minpos <= nargs43.9k
&&
nargs <= maxpos43.7k
) {
  Branch (2267:9): [True: 43.9k, False: 1.24M]
  Branch (2267:25): [True: 43.9k, False: 0]
  Branch (2267:39): [True: 43.7k, False: 152]
  Branch (2267:58): [True: 43.6k, False: 54]
2268
        /* Fast path. */
2269
        return args;
2270
    }
2271
    if (nargs + nkwargs > maxargs) {
  Branch (2271:9): [True: 39, False: 1.24M]
2272
        /* Adding "keyword" (when nargs == 0) prevents producing wrong error
2273
           messages in some special cases (see bpo-31229). */
2274
        PyErr_Format(PyExc_TypeError,
2275
                     "%.200s%s takes at most %d %sargument%s (%zd given)",
2276
                     (parser->fname == NULL) ? 
"function"0
: parser->fname,
  Branch (2276:22): [True: 0, False: 39]
2277
                     (parser->fname == NULL) ? 
""0
: "()",
  Branch (2277:22): [True: 0, False: 39]
2278
                     maxargs,
2279
                     (nargs == 0) ? 
"keyword "0
: "",
  Branch (2279:22): [True: 0, False: 39]
2280
                     (maxargs == 1) ? 
""14
:
"s"25
,
  Branch (2280:22): [True: 14, False: 25]
2281
                     nargs + nkwargs);
2282
        return NULL;
2283
    }
2284
    if (nargs > maxpos) {
  Branch (2284:9): [True: 20, False: 1.24M]
2285
        if (maxpos == 0) {
  Branch (2285:13): [True: 7, False: 13]
2286
            PyErr_Format(PyExc_TypeError,
2287
                         "%.200s%s takes no positional arguments",
2288
                         (parser->fname == NULL) ? 
"function"0
: parser->fname,
  Branch (2288:26): [True: 0, False: 7]
2289
                         (parser->fname == NULL) ? 
""0
: "()");
  Branch (2289:26): [True: 0, False: 7]
2290
        }
2291
        else {
2292
            PyErr_Format(PyExc_TypeError,
2293
                         "%.200s%s takes %s %d positional argument%s (%zd given)",
2294
                         (parser->fname == NULL) ? 
"function"0
: parser->fname,
  Branch (2294:26): [True: 0, False: 13]
2295
                         (parser->fname == NULL) ? 
""0
: "()",
  Branch (2295:26): [True: 0, False: 13]
2296
                         (minpos < maxpos) ? 
"at most"4
:
"exactly"9
,
  Branch (2296:26): [True: 4, False: 9]
2297
                         maxpos,
2298
                         (maxpos == 1) ? 
""8
:
"s"5
,
  Branch (2298:26): [True: 8, False: 5]
2299
                         nargs);
2300
        }
2301
        return NULL;
2302
    }
2303
    if (nargs < minposonly) {
  Branch (2303:9): [True: 60, False: 1.24M]
2304
        PyErr_Format(PyExc_TypeError,
2305
                     "%.200s%s takes %s %d positional argument%s"
2306
                     " (%zd given)",
2307
                     (parser->fname == NULL) ? 
"function"0
: parser->fname,
  Branch (2307:22): [True: 0, False: 60]
2308
                     (parser->fname == NULL) ? 
""0
: "()",
  Branch (2308:22): [True: 0, False: 60]
2309
                     minposonly < maxpos ? 
"at least"7
:
"exactly"53
,
  Branch (2309:22): [True: 7, False: 53]
2310
                     minposonly,
2311
                     minposonly == 1 ? 
""47
:
"s"13
,
  Branch (2311:22): [True: 47, False: 13]
2312
                     nargs);
2313
        return NULL;
2314
    }
2315
2316
    /* copy tuple args */
2317
    
for (i = 0; 1.24M
i < nargs;
i++265k
) {
  Branch (2317:17): [True: 265k, False: 1.24M]
2318
        buf[i] = args[i];
2319
    }
2320
2321
    /* copy keyword args using kwtuple to drive process */
2322
    for (i = 
Py_MAX1.24M
((int)nargs, posonly); i < maxargs;
i++1.45M
) {
  Branch (2322:43): [True: 2.14M, False: 551k]
2323
        if (nkwargs) {
  Branch (2323:13): [True: 1.45M, False: 691k]
2324
            keyword = PyTuple_GET_ITEM(kwtuple, i - posonly);
2325
            if (kwargs != NULL) {
  Branch (2325:17): [True: 85.4k, False: 1.36M]
2326
                current_arg = PyDict_GetItemWithError(kwargs, keyword);
2327
                if (!current_arg && 
PyErr_Occurred()25.5k
) {
  Branch (2327:21): [True: 25.5k, False: 59.8k]
  Branch (2327:37): [True: 0, False: 25.5k]
2328
                    return NULL;
2329
                }
2330
            }
2331
            else {
2332
                current_arg = find_keyword(kwnames, kwstack, keyword);
2333
            }
2334
        }
2335
        else if (i >= reqlimit) {
  Branch (2335:18): [True: 691k, False: 95]
2336
            break;
2337
        }
2338
        else {
2339
            current_arg = NULL;
2340
        }
2341
2342
        buf[i] = current_arg;
2343
2344
        if (current_arg) {
  Branch (2344:13): [True: 1.29M, False: 164k]
2345
            --nkwargs;
2346
        }
2347
        else if (i < minpos || 
(164k
maxpos <= i164k
&&
i < reqlimit40.5k
)) {
  Branch (2347:18): [True: 106, False: 164k]
  Branch (2347:33): [True: 40.5k, False: 123k]
  Branch (2347:48): [True: 0, False: 40.5k]
2348
            /* Less arguments than required */
2349
            keyword = PyTuple_GET_ITEM(kwtuple, i - posonly);
2350
            PyErr_Format(PyExc_TypeError,  "%.200s%s missing required "
2351
                         "argument '%U' (pos %d)",
2352
                         (parser->fname == NULL) ? 
"function"0
: parser->fname,
  Branch (2352:26): [True: 0, False: 106]
2353
                         (parser->fname == NULL) ? 
""0
: "()",
  Branch (2353:26): [True: 0, False: 106]
2354
                         keyword, i+1);
2355
            return NULL;
2356
        }
2357
    }
2358
2359
    if (nkwargs > 0) {
  Branch (2359:9): [True: 19, False: 1.24M]
2360
        Py_ssize_t j;
2361
        /* make sure there are no arguments given by name and position */
2362
        for (i = posonly; i < nargs; 
i++1
) {
  Branch (2362:27): [True: 3, False: 17]
2363
            keyword = PyTuple_GET_ITEM(kwtuple, i - posonly);
2364
            if (kwargs != NULL) {
  Branch (2364:17): [True: 1, False: 2]
2365
                current_arg = PyDict_GetItemWithError(kwargs, keyword);
2366
                if (!current_arg && PyErr_Occurred()) {
  Branch (2366:21): [True: 1, False: 0]
  Branch (2366:37): [True: 0, False: 1]
2367
                    return NULL;
2368
                }
2369
            }
2370
            else {
2371
                current_arg = find_keyword(kwnames, kwstack, keyword);
2372
            }
2373
            if (current_arg) {
  Branch (2373:17): [True: 2, False: 1]
2374
                /* arg present in tuple and in dict */
2375
                PyErr_Format(PyExc_TypeError,
2376
                             "argument for %.200s%s given by name ('%U') "
2377
                             "and position (%d)",
2378
                             (parser->fname == NULL) ? 
"function"0
: parser->fname,
  Branch (2378:30): [True: 0, False: 2]
2379
                             (parser->fname == NULL) ? 
""0
: "()",
  Branch (2379:30): [True: 0, False: 2]
2380
                             keyword, i+1);
2381
                return NULL;
2382
            }
2383
        }
2384
        /* make sure there are no extraneous keyword arguments */
2385
        j = 0;
2386
        while (1) {
  Branch (2386:16): [Folded - Ignored]
2387
            int match;
2388
            if (kwargs != NULL) {
  Branch (2388:17): [True: 15, False: 3]
2389
                if (!PyDict_Next(kwargs, &j, &keyword, NULL))
  Branch (2389:21): [True: 0, False: 15]
2390
                    break;
2391
            }
2392
            else {
2393
                if (j >= PyTuple_GET_SIZE(kwnames))
  Branch (2393:21): [True: 0, False: 3]
2394
                    break;
2395
                keyword = PyTuple_GET_ITEM(kwnames, j);
2396
                j++;
2397
            }
2398
2399
            match = PySequence_Contains(kwtuple, keyword);
2400
            if (match <= 0) {
  Branch (2400:17): [True: 17, False: 1]
2401
                if (!match) {
  Branch (2401:21): [True: 17, False: 0]
2402
                    PyErr_Format(PyExc_TypeError,
2403
                                 "'%S' is an invalid keyword "
2404
                                 "argument for %.200s%s",
2405
                                 keyword,
2406
                                 (parser->fname == NULL) ? 
"this function"0
: parser->fname,
  Branch (2406:34): [True: 0, False: 17]
2407
                                 (parser->fname == NULL) ? 
""0
: "()");
  Branch (2407:34): [True: 0, False: 17]
2408
                }
2409
                return NULL;
2410
            }
2411
        }
2412
    }
2413
2414
    return buf;
2415
}
2416
2417
PyObject * const *
2418
_PyArg_UnpackKeywordsWithVararg(PyObject *const *args, Py_ssize_t nargs,
2419
                                PyObject *kwargs, PyObject *kwnames,
2420
                                struct _PyArg_Parser *parser,
2421
                                int minpos, int maxpos, int minkw,
2422
                                int vararg, PyObject **buf)
2423
{
2424
    PyObject *kwtuple;
2425
    PyObject *keyword;
2426
    Py_ssize_t varargssize = 0;
2427
    int i, posonly, minposonly, maxargs;
2428
    int reqlimit = minkw ? 
maxpos + minkw0
: minpos;
  Branch (2428:20): [True: 0, False: 60.6k]
2429
    Py_ssize_t nkwargs;
2430
    PyObject *current_arg;
2431
    PyObject * const *kwstack = NULL;
2432
2433
    assert(kwargs == NULL || PyDict_Check(kwargs));
2434
    assert(kwargs == NULL || kwnames == NULL);
2435
2436
    if (parser == NULL) {
  Branch (2436:9): [True: 0, False: 60.6k]
2437
        PyErr_BadInternalCall();
2438
        return NULL;
2439
    }
2440
2441
    if (kwnames != NULL && 
!56.9k
PyTuple_Check56.9k
(kwnames)) {
  Branch (2441:9): [True: 56.9k, False: 3.68k]
  Branch (2441:28): [True: 0, False: 56.9k]
2442
        PyErr_BadInternalCall();
2443
        return NULL;
2444
    }
2445
2446
    if (args == NULL && 
nargs == 00
) {
  Branch (2446:9): [True: 0, False: 60.6k]
  Branch (2446:25): [True: 0, False: 0]
2447
        args = buf;
2448
    }
2449
2450
    if (!parser_init(parser)) {
  Branch (2450:9): [True: 0, False: 60.6k]
2451
        return NULL;
2452
    }
2453
2454
    kwtuple = parser->kwtuple;
2455
    posonly = parser->pos;
2456
    minposonly = Py_MIN(posonly, minpos);
2457
    maxargs = posonly + (int)PyTuple_GET_SIZE(kwtuple);
2458
    if (kwargs != NULL) {
  Branch (2458:9): [True: 0, False: 60.6k]
2459
        nkwargs = PyDict_GET_SIZE(kwargs);
2460
    }
2461
    else if (kwnames != NULL) {
  Branch (2461:14): [True: 56.9k, False: 3.68k]
2462
        nkwargs = PyTuple_GET_SIZE(kwnames);
2463
        kwstack = args + nargs;
2464
    }
2465
    else {
2466
        nkwargs = 0;
2467
    }
2468
    if (nargs < minposonly) {
  Branch (2468:9): [True: 0, False: 60.6k]
2469
        PyErr_Format(PyExc_TypeError,
2470
                     "%.200s%s takes %s %d positional argument%s"
2471
                     " (%zd given)",
2472
                     (parser->fname == NULL) ? "function" : parser->fname,
  Branch (2472:22): [True: 0, False: 0]
2473
                     (parser->fname == NULL) ? "" : "()",
  Branch (2473:22): [True: 0, False: 0]
2474
                     minposonly < maxpos ? "at least" : "exactly",
  Branch (2474:22): [True: 0, False: 0]
2475
                     minposonly,
2476
                     minposonly == 1 ? "" : "s",
  Branch (2476:22): [True: 0, False: 0]
2477
                     nargs);
2478
        return NULL;
2479
    }
2480
2481
    /* create varargs tuple */
2482
    varargssize = nargs - maxpos;
2483
    if (varargssize < 0) {
  Branch (2483:9): [True: 0, False: 60.6k]
2484
        varargssize = 0;
2485
    }
2486
    buf[vararg] = PyTuple_New(varargssize);
2487
    if (!buf[vararg]) {
  Branch (2487:9): [True: 0, False: 60.6k]
2488
        return NULL;
2489
    }
2490
2491
    /* copy tuple args */
2492
    
for (i = 0; 60.6k
i < nargs;
i++59.4k
) {
  Branch (2492:17): [True: 59.4k, False: 60.6k]
2493
        if (i >= vararg) {
  Branch (2493:13): [True: 59.4k, False: 0]
2494
            Py_INCREF(args[i]);
2495
            PyTuple_SET_ITEM(buf[vararg], i - vararg, args[i]);
2496
            continue;
2497
        }
2498
        else {
2499
            buf[i] = args[i];
2500
        }
2501
    }
2502
2503
    /* copy keyword args using kwtuple to drive process */
2504
    for (i = Py_MAX((int)nargs, posonly) -
2505
         
Py_SAFE_DOWNCAST60.6k
(varargssize, Py_ssize_t, int); i < maxargs;
i++242k
) {
  Branch (2505:58): [True: 242k, False: 60.6k]
2506
        if (nkwargs) {
  Branch (2506:13): [True: 168k, False: 74.0k]
2507
            keyword = PyTuple_GET_ITEM(kwtuple, i - posonly);
2508
            if (kwargs != NULL) {
  Branch (2508:17): [True: 0, False: 168k]
2509
                current_arg = PyDict_GetItemWithError(kwargs, keyword);
2510
                if (!current_arg && PyErr_Occurred()) {
  Branch (2510:21): [True: 0, False: 0]
  Branch (2510:37): [True: 0, False: 0]
2511
                    goto exit;
2512
                }
2513
            }
2514
            else {
2515
                current_arg = find_keyword(kwnames, kwstack, keyword);
2516
            }
2517
        }
2518
        else {
2519
            current_arg = NULL;
2520
        }
2521
2522
        buf[i + vararg + 1] = current_arg;
2523
2524
        if (current_arg) {
  Branch (2524:13): [True: 71.0k, False: 171k]
2525
            --nkwargs;
2526
        }
2527
        else if (i < minpos || (maxpos <= i && i < reqlimit)) {
  Branch (2527:18): [True: 0, False: 171k]
  Branch (2527:33): [True: 171k, False: 0]
  Branch (2527:48): [True: 0, False: 171k]
2528
            /* Less arguments than required */
2529
            keyword = PyTuple_GET_ITEM(kwtuple, i - posonly);
2530
            PyErr_Format(PyExc_TypeError,  "%.200s%s missing required "
2531
                         "argument '%U' (pos %d)",
2532
                         (parser->fname == NULL) ? "function" : parser->fname,
  Branch (2532:26): [True: 0, False: 0]
2533
                         (parser->fname == NULL) ? "" : "()",
  Branch (2533:26): [True: 0, False: 0]
2534
                         keyword, i+1);
2535
            goto exit;
2536
        }
2537
    }
2538
2539
    if (nkwargs > 0) {
  Branch (2539:9): [True: 1, False: 60.6k]
2540
        Py_ssize_t j;
2541
        /* make sure there are no extraneous keyword arguments */
2542
        j = 0;
2543
        while (1) {
  Branch (2543:16): [Folded - Ignored]
2544
            int match;
2545
            if (kwargs != NULL) {
  Branch (2545:17): [True: 0, False: 5]
2546
                if (!PyDict_Next(kwargs, &j, &keyword, NULL))
  Branch (2546:21): [True: 0, False: 0]
2547
                    break;
2548
            }
2549
            else {
2550
                if (j >= PyTuple_GET_SIZE(kwnames))
  Branch (2550:21): [True: 0, False: 5]
2551
                    break;
2552
                keyword = PyTuple_GET_ITEM(kwnames, j);
2553
                j++;
2554
            }
2555
2556
            match = PySequence_Contains(kwtuple, keyword);
2557
            if (match <= 0) {
  Branch (2557:17): [True: 1, False: 4]
2558
                if (!match) {
  Branch (2558:21): [True: 1, False: 0]
2559
                    PyErr_Format(PyExc_TypeError,
2560
                                 "'%S' is an invalid keyword "
2561
                                 "argument for %.200s%s",
2562
                                 keyword,
2563
                                 (parser->fname == NULL) ? 
"this function"0
: parser->fname,
  Branch (2563:34): [True: 0, False: 1]
2564
                                 (parser->fname == NULL) ? 
""0
: "()");
  Branch (2564:34): [True: 0, False: 1]
2565
                }
2566
                goto exit;
2567
            }
2568
        }
2569
    }
2570
2571
    return buf;
2572
2573
exit:
2574
    Py_XDECREF(buf[vararg]);
2575
    return NULL;
2576
}
2577
2578
2579
static const char *
2580
skipitem(const char **p_format, va_list *p_va, int flags)
2581
{
2582
    const char *format = *p_format;
2583
    char c = *format++;
2584
2585
    switch (c) {
2586
2587
    /*
2588
     * codes that take a single data pointer as an argument
2589
     * (the type of the pointer is irrelevant)
2590
     */
2591
2592
    case 'b': /* byte -- very short int */
  Branch (2592:5): [True: 3, False: 652k]
2593
    case 'B': /* byte as bitfield */
  Branch (2593:5): [True: 3, False: 652k]
2594
    case 'h': /* short int */
  Branch (2594:5): [True: 3, False: 652k]
2595
    case 'H': /* short int as bitfield */
  Branch (2595:5): [True: 3, False: 652k]
2596
    case 'i': /* int */
  Branch (2596:5): [True: 177k, False: 475k]
2597
    case 'I': /* int sized bitfield */
  Branch (2597:5): [True: 3, False: 652k]
2598
    case 'l': /* long int */
  Branch (2598:5): [True: 3, False: 652k]
2599
    case 'k': /* long int sized bitfield */
  Branch (2599:5): [True: 3, False: 652k]
2600
    case 'L': /* long long */
  Branch (2600:5): [True: 3, False: 652k]
2601
    case 'K': /* long long sized bitfield */
  Branch (2601:5): [True: 3, False: 652k]
2602
    case 'n': /* Py_ssize_t */
  Branch (2602:5): [True: 189k, False: 463k]
2603
    case 'f': /* float */
  Branch (2603:5): [True: 3, False: 652k]
2604
    case 'd': /* double */
  Branch (2604:5): [True: 3, False: 652k]
2605
    case 'D': /* complex double */
  Branch (2605:5): [True: 3, False: 652k]
2606
    case 'c': /* char */
  Branch (2606:5): [True: 3, False: 652k]
2607
    case 'C': /* unicode char */
  Branch (2607:5): [True: 192, False: 652k]
2608
    case 'p': /* boolean predicate */
  Branch (2608:5): [True: 29, False: 652k]
2609
    case 'S': /* string object */
  Branch (2609:5): [True: 3, False: 652k]
2610
    case 'Y': /* string object */
  Branch (2610:5): [True: 3, False: 652k]
2611
    case 'U': /* unicode string object */
  Branch (2611:5): [True: 3, False: 652k]
2612
        {
2613
            if (p_va != NULL) {
  Branch (2613:17): [True: 366k, False: 4]
2614
                (void) va_arg(*p_va, void *);
2615
            }
2616
            break;
2617
        }
2618
2619
    /* string codes */
2620
2621
    case 'e': /* string with encoding */
  Branch (2621:5): [True: 98, False: 652k]
2622
        {
2623
            if (p_va != NULL) {
  Branch (2623:17): [True: 98, False: 0]
2624
                (void) va_arg(*p_va, const char *);
2625
            }
2626
            if (!(*format == 's' || 
*format == 't'97
))
  Branch (2626:19): [True: 1, False: 97]
  Branch (2626:37): [True: 1, False: 96]
2627
                /* after 'e', only 's' and 't' is allowed */
2628
                goto err;
2629
            format++;
2630
        }
2631
        /* fall through */
2632
2633
    case 's': /* string */
  Branch (2633:5): [True: 10, False: 652k]
2634
    case 'z': /* string or None */
  Branch (2634:5): [True: 3, False: 652k]
2635
    case 'y': /* bytes */
  Branch (2635:5): [True: 5, False: 652k]
2636
    case 'w': /* buffer, read-write */
  Branch (2636:5): [True: 3, False: 652k]
2637
        {
2638
            if (p_va != NULL) {
  Branch (2638:17): [True: 20, False: 3]
2639
                (void) va_arg(*p_va, char **);
2640
            }
2641
            if (*format == '#') {
  Branch (2641:17): [True: 8, False: 15]
2642
                if (p_va != NULL) {
  Branch (2642:21): [True: 5, False: 3]
2643
                    if (!(flags & FLAG_SIZE_T)) {
  Branch (2643:25): [True: 1, False: 4]
2644
                        PyErr_SetString(PyExc_SystemError,
2645
                                "PY_SSIZE_T_CLEAN macro must be defined for '#' formats");
2646
                        return NULL;
2647
                    }
2648
                    (void) va_arg(*p_va, Py_ssize_t *);
2649
                }
2650
                format++;
2651
            } else if ((c == 's' || 
c == 'z'10
||
c == 'y'8
||
c == 'w'4
)
  Branch (2651:25): [True: 5, False: 10]
  Branch (2651:37): [True: 2, False: 8]
  Branch (2651:49): [True: 4, False: 4]
  Branch (2651:61): [True: 2, False: 2]
2652
                       && 
*format == '*'13
)
  Branch (2652:27): [True: 6, False: 7]
2653
            {
2654
                format++;
2655
            }
2656
            break;
2657
        }
2658
2659
    case 'O': /* object */
  Branch (2659:5): [True: 285k, False: 367k]
2660
        {
2661
            if (*format == '!') {
  Branch (2661:17): [True: 1, False: 285k]
2662
                format++;
2663
                if (p_va != NULL) {
  Branch (2663:21): [True: 1, False: 0]
2664
                    (void) va_arg(*p_va, PyTypeObject*);
2665
                    (void) va_arg(*p_va, PyObject **);
2666
                }
2667
            }
2668
            else if (*format == '&') {
  Branch (2668:22): [True: 39, False: 285k]
2669
                typedef int (*converter)(PyObject *, void *);
2670
                if (p_va != NULL) {
  Branch (2670:21): [True: 38, False: 1]
2671
                    (void) va_arg(*p_va, converter);
2672
                    (void) va_arg(*p_va, void *);
2673
                }
2674
                format++;
2675
            }
2676
            else {
2677
                if (p_va != NULL) {
  Branch (2677:21): [True: 285k, False: 2]
2678
                    (void) va_arg(*p_va, PyObject **);
2679
                }
2680
            }
2681
            break;
2682
        }
2683
2684
    case '(':           /* bypass tuple, not handled at all previously */
  Branch (2684:5): [True: 6, False: 652k]
2685
        {
2686
            const char *msg;
2687
            for (;;) {
2688
                if (*format==')')
  Branch (2688:21): [True: 6, False: 14]
2689
                    break;
2690
                if (IS_END_OF_FORMAT(*format))
2691
                    return "Unmatched left paren in format "
2692
                           "string";
2693
                msg = skipitem(&format, p_va, flags);
2694
                if (msg)
  Branch (2694:21): [True: 0, False: 14]
2695
                    return msg;
2696
            }
2697
            format++;
2698
            break;
2699
        }
2700
2701
    case ')':
  Branch (2701:5): [True: 0, False: 652k]
2702
        return "Unmatched right paren in format string";
2703
2704
    default:
  Branch (2704:5): [True: 115, False: 652k]
2705
err:
2706
        return "impossible<bad format char>";
2707
2708
    }
2709
2710
    *p_format = format;
2711
    return NULL;
2712
}
2713
2714
2715
#undef _PyArg_CheckPositional
2716
2717
int
2718
_PyArg_CheckPositional(const char *name, Py_ssize_t nargs,
2719
                       Py_ssize_t min, Py_ssize_t max)
2720
{
2721
    assert(min >= 0);
2722
    assert(min <= max);
2723
2724
    if (nargs < min) {
  Branch (2724:9): [True: 284, False: 6.24M]
2725
        if (name != NULL)
  Branch (2725:13): [True: 284, False: 0]
2726
            PyErr_Format(
2727
                PyExc_TypeError,
2728
                "%.200s expected %s%zd argument%s, got %zd",
2729
                name, (min == max ? 
""163
:
"at least "121
), min, min == 1 ?
""129
:
"s"155
, nargs);
  Branch (2729:24): [True: 163, False: 121]
  Branch (2729:61): [True: 129, False: 155]
2730
        else
2731
            PyErr_Format(
2732
                PyExc_TypeError,
2733
                "unpacked tuple should have %s%zd element%s,"
2734
                " but has %zd",
2735
                (min == max ? "" : "at least "), min, min == 1 ? "" : "s", nargs);
  Branch (2735:18): [True: 0, False: 0]
  Branch (2735:55): [True: 0, False: 0]
2736
        return 0;
2737
    }
2738
2739
    if (nargs == 0) {
  Branch (2739:9): [True: 52.2k, False: 6.19M]
2740
        return 1;
2741
    }
2742
2743
    if (nargs > max) {
  Branch (2743:9): [True: 109, False: 6.19M]
2744
        if (name != NULL)
  Branch (2744:13): [True: 109, False: 0]
2745
            PyErr_Format(
2746
                PyExc_TypeError,
2747
                "%.200s expected %s%zd argument%s, got %zd",
2748
                name, (min == max ? 
""18
:
"at most "91
), max, max == 1 ?
""54
:
"s"55
, nargs);
  Branch (2748:24): [True: 18, False: 91]
  Branch (2748:60): [True: 54, False: 55]
2749
        else
2750
            PyErr_Format(
2751
                PyExc_TypeError,
2752
                "unpacked tuple should have %s%zd element%s,"
2753
                " but has %zd",
2754
                (min == max ? "" : "at most "), max, max == 1 ? "" : "s", nargs);
  Branch (2754:18): [True: 0, False: 0]
  Branch (2754:54): [True: 0, False: 0]
2755
        return 0;
2756
    }
2757
2758
    return 1;
2759
}
2760
2761
static int
2762
unpack_stack(PyObject *const *args, Py_ssize_t nargs, const char *name,
2763
             Py_ssize_t min, Py_ssize_t max, va_list vargs)
2764
{
2765
    Py_ssize_t i;
2766
    PyObject **o;
2767
2768
    if (!_PyArg_CheckPositional(name, nargs, min, max)) {
  Branch (2768:9): [True: 61, False: 6.24M]
2769
        return 0;
2770
    }
2771
2772
    
for (i = 0; 6.24M
i < nargs;
i++11.4M
) {
  Branch (2772:17): [True: 11.4M, False: 6.24M]
2773
        o = va_arg(vargs, PyObject **);
2774
        *o = args[i];
2775
    }
2776
    return 1;
2777
}
2778
2779
int
2780
PyArg_UnpackTuple(PyObject *args, const char *name, Py_ssize_t min, Py_ssize_t max, ...)
2781
{
2782
    PyObject **stack;
2783
    Py_ssize_t nargs;
2784
    int retval;
2785
    va_list vargs;
2786
2787
    if (!PyTuple_Check(args)) {
  Branch (2787:9): [True: 0, False: 5.66M]
2788
        PyErr_SetString(PyExc_SystemError,
2789
            "PyArg_UnpackTuple() argument list is not a tuple");
2790
        return 0;
2791
    }
2792
    stack = _PyTuple_ITEMS(args);
2793
    nargs = PyTuple_GET_SIZE(args);
2794
2795
    va_start(vargs, max);
2796
    retval = unpack_stack(stack, nargs, name, min, max, vargs);
2797
    va_end(vargs);
2798
    return retval;
2799
}
2800
2801
int
2802
_PyArg_UnpackStack(PyObject *const *args, Py_ssize_t nargs, const char *name,
2803
                   Py_ssize_t min, Py_ssize_t max, ...)
2804
{
2805
    int retval;
2806
    va_list vargs;
2807
2808
    va_start(vargs, max);
2809
    retval = unpack_stack(args, nargs, name, min, max, vargs);
2810
    va_end(vargs);
2811
    return retval;
2812
}
2813
2814
2815
#undef _PyArg_NoKeywords
2816
#undef _PyArg_NoKwnames
2817
#undef _PyArg_NoPositional
2818
2819
/* For type constructors that don't take keyword args
2820
 *
2821
 * Sets a TypeError and returns 0 if the args/kwargs is
2822
 * not empty, returns 1 otherwise
2823
 */
2824
int
2825
_PyArg_NoKeywords(const char *funcname, PyObject *kwargs)
2826
{
2827
    if (kwargs == NULL) {
  Branch (2827:9): [True: 0, False: 58.6k]
2828
        return 1;
2829
    }
2830
    if (!PyDict_CheckExact(kwargs)) {
  Branch (2830:9): [True: 0, False: 58.6k]
2831
        PyErr_BadInternalCall();
2832
        return 0;
2833
    }
2834
    if (PyDict_GET_SIZE(kwargs) == 0) {
  Branch (2834:9): [True: 58.6k, False: 29]
2835
        return 1;
2836
    }
2837
2838
    PyErr_Format(PyExc_TypeError, "%.200s() takes no keyword arguments",
2839
                    funcname);
2840
    return 0;
2841
}
2842
2843
int
2844
_PyArg_NoPositional(const char *funcname, PyObject *args)
2845
{
2846
    if (args == NULL)
  Branch (2846:9): [True: 0, False: 11.9k]
2847
        return 1;
2848
    if (!PyTuple_CheckExact(args)) {
  Branch (2848:9): [True: 0, False: 11.9k]
2849
        PyErr_BadInternalCall();
2850
        return 0;
2851
    }
2852
    if (PyTuple_GET_SIZE(args) == 0)
  Branch (2852:9): [True: 11.9k, False: 1]
2853
        return 1;
2854
2855
    PyErr_Format(PyExc_TypeError, "%.200s() takes no positional arguments",
2856
                    funcname);
2857
    return 0;
2858
}
2859
2860
int
2861
_PyArg_NoKwnames(const char *funcname, PyObject *kwnames)
2862
{
2863
    if (kwnames == NULL) {
  Branch (2863:9): [True: 0, False: 18]
2864
        return 1;
2865
    }
2866
2867
    assert(PyTuple_CheckExact(kwnames));
2868
2869
    if (PyTuple_GET_SIZE(kwnames) == 0) {
  Branch (2869:9): [True: 0, False: 18]
2870
        return 1;
2871
    }
2872
2873
    PyErr_Format(PyExc_TypeError, "%s() takes no keyword arguments", funcname);
2874
    return 0;
2875
}
2876
2877
void
2878
_PyArg_Fini(void)
2879
{
2880
    struct _PyArg_Parser *tmp, *s = static_arg_parsers;
2881
    while (s) {
  Branch (2881:12): [True: 441, False: 103]
2882
        tmp = s->next;
2883
        s->next = NULL;
2884
        parser_clear(s);
2885
        s = tmp;
2886
    }
2887
    static_arg_parsers = NULL;
2888
}
2889
2890
#ifdef __cplusplus
2891
};
2892
#endif