X-Git-Url: https://sigrok.org/gitweb/?p=libsigrokdecode.git;a=blobdiff_plain;f=controller.c;h=f3c1446f9ac40a952180fad8415369965fb33b57;hp=d2056915b831c961c90cc1373ecf395c89e7f478;hb=9d9fcb375d7702082146bf917a5d19cc83480eae;hpb=4fadb1282f5e9aa41abcb67e7d90cdc4a9b2628d diff --git a/controller.c b/controller.c index d205691..f3c1446 100644 --- a/controller.c +++ b/controller.c @@ -118,10 +118,19 @@ int srd_exit(void) /** - * Add search directories for the protocol decoders. + * Add an additional search directory for the protocol decoders. + * + * The specified directory is prepended (not appended!) to Python's sys.path, + * in order to search for sigrok protocol decoders in the specified + * directories first, and in the generic Python module directories (and in + * the current working directory) last. This avoids conflicts if there are + * Python modules which have the same name as a sigrok protocol decoder in + * sys.path or in the current working directory. * * TODO: add path from env var SIGROKDECODE_PATH, config etc * TODO: Should take directoryname/path as input. + * + * @return TODO. */ int set_modulepath(void) { @@ -143,9 +152,8 @@ int set_modulepath(void) path = g_strdup(DECODERS_DIR); #endif - /* TODO: Prepend instead of appending. */ /* TODO: Sanity check on 'path' (length, escape special chars, ...). */ - s = g_strdup_printf("import sys; sys.path.append(r'%s')", path); + s = g_strdup_printf("import sys; sys.path.insert(0, r'%s')", path); ret = PyRun_SimpleString(s); @@ -266,11 +274,8 @@ err_out: Py_XDECREF(py_dec_options); if (key) g_free(key); - if (PyErr_Occurred()) { - srd_dbg("srd: stray exception!"); - PyErr_Print(); - PyErr_Clear(); - } + if (PyErr_Occurred()) + catch_exception("srd: stray exception in srd_instance_set_options()"); return ret; } @@ -299,7 +304,7 @@ int srd_instance_set_probes(struct srd_decoder_instance *di, GSList *sl; struct srd_probe *p; int *new_probemap, new_probenum; - char *probe_id; + char *probe_id, *probenum_str; if (g_hash_table_size(new_probes) == 0) /* No probes provided. */ @@ -321,7 +326,14 @@ int srd_instance_set_probes(struct srd_decoder_instance *di, for (l = g_hash_table_get_keys(new_probes); l; l = l->next) { probe_id = l->data; - new_probenum = strtol(g_hash_table_lookup(new_probes, probe_id), NULL, 10); + probenum_str = g_hash_table_lookup(new_probes, probe_id); + if (!probenum_str) { + /* Probe name was specified without a value. */ + srd_err("No probe number was specified for %s.", probe_id); + g_free(new_probemap); + return SRD_ERR_ARG; + } + new_probenum = strtol(probenum_str, NULL, 10); if (!(sl = g_slist_find_custom(di->decoder->probes, probe_id, (GCompareFunc)compare_probe_id))) { /* Fall back on optional probes. */ @@ -394,7 +406,7 @@ struct srd_decoder_instance *srd_instance_new(const char *decoder_id, /* Create a new instance of this decoder class. */ if (!(di->py_instance = PyObject_CallObject(dec->py_dec, NULL))) { if (PyErr_Occurred()) - PyErr_Print(); + catch_exception("failed to create %s instance: ", decoder_id); g_free(di->dec_probemap); g_free(di); return NULL; @@ -463,15 +475,13 @@ int srd_instance_start(struct srd_decoder_instance *di, PyObject *args) if (!(py_name = PyUnicode_FromString("start"))) { srd_err("Unable to build python object for 'start'."); - if (PyErr_Occurred()) - PyErr_Print(); + catch_exception("Protocol decoder instance %s: ", di->instance_id); return SRD_ERR_PYTHON; } if (!(py_res = PyObject_CallMethodObjArgs(di->py_instance, py_name, args, NULL))) { - if (PyErr_Occurred()) - PyErr_Print(); + catch_exception("Protocol decoder instance %s: ", di->instance_id); return SRD_ERR_PYTHON; } @@ -533,9 +543,7 @@ int srd_instance_decode(uint64_t start_samplenum, end_samplenum = start_samplenum + inbuflen / di->data_unitsize; if (!(py_res = PyObject_CallMethod(di->py_instance, "decode", "KKO", logic->start_samplenum, end_samplenum, logic))) { - if (PyErr_Occurred()) - PyErr_Print(); /* Returns void. */ - + catch_exception("Protocol decoder instance %s: ", di->instance_id); return SRD_ERR_PYTHON; /* TODO: More specific error? */ } Py_DecRef(py_res);