When your code is called from Python, you may assume your thread has the GIL. When your code is called from anything that is not Python, you may not make this assumption.
You must have the GIL before you can call into any part of the Python/C API unless explicitly documented otherwise. This includes everything owned by the Python/C API, even simple things like the refcounting macros Py_INCREF() and Py_DECREF().
The GIL does not release itself automatically while execution is within a C or C++ function. You need to do that manually if you do not need the GIL. In particular, it does not automatically release itself when you call a blocking function like pthread_join() or select(), which means you block the whole interpreter.