This repository has been archived by the owner on May 9, 2023. It is now read-only.
-
Notifications
You must be signed in to change notification settings - Fork 4
/
what.c
70 lines (55 loc) · 1.84 KB
/
what.c
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
#define PY_SSIZE_T_CLEAN
#include <Python.h>
#include "frameobject.h"
static PyObject *
what_next(PyObject *self, PyObject *arg)
{
if (!PyFrame_Check(arg)) {
PyErr_SetString(PyExc_TypeError, "Argument must be a frame object.");
return NULL;
}
PyFrameObject *frame = (PyFrameObject *)arg;
// FIXME validate that current instruction is YIELD_FROM
// Due to optimisations, it may be the preceding GET_AWAITABLE
// int opcode = _Py_OPCODE(*next_instr);
// printf("val %p top %p delta value to top: %ld\n",
// frame->f_valuestack,
// frame->f_stacktop,
// (long)(frame->f_stacktop - frame->f_valuestack));
PyObject **stack_pointer = frame->f_stacktop;
if (frame->f_stacktop == frame->f_valuestack) {
PyErr_SetString(PyExc_ValueError, "stack is empty");
return NULL;
}
if (!stack_pointer) {
PyErr_SetString(PyExc_ValueError, "stack pointer is null?");
return NULL;
}
// Top-most on the value stack ought to be the "receiver".
PyObject *next = stack_pointer[-1];
if (!next) {
PyErr_SetString(PyExc_SystemError, "thing on stack is null?");
return NULL;
}
Py_INCREF(next);
return next;
}
static PyMethodDef what_functions[] = {
{"next", what_next, METH_O,
"Next frame for the given frame."}, /* FIXME: function docstring */
{NULL, NULL, 0, NULL}};
static struct PyModuleDef whatmodule = {
PyModuleDef_HEAD_INIT, "what", /* name of module */
NULL, /* FIXME: module docstring, module documentation, may be NULL */
0, /* size of per-interpreter state of the module */
what_functions};
PyMODINIT_FUNC
PyInit__what(void)
{
PyObject *m;
m = PyModule_Create(&whatmodule);
if (m == NULL)
return NULL;
PyModule_AddFunctions(m, what_functions);
return m;
}