1

When writing a Python extension with C code, one can print to the python standard output and standard error streams using functions PySys_WriteStdout and PySys_WriteStderr, which work similarly to C's printf (https://docs.python.org/3/c-api/sys.html).

But after printing something through those functions, how can I flush the corresponding output stream? E.g. like C's fflush(stdout) and fflush(stderr).

anymous.asker
  • 1,179
  • 9
  • 14

1 Answers1

1

You can do two things from what I remember based on the PySys_WriteStdout() call which simply calls sysmodule.sys_write(_Py_Identifier *key, FILE *fp, const char *format, va_list va):

  • unset the sys.stdout, thus you'll access the raw STDOUT, not just Python's wrapper and for that you should be able to use standard C flushing
  • get the reference for sys.stdout and flush it directly

Optionally, just set PYTHONUNBUFFERED as env var, but it's not as flexible and isn't present by default in the system

For the sys.stdout flushing, you might also be able to utilize PySys_GetObject(const char *name) directly and then call the io.IOBase.flush() in the sys.stdout reference.

PySys_GetObject("__stdout__") according to the implementation in the pylifecycle.init_sys_streams(PyThreadState *tstate)

Or if you want to live dangerously, just pull the private API (_PySys_GetObjectId(&PyId_stdout)) to utilize the same way CPython does. It's defined in bltinmodule.c via _Py_IDENTIFIER(varname).

Here is how CPython does the flushing via its pylifecycle.flush_std_files() function.

Peter Badida
  • 11,310
  • 10
  • 44
  • 90