1 PYTHON PLUGIN DOCUMENTATION 2============================= 3 4With the python plugin (make python-plugin) you can now 5write plugins in python. The API exported by the python 6plugin itself (written in C) allows you to access most 7information about a record from python. 8 9To write a python plugin, put a new .py file into a new 10~/.trace-cmd/python/ directory. 11 12The most basic python plugin is this: 13 14--- %< --- 15def register(pevent): 16 pass 17--- >% --- 18 19which obviously does nothing at all. 20 21To register a callback, use the pevent.register_event_handler 22function: 23 24--- %< --- 25import tracecmd 26 27def my_event_handler(trace_seq, event): 28 pass 29 30def register(pevent): 31 pevent.register_event_handler("subsys", "event_name", 32 my_event_handler) 33--- >% --- 34 35 36There are four object types that you get, described below. 37 38 tracecmd.PEvent 39----------------- 40 41This is the class of the 'pevent' object above, 42you get one of those via your register callback. 43It has one method and one property: 44 * register_event_handler() - example above, to register 45 an event handler function 46 * file_endian - either '<' or '>' indicating 47 which endianness the file has, 48 to be used with struct.unpack() 49 50 tracecmd.TraceSeq 51------------------- 52 53This is the class of the 'trace_seq' parameter to your callback 54function. It has only one method, puts(), to put data into the 55buffer. Formatting must be done in python. 56 57 tracecmd.Event 58---------------------- 59 60This is the class of the 'event' parameter to your callback 61function. Note that it doesn't just contain the format, but 62also the event data. As such, you can do much with this, and 63this is what you'll usually use. Each instance of this allows 64access to record items via the dict protocol, and you can get 65the items via its keys() methods. So for example, your 66callback could be 67 68--- %< --- 69def my_callback(trace_seq, event): 70 for fieldname in event.keys(): 71 field = event[fieldname] 72--- >% --- 73 74Each field returned from the dict protocol is an instance of 75the next (and last) class: 76 77 tracecmd.Field 78---------------------- 79 80This is an instance of a field, including its data. It affords 81numerous use cases and is what you'll be using most. 82 83 * If this is an integer field, i.e. 1, 2, 4 or 8 bytes long, 84 you can convert it to the number contained, according to 85 the file's endianness, by simply casting it to a long: 86 87 field = event['myint'] 88 value = long(field) 89 90 * You can access the field's data, as field.data, and if the 91 data is really a "__data_loc" type that will be resolved 92 automatically. (If you don't know what this means, don't 93 worry about it and just use field.data) 94 95 96This is it. It's pretty simple. A fully-featured plugin could 97look like this: 98 99--- %< --- 100def my_event_handler(trace_seq, event): 101 trace_seq.puts("myev: %u", long(event['myfield'])) 102 103def register(pevent): 104 pevent.register_event_handler("subsys", "event_name", 105 my_event_handler) 106--- >% --- 107 108 109 Tips and tricks 110----------------- 111 112Be familiar with the struct module and use it, always 113checking endianness and potentially using pevent.file_endian. 114 115 116If you need access to pevent in your callbacks, simply 117pass it in yourself: 118 119--- %< --- 120def my_event_handler(pevent, trace_seq, event): 121 pass 122 123def register(pevent): 124 pevent.register_event_handler("subsys", "event_name", 125 lambda *args: my_event_handler(pevent, *args) 126 ) 127--- >% --- 128