• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 
2 /* System module */
3 
4 /*
5 Various bits of information used by the interpreter are collected in
6 module 'sys'.
7 Function member:
8 - exit(sts): raise SystemExit
9 Data members:
10 - stdin, stdout, stderr: standard file objects
11 - modules: the table of modules (dictionary)
12 - path: module search path (list of strings)
13 - argv: script arguments (list of strings)
14 - ps1, ps2: optional primary and secondary prompts (strings)
15 */
16 
17 #include "Python.h"
18 #include "pycore_ceval.h"         // _Py_RecursionLimitLowerWaterMark()
19 #include "pycore_initconfig.h"    // _PyStatus_EXCEPTION()
20 #include "pycore_long.h"          // _PY_LONG_MAX_STR_DIGITS_THRESHOLD
21 #include "pycore_object.h"        // _PyObject_IS_GC()
22 #include "pycore_pathconfig.h"    // _PyPathConfig_ComputeSysPath0()
23 #include "pycore_pyerrors.h"      // _PyErr_Fetch()
24 #include "pycore_pylifecycle.h"   // _PyErr_WriteUnraisableDefaultHook()
25 #include "pycore_pymem.h"         // _PyMem_SetDefaultAllocator()
26 #include "pycore_pystate.h"       // _PyThreadState_GET()
27 #include "pycore_tuple.h"         // _PyTuple_FromArray()
28 #include "pycore_structseq.h"     // PyStructSequence_InitType()
29 
30 #include "code.h"
31 #include "frameobject.h"          // PyFrame_GetBack()
32 #include "pydtrace.h"
33 #include "osdefs.h"               // DELIM
34 #include "stdlib_module_names.h"  // _Py_stdlib_module_names
35 #include <locale.h>
36 
37 #ifdef MS_WINDOWS
38 #define WIN32_LEAN_AND_MEAN
39 #include <windows.h>
40 #endif /* MS_WINDOWS */
41 
42 #ifdef MS_COREDLL
43 extern void *PyWin_DLLhModule;
44 /* A string loaded from the DLL at startup: */
45 extern const char *PyWin_DLLVersionString;
46 #endif
47 
48 /*[clinic input]
49 module sys
50 [clinic start generated code]*/
51 /*[clinic end generated code: output=da39a3ee5e6b4b0d input=3726b388feee8cea]*/
52 
53 #include "clinic/sysmodule.c.h"
54 
55 _Py_IDENTIFIER(_);
56 _Py_IDENTIFIER(__sizeof__);
57 _Py_IDENTIFIER(_xoptions);
58 _Py_IDENTIFIER(buffer);
59 _Py_IDENTIFIER(builtins);
60 _Py_IDENTIFIER(encoding);
61 _Py_IDENTIFIER(path);
62 _Py_IDENTIFIER(stdout);
63 _Py_IDENTIFIER(stderr);
64 _Py_IDENTIFIER(warnoptions);
65 _Py_IDENTIFIER(write);
66 
67 static PyObject *
sys_get_object_id(PyThreadState * tstate,_Py_Identifier * key)68 sys_get_object_id(PyThreadState *tstate, _Py_Identifier *key)
69 {
70     PyObject *sd = tstate->interp->sysdict;
71     if (sd == NULL) {
72         return NULL;
73     }
74     PyObject *exc_type, *exc_value, *exc_tb;
75     _PyErr_Fetch(tstate, &exc_type, &exc_value, &exc_tb);
76     PyObject *value = _PyDict_GetItemIdWithError(sd, key);
77     /* XXX Suppress a new exception if it was raised and restore
78      * the old one. */
79     _PyErr_Restore(tstate, exc_type, exc_value, exc_tb);
80     return value;
81 }
82 
83 PyObject *
_PySys_GetObjectId(_Py_Identifier * key)84 _PySys_GetObjectId(_Py_Identifier *key)
85 {
86     PyThreadState *tstate = _PyThreadState_GET();
87     return sys_get_object_id(tstate, key);
88 }
89 
90 static PyObject *
_PySys_GetObject(PyInterpreterState * interp,const char * name)91 _PySys_GetObject(PyInterpreterState *interp, const char *name)
92 {
93     PyObject *sysdict = interp->sysdict;
94     if (sysdict == NULL) {
95         return NULL;
96     }
97     return _PyDict_GetItemStringWithError(sysdict, name);
98 }
99 
100 PyObject *
PySys_GetObject(const char * name)101 PySys_GetObject(const char *name)
102 {
103     PyThreadState *tstate = _PyThreadState_GET();
104 
105     PyObject *exc_type, *exc_value, *exc_tb;
106     _PyErr_Fetch(tstate, &exc_type, &exc_value, &exc_tb);
107     PyObject *value = _PySys_GetObject(tstate->interp, name);
108     /* XXX Suppress a new exception if it was raised and restore
109      * the old one. */
110     _PyErr_Restore(tstate, exc_type, exc_value, exc_tb);
111     return value;
112 }
113 
114 static int
sys_set_object(PyInterpreterState * interp,PyObject * key,PyObject * v)115 sys_set_object(PyInterpreterState *interp, PyObject *key, PyObject *v)
116 {
117     if (key == NULL) {
118         return -1;
119     }
120     PyObject *sd = interp->sysdict;
121     if (v == NULL) {
122         v = _PyDict_Pop(sd, key, Py_None);
123         if (v == NULL) {
124             return -1;
125         }
126         Py_DECREF(v);
127         return 0;
128     }
129     else {
130         return PyDict_SetItem(sd, key, v);
131     }
132 }
133 
134 static int
sys_set_object_id(PyInterpreterState * interp,_Py_Identifier * key,PyObject * v)135 sys_set_object_id(PyInterpreterState *interp, _Py_Identifier *key, PyObject *v)
136 {
137     return sys_set_object(interp, _PyUnicode_FromId(key), v);
138 }
139 
140 int
_PySys_SetObjectId(_Py_Identifier * key,PyObject * v)141 _PySys_SetObjectId(_Py_Identifier *key, PyObject *v)
142 {
143     PyInterpreterState *interp = _PyInterpreterState_GET();
144     return sys_set_object_id(interp, key, v);
145 }
146 
147 static int
sys_set_object_str(PyInterpreterState * interp,const char * name,PyObject * v)148 sys_set_object_str(PyInterpreterState *interp, const char *name, PyObject *v)
149 {
150     PyObject *key = v ? PyUnicode_InternFromString(name)
151                       : PyUnicode_FromString(name);
152     int r = sys_set_object(interp, key, v);
153     Py_XDECREF(key);
154     return r;
155 }
156 
157 int
PySys_SetObject(const char * name,PyObject * v)158 PySys_SetObject(const char *name, PyObject *v)
159 {
160     PyInterpreterState *interp = _PyInterpreterState_GET();
161     return sys_set_object_str(interp, name, v);
162 }
163 
164 
165 static int
should_audit(PyInterpreterState * interp)166 should_audit(PyInterpreterState *interp)
167 {
168     /* interp must not be NULL, but test it just in case for extra safety */
169     assert(interp != NULL);
170     if (!interp) {
171         return 0;
172     }
173     return (interp->runtime->audit_hook_head
174             || interp->audit_hooks
175             || PyDTrace_AUDIT_ENABLED());
176 }
177 
178 
179 static int
sys_audit_tstate(PyThreadState * ts,const char * event,const char * argFormat,va_list vargs)180 sys_audit_tstate(PyThreadState *ts, const char *event,
181                  const char *argFormat, va_list vargs)
182 {
183     /* N format is inappropriate, because you do not know
184        whether the reference is consumed by the call.
185        Assert rather than exception for perf reasons */
186     assert(!argFormat || !strchr(argFormat, 'N'));
187 
188     if (!ts) {
189         /* Audit hooks cannot be called with a NULL thread state */
190         return 0;
191     }
192 
193     /* The current implementation cannot be called if tstate is not
194        the current Python thread state. */
195     assert(ts == _PyThreadState_GET());
196 
197     /* Early exit when no hooks are registered */
198     PyInterpreterState *is = ts->interp;
199     if (!should_audit(is)) {
200         return 0;
201     }
202 
203     PyObject *eventName = NULL;
204     PyObject *eventArgs = NULL;
205     PyObject *hooks = NULL;
206     PyObject *hook = NULL;
207     int res = -1;
208 
209     int dtrace = PyDTrace_AUDIT_ENABLED();
210 
211     PyObject *exc_type, *exc_value, *exc_tb;
212     _PyErr_Fetch(ts, &exc_type, &exc_value, &exc_tb);
213 
214     /* Initialize event args now */
215     if (argFormat && argFormat[0]) {
216         eventArgs = _Py_VaBuildValue_SizeT(argFormat, vargs);
217         if (eventArgs && !PyTuple_Check(eventArgs)) {
218             PyObject *argTuple = PyTuple_Pack(1, eventArgs);
219             Py_DECREF(eventArgs);
220             eventArgs = argTuple;
221         }
222     }
223     else {
224         eventArgs = PyTuple_New(0);
225     }
226     if (!eventArgs) {
227         goto exit;
228     }
229 
230     /* Call global hooks */
231     _Py_AuditHookEntry *e = is->runtime->audit_hook_head;
232     for (; e; e = e->next) {
233         if (e->hookCFunction(event, eventArgs, e->userData) < 0) {
234             goto exit;
235         }
236     }
237 
238     /* Dtrace USDT point */
239     if (dtrace) {
240         PyDTrace_AUDIT(event, (void *)eventArgs);
241     }
242 
243     /* Call interpreter hooks */
244     if (is->audit_hooks) {
245         eventName = PyUnicode_FromString(event);
246         if (!eventName) {
247             goto exit;
248         }
249 
250         hooks = PyObject_GetIter(is->audit_hooks);
251         if (!hooks) {
252             goto exit;
253         }
254 
255         /* Disallow tracing in hooks unless explicitly enabled */
256         ts->tracing++;
257         ts->cframe->use_tracing = 0;
258         while ((hook = PyIter_Next(hooks)) != NULL) {
259             _Py_IDENTIFIER(__cantrace__);
260             PyObject *o;
261             int canTrace = _PyObject_LookupAttrId(hook, &PyId___cantrace__, &o);
262             if (o) {
263                 canTrace = PyObject_IsTrue(o);
264                 Py_DECREF(o);
265             }
266             if (canTrace < 0) {
267                 break;
268             }
269             if (canTrace) {
270                 ts->cframe->use_tracing = (ts->c_tracefunc || ts->c_profilefunc);
271                 ts->tracing--;
272             }
273             PyObject* args[2] = {eventName, eventArgs};
274             o = _PyObject_FastCallTstate(ts, hook, args, 2);
275             if (canTrace) {
276                 ts->tracing++;
277                 ts->cframe->use_tracing = 0;
278             }
279             if (!o) {
280                 break;
281             }
282             Py_DECREF(o);
283             Py_CLEAR(hook);
284         }
285         ts->cframe->use_tracing = (ts->c_tracefunc || ts->c_profilefunc);
286         ts->tracing--;
287         if (_PyErr_Occurred(ts)) {
288             goto exit;
289         }
290     }
291 
292     res = 0;
293 
294 exit:
295     Py_XDECREF(hook);
296     Py_XDECREF(hooks);
297     Py_XDECREF(eventName);
298     Py_XDECREF(eventArgs);
299 
300     if (!res) {
301         _PyErr_Restore(ts, exc_type, exc_value, exc_tb);
302     }
303     else {
304         assert(_PyErr_Occurred(ts));
305         Py_XDECREF(exc_type);
306         Py_XDECREF(exc_value);
307         Py_XDECREF(exc_tb);
308     }
309 
310     return res;
311 }
312 
313 int
_PySys_Audit(PyThreadState * tstate,const char * event,const char * argFormat,...)314 _PySys_Audit(PyThreadState *tstate, const char *event,
315              const char *argFormat, ...)
316 {
317     va_list vargs;
318 #ifdef HAVE_STDARG_PROTOTYPES
319     va_start(vargs, argFormat);
320 #else
321     va_start(vargs);
322 #endif
323     int res = sys_audit_tstate(tstate, event, argFormat, vargs);
324     va_end(vargs);
325     return res;
326 }
327 
328 int
PySys_Audit(const char * event,const char * argFormat,...)329 PySys_Audit(const char *event, const char *argFormat, ...)
330 {
331     PyThreadState *tstate = _PyThreadState_GET();
332     va_list vargs;
333 #ifdef HAVE_STDARG_PROTOTYPES
334     va_start(vargs, argFormat);
335 #else
336     va_start(vargs);
337 #endif
338     int res = sys_audit_tstate(tstate, event, argFormat, vargs);
339     va_end(vargs);
340     return res;
341 }
342 
343 /* We expose this function primarily for our own cleanup during
344  * finalization. In general, it should not need to be called,
345  * and as such the function is not exported.
346  *
347  * Must be finalizing to clear hooks */
348 void
_PySys_ClearAuditHooks(PyThreadState * ts)349 _PySys_ClearAuditHooks(PyThreadState *ts)
350 {
351     assert(ts != NULL);
352     if (!ts) {
353         return;
354     }
355 
356     _PyRuntimeState *runtime = ts->interp->runtime;
357     PyThreadState *finalizing = _PyRuntimeState_GetFinalizing(runtime);
358     assert(finalizing == ts);
359     if (finalizing != ts) {
360         return;
361     }
362 
363     const PyConfig *config = _PyInterpreterState_GetConfig(ts->interp);
364     if (config->verbose) {
365         PySys_WriteStderr("# clear sys.audit hooks\n");
366     }
367 
368     /* Hooks can abort later hooks for this event, but cannot
369        abort the clear operation itself. */
370     _PySys_Audit(ts, "cpython._PySys_ClearAuditHooks", NULL);
371     _PyErr_Clear(ts);
372 
373     _Py_AuditHookEntry *e = runtime->audit_hook_head, *n;
374     runtime->audit_hook_head = NULL;
375     while (e) {
376         n = e->next;
377         PyMem_RawFree(e);
378         e = n;
379     }
380 }
381 
382 int
PySys_AddAuditHook(Py_AuditHookFunction hook,void * userData)383 PySys_AddAuditHook(Py_AuditHookFunction hook, void *userData)
384 {
385     /* tstate can be NULL, so access directly _PyRuntime:
386        PySys_AddAuditHook() can be called before Python is initialized. */
387     _PyRuntimeState *runtime = &_PyRuntime;
388     PyThreadState *tstate;
389     if (runtime->initialized) {
390         tstate = _PyRuntimeState_GetThreadState(runtime);
391     }
392     else {
393         tstate = NULL;
394     }
395 
396     /* Invoke existing audit hooks to allow them an opportunity to abort. */
397     /* Cannot invoke hooks until we are initialized */
398     if (tstate != NULL) {
399         if (_PySys_Audit(tstate, "sys.addaudithook", NULL) < 0) {
400             if (_PyErr_ExceptionMatches(tstate, PyExc_RuntimeError)) {
401                 /* We do not report errors derived from RuntimeError */
402                 _PyErr_Clear(tstate);
403                 return 0;
404             }
405             return -1;
406         }
407     }
408 
409     _Py_AuditHookEntry *e = runtime->audit_hook_head;
410     if (!e) {
411         e = (_Py_AuditHookEntry*)PyMem_RawMalloc(sizeof(_Py_AuditHookEntry));
412         runtime->audit_hook_head = e;
413     } else {
414         while (e->next) {
415             e = e->next;
416         }
417         e = e->next = (_Py_AuditHookEntry*)PyMem_RawMalloc(
418             sizeof(_Py_AuditHookEntry));
419     }
420 
421     if (!e) {
422         if (tstate != NULL) {
423             _PyErr_NoMemory(tstate);
424         }
425         return -1;
426     }
427 
428     e->next = NULL;
429     e->hookCFunction = (Py_AuditHookFunction)hook;
430     e->userData = userData;
431 
432     return 0;
433 }
434 
435 /*[clinic input]
436 sys.addaudithook
437 
438     hook: object
439 
440 Adds a new audit hook callback.
441 [clinic start generated code]*/
442 
443 static PyObject *
sys_addaudithook_impl(PyObject * module,PyObject * hook)444 sys_addaudithook_impl(PyObject *module, PyObject *hook)
445 /*[clinic end generated code: output=4f9c17aaeb02f44e input=0f3e191217a45e34]*/
446 {
447     PyThreadState *tstate = _PyThreadState_GET();
448 
449     /* Invoke existing audit hooks to allow them an opportunity to abort. */
450     if (_PySys_Audit(tstate, "sys.addaudithook", NULL) < 0) {
451         if (_PyErr_ExceptionMatches(tstate, PyExc_Exception)) {
452             /* We do not report errors derived from Exception */
453             _PyErr_Clear(tstate);
454             Py_RETURN_NONE;
455         }
456         return NULL;
457     }
458 
459     PyInterpreterState *interp = tstate->interp;
460     if (interp->audit_hooks == NULL) {
461         interp->audit_hooks = PyList_New(0);
462         if (interp->audit_hooks == NULL) {
463             return NULL;
464         }
465     }
466 
467     if (PyList_Append(interp->audit_hooks, hook) < 0) {
468         return NULL;
469     }
470 
471     Py_RETURN_NONE;
472 }
473 
474 PyDoc_STRVAR(audit_doc,
475 "audit(event, *args)\n\
476 \n\
477 Passes the event to any audit hooks that are attached.");
478 
479 static PyObject *
sys_audit(PyObject * self,PyObject * const * args,Py_ssize_t argc)480 sys_audit(PyObject *self, PyObject *const *args, Py_ssize_t argc)
481 {
482     PyThreadState *tstate = _PyThreadState_GET();
483     _Py_EnsureTstateNotNULL(tstate);
484 
485     if (argc == 0) {
486         _PyErr_SetString(tstate, PyExc_TypeError,
487                          "audit() missing 1 required positional argument: "
488                          "'event'");
489         return NULL;
490     }
491 
492     if (!should_audit(tstate->interp)) {
493         Py_RETURN_NONE;
494     }
495 
496     PyObject *auditEvent = args[0];
497     if (!auditEvent) {
498         _PyErr_SetString(tstate, PyExc_TypeError,
499                          "expected str for argument 'event'");
500         return NULL;
501     }
502     if (!PyUnicode_Check(auditEvent)) {
503         _PyErr_Format(tstate, PyExc_TypeError,
504                       "expected str for argument 'event', not %.200s",
505                       Py_TYPE(auditEvent)->tp_name);
506         return NULL;
507     }
508     const char *event = PyUnicode_AsUTF8(auditEvent);
509     if (!event) {
510         return NULL;
511     }
512 
513     PyObject *auditArgs = _PyTuple_FromArray(args + 1, argc - 1);
514     if (!auditArgs) {
515         return NULL;
516     }
517 
518     int res = _PySys_Audit(tstate, event, "O", auditArgs);
519     Py_DECREF(auditArgs);
520 
521     if (res < 0) {
522         return NULL;
523     }
524 
525     Py_RETURN_NONE;
526 }
527 
528 
529 static PyObject *
sys_breakpointhook(PyObject * self,PyObject * const * args,Py_ssize_t nargs,PyObject * keywords)530 sys_breakpointhook(PyObject *self, PyObject *const *args, Py_ssize_t nargs, PyObject *keywords)
531 {
532     PyThreadState *tstate = _PyThreadState_GET();
533     assert(!_PyErr_Occurred(tstate));
534     char *envar = Py_GETENV("PYTHONBREAKPOINT");
535 
536     if (envar == NULL || strlen(envar) == 0) {
537         envar = "pdb.set_trace";
538     }
539     else if (!strcmp(envar, "0")) {
540         /* The breakpoint is explicitly no-op'd. */
541         Py_RETURN_NONE;
542     }
543     /* According to POSIX the string returned by getenv() might be invalidated
544      * or the string content might be overwritten by a subsequent call to
545      * getenv().  Since importing a module can performs the getenv() calls,
546      * we need to save a copy of envar. */
547     envar = _PyMem_RawStrdup(envar);
548     if (envar == NULL) {
549         _PyErr_NoMemory(tstate);
550         return NULL;
551     }
552     const char *last_dot = strrchr(envar, '.');
553     const char *attrname = NULL;
554     PyObject *modulepath = NULL;
555 
556     if (last_dot == NULL) {
557         /* The breakpoint is a built-in, e.g. PYTHONBREAKPOINT=int */
558         modulepath = PyUnicode_FromString("builtins");
559         attrname = envar;
560     }
561     else if (last_dot != envar) {
562         /* Split on the last dot; */
563         modulepath = PyUnicode_FromStringAndSize(envar, last_dot - envar);
564         attrname = last_dot + 1;
565     }
566     else {
567         goto warn;
568     }
569     if (modulepath == NULL) {
570         PyMem_RawFree(envar);
571         return NULL;
572     }
573 
574     PyObject *module = PyImport_Import(modulepath);
575     Py_DECREF(modulepath);
576 
577     if (module == NULL) {
578         if (_PyErr_ExceptionMatches(tstate, PyExc_ImportError)) {
579             goto warn;
580         }
581         PyMem_RawFree(envar);
582         return NULL;
583     }
584 
585     PyObject *hook = PyObject_GetAttrString(module, attrname);
586     Py_DECREF(module);
587 
588     if (hook == NULL) {
589         if (_PyErr_ExceptionMatches(tstate, PyExc_AttributeError)) {
590             goto warn;
591         }
592         PyMem_RawFree(envar);
593         return NULL;
594     }
595     PyMem_RawFree(envar);
596     PyObject *retval = PyObject_Vectorcall(hook, args, nargs, keywords);
597     Py_DECREF(hook);
598     return retval;
599 
600   warn:
601     /* If any of the imports went wrong, then warn and ignore. */
602     _PyErr_Clear(tstate);
603     int status = PyErr_WarnFormat(
604         PyExc_RuntimeWarning, 0,
605         "Ignoring unimportable $PYTHONBREAKPOINT: \"%s\"", envar);
606     PyMem_RawFree(envar);
607     if (status < 0) {
608         /* Printing the warning raised an exception. */
609         return NULL;
610     }
611     /* The warning was (probably) issued. */
612     Py_RETURN_NONE;
613 }
614 
615 PyDoc_STRVAR(breakpointhook_doc,
616 "breakpointhook(*args, **kws)\n"
617 "\n"
618 "This hook function is called by built-in breakpoint().\n"
619 );
620 
621 /* Write repr(o) to sys.stdout using sys.stdout.encoding and 'backslashreplace'
622    error handler. If sys.stdout has a buffer attribute, use
623    sys.stdout.buffer.write(encoded), otherwise redecode the string and use
624    sys.stdout.write(redecoded).
625 
626    Helper function for sys_displayhook(). */
627 static int
sys_displayhook_unencodable(PyObject * outf,PyObject * o)628 sys_displayhook_unencodable(PyObject *outf, PyObject *o)
629 {
630     PyObject *stdout_encoding = NULL;
631     PyObject *encoded, *escaped_str, *repr_str, *buffer, *result;
632     const char *stdout_encoding_str;
633     int ret;
634 
635     stdout_encoding = _PyObject_GetAttrId(outf, &PyId_encoding);
636     if (stdout_encoding == NULL)
637         goto error;
638     stdout_encoding_str = PyUnicode_AsUTF8(stdout_encoding);
639     if (stdout_encoding_str == NULL)
640         goto error;
641 
642     repr_str = PyObject_Repr(o);
643     if (repr_str == NULL)
644         goto error;
645     encoded = PyUnicode_AsEncodedString(repr_str,
646                                         stdout_encoding_str,
647                                         "backslashreplace");
648     Py_DECREF(repr_str);
649     if (encoded == NULL)
650         goto error;
651 
652     if (_PyObject_LookupAttrId(outf, &PyId_buffer, &buffer) < 0) {
653         Py_DECREF(encoded);
654         goto error;
655     }
656     if (buffer) {
657         result = _PyObject_CallMethodIdOneArg(buffer, &PyId_write, encoded);
658         Py_DECREF(buffer);
659         Py_DECREF(encoded);
660         if (result == NULL)
661             goto error;
662         Py_DECREF(result);
663     }
664     else {
665         escaped_str = PyUnicode_FromEncodedObject(encoded,
666                                                   stdout_encoding_str,
667                                                   "strict");
668         Py_DECREF(encoded);
669         if (PyFile_WriteObject(escaped_str, outf, Py_PRINT_RAW) != 0) {
670             Py_DECREF(escaped_str);
671             goto error;
672         }
673         Py_DECREF(escaped_str);
674     }
675     ret = 0;
676     goto finally;
677 
678 error:
679     ret = -1;
680 finally:
681     Py_XDECREF(stdout_encoding);
682     return ret;
683 }
684 
685 /*[clinic input]
686 sys.displayhook
687 
688     object as o: object
689     /
690 
691 Print an object to sys.stdout and also save it in builtins._
692 [clinic start generated code]*/
693 
694 static PyObject *
sys_displayhook(PyObject * module,PyObject * o)695 sys_displayhook(PyObject *module, PyObject *o)
696 /*[clinic end generated code: output=347477d006df92ed input=08ba730166d7ef72]*/
697 {
698     PyObject *outf;
699     PyObject *builtins;
700     static PyObject *newline = NULL;
701     PyThreadState *tstate = _PyThreadState_GET();
702 
703     builtins = _PyImport_GetModuleId(&PyId_builtins);
704     if (builtins == NULL) {
705         if (!_PyErr_Occurred(tstate)) {
706             _PyErr_SetString(tstate, PyExc_RuntimeError,
707                              "lost builtins module");
708         }
709         return NULL;
710     }
711     Py_DECREF(builtins);
712 
713     /* Print value except if None */
714     /* After printing, also assign to '_' */
715     /* Before, set '_' to None to avoid recursion */
716     if (o == Py_None) {
717         Py_RETURN_NONE;
718     }
719     if (_PyObject_SetAttrId(builtins, &PyId__, Py_None) != 0)
720         return NULL;
721     outf = sys_get_object_id(tstate, &PyId_stdout);
722     if (outf == NULL || outf == Py_None) {
723         _PyErr_SetString(tstate, PyExc_RuntimeError, "lost sys.stdout");
724         return NULL;
725     }
726     if (PyFile_WriteObject(o, outf, 0) != 0) {
727         if (_PyErr_ExceptionMatches(tstate, PyExc_UnicodeEncodeError)) {
728             int err;
729             /* repr(o) is not encodable to sys.stdout.encoding with
730              * sys.stdout.errors error handler (which is probably 'strict') */
731             _PyErr_Clear(tstate);
732             err = sys_displayhook_unencodable(outf, o);
733             if (err) {
734                 return NULL;
735             }
736         }
737         else {
738             return NULL;
739         }
740     }
741     if (newline == NULL) {
742         newline = PyUnicode_FromString("\n");
743         if (newline == NULL)
744             return NULL;
745     }
746     if (PyFile_WriteObject(newline, outf, Py_PRINT_RAW) != 0)
747         return NULL;
748     if (_PyObject_SetAttrId(builtins, &PyId__, o) != 0)
749         return NULL;
750     Py_RETURN_NONE;
751 }
752 
753 
754 /*[clinic input]
755 sys.excepthook
756 
757     exctype:   object
758     value:     object
759     traceback: object
760     /
761 
762 Handle an exception by displaying it with a traceback on sys.stderr.
763 [clinic start generated code]*/
764 
765 static PyObject *
sys_excepthook_impl(PyObject * module,PyObject * exctype,PyObject * value,PyObject * traceback)766 sys_excepthook_impl(PyObject *module, PyObject *exctype, PyObject *value,
767                     PyObject *traceback)
768 /*[clinic end generated code: output=18d99fdda21b6b5e input=ecf606fa826f19d9]*/
769 {
770     PyErr_Display(exctype, value, traceback);
771     Py_RETURN_NONE;
772 }
773 
774 
775 /*[clinic input]
776 sys.exc_info
777 
778 Return current exception information: (type, value, traceback).
779 
780 Return information about the most recent exception caught by an except
781 clause in the current stack frame or in an older stack frame.
782 [clinic start generated code]*/
783 
784 static PyObject *
sys_exc_info_impl(PyObject * module)785 sys_exc_info_impl(PyObject *module)
786 /*[clinic end generated code: output=3afd0940cf3a4d30 input=b5c5bf077788a3e5]*/
787 {
788     _PyErr_StackItem *err_info = _PyErr_GetTopmostException(_PyThreadState_GET());
789     return Py_BuildValue(
790         "(OOO)",
791         err_info->exc_type != NULL ? err_info->exc_type : Py_None,
792         err_info->exc_value != NULL ? err_info->exc_value : Py_None,
793         err_info->exc_traceback != NULL ?
794             err_info->exc_traceback : Py_None);
795 }
796 
797 
798 /*[clinic input]
799 sys.unraisablehook
800 
801     unraisable: object
802     /
803 
804 Handle an unraisable exception.
805 
806 The unraisable argument has the following attributes:
807 
808 * exc_type: Exception type.
809 * exc_value: Exception value, can be None.
810 * exc_traceback: Exception traceback, can be None.
811 * err_msg: Error message, can be None.
812 * object: Object causing the exception, can be None.
813 [clinic start generated code]*/
814 
815 static PyObject *
sys_unraisablehook(PyObject * module,PyObject * unraisable)816 sys_unraisablehook(PyObject *module, PyObject *unraisable)
817 /*[clinic end generated code: output=bb92838b32abaa14 input=ec3af148294af8d3]*/
818 {
819     return _PyErr_WriteUnraisableDefaultHook(unraisable);
820 }
821 
822 
823 /*[clinic input]
824 sys.exit
825 
826     status: object = None
827     /
828 
829 Exit the interpreter by raising SystemExit(status).
830 
831 If the status is omitted or None, it defaults to zero (i.e., success).
832 If the status is an integer, it will be used as the system exit status.
833 If it is another kind of object, it will be printed and the system
834 exit status will be one (i.e., failure).
835 [clinic start generated code]*/
836 
837 static PyObject *
sys_exit_impl(PyObject * module,PyObject * status)838 sys_exit_impl(PyObject *module, PyObject *status)
839 /*[clinic end generated code: output=13870986c1ab2ec0 input=b86ca9497baa94f2]*/
840 {
841     /* Raise SystemExit so callers may catch it or clean up. */
842     PyErr_SetObject(PyExc_SystemExit, status);
843     return NULL;
844 }
845 
846 
847 
848 /*[clinic input]
849 sys.getdefaultencoding
850 
851 Return the current default encoding used by the Unicode implementation.
852 [clinic start generated code]*/
853 
854 static PyObject *
sys_getdefaultencoding_impl(PyObject * module)855 sys_getdefaultencoding_impl(PyObject *module)
856 /*[clinic end generated code: output=256d19dfcc0711e6 input=d416856ddbef6909]*/
857 {
858     return PyUnicode_FromString(PyUnicode_GetDefaultEncoding());
859 }
860 
861 /*[clinic input]
862 sys.getfilesystemencoding
863 
864 Return the encoding used to convert Unicode filenames to OS filenames.
865 [clinic start generated code]*/
866 
867 static PyObject *
sys_getfilesystemencoding_impl(PyObject * module)868 sys_getfilesystemencoding_impl(PyObject *module)
869 /*[clinic end generated code: output=1dc4bdbe9be44aa7 input=8475f8649b8c7d8c]*/
870 {
871     PyInterpreterState *interp = _PyInterpreterState_GET();
872     const PyConfig *config = _PyInterpreterState_GetConfig(interp);
873     return PyUnicode_FromWideChar(config->filesystem_encoding, -1);
874 }
875 
876 /*[clinic input]
877 sys.getfilesystemencodeerrors
878 
879 Return the error mode used Unicode to OS filename conversion.
880 [clinic start generated code]*/
881 
882 static PyObject *
sys_getfilesystemencodeerrors_impl(PyObject * module)883 sys_getfilesystemencodeerrors_impl(PyObject *module)
884 /*[clinic end generated code: output=ba77b36bbf7c96f5 input=22a1e8365566f1e5]*/
885 {
886     PyInterpreterState *interp = _PyInterpreterState_GET();
887     const PyConfig *config = _PyInterpreterState_GetConfig(interp);
888     return PyUnicode_FromWideChar(config->filesystem_errors, -1);
889 }
890 
891 /*[clinic input]
892 sys.intern
893 
894     string as s: unicode
895     /
896 
897 ``Intern'' the given string.
898 
899 This enters the string in the (global) table of interned strings whose
900 purpose is to speed up dictionary lookups. Return the string itself or
901 the previously interned string object with the same value.
902 [clinic start generated code]*/
903 
904 static PyObject *
sys_intern_impl(PyObject * module,PyObject * s)905 sys_intern_impl(PyObject *module, PyObject *s)
906 /*[clinic end generated code: output=be680c24f5c9e5d6 input=849483c006924e2f]*/
907 {
908     if (PyUnicode_CheckExact(s)) {
909         Py_INCREF(s);
910         PyUnicode_InternInPlace(&s);
911         return s;
912     }
913     else {
914         PyErr_Format(PyExc_TypeError,
915                      "can't intern %.400s", Py_TYPE(s)->tp_name);
916         return NULL;
917     }
918 }
919 
920 
921 /*
922  * Cached interned string objects used for calling the profile and
923  * trace functions.  Initialized by trace_init().
924  */
925 static PyObject *whatstrings[8] = {NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL};
926 
927 static int
trace_init(void)928 trace_init(void)
929 {
930     static const char * const whatnames[8] = {
931         "call", "exception", "line", "return",
932         "c_call", "c_exception", "c_return",
933         "opcode"
934     };
935     PyObject *name;
936     int i;
937     for (i = 0; i < 8; ++i) {
938         if (whatstrings[i] == NULL) {
939             name = PyUnicode_InternFromString(whatnames[i]);
940             if (name == NULL)
941                 return -1;
942             whatstrings[i] = name;
943         }
944     }
945     return 0;
946 }
947 
948 
949 static PyObject *
call_trampoline(PyThreadState * tstate,PyObject * callback,PyFrameObject * frame,int what,PyObject * arg)950 call_trampoline(PyThreadState *tstate, PyObject* callback,
951                 PyFrameObject *frame, int what, PyObject *arg)
952 {
953     if (PyFrame_FastToLocalsWithError(frame) < 0) {
954         return NULL;
955     }
956 
957     PyObject *stack[3];
958     stack[0] = (PyObject *)frame;
959     stack[1] = whatstrings[what];
960     stack[2] = (arg != NULL) ? arg : Py_None;
961 
962     /* call the Python-level function */
963     PyObject *result = _PyObject_FastCallTstate(tstate, callback, stack, 3);
964 
965     PyFrame_LocalsToFast(frame, 1);
966     if (result == NULL) {
967         PyTraceBack_Here(frame);
968     }
969 
970     return result;
971 }
972 
973 static int
profile_trampoline(PyObject * self,PyFrameObject * frame,int what,PyObject * arg)974 profile_trampoline(PyObject *self, PyFrameObject *frame,
975                    int what, PyObject *arg)
976 {
977     if (arg == NULL) {
978         arg = Py_None;
979     }
980 
981     PyThreadState *tstate = _PyThreadState_GET();
982     PyObject *result = call_trampoline(tstate, self, frame, what, arg);
983     if (result == NULL) {
984         _PyEval_SetProfile(tstate, NULL, NULL);
985         return -1;
986     }
987 
988     Py_DECREF(result);
989     return 0;
990 }
991 
992 static int
trace_trampoline(PyObject * self,PyFrameObject * frame,int what,PyObject * arg)993 trace_trampoline(PyObject *self, PyFrameObject *frame,
994                  int what, PyObject *arg)
995 {
996     PyObject *callback;
997     if (what == PyTrace_CALL) {
998         callback = self;
999     }
1000     else {
1001         callback = frame->f_trace;
1002     }
1003     if (callback == NULL) {
1004         return 0;
1005     }
1006 
1007     PyThreadState *tstate = _PyThreadState_GET();
1008     PyObject *result = call_trampoline(tstate, callback, frame, what, arg);
1009     if (result == NULL) {
1010         _PyEval_SetTrace(tstate, NULL, NULL);
1011         Py_CLEAR(frame->f_trace);
1012         return -1;
1013     }
1014 
1015     if (result != Py_None) {
1016         Py_XSETREF(frame->f_trace, result);
1017     }
1018     else {
1019         Py_DECREF(result);
1020     }
1021     return 0;
1022 }
1023 
1024 static PyObject *
sys_settrace(PyObject * self,PyObject * args)1025 sys_settrace(PyObject *self, PyObject *args)
1026 {
1027     if (trace_init() == -1) {
1028         return NULL;
1029     }
1030 
1031     PyThreadState *tstate = _PyThreadState_GET();
1032     if (args == Py_None) {
1033         if (_PyEval_SetTrace(tstate, NULL, NULL) < 0) {
1034             return NULL;
1035         }
1036     }
1037     else {
1038         if (_PyEval_SetTrace(tstate, trace_trampoline, args) < 0) {
1039             return NULL;
1040         }
1041     }
1042     Py_RETURN_NONE;
1043 }
1044 
1045 PyDoc_STRVAR(settrace_doc,
1046 "settrace(function)\n\
1047 \n\
1048 Set the global debug tracing function.  It will be called on each\n\
1049 function call.  See the debugger chapter in the library manual."
1050 );
1051 
1052 /*[clinic input]
1053 sys.gettrace
1054 
1055 Return the global debug tracing function set with sys.settrace.
1056 
1057 See the debugger chapter in the library manual.
1058 [clinic start generated code]*/
1059 
1060 static PyObject *
sys_gettrace_impl(PyObject * module)1061 sys_gettrace_impl(PyObject *module)
1062 /*[clinic end generated code: output=e97e3a4d8c971b6e input=373b51bb2147f4d8]*/
1063 {
1064     PyThreadState *tstate = _PyThreadState_GET();
1065     PyObject *temp = tstate->c_traceobj;
1066 
1067     if (temp == NULL)
1068         temp = Py_None;
1069     Py_INCREF(temp);
1070     return temp;
1071 }
1072 
1073 static PyObject *
sys_setprofile(PyObject * self,PyObject * args)1074 sys_setprofile(PyObject *self, PyObject *args)
1075 {
1076     if (trace_init() == -1) {
1077         return NULL;
1078     }
1079 
1080     PyThreadState *tstate = _PyThreadState_GET();
1081     if (args == Py_None) {
1082         if (_PyEval_SetProfile(tstate, NULL, NULL) < 0) {
1083             return NULL;
1084         }
1085     }
1086     else {
1087         if (_PyEval_SetProfile(tstate, profile_trampoline, args) < 0) {
1088             return NULL;
1089         }
1090     }
1091     Py_RETURN_NONE;
1092 }
1093 
1094 PyDoc_STRVAR(setprofile_doc,
1095 "setprofile(function)\n\
1096 \n\
1097 Set the profiling function.  It will be called on each function call\n\
1098 and return.  See the profiler chapter in the library manual."
1099 );
1100 
1101 /*[clinic input]
1102 sys.getprofile
1103 
1104 Return the profiling function set with sys.setprofile.
1105 
1106 See the profiler chapter in the library manual.
1107 [clinic start generated code]*/
1108 
1109 static PyObject *
sys_getprofile_impl(PyObject * module)1110 sys_getprofile_impl(PyObject *module)
1111 /*[clinic end generated code: output=579b96b373448188 input=1b3209d89a32965d]*/
1112 {
1113     PyThreadState *tstate = _PyThreadState_GET();
1114     PyObject *temp = tstate->c_profileobj;
1115 
1116     if (temp == NULL)
1117         temp = Py_None;
1118     Py_INCREF(temp);
1119     return temp;
1120 }
1121 
1122 
1123 /*[clinic input]
1124 sys.setswitchinterval
1125 
1126     interval: double
1127     /
1128 
1129 Set the ideal thread switching delay inside the Python interpreter.
1130 
1131 The actual frequency of switching threads can be lower if the
1132 interpreter executes long sequences of uninterruptible code
1133 (this is implementation-specific and workload-dependent).
1134 
1135 The parameter must represent the desired switching delay in seconds
1136 A typical value is 0.005 (5 milliseconds).
1137 [clinic start generated code]*/
1138 
1139 static PyObject *
sys_setswitchinterval_impl(PyObject * module,double interval)1140 sys_setswitchinterval_impl(PyObject *module, double interval)
1141 /*[clinic end generated code: output=65a19629e5153983 input=561b477134df91d9]*/
1142 {
1143     if (interval <= 0.0) {
1144         PyErr_SetString(PyExc_ValueError,
1145                         "switch interval must be strictly positive");
1146         return NULL;
1147     }
1148     _PyEval_SetSwitchInterval((unsigned long) (1e6 * interval));
1149     Py_RETURN_NONE;
1150 }
1151 
1152 
1153 /*[clinic input]
1154 sys.getswitchinterval -> double
1155 
1156 Return the current thread switch interval; see sys.setswitchinterval().
1157 [clinic start generated code]*/
1158 
1159 static double
sys_getswitchinterval_impl(PyObject * module)1160 sys_getswitchinterval_impl(PyObject *module)
1161 /*[clinic end generated code: output=a38c277c85b5096d input=bdf9d39c0ebbbb6f]*/
1162 {
1163     return 1e-6 * _PyEval_GetSwitchInterval();
1164 }
1165 
1166 /*[clinic input]
1167 sys.setrecursionlimit
1168 
1169     limit as new_limit: int
1170     /
1171 
1172 Set the maximum depth of the Python interpreter stack to n.
1173 
1174 This limit prevents infinite recursion from causing an overflow of the C
1175 stack and crashing Python.  The highest possible limit is platform-
1176 dependent.
1177 [clinic start generated code]*/
1178 
1179 static PyObject *
sys_setrecursionlimit_impl(PyObject * module,int new_limit)1180 sys_setrecursionlimit_impl(PyObject *module, int new_limit)
1181 /*[clinic end generated code: output=35e1c64754800ace input=b0f7a23393924af3]*/
1182 {
1183     PyThreadState *tstate = _PyThreadState_GET();
1184 
1185     if (new_limit < 1) {
1186         _PyErr_SetString(tstate, PyExc_ValueError,
1187                          "recursion limit must be greater or equal than 1");
1188         return NULL;
1189     }
1190 
1191     /* Issue #25274: When the recursion depth hits the recursion limit in
1192        _Py_CheckRecursiveCall(), the overflowed flag of the thread state is
1193        set to 1 and a RecursionError is raised. The overflowed flag is reset
1194        to 0 when the recursion depth goes below the low-water mark: see
1195        Py_LeaveRecursiveCall().
1196 
1197        Reject too low new limit if the current recursion depth is higher than
1198        the new low-water mark. Otherwise it may not be possible anymore to
1199        reset the overflowed flag to 0. */
1200     if (tstate->recursion_depth >= new_limit) {
1201         _PyErr_Format(tstate, PyExc_RecursionError,
1202                       "cannot set the recursion limit to %i at "
1203                       "the recursion depth %i: the limit is too low",
1204                       new_limit, tstate->recursion_depth);
1205         return NULL;
1206     }
1207 
1208     Py_SetRecursionLimit(new_limit);
1209     Py_RETURN_NONE;
1210 }
1211 
1212 /*[clinic input]
1213 sys.set_coroutine_origin_tracking_depth
1214 
1215   depth: int
1216 
1217 Enable or disable origin tracking for coroutine objects in this thread.
1218 
1219 Coroutine objects will track 'depth' frames of traceback information
1220 about where they came from, available in their cr_origin attribute.
1221 
1222 Set a depth of 0 to disable.
1223 [clinic start generated code]*/
1224 
1225 static PyObject *
sys_set_coroutine_origin_tracking_depth_impl(PyObject * module,int depth)1226 sys_set_coroutine_origin_tracking_depth_impl(PyObject *module, int depth)
1227 /*[clinic end generated code: output=0a2123c1cc6759c5 input=a1d0a05f89d2c426]*/
1228 {
1229     PyThreadState *tstate = _PyThreadState_GET();
1230     if (depth < 0) {
1231         _PyErr_SetString(tstate, PyExc_ValueError, "depth must be >= 0");
1232         return NULL;
1233     }
1234     _PyEval_SetCoroutineOriginTrackingDepth(tstate, depth);
1235     Py_RETURN_NONE;
1236 }
1237 
1238 /*[clinic input]
1239 sys.get_coroutine_origin_tracking_depth -> int
1240 
1241 Check status of origin tracking for coroutine objects in this thread.
1242 [clinic start generated code]*/
1243 
1244 static int
sys_get_coroutine_origin_tracking_depth_impl(PyObject * module)1245 sys_get_coroutine_origin_tracking_depth_impl(PyObject *module)
1246 /*[clinic end generated code: output=3699f7be95a3afb8 input=335266a71205b61a]*/
1247 {
1248     return _PyEval_GetCoroutineOriginTrackingDepth();
1249 }
1250 
1251 static PyTypeObject AsyncGenHooksType;
1252 
1253 PyDoc_STRVAR(asyncgen_hooks_doc,
1254 "asyncgen_hooks\n\
1255 \n\
1256 A named tuple providing information about asynchronous\n\
1257 generators hooks.  The attributes are read only.");
1258 
1259 static PyStructSequence_Field asyncgen_hooks_fields[] = {
1260     {"firstiter", "Hook to intercept first iteration"},
1261     {"finalizer", "Hook to intercept finalization"},
1262     {0}
1263 };
1264 
1265 static PyStructSequence_Desc asyncgen_hooks_desc = {
1266     "asyncgen_hooks",          /* name */
1267     asyncgen_hooks_doc,        /* doc */
1268     asyncgen_hooks_fields ,    /* fields */
1269     2
1270 };
1271 
1272 static PyObject *
sys_set_asyncgen_hooks(PyObject * self,PyObject * args,PyObject * kw)1273 sys_set_asyncgen_hooks(PyObject *self, PyObject *args, PyObject *kw)
1274 {
1275     static char *keywords[] = {"firstiter", "finalizer", NULL};
1276     PyObject *firstiter = NULL;
1277     PyObject *finalizer = NULL;
1278 
1279     if (!PyArg_ParseTupleAndKeywords(
1280             args, kw, "|OO", keywords,
1281             &firstiter, &finalizer)) {
1282         return NULL;
1283     }
1284 
1285     if (finalizer && finalizer != Py_None) {
1286         if (!PyCallable_Check(finalizer)) {
1287             PyErr_Format(PyExc_TypeError,
1288                          "callable finalizer expected, got %.50s",
1289                          Py_TYPE(finalizer)->tp_name);
1290             return NULL;
1291         }
1292         if (_PyEval_SetAsyncGenFinalizer(finalizer) < 0) {
1293             return NULL;
1294         }
1295     }
1296     else if (finalizer == Py_None && _PyEval_SetAsyncGenFinalizer(NULL) < 0) {
1297         return NULL;
1298     }
1299 
1300     if (firstiter && firstiter != Py_None) {
1301         if (!PyCallable_Check(firstiter)) {
1302             PyErr_Format(PyExc_TypeError,
1303                          "callable firstiter expected, got %.50s",
1304                          Py_TYPE(firstiter)->tp_name);
1305             return NULL;
1306         }
1307         if (_PyEval_SetAsyncGenFirstiter(firstiter) < 0) {
1308             return NULL;
1309         }
1310     }
1311     else if (firstiter == Py_None && _PyEval_SetAsyncGenFirstiter(NULL) < 0) {
1312         return NULL;
1313     }
1314 
1315     Py_RETURN_NONE;
1316 }
1317 
1318 PyDoc_STRVAR(set_asyncgen_hooks_doc,
1319 "set_asyncgen_hooks(* [, firstiter] [, finalizer])\n\
1320 \n\
1321 Set a finalizer for async generators objects."
1322 );
1323 
1324 /*[clinic input]
1325 sys.get_asyncgen_hooks
1326 
1327 Return the installed asynchronous generators hooks.
1328 
1329 This returns a namedtuple of the form (firstiter, finalizer).
1330 [clinic start generated code]*/
1331 
1332 static PyObject *
sys_get_asyncgen_hooks_impl(PyObject * module)1333 sys_get_asyncgen_hooks_impl(PyObject *module)
1334 /*[clinic end generated code: output=53a253707146f6cf input=3676b9ea62b14625]*/
1335 {
1336     PyObject *res;
1337     PyObject *firstiter = _PyEval_GetAsyncGenFirstiter();
1338     PyObject *finalizer = _PyEval_GetAsyncGenFinalizer();
1339 
1340     res = PyStructSequence_New(&AsyncGenHooksType);
1341     if (res == NULL) {
1342         return NULL;
1343     }
1344 
1345     if (firstiter == NULL) {
1346         firstiter = Py_None;
1347     }
1348 
1349     if (finalizer == NULL) {
1350         finalizer = Py_None;
1351     }
1352 
1353     Py_INCREF(firstiter);
1354     PyStructSequence_SET_ITEM(res, 0, firstiter);
1355 
1356     Py_INCREF(finalizer);
1357     PyStructSequence_SET_ITEM(res, 1, finalizer);
1358 
1359     return res;
1360 }
1361 
1362 
1363 static PyTypeObject Hash_InfoType;
1364 
1365 PyDoc_STRVAR(hash_info_doc,
1366 "hash_info\n\
1367 \n\
1368 A named tuple providing parameters used for computing\n\
1369 hashes. The attributes are read only.");
1370 
1371 static PyStructSequence_Field hash_info_fields[] = {
1372     {"width", "width of the type used for hashing, in bits"},
1373     {"modulus", "prime number giving the modulus on which the hash "
1374                 "function is based"},
1375     {"inf", "value to be used for hash of a positive infinity"},
1376     {"nan", "value to be used for hash of a nan"},
1377     {"imag", "multiplier used for the imaginary part of a complex number"},
1378     {"algorithm", "name of the algorithm for hashing of str, bytes and "
1379                   "memoryviews"},
1380     {"hash_bits", "internal output size of hash algorithm"},
1381     {"seed_bits", "seed size of hash algorithm"},
1382     {"cutoff", "small string optimization cutoff"},
1383     {NULL, NULL}
1384 };
1385 
1386 static PyStructSequence_Desc hash_info_desc = {
1387     "sys.hash_info",
1388     hash_info_doc,
1389     hash_info_fields,
1390     9,
1391 };
1392 
1393 static PyObject *
get_hash_info(PyThreadState * tstate)1394 get_hash_info(PyThreadState *tstate)
1395 {
1396     PyObject *hash_info;
1397     int field = 0;
1398     PyHash_FuncDef *hashfunc;
1399     hash_info = PyStructSequence_New(&Hash_InfoType);
1400     if (hash_info == NULL)
1401         return NULL;
1402     hashfunc = PyHash_GetFuncDef();
1403     PyStructSequence_SET_ITEM(hash_info, field++,
1404                               PyLong_FromLong(8*sizeof(Py_hash_t)));
1405     PyStructSequence_SET_ITEM(hash_info, field++,
1406                               PyLong_FromSsize_t(_PyHASH_MODULUS));
1407     PyStructSequence_SET_ITEM(hash_info, field++,
1408                               PyLong_FromLong(_PyHASH_INF));
1409     PyStructSequence_SET_ITEM(hash_info, field++,
1410                               PyLong_FromLong(0));  // This is no longer used
1411     PyStructSequence_SET_ITEM(hash_info, field++,
1412                               PyLong_FromLong(_PyHASH_IMAG));
1413     PyStructSequence_SET_ITEM(hash_info, field++,
1414                               PyUnicode_FromString(hashfunc->name));
1415     PyStructSequence_SET_ITEM(hash_info, field++,
1416                               PyLong_FromLong(hashfunc->hash_bits));
1417     PyStructSequence_SET_ITEM(hash_info, field++,
1418                               PyLong_FromLong(hashfunc->seed_bits));
1419     PyStructSequence_SET_ITEM(hash_info, field++,
1420                               PyLong_FromLong(Py_HASH_CUTOFF));
1421     if (_PyErr_Occurred(tstate)) {
1422         Py_CLEAR(hash_info);
1423         return NULL;
1424     }
1425     return hash_info;
1426 }
1427 /*[clinic input]
1428 sys.getrecursionlimit
1429 
1430 Return the current value of the recursion limit.
1431 
1432 The recursion limit is the maximum depth of the Python interpreter
1433 stack.  This limit prevents infinite recursion from causing an overflow
1434 of the C stack and crashing Python.
1435 [clinic start generated code]*/
1436 
1437 static PyObject *
sys_getrecursionlimit_impl(PyObject * module)1438 sys_getrecursionlimit_impl(PyObject *module)
1439 /*[clinic end generated code: output=d571fb6b4549ef2e input=1c6129fd2efaeea8]*/
1440 {
1441     return PyLong_FromLong(Py_GetRecursionLimit());
1442 }
1443 
1444 #ifdef MS_WINDOWS
1445 
1446 static PyTypeObject WindowsVersionType = {0, 0, 0, 0, 0, 0};
1447 
1448 static PyStructSequence_Field windows_version_fields[] = {
1449     {"major", "Major version number"},
1450     {"minor", "Minor version number"},
1451     {"build", "Build number"},
1452     {"platform", "Operating system platform"},
1453     {"service_pack", "Latest Service Pack installed on the system"},
1454     {"service_pack_major", "Service Pack major version number"},
1455     {"service_pack_minor", "Service Pack minor version number"},
1456     {"suite_mask", "Bit mask identifying available product suites"},
1457     {"product_type", "System product type"},
1458     {"platform_version", "Diagnostic version number"},
1459     {0}
1460 };
1461 
1462 static PyStructSequence_Desc windows_version_desc = {
1463     "sys.getwindowsversion",       /* name */
1464     sys_getwindowsversion__doc__,  /* doc */
1465     windows_version_fields,        /* fields */
1466     5                              /* For backward compatibility,
1467                                       only the first 5 items are accessible
1468                                       via indexing, the rest are name only */
1469 };
1470 
1471 /* Disable deprecation warnings about GetVersionEx as the result is
1472    being passed straight through to the caller, who is responsible for
1473    using it correctly. */
1474 #pragma warning(push)
1475 #pragma warning(disable:4996)
1476 
1477 /*[clinic input]
1478 sys.getwindowsversion
1479 
1480 Return info about the running version of Windows as a named tuple.
1481 
1482 The members are named: major, minor, build, platform, service_pack,
1483 service_pack_major, service_pack_minor, suite_mask, product_type and
1484 platform_version. For backward compatibility, only the first 5 items
1485 are available by indexing. All elements are numbers, except
1486 service_pack and platform_type which are strings, and platform_version
1487 which is a 3-tuple. Platform is always 2. Product_type may be 1 for a
1488 workstation, 2 for a domain controller, 3 for a server.
1489 Platform_version is a 3-tuple containing a version number that is
1490 intended for identifying the OS rather than feature detection.
1491 [clinic start generated code]*/
1492 
1493 static PyObject *
sys_getwindowsversion_impl(PyObject * module)1494 sys_getwindowsversion_impl(PyObject *module)
1495 /*[clinic end generated code: output=1ec063280b932857 input=73a228a328fee63a]*/
1496 {
1497     PyObject *version;
1498     int pos = 0;
1499     OSVERSIONINFOEXW ver;
1500     DWORD realMajor, realMinor, realBuild;
1501     HANDLE hKernel32;
1502     wchar_t kernel32_path[MAX_PATH];
1503     LPVOID verblock;
1504     DWORD verblock_size;
1505 
1506     ver.dwOSVersionInfoSize = sizeof(ver);
1507     if (!GetVersionExW((OSVERSIONINFOW*) &ver))
1508         return PyErr_SetFromWindowsErr(0);
1509 
1510     version = PyStructSequence_New(&WindowsVersionType);
1511     if (version == NULL)
1512         return NULL;
1513 
1514     PyStructSequence_SET_ITEM(version, pos++, PyLong_FromLong(ver.dwMajorVersion));
1515     PyStructSequence_SET_ITEM(version, pos++, PyLong_FromLong(ver.dwMinorVersion));
1516     PyStructSequence_SET_ITEM(version, pos++, PyLong_FromLong(ver.dwBuildNumber));
1517     PyStructSequence_SET_ITEM(version, pos++, PyLong_FromLong(ver.dwPlatformId));
1518     PyStructSequence_SET_ITEM(version, pos++, PyUnicode_FromWideChar(ver.szCSDVersion, -1));
1519     PyStructSequence_SET_ITEM(version, pos++, PyLong_FromLong(ver.wServicePackMajor));
1520     PyStructSequence_SET_ITEM(version, pos++, PyLong_FromLong(ver.wServicePackMinor));
1521     PyStructSequence_SET_ITEM(version, pos++, PyLong_FromLong(ver.wSuiteMask));
1522     PyStructSequence_SET_ITEM(version, pos++, PyLong_FromLong(ver.wProductType));
1523 
1524     realMajor = ver.dwMajorVersion;
1525     realMinor = ver.dwMinorVersion;
1526     realBuild = ver.dwBuildNumber;
1527 
1528     // GetVersion will lie if we are running in a compatibility mode.
1529     // We need to read the version info from a system file resource
1530     // to accurately identify the OS version. If we fail for any reason,
1531     // just return whatever GetVersion said.
1532     Py_BEGIN_ALLOW_THREADS
1533     hKernel32 = GetModuleHandleW(L"kernel32.dll");
1534     Py_END_ALLOW_THREADS
1535     if (hKernel32 && GetModuleFileNameW(hKernel32, kernel32_path, MAX_PATH) &&
1536         (verblock_size = GetFileVersionInfoSizeW(kernel32_path, NULL)) &&
1537         (verblock = PyMem_RawMalloc(verblock_size))) {
1538         VS_FIXEDFILEINFO *ffi;
1539         UINT ffi_len;
1540 
1541         if (GetFileVersionInfoW(kernel32_path, 0, verblock_size, verblock) &&
1542             VerQueryValueW(verblock, L"", (LPVOID)&ffi, &ffi_len)) {
1543             realMajor = HIWORD(ffi->dwProductVersionMS);
1544             realMinor = LOWORD(ffi->dwProductVersionMS);
1545             realBuild = HIWORD(ffi->dwProductVersionLS);
1546         }
1547         PyMem_RawFree(verblock);
1548     }
1549     PyStructSequence_SET_ITEM(version, pos++, Py_BuildValue("(kkk)",
1550         realMajor,
1551         realMinor,
1552         realBuild
1553     ));
1554 
1555     if (PyErr_Occurred()) {
1556         Py_DECREF(version);
1557         return NULL;
1558     }
1559     return version;
1560 }
1561 
1562 #pragma warning(pop)
1563 
1564 /*[clinic input]
1565 sys._enablelegacywindowsfsencoding
1566 
1567 Changes the default filesystem encoding to mbcs:replace.
1568 
1569 This is done for consistency with earlier versions of Python. See PEP
1570 529 for more information.
1571 
1572 This is equivalent to defining the PYTHONLEGACYWINDOWSFSENCODING
1573 environment variable before launching Python.
1574 [clinic start generated code]*/
1575 
1576 static PyObject *
sys__enablelegacywindowsfsencoding_impl(PyObject * module)1577 sys__enablelegacywindowsfsencoding_impl(PyObject *module)
1578 /*[clinic end generated code: output=f5c3855b45e24fe9 input=2bfa931a20704492]*/
1579 {
1580     if (_PyUnicode_EnableLegacyWindowsFSEncoding() < 0) {
1581         return NULL;
1582     }
1583     Py_RETURN_NONE;
1584 }
1585 
1586 #endif /* MS_WINDOWS */
1587 
1588 #ifdef HAVE_DLOPEN
1589 
1590 /*[clinic input]
1591 sys.setdlopenflags
1592 
1593     flags as new_val: int
1594     /
1595 
1596 Set the flags used by the interpreter for dlopen calls.
1597 
1598 This is used, for example, when the interpreter loads extension
1599 modules. Among other things, this will enable a lazy resolving of
1600 symbols when importing a module, if called as sys.setdlopenflags(0).
1601 To share symbols across extension modules, call as
1602 sys.setdlopenflags(os.RTLD_GLOBAL).  Symbolic names for the flag
1603 modules can be found in the os module (RTLD_xxx constants, e.g.
1604 os.RTLD_LAZY).
1605 [clinic start generated code]*/
1606 
1607 static PyObject *
sys_setdlopenflags_impl(PyObject * module,int new_val)1608 sys_setdlopenflags_impl(PyObject *module, int new_val)
1609 /*[clinic end generated code: output=ec918b7fe0a37281 input=4c838211e857a77f]*/
1610 {
1611     PyInterpreterState *interp = _PyInterpreterState_GET();
1612     interp->dlopenflags = new_val;
1613     Py_RETURN_NONE;
1614 }
1615 
1616 
1617 /*[clinic input]
1618 sys.getdlopenflags
1619 
1620 Return the current value of the flags that are used for dlopen calls.
1621 
1622 The flag constants are defined in the os module.
1623 [clinic start generated code]*/
1624 
1625 static PyObject *
sys_getdlopenflags_impl(PyObject * module)1626 sys_getdlopenflags_impl(PyObject *module)
1627 /*[clinic end generated code: output=e92cd1bc5005da6e input=dc4ea0899c53b4b6]*/
1628 {
1629     PyInterpreterState *interp = _PyInterpreterState_GET();
1630     return PyLong_FromLong(interp->dlopenflags);
1631 }
1632 
1633 #endif  /* HAVE_DLOPEN */
1634 
1635 #ifdef USE_MALLOPT
1636 /* Link with -lmalloc (or -lmpc) on an SGI */
1637 #include <malloc.h>
1638 
1639 /*[clinic input]
1640 sys.mdebug
1641 
1642     flag: int
1643     /
1644 [clinic start generated code]*/
1645 
1646 static PyObject *
sys_mdebug_impl(PyObject * module,int flag)1647 sys_mdebug_impl(PyObject *module, int flag)
1648 /*[clinic end generated code: output=5431d545847c3637 input=151d150ae1636f8a]*/
1649 {
1650     int flag;
1651     mallopt(M_DEBUG, flag);
1652     Py_RETURN_NONE;
1653 }
1654 #endif /* USE_MALLOPT */
1655 
1656 
1657 /*[clinic input]
1658 sys.get_int_max_str_digits
1659 
1660 Set the maximum string digits limit for non-binary int<->str conversions.
1661 [clinic start generated code]*/
1662 
1663 static PyObject *
sys_get_int_max_str_digits_impl(PyObject * module)1664 sys_get_int_max_str_digits_impl(PyObject *module)
1665 /*[clinic end generated code: output=0042f5e8ae0e8631 input=8dab13e2023e60d5]*/
1666 {
1667     PyInterpreterState *interp = _PyInterpreterState_GET();
1668     return PyLong_FromSsize_t(interp->int_max_str_digits);
1669 }
1670 
1671 /*[clinic input]
1672 sys.set_int_max_str_digits
1673 
1674     maxdigits: int
1675 
1676 Set the maximum string digits limit for non-binary int<->str conversions.
1677 [clinic start generated code]*/
1678 
1679 static PyObject *
sys_set_int_max_str_digits_impl(PyObject * module,int maxdigits)1680 sys_set_int_max_str_digits_impl(PyObject *module, int maxdigits)
1681 /*[clinic end generated code: output=734d4c2511f2a56d input=d7e3f325db6910c5]*/
1682 {
1683     PyThreadState *tstate = _PyThreadState_GET();
1684     if ((!maxdigits) || (maxdigits >= _PY_LONG_MAX_STR_DIGITS_THRESHOLD)) {
1685         tstate->interp->int_max_str_digits = maxdigits;
1686         Py_RETURN_NONE;
1687     } else {
1688         PyErr_Format(
1689             PyExc_ValueError, "maxdigits must be 0 or larger than %d",
1690             _PY_LONG_MAX_STR_DIGITS_THRESHOLD);
1691         return NULL;
1692     }
1693 }
1694 
1695 size_t
_PySys_GetSizeOf(PyObject * o)1696 _PySys_GetSizeOf(PyObject *o)
1697 {
1698     PyObject *res = NULL;
1699     PyObject *method;
1700     Py_ssize_t size;
1701     PyThreadState *tstate = _PyThreadState_GET();
1702 
1703     /* Make sure the type is initialized. float gets initialized late */
1704     if (PyType_Ready(Py_TYPE(o)) < 0) {
1705         return (size_t)-1;
1706     }
1707 
1708     method = _PyObject_LookupSpecial(o, &PyId___sizeof__);
1709     if (method == NULL) {
1710         if (!_PyErr_Occurred(tstate)) {
1711             _PyErr_Format(tstate, PyExc_TypeError,
1712                           "Type %.100s doesn't define __sizeof__",
1713                           Py_TYPE(o)->tp_name);
1714         }
1715     }
1716     else {
1717         res = _PyObject_CallNoArg(method);
1718         Py_DECREF(method);
1719     }
1720 
1721     if (res == NULL)
1722         return (size_t)-1;
1723 
1724     size = PyLong_AsSsize_t(res);
1725     Py_DECREF(res);
1726     if (size == -1 && _PyErr_Occurred(tstate))
1727         return (size_t)-1;
1728 
1729     if (size < 0) {
1730         _PyErr_SetString(tstate, PyExc_ValueError,
1731                           "__sizeof__() should return >= 0");
1732         return (size_t)-1;
1733     }
1734 
1735     /* add gc_head size */
1736     if (_PyObject_IS_GC(o))
1737         return ((size_t)size) + sizeof(PyGC_Head);
1738     return (size_t)size;
1739 }
1740 
1741 static PyObject *
sys_getsizeof(PyObject * self,PyObject * args,PyObject * kwds)1742 sys_getsizeof(PyObject *self, PyObject *args, PyObject *kwds)
1743 {
1744     static char *kwlist[] = {"object", "default", 0};
1745     size_t size;
1746     PyObject *o, *dflt = NULL;
1747     PyThreadState *tstate = _PyThreadState_GET();
1748 
1749     if (!PyArg_ParseTupleAndKeywords(args, kwds, "O|O:getsizeof",
1750                                      kwlist, &o, &dflt)) {
1751         return NULL;
1752     }
1753 
1754     size = _PySys_GetSizeOf(o);
1755 
1756     if (size == (size_t)-1 && _PyErr_Occurred(tstate)) {
1757         /* Has a default value been given */
1758         if (dflt != NULL && _PyErr_ExceptionMatches(tstate, PyExc_TypeError)) {
1759             _PyErr_Clear(tstate);
1760             Py_INCREF(dflt);
1761             return dflt;
1762         }
1763         else
1764             return NULL;
1765     }
1766 
1767     return PyLong_FromSize_t(size);
1768 }
1769 
1770 PyDoc_STRVAR(getsizeof_doc,
1771 "getsizeof(object [, default]) -> int\n\
1772 \n\
1773 Return the size of object in bytes.");
1774 
1775 /*[clinic input]
1776 sys.getrefcount -> Py_ssize_t
1777 
1778     object:  object
1779     /
1780 
1781 Return the reference count of object.
1782 
1783 The count returned is generally one higher than you might expect,
1784 because it includes the (temporary) reference as an argument to
1785 getrefcount().
1786 [clinic start generated code]*/
1787 
1788 static Py_ssize_t
sys_getrefcount_impl(PyObject * module,PyObject * object)1789 sys_getrefcount_impl(PyObject *module, PyObject *object)
1790 /*[clinic end generated code: output=5fd477f2264b85b2 input=bf474efd50a21535]*/
1791 {
1792     return Py_REFCNT(object);
1793 }
1794 
1795 #ifdef Py_REF_DEBUG
1796 /*[clinic input]
1797 sys.gettotalrefcount -> Py_ssize_t
1798 [clinic start generated code]*/
1799 
1800 static Py_ssize_t
sys_gettotalrefcount_impl(PyObject * module)1801 sys_gettotalrefcount_impl(PyObject *module)
1802 /*[clinic end generated code: output=4103886cf17c25bc input=53b744faa5d2e4f6]*/
1803 {
1804     return _Py_GetRefTotal();
1805 }
1806 #endif /* Py_REF_DEBUG */
1807 
1808 /*[clinic input]
1809 sys.getallocatedblocks -> Py_ssize_t
1810 
1811 Return the number of memory blocks currently allocated.
1812 [clinic start generated code]*/
1813 
1814 static Py_ssize_t
sys_getallocatedblocks_impl(PyObject * module)1815 sys_getallocatedblocks_impl(PyObject *module)
1816 /*[clinic end generated code: output=f0c4e873f0b6dcf7 input=dab13ee346a0673e]*/
1817 {
1818     return _Py_GetAllocatedBlocks();
1819 }
1820 
1821 
1822 /*[clinic input]
1823 sys._getframe
1824 
1825     depth: int = 0
1826     /
1827 
1828 Return a frame object from the call stack.
1829 
1830 If optional integer depth is given, return the frame object that many
1831 calls below the top of the stack.  If that is deeper than the call
1832 stack, ValueError is raised.  The default for depth is zero, returning
1833 the frame at the top of the call stack.
1834 
1835 This function should be used for internal and specialized purposes
1836 only.
1837 [clinic start generated code]*/
1838 
1839 static PyObject *
sys__getframe_impl(PyObject * module,int depth)1840 sys__getframe_impl(PyObject *module, int depth)
1841 /*[clinic end generated code: output=d438776c04d59804 input=c1be8a6464b11ee5]*/
1842 {
1843     PyThreadState *tstate = _PyThreadState_GET();
1844     PyFrameObject *f = PyThreadState_GetFrame(tstate);
1845 
1846     if (_PySys_Audit(tstate, "sys._getframe", "O", f) < 0) {
1847         Py_DECREF(f);
1848         return NULL;
1849     }
1850 
1851     while (depth > 0 && f != NULL) {
1852         PyFrameObject *back = PyFrame_GetBack(f);
1853         Py_DECREF(f);
1854         f = back;
1855         --depth;
1856     }
1857     if (f == NULL) {
1858         _PyErr_SetString(tstate, PyExc_ValueError,
1859                          "call stack is not deep enough");
1860         return NULL;
1861     }
1862     return (PyObject*)f;
1863 }
1864 
1865 /*[clinic input]
1866 sys._current_frames
1867 
1868 Return a dict mapping each thread's thread id to its current stack frame.
1869 
1870 This function should be used for specialized purposes only.
1871 [clinic start generated code]*/
1872 
1873 static PyObject *
sys__current_frames_impl(PyObject * module)1874 sys__current_frames_impl(PyObject *module)
1875 /*[clinic end generated code: output=d2a41ac0a0a3809a input=2a9049c5f5033691]*/
1876 {
1877     return _PyThread_CurrentFrames();
1878 }
1879 
1880 /*[clinic input]
1881 sys._current_exceptions
1882 
1883 Return a dict mapping each thread's identifier to its current raised exception.
1884 
1885 This function should be used for specialized purposes only.
1886 [clinic start generated code]*/
1887 
1888 static PyObject *
sys__current_exceptions_impl(PyObject * module)1889 sys__current_exceptions_impl(PyObject *module)
1890 /*[clinic end generated code: output=2ccfd838c746f0ba input=0e91818fbf2edc1f]*/
1891 {
1892     return _PyThread_CurrentExceptions();
1893 }
1894 
1895 /*[clinic input]
1896 sys.call_tracing
1897 
1898     func: object
1899     args as funcargs: object(subclass_of='&PyTuple_Type')
1900     /
1901 
1902 Call func(*args), while tracing is enabled.
1903 
1904 The tracing state is saved, and restored afterwards.  This is intended
1905 to be called from a debugger from a checkpoint, to recursively debug
1906 some other code.
1907 [clinic start generated code]*/
1908 
1909 static PyObject *
sys_call_tracing_impl(PyObject * module,PyObject * func,PyObject * funcargs)1910 sys_call_tracing_impl(PyObject *module, PyObject *func, PyObject *funcargs)
1911 /*[clinic end generated code: output=7e4999853cd4e5a6 input=5102e8b11049f92f]*/
1912 {
1913     return _PyEval_CallTracing(func, funcargs);
1914 }
1915 
1916 
1917 #ifdef __cplusplus
1918 extern "C" {
1919 #endif
1920 
1921 /*[clinic input]
1922 sys._debugmallocstats
1923 
1924 Print summary info to stderr about the state of pymalloc's structures.
1925 
1926 In Py_DEBUG mode, also perform some expensive internal consistency
1927 checks.
1928 [clinic start generated code]*/
1929 
1930 static PyObject *
sys__debugmallocstats_impl(PyObject * module)1931 sys__debugmallocstats_impl(PyObject *module)
1932 /*[clinic end generated code: output=ec3565f8c7cee46a input=33c0c9c416f98424]*/
1933 {
1934 #ifdef WITH_PYMALLOC
1935     if (_PyObject_DebugMallocStats(stderr)) {
1936         fputc('\n', stderr);
1937     }
1938 #endif
1939     _PyObject_DebugTypeStats(stderr);
1940 
1941     Py_RETURN_NONE;
1942 }
1943 
1944 #ifdef Py_TRACE_REFS
1945 /* Defined in objects.c because it uses static globals in that file */
1946 extern PyObject *_Py_GetObjects(PyObject *, PyObject *);
1947 #endif
1948 
1949 #ifdef DYNAMIC_EXECUTION_PROFILE
1950 /* Defined in ceval.c because it uses static globals in that file */
1951 extern PyObject *_Py_GetDXProfile(PyObject *,  PyObject *);
1952 #endif
1953 
1954 #ifdef __cplusplus
1955 }
1956 #endif
1957 
1958 
1959 /*[clinic input]
1960 sys._clear_type_cache
1961 
1962 Clear the internal type lookup cache.
1963 [clinic start generated code]*/
1964 
1965 static PyObject *
sys__clear_type_cache_impl(PyObject * module)1966 sys__clear_type_cache_impl(PyObject *module)
1967 /*[clinic end generated code: output=20e48ca54a6f6971 input=127f3e04a8d9b555]*/
1968 {
1969     PyType_ClearCache();
1970     Py_RETURN_NONE;
1971 }
1972 
1973 /*[clinic input]
1974 sys.is_finalizing
1975 
1976 Return True if Python is exiting.
1977 [clinic start generated code]*/
1978 
1979 static PyObject *
sys_is_finalizing_impl(PyObject * module)1980 sys_is_finalizing_impl(PyObject *module)
1981 /*[clinic end generated code: output=735b5ff7962ab281 input=f0df747a039948a5]*/
1982 {
1983     return PyBool_FromLong(_Py_IsFinalizing());
1984 }
1985 
1986 #ifdef ANDROID_API_LEVEL
1987 /*[clinic input]
1988 sys.getandroidapilevel
1989 
1990 Return the build time API version of Android as an integer.
1991 [clinic start generated code]*/
1992 
1993 static PyObject *
sys_getandroidapilevel_impl(PyObject * module)1994 sys_getandroidapilevel_impl(PyObject *module)
1995 /*[clinic end generated code: output=214abf183a1c70c1 input=3e6d6c9fcdd24ac6]*/
1996 {
1997     return PyLong_FromLong(ANDROID_API_LEVEL);
1998 }
1999 #endif   /* ANDROID_API_LEVEL */
2000 
2001 
2002 /*[clinic input]
2003 sys._deactivate_opcache
2004 
2005 Deactivate the opcode cache permanently
2006 [clinic start generated code]*/
2007 
2008 static PyObject *
sys__deactivate_opcache_impl(PyObject * module)2009 sys__deactivate_opcache_impl(PyObject *module)
2010 /*[clinic end generated code: output=00e20982bd012122 input=501eac146735ccf9]*/
2011 {
2012     _PyEval_DeactivateOpCache();
2013     Py_RETURN_NONE;
2014 }
2015 
2016 
2017 static PyMethodDef sys_methods[] = {
2018     /* Might as well keep this in alphabetic order */
2019     SYS_ADDAUDITHOOK_METHODDEF
2020     {"audit",           (PyCFunction)(void(*)(void))sys_audit, METH_FASTCALL, audit_doc },
2021     {"breakpointhook",  (PyCFunction)(void(*)(void))sys_breakpointhook,
2022      METH_FASTCALL | METH_KEYWORDS, breakpointhook_doc},
2023     SYS__CLEAR_TYPE_CACHE_METHODDEF
2024     SYS__CURRENT_FRAMES_METHODDEF
2025     SYS__CURRENT_EXCEPTIONS_METHODDEF
2026     SYS_DISPLAYHOOK_METHODDEF
2027     SYS_EXC_INFO_METHODDEF
2028     SYS_EXCEPTHOOK_METHODDEF
2029     SYS_EXIT_METHODDEF
2030     SYS_GETDEFAULTENCODING_METHODDEF
2031     SYS_GETDLOPENFLAGS_METHODDEF
2032     SYS_GETALLOCATEDBLOCKS_METHODDEF
2033 #ifdef DYNAMIC_EXECUTION_PROFILE
2034     {"getdxp",          _Py_GetDXProfile, METH_VARARGS},
2035 #endif
2036     SYS_GETFILESYSTEMENCODING_METHODDEF
2037     SYS_GETFILESYSTEMENCODEERRORS_METHODDEF
2038 #ifdef Py_TRACE_REFS
2039     {"getobjects",      _Py_GetObjects, METH_VARARGS},
2040 #endif
2041     SYS_GETTOTALREFCOUNT_METHODDEF
2042     SYS_GETREFCOUNT_METHODDEF
2043     SYS_GETRECURSIONLIMIT_METHODDEF
2044     {"getsizeof",   (PyCFunction)(void(*)(void))sys_getsizeof,
2045      METH_VARARGS | METH_KEYWORDS, getsizeof_doc},
2046     SYS__GETFRAME_METHODDEF
2047     SYS_GETWINDOWSVERSION_METHODDEF
2048     SYS__ENABLELEGACYWINDOWSFSENCODING_METHODDEF
2049     SYS_INTERN_METHODDEF
2050     SYS_IS_FINALIZING_METHODDEF
2051     SYS_MDEBUG_METHODDEF
2052     SYS_SETSWITCHINTERVAL_METHODDEF
2053     SYS_GETSWITCHINTERVAL_METHODDEF
2054     SYS_SETDLOPENFLAGS_METHODDEF
2055     {"setprofile",      sys_setprofile, METH_O, setprofile_doc},
2056     SYS_GETPROFILE_METHODDEF
2057     SYS_SETRECURSIONLIMIT_METHODDEF
2058     {"settrace",        sys_settrace, METH_O, settrace_doc},
2059     SYS_GETTRACE_METHODDEF
2060     SYS_CALL_TRACING_METHODDEF
2061     SYS__DEBUGMALLOCSTATS_METHODDEF
2062     SYS_SET_COROUTINE_ORIGIN_TRACKING_DEPTH_METHODDEF
2063     SYS_GET_COROUTINE_ORIGIN_TRACKING_DEPTH_METHODDEF
2064     {"set_asyncgen_hooks", (PyCFunction)(void(*)(void))sys_set_asyncgen_hooks,
2065      METH_VARARGS | METH_KEYWORDS, set_asyncgen_hooks_doc},
2066     SYS_GET_ASYNCGEN_HOOKS_METHODDEF
2067     SYS_GETANDROIDAPILEVEL_METHODDEF
2068     SYS_UNRAISABLEHOOK_METHODDEF
2069     SYS__DEACTIVATE_OPCACHE_METHODDEF
2070     SYS_GET_INT_MAX_STR_DIGITS_METHODDEF
2071     SYS_SET_INT_MAX_STR_DIGITS_METHODDEF
2072     {NULL,              NULL}           /* sentinel */
2073 };
2074 
2075 
2076 static PyObject *
list_builtin_module_names(void)2077 list_builtin_module_names(void)
2078 {
2079     PyObject *list = PyList_New(0);
2080     if (list == NULL) {
2081         return NULL;
2082     }
2083     for (Py_ssize_t i = 0; PyImport_Inittab[i].name != NULL; i++) {
2084         PyObject *name = PyUnicode_FromString(PyImport_Inittab[i].name);
2085         if (name == NULL) {
2086             goto error;
2087         }
2088         if (PyList_Append(list, name) < 0) {
2089             Py_DECREF(name);
2090             goto error;
2091         }
2092         Py_DECREF(name);
2093     }
2094     if (PyList_Sort(list) != 0) {
2095         goto error;
2096     }
2097     PyObject *tuple = PyList_AsTuple(list);
2098     Py_DECREF(list);
2099     return tuple;
2100 
2101 error:
2102     Py_DECREF(list);
2103     return NULL;
2104 }
2105 
2106 
2107 static PyObject *
list_stdlib_module_names(void)2108 list_stdlib_module_names(void)
2109 {
2110     Py_ssize_t len = Py_ARRAY_LENGTH(_Py_stdlib_module_names);
2111     PyObject *names = PyTuple_New(len);
2112     if (names == NULL) {
2113         return NULL;
2114     }
2115 
2116     for (Py_ssize_t i = 0; i < len; i++) {
2117         PyObject *name = PyUnicode_FromString(_Py_stdlib_module_names[i]);
2118         if (name == NULL) {
2119             Py_DECREF(names);
2120             return NULL;
2121         }
2122         PyTuple_SET_ITEM(names, i, name);
2123     }
2124 
2125     PyObject *set = PyObject_CallFunction((PyObject *)&PyFrozenSet_Type,
2126                                           "(O)", names);
2127     Py_DECREF(names);
2128     return set;
2129 }
2130 
2131 
2132 /* Pre-initialization support for sys.warnoptions and sys._xoptions
2133  *
2134  * Modern internal code paths:
2135  *   These APIs get called after _Py_InitializeCore and get to use the
2136  *   regular CPython list, dict, and unicode APIs.
2137  *
2138  * Legacy embedding code paths:
2139  *   The multi-phase initialization API isn't public yet, so embedding
2140  *   apps still need to be able configure sys.warnoptions and sys._xoptions
2141  *   before they call Py_Initialize. To support this, we stash copies of
2142  *   the supplied wchar * sequences in linked lists, and then migrate the
2143  *   contents of those lists to the sys module in _PyInitializeCore.
2144  *
2145  */
2146 
2147 struct _preinit_entry {
2148     wchar_t *value;
2149     struct _preinit_entry *next;
2150 };
2151 
2152 typedef struct _preinit_entry *_Py_PreInitEntry;
2153 
2154 static _Py_PreInitEntry _preinit_warnoptions = NULL;
2155 static _Py_PreInitEntry _preinit_xoptions = NULL;
2156 
2157 static _Py_PreInitEntry
_alloc_preinit_entry(const wchar_t * value)2158 _alloc_preinit_entry(const wchar_t *value)
2159 {
2160     /* To get this to work, we have to initialize the runtime implicitly */
2161     _PyRuntime_Initialize();
2162 
2163     /* Force default allocator, so we can ensure that it also gets used to
2164      * destroy the linked list in _clear_preinit_entries.
2165      */
2166     PyMemAllocatorEx old_alloc;
2167     _PyMem_SetDefaultAllocator(PYMEM_DOMAIN_RAW, &old_alloc);
2168 
2169     _Py_PreInitEntry node = PyMem_RawCalloc(1, sizeof(*node));
2170     if (node != NULL) {
2171         node->value = _PyMem_RawWcsdup(value);
2172         if (node->value == NULL) {
2173             PyMem_RawFree(node);
2174             node = NULL;
2175         };
2176     };
2177 
2178     PyMem_SetAllocator(PYMEM_DOMAIN_RAW, &old_alloc);
2179     return node;
2180 }
2181 
2182 static int
_append_preinit_entry(_Py_PreInitEntry * optionlist,const wchar_t * value)2183 _append_preinit_entry(_Py_PreInitEntry *optionlist, const wchar_t *value)
2184 {
2185     _Py_PreInitEntry new_entry = _alloc_preinit_entry(value);
2186     if (new_entry == NULL) {
2187         return -1;
2188     }
2189     /* We maintain the linked list in this order so it's easy to play back
2190      * the add commands in the same order later on in _Py_InitializeCore
2191      */
2192     _Py_PreInitEntry last_entry = *optionlist;
2193     if (last_entry == NULL) {
2194         *optionlist = new_entry;
2195     } else {
2196         while (last_entry->next != NULL) {
2197             last_entry = last_entry->next;
2198         }
2199         last_entry->next = new_entry;
2200     }
2201     return 0;
2202 }
2203 
2204 static void
_clear_preinit_entries(_Py_PreInitEntry * optionlist)2205 _clear_preinit_entries(_Py_PreInitEntry *optionlist)
2206 {
2207     _Py_PreInitEntry current = *optionlist;
2208     *optionlist = NULL;
2209     /* Deallocate the nodes and their contents using the default allocator */
2210     PyMemAllocatorEx old_alloc;
2211     _PyMem_SetDefaultAllocator(PYMEM_DOMAIN_RAW, &old_alloc);
2212     while (current != NULL) {
2213         _Py_PreInitEntry next = current->next;
2214         PyMem_RawFree(current->value);
2215         PyMem_RawFree(current);
2216         current = next;
2217     }
2218     PyMem_SetAllocator(PYMEM_DOMAIN_RAW, &old_alloc);
2219 }
2220 
2221 
2222 PyStatus
_PySys_ReadPreinitWarnOptions(PyWideStringList * options)2223 _PySys_ReadPreinitWarnOptions(PyWideStringList *options)
2224 {
2225     PyStatus status;
2226     _Py_PreInitEntry entry;
2227 
2228     for (entry = _preinit_warnoptions; entry != NULL; entry = entry->next) {
2229         status = PyWideStringList_Append(options, entry->value);
2230         if (_PyStatus_EXCEPTION(status)) {
2231             return status;
2232         }
2233     }
2234 
2235     _clear_preinit_entries(&_preinit_warnoptions);
2236     return _PyStatus_OK();
2237 }
2238 
2239 
2240 PyStatus
_PySys_ReadPreinitXOptions(PyConfig * config)2241 _PySys_ReadPreinitXOptions(PyConfig *config)
2242 {
2243     PyStatus status;
2244     _Py_PreInitEntry entry;
2245 
2246     for (entry = _preinit_xoptions; entry != NULL; entry = entry->next) {
2247         status = PyWideStringList_Append(&config->xoptions, entry->value);
2248         if (_PyStatus_EXCEPTION(status)) {
2249             return status;
2250         }
2251     }
2252 
2253     _clear_preinit_entries(&_preinit_xoptions);
2254     return _PyStatus_OK();
2255 }
2256 
2257 
2258 static PyObject *
get_warnoptions(PyThreadState * tstate)2259 get_warnoptions(PyThreadState *tstate)
2260 {
2261     PyObject *warnoptions = sys_get_object_id(tstate, &PyId_warnoptions);
2262     if (warnoptions == NULL || !PyList_Check(warnoptions)) {
2263         /* PEP432 TODO: we can reach this if warnoptions is NULL in the main
2264         *  interpreter config. When that happens, we need to properly set
2265          * the `warnoptions` reference in the main interpreter config as well.
2266          *
2267          * For Python 3.7, we shouldn't be able to get here due to the
2268          * combination of how _PyMainInterpreter_ReadConfig and _PySys_EndInit
2269          * work, but we expect 3.8+ to make the _PyMainInterpreter_ReadConfig
2270          * call optional for embedding applications, thus making this
2271          * reachable again.
2272          */
2273         warnoptions = PyList_New(0);
2274         if (warnoptions == NULL) {
2275             return NULL;
2276         }
2277         if (sys_set_object_id(tstate->interp, &PyId_warnoptions, warnoptions)) {
2278             Py_DECREF(warnoptions);
2279             return NULL;
2280         }
2281         Py_DECREF(warnoptions);
2282     }
2283     return warnoptions;
2284 }
2285 
2286 void
PySys_ResetWarnOptions(void)2287 PySys_ResetWarnOptions(void)
2288 {
2289     PyThreadState *tstate = _PyThreadState_GET();
2290     if (tstate == NULL) {
2291         _clear_preinit_entries(&_preinit_warnoptions);
2292         return;
2293     }
2294 
2295     PyObject *warnoptions = sys_get_object_id(tstate, &PyId_warnoptions);
2296     if (warnoptions == NULL || !PyList_Check(warnoptions))
2297         return;
2298     PyList_SetSlice(warnoptions, 0, PyList_GET_SIZE(warnoptions), NULL);
2299 }
2300 
2301 static int
_PySys_AddWarnOptionWithError(PyThreadState * tstate,PyObject * option)2302 _PySys_AddWarnOptionWithError(PyThreadState *tstate, PyObject *option)
2303 {
2304     PyObject *warnoptions = get_warnoptions(tstate);
2305     if (warnoptions == NULL) {
2306         return -1;
2307     }
2308     if (PyList_Append(warnoptions, option)) {
2309         return -1;
2310     }
2311     return 0;
2312 }
2313 
2314 void
PySys_AddWarnOptionUnicode(PyObject * option)2315 PySys_AddWarnOptionUnicode(PyObject *option)
2316 {
2317     PyThreadState *tstate = _PyThreadState_GET();
2318     if (_PySys_AddWarnOptionWithError(tstate, option) < 0) {
2319         /* No return value, therefore clear error state if possible */
2320         if (tstate) {
2321             _PyErr_Clear(tstate);
2322         }
2323     }
2324 }
2325 
2326 void
PySys_AddWarnOption(const wchar_t * s)2327 PySys_AddWarnOption(const wchar_t *s)
2328 {
2329     PyThreadState *tstate = _PyThreadState_GET();
2330     if (tstate == NULL) {
2331         _append_preinit_entry(&_preinit_warnoptions, s);
2332         return;
2333     }
2334     PyObject *unicode;
2335     unicode = PyUnicode_FromWideChar(s, -1);
2336     if (unicode == NULL)
2337         return;
2338     PySys_AddWarnOptionUnicode(unicode);
2339     Py_DECREF(unicode);
2340 }
2341 
2342 int
PySys_HasWarnOptions(void)2343 PySys_HasWarnOptions(void)
2344 {
2345     PyThreadState *tstate = _PyThreadState_GET();
2346     PyObject *warnoptions = sys_get_object_id(tstate, &PyId_warnoptions);
2347     return (warnoptions != NULL && PyList_Check(warnoptions)
2348             && PyList_GET_SIZE(warnoptions) > 0);
2349 }
2350 
2351 static PyObject *
get_xoptions(PyThreadState * tstate)2352 get_xoptions(PyThreadState *tstate)
2353 {
2354     PyObject *xoptions = sys_get_object_id(tstate, &PyId__xoptions);
2355     if (xoptions == NULL || !PyDict_Check(xoptions)) {
2356         /* PEP432 TODO: we can reach this if xoptions is NULL in the main
2357         *  interpreter config. When that happens, we need to properly set
2358          * the `xoptions` reference in the main interpreter config as well.
2359          *
2360          * For Python 3.7, we shouldn't be able to get here due to the
2361          * combination of how _PyMainInterpreter_ReadConfig and _PySys_EndInit
2362          * work, but we expect 3.8+ to make the _PyMainInterpreter_ReadConfig
2363          * call optional for embedding applications, thus making this
2364          * reachable again.
2365          */
2366         xoptions = PyDict_New();
2367         if (xoptions == NULL) {
2368             return NULL;
2369         }
2370         if (sys_set_object_id(tstate->interp, &PyId__xoptions, xoptions)) {
2371             Py_DECREF(xoptions);
2372             return NULL;
2373         }
2374         Py_DECREF(xoptions);
2375     }
2376     return xoptions;
2377 }
2378 
2379 static int
_PySys_AddXOptionWithError(const wchar_t * s)2380 _PySys_AddXOptionWithError(const wchar_t *s)
2381 {
2382     PyObject *name = NULL, *value = NULL;
2383 
2384     PyThreadState *tstate = _PyThreadState_GET();
2385     PyObject *opts = get_xoptions(tstate);
2386     if (opts == NULL) {
2387         goto error;
2388     }
2389 
2390     const wchar_t *name_end = wcschr(s, L'=');
2391     if (!name_end) {
2392         name = PyUnicode_FromWideChar(s, -1);
2393         value = Py_True;
2394         Py_INCREF(value);
2395     }
2396     else {
2397         name = PyUnicode_FromWideChar(s, name_end - s);
2398         value = PyUnicode_FromWideChar(name_end + 1, -1);
2399     }
2400     if (name == NULL || value == NULL) {
2401         goto error;
2402     }
2403     if (PyDict_SetItem(opts, name, value) < 0) {
2404         goto error;
2405     }
2406     Py_DECREF(name);
2407     Py_DECREF(value);
2408     return 0;
2409 
2410 error:
2411     Py_XDECREF(name);
2412     Py_XDECREF(value);
2413     return -1;
2414 }
2415 
2416 void
PySys_AddXOption(const wchar_t * s)2417 PySys_AddXOption(const wchar_t *s)
2418 {
2419     PyThreadState *tstate = _PyThreadState_GET();
2420     if (tstate == NULL) {
2421         _append_preinit_entry(&_preinit_xoptions, s);
2422         return;
2423     }
2424     if (_PySys_AddXOptionWithError(s) < 0) {
2425         /* No return value, therefore clear error state if possible */
2426         _PyErr_Clear(tstate);
2427     }
2428 }
2429 
2430 PyObject *
PySys_GetXOptions(void)2431 PySys_GetXOptions(void)
2432 {
2433     PyThreadState *tstate = _PyThreadState_GET();
2434     return get_xoptions(tstate);
2435 }
2436 
2437 /* XXX This doc string is too long to be a single string literal in VC++ 5.0.
2438    Two literals concatenated works just fine.  If you have a K&R compiler
2439    or other abomination that however *does* understand longer strings,
2440    get rid of the !!! comment in the middle and the quotes that surround it. */
2441 PyDoc_VAR(sys_doc) =
2442 PyDoc_STR(
2443 "This module provides access to some objects used or maintained by the\n\
2444 interpreter and to functions that interact strongly with the interpreter.\n\
2445 \n\
2446 Dynamic objects:\n\
2447 \n\
2448 argv -- command line arguments; argv[0] is the script pathname if known\n\
2449 path -- module search path; path[0] is the script directory, else ''\n\
2450 modules -- dictionary of loaded modules\n\
2451 \n\
2452 displayhook -- called to show results in an interactive session\n\
2453 excepthook -- called to handle any uncaught exception other than SystemExit\n\
2454   To customize printing in an interactive session or to install a custom\n\
2455   top-level exception handler, assign other functions to replace these.\n\
2456 \n\
2457 stdin -- standard input file object; used by input()\n\
2458 stdout -- standard output file object; used by print()\n\
2459 stderr -- standard error object; used for error messages\n\
2460   By assigning other file objects (or objects that behave like files)\n\
2461   to these, it is possible to redirect all of the interpreter's I/O.\n\
2462 \n\
2463 last_type -- type of last uncaught exception\n\
2464 last_value -- value of last uncaught exception\n\
2465 last_traceback -- traceback of last uncaught exception\n\
2466   These three are only available in an interactive session after a\n\
2467   traceback has been printed.\n\
2468 "
2469 )
2470 /* concatenating string here */
2471 PyDoc_STR(
2472 "\n\
2473 Static objects:\n\
2474 \n\
2475 builtin_module_names -- tuple of module names built into this interpreter\n\
2476 copyright -- copyright notice pertaining to this interpreter\n\
2477 exec_prefix -- prefix used to find the machine-specific Python library\n\
2478 executable -- absolute path of the executable binary of the Python interpreter\n\
2479 float_info -- a named tuple with information about the float implementation.\n\
2480 float_repr_style -- string indicating the style of repr() output for floats\n\
2481 hash_info -- a named tuple with information about the hash algorithm.\n\
2482 hexversion -- version information encoded as a single integer\n\
2483 implementation -- Python implementation information.\n\
2484 int_info -- a named tuple with information about the int implementation.\n\
2485 maxsize -- the largest supported length of containers.\n\
2486 maxunicode -- the value of the largest Unicode code point\n\
2487 platform -- platform identifier\n\
2488 prefix -- prefix used to find the Python library\n\
2489 thread_info -- a named tuple with information about the thread implementation.\n\
2490 version -- the version of this interpreter as a string\n\
2491 version_info -- version information as a named tuple\n\
2492 "
2493 )
2494 #ifdef MS_COREDLL
2495 /* concatenating string here */
2496 PyDoc_STR(
2497 "dllhandle -- [Windows only] integer handle of the Python DLL\n\
2498 winver -- [Windows only] version number of the Python DLL\n\
2499 "
2500 )
2501 #endif /* MS_COREDLL */
2502 #ifdef MS_WINDOWS
2503 /* concatenating string here */
2504 PyDoc_STR(
2505 "_enablelegacywindowsfsencoding -- [Windows only]\n\
2506 "
2507 )
2508 #endif
2509 PyDoc_STR(
2510 "__stdin__ -- the original stdin; don't touch!\n\
2511 __stdout__ -- the original stdout; don't touch!\n\
2512 __stderr__ -- the original stderr; don't touch!\n\
2513 __displayhook__ -- the original displayhook; don't touch!\n\
2514 __excepthook__ -- the original excepthook; don't touch!\n\
2515 \n\
2516 Functions:\n\
2517 \n\
2518 displayhook() -- print an object to the screen, and save it in builtins._\n\
2519 excepthook() -- print an exception and its traceback to sys.stderr\n\
2520 exc_info() -- return thread-safe information about the current exception\n\
2521 exit() -- exit the interpreter by raising SystemExit\n\
2522 getdlopenflags() -- returns flags to be used for dlopen() calls\n\
2523 getprofile() -- get the global profiling function\n\
2524 getrefcount() -- return the reference count for an object (plus one :-)\n\
2525 getrecursionlimit() -- return the max recursion depth for the interpreter\n\
2526 getsizeof() -- return the size of an object in bytes\n\
2527 gettrace() -- get the global debug tracing function\n\
2528 setdlopenflags() -- set the flags to be used for dlopen() calls\n\
2529 setprofile() -- set the global profiling function\n\
2530 setrecursionlimit() -- set the max recursion depth for the interpreter\n\
2531 settrace() -- set the global debug tracing function\n\
2532 "
2533 )
2534 /* end of sys_doc */ ;
2535 
2536 
2537 PyDoc_STRVAR(flags__doc__,
2538 "sys.flags\n\
2539 \n\
2540 Flags provided through command line arguments or environment vars.");
2541 
2542 static PyTypeObject FlagsType;
2543 
2544 static PyStructSequence_Field flags_fields[] = {
2545     {"debug",                   "-d"},
2546     {"inspect",                 "-i"},
2547     {"interactive",             "-i"},
2548     {"optimize",                "-O or -OO"},
2549     {"dont_write_bytecode",     "-B"},
2550     {"no_user_site",            "-s"},
2551     {"no_site",                 "-S"},
2552     {"ignore_environment",      "-E"},
2553     {"verbose",                 "-v"},
2554     {"bytes_warning",           "-b"},
2555     {"quiet",                   "-q"},
2556     {"hash_randomization",      "-R"},
2557     {"isolated",                "-I"},
2558     {"dev_mode",                "-X dev"},
2559     {"utf8_mode",               "-X utf8"},
2560     {"warn_default_encoding",   "-X warn_default_encoding"},
2561     {"int_max_str_digits",      "-X int_max_str_digits"},
2562     {0}
2563 };
2564 
2565 static PyStructSequence_Desc flags_desc = {
2566     "sys.flags",        /* name */
2567     flags__doc__,       /* doc */
2568     flags_fields,       /* fields */
2569     17
2570 };
2571 
2572 static int
set_flags_from_config(PyInterpreterState * interp,PyObject * flags)2573 set_flags_from_config(PyInterpreterState *interp, PyObject *flags)
2574 {
2575     const PyPreConfig *preconfig = &interp->runtime->preconfig;
2576     const PyConfig *config = _PyInterpreterState_GetConfig(interp);
2577 
2578     // _PySys_UpdateConfig() modifies sys.flags in-place:
2579     // Py_XDECREF() is needed in this case.
2580     Py_ssize_t pos = 0;
2581 #define SetFlagObj(expr) \
2582     do { \
2583         PyObject *value = (expr); \
2584         if (value == NULL) { \
2585             return -1; \
2586         } \
2587         Py_XDECREF(PyStructSequence_GET_ITEM(flags, pos)); \
2588         PyStructSequence_SET_ITEM(flags, pos, value); \
2589         pos++; \
2590     } while (0)
2591 #define SetFlag(expr) SetFlagObj(PyLong_FromLong(expr))
2592 
2593     SetFlag(config->parser_debug);
2594     SetFlag(config->inspect);
2595     SetFlag(config->interactive);
2596     SetFlag(config->optimization_level);
2597     SetFlag(!config->write_bytecode);
2598     SetFlag(!config->user_site_directory);
2599     SetFlag(!config->site_import);
2600     SetFlag(!config->use_environment);
2601     SetFlag(config->verbose);
2602     SetFlag(config->bytes_warning);
2603     SetFlag(config->quiet);
2604     SetFlag(config->use_hash_seed == 0 || config->hash_seed != 0);
2605     SetFlag(config->isolated);
2606     SetFlagObj(PyBool_FromLong(config->dev_mode));
2607     SetFlag(preconfig->utf8_mode);
2608     SetFlag(config->warn_default_encoding);
2609     SetFlag(_Py_global_config_int_max_str_digits);
2610 #undef SetFlagObj
2611 #undef SetFlag
2612     return 0;
2613 }
2614 
2615 
2616 static PyObject*
make_flags(PyInterpreterState * interp)2617 make_flags(PyInterpreterState *interp)
2618 {
2619     PyObject *flags = PyStructSequence_New(&FlagsType);
2620     if (flags == NULL) {
2621         return NULL;
2622     }
2623 
2624     if (set_flags_from_config(interp, flags) < 0) {
2625         Py_DECREF(flags);
2626         return NULL;
2627     }
2628     return flags;
2629 }
2630 
2631 
2632 PyDoc_STRVAR(version_info__doc__,
2633 "sys.version_info\n\
2634 \n\
2635 Version information as a named tuple.");
2636 
2637 static PyTypeObject VersionInfoType;
2638 
2639 static PyStructSequence_Field version_info_fields[] = {
2640     {"major", "Major release number"},
2641     {"minor", "Minor release number"},
2642     {"micro", "Patch release number"},
2643     {"releaselevel", "'alpha', 'beta', 'candidate', or 'final'"},
2644     {"serial", "Serial release number"},
2645     {0}
2646 };
2647 
2648 static PyStructSequence_Desc version_info_desc = {
2649     "sys.version_info",     /* name */
2650     version_info__doc__,    /* doc */
2651     version_info_fields,    /* fields */
2652     5
2653 };
2654 
2655 static PyObject *
make_version_info(PyThreadState * tstate)2656 make_version_info(PyThreadState *tstate)
2657 {
2658     PyObject *version_info;
2659     char *s;
2660     int pos = 0;
2661 
2662     version_info = PyStructSequence_New(&VersionInfoType);
2663     if (version_info == NULL) {
2664         return NULL;
2665     }
2666 
2667     /*
2668      * These release level checks are mutually exclusive and cover
2669      * the field, so don't get too fancy with the pre-processor!
2670      */
2671 #if PY_RELEASE_LEVEL == PY_RELEASE_LEVEL_ALPHA
2672     s = "alpha";
2673 #elif PY_RELEASE_LEVEL == PY_RELEASE_LEVEL_BETA
2674     s = "beta";
2675 #elif PY_RELEASE_LEVEL == PY_RELEASE_LEVEL_GAMMA
2676     s = "candidate";
2677 #elif PY_RELEASE_LEVEL == PY_RELEASE_LEVEL_FINAL
2678     s = "final";
2679 #endif
2680 
2681 #define SetIntItem(flag) \
2682     PyStructSequence_SET_ITEM(version_info, pos++, PyLong_FromLong(flag))
2683 #define SetStrItem(flag) \
2684     PyStructSequence_SET_ITEM(version_info, pos++, PyUnicode_FromString(flag))
2685 
2686     SetIntItem(PY_MAJOR_VERSION);
2687     SetIntItem(PY_MINOR_VERSION);
2688     SetIntItem(PY_MICRO_VERSION);
2689     SetStrItem(s);
2690     SetIntItem(PY_RELEASE_SERIAL);
2691 #undef SetIntItem
2692 #undef SetStrItem
2693 
2694     if (_PyErr_Occurred(tstate)) {
2695         Py_CLEAR(version_info);
2696         return NULL;
2697     }
2698     return version_info;
2699 }
2700 
2701 /* sys.implementation values */
2702 #define NAME "cpython"
2703 const char *_PySys_ImplName = NAME;
2704 #define MAJOR Py_STRINGIFY(PY_MAJOR_VERSION)
2705 #define MINOR Py_STRINGIFY(PY_MINOR_VERSION)
2706 #define TAG NAME "-" MAJOR MINOR
2707 const char *_PySys_ImplCacheTag = TAG;
2708 #undef NAME
2709 #undef MAJOR
2710 #undef MINOR
2711 #undef TAG
2712 
2713 static PyObject *
make_impl_info(PyObject * version_info)2714 make_impl_info(PyObject *version_info)
2715 {
2716     int res;
2717     PyObject *impl_info, *value, *ns;
2718 
2719     impl_info = PyDict_New();
2720     if (impl_info == NULL)
2721         return NULL;
2722 
2723     /* populate the dict */
2724 
2725     value = PyUnicode_FromString(_PySys_ImplName);
2726     if (value == NULL)
2727         goto error;
2728     res = PyDict_SetItemString(impl_info, "name", value);
2729     Py_DECREF(value);
2730     if (res < 0)
2731         goto error;
2732 
2733     value = PyUnicode_FromString(_PySys_ImplCacheTag);
2734     if (value == NULL)
2735         goto error;
2736     res = PyDict_SetItemString(impl_info, "cache_tag", value);
2737     Py_DECREF(value);
2738     if (res < 0)
2739         goto error;
2740 
2741     res = PyDict_SetItemString(impl_info, "version", version_info);
2742     if (res < 0)
2743         goto error;
2744 
2745     value = PyLong_FromLong(PY_VERSION_HEX);
2746     if (value == NULL)
2747         goto error;
2748     res = PyDict_SetItemString(impl_info, "hexversion", value);
2749     Py_DECREF(value);
2750     if (res < 0)
2751         goto error;
2752 
2753 #ifdef MULTIARCH
2754     value = PyUnicode_FromString(MULTIARCH);
2755     if (value == NULL)
2756         goto error;
2757     res = PyDict_SetItemString(impl_info, "_multiarch", value);
2758     Py_DECREF(value);
2759     if (res < 0)
2760         goto error;
2761 #endif
2762 
2763     /* dict ready */
2764 
2765     ns = _PyNamespace_New(impl_info);
2766     Py_DECREF(impl_info);
2767     return ns;
2768 
2769 error:
2770     Py_CLEAR(impl_info);
2771     return NULL;
2772 }
2773 
2774 static struct PyModuleDef sysmodule = {
2775     PyModuleDef_HEAD_INIT,
2776     "sys",
2777     sys_doc,
2778     -1, /* multiple "initialization" just copies the module dict. */
2779     sys_methods,
2780     NULL,
2781     NULL,
2782     NULL,
2783     NULL
2784 };
2785 
2786 /* Updating the sys namespace, returning NULL pointer on error */
2787 #define SET_SYS(key, value)                                \
2788     do {                                                   \
2789         PyObject *v = (value);                             \
2790         if (v == NULL) {                                   \
2791             goto err_occurred;                             \
2792         }                                                  \
2793         res = PyDict_SetItemString(sysdict, key, v);       \
2794         Py_DECREF(v);                                      \
2795         if (res < 0) {                                     \
2796             goto err_occurred;                             \
2797         }                                                  \
2798     } while (0)
2799 
2800 #define SET_SYS_FROM_STRING(key, value) \
2801         SET_SYS(key, PyUnicode_FromString(value))
2802 
2803 static PyStatus
_PySys_InitCore(PyThreadState * tstate,PyObject * sysdict)2804 _PySys_InitCore(PyThreadState *tstate, PyObject *sysdict)
2805 {
2806     PyObject *version_info;
2807     int res;
2808 
2809     /* stdin/stdout/stderr are set in pylifecycle.c */
2810 
2811 #define COPY_SYS_ATTR(tokey, fromkey) \
2812         SET_SYS(tokey, PyMapping_GetItemString(sysdict, fromkey))
2813 
2814     COPY_SYS_ATTR("__displayhook__", "displayhook");
2815     COPY_SYS_ATTR("__excepthook__", "excepthook");
2816     COPY_SYS_ATTR("__breakpointhook__", "breakpointhook");
2817     COPY_SYS_ATTR("__unraisablehook__", "unraisablehook");
2818 
2819 #undef COPY_SYS_ATTR
2820 
2821     SET_SYS_FROM_STRING("version", Py_GetVersion());
2822     SET_SYS("hexversion", PyLong_FromLong(PY_VERSION_HEX));
2823     SET_SYS("_git", Py_BuildValue("(szz)", "CPython", _Py_gitidentifier(),
2824                                   _Py_gitversion()));
2825     SET_SYS_FROM_STRING("_framework", _PYTHONFRAMEWORK);
2826     SET_SYS("api_version", PyLong_FromLong(PYTHON_API_VERSION));
2827     SET_SYS_FROM_STRING("copyright", Py_GetCopyright());
2828     SET_SYS_FROM_STRING("platform", Py_GetPlatform());
2829     SET_SYS("maxsize", PyLong_FromSsize_t(PY_SSIZE_T_MAX));
2830     SET_SYS("float_info", PyFloat_GetInfo());
2831     SET_SYS("int_info", PyLong_GetInfo());
2832     /* initialize hash_info */
2833     if (Hash_InfoType.tp_name == NULL) {
2834         if (PyStructSequence_InitType2(&Hash_InfoType, &hash_info_desc) < 0) {
2835             goto type_init_failed;
2836         }
2837     }
2838     SET_SYS("hash_info", get_hash_info(tstate));
2839     SET_SYS("maxunicode", PyLong_FromLong(0x10FFFF));
2840     SET_SYS("builtin_module_names", list_builtin_module_names());
2841     SET_SYS("stdlib_module_names", list_stdlib_module_names());
2842 #if PY_BIG_ENDIAN
2843     SET_SYS_FROM_STRING("byteorder", "big");
2844 #else
2845     SET_SYS_FROM_STRING("byteorder", "little");
2846 #endif
2847 
2848 #ifdef MS_COREDLL
2849     SET_SYS("dllhandle", PyLong_FromVoidPtr(PyWin_DLLhModule));
2850     SET_SYS_FROM_STRING("winver", PyWin_DLLVersionString);
2851 #endif
2852 #ifdef ABIFLAGS
2853     SET_SYS_FROM_STRING("abiflags", ABIFLAGS);
2854 #endif
2855 
2856     /* version_info */
2857     if (VersionInfoType.tp_name == NULL) {
2858         if (_PyStructSequence_InitType(&VersionInfoType,
2859                                        &version_info_desc,
2860                                        Py_TPFLAGS_DISALLOW_INSTANTIATION) < 0) {
2861             goto type_init_failed;
2862         }
2863     }
2864     version_info = make_version_info(tstate);
2865     SET_SYS("version_info", version_info);
2866 
2867     /* implementation */
2868     SET_SYS("implementation", make_impl_info(version_info));
2869 
2870     // sys.flags: updated in-place later by _PySys_UpdateConfig()
2871     if (FlagsType.tp_name == 0) {
2872         if (_PyStructSequence_InitType(&FlagsType, &flags_desc,
2873                                        Py_TPFLAGS_DISALLOW_INSTANTIATION) < 0) {
2874             goto type_init_failed;
2875         }
2876     }
2877     SET_SYS("flags", make_flags(tstate->interp));
2878 
2879 #if defined(MS_WINDOWS)
2880     /* getwindowsversion */
2881     if (WindowsVersionType.tp_name == 0) {
2882         if (_PyStructSequence_InitType(&WindowsVersionType,
2883                                        &windows_version_desc,
2884                                        Py_TPFLAGS_DISALLOW_INSTANTIATION) < 0) {
2885             goto type_init_failed;
2886         }
2887     }
2888 #endif
2889 
2890     /* float repr style: 0.03 (short) vs 0.029999999999999999 (legacy) */
2891 #ifndef PY_NO_SHORT_FLOAT_REPR
2892     SET_SYS_FROM_STRING("float_repr_style", "short");
2893 #else
2894     SET_SYS_FROM_STRING("float_repr_style", "legacy");
2895 #endif
2896 
2897     SET_SYS("thread_info", PyThread_GetInfo());
2898 
2899     /* initialize asyncgen_hooks */
2900     if (AsyncGenHooksType.tp_name == NULL) {
2901         if (PyStructSequence_InitType2(
2902                 &AsyncGenHooksType, &asyncgen_hooks_desc) < 0) {
2903             goto type_init_failed;
2904         }
2905     }
2906 
2907     /* adding sys.path_hooks and sys.path_importer_cache */
2908     SET_SYS("meta_path", PyList_New(0));
2909     SET_SYS("path_importer_cache", PyDict_New());
2910     SET_SYS("path_hooks", PyList_New(0));
2911 
2912     if (_PyErr_Occurred(tstate)) {
2913         goto err_occurred;
2914     }
2915     return _PyStatus_OK();
2916 
2917 type_init_failed:
2918     return _PyStatus_ERR("failed to initialize a type");
2919 
2920 err_occurred:
2921     return _PyStatus_ERR("can't initialize sys module");
2922 }
2923 
2924 static int
sys_add_xoption(PyObject * opts,const wchar_t * s)2925 sys_add_xoption(PyObject *opts, const wchar_t *s)
2926 {
2927     PyObject *name, *value;
2928 
2929     const wchar_t *name_end = wcschr(s, L'=');
2930     if (!name_end) {
2931         name = PyUnicode_FromWideChar(s, -1);
2932         value = Py_True;
2933         Py_INCREF(value);
2934     }
2935     else {
2936         name = PyUnicode_FromWideChar(s, name_end - s);
2937         value = PyUnicode_FromWideChar(name_end + 1, -1);
2938     }
2939     if (name == NULL || value == NULL) {
2940         goto error;
2941     }
2942     if (PyDict_SetItem(opts, name, value) < 0) {
2943         goto error;
2944     }
2945     Py_DECREF(name);
2946     Py_DECREF(value);
2947     return 0;
2948 
2949 error:
2950     Py_XDECREF(name);
2951     Py_XDECREF(value);
2952     return -1;
2953 }
2954 
2955 
2956 static PyObject*
sys_create_xoptions_dict(const PyConfig * config)2957 sys_create_xoptions_dict(const PyConfig *config)
2958 {
2959     Py_ssize_t nxoption = config->xoptions.length;
2960     wchar_t * const * xoptions = config->xoptions.items;
2961     PyObject *dict = PyDict_New();
2962     if (dict == NULL) {
2963         return NULL;
2964     }
2965 
2966     for (Py_ssize_t i=0; i < nxoption; i++) {
2967         const wchar_t *option = xoptions[i];
2968         if (sys_add_xoption(dict, option) < 0) {
2969             Py_DECREF(dict);
2970             return NULL;
2971         }
2972     }
2973 
2974     return dict;
2975 }
2976 
2977 
2978 // Update sys attributes for a new PyConfig configuration.
2979 // This function also adds attributes that _PySys_InitCore() didn't add.
2980 int
_PySys_UpdateConfig(PyThreadState * tstate)2981 _PySys_UpdateConfig(PyThreadState *tstate)
2982 {
2983     PyInterpreterState *interp = tstate->interp;
2984     PyObject *sysdict = interp->sysdict;
2985     const PyConfig *config = _PyInterpreterState_GetConfig(interp);
2986     int res;
2987 
2988 #define COPY_LIST(KEY, VALUE) \
2989         SET_SYS(KEY, _PyWideStringList_AsList(&(VALUE)));
2990 
2991 #define SET_SYS_FROM_WSTR(KEY, VALUE) \
2992         SET_SYS(KEY, PyUnicode_FromWideChar(VALUE, -1));
2993 
2994 #define COPY_WSTR(SYS_ATTR, WSTR) \
2995     if (WSTR != NULL) { \
2996         SET_SYS_FROM_WSTR(SYS_ATTR, WSTR); \
2997     }
2998 
2999     if (config->module_search_paths_set) {
3000         COPY_LIST("path", config->module_search_paths);
3001     }
3002 
3003     COPY_WSTR("executable", config->executable);
3004     COPY_WSTR("_base_executable", config->base_executable);
3005     COPY_WSTR("prefix", config->prefix);
3006     COPY_WSTR("base_prefix", config->base_prefix);
3007     COPY_WSTR("exec_prefix", config->exec_prefix);
3008     COPY_WSTR("base_exec_prefix", config->base_exec_prefix);
3009     COPY_WSTR("platlibdir", config->platlibdir);
3010 
3011     if (config->pycache_prefix != NULL) {
3012         SET_SYS_FROM_WSTR("pycache_prefix", config->pycache_prefix);
3013     } else {
3014         PyDict_SetItemString(sysdict, "pycache_prefix", Py_None);
3015     }
3016 
3017     COPY_LIST("argv", config->argv);
3018     COPY_LIST("orig_argv", config->orig_argv);
3019     COPY_LIST("warnoptions", config->warnoptions);
3020 
3021     SET_SYS("_xoptions", sys_create_xoptions_dict(config));
3022 
3023 #undef SET_SYS_FROM_WSTR
3024 #undef COPY_LIST
3025 #undef COPY_WSTR
3026 
3027     // sys.flags
3028     PyObject *flags = _PySys_GetObject(interp, "flags"); // borrowed ref
3029     if (flags == NULL) {
3030         return -1;
3031     }
3032     if (set_flags_from_config(interp, flags) < 0) {
3033         return -1;
3034     }
3035 
3036     SET_SYS("dont_write_bytecode", PyBool_FromLong(!config->write_bytecode));
3037 
3038     if (_PyErr_Occurred(tstate)) {
3039         goto err_occurred;
3040     }
3041 
3042     return 0;
3043 
3044 err_occurred:
3045     return -1;
3046 }
3047 
3048 #undef SET_SYS
3049 #undef SET_SYS_FROM_STRING
3050 
3051 
3052 /* Set up a preliminary stderr printer until we have enough
3053    infrastructure for the io module in place.
3054 
3055    Use UTF-8/backslashreplace and ignore EAGAIN errors. */
3056 static PyStatus
_PySys_SetPreliminaryStderr(PyObject * sysdict)3057 _PySys_SetPreliminaryStderr(PyObject *sysdict)
3058 {
3059     PyObject *pstderr = PyFile_NewStdPrinter(fileno(stderr));
3060     if (pstderr == NULL) {
3061         goto error;
3062     }
3063     if (_PyDict_SetItemId(sysdict, &PyId_stderr, pstderr) < 0) {
3064         goto error;
3065     }
3066     if (PyDict_SetItemString(sysdict, "__stderr__", pstderr) < 0) {
3067         goto error;
3068     }
3069     Py_DECREF(pstderr);
3070     return _PyStatus_OK();
3071 
3072 error:
3073     Py_XDECREF(pstderr);
3074     return _PyStatus_ERR("can't set preliminary stderr");
3075 }
3076 
3077 
3078 /* Create sys module without all attributes.
3079    _PySys_UpdateConfig() should be called later to add remaining attributes. */
3080 PyStatus
_PySys_Create(PyThreadState * tstate,PyObject ** sysmod_p)3081 _PySys_Create(PyThreadState *tstate, PyObject **sysmod_p)
3082 {
3083     assert(!_PyErr_Occurred(tstate));
3084 
3085     PyInterpreterState *interp = tstate->interp;
3086 
3087     PyObject *modules = PyDict_New();
3088     if (modules == NULL) {
3089         goto error;
3090     }
3091     interp->modules = modules;
3092 
3093     PyObject *sysmod = _PyModule_CreateInitialized(&sysmodule, PYTHON_API_VERSION);
3094     if (sysmod == NULL) {
3095         return _PyStatus_ERR("failed to create a module object");
3096     }
3097 
3098     PyObject *sysdict = PyModule_GetDict(sysmod);
3099     if (sysdict == NULL) {
3100         goto error;
3101     }
3102     Py_INCREF(sysdict);
3103     interp->sysdict = sysdict;
3104 
3105     if (PyDict_SetItemString(sysdict, "modules", interp->modules) < 0) {
3106         goto error;
3107     }
3108 
3109     PyStatus status = _PySys_SetPreliminaryStderr(sysdict);
3110     if (_PyStatus_EXCEPTION(status)) {
3111         return status;
3112     }
3113 
3114     status = _PySys_InitCore(tstate, sysdict);
3115     if (_PyStatus_EXCEPTION(status)) {
3116         return status;
3117     }
3118 
3119     if (_PyImport_FixupBuiltin(sysmod, "sys", interp->modules) < 0) {
3120         goto error;
3121     }
3122 
3123     assert(!_PyErr_Occurred(tstate));
3124 
3125     *sysmod_p = sysmod;
3126     return _PyStatus_OK();
3127 
3128 error:
3129     return _PyStatus_ERR("can't initialize sys module");
3130 }
3131 
3132 
3133 static PyObject *
makepathobject(const wchar_t * path,wchar_t delim)3134 makepathobject(const wchar_t *path, wchar_t delim)
3135 {
3136     int i, n;
3137     const wchar_t *p;
3138     PyObject *v, *w;
3139 
3140     n = 1;
3141     p = path;
3142     while ((p = wcschr(p, delim)) != NULL) {
3143         n++;
3144         p++;
3145     }
3146     v = PyList_New(n);
3147     if (v == NULL)
3148         return NULL;
3149     for (i = 0; ; i++) {
3150         p = wcschr(path, delim);
3151         if (p == NULL)
3152             p = path + wcslen(path); /* End of string */
3153         w = PyUnicode_FromWideChar(path, (Py_ssize_t)(p - path));
3154         if (w == NULL) {
3155             Py_DECREF(v);
3156             return NULL;
3157         }
3158         PyList_SET_ITEM(v, i, w);
3159         if (*p == '\0')
3160             break;
3161         path = p+1;
3162     }
3163     return v;
3164 }
3165 
3166 void
PySys_SetPath(const wchar_t * path)3167 PySys_SetPath(const wchar_t *path)
3168 {
3169     PyObject *v;
3170     if ((v = makepathobject(path, DELIM)) == NULL)
3171         Py_FatalError("can't create sys.path");
3172     PyInterpreterState *interp = _PyInterpreterState_GET();
3173     if (sys_set_object_id(interp, &PyId_path, v) != 0) {
3174         Py_FatalError("can't assign sys.path");
3175     }
3176     Py_DECREF(v);
3177 }
3178 
3179 static PyObject *
make_sys_argv(int argc,wchar_t * const * argv)3180 make_sys_argv(int argc, wchar_t * const * argv)
3181 {
3182     PyObject *list = PyList_New(argc);
3183     if (list == NULL) {
3184         return NULL;
3185     }
3186 
3187     for (Py_ssize_t i = 0; i < argc; i++) {
3188         PyObject *v = PyUnicode_FromWideChar(argv[i], -1);
3189         if (v == NULL) {
3190             Py_DECREF(list);
3191             return NULL;
3192         }
3193         PyList_SET_ITEM(list, i, v);
3194     }
3195     return list;
3196 }
3197 
3198 void
PySys_SetArgvEx(int argc,wchar_t ** argv,int updatepath)3199 PySys_SetArgvEx(int argc, wchar_t **argv, int updatepath)
3200 {
3201     wchar_t* empty_argv[1] = {L""};
3202     PyThreadState *tstate = _PyThreadState_GET();
3203 
3204     if (argc < 1 || argv == NULL) {
3205         /* Ensure at least one (empty) argument is seen */
3206         argv = empty_argv;
3207         argc = 1;
3208     }
3209 
3210     PyObject *av = make_sys_argv(argc, argv);
3211     if (av == NULL) {
3212         Py_FatalError("no mem for sys.argv");
3213     }
3214     if (sys_set_object_str(tstate->interp, "argv", av) != 0) {
3215         Py_DECREF(av);
3216         Py_FatalError("can't assign sys.argv");
3217     }
3218     Py_DECREF(av);
3219 
3220     if (updatepath) {
3221         /* If argv[0] is not '-c' nor '-m', prepend argv[0] to sys.path.
3222            If argv[0] is a symlink, use the real path. */
3223         const PyWideStringList argv_list = {.length = argc, .items = argv};
3224         PyObject *path0 = NULL;
3225         if (_PyPathConfig_ComputeSysPath0(&argv_list, &path0)) {
3226             if (path0 == NULL) {
3227                 Py_FatalError("can't compute path0 from argv");
3228             }
3229 
3230             PyObject *sys_path = sys_get_object_id(tstate, &PyId_path);
3231             if (sys_path != NULL) {
3232                 if (PyList_Insert(sys_path, 0, path0) < 0) {
3233                     Py_DECREF(path0);
3234                     Py_FatalError("can't prepend path0 to sys.path");
3235                 }
3236             }
3237             Py_DECREF(path0);
3238         }
3239     }
3240 }
3241 
3242 void
PySys_SetArgv(int argc,wchar_t ** argv)3243 PySys_SetArgv(int argc, wchar_t **argv)
3244 {
3245     PySys_SetArgvEx(argc, argv, Py_IsolatedFlag == 0);
3246 }
3247 
3248 /* Reimplementation of PyFile_WriteString() no calling indirectly
3249    PyErr_CheckSignals(): avoid the call to PyObject_Str(). */
3250 
3251 static int
sys_pyfile_write_unicode(PyObject * unicode,PyObject * file)3252 sys_pyfile_write_unicode(PyObject *unicode, PyObject *file)
3253 {
3254     if (file == NULL)
3255         return -1;
3256     assert(unicode != NULL);
3257     PyObject *result = _PyObject_CallMethodIdOneArg(file, &PyId_write, unicode);
3258     if (result == NULL) {
3259         return -1;
3260     }
3261     Py_DECREF(result);
3262     return 0;
3263 }
3264 
3265 static int
sys_pyfile_write(const char * text,PyObject * file)3266 sys_pyfile_write(const char *text, PyObject *file)
3267 {
3268     PyObject *unicode = NULL;
3269     int err;
3270 
3271     if (file == NULL)
3272         return -1;
3273 
3274     unicode = PyUnicode_FromString(text);
3275     if (unicode == NULL)
3276         return -1;
3277 
3278     err = sys_pyfile_write_unicode(unicode, file);
3279     Py_DECREF(unicode);
3280     return err;
3281 }
3282 
3283 /* APIs to write to sys.stdout or sys.stderr using a printf-like interface.
3284    Adapted from code submitted by Just van Rossum.
3285 
3286    PySys_WriteStdout(format, ...)
3287    PySys_WriteStderr(format, ...)
3288 
3289       The first function writes to sys.stdout; the second to sys.stderr.  When
3290       there is a problem, they write to the real (C level) stdout or stderr;
3291       no exceptions are raised.
3292 
3293       PyErr_CheckSignals() is not called to avoid the execution of the Python
3294       signal handlers: they may raise a new exception whereas sys_write()
3295       ignores all exceptions.
3296 
3297       Both take a printf-style format string as their first argument followed
3298       by a variable length argument list determined by the format string.
3299 
3300       *** WARNING ***
3301 
3302       The format should limit the total size of the formatted output string to
3303       1000 bytes.  In particular, this means that no unrestricted "%s" formats
3304       should occur; these should be limited using "%.<N>s where <N> is a
3305       decimal number calculated so that <N> plus the maximum size of other
3306       formatted text does not exceed 1000 bytes.  Also watch out for "%f",
3307       which can print hundreds of digits for very large numbers.
3308 
3309  */
3310 
3311 static void
sys_write(_Py_Identifier * key,FILE * fp,const char * format,va_list va)3312 sys_write(_Py_Identifier *key, FILE *fp, const char *format, va_list va)
3313 {
3314     PyObject *file;
3315     PyObject *error_type, *error_value, *error_traceback;
3316     char buffer[1001];
3317     int written;
3318     PyThreadState *tstate = _PyThreadState_GET();
3319 
3320     _PyErr_Fetch(tstate, &error_type, &error_value, &error_traceback);
3321     file = sys_get_object_id(tstate, key);
3322     written = PyOS_vsnprintf(buffer, sizeof(buffer), format, va);
3323     if (sys_pyfile_write(buffer, file) != 0) {
3324         _PyErr_Clear(tstate);
3325         fputs(buffer, fp);
3326     }
3327     if (written < 0 || (size_t)written >= sizeof(buffer)) {
3328         const char *truncated = "... truncated";
3329         if (sys_pyfile_write(truncated, file) != 0)
3330             fputs(truncated, fp);
3331     }
3332     _PyErr_Restore(tstate, error_type, error_value, error_traceback);
3333 }
3334 
3335 void
PySys_WriteStdout(const char * format,...)3336 PySys_WriteStdout(const char *format, ...)
3337 {
3338     va_list va;
3339 
3340     va_start(va, format);
3341     sys_write(&PyId_stdout, stdout, format, va);
3342     va_end(va);
3343 }
3344 
3345 void
PySys_WriteStderr(const char * format,...)3346 PySys_WriteStderr(const char *format, ...)
3347 {
3348     va_list va;
3349 
3350     va_start(va, format);
3351     sys_write(&PyId_stderr, stderr, format, va);
3352     va_end(va);
3353 }
3354 
3355 static void
sys_format(_Py_Identifier * key,FILE * fp,const char * format,va_list va)3356 sys_format(_Py_Identifier *key, FILE *fp, const char *format, va_list va)
3357 {
3358     PyObject *file, *message;
3359     PyObject *error_type, *error_value, *error_traceback;
3360     const char *utf8;
3361     PyThreadState *tstate = _PyThreadState_GET();
3362 
3363     _PyErr_Fetch(tstate, &error_type, &error_value, &error_traceback);
3364     file = sys_get_object_id(tstate, key);
3365     message = PyUnicode_FromFormatV(format, va);
3366     if (message != NULL) {
3367         if (sys_pyfile_write_unicode(message, file) != 0) {
3368             _PyErr_Clear(tstate);
3369             utf8 = PyUnicode_AsUTF8(message);
3370             if (utf8 != NULL)
3371                 fputs(utf8, fp);
3372         }
3373         Py_DECREF(message);
3374     }
3375     _PyErr_Restore(tstate, error_type, error_value, error_traceback);
3376 }
3377 
3378 void
PySys_FormatStdout(const char * format,...)3379 PySys_FormatStdout(const char *format, ...)
3380 {
3381     va_list va;
3382 
3383     va_start(va, format);
3384     sys_format(&PyId_stdout, stdout, format, va);
3385     va_end(va);
3386 }
3387 
3388 void
PySys_FormatStderr(const char * format,...)3389 PySys_FormatStderr(const char *format, ...)
3390 {
3391     va_list va;
3392 
3393     va_start(va, format);
3394     sys_format(&PyId_stderr, stderr, format, va);
3395     va_end(va);
3396 }
3397