From 409d85b3ac23c2915413c97354533f1d05f7dd9e Mon Sep 17 00:00:00 2001 From: Martin Ling Date: Tue, 17 Dec 2013 00:42:33 +0000 Subject: [PATCH] python: Finish output format support. --- bindings/python/sigrok/core/classes.py | 56 +++++++++++++++++++++++++- bindings/swig/libsigrok.i | 48 ++++++++++++++++++++-- 2 files changed, 99 insertions(+), 5 deletions(-) diff --git a/bindings/python/sigrok/core/classes.py b/bindings/python/sigrok/core/classes.py index 15bfc937..e73c94cb 100644 --- a/bindings/python/sigrok/core/classes.py +++ b/bindings/python/sigrok/core/classes.py @@ -26,7 +26,7 @@ import itertools __all__ = ['Error', 'Context', 'Driver', 'Device', 'Session', 'Packet', 'Log', 'LogLevel', 'PacketType', 'Quantity', 'Unit', 'QuantityFlag', 'ConfigKey', 'ProbeType', 'Probe', 'ProbeGroup', 'InputFormat', 'OutputFormat', - 'InputFile'] + 'InputFile', 'Output'] class Error(Exception): @@ -446,7 +446,7 @@ class InputFile(object): self.struct = sr_input() self.struct.format = self.format.struct self.struct.param = g_hash_table_new_full( - g_str_hash, g_str_equal, g_free, g_free) + g_str_hash_ptr, g_str_equal_ptr, g_free_ptr, g_free_ptr) for key, value in kwargs.items(): g_hash_table_insert(self.struct.param, g_strdup(key), g_strdup(str(value))) check(self.format.struct.call_init(self.struct, self.filename)) @@ -471,6 +471,58 @@ class OutputFormat(object): def description(self): return self.struct.description +class Output(object): + + def __init__(self, format, device, param=None): + self.format = format + self.device = device + self.param = param + self.struct = sr_output() + self.struct.format = self.format.struct + self.struct.sdi = self.device.struct + self.struct.param = param + check(self.format.struct.call_init(self.struct)) + + def receive(self, packet): + + output_buf_ptr = new_uint8_ptr_ptr() + output_len_ptr = new_uint64_ptr() + using_obsolete_api = False + + if self.format.struct.event and packet.type in ( + PacketType.TRIGGER, PacketType.FRAME_BEGIN, + PacketType.FRAME_END, PacketType.END): + check(self.format.struct.call_event(self.struct, packet.type.id, + output_buf_ptr, output_len_ptr)) + using_obsolete_api = True + elif self.format.struct.data and packet.type.id == self.format.struct.df_type: + check(self.format.struct.call_data(self.struct, + packet.payload.struct.data, packet.payload.struct.length, + output_buf_ptr, output_len_ptr)) + using_obsolete_api = True + + if using_obsolete_api: + output_buf = uint8_ptr_ptr_value(output_buf_ptr) + output_len = uint64_ptr_value(output_len_ptr) + result = cdata(output_buf, output_len) + g_free(output_buf) + return result + + if self.format.struct.receive: + out_ptr = new_gstring_ptr_ptr() + check(self.format.struct.call_receive(self.struct, self.device.struct, + packet.struct, out_ptr)) + out = gstring_ptr_ptr_value(out_ptr) + if out: + result = out.str + g_string_free(out, True) + return result + + return None + + def __del__(self): + check(self.format.struct.call_cleanup(self.struct)) + class EnumValue(object): _enum_values = {} diff --git a/bindings/swig/libsigrok.i b/bindings/swig/libsigrok.i index 773bb947..d670efc8 100644 --- a/bindings/swig/libsigrok.i +++ b/bindings/swig/libsigrok.i @@ -26,6 +26,7 @@ %} typedef void *gpointer; +typedef int gboolean; typedef struct _GSList GSList; @@ -58,12 +59,25 @@ GHashTable *g_hash_table_new_full(GHashFunc hash_func, GEqualFunc key_equal_func void g_hash_table_insert(GHashTable *hash_table, gpointer key, gpointer value); void g_hash_table_destroy(GHashTable *hash_table); -%constant guint g_str_hash(gconstpointer v); -%constant gboolean g_str_equal(gconstpointer v1, gconstpointer v2);; -%constant void g_free(gpointer mem); +%callback("%s_ptr"); +guint g_str_hash(gconstpointer v); +gboolean g_str_equal(gconstpointer v1, gconstpointer v2);; +void g_free(gpointer mem); +%nocallback; gchar *g_strdup(const char *str); +typedef struct _GString GString; + +struct _GString +{ + char *str; + gsize len; + gsize allocated_len; +}; + +gchar *g_string_free(GString *string, gboolean free_segment); + %include "libsigrok/libsigrok.h" #undef SR_API #define SR_API @@ -72,6 +86,9 @@ gchar *g_strdup(const char *str); %include "libsigrok/version.h" %array_class(float, float_array); +%pointer_functions(uint8_t *, uint8_ptr_ptr); +%pointer_functions(uint64_t, uint64_ptr); +%pointer_functions(GString *, gstring_ptr_ptr); %pointer_functions(GVariant *, gvariant_ptr_ptr); %array_functions(GVariant *, gvariant_ptr_array); %pointer_functions(struct sr_context *, sr_context_ptr_ptr); @@ -97,3 +114,28 @@ gchar *g_strdup(const char *str); return $self->loadfile(in, filename); } } + +%extend sr_output_format { + int call_init(struct sr_output *o) { + return $self->init(o); + } + + int call_event(struct sr_output *o, int event_type, uint8_t **data_out, + uint64_t *length_out) { + return $self->event(o, event_type, data_out, length_out); + } + + int call_data(struct sr_output *o, const void *data_in, + uint64_t length_in, uint8_t **data_out, uint64_t *length_out) { + return $self->data(o, data_in, length_in, data_out, length_out); + } + + int call_receive(struct sr_output *o, const struct sr_dev_inst *sdi, + const struct sr_datafeed_packet *packet, GString **out) { + return $self->receive(o, sdi, packet, out); + } + + int call_cleanup(struct sr_output *o) { + return $self->cleanup(o); + } +}