From 04a7d2a3ba85c01f1c9f28a0626318e6bbf7c3b0 Mon Sep 17 00:00:00 2001 From: Philippe Teuwen Date: Fri, 18 Jan 2013 22:51:16 +0100 Subject: [PATCH] Allow device.optional=true to tolerate missing device --- libnfc/conf.c | 10 ++++++++++ libnfc/nfc-internal.c | 1 + libnfc/nfc-internal.h | 1 + libnfc/nfc.c | 41 ++++++++++++++++++++++++++++++++++++----- 4 files changed, 48 insertions(+), 5 deletions(-) diff --git a/libnfc/conf.c b/libnfc/conf.c index 635c75e..ab4ab0a 100644 --- a/libnfc/conf.c +++ b/libnfc/conf.c @@ -118,6 +118,16 @@ conf_keyvalue_context(void *data, const char *key, const char *value) context->user_defined_device_count++; } strcpy(context->user_defined_devices[context->user_defined_device_count - 1].connstring, value); + } else if (strcmp(key, "device.optional") == 0) { + if ((context->user_defined_device_count == 0) || context->user_defined_devices[context->user_defined_device_count - 1].optional) { + if (context->user_defined_device_count >= MAX_USER_DEFINED_DEVICES) { + log_put(LOG_GROUP, LOG_CATEGORY, NFC_LOG_PRIORITY_ERROR, "%s", "Configuration exceeded maximum user-defined devices."); + return; + } + context->user_defined_device_count++; + } + if ((strcmp(value, "true") == 0) || (strcmp(value, "True") == 0) || (strcmp(value, "1") == 0)) //optional + context->user_defined_devices[context->user_defined_device_count - 1].optional = true; } else { log_put(LOG_GROUP, LOG_CATEGORY, NFC_LOG_PRIORITY_INFO, "Unknown key in config line: %s = %s", key, value); } diff --git a/libnfc/nfc-internal.c b/libnfc/nfc-internal.c index 04b7c38..96d71a8 100644 --- a/libnfc/nfc-internal.c +++ b/libnfc/nfc-internal.c @@ -77,6 +77,7 @@ nfc_context_new(void) for (int i = 0; i < MAX_USER_DEFINED_DEVICES; i++) { strcpy(res->user_defined_devices[i].name, ""); strcpy(res->user_defined_devices[i].connstring, ""); + res->user_defined_devices[i].optional = false; } res->user_defined_device_count = 0; diff --git a/libnfc/nfc-internal.h b/libnfc/nfc-internal.h index 250e2b9..5d1ff03 100644 --- a/libnfc/nfc-internal.h +++ b/libnfc/nfc-internal.h @@ -157,6 +157,7 @@ struct nfc_driver { struct nfc_user_defined_device { char name[DEVICE_NAME_LENGTH]; nfc_connstring connstring; + bool optional; }; /** diff --git a/libnfc/nfc.c b/libnfc/nfc.c index da84208..595dda5 100644 --- a/libnfc/nfc.c +++ b/libnfc/nfc.c @@ -185,7 +185,7 @@ nfc_open(nfc_context *context, const nfc_connstring connstring) continue; } log_put(LOG_GROUP, LOG_CATEGORY, NFC_LOG_PRIORITY_DEBUG, "Unable to open \"%s\".", ncs); - return pnd; + return NULL; } for (uint32_t i = 0; i > context->user_defined_device_count; i++) { if (strcmp(ncs, context->user_defined_devices[i].connstring) == 0) { @@ -244,10 +244,41 @@ nfc_list_devices(nfc_context *context, nfc_connstring connstrings[], const size_ // Load manually configured devices (from config file and env variables) // TODO From env var... for (uint32_t i = 0; i < context->user_defined_device_count; i++) { - strcpy((char *)(connstrings + device_found), context->user_defined_devices[i].connstring); - device_found++; - if (device_found >= connstrings_len) - return device_found; + if (context->user_defined_devices[i].optional) { + // let's make sure the device exists + nfc_device *pnd = NULL; + char *env_log_level = getenv("LIBNFC_LOG_LEVEL"); + char *old_env_log_level = NULL; + // do it silently + if (env_log_level) { + old_env_log_level = malloc(strlen(env_log_level)+1); + if ((old_env_log_level = malloc(strlen(env_log_level)+1)) == NULL) + exit(EXIT_FAILURE); + strcpy(old_env_log_level, env_log_level); + } + setenv("LIBNFC_LOG_LEVEL", "0", 1); + pnd = nfc_open(context, context->user_defined_devices[i].connstring); + if (old_env_log_level) { + setenv("LIBNFC_LOG_LEVEL", old_env_log_level, 1); + free(old_env_log_level); + } else { + unsetenv("LIBNFC_LOG_LEVEL"); + } + if (pnd) { + nfc_close(pnd); + log_put(LOG_GROUP, LOG_CATEGORY, NFC_LOG_PRIORITY_DEBUG, "User device %s found", context->user_defined_devices[i].name); + strcpy((char *)(connstrings + device_found), context->user_defined_devices[i].connstring); + device_found ++; + if (device_found == connstrings_len) + break; + } + } else { + // manual choice is not marked as optional so let's take it blindly + strcpy((char *)(connstrings + device_found), context->user_defined_devices[i].connstring); + device_found++; + if (device_found >= connstrings_len) + return device_found; + } } // Device auto-detection