]> sigrok.org Git - libsigrok.git/blobdiff - src/std.c
drivers: Factor out std_*_idx*().
[libsigrok.git] / src / std.c
index 45cc3a49acf9b3ea25cae96513d095313b89f97d..7add7dd9c1ebdcebd6dfd9acea89f65f18430afa 100644 (file)
--- a/src/std.c
+++ b/src/std.c
@@ -26,6 +26,8 @@
  */
 
 #include <config.h>
+#include <string.h>
+#include <math.h>
 #include <glib.h>
 #include <libsigrok/libsigrok.h>
 #include "libsigrok-internal.h"
@@ -541,7 +543,7 @@ SR_PRIV int std_opts_config_list(uint32_t key, GVariant **data,
        return SR_OK;
 }
 
-SR_PRIV GVariant *std_gvar_tuple_array(const uint64_t (*a)[][2], unsigned int n)
+SR_PRIV GVariant *std_gvar_tuple_array(const uint64_t a[][2], unsigned int n)
 {
        unsigned int i;
        GVariant *rational[2];
@@ -550,8 +552,8 @@ SR_PRIV GVariant *std_gvar_tuple_array(const uint64_t (*a)[][2], unsigned int n)
        g_variant_builder_init(&gvb, G_VARIANT_TYPE_ARRAY);
 
        for (i = 0; i < n; i++) {
-               rational[0] = g_variant_new_uint64((*a)[i][0]);
-               rational[1] = g_variant_new_uint64((*a)[i][1]);
+               rational[0] = g_variant_new_uint64(a[i][0]);
+               rational[1] = g_variant_new_uint64(a[i][1]);
 
                /* FIXME: Valgrind reports a memory leak here. */
                g_variant_builder_add_value(&gvb, g_variant_new_tuple(rational, 2));
@@ -646,3 +648,183 @@ SR_PRIV GVariant *std_gvar_min_max_step_thresholds(const double min, const doubl
 
        return g_variant_builder_end(&gvb);
 }
+
+SR_PRIV GVariant *std_gvar_tuple_u64(uint64_t low, uint64_t high)
+{
+       GVariant *range[2];
+
+       range[0] = g_variant_new_uint64(low);
+       range[1] = g_variant_new_uint64(high);
+
+       return g_variant_new_tuple(range, 2);
+}
+
+SR_PRIV GVariant *std_gvar_tuple_double(double low, double high)
+{
+       GVariant *range[2];
+
+       range[0] = g_variant_new_double(low);
+       range[1] = g_variant_new_double(high);
+
+       return g_variant_new_tuple(range, 2);
+}
+
+SR_PRIV GVariant *std_gvar_array_i32(const int32_t *a, unsigned int n)
+{
+       return g_variant_new_fixed_array(G_VARIANT_TYPE_INT32,
+                               a, n, sizeof(int32_t));
+}
+
+SR_PRIV GVariant *std_gvar_array_u32(const uint32_t *a, unsigned int n)
+{
+       return g_variant_new_fixed_array(G_VARIANT_TYPE_UINT32,
+                               a, n, sizeof(uint32_t));
+}
+
+SR_PRIV GVariant *std_gvar_array_u64(const uint64_t *a, unsigned int n)
+{
+       return g_variant_new_fixed_array(G_VARIANT_TYPE_UINT64,
+                               a, n, sizeof(uint64_t));
+}
+
+SR_PRIV GVariant *std_gvar_thresholds(const double a[][2], unsigned int n)
+{
+       unsigned int i;
+       GVariant *gvar, *range[2];
+       GVariantBuilder gvb;
+
+       g_variant_builder_init(&gvb, G_VARIANT_TYPE_ARRAY);
+
+       for (i = 0; i < n; i++) {
+               range[0] = g_variant_new_double(a[i][0]);
+               range[1] = g_variant_new_double(a[i][1]);
+               gvar = g_variant_new_tuple(range, 2);
+               g_variant_builder_add_value(&gvb, gvar);
+       }
+
+       return g_variant_builder_end(&gvb);
+}
+
+/* Return the index of 'data' in the array 'arr' (or -1). */
+static int find_in_array(GVariant *data, const GVariantType *type,
+                        const void *arr, unsigned int n)
+{
+       const char * const *sarr;
+       const char *s;
+       const uint64_t *u64arr;
+       const uint8_t *u8arr;
+       uint64_t u64;
+       uint8_t u8;
+       unsigned int i;
+
+       if (!g_variant_is_of_type(data, type))
+               return -1;
+
+       switch (g_variant_classify(data)) {
+       case G_VARIANT_CLASS_STRING:
+               s = g_variant_get_string(data, NULL);
+               sarr = arr;
+
+               for (i = 0; i < n; i++)
+                       if (!strcmp(s, sarr[i]))
+                               return i;
+               break;
+       case G_VARIANT_CLASS_UINT64:
+               u64 = g_variant_get_uint64(data);
+               u64arr = arr;
+
+               for (i = 0; i < n; i++)
+                       if (u64 == u64arr[i])
+                               return i;
+               break;
+       case G_VARIANT_CLASS_BYTE:
+               u8 = g_variant_get_byte(data);
+               u8arr = arr;
+
+               for (i = 0; i < n; i++)
+                       if (u8 == u8arr[i])
+                               return i;
+       default:
+               break;
+       }
+
+       return -1;
+}
+
+SR_PRIV int std_str_idx(GVariant *data, const char *a[], unsigned int n)
+{
+       return find_in_array(data, G_VARIANT_TYPE_STRING, a, n);
+}
+
+SR_PRIV int std_u64_idx(GVariant *data, const uint64_t a[], unsigned int n)
+{
+       return find_in_array(data, G_VARIANT_TYPE_UINT64, a, n);
+}
+
+SR_PRIV int std_u8_idx(GVariant *data, const uint8_t a[], unsigned int n)
+{
+       return find_in_array(data, G_VARIANT_TYPE_BYTE, a, n);
+}
+
+SR_PRIV int std_str_idx_s(const char *s, const char *a[], unsigned int n)
+{
+       int idx;
+       GVariant *data;
+
+       data = g_variant_new_string(s);
+       idx = find_in_array(data, G_VARIANT_TYPE_STRING, a, n);
+       g_variant_unref(data);
+
+       return idx;
+}
+
+SR_PRIV int std_u8_idx_s(uint8_t b, const uint8_t a[], unsigned int n)
+{
+       int idx;
+       GVariant *data;
+
+       data = g_variant_new_byte(b);
+       idx = find_in_array(data, G_VARIANT_TYPE_BYTE, a, n);
+       g_variant_unref(data);
+
+       return idx;
+}
+
+SR_PRIV int std_u64_tuple_idx(GVariant *data, const uint64_t a[][2], unsigned int n)
+{
+       unsigned int i;
+       uint64_t low, high;
+
+       g_variant_get(data, "(tt)", &low, &high);
+
+       for (i = 0; i < n; i++)
+               if (a[i][0] == low && a[i][1] == high)
+                       return i;
+
+       return -1;
+}
+
+SR_PRIV int std_double_tuple_idx(GVariant *data, const double a[][2], unsigned int n)
+{
+       unsigned int i;
+       double low, high;
+
+       g_variant_get(data, "(dd)", &low, &high);
+
+       for (i = 0; i < n; i++)
+               if ((fabs(a[i][0] - low) < 0.1) && ((fabs(a[i][1] - high) < 0.1)))
+                       return i;
+
+       return -1;
+}
+
+SR_PRIV int std_double_tuple_idx_d0(const double d, const double a[][2], unsigned int n)
+{
+       unsigned int i;
+
+       for (i = 0; i < n; i++)
+               if (d == a[i][0])
+                       return i;
+
+       return -1;
+}