]> sigrok.org Git - libsigrok.git/blobdiff - src/scpi/scpi.c
scpi_vxi: fix memory leak for SCPI response data in VXI support code
[libsigrok.git] / src / scpi / scpi.c
index 0f767f2a2de1c6862b61620d6e2dc0b9178c2f7d..0e74b32901f10e21b4a657d2ddebd57dbd401957 100644 (file)
@@ -315,33 +315,32 @@ SR_PRIV GSList *sr_scpi_scan(struct drv_context *drvc, GSList *options,
 {
        GSList *resources, *l, *devices;
        struct sr_dev_inst *sdi;
-       const char *resource = NULL;
-       const char *serialcomm = NULL;
+       const char *resource, *conn;
+       const char *serialcomm, *comm;
        gchar **res;
        unsigned i;
 
-       for (l = options; l; l = l->next) {
-               struct sr_config *src = l->data;
-               switch (src->key) {
-               case SR_CONF_CONN:
-                       resource = g_variant_get_string(src->data, NULL);
-                       break;
-               case SR_CONF_SERIALCOMM:
-                       serialcomm = g_variant_get_string(src->data, NULL);
-                       break;
-               }
-       }
+       resource = NULL;
+       serialcomm = NULL;
+       (void)sr_serial_extract_options(options, &resource, &serialcomm);
 
        devices = NULL;
        for (i = 0; i < ARRAY_SIZE(scpi_devs); i++) {
-               if ((resource && strcmp(resource, scpi_devs[i]->prefix))
-                   || !scpi_devs[i]->scan)
+               if (resource && strcmp(resource, scpi_devs[i]->prefix) != 0)
+                       continue;
+               if (!scpi_devs[i]->scan)
                        continue;
                resources = scpi_devs[i]->scan(drvc);
                for (l = resources; l; l = l->next) {
                        res = g_strsplit(l->data, ":", 2);
-                       if (res[0] && (sdi = sr_scpi_scan_resource(drvc, res[0],
-                                      serialcomm ? serialcomm : res[1], probe_device))) {
+                       if (!res[0]) {
+                               g_strfreev(res);
+                               continue;
+                       }
+                       conn = res[0];
+                       comm = serialcomm ? : res[1];
+                       sdi = sr_scpi_scan_resource(drvc, conn, comm, probe_device);
+                       if (sdi) {
                                devices = g_slist_append(devices, sdi);
                                sdi->connection_id = g_strdup(l->data);
                        }
@@ -863,28 +862,30 @@ SR_PRIV int sr_scpi_get_floatv(struct sr_scpi_dev_inst *scpi,
        float tmp;
        char *response;
        gchar **ptr, **tokens;
+       size_t token_count;
        GArray *response_array;
 
        *scpi_response = NULL;
-       response = NULL;
-       tokens = NULL;
 
+       response = NULL;
        ret = sr_scpi_get_string(scpi, command, &response);
        if (ret != SR_OK && !response)
                return ret;
 
        tokens = g_strsplit(response, ",", 0);
-       ptr = tokens;
+       token_count = g_strv_length(tokens);
 
-       response_array = g_array_sized_new(TRUE, FALSE, sizeof(float), 256);
+       response_array = g_array_sized_new(TRUE, FALSE,
+               sizeof(float), token_count + 1);
 
+       ptr = tokens;
        while (*ptr) {
-               if (sr_atof_ascii(*ptr, &tmp) == SR_OK)
-                       response_array = g_array_append_val(response_array,
-                                                           tmp);
-               else
+               ret = sr_atof_ascii(*ptr, &tmp);
+               if (ret != SR_OK) {
                        ret = SR_ERR_DATA;
-
+                       break;
+               }
+               response_array = g_array_append_val(response_array, tmp);
                ptr++;
        }
        g_strfreev(tokens);
@@ -920,28 +921,30 @@ SR_PRIV int sr_scpi_get_uint8v(struct sr_scpi_dev_inst *scpi,
        int tmp, ret;
        char *response;
        gchar **ptr, **tokens;
+       size_t token_count;
        GArray *response_array;
 
        *scpi_response = NULL;
-       response = NULL;
-       tokens = NULL;
 
+       response = NULL;
        ret = sr_scpi_get_string(scpi, command, &response);
        if (ret != SR_OK && !response)
                return ret;
 
        tokens = g_strsplit(response, ",", 0);
-       ptr = tokens;
+       token_count = g_strv_length(tokens);
 
-       response_array = g_array_sized_new(TRUE, FALSE, sizeof(uint8_t), 256);
+       response_array = g_array_sized_new(TRUE, FALSE,
+               sizeof(uint8_t), token_count + 1);
 
+       ptr = tokens;
        while (*ptr) {
-               if (sr_atoi(*ptr, &tmp) == SR_OK)
-                       response_array = g_array_append_val(response_array,
-                                                           tmp);
-               else
+               ret = sr_atoi(*ptr, &tmp);
+               if (ret != SR_OK) {
                        ret = SR_ERR_DATA;
-
+                       break;
+               }
+               response_array = g_array_append_val(response_array, tmp);
                ptr++;
        }
        g_strfreev(tokens);
@@ -1151,7 +1154,7 @@ SR_PRIV int sr_scpi_get_hw_id(struct sr_scpi_dev_inst *scpi,
        }
        g_free(response);
 
-       hw_info = g_malloc0(sizeof(struct sr_scpi_hw_info));
+       hw_info = g_malloc0(sizeof(*hw_info));
 
        idn_substr = g_strstr_len(tokens[0], -1, "IDN ");
        if (idn_substr == NULL)