前幾天寫了一篇文章,詳述了libnfc 1.7.0在windows下的編譯過程,打開了對acr122u模塊、pn53x_usb模塊、pn532_uart模塊等的支持,今天試了一下,發現在win下libnfc默認好像只掃描使用acr122_pcsc driver和pn53x_usb driver的模塊,而我連接了pn532_uart模塊之後提示沒有找到NFC設備。
Debug模式編譯運行nfc-list.exe輸出如下:
unknown libnfc.general log_level is set to 3
debug libnfc.general allow_autoscan is set to true
debug libnfc.general allow_intrusive_scan is set to false
debug libnfc.general 0 device(s) defined by user
nfc-list.exe uses libnfc 1.7.0
debug libnfc.general 0 device(s) found using acr122_pcsc driver
debug libnfc.general 0 device(s) found using pn53x_usb driver
No NFC device found.
於是,我開始查找支持pn532_uart的方法,通過查看源碼發現libnfc使用兩種方式獲取nfc設備:
1.自動掃描 autoscan
2.用戶自定義設備 user_defined_device
libnfc支持讀取libnfc.conf配置文件的方式加載用戶定義的設備。
最開始,我嘗試了在cmake生成的config.h裏增加#define CONFFILES,重新編譯的時候報錯:
undefined reference to '_imp__regcomp'
這是由於conf.c裏面調用了regcomp等函數,這些函數屬於regex正則解析庫,但是我使用的MinGW64裏面沒有這個庫。
於是我複製了早期的MinGW的libregex庫以及頭文件,編譯能通過,但是運行nfc-list.exe運行到讀取配置文件時就出錯退出了,估計還是正則庫有問題。
libregex使用不了也沒關係,其實可以修改conf.c去掉正則解析的過程,直接將參數賦值給nfc_context。
主要需要修改config.h和conf.c兩個文件。
在config.h裏增加 #define CONFFILES
修改conf.c如下:
#include "conf.h"
#ifdef HAVE_CONFIG_H
# include "config.h"
#endif // HAVE_CONFIG_H
#ifdef CONFFILES
#include <stdio.h>
#include <stdlib.h>
#include <dirent.h>
#include <string.h>
#include <regex.h>
#include <sys/stat.h>
#include <nfc/nfc.h>
#include "nfc-internal.h"
#include "log.h"
#define LOG_CATEGORY "libnfc.config"
#define LOG_GROUP NFC_LOG_GROUP_CONFIG
#ifndef LIBNFC_SYSCONFDIR
// If this define does not already exists, we build it using SYSCONFDIR
#ifndef SYSCONFDIR
#error "SYSCONFDIR is not defined but required."
#endif // SYSCONFDIR
#define LIBNFC_SYSCONFDIR SYSCONFDIR"/nfc"
#endif // LIBNFC_SYSCONFDIR
//#define LIBNFC_CONFFILE LIBNFC_SYSCONFDIR"/libnfc.conf"
//#define LIBNFC_DEVICECONFDIR LIBNFC_SYSCONFDIR"/devices.d"
#define LIBNFC_CONFFILE "libnfc.conf"
#define LIBNFC_DEVICECONFDIR "devices.d"
static bool
conf_parse_file(const char *filename, void (*conf_keyvalue)(void *data), void *data)
{
printf("Try to Conf Key Value by chenxupro\n");
conf_keyvalue(data);
return true;
}
static void
conf_keyvalue_context(void *data)
{
nfc_context *context = (nfc_context *)data;
//if (strcmp(key, "allow_autoscan") == 0) {
string_as_boolean("true", &(context->allow_autoscan));
//} else if (strcmp(key, "allow_intrusive_scan") == 0) {
string_as_boolean("false", &(context->allow_intrusive_scan));
//} else if (strcmp(key, "log_level") == 0) {
context->log_level = atoi("2");
//} else if (strcmp(key, "device.name") == 0) {
if ((context->user_defined_device_count == 0) || strcmp(context->user_defined_devices[context->user_defined_device_count - 1].name, "") != 0) {
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++;
}
strcpy(context->user_defined_devices[context->user_defined_device_count - 1].name, "chenxupro PN532");
//} else if (strcmp(key, "device.connstring") == 0) {
if ((context->user_defined_device_count == 0) || strcmp(context->user_defined_devices[context->user_defined_device_count - 1].connstring, "") != 0) {
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++;
}
strcpy(context->user_defined_devices[context->user_defined_device_count - 1].connstring, "pn532_uart:COM9:115200");
}
void conf_load(nfc_context *context)
{
conf_parse_file(LIBNFC_CONFFILE, conf_keyvalue_context, context);
}
#endif // CONFFILES
重新編譯,運行結果如下:
unknown libnfc.general log_level is set to 2
debug libnfc.general allow_autoscan is set to true
debug libnfc.general allow_intrusive_scan is set to false
debug libnfc.general 1 device(s) defined by user
debug libnfc.general #0 name: "chenxupro PN532", connstring: "pn532_uart:COM9:115200"
debug libnfc.general 0 device(s) found using acr122_pcsc driver
debug libnfc.general 0 device(s) found using pn53x_usb driver
debug libnfc.driver.pn532_uart Attempt to open: COM9 at 115200 bauds.
Try to Conf Key Value by chenxupro
nfc-list.exe uses libnfc 1.7.0
NFC device: pn532_uart:COM9 opened
1 ISO14443A passive target(s) found:
ISO/IEC 14443A (106 kbps) target:
ATQA (SENS_RES): 00 04
UID (NFCID1): 7d 88 c9 1d
SAK (SEL_RES): 08