diff options
| author | Johannes Berg <johannes@sipsolutions.net> | 2010-05-15 05:05:54 -0400 |
|---|---|---|
| committer | Johannes Berg <johannes@sipsolutions.net> | 2010-05-25 07:17:03 -0400 |
| commit | c6ed0d9b74dc0ffc29b3e8b11fb199517b2c251e (patch) | |
| tree | 8fac1ac694418596adae78abe868a7f3756a13c8 | |
| parent | 436458c3567f64355095e0b75474d94bdfe9646f (diff) | |
python: provide more C methods
This provides the C methods for wrapping
callbacks and the upcoming Event/Field
classes.
Acked-by: Darren Hart <dvhltc@us.ibm.com>
Signed-off-by: Johannes Berg <johannes@sipsolutions.net>
| -rw-r--r-- | ctracecmd.i | 113 |
1 files changed, 113 insertions, 0 deletions
diff --git a/ctracecmd.i b/ctracecmd.i index ea62772..9569419 100644 --- a/ctracecmd.i +++ b/ctracecmd.i | |||
| @@ -17,6 +17,119 @@ | |||
| 17 | #include "trace-cmd.h" | 17 | #include "trace-cmd.h" |
| 18 | %} | 18 | %} |
| 19 | 19 | ||
| 20 | |||
| 21 | %typemap(in) PyObject *pyfunc { | ||
| 22 | if (!PyCallable_Check($input)) { | ||
| 23 | PyErr_SetString(PyExc_TypeError, "Need a callable object!"); | ||
| 24 | return NULL; | ||
| 25 | } | ||
| 26 | $1 = $input; | ||
| 27 | } | ||
| 28 | |||
| 29 | %ignore python_callback; | ||
| 30 | |||
| 31 | %inline %{ | ||
| 32 | static int python_callback(struct trace_seq *s, | ||
| 33 | struct record *record, | ||
| 34 | struct event_format *event, | ||
| 35 | void *context); | ||
| 36 | |||
| 37 | void py_pevent_register_event_handler(struct pevent *pevent, int id, | ||
| 38 | char *subsys, char *evname, | ||
| 39 | PyObject *pyfunc) | ||
| 40 | { | ||
| 41 | Py_INCREF(pyfunc); | ||
| 42 | pevent_register_event_handler(pevent, id, subsys, evname, | ||
| 43 | python_callback, pyfunc); | ||
| 44 | } | ||
| 45 | |||
| 46 | static PyObject *py_field_get_data(struct format_field *f, struct record *r) | ||
| 47 | { | ||
| 48 | if (!strncmp(f->type, "__data_loc ", 11)) { | ||
| 49 | unsigned long long val; | ||
| 50 | int len, offset; | ||
| 51 | |||
| 52 | if (pevent_read_number_field(f, r->data, &val)) { | ||
| 53 | PyErr_SetString(PyExc_TypeError, | ||
| 54 | "Field is not a valid number"); | ||
| 55 | return NULL; | ||
| 56 | } | ||
| 57 | |||
| 58 | /* | ||
| 59 | * The actual length of the dynamic array is stored | ||
| 60 | * in the top half of the field, and the offset | ||
| 61 | * is in the bottom half of the 32 bit field. | ||
| 62 | */ | ||
| 63 | offset = val & 0xffff; | ||
| 64 | len = val >> 16; | ||
| 65 | |||
| 66 | return PyBuffer_FromMemory((char *)r->data + offset, len); | ||
| 67 | } | ||
| 68 | |||
| 69 | return PyBuffer_FromMemory((char *)r->data + f->offset, f->size); | ||
| 70 | } | ||
| 71 | |||
| 72 | static PyObject *py_format_get_keys(struct event_format *ef) | ||
| 73 | { | ||
| 74 | PyObject *list; | ||
| 75 | struct format_field *f; | ||
| 76 | |||
| 77 | list = PyList_New(0); | ||
| 78 | |||
| 79 | for (f = ef->format.fields; f; f = f->next) { | ||
| 80 | if (PyList_Append(list, PyString_FromString(f->name))) { | ||
| 81 | Py_DECREF(list); | ||
| 82 | return NULL; | ||
| 83 | } | ||
| 84 | } | ||
| 85 | |||
| 86 | return list; | ||
| 87 | } | ||
| 88 | %} | ||
| 89 | |||
| 90 | |||
| 91 | %wrapper %{ | ||
| 92 | static int python_callback(struct trace_seq *s, | ||
| 93 | struct record *record, | ||
| 94 | struct event_format *event, | ||
| 95 | void *context) | ||
| 96 | { | ||
| 97 | PyObject *arglist, *result; | ||
| 98 | int r = 0; | ||
| 99 | |||
| 100 | record->ref_count++; | ||
| 101 | |||
| 102 | arglist = Py_BuildValue("(OOO)", | ||
| 103 | SWIG_NewPointerObj(SWIG_as_voidptr(s), | ||
| 104 | SWIGTYPE_p_trace_seq, 0), | ||
| 105 | SWIG_NewPointerObj(SWIG_as_voidptr(record), | ||
| 106 | SWIGTYPE_p_record, 0), | ||
| 107 | SWIG_NewPointerObj(SWIG_as_voidptr(event), | ||
| 108 | SWIGTYPE_p_event_format, 0)); | ||
| 109 | |||
| 110 | result = PyEval_CallObject(context, arglist); | ||
| 111 | Py_XDECREF(arglist); | ||
| 112 | if (result && result != Py_None) { | ||
| 113 | if (!PyInt_Check(result)) { | ||
| 114 | PyErr_SetString(PyExc_TypeError, | ||
| 115 | "callback must return int"); | ||
| 116 | PyErr_Print(); | ||
| 117 | Py_XDECREF(result); | ||
| 118 | return 0; | ||
| 119 | } | ||
| 120 | r = PyInt_AS_LONG(result); | ||
| 121 | } else if (result == Py_None) | ||
| 122 | r = 0; | ||
| 123 | else | ||
| 124 | PyErr_Print(); | ||
| 125 | |||
| 126 | Py_XDECREF(result); | ||
| 127 | |||
| 128 | return r; | ||
| 129 | } | ||
| 130 | %} | ||
| 131 | |||
| 132 | |||
| 20 | %ignore trace_seq_vprintf; | 133 | %ignore trace_seq_vprintf; |
| 21 | 134 | ||
| 22 | /* SWIG can't grok these, define them to nothing */ | 135 | /* SWIG can't grok these, define them to nothing */ |
