1877108e4SArnaldo Carvalho de Melo #include <Python.h> 2877108e4SArnaldo Carvalho de Melo #include <structmember.h> 3877108e4SArnaldo Carvalho de Melo #include <inttypes.h> 4877108e4SArnaldo Carvalho de Melo #include <poll.h> 5877108e4SArnaldo Carvalho de Melo #include "evlist.h" 6877108e4SArnaldo Carvalho de Melo #include "evsel.h" 7877108e4SArnaldo Carvalho de Melo #include "event.h" 8877108e4SArnaldo Carvalho de Melo #include "cpumap.h" 9877108e4SArnaldo Carvalho de Melo #include "thread_map.h" 10877108e4SArnaldo Carvalho de Melo 118afb4c01SAdrian Hunter /* 128afb4c01SAdrian Hunter * Support debug printing even though util/debug.c is not linked. That means 138afb4c01SAdrian Hunter * implementing 'verbose' and 'eprintf'. 148afb4c01SAdrian Hunter */ 158afb4c01SAdrian Hunter int verbose; 168afb4c01SAdrian Hunter 178afb4c01SAdrian Hunter int eprintf(int level, const char *fmt, ...) 188afb4c01SAdrian Hunter { 198afb4c01SAdrian Hunter va_list args; 208afb4c01SAdrian Hunter int ret = 0; 218afb4c01SAdrian Hunter 228afb4c01SAdrian Hunter if (verbose >= level) { 238afb4c01SAdrian Hunter va_start(args, fmt); 248afb4c01SAdrian Hunter ret = vfprintf(stderr, fmt, args); 258afb4c01SAdrian Hunter va_end(args); 268afb4c01SAdrian Hunter } 278afb4c01SAdrian Hunter 288afb4c01SAdrian Hunter return ret; 298afb4c01SAdrian Hunter } 308afb4c01SAdrian Hunter 31cfff2d90SFrederic Weisbecker /* Define PyVarObject_HEAD_INIT for python 2.5 */ 32cfff2d90SFrederic Weisbecker #ifndef PyVarObject_HEAD_INIT 33cfff2d90SFrederic Weisbecker # define PyVarObject_HEAD_INIT(type, size) PyObject_HEAD_INIT(type) size, 34cfff2d90SFrederic Weisbecker #endif 35cfff2d90SFrederic Weisbecker 36877108e4SArnaldo Carvalho de Melo struct throttle_event { 37877108e4SArnaldo Carvalho de Melo struct perf_event_header header; 38877108e4SArnaldo Carvalho de Melo u64 time; 39877108e4SArnaldo Carvalho de Melo u64 id; 40877108e4SArnaldo Carvalho de Melo u64 stream_id; 41877108e4SArnaldo Carvalho de Melo }; 42877108e4SArnaldo Carvalho de Melo 43f6bbc1daSArnaldo Carvalho de Melo PyMODINIT_FUNC initperf(void); 44f6bbc1daSArnaldo Carvalho de Melo 45877108e4SArnaldo Carvalho de Melo #define member_def(type, member, ptype, help) \ 46877108e4SArnaldo Carvalho de Melo { #member, ptype, \ 47877108e4SArnaldo Carvalho de Melo offsetof(struct pyrf_event, event) + offsetof(struct type, member), \ 48877108e4SArnaldo Carvalho de Melo 0, help } 49877108e4SArnaldo Carvalho de Melo 50877108e4SArnaldo Carvalho de Melo #define sample_member_def(name, member, ptype, help) \ 51877108e4SArnaldo Carvalho de Melo { #name, ptype, \ 52877108e4SArnaldo Carvalho de Melo offsetof(struct pyrf_event, sample) + offsetof(struct perf_sample, member), \ 53877108e4SArnaldo Carvalho de Melo 0, help } 54877108e4SArnaldo Carvalho de Melo 55877108e4SArnaldo Carvalho de Melo struct pyrf_event { 56877108e4SArnaldo Carvalho de Melo PyObject_HEAD 57877108e4SArnaldo Carvalho de Melo struct perf_sample sample; 58877108e4SArnaldo Carvalho de Melo union perf_event event; 59877108e4SArnaldo Carvalho de Melo }; 60877108e4SArnaldo Carvalho de Melo 61877108e4SArnaldo Carvalho de Melo #define sample_members \ 62f6bbc1daSArnaldo Carvalho de Melo sample_member_def(sample_ip, ip, T_ULONGLONG, "event type"), \ 63877108e4SArnaldo Carvalho de Melo sample_member_def(sample_pid, pid, T_INT, "event pid"), \ 64877108e4SArnaldo Carvalho de Melo sample_member_def(sample_tid, tid, T_INT, "event tid"), \ 65f6bbc1daSArnaldo Carvalho de Melo sample_member_def(sample_time, time, T_ULONGLONG, "event timestamp"), \ 66f6bbc1daSArnaldo Carvalho de Melo sample_member_def(sample_addr, addr, T_ULONGLONG, "event addr"), \ 67f6bbc1daSArnaldo Carvalho de Melo sample_member_def(sample_id, id, T_ULONGLONG, "event id"), \ 68f6bbc1daSArnaldo Carvalho de Melo sample_member_def(sample_stream_id, stream_id, T_ULONGLONG, "event stream id"), \ 69f6bbc1daSArnaldo Carvalho de Melo sample_member_def(sample_period, period, T_ULONGLONG, "event period"), \ 70877108e4SArnaldo Carvalho de Melo sample_member_def(sample_cpu, cpu, T_UINT, "event cpu"), 71877108e4SArnaldo Carvalho de Melo 72877108e4SArnaldo Carvalho de Melo static char pyrf_mmap_event__doc[] = PyDoc_STR("perf mmap event object."); 73877108e4SArnaldo Carvalho de Melo 74877108e4SArnaldo Carvalho de Melo static PyMemberDef pyrf_mmap_event__members[] = { 75877108e4SArnaldo Carvalho de Melo sample_members 76877108e4SArnaldo Carvalho de Melo member_def(perf_event_header, type, T_UINT, "event type"), 77877108e4SArnaldo Carvalho de Melo member_def(mmap_event, pid, T_UINT, "event pid"), 78877108e4SArnaldo Carvalho de Melo member_def(mmap_event, tid, T_UINT, "event tid"), 79f6bbc1daSArnaldo Carvalho de Melo member_def(mmap_event, start, T_ULONGLONG, "start of the map"), 80f6bbc1daSArnaldo Carvalho de Melo member_def(mmap_event, len, T_ULONGLONG, "map length"), 81f6bbc1daSArnaldo Carvalho de Melo member_def(mmap_event, pgoff, T_ULONGLONG, "page offset"), 82877108e4SArnaldo Carvalho de Melo member_def(mmap_event, filename, T_STRING_INPLACE, "backing store"), 83f6bbc1daSArnaldo Carvalho de Melo { .name = NULL, }, 84877108e4SArnaldo Carvalho de Melo }; 85877108e4SArnaldo Carvalho de Melo 86877108e4SArnaldo Carvalho de Melo static PyObject *pyrf_mmap_event__repr(struct pyrf_event *pevent) 87877108e4SArnaldo Carvalho de Melo { 88877108e4SArnaldo Carvalho de Melo PyObject *ret; 89877108e4SArnaldo Carvalho de Melo char *s; 90877108e4SArnaldo Carvalho de Melo 91877108e4SArnaldo Carvalho de Melo if (asprintf(&s, "{ type: mmap, pid: %u, tid: %u, start: %#" PRIx64 ", " 92877108e4SArnaldo Carvalho de Melo "length: %#" PRIx64 ", offset: %#" PRIx64 ", " 93877108e4SArnaldo Carvalho de Melo "filename: %s }", 94877108e4SArnaldo Carvalho de Melo pevent->event.mmap.pid, pevent->event.mmap.tid, 95877108e4SArnaldo Carvalho de Melo pevent->event.mmap.start, pevent->event.mmap.len, 96877108e4SArnaldo Carvalho de Melo pevent->event.mmap.pgoff, pevent->event.mmap.filename) < 0) { 97877108e4SArnaldo Carvalho de Melo ret = PyErr_NoMemory(); 98877108e4SArnaldo Carvalho de Melo } else { 99877108e4SArnaldo Carvalho de Melo ret = PyString_FromString(s); 100877108e4SArnaldo Carvalho de Melo free(s); 101877108e4SArnaldo Carvalho de Melo } 102877108e4SArnaldo Carvalho de Melo return ret; 103877108e4SArnaldo Carvalho de Melo } 104877108e4SArnaldo Carvalho de Melo 105877108e4SArnaldo Carvalho de Melo static PyTypeObject pyrf_mmap_event__type = { 106877108e4SArnaldo Carvalho de Melo PyVarObject_HEAD_INIT(NULL, 0) 107877108e4SArnaldo Carvalho de Melo .tp_name = "perf.mmap_event", 108877108e4SArnaldo Carvalho de Melo .tp_basicsize = sizeof(struct pyrf_event), 109877108e4SArnaldo Carvalho de Melo .tp_flags = Py_TPFLAGS_DEFAULT|Py_TPFLAGS_BASETYPE, 110877108e4SArnaldo Carvalho de Melo .tp_doc = pyrf_mmap_event__doc, 111877108e4SArnaldo Carvalho de Melo .tp_members = pyrf_mmap_event__members, 112877108e4SArnaldo Carvalho de Melo .tp_repr = (reprfunc)pyrf_mmap_event__repr, 113877108e4SArnaldo Carvalho de Melo }; 114877108e4SArnaldo Carvalho de Melo 115877108e4SArnaldo Carvalho de Melo static char pyrf_task_event__doc[] = PyDoc_STR("perf task (fork/exit) event object."); 116877108e4SArnaldo Carvalho de Melo 117877108e4SArnaldo Carvalho de Melo static PyMemberDef pyrf_task_event__members[] = { 118877108e4SArnaldo Carvalho de Melo sample_members 119877108e4SArnaldo Carvalho de Melo member_def(perf_event_header, type, T_UINT, "event type"), 120877108e4SArnaldo Carvalho de Melo member_def(fork_event, pid, T_UINT, "event pid"), 121877108e4SArnaldo Carvalho de Melo member_def(fork_event, ppid, T_UINT, "event ppid"), 122877108e4SArnaldo Carvalho de Melo member_def(fork_event, tid, T_UINT, "event tid"), 123877108e4SArnaldo Carvalho de Melo member_def(fork_event, ptid, T_UINT, "event ptid"), 124f6bbc1daSArnaldo Carvalho de Melo member_def(fork_event, time, T_ULONGLONG, "timestamp"), 125f6bbc1daSArnaldo Carvalho de Melo { .name = NULL, }, 126877108e4SArnaldo Carvalho de Melo }; 127877108e4SArnaldo Carvalho de Melo 128877108e4SArnaldo Carvalho de Melo static PyObject *pyrf_task_event__repr(struct pyrf_event *pevent) 129877108e4SArnaldo Carvalho de Melo { 130877108e4SArnaldo Carvalho de Melo return PyString_FromFormat("{ type: %s, pid: %u, ppid: %u, tid: %u, " 131877108e4SArnaldo Carvalho de Melo "ptid: %u, time: %" PRIu64 "}", 132877108e4SArnaldo Carvalho de Melo pevent->event.header.type == PERF_RECORD_FORK ? "fork" : "exit", 133877108e4SArnaldo Carvalho de Melo pevent->event.fork.pid, 134877108e4SArnaldo Carvalho de Melo pevent->event.fork.ppid, 135877108e4SArnaldo Carvalho de Melo pevent->event.fork.tid, 136877108e4SArnaldo Carvalho de Melo pevent->event.fork.ptid, 137877108e4SArnaldo Carvalho de Melo pevent->event.fork.time); 138877108e4SArnaldo Carvalho de Melo } 139877108e4SArnaldo Carvalho de Melo 140877108e4SArnaldo Carvalho de Melo static PyTypeObject pyrf_task_event__type = { 141877108e4SArnaldo Carvalho de Melo PyVarObject_HEAD_INIT(NULL, 0) 142877108e4SArnaldo Carvalho de Melo .tp_name = "perf.task_event", 143877108e4SArnaldo Carvalho de Melo .tp_basicsize = sizeof(struct pyrf_event), 144877108e4SArnaldo Carvalho de Melo .tp_flags = Py_TPFLAGS_DEFAULT|Py_TPFLAGS_BASETYPE, 145877108e4SArnaldo Carvalho de Melo .tp_doc = pyrf_task_event__doc, 146877108e4SArnaldo Carvalho de Melo .tp_members = pyrf_task_event__members, 147877108e4SArnaldo Carvalho de Melo .tp_repr = (reprfunc)pyrf_task_event__repr, 148877108e4SArnaldo Carvalho de Melo }; 149877108e4SArnaldo Carvalho de Melo 150877108e4SArnaldo Carvalho de Melo static char pyrf_comm_event__doc[] = PyDoc_STR("perf comm event object."); 151877108e4SArnaldo Carvalho de Melo 152877108e4SArnaldo Carvalho de Melo static PyMemberDef pyrf_comm_event__members[] = { 153877108e4SArnaldo Carvalho de Melo sample_members 154877108e4SArnaldo Carvalho de Melo member_def(perf_event_header, type, T_UINT, "event type"), 155877108e4SArnaldo Carvalho de Melo member_def(comm_event, pid, T_UINT, "event pid"), 156877108e4SArnaldo Carvalho de Melo member_def(comm_event, tid, T_UINT, "event tid"), 157877108e4SArnaldo Carvalho de Melo member_def(comm_event, comm, T_STRING_INPLACE, "process name"), 158f6bbc1daSArnaldo Carvalho de Melo { .name = NULL, }, 159877108e4SArnaldo Carvalho de Melo }; 160877108e4SArnaldo Carvalho de Melo 161877108e4SArnaldo Carvalho de Melo static PyObject *pyrf_comm_event__repr(struct pyrf_event *pevent) 162877108e4SArnaldo Carvalho de Melo { 163877108e4SArnaldo Carvalho de Melo return PyString_FromFormat("{ type: comm, pid: %u, tid: %u, comm: %s }", 164877108e4SArnaldo Carvalho de Melo pevent->event.comm.pid, 165877108e4SArnaldo Carvalho de Melo pevent->event.comm.tid, 166877108e4SArnaldo Carvalho de Melo pevent->event.comm.comm); 167877108e4SArnaldo Carvalho de Melo } 168877108e4SArnaldo Carvalho de Melo 169877108e4SArnaldo Carvalho de Melo static PyTypeObject pyrf_comm_event__type = { 170877108e4SArnaldo Carvalho de Melo PyVarObject_HEAD_INIT(NULL, 0) 171877108e4SArnaldo Carvalho de Melo .tp_name = "perf.comm_event", 172877108e4SArnaldo Carvalho de Melo .tp_basicsize = sizeof(struct pyrf_event), 173877108e4SArnaldo Carvalho de Melo .tp_flags = Py_TPFLAGS_DEFAULT|Py_TPFLAGS_BASETYPE, 174877108e4SArnaldo Carvalho de Melo .tp_doc = pyrf_comm_event__doc, 175877108e4SArnaldo Carvalho de Melo .tp_members = pyrf_comm_event__members, 176877108e4SArnaldo Carvalho de Melo .tp_repr = (reprfunc)pyrf_comm_event__repr, 177877108e4SArnaldo Carvalho de Melo }; 178877108e4SArnaldo Carvalho de Melo 179877108e4SArnaldo Carvalho de Melo static char pyrf_throttle_event__doc[] = PyDoc_STR("perf throttle event object."); 180877108e4SArnaldo Carvalho de Melo 181877108e4SArnaldo Carvalho de Melo static PyMemberDef pyrf_throttle_event__members[] = { 182877108e4SArnaldo Carvalho de Melo sample_members 183877108e4SArnaldo Carvalho de Melo member_def(perf_event_header, type, T_UINT, "event type"), 184f6bbc1daSArnaldo Carvalho de Melo member_def(throttle_event, time, T_ULONGLONG, "timestamp"), 185f6bbc1daSArnaldo Carvalho de Melo member_def(throttle_event, id, T_ULONGLONG, "event id"), 186f6bbc1daSArnaldo Carvalho de Melo member_def(throttle_event, stream_id, T_ULONGLONG, "event stream id"), 187f6bbc1daSArnaldo Carvalho de Melo { .name = NULL, }, 188877108e4SArnaldo Carvalho de Melo }; 189877108e4SArnaldo Carvalho de Melo 190877108e4SArnaldo Carvalho de Melo static PyObject *pyrf_throttle_event__repr(struct pyrf_event *pevent) 191877108e4SArnaldo Carvalho de Melo { 192877108e4SArnaldo Carvalho de Melo struct throttle_event *te = (struct throttle_event *)(&pevent->event.header + 1); 193877108e4SArnaldo Carvalho de Melo 194877108e4SArnaldo Carvalho de Melo return PyString_FromFormat("{ type: %sthrottle, time: %" PRIu64 ", id: %" PRIu64 195877108e4SArnaldo Carvalho de Melo ", stream_id: %" PRIu64 " }", 196877108e4SArnaldo Carvalho de Melo pevent->event.header.type == PERF_RECORD_THROTTLE ? "" : "un", 197877108e4SArnaldo Carvalho de Melo te->time, te->id, te->stream_id); 198877108e4SArnaldo Carvalho de Melo } 199877108e4SArnaldo Carvalho de Melo 200877108e4SArnaldo Carvalho de Melo static PyTypeObject pyrf_throttle_event__type = { 201877108e4SArnaldo Carvalho de Melo PyVarObject_HEAD_INIT(NULL, 0) 202877108e4SArnaldo Carvalho de Melo .tp_name = "perf.throttle_event", 203877108e4SArnaldo Carvalho de Melo .tp_basicsize = sizeof(struct pyrf_event), 204877108e4SArnaldo Carvalho de Melo .tp_flags = Py_TPFLAGS_DEFAULT|Py_TPFLAGS_BASETYPE, 205877108e4SArnaldo Carvalho de Melo .tp_doc = pyrf_throttle_event__doc, 206877108e4SArnaldo Carvalho de Melo .tp_members = pyrf_throttle_event__members, 207877108e4SArnaldo Carvalho de Melo .tp_repr = (reprfunc)pyrf_throttle_event__repr, 208877108e4SArnaldo Carvalho de Melo }; 209877108e4SArnaldo Carvalho de Melo 2103e9f45a7SArnaldo Carvalho de Melo static char pyrf_lost_event__doc[] = PyDoc_STR("perf lost event object."); 2113e9f45a7SArnaldo Carvalho de Melo 2123e9f45a7SArnaldo Carvalho de Melo static PyMemberDef pyrf_lost_event__members[] = { 2133e9f45a7SArnaldo Carvalho de Melo sample_members 2143e9f45a7SArnaldo Carvalho de Melo member_def(lost_event, id, T_ULONGLONG, "event id"), 2153e9f45a7SArnaldo Carvalho de Melo member_def(lost_event, lost, T_ULONGLONG, "number of lost events"), 2163e9f45a7SArnaldo Carvalho de Melo { .name = NULL, }, 2173e9f45a7SArnaldo Carvalho de Melo }; 2183e9f45a7SArnaldo Carvalho de Melo 2193e9f45a7SArnaldo Carvalho de Melo static PyObject *pyrf_lost_event__repr(struct pyrf_event *pevent) 2203e9f45a7SArnaldo Carvalho de Melo { 2213e9f45a7SArnaldo Carvalho de Melo PyObject *ret; 2223e9f45a7SArnaldo Carvalho de Melo char *s; 2233e9f45a7SArnaldo Carvalho de Melo 2243e9f45a7SArnaldo Carvalho de Melo if (asprintf(&s, "{ type: lost, id: %#" PRIx64 ", " 2253e9f45a7SArnaldo Carvalho de Melo "lost: %#" PRIx64 " }", 2263e9f45a7SArnaldo Carvalho de Melo pevent->event.lost.id, pevent->event.lost.lost) < 0) { 2273e9f45a7SArnaldo Carvalho de Melo ret = PyErr_NoMemory(); 2283e9f45a7SArnaldo Carvalho de Melo } else { 2293e9f45a7SArnaldo Carvalho de Melo ret = PyString_FromString(s); 2303e9f45a7SArnaldo Carvalho de Melo free(s); 2313e9f45a7SArnaldo Carvalho de Melo } 2323e9f45a7SArnaldo Carvalho de Melo return ret; 2333e9f45a7SArnaldo Carvalho de Melo } 2343e9f45a7SArnaldo Carvalho de Melo 2353e9f45a7SArnaldo Carvalho de Melo static PyTypeObject pyrf_lost_event__type = { 2363e9f45a7SArnaldo Carvalho de Melo PyVarObject_HEAD_INIT(NULL, 0) 2373e9f45a7SArnaldo Carvalho de Melo .tp_name = "perf.lost_event", 2383e9f45a7SArnaldo Carvalho de Melo .tp_basicsize = sizeof(struct pyrf_event), 2393e9f45a7SArnaldo Carvalho de Melo .tp_flags = Py_TPFLAGS_DEFAULT|Py_TPFLAGS_BASETYPE, 2403e9f45a7SArnaldo Carvalho de Melo .tp_doc = pyrf_lost_event__doc, 2413e9f45a7SArnaldo Carvalho de Melo .tp_members = pyrf_lost_event__members, 2423e9f45a7SArnaldo Carvalho de Melo .tp_repr = (reprfunc)pyrf_lost_event__repr, 2433e9f45a7SArnaldo Carvalho de Melo }; 2443e9f45a7SArnaldo Carvalho de Melo 2453e9f45a7SArnaldo Carvalho de Melo static char pyrf_read_event__doc[] = PyDoc_STR("perf read event object."); 2463e9f45a7SArnaldo Carvalho de Melo 2473e9f45a7SArnaldo Carvalho de Melo static PyMemberDef pyrf_read_event__members[] = { 2483e9f45a7SArnaldo Carvalho de Melo sample_members 2493e9f45a7SArnaldo Carvalho de Melo member_def(read_event, pid, T_UINT, "event pid"), 2503e9f45a7SArnaldo Carvalho de Melo member_def(read_event, tid, T_UINT, "event tid"), 2513e9f45a7SArnaldo Carvalho de Melo { .name = NULL, }, 2523e9f45a7SArnaldo Carvalho de Melo }; 2533e9f45a7SArnaldo Carvalho de Melo 2543e9f45a7SArnaldo Carvalho de Melo static PyObject *pyrf_read_event__repr(struct pyrf_event *pevent) 2553e9f45a7SArnaldo Carvalho de Melo { 2563e9f45a7SArnaldo Carvalho de Melo return PyString_FromFormat("{ type: read, pid: %u, tid: %u }", 2573e9f45a7SArnaldo Carvalho de Melo pevent->event.read.pid, 2583e9f45a7SArnaldo Carvalho de Melo pevent->event.read.tid); 2593e9f45a7SArnaldo Carvalho de Melo /* 2603e9f45a7SArnaldo Carvalho de Melo * FIXME: return the array of read values, 2613e9f45a7SArnaldo Carvalho de Melo * making this method useful ;-) 2623e9f45a7SArnaldo Carvalho de Melo */ 2633e9f45a7SArnaldo Carvalho de Melo } 2643e9f45a7SArnaldo Carvalho de Melo 2653e9f45a7SArnaldo Carvalho de Melo static PyTypeObject pyrf_read_event__type = { 2663e9f45a7SArnaldo Carvalho de Melo PyVarObject_HEAD_INIT(NULL, 0) 2673e9f45a7SArnaldo Carvalho de Melo .tp_name = "perf.read_event", 2683e9f45a7SArnaldo Carvalho de Melo .tp_basicsize = sizeof(struct pyrf_event), 2693e9f45a7SArnaldo Carvalho de Melo .tp_flags = Py_TPFLAGS_DEFAULT|Py_TPFLAGS_BASETYPE, 2703e9f45a7SArnaldo Carvalho de Melo .tp_doc = pyrf_read_event__doc, 2713e9f45a7SArnaldo Carvalho de Melo .tp_members = pyrf_read_event__members, 2723e9f45a7SArnaldo Carvalho de Melo .tp_repr = (reprfunc)pyrf_read_event__repr, 2733e9f45a7SArnaldo Carvalho de Melo }; 2743e9f45a7SArnaldo Carvalho de Melo 2753e9f45a7SArnaldo Carvalho de Melo static char pyrf_sample_event__doc[] = PyDoc_STR("perf sample event object."); 2763e9f45a7SArnaldo Carvalho de Melo 2773e9f45a7SArnaldo Carvalho de Melo static PyMemberDef pyrf_sample_event__members[] = { 2783e9f45a7SArnaldo Carvalho de Melo sample_members 2793e9f45a7SArnaldo Carvalho de Melo member_def(perf_event_header, type, T_UINT, "event type"), 2803e9f45a7SArnaldo Carvalho de Melo { .name = NULL, }, 2813e9f45a7SArnaldo Carvalho de Melo }; 2823e9f45a7SArnaldo Carvalho de Melo 2833e9f45a7SArnaldo Carvalho de Melo static PyObject *pyrf_sample_event__repr(struct pyrf_event *pevent) 2843e9f45a7SArnaldo Carvalho de Melo { 2853e9f45a7SArnaldo Carvalho de Melo PyObject *ret; 2863e9f45a7SArnaldo Carvalho de Melo char *s; 2873e9f45a7SArnaldo Carvalho de Melo 2883e9f45a7SArnaldo Carvalho de Melo if (asprintf(&s, "{ type: sample }") < 0) { 2893e9f45a7SArnaldo Carvalho de Melo ret = PyErr_NoMemory(); 2903e9f45a7SArnaldo Carvalho de Melo } else { 2913e9f45a7SArnaldo Carvalho de Melo ret = PyString_FromString(s); 2923e9f45a7SArnaldo Carvalho de Melo free(s); 2933e9f45a7SArnaldo Carvalho de Melo } 2943e9f45a7SArnaldo Carvalho de Melo return ret; 2953e9f45a7SArnaldo Carvalho de Melo } 2963e9f45a7SArnaldo Carvalho de Melo 2973e9f45a7SArnaldo Carvalho de Melo static PyTypeObject pyrf_sample_event__type = { 2983e9f45a7SArnaldo Carvalho de Melo PyVarObject_HEAD_INIT(NULL, 0) 2993e9f45a7SArnaldo Carvalho de Melo .tp_name = "perf.sample_event", 3003e9f45a7SArnaldo Carvalho de Melo .tp_basicsize = sizeof(struct pyrf_event), 3013e9f45a7SArnaldo Carvalho de Melo .tp_flags = Py_TPFLAGS_DEFAULT|Py_TPFLAGS_BASETYPE, 3023e9f45a7SArnaldo Carvalho de Melo .tp_doc = pyrf_sample_event__doc, 3033e9f45a7SArnaldo Carvalho de Melo .tp_members = pyrf_sample_event__members, 3043e9f45a7SArnaldo Carvalho de Melo .tp_repr = (reprfunc)pyrf_sample_event__repr, 3053e9f45a7SArnaldo Carvalho de Melo }; 3063e9f45a7SArnaldo Carvalho de Melo 307877108e4SArnaldo Carvalho de Melo static int pyrf_event__setup_types(void) 308877108e4SArnaldo Carvalho de Melo { 309877108e4SArnaldo Carvalho de Melo int err; 310877108e4SArnaldo Carvalho de Melo pyrf_mmap_event__type.tp_new = 311877108e4SArnaldo Carvalho de Melo pyrf_task_event__type.tp_new = 312877108e4SArnaldo Carvalho de Melo pyrf_comm_event__type.tp_new = 3133e9f45a7SArnaldo Carvalho de Melo pyrf_lost_event__type.tp_new = 3143e9f45a7SArnaldo Carvalho de Melo pyrf_read_event__type.tp_new = 3153e9f45a7SArnaldo Carvalho de Melo pyrf_sample_event__type.tp_new = 316877108e4SArnaldo Carvalho de Melo pyrf_throttle_event__type.tp_new = PyType_GenericNew; 317877108e4SArnaldo Carvalho de Melo err = PyType_Ready(&pyrf_mmap_event__type); 318877108e4SArnaldo Carvalho de Melo if (err < 0) 319877108e4SArnaldo Carvalho de Melo goto out; 3203e9f45a7SArnaldo Carvalho de Melo err = PyType_Ready(&pyrf_lost_event__type); 3213e9f45a7SArnaldo Carvalho de Melo if (err < 0) 3223e9f45a7SArnaldo Carvalho de Melo goto out; 323877108e4SArnaldo Carvalho de Melo err = PyType_Ready(&pyrf_task_event__type); 324877108e4SArnaldo Carvalho de Melo if (err < 0) 325877108e4SArnaldo Carvalho de Melo goto out; 326877108e4SArnaldo Carvalho de Melo err = PyType_Ready(&pyrf_comm_event__type); 327877108e4SArnaldo Carvalho de Melo if (err < 0) 328877108e4SArnaldo Carvalho de Melo goto out; 329877108e4SArnaldo Carvalho de Melo err = PyType_Ready(&pyrf_throttle_event__type); 330877108e4SArnaldo Carvalho de Melo if (err < 0) 331877108e4SArnaldo Carvalho de Melo goto out; 3323e9f45a7SArnaldo Carvalho de Melo err = PyType_Ready(&pyrf_read_event__type); 3333e9f45a7SArnaldo Carvalho de Melo if (err < 0) 3343e9f45a7SArnaldo Carvalho de Melo goto out; 3353e9f45a7SArnaldo Carvalho de Melo err = PyType_Ready(&pyrf_sample_event__type); 3363e9f45a7SArnaldo Carvalho de Melo if (err < 0) 3373e9f45a7SArnaldo Carvalho de Melo goto out; 338877108e4SArnaldo Carvalho de Melo out: 339877108e4SArnaldo Carvalho de Melo return err; 340877108e4SArnaldo Carvalho de Melo } 341877108e4SArnaldo Carvalho de Melo 342877108e4SArnaldo Carvalho de Melo static PyTypeObject *pyrf_event__type[] = { 343877108e4SArnaldo Carvalho de Melo [PERF_RECORD_MMAP] = &pyrf_mmap_event__type, 3443e9f45a7SArnaldo Carvalho de Melo [PERF_RECORD_LOST] = &pyrf_lost_event__type, 345877108e4SArnaldo Carvalho de Melo [PERF_RECORD_COMM] = &pyrf_comm_event__type, 346877108e4SArnaldo Carvalho de Melo [PERF_RECORD_EXIT] = &pyrf_task_event__type, 347877108e4SArnaldo Carvalho de Melo [PERF_RECORD_THROTTLE] = &pyrf_throttle_event__type, 348877108e4SArnaldo Carvalho de Melo [PERF_RECORD_UNTHROTTLE] = &pyrf_throttle_event__type, 349877108e4SArnaldo Carvalho de Melo [PERF_RECORD_FORK] = &pyrf_task_event__type, 3503e9f45a7SArnaldo Carvalho de Melo [PERF_RECORD_READ] = &pyrf_read_event__type, 3513e9f45a7SArnaldo Carvalho de Melo [PERF_RECORD_SAMPLE] = &pyrf_sample_event__type, 352877108e4SArnaldo Carvalho de Melo }; 353877108e4SArnaldo Carvalho de Melo 354877108e4SArnaldo Carvalho de Melo static PyObject *pyrf_event__new(union perf_event *event) 355877108e4SArnaldo Carvalho de Melo { 356877108e4SArnaldo Carvalho de Melo struct pyrf_event *pevent; 357877108e4SArnaldo Carvalho de Melo PyTypeObject *ptype; 358877108e4SArnaldo Carvalho de Melo 359877108e4SArnaldo Carvalho de Melo if (event->header.type < PERF_RECORD_MMAP || 360877108e4SArnaldo Carvalho de Melo event->header.type > PERF_RECORD_SAMPLE) 361877108e4SArnaldo Carvalho de Melo return NULL; 362877108e4SArnaldo Carvalho de Melo 363877108e4SArnaldo Carvalho de Melo ptype = pyrf_event__type[event->header.type]; 364877108e4SArnaldo Carvalho de Melo pevent = PyObject_New(struct pyrf_event, ptype); 365877108e4SArnaldo Carvalho de Melo if (pevent != NULL) 366877108e4SArnaldo Carvalho de Melo memcpy(&pevent->event, event, event->header.size); 367877108e4SArnaldo Carvalho de Melo return (PyObject *)pevent; 368877108e4SArnaldo Carvalho de Melo } 369877108e4SArnaldo Carvalho de Melo 370877108e4SArnaldo Carvalho de Melo struct pyrf_cpu_map { 371877108e4SArnaldo Carvalho de Melo PyObject_HEAD 372877108e4SArnaldo Carvalho de Melo 373877108e4SArnaldo Carvalho de Melo struct cpu_map *cpus; 374877108e4SArnaldo Carvalho de Melo }; 375877108e4SArnaldo Carvalho de Melo 376877108e4SArnaldo Carvalho de Melo static int pyrf_cpu_map__init(struct pyrf_cpu_map *pcpus, 377877108e4SArnaldo Carvalho de Melo PyObject *args, PyObject *kwargs) 378877108e4SArnaldo Carvalho de Melo { 37964348153SFrederic Weisbecker static char *kwlist[] = { "cpustr", NULL }; 380877108e4SArnaldo Carvalho de Melo char *cpustr = NULL; 381877108e4SArnaldo Carvalho de Melo 382877108e4SArnaldo Carvalho de Melo if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|s", 383877108e4SArnaldo Carvalho de Melo kwlist, &cpustr)) 384877108e4SArnaldo Carvalho de Melo return -1; 385877108e4SArnaldo Carvalho de Melo 386877108e4SArnaldo Carvalho de Melo pcpus->cpus = cpu_map__new(cpustr); 387877108e4SArnaldo Carvalho de Melo if (pcpus->cpus == NULL) 388877108e4SArnaldo Carvalho de Melo return -1; 389877108e4SArnaldo Carvalho de Melo return 0; 390877108e4SArnaldo Carvalho de Melo } 391877108e4SArnaldo Carvalho de Melo 392877108e4SArnaldo Carvalho de Melo static void pyrf_cpu_map__delete(struct pyrf_cpu_map *pcpus) 393877108e4SArnaldo Carvalho de Melo { 394877108e4SArnaldo Carvalho de Melo cpu_map__delete(pcpus->cpus); 395877108e4SArnaldo Carvalho de Melo pcpus->ob_type->tp_free((PyObject*)pcpus); 396877108e4SArnaldo Carvalho de Melo } 397877108e4SArnaldo Carvalho de Melo 398877108e4SArnaldo Carvalho de Melo static Py_ssize_t pyrf_cpu_map__length(PyObject *obj) 399877108e4SArnaldo Carvalho de Melo { 400877108e4SArnaldo Carvalho de Melo struct pyrf_cpu_map *pcpus = (void *)obj; 401877108e4SArnaldo Carvalho de Melo 402877108e4SArnaldo Carvalho de Melo return pcpus->cpus->nr; 403877108e4SArnaldo Carvalho de Melo } 404877108e4SArnaldo Carvalho de Melo 405877108e4SArnaldo Carvalho de Melo static PyObject *pyrf_cpu_map__item(PyObject *obj, Py_ssize_t i) 406877108e4SArnaldo Carvalho de Melo { 407877108e4SArnaldo Carvalho de Melo struct pyrf_cpu_map *pcpus = (void *)obj; 408877108e4SArnaldo Carvalho de Melo 409877108e4SArnaldo Carvalho de Melo if (i >= pcpus->cpus->nr) 410877108e4SArnaldo Carvalho de Melo return NULL; 411877108e4SArnaldo Carvalho de Melo 412877108e4SArnaldo Carvalho de Melo return Py_BuildValue("i", pcpus->cpus->map[i]); 413877108e4SArnaldo Carvalho de Melo } 414877108e4SArnaldo Carvalho de Melo 415877108e4SArnaldo Carvalho de Melo static PySequenceMethods pyrf_cpu_map__sequence_methods = { 416877108e4SArnaldo Carvalho de Melo .sq_length = pyrf_cpu_map__length, 417877108e4SArnaldo Carvalho de Melo .sq_item = pyrf_cpu_map__item, 418877108e4SArnaldo Carvalho de Melo }; 419877108e4SArnaldo Carvalho de Melo 420877108e4SArnaldo Carvalho de Melo static char pyrf_cpu_map__doc[] = PyDoc_STR("cpu map object."); 421877108e4SArnaldo Carvalho de Melo 422877108e4SArnaldo Carvalho de Melo static PyTypeObject pyrf_cpu_map__type = { 423877108e4SArnaldo Carvalho de Melo PyVarObject_HEAD_INIT(NULL, 0) 424877108e4SArnaldo Carvalho de Melo .tp_name = "perf.cpu_map", 425877108e4SArnaldo Carvalho de Melo .tp_basicsize = sizeof(struct pyrf_cpu_map), 426877108e4SArnaldo Carvalho de Melo .tp_dealloc = (destructor)pyrf_cpu_map__delete, 427877108e4SArnaldo Carvalho de Melo .tp_flags = Py_TPFLAGS_DEFAULT|Py_TPFLAGS_BASETYPE, 428877108e4SArnaldo Carvalho de Melo .tp_doc = pyrf_cpu_map__doc, 429877108e4SArnaldo Carvalho de Melo .tp_as_sequence = &pyrf_cpu_map__sequence_methods, 430877108e4SArnaldo Carvalho de Melo .tp_init = (initproc)pyrf_cpu_map__init, 431877108e4SArnaldo Carvalho de Melo }; 432877108e4SArnaldo Carvalho de Melo 433877108e4SArnaldo Carvalho de Melo static int pyrf_cpu_map__setup_types(void) 434877108e4SArnaldo Carvalho de Melo { 435877108e4SArnaldo Carvalho de Melo pyrf_cpu_map__type.tp_new = PyType_GenericNew; 436877108e4SArnaldo Carvalho de Melo return PyType_Ready(&pyrf_cpu_map__type); 437877108e4SArnaldo Carvalho de Melo } 438877108e4SArnaldo Carvalho de Melo 439877108e4SArnaldo Carvalho de Melo struct pyrf_thread_map { 440877108e4SArnaldo Carvalho de Melo PyObject_HEAD 441877108e4SArnaldo Carvalho de Melo 442877108e4SArnaldo Carvalho de Melo struct thread_map *threads; 443877108e4SArnaldo Carvalho de Melo }; 444877108e4SArnaldo Carvalho de Melo 445877108e4SArnaldo Carvalho de Melo static int pyrf_thread_map__init(struct pyrf_thread_map *pthreads, 446877108e4SArnaldo Carvalho de Melo PyObject *args, PyObject *kwargs) 447877108e4SArnaldo Carvalho de Melo { 4480d37aa34SArnaldo Carvalho de Melo static char *kwlist[] = { "pid", "tid", "uid", NULL }; 4490d37aa34SArnaldo Carvalho de Melo int pid = -1, tid = -1, uid = UINT_MAX; 450877108e4SArnaldo Carvalho de Melo 4510d37aa34SArnaldo Carvalho de Melo if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|iii", 4520d37aa34SArnaldo Carvalho de Melo kwlist, &pid, &tid, &uid)) 453877108e4SArnaldo Carvalho de Melo return -1; 454877108e4SArnaldo Carvalho de Melo 4550d37aa34SArnaldo Carvalho de Melo pthreads->threads = thread_map__new(pid, tid, uid); 456877108e4SArnaldo Carvalho de Melo if (pthreads->threads == NULL) 457877108e4SArnaldo Carvalho de Melo return -1; 458877108e4SArnaldo Carvalho de Melo return 0; 459877108e4SArnaldo Carvalho de Melo } 460877108e4SArnaldo Carvalho de Melo 461877108e4SArnaldo Carvalho de Melo static void pyrf_thread_map__delete(struct pyrf_thread_map *pthreads) 462877108e4SArnaldo Carvalho de Melo { 463877108e4SArnaldo Carvalho de Melo thread_map__delete(pthreads->threads); 464877108e4SArnaldo Carvalho de Melo pthreads->ob_type->tp_free((PyObject*)pthreads); 465877108e4SArnaldo Carvalho de Melo } 466877108e4SArnaldo Carvalho de Melo 467877108e4SArnaldo Carvalho de Melo static Py_ssize_t pyrf_thread_map__length(PyObject *obj) 468877108e4SArnaldo Carvalho de Melo { 469877108e4SArnaldo Carvalho de Melo struct pyrf_thread_map *pthreads = (void *)obj; 470877108e4SArnaldo Carvalho de Melo 471877108e4SArnaldo Carvalho de Melo return pthreads->threads->nr; 472877108e4SArnaldo Carvalho de Melo } 473877108e4SArnaldo Carvalho de Melo 474877108e4SArnaldo Carvalho de Melo static PyObject *pyrf_thread_map__item(PyObject *obj, Py_ssize_t i) 475877108e4SArnaldo Carvalho de Melo { 476877108e4SArnaldo Carvalho de Melo struct pyrf_thread_map *pthreads = (void *)obj; 477877108e4SArnaldo Carvalho de Melo 478877108e4SArnaldo Carvalho de Melo if (i >= pthreads->threads->nr) 479877108e4SArnaldo Carvalho de Melo return NULL; 480877108e4SArnaldo Carvalho de Melo 481877108e4SArnaldo Carvalho de Melo return Py_BuildValue("i", pthreads->threads->map[i]); 482877108e4SArnaldo Carvalho de Melo } 483877108e4SArnaldo Carvalho de Melo 484877108e4SArnaldo Carvalho de Melo static PySequenceMethods pyrf_thread_map__sequence_methods = { 485877108e4SArnaldo Carvalho de Melo .sq_length = pyrf_thread_map__length, 486877108e4SArnaldo Carvalho de Melo .sq_item = pyrf_thread_map__item, 487877108e4SArnaldo Carvalho de Melo }; 488877108e4SArnaldo Carvalho de Melo 489877108e4SArnaldo Carvalho de Melo static char pyrf_thread_map__doc[] = PyDoc_STR("thread map object."); 490877108e4SArnaldo Carvalho de Melo 491877108e4SArnaldo Carvalho de Melo static PyTypeObject pyrf_thread_map__type = { 492877108e4SArnaldo Carvalho de Melo PyVarObject_HEAD_INIT(NULL, 0) 493877108e4SArnaldo Carvalho de Melo .tp_name = "perf.thread_map", 494877108e4SArnaldo Carvalho de Melo .tp_basicsize = sizeof(struct pyrf_thread_map), 495877108e4SArnaldo Carvalho de Melo .tp_dealloc = (destructor)pyrf_thread_map__delete, 496877108e4SArnaldo Carvalho de Melo .tp_flags = Py_TPFLAGS_DEFAULT|Py_TPFLAGS_BASETYPE, 497877108e4SArnaldo Carvalho de Melo .tp_doc = pyrf_thread_map__doc, 498877108e4SArnaldo Carvalho de Melo .tp_as_sequence = &pyrf_thread_map__sequence_methods, 499877108e4SArnaldo Carvalho de Melo .tp_init = (initproc)pyrf_thread_map__init, 500877108e4SArnaldo Carvalho de Melo }; 501877108e4SArnaldo Carvalho de Melo 502877108e4SArnaldo Carvalho de Melo static int pyrf_thread_map__setup_types(void) 503877108e4SArnaldo Carvalho de Melo { 504877108e4SArnaldo Carvalho de Melo pyrf_thread_map__type.tp_new = PyType_GenericNew; 505877108e4SArnaldo Carvalho de Melo return PyType_Ready(&pyrf_thread_map__type); 506877108e4SArnaldo Carvalho de Melo } 507877108e4SArnaldo Carvalho de Melo 508877108e4SArnaldo Carvalho de Melo struct pyrf_evsel { 509877108e4SArnaldo Carvalho de Melo PyObject_HEAD 510877108e4SArnaldo Carvalho de Melo 511877108e4SArnaldo Carvalho de Melo struct perf_evsel evsel; 512877108e4SArnaldo Carvalho de Melo }; 513877108e4SArnaldo Carvalho de Melo 514877108e4SArnaldo Carvalho de Melo static int pyrf_evsel__init(struct pyrf_evsel *pevsel, 515877108e4SArnaldo Carvalho de Melo PyObject *args, PyObject *kwargs) 516877108e4SArnaldo Carvalho de Melo { 517877108e4SArnaldo Carvalho de Melo struct perf_event_attr attr = { 518877108e4SArnaldo Carvalho de Melo .type = PERF_TYPE_HARDWARE, 519877108e4SArnaldo Carvalho de Melo .config = PERF_COUNT_HW_CPU_CYCLES, 520877108e4SArnaldo Carvalho de Melo .sample_type = PERF_SAMPLE_PERIOD | PERF_SAMPLE_TID, 521877108e4SArnaldo Carvalho de Melo }; 522877108e4SArnaldo Carvalho de Melo static char *kwlist[] = { 523877108e4SArnaldo Carvalho de Melo "type", 524877108e4SArnaldo Carvalho de Melo "config", 525877108e4SArnaldo Carvalho de Melo "sample_freq", 526877108e4SArnaldo Carvalho de Melo "sample_period", 527877108e4SArnaldo Carvalho de Melo "sample_type", 528877108e4SArnaldo Carvalho de Melo "read_format", 529877108e4SArnaldo Carvalho de Melo "disabled", 530877108e4SArnaldo Carvalho de Melo "inherit", 531877108e4SArnaldo Carvalho de Melo "pinned", 532877108e4SArnaldo Carvalho de Melo "exclusive", 533877108e4SArnaldo Carvalho de Melo "exclude_user", 534877108e4SArnaldo Carvalho de Melo "exclude_kernel", 535877108e4SArnaldo Carvalho de Melo "exclude_hv", 536877108e4SArnaldo Carvalho de Melo "exclude_idle", 537877108e4SArnaldo Carvalho de Melo "mmap", 538877108e4SArnaldo Carvalho de Melo "comm", 539877108e4SArnaldo Carvalho de Melo "freq", 540877108e4SArnaldo Carvalho de Melo "inherit_stat", 541877108e4SArnaldo Carvalho de Melo "enable_on_exec", 542877108e4SArnaldo Carvalho de Melo "task", 543877108e4SArnaldo Carvalho de Melo "watermark", 544877108e4SArnaldo Carvalho de Melo "precise_ip", 545877108e4SArnaldo Carvalho de Melo "mmap_data", 546877108e4SArnaldo Carvalho de Melo "sample_id_all", 547877108e4SArnaldo Carvalho de Melo "wakeup_events", 548877108e4SArnaldo Carvalho de Melo "bp_type", 549877108e4SArnaldo Carvalho de Melo "bp_addr", 55064348153SFrederic Weisbecker "bp_len", 55164348153SFrederic Weisbecker NULL 55264348153SFrederic Weisbecker }; 553877108e4SArnaldo Carvalho de Melo u64 sample_period = 0; 554877108e4SArnaldo Carvalho de Melo u32 disabled = 0, 555877108e4SArnaldo Carvalho de Melo inherit = 0, 556877108e4SArnaldo Carvalho de Melo pinned = 0, 557877108e4SArnaldo Carvalho de Melo exclusive = 0, 558877108e4SArnaldo Carvalho de Melo exclude_user = 0, 559877108e4SArnaldo Carvalho de Melo exclude_kernel = 0, 560877108e4SArnaldo Carvalho de Melo exclude_hv = 0, 561877108e4SArnaldo Carvalho de Melo exclude_idle = 0, 562877108e4SArnaldo Carvalho de Melo mmap = 0, 563877108e4SArnaldo Carvalho de Melo comm = 0, 564877108e4SArnaldo Carvalho de Melo freq = 1, 565877108e4SArnaldo Carvalho de Melo inherit_stat = 0, 566877108e4SArnaldo Carvalho de Melo enable_on_exec = 0, 567877108e4SArnaldo Carvalho de Melo task = 0, 568877108e4SArnaldo Carvalho de Melo watermark = 0, 569877108e4SArnaldo Carvalho de Melo precise_ip = 0, 570877108e4SArnaldo Carvalho de Melo mmap_data = 0, 571877108e4SArnaldo Carvalho de Melo sample_id_all = 1; 572877108e4SArnaldo Carvalho de Melo int idx = 0; 573877108e4SArnaldo Carvalho de Melo 574877108e4SArnaldo Carvalho de Melo if (!PyArg_ParseTupleAndKeywords(args, kwargs, 575877108e4SArnaldo Carvalho de Melo "|iKiKKiiiiiiiiiiiiiiiiiiiiiKK", kwlist, 576877108e4SArnaldo Carvalho de Melo &attr.type, &attr.config, &attr.sample_freq, 577877108e4SArnaldo Carvalho de Melo &sample_period, &attr.sample_type, 578877108e4SArnaldo Carvalho de Melo &attr.read_format, &disabled, &inherit, 579877108e4SArnaldo Carvalho de Melo &pinned, &exclusive, &exclude_user, 580877108e4SArnaldo Carvalho de Melo &exclude_kernel, &exclude_hv, &exclude_idle, 581877108e4SArnaldo Carvalho de Melo &mmap, &comm, &freq, &inherit_stat, 582877108e4SArnaldo Carvalho de Melo &enable_on_exec, &task, &watermark, 583877108e4SArnaldo Carvalho de Melo &precise_ip, &mmap_data, &sample_id_all, 584877108e4SArnaldo Carvalho de Melo &attr.wakeup_events, &attr.bp_type, 585877108e4SArnaldo Carvalho de Melo &attr.bp_addr, &attr.bp_len, &idx)) 586877108e4SArnaldo Carvalho de Melo return -1; 587877108e4SArnaldo Carvalho de Melo 588877108e4SArnaldo Carvalho de Melo /* union... */ 589877108e4SArnaldo Carvalho de Melo if (sample_period != 0) { 590877108e4SArnaldo Carvalho de Melo if (attr.sample_freq != 0) 591877108e4SArnaldo Carvalho de Melo return -1; /* FIXME: throw right exception */ 592877108e4SArnaldo Carvalho de Melo attr.sample_period = sample_period; 593877108e4SArnaldo Carvalho de Melo } 594877108e4SArnaldo Carvalho de Melo 595877108e4SArnaldo Carvalho de Melo /* Bitfields */ 596877108e4SArnaldo Carvalho de Melo attr.disabled = disabled; 597877108e4SArnaldo Carvalho de Melo attr.inherit = inherit; 598877108e4SArnaldo Carvalho de Melo attr.pinned = pinned; 599877108e4SArnaldo Carvalho de Melo attr.exclusive = exclusive; 600877108e4SArnaldo Carvalho de Melo attr.exclude_user = exclude_user; 601877108e4SArnaldo Carvalho de Melo attr.exclude_kernel = exclude_kernel; 602877108e4SArnaldo Carvalho de Melo attr.exclude_hv = exclude_hv; 603877108e4SArnaldo Carvalho de Melo attr.exclude_idle = exclude_idle; 604877108e4SArnaldo Carvalho de Melo attr.mmap = mmap; 605877108e4SArnaldo Carvalho de Melo attr.comm = comm; 606877108e4SArnaldo Carvalho de Melo attr.freq = freq; 607877108e4SArnaldo Carvalho de Melo attr.inherit_stat = inherit_stat; 608877108e4SArnaldo Carvalho de Melo attr.enable_on_exec = enable_on_exec; 609877108e4SArnaldo Carvalho de Melo attr.task = task; 610877108e4SArnaldo Carvalho de Melo attr.watermark = watermark; 611877108e4SArnaldo Carvalho de Melo attr.precise_ip = precise_ip; 612877108e4SArnaldo Carvalho de Melo attr.mmap_data = mmap_data; 613877108e4SArnaldo Carvalho de Melo attr.sample_id_all = sample_id_all; 614877108e4SArnaldo Carvalho de Melo 615877108e4SArnaldo Carvalho de Melo perf_evsel__init(&pevsel->evsel, &attr, idx); 616877108e4SArnaldo Carvalho de Melo return 0; 617877108e4SArnaldo Carvalho de Melo } 618877108e4SArnaldo Carvalho de Melo 619877108e4SArnaldo Carvalho de Melo static void pyrf_evsel__delete(struct pyrf_evsel *pevsel) 620877108e4SArnaldo Carvalho de Melo { 621877108e4SArnaldo Carvalho de Melo perf_evsel__exit(&pevsel->evsel); 622877108e4SArnaldo Carvalho de Melo pevsel->ob_type->tp_free((PyObject*)pevsel); 623877108e4SArnaldo Carvalho de Melo } 624877108e4SArnaldo Carvalho de Melo 625877108e4SArnaldo Carvalho de Melo static PyObject *pyrf_evsel__open(struct pyrf_evsel *pevsel, 626877108e4SArnaldo Carvalho de Melo PyObject *args, PyObject *kwargs) 627877108e4SArnaldo Carvalho de Melo { 628877108e4SArnaldo Carvalho de Melo struct perf_evsel *evsel = &pevsel->evsel; 629877108e4SArnaldo Carvalho de Melo struct cpu_map *cpus = NULL; 630877108e4SArnaldo Carvalho de Melo struct thread_map *threads = NULL; 631877108e4SArnaldo Carvalho de Melo PyObject *pcpus = NULL, *pthreads = NULL; 6325d2cd909SArnaldo Carvalho de Melo int group = 0, inherit = 0; 63364348153SFrederic Weisbecker static char *kwlist[] = { "cpus", "threads", "group", "inherit", NULL }; 634877108e4SArnaldo Carvalho de Melo 635877108e4SArnaldo Carvalho de Melo if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|OOii", kwlist, 6365d2cd909SArnaldo Carvalho de Melo &pcpus, &pthreads, &group, &inherit)) 637877108e4SArnaldo Carvalho de Melo return NULL; 638877108e4SArnaldo Carvalho de Melo 639877108e4SArnaldo Carvalho de Melo if (pthreads != NULL) 640877108e4SArnaldo Carvalho de Melo threads = ((struct pyrf_thread_map *)pthreads)->threads; 641877108e4SArnaldo Carvalho de Melo 642877108e4SArnaldo Carvalho de Melo if (pcpus != NULL) 643877108e4SArnaldo Carvalho de Melo cpus = ((struct pyrf_cpu_map *)pcpus)->cpus; 644877108e4SArnaldo Carvalho de Melo 6455d2cd909SArnaldo Carvalho de Melo evsel->attr.inherit = inherit; 646727ab04eSArnaldo Carvalho de Melo /* 647727ab04eSArnaldo Carvalho de Melo * This will group just the fds for this single evsel, to group 648727ab04eSArnaldo Carvalho de Melo * multiple events, use evlist.open(). 649727ab04eSArnaldo Carvalho de Melo */ 6506a4bb04cSJiri Olsa if (perf_evsel__open(evsel, cpus, threads) < 0) { 651877108e4SArnaldo Carvalho de Melo PyErr_SetFromErrno(PyExc_OSError); 652877108e4SArnaldo Carvalho de Melo return NULL; 653877108e4SArnaldo Carvalho de Melo } 654877108e4SArnaldo Carvalho de Melo 655877108e4SArnaldo Carvalho de Melo Py_INCREF(Py_None); 656877108e4SArnaldo Carvalho de Melo return Py_None; 657877108e4SArnaldo Carvalho de Melo } 658877108e4SArnaldo Carvalho de Melo 659877108e4SArnaldo Carvalho de Melo static PyMethodDef pyrf_evsel__methods[] = { 660877108e4SArnaldo Carvalho de Melo { 661877108e4SArnaldo Carvalho de Melo .ml_name = "open", 662877108e4SArnaldo Carvalho de Melo .ml_meth = (PyCFunction)pyrf_evsel__open, 663877108e4SArnaldo Carvalho de Melo .ml_flags = METH_VARARGS | METH_KEYWORDS, 664877108e4SArnaldo Carvalho de Melo .ml_doc = PyDoc_STR("open the event selector file descriptor table.") 665877108e4SArnaldo Carvalho de Melo }, 666f6bbc1daSArnaldo Carvalho de Melo { .ml_name = NULL, } 667877108e4SArnaldo Carvalho de Melo }; 668877108e4SArnaldo Carvalho de Melo 669877108e4SArnaldo Carvalho de Melo static char pyrf_evsel__doc[] = PyDoc_STR("perf event selector list object."); 670877108e4SArnaldo Carvalho de Melo 671877108e4SArnaldo Carvalho de Melo static PyTypeObject pyrf_evsel__type = { 672877108e4SArnaldo Carvalho de Melo PyVarObject_HEAD_INIT(NULL, 0) 673877108e4SArnaldo Carvalho de Melo .tp_name = "perf.evsel", 674877108e4SArnaldo Carvalho de Melo .tp_basicsize = sizeof(struct pyrf_evsel), 675877108e4SArnaldo Carvalho de Melo .tp_dealloc = (destructor)pyrf_evsel__delete, 676877108e4SArnaldo Carvalho de Melo .tp_flags = Py_TPFLAGS_DEFAULT|Py_TPFLAGS_BASETYPE, 677877108e4SArnaldo Carvalho de Melo .tp_doc = pyrf_evsel__doc, 678877108e4SArnaldo Carvalho de Melo .tp_methods = pyrf_evsel__methods, 679877108e4SArnaldo Carvalho de Melo .tp_init = (initproc)pyrf_evsel__init, 680877108e4SArnaldo Carvalho de Melo }; 681877108e4SArnaldo Carvalho de Melo 682877108e4SArnaldo Carvalho de Melo static int pyrf_evsel__setup_types(void) 683877108e4SArnaldo Carvalho de Melo { 684877108e4SArnaldo Carvalho de Melo pyrf_evsel__type.tp_new = PyType_GenericNew; 685877108e4SArnaldo Carvalho de Melo return PyType_Ready(&pyrf_evsel__type); 686877108e4SArnaldo Carvalho de Melo } 687877108e4SArnaldo Carvalho de Melo 688877108e4SArnaldo Carvalho de Melo struct pyrf_evlist { 689877108e4SArnaldo Carvalho de Melo PyObject_HEAD 690877108e4SArnaldo Carvalho de Melo 691877108e4SArnaldo Carvalho de Melo struct perf_evlist evlist; 692877108e4SArnaldo Carvalho de Melo }; 693877108e4SArnaldo Carvalho de Melo 694877108e4SArnaldo Carvalho de Melo static int pyrf_evlist__init(struct pyrf_evlist *pevlist, 6951d037ca1SIrina Tirdea PyObject *args, PyObject *kwargs __maybe_unused) 696877108e4SArnaldo Carvalho de Melo { 6977e2ed097SArnaldo Carvalho de Melo PyObject *pcpus = NULL, *pthreads = NULL; 6987e2ed097SArnaldo Carvalho de Melo struct cpu_map *cpus; 6997e2ed097SArnaldo Carvalho de Melo struct thread_map *threads; 7007e2ed097SArnaldo Carvalho de Melo 7017e2ed097SArnaldo Carvalho de Melo if (!PyArg_ParseTuple(args, "OO", &pcpus, &pthreads)) 7027e2ed097SArnaldo Carvalho de Melo return -1; 7037e2ed097SArnaldo Carvalho de Melo 7047e2ed097SArnaldo Carvalho de Melo threads = ((struct pyrf_thread_map *)pthreads)->threads; 7057e2ed097SArnaldo Carvalho de Melo cpus = ((struct pyrf_cpu_map *)pcpus)->cpus; 7067e2ed097SArnaldo Carvalho de Melo perf_evlist__init(&pevlist->evlist, cpus, threads); 707877108e4SArnaldo Carvalho de Melo return 0; 708877108e4SArnaldo Carvalho de Melo } 709877108e4SArnaldo Carvalho de Melo 710877108e4SArnaldo Carvalho de Melo static void pyrf_evlist__delete(struct pyrf_evlist *pevlist) 711877108e4SArnaldo Carvalho de Melo { 712877108e4SArnaldo Carvalho de Melo perf_evlist__exit(&pevlist->evlist); 713877108e4SArnaldo Carvalho de Melo pevlist->ob_type->tp_free((PyObject*)pevlist); 714877108e4SArnaldo Carvalho de Melo } 715877108e4SArnaldo Carvalho de Melo 716877108e4SArnaldo Carvalho de Melo static PyObject *pyrf_evlist__mmap(struct pyrf_evlist *pevlist, 717877108e4SArnaldo Carvalho de Melo PyObject *args, PyObject *kwargs) 718877108e4SArnaldo Carvalho de Melo { 719877108e4SArnaldo Carvalho de Melo struct perf_evlist *evlist = &pevlist->evlist; 72064348153SFrederic Weisbecker static char *kwlist[] = { "pages", "overwrite", NULL }; 721877108e4SArnaldo Carvalho de Melo int pages = 128, overwrite = false; 722877108e4SArnaldo Carvalho de Melo 7237e2ed097SArnaldo Carvalho de Melo if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|ii", kwlist, 7247e2ed097SArnaldo Carvalho de Melo &pages, &overwrite)) 725877108e4SArnaldo Carvalho de Melo return NULL; 726877108e4SArnaldo Carvalho de Melo 7277e2ed097SArnaldo Carvalho de Melo if (perf_evlist__mmap(evlist, pages, overwrite) < 0) { 728877108e4SArnaldo Carvalho de Melo PyErr_SetFromErrno(PyExc_OSError); 729877108e4SArnaldo Carvalho de Melo return NULL; 730877108e4SArnaldo Carvalho de Melo } 731877108e4SArnaldo Carvalho de Melo 732877108e4SArnaldo Carvalho de Melo Py_INCREF(Py_None); 733877108e4SArnaldo Carvalho de Melo return Py_None; 734877108e4SArnaldo Carvalho de Melo } 735877108e4SArnaldo Carvalho de Melo 736877108e4SArnaldo Carvalho de Melo static PyObject *pyrf_evlist__poll(struct pyrf_evlist *pevlist, 737877108e4SArnaldo Carvalho de Melo PyObject *args, PyObject *kwargs) 738877108e4SArnaldo Carvalho de Melo { 739877108e4SArnaldo Carvalho de Melo struct perf_evlist *evlist = &pevlist->evlist; 74064348153SFrederic Weisbecker static char *kwlist[] = { "timeout", NULL }; 741877108e4SArnaldo Carvalho de Melo int timeout = -1, n; 742877108e4SArnaldo Carvalho de Melo 743877108e4SArnaldo Carvalho de Melo if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|i", kwlist, &timeout)) 744877108e4SArnaldo Carvalho de Melo return NULL; 745877108e4SArnaldo Carvalho de Melo 746877108e4SArnaldo Carvalho de Melo n = poll(evlist->pollfd, evlist->nr_fds, timeout); 747877108e4SArnaldo Carvalho de Melo if (n < 0) { 748877108e4SArnaldo Carvalho de Melo PyErr_SetFromErrno(PyExc_OSError); 749877108e4SArnaldo Carvalho de Melo return NULL; 750877108e4SArnaldo Carvalho de Melo } 751877108e4SArnaldo Carvalho de Melo 752877108e4SArnaldo Carvalho de Melo return Py_BuildValue("i", n); 753877108e4SArnaldo Carvalho de Melo } 754877108e4SArnaldo Carvalho de Melo 755877108e4SArnaldo Carvalho de Melo static PyObject *pyrf_evlist__get_pollfd(struct pyrf_evlist *pevlist, 7561d037ca1SIrina Tirdea PyObject *args __maybe_unused, 7571d037ca1SIrina Tirdea PyObject *kwargs __maybe_unused) 758877108e4SArnaldo Carvalho de Melo { 759877108e4SArnaldo Carvalho de Melo struct perf_evlist *evlist = &pevlist->evlist; 760877108e4SArnaldo Carvalho de Melo PyObject *list = PyList_New(0); 761877108e4SArnaldo Carvalho de Melo int i; 762877108e4SArnaldo Carvalho de Melo 763877108e4SArnaldo Carvalho de Melo for (i = 0; i < evlist->nr_fds; ++i) { 764877108e4SArnaldo Carvalho de Melo PyObject *file; 765877108e4SArnaldo Carvalho de Melo FILE *fp = fdopen(evlist->pollfd[i].fd, "r"); 766877108e4SArnaldo Carvalho de Melo 767877108e4SArnaldo Carvalho de Melo if (fp == NULL) 768877108e4SArnaldo Carvalho de Melo goto free_list; 769877108e4SArnaldo Carvalho de Melo 770877108e4SArnaldo Carvalho de Melo file = PyFile_FromFile(fp, "perf", "r", NULL); 771877108e4SArnaldo Carvalho de Melo if (file == NULL) 772877108e4SArnaldo Carvalho de Melo goto free_list; 773877108e4SArnaldo Carvalho de Melo 774877108e4SArnaldo Carvalho de Melo if (PyList_Append(list, file) != 0) { 775877108e4SArnaldo Carvalho de Melo Py_DECREF(file); 776877108e4SArnaldo Carvalho de Melo goto free_list; 777877108e4SArnaldo Carvalho de Melo } 778877108e4SArnaldo Carvalho de Melo 779877108e4SArnaldo Carvalho de Melo Py_DECREF(file); 780877108e4SArnaldo Carvalho de Melo } 781877108e4SArnaldo Carvalho de Melo 782877108e4SArnaldo Carvalho de Melo return list; 783877108e4SArnaldo Carvalho de Melo free_list: 784877108e4SArnaldo Carvalho de Melo return PyErr_NoMemory(); 785877108e4SArnaldo Carvalho de Melo } 786877108e4SArnaldo Carvalho de Melo 787877108e4SArnaldo Carvalho de Melo 788877108e4SArnaldo Carvalho de Melo static PyObject *pyrf_evlist__add(struct pyrf_evlist *pevlist, 7891d037ca1SIrina Tirdea PyObject *args, 7901d037ca1SIrina Tirdea PyObject *kwargs __maybe_unused) 791877108e4SArnaldo Carvalho de Melo { 792877108e4SArnaldo Carvalho de Melo struct perf_evlist *evlist = &pevlist->evlist; 793877108e4SArnaldo Carvalho de Melo PyObject *pevsel; 794877108e4SArnaldo Carvalho de Melo struct perf_evsel *evsel; 795877108e4SArnaldo Carvalho de Melo 796877108e4SArnaldo Carvalho de Melo if (!PyArg_ParseTuple(args, "O", &pevsel)) 797877108e4SArnaldo Carvalho de Melo return NULL; 798877108e4SArnaldo Carvalho de Melo 799877108e4SArnaldo Carvalho de Melo Py_INCREF(pevsel); 800877108e4SArnaldo Carvalho de Melo evsel = &((struct pyrf_evsel *)pevsel)->evsel; 801877108e4SArnaldo Carvalho de Melo evsel->idx = evlist->nr_entries; 802877108e4SArnaldo Carvalho de Melo perf_evlist__add(evlist, evsel); 803877108e4SArnaldo Carvalho de Melo 804877108e4SArnaldo Carvalho de Melo return Py_BuildValue("i", evlist->nr_entries); 805877108e4SArnaldo Carvalho de Melo } 806877108e4SArnaldo Carvalho de Melo 807877108e4SArnaldo Carvalho de Melo static PyObject *pyrf_evlist__read_on_cpu(struct pyrf_evlist *pevlist, 808877108e4SArnaldo Carvalho de Melo PyObject *args, PyObject *kwargs) 809877108e4SArnaldo Carvalho de Melo { 810877108e4SArnaldo Carvalho de Melo struct perf_evlist *evlist = &pevlist->evlist; 811877108e4SArnaldo Carvalho de Melo union perf_event *event; 812877108e4SArnaldo Carvalho de Melo int sample_id_all = 1, cpu; 81364348153SFrederic Weisbecker static char *kwlist[] = { "cpu", "sample_id_all", NULL }; 8145538becaSFrederic Weisbecker int err; 815877108e4SArnaldo Carvalho de Melo 816877108e4SArnaldo Carvalho de Melo if (!PyArg_ParseTupleAndKeywords(args, kwargs, "i|i", kwlist, 817877108e4SArnaldo Carvalho de Melo &cpu, &sample_id_all)) 818877108e4SArnaldo Carvalho de Melo return NULL; 819877108e4SArnaldo Carvalho de Melo 820aece948fSArnaldo Carvalho de Melo event = perf_evlist__mmap_read(evlist, cpu); 821877108e4SArnaldo Carvalho de Melo if (event != NULL) { 822877108e4SArnaldo Carvalho de Melo PyObject *pyevent = pyrf_event__new(event); 823877108e4SArnaldo Carvalho de Melo struct pyrf_event *pevent = (struct pyrf_event *)pyevent; 824877108e4SArnaldo Carvalho de Melo 825877108e4SArnaldo Carvalho de Melo if (pyevent == NULL) 826877108e4SArnaldo Carvalho de Melo return PyErr_NoMemory(); 827877108e4SArnaldo Carvalho de Melo 8280807d2d8SArnaldo Carvalho de Melo err = perf_evlist__parse_sample(evlist, event, &pevent->sample); 8295c6970afSArnaldo Carvalho de Melo if (err) 8305c6970afSArnaldo Carvalho de Melo return PyErr_Format(PyExc_OSError, 8315c6970afSArnaldo Carvalho de Melo "perf: can't parse sample, err=%d", err); 8325538becaSFrederic Weisbecker return pyevent; 8335538becaSFrederic Weisbecker } 8345c6970afSArnaldo Carvalho de Melo 835877108e4SArnaldo Carvalho de Melo Py_INCREF(Py_None); 836877108e4SArnaldo Carvalho de Melo return Py_None; 837877108e4SArnaldo Carvalho de Melo } 838877108e4SArnaldo Carvalho de Melo 839727ab04eSArnaldo Carvalho de Melo static PyObject *pyrf_evlist__open(struct pyrf_evlist *pevlist, 840727ab04eSArnaldo Carvalho de Melo PyObject *args, PyObject *kwargs) 841727ab04eSArnaldo Carvalho de Melo { 842727ab04eSArnaldo Carvalho de Melo struct perf_evlist *evlist = &pevlist->evlist; 843727ab04eSArnaldo Carvalho de Melo int group = 0; 844727ab04eSArnaldo Carvalho de Melo static char *kwlist[] = { "group", NULL }; 845727ab04eSArnaldo Carvalho de Melo 846727ab04eSArnaldo Carvalho de Melo if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|OOii", kwlist, &group)) 847727ab04eSArnaldo Carvalho de Melo return NULL; 848727ab04eSArnaldo Carvalho de Melo 8496a4bb04cSJiri Olsa if (group) 85063dab225SArnaldo Carvalho de Melo perf_evlist__set_leader(evlist); 8516a4bb04cSJiri Olsa 8526a4bb04cSJiri Olsa if (perf_evlist__open(evlist) < 0) { 853727ab04eSArnaldo Carvalho de Melo PyErr_SetFromErrno(PyExc_OSError); 854727ab04eSArnaldo Carvalho de Melo return NULL; 855727ab04eSArnaldo Carvalho de Melo } 856727ab04eSArnaldo Carvalho de Melo 857727ab04eSArnaldo Carvalho de Melo Py_INCREF(Py_None); 858727ab04eSArnaldo Carvalho de Melo return Py_None; 859727ab04eSArnaldo Carvalho de Melo } 860727ab04eSArnaldo Carvalho de Melo 861877108e4SArnaldo Carvalho de Melo static PyMethodDef pyrf_evlist__methods[] = { 862877108e4SArnaldo Carvalho de Melo { 863877108e4SArnaldo Carvalho de Melo .ml_name = "mmap", 864877108e4SArnaldo Carvalho de Melo .ml_meth = (PyCFunction)pyrf_evlist__mmap, 865877108e4SArnaldo Carvalho de Melo .ml_flags = METH_VARARGS | METH_KEYWORDS, 866877108e4SArnaldo Carvalho de Melo .ml_doc = PyDoc_STR("mmap the file descriptor table.") 867877108e4SArnaldo Carvalho de Melo }, 868877108e4SArnaldo Carvalho de Melo { 869727ab04eSArnaldo Carvalho de Melo .ml_name = "open", 870727ab04eSArnaldo Carvalho de Melo .ml_meth = (PyCFunction)pyrf_evlist__open, 871727ab04eSArnaldo Carvalho de Melo .ml_flags = METH_VARARGS | METH_KEYWORDS, 872727ab04eSArnaldo Carvalho de Melo .ml_doc = PyDoc_STR("open the file descriptors.") 873727ab04eSArnaldo Carvalho de Melo }, 874727ab04eSArnaldo Carvalho de Melo { 875877108e4SArnaldo Carvalho de Melo .ml_name = "poll", 876877108e4SArnaldo Carvalho de Melo .ml_meth = (PyCFunction)pyrf_evlist__poll, 877877108e4SArnaldo Carvalho de Melo .ml_flags = METH_VARARGS | METH_KEYWORDS, 878877108e4SArnaldo Carvalho de Melo .ml_doc = PyDoc_STR("poll the file descriptor table.") 879877108e4SArnaldo Carvalho de Melo }, 880877108e4SArnaldo Carvalho de Melo { 881877108e4SArnaldo Carvalho de Melo .ml_name = "get_pollfd", 882877108e4SArnaldo Carvalho de Melo .ml_meth = (PyCFunction)pyrf_evlist__get_pollfd, 883877108e4SArnaldo Carvalho de Melo .ml_flags = METH_VARARGS | METH_KEYWORDS, 884877108e4SArnaldo Carvalho de Melo .ml_doc = PyDoc_STR("get the poll file descriptor table.") 885877108e4SArnaldo Carvalho de Melo }, 886877108e4SArnaldo Carvalho de Melo { 887877108e4SArnaldo Carvalho de Melo .ml_name = "add", 888877108e4SArnaldo Carvalho de Melo .ml_meth = (PyCFunction)pyrf_evlist__add, 889877108e4SArnaldo Carvalho de Melo .ml_flags = METH_VARARGS | METH_KEYWORDS, 890877108e4SArnaldo Carvalho de Melo .ml_doc = PyDoc_STR("adds an event selector to the list.") 891877108e4SArnaldo Carvalho de Melo }, 892877108e4SArnaldo Carvalho de Melo { 893877108e4SArnaldo Carvalho de Melo .ml_name = "read_on_cpu", 894877108e4SArnaldo Carvalho de Melo .ml_meth = (PyCFunction)pyrf_evlist__read_on_cpu, 895877108e4SArnaldo Carvalho de Melo .ml_flags = METH_VARARGS | METH_KEYWORDS, 896877108e4SArnaldo Carvalho de Melo .ml_doc = PyDoc_STR("reads an event.") 897877108e4SArnaldo Carvalho de Melo }, 898f6bbc1daSArnaldo Carvalho de Melo { .ml_name = NULL, } 899877108e4SArnaldo Carvalho de Melo }; 900877108e4SArnaldo Carvalho de Melo 901877108e4SArnaldo Carvalho de Melo static Py_ssize_t pyrf_evlist__length(PyObject *obj) 902877108e4SArnaldo Carvalho de Melo { 903877108e4SArnaldo Carvalho de Melo struct pyrf_evlist *pevlist = (void *)obj; 904877108e4SArnaldo Carvalho de Melo 905877108e4SArnaldo Carvalho de Melo return pevlist->evlist.nr_entries; 906877108e4SArnaldo Carvalho de Melo } 907877108e4SArnaldo Carvalho de Melo 908877108e4SArnaldo Carvalho de Melo static PyObject *pyrf_evlist__item(PyObject *obj, Py_ssize_t i) 909877108e4SArnaldo Carvalho de Melo { 910877108e4SArnaldo Carvalho de Melo struct pyrf_evlist *pevlist = (void *)obj; 911877108e4SArnaldo Carvalho de Melo struct perf_evsel *pos; 912877108e4SArnaldo Carvalho de Melo 913877108e4SArnaldo Carvalho de Melo if (i >= pevlist->evlist.nr_entries) 914877108e4SArnaldo Carvalho de Melo return NULL; 915877108e4SArnaldo Carvalho de Melo 916877108e4SArnaldo Carvalho de Melo list_for_each_entry(pos, &pevlist->evlist.entries, node) 917877108e4SArnaldo Carvalho de Melo if (i-- == 0) 918877108e4SArnaldo Carvalho de Melo break; 919877108e4SArnaldo Carvalho de Melo 920877108e4SArnaldo Carvalho de Melo return Py_BuildValue("O", container_of(pos, struct pyrf_evsel, evsel)); 921877108e4SArnaldo Carvalho de Melo } 922877108e4SArnaldo Carvalho de Melo 923877108e4SArnaldo Carvalho de Melo static PySequenceMethods pyrf_evlist__sequence_methods = { 924877108e4SArnaldo Carvalho de Melo .sq_length = pyrf_evlist__length, 925877108e4SArnaldo Carvalho de Melo .sq_item = pyrf_evlist__item, 926877108e4SArnaldo Carvalho de Melo }; 927877108e4SArnaldo Carvalho de Melo 928877108e4SArnaldo Carvalho de Melo static char pyrf_evlist__doc[] = PyDoc_STR("perf event selector list object."); 929877108e4SArnaldo Carvalho de Melo 930877108e4SArnaldo Carvalho de Melo static PyTypeObject pyrf_evlist__type = { 931877108e4SArnaldo Carvalho de Melo PyVarObject_HEAD_INIT(NULL, 0) 932877108e4SArnaldo Carvalho de Melo .tp_name = "perf.evlist", 933877108e4SArnaldo Carvalho de Melo .tp_basicsize = sizeof(struct pyrf_evlist), 934877108e4SArnaldo Carvalho de Melo .tp_dealloc = (destructor)pyrf_evlist__delete, 935877108e4SArnaldo Carvalho de Melo .tp_flags = Py_TPFLAGS_DEFAULT|Py_TPFLAGS_BASETYPE, 936877108e4SArnaldo Carvalho de Melo .tp_as_sequence = &pyrf_evlist__sequence_methods, 937877108e4SArnaldo Carvalho de Melo .tp_doc = pyrf_evlist__doc, 938877108e4SArnaldo Carvalho de Melo .tp_methods = pyrf_evlist__methods, 939877108e4SArnaldo Carvalho de Melo .tp_init = (initproc)pyrf_evlist__init, 940877108e4SArnaldo Carvalho de Melo }; 941877108e4SArnaldo Carvalho de Melo 942877108e4SArnaldo Carvalho de Melo static int pyrf_evlist__setup_types(void) 943877108e4SArnaldo Carvalho de Melo { 944877108e4SArnaldo Carvalho de Melo pyrf_evlist__type.tp_new = PyType_GenericNew; 945877108e4SArnaldo Carvalho de Melo return PyType_Ready(&pyrf_evlist__type); 946877108e4SArnaldo Carvalho de Melo } 947877108e4SArnaldo Carvalho de Melo 948877108e4SArnaldo Carvalho de Melo static struct { 949877108e4SArnaldo Carvalho de Melo const char *name; 950877108e4SArnaldo Carvalho de Melo int value; 951877108e4SArnaldo Carvalho de Melo } perf__constants[] = { 952877108e4SArnaldo Carvalho de Melo { "TYPE_HARDWARE", PERF_TYPE_HARDWARE }, 953877108e4SArnaldo Carvalho de Melo { "TYPE_SOFTWARE", PERF_TYPE_SOFTWARE }, 954877108e4SArnaldo Carvalho de Melo { "TYPE_TRACEPOINT", PERF_TYPE_TRACEPOINT }, 955877108e4SArnaldo Carvalho de Melo { "TYPE_HW_CACHE", PERF_TYPE_HW_CACHE }, 956877108e4SArnaldo Carvalho de Melo { "TYPE_RAW", PERF_TYPE_RAW }, 957877108e4SArnaldo Carvalho de Melo { "TYPE_BREAKPOINT", PERF_TYPE_BREAKPOINT }, 958877108e4SArnaldo Carvalho de Melo 959877108e4SArnaldo Carvalho de Melo { "COUNT_HW_CPU_CYCLES", PERF_COUNT_HW_CPU_CYCLES }, 960877108e4SArnaldo Carvalho de Melo { "COUNT_HW_INSTRUCTIONS", PERF_COUNT_HW_INSTRUCTIONS }, 961877108e4SArnaldo Carvalho de Melo { "COUNT_HW_CACHE_REFERENCES", PERF_COUNT_HW_CACHE_REFERENCES }, 962877108e4SArnaldo Carvalho de Melo { "COUNT_HW_CACHE_MISSES", PERF_COUNT_HW_CACHE_MISSES }, 963877108e4SArnaldo Carvalho de Melo { "COUNT_HW_BRANCH_INSTRUCTIONS", PERF_COUNT_HW_BRANCH_INSTRUCTIONS }, 964877108e4SArnaldo Carvalho de Melo { "COUNT_HW_BRANCH_MISSES", PERF_COUNT_HW_BRANCH_MISSES }, 965877108e4SArnaldo Carvalho de Melo { "COUNT_HW_BUS_CYCLES", PERF_COUNT_HW_BUS_CYCLES }, 966877108e4SArnaldo Carvalho de Melo { "COUNT_HW_CACHE_L1D", PERF_COUNT_HW_CACHE_L1D }, 967877108e4SArnaldo Carvalho de Melo { "COUNT_HW_CACHE_L1I", PERF_COUNT_HW_CACHE_L1I }, 968877108e4SArnaldo Carvalho de Melo { "COUNT_HW_CACHE_LL", PERF_COUNT_HW_CACHE_LL }, 969877108e4SArnaldo Carvalho de Melo { "COUNT_HW_CACHE_DTLB", PERF_COUNT_HW_CACHE_DTLB }, 970877108e4SArnaldo Carvalho de Melo { "COUNT_HW_CACHE_ITLB", PERF_COUNT_HW_CACHE_ITLB }, 971877108e4SArnaldo Carvalho de Melo { "COUNT_HW_CACHE_BPU", PERF_COUNT_HW_CACHE_BPU }, 972877108e4SArnaldo Carvalho de Melo { "COUNT_HW_CACHE_OP_READ", PERF_COUNT_HW_CACHE_OP_READ }, 973877108e4SArnaldo Carvalho de Melo { "COUNT_HW_CACHE_OP_WRITE", PERF_COUNT_HW_CACHE_OP_WRITE }, 974877108e4SArnaldo Carvalho de Melo { "COUNT_HW_CACHE_OP_PREFETCH", PERF_COUNT_HW_CACHE_OP_PREFETCH }, 975877108e4SArnaldo Carvalho de Melo { "COUNT_HW_CACHE_RESULT_ACCESS", PERF_COUNT_HW_CACHE_RESULT_ACCESS }, 976877108e4SArnaldo Carvalho de Melo { "COUNT_HW_CACHE_RESULT_MISS", PERF_COUNT_HW_CACHE_RESULT_MISS }, 977877108e4SArnaldo Carvalho de Melo 978129c04cbSIngo Molnar { "COUNT_HW_STALLED_CYCLES_FRONTEND", PERF_COUNT_HW_STALLED_CYCLES_FRONTEND }, 979129c04cbSIngo Molnar { "COUNT_HW_STALLED_CYCLES_BACKEND", PERF_COUNT_HW_STALLED_CYCLES_BACKEND }, 980129c04cbSIngo Molnar 981877108e4SArnaldo Carvalho de Melo { "COUNT_SW_CPU_CLOCK", PERF_COUNT_SW_CPU_CLOCK }, 982877108e4SArnaldo Carvalho de Melo { "COUNT_SW_TASK_CLOCK", PERF_COUNT_SW_TASK_CLOCK }, 983877108e4SArnaldo Carvalho de Melo { "COUNT_SW_PAGE_FAULTS", PERF_COUNT_SW_PAGE_FAULTS }, 984877108e4SArnaldo Carvalho de Melo { "COUNT_SW_CONTEXT_SWITCHES", PERF_COUNT_SW_CONTEXT_SWITCHES }, 985877108e4SArnaldo Carvalho de Melo { "COUNT_SW_CPU_MIGRATIONS", PERF_COUNT_SW_CPU_MIGRATIONS }, 986877108e4SArnaldo Carvalho de Melo { "COUNT_SW_PAGE_FAULTS_MIN", PERF_COUNT_SW_PAGE_FAULTS_MIN }, 987877108e4SArnaldo Carvalho de Melo { "COUNT_SW_PAGE_FAULTS_MAJ", PERF_COUNT_SW_PAGE_FAULTS_MAJ }, 988877108e4SArnaldo Carvalho de Melo { "COUNT_SW_ALIGNMENT_FAULTS", PERF_COUNT_SW_ALIGNMENT_FAULTS }, 989877108e4SArnaldo Carvalho de Melo { "COUNT_SW_EMULATION_FAULTS", PERF_COUNT_SW_EMULATION_FAULTS }, 990*d22d1a2aSAdrian Hunter { "COUNT_SW_DUMMY", PERF_COUNT_SW_DUMMY }, 991877108e4SArnaldo Carvalho de Melo 992877108e4SArnaldo Carvalho de Melo { "SAMPLE_IP", PERF_SAMPLE_IP }, 993877108e4SArnaldo Carvalho de Melo { "SAMPLE_TID", PERF_SAMPLE_TID }, 994877108e4SArnaldo Carvalho de Melo { "SAMPLE_TIME", PERF_SAMPLE_TIME }, 995877108e4SArnaldo Carvalho de Melo { "SAMPLE_ADDR", PERF_SAMPLE_ADDR }, 996877108e4SArnaldo Carvalho de Melo { "SAMPLE_READ", PERF_SAMPLE_READ }, 997877108e4SArnaldo Carvalho de Melo { "SAMPLE_CALLCHAIN", PERF_SAMPLE_CALLCHAIN }, 998877108e4SArnaldo Carvalho de Melo { "SAMPLE_ID", PERF_SAMPLE_ID }, 999877108e4SArnaldo Carvalho de Melo { "SAMPLE_CPU", PERF_SAMPLE_CPU }, 1000877108e4SArnaldo Carvalho de Melo { "SAMPLE_PERIOD", PERF_SAMPLE_PERIOD }, 1001877108e4SArnaldo Carvalho de Melo { "SAMPLE_STREAM_ID", PERF_SAMPLE_STREAM_ID }, 1002877108e4SArnaldo Carvalho de Melo { "SAMPLE_RAW", PERF_SAMPLE_RAW }, 1003877108e4SArnaldo Carvalho de Melo 1004877108e4SArnaldo Carvalho de Melo { "FORMAT_TOTAL_TIME_ENABLED", PERF_FORMAT_TOTAL_TIME_ENABLED }, 1005877108e4SArnaldo Carvalho de Melo { "FORMAT_TOTAL_TIME_RUNNING", PERF_FORMAT_TOTAL_TIME_RUNNING }, 1006877108e4SArnaldo Carvalho de Melo { "FORMAT_ID", PERF_FORMAT_ID }, 1007877108e4SArnaldo Carvalho de Melo { "FORMAT_GROUP", PERF_FORMAT_GROUP }, 1008877108e4SArnaldo Carvalho de Melo 1009877108e4SArnaldo Carvalho de Melo { "RECORD_MMAP", PERF_RECORD_MMAP }, 1010877108e4SArnaldo Carvalho de Melo { "RECORD_LOST", PERF_RECORD_LOST }, 1011877108e4SArnaldo Carvalho de Melo { "RECORD_COMM", PERF_RECORD_COMM }, 1012877108e4SArnaldo Carvalho de Melo { "RECORD_EXIT", PERF_RECORD_EXIT }, 1013877108e4SArnaldo Carvalho de Melo { "RECORD_THROTTLE", PERF_RECORD_THROTTLE }, 1014877108e4SArnaldo Carvalho de Melo { "RECORD_UNTHROTTLE", PERF_RECORD_UNTHROTTLE }, 1015877108e4SArnaldo Carvalho de Melo { "RECORD_FORK", PERF_RECORD_FORK }, 1016877108e4SArnaldo Carvalho de Melo { "RECORD_READ", PERF_RECORD_READ }, 1017877108e4SArnaldo Carvalho de Melo { "RECORD_SAMPLE", PERF_RECORD_SAMPLE }, 1018f6bbc1daSArnaldo Carvalho de Melo { .name = NULL, }, 1019877108e4SArnaldo Carvalho de Melo }; 1020877108e4SArnaldo Carvalho de Melo 1021877108e4SArnaldo Carvalho de Melo static PyMethodDef perf__methods[] = { 1022f6bbc1daSArnaldo Carvalho de Melo { .ml_name = NULL, } 1023877108e4SArnaldo Carvalho de Melo }; 1024877108e4SArnaldo Carvalho de Melo 1025877108e4SArnaldo Carvalho de Melo PyMODINIT_FUNC initperf(void) 1026877108e4SArnaldo Carvalho de Melo { 1027877108e4SArnaldo Carvalho de Melo PyObject *obj; 1028877108e4SArnaldo Carvalho de Melo int i; 1029877108e4SArnaldo Carvalho de Melo PyObject *dict, *module = Py_InitModule("perf", perf__methods); 1030877108e4SArnaldo Carvalho de Melo 1031877108e4SArnaldo Carvalho de Melo if (module == NULL || 1032877108e4SArnaldo Carvalho de Melo pyrf_event__setup_types() < 0 || 1033877108e4SArnaldo Carvalho de Melo pyrf_evlist__setup_types() < 0 || 1034877108e4SArnaldo Carvalho de Melo pyrf_evsel__setup_types() < 0 || 1035877108e4SArnaldo Carvalho de Melo pyrf_thread_map__setup_types() < 0 || 1036877108e4SArnaldo Carvalho de Melo pyrf_cpu_map__setup_types() < 0) 1037877108e4SArnaldo Carvalho de Melo return; 1038877108e4SArnaldo Carvalho de Melo 10390da2e9c2SArnaldo Carvalho de Melo page_size = sysconf(_SC_PAGE_SIZE); 10400da2e9c2SArnaldo Carvalho de Melo 1041877108e4SArnaldo Carvalho de Melo Py_INCREF(&pyrf_evlist__type); 1042877108e4SArnaldo Carvalho de Melo PyModule_AddObject(module, "evlist", (PyObject*)&pyrf_evlist__type); 1043877108e4SArnaldo Carvalho de Melo 1044877108e4SArnaldo Carvalho de Melo Py_INCREF(&pyrf_evsel__type); 1045877108e4SArnaldo Carvalho de Melo PyModule_AddObject(module, "evsel", (PyObject*)&pyrf_evsel__type); 1046877108e4SArnaldo Carvalho de Melo 1047877108e4SArnaldo Carvalho de Melo Py_INCREF(&pyrf_thread_map__type); 1048877108e4SArnaldo Carvalho de Melo PyModule_AddObject(module, "thread_map", (PyObject*)&pyrf_thread_map__type); 1049877108e4SArnaldo Carvalho de Melo 1050877108e4SArnaldo Carvalho de Melo Py_INCREF(&pyrf_cpu_map__type); 1051877108e4SArnaldo Carvalho de Melo PyModule_AddObject(module, "cpu_map", (PyObject*)&pyrf_cpu_map__type); 1052877108e4SArnaldo Carvalho de Melo 1053877108e4SArnaldo Carvalho de Melo dict = PyModule_GetDict(module); 1054877108e4SArnaldo Carvalho de Melo if (dict == NULL) 1055877108e4SArnaldo Carvalho de Melo goto error; 1056877108e4SArnaldo Carvalho de Melo 1057877108e4SArnaldo Carvalho de Melo for (i = 0; perf__constants[i].name != NULL; i++) { 1058877108e4SArnaldo Carvalho de Melo obj = PyInt_FromLong(perf__constants[i].value); 1059877108e4SArnaldo Carvalho de Melo if (obj == NULL) 1060877108e4SArnaldo Carvalho de Melo goto error; 1061877108e4SArnaldo Carvalho de Melo PyDict_SetItemString(dict, perf__constants[i].name, obj); 1062877108e4SArnaldo Carvalho de Melo Py_DECREF(obj); 1063877108e4SArnaldo Carvalho de Melo } 1064877108e4SArnaldo Carvalho de Melo 1065877108e4SArnaldo Carvalho de Melo error: 1066877108e4SArnaldo Carvalho de Melo if (PyErr_Occurred()) 1067877108e4SArnaldo Carvalho de Melo PyErr_SetString(PyExc_ImportError, "perf: Init failed!"); 1068877108e4SArnaldo Carvalho de Melo } 10690c6332e9SArnaldo Carvalho de Melo 10700c6332e9SArnaldo Carvalho de Melo /* 10710c6332e9SArnaldo Carvalho de Melo * Dummy, to avoid dragging all the test_attr infrastructure in the python 10720c6332e9SArnaldo Carvalho de Melo * binding. 10730c6332e9SArnaldo Carvalho de Melo */ 10740c6332e9SArnaldo Carvalho de Melo void test_attr__open(struct perf_event_attr *attr, pid_t pid, int cpu, 10750c6332e9SArnaldo Carvalho de Melo int fd, int group_fd, unsigned long flags) 10760c6332e9SArnaldo Carvalho de Melo { 10770c6332e9SArnaldo Carvalho de Melo } 1078