Показаны сообщения с ярлыком mifare classic 1K. Показать все сообщения
Показаны сообщения с ярлыком mifare classic 1K. Показать все сообщения

среда, 20 мая 2015 г.

Хранение кодовой фразы в NFC-картах Mifare Classic Ultralight, 1K, 4K для картридеров ACR122, ACR1251

Кодовая фраза, состоящая из шести байт, хранится на NFC-картах (например, Mifare Classic 1K, ) вместе с секторами данных. Перед записью блока на карту или чтением c карты нужно пройти аутентификацию для доступа к сектору, содержащему указанный блок. Это справедливо для карт Mifare Classic 1K, 4K. Для самой простой и наименьшей по объему хранения данных карты Mifare Classic Ultralight аутентификация не нужна, доступ на запись и чтение к блоку данных её не требует.

Для карты Mifare Classic 1K каждый сектор состоит из четырех блоков: три блока данных (data block) и один дополнительный блок (trailer block). В этом блоке хранится информация для проверки доступа к блокам сектора. Описание (datasheet) карты хранения памяти (memory map) в картах Mifare Classic 1K можно посмотреть здесь.

В картридере ACR122 нет энергонезависимой памяти для хранения ключей доступа к картам для проверки. Перед работой с картами 6-байтный ключ должен быть загружен при помощи функции Load Authentication Keys APDU Format (11 bytes). Например, для дефолтного ключа FF FF FF FF FF FF с загрузкой в энергозависимую область хранения картридера с адресом 0x00 APDU-структура (записываемая в картридер команда) имеет следующий вид {FF 82 00 00h 06 FF FF FF FF FF FFh}. Затем перед доступом на чтение или запись к определенному блоку карты нужно пройти аутентификацию при помощи вызова одного из двух вариантов функции Load Authentication Keys APDU Format (6 Bytes) или (10 Bytes). Рассмотрим пример вызова функции (6 Bytes). Для аутентификации доступа к блоку 04h будем использовать тип ключа A (Type A) 60h, загруженный в область 00h. APDU-структура имеет следующий вид {FF 88 00 04 60 00h}. Теперь можно, например, прочитать 16-байтовый блок с адресом 04h при помощи функции Read Binary APDU Format (5 Bytes) APDU = {FF B0 00 04 10h}. Описание API работы картридера ACR122 можно посмотреть здесь.

Картридер ACR1251, в отличии от ACR122, имеет встроенную энергонезависимую память для хранения до 32 ключей для доступа к секторам карт. Описание API работы картридера ACR1251 можно скачать отсюда.

Для работы с картридером используется API проекта pcsc-lite, doxygen-документацию по которому можно найти на сайте проекта https://pcsclite.alioth.debian.org/api/.

Интересная статья про уязвимости карт Mifare Classic 1K http://habrahabr.ru/post/141213/.

Дополнительный материал:
1) MIFARE Ultralight datasheet
2) MIFARE Classic EV1 1K datasheet

понедельник, 18 мая 2015 г.

Установка драйвера (libacsccid) для работы с NFC-картридером ACR122 под Ubuntu 14.04

Файлы библиотеки libpcsclite уже предустановлены в дистрибутиве Ubuntu (библиотека /lib/x86_64-linux-gnu/libpcsclite.so.1.0.0 и символьная ссылка /lib/x86_64-linux-gnu/libpcsclite.so). Устанавливаем необходимые пакеты демона (pcscd) и драйвера (libacsccid) из репозитария Ubuntu. Есть два драйвера, два пакета libacsccid (поддерживающий большее количество карт фирмы ACS и тестирующийся ее инженерами https://lists.debian.org/debian-devel/2011/05/msg00705.html) и libccid (дефолный). Ставим демон pcscd и библиотеку libacsccid из репозитария:

sudo apt-get install pcscd

sudo apt-get install libacsccid1

Команда lsusb (sudo lsusb) видит картридер ACR122:

Bus 002 Device 002: ID 058f:6362 Alcor Micro Corp. Flash Card Reader/Writer
Bus 002 Device 001: ID 1d6b:0002 Linux Foundation 2.0 root hub
Bus 008 Device 002: ID 04d9:1702 Holtek Semiconductor, Inc. 
Bus 008 Device 001: ID 1d6b:0001 Linux Foundation 1.1 root hub
Bus 007 Device 003: ID 072f:2200 Advanced Card Systems, Ltd 
Bus 007 Device 001: ID 1d6b:0001 Linux Foundation 1.1 root hub
Bus 006 Device 001: ID 1d6b:0001 Linux Foundation 1.1 root hub
Bus 001 Device 001: ID 1d6b:0002 Linux Foundation 2.0 root hub
Bus 005 Device 001: ID 1d6b:0001 Linux Foundation 1.1 root hub
Bus 004 Device 001: ID 1d6b:0001 Linux Foundation 1.1 root hub
Bus 003 Device 001: ID 1d6b:0001 Linux Foundation 1.1 root hub

Остановим запущенный демон pcscd (sudo service pcscd stop или sudo killall pcscd). Запустим демон в режиме отладки (sudo /usr/sbin/pcscd -fd), чтобы увидеть, что драйвер картридера libacsccid корректно загрузился при подключении устройства:

00000000 debuglog.c:269:DebugLogSetLevel() debug level=debug
00000150 configfile.l:254:DBGetReaderListDir() Parsing conf directory: /etc/reader.conf.d
00000034 configfile.l:307:DBGetReaderList() Parsing conf file: /etc/reader.conf.d/libccidtwin
00000059 configfile.l:266:DBGetReaderListDir() Skipping non regular file: .
00000019 configfile.l:266:DBGetReaderListDir() Skipping non regular file: ..
00000020 pcscdaemon.c:545:main() pcsc-lite 1.8.10 daemon ready.
00001981 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x1D6B, PID: 0x0001, path: /dev/bus/usb/003/001
00000157 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x1D6B, PID: 0x0001, path: /dev/bus/usb/004/001
00000149 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x1D6B, PID: 0x0001, path: /dev/bus/usb/005/001
00000148 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x1D6B, PID: 0x0002, path: /dev/bus/usb/001/001
00000140 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x1D6B, PID: 0x0001, path: /dev/bus/usb/006/001
00000140 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x1D6B, PID: 0x0001, path: /dev/bus/usb/007/001
00000111 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x1D6B, PID: 0x0001, path: /dev/bus/usb/007/001
00000116 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x072F, PID: 0x2200, path: /dev/bus/usb/007/003
00000040 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x072F, PID: 0x2200, path: /dev/bus/usb/007/003
00000017 hotplug_libudev.c:321:HPAddDevice() Adding USB device: ACS ACR122U
00000038 readerfactory.c:989:RFInitializeReader() Attempting startup of ACS ACR122U 00 00 using /usr/lib/pcsc/drivers/ifd-acsccid.bundle/Contents/Linux/libacsccid.so
00000210 readerfactory.c:874:RFBindFunctions() Loading IFD Handler 3.0
00000041 ifdhandler.c:2328:init_driver() Driver version: 1.0.5
00000248 ifdhandler.c:2341:init_driver() LogLevel: 0x0003
00001316 ifdhandler.c:2361:init_driver() DriverOptions: 0x00C0
00000221 ifdhandler.c:2388:init_driver() ACR38CardVoltage: 0
00000210 ifdhandler.c:2395:init_driver() ACR38CardType: 0
00000016 ifdhandler.c:94:IFDHCreateChannelByName() lun: 0, device: usb:072f/2200:libudev:0:/dev/bus/usb/007/003
00094665 ccid_usb.c:375:OpenUSBByName() Manufacturer: Advanced Card Systems Ltd.
00000199 ccid_usb.c:385:OpenUSBByName() ProductString: ACS CCID driver
00000191 ccid_usb.c:391:OpenUSBByName() Copyright: This driver is protected by terms of the GNU Lesser General Public License version 2.1, or (at your option) any later version.
00012154 ccid_usb.c:643:OpenUSBByName() Can't claim interface 007/003: Device or resource busy
00025410 ifdhandler.c:118:IFDHCreateChannelByName() failed
00000039 readerfactory.c:1020:RFInitializeReader() Open Port 0x200000 Failed (usb:072f/2200:libudev:0:/dev/bus/usb/007/003)
00000015 readerfactory.c:312:RFAddReader() ACS ACR122U init failed.
00000018 readerfactory.c:535:RFRemoveReader() UnrefReader() count was: 1
00000013 readerfactory.c:1040:RFUnInitializeReader() Attempting shutdown of ACS ACR122U 00 00.
00000012 readerfactory.c:911:RFUnloadReader() Unloading reader driver.
00000238 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x1D6B, PID: 0x0001, path: /dev/bus/usb/008/001
00000126 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x1D6B, PID: 0x0001, path: /dev/bus/usb/008/001
00000121 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x04D9, PID: 0x1702, path: /dev/bus/usb/008/002
00000119 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x04D9, PID: 0x1702, path: /dev/bus/usb/008/002
00000150 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x1D6B, PID: 0x0002, path: /dev/bus/usb/002/001
00000116 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x1D6B, PID: 0x0002, path: /dev/bus/usb/002/001
00000118 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x058F, PID: 0x6362, path: /dev/bus/usb/002/002
^C31211962 pcscdaemon.c:726:signal_trap() Received signal: 2
00000017 pcscdaemon.c:745:signal_trap() Preparing for suicide
01000081 readerfactory.c:1273:RFCleanupReaders() entering cleaning function
00000026 winscard_svc.c:130:ContextsDeinitialize() remaining threads: 0

00000007 pcscdaemon.c:670:at_exit() cleaning /var/run/pcscd

Возникает ошибка: "Can't claim interface 007/003: Device or resource busy".

При загрузке ядра мы получаем следующие сообщения инициализации USB (dmesg | grep usb):

...
[ 9636.196045] usb 7-2: new full-speed USB device number 2 using uhci_hcd
[ 9636.379053] usb 7-2: New USB device found, idVendor=072f, idProduct=2200
[ 9636.379057] usb 7-2: New USB device strings: Mfr=1, Product=2, SerialNumber=0
[ 9636.379059] usb 7-2: Product: ACR122U PICC Interface
[ 9636.379061] usb 7-2: Manufacturer: ACS
[ 9636.793182] usbcore: registered new interface driver pn533
...

Картридер неправильно опознается ядром как устройство pn533 (usbcore: registered new interface driver pn533). Как пишут на форуме, в ядре версии  (>= 3.1) появилась своя подсистема NFC с своими драйверами, которые конфликтуют с драйверами CCID самого разработчика pscslite
Ludovic Rousseau. Решение проблемы состоит в том, чтобы выгрузить и отменить загрузку драйвера устройства pn533 (можно ещё залезть в сборку Device Tree ядра и отключить драйвер там).

Формируем конфигурационный файл, запрещающий загрузку драйвера pn533:

sudo nano /etc/modprobe.d/blacklist-libnfc.conf

Добавляем в него:

blacklist pn533

После перезагрузки системы на BBB вызов команды sudo /usr/sbin/pcscd -fd выводит следующее:

00000000 debuglog.c:269:DebugLogSetLevel() debug level=debug
00000097 configfile.l:254:DBGetReaderListDir() Parsing conf directory: /etc/reader.conf.d
00000023 configfile.l:307:DBGetReaderList() Parsing conf file: /etc/reader.conf.d/libccidtwin
00000039 configfile.l:266:DBGetReaderListDir() Skipping non regular file: .
00000012 configfile.l:266:DBGetReaderListDir() Skipping non regular file: ..
00000012 pcscdaemon.c:545:main() pcsc-lite 1.8.10 daemon ready.
00001284 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x1D6B, PID: 0x0001, path: /dev/bus/usb/003/001
00000100 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x1D6B, PID: 0x0001, path: /dev/bus/usb/004/001
00000093 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x1D6B, PID: 0x0001, path: /dev/bus/usb/005/001
00000092 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x1D6B, PID: 0x0002, path: /dev/bus/usb/001/001
00000090 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x1D6B, PID: 0x0001, path: /dev/bus/usb/006/001
00000089 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x1D6B, PID: 0x0001, path: /dev/bus/usb/007/001
00000069 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x1D6B, PID: 0x0001, path: /dev/bus/usb/007/001
00000073 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x072F, PID: 0x2200, path: /dev/bus/usb/007/002
00000026 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x072F, PID: 0x2200, path: /dev/bus/usb/007/002
00000012 hotplug_libudev.c:321:HPAddDevice() Adding USB device: ACS ACR122U
00000023 readerfactory.c:989:RFInitializeReader() Attempting startup of ACS ACR122U 00 00 using /usr/lib/pcsc/drivers/ifd-acsccid.bundle/Contents/Linux/libacsccid.so
00000129 readerfactory.c:874:RFBindFunctions() Loading IFD Handler 3.0
00000027 ifdhandler.c:2328:init_driver() Driver version: 1.0.5
00000150 ifdhandler.c:2341:init_driver() LogLevel: 0x0003
00000130 ifdhandler.c:2361:init_driver() DriverOptions: 0x00C0
00000128 ifdhandler.c:2388:init_driver() ACR38CardVoltage: 0
00000128 ifdhandler.c:2395:init_driver() ACR38CardType: 0
00000012 ifdhandler.c:94:IFDHCreateChannelByName() lun: 0, device: usb:072f/2200:libudev:0:/dev/bus/usb/007/002
00178155 ccid_usb.c:375:OpenUSBByName() Manufacturer: Advanced Card Systems Ltd.
00000160 ccid_usb.c:385:OpenUSBByName() ProductString: ACS CCID driver
00000122 ccid_usb.c:391:OpenUSBByName() Copyright: This driver is protected by terms of the GNU Lesser General Public License version 2.1, or (at your option) any later version.
00007615 ccid_usb.c:650:OpenUSBByName() Found Vendor/Product: 072F/2200 (ACS ACR122U)
00000015 ccid_usb.c:652:OpenUSBByName() Using USB bus/device: 007/002
00002182 ccid_usb.c:1368:get_data_rates() IFD does not support GET_DATA_RATES request: Success
01013513 ifdhandler.c:220:IFDHCreateChannelByName() dwFeatures: 0x00020040
00000019 ifdhandler.c:221:IFDHCreateChannelByName() wLcdLayout: 0x0000
00000005 ifdhandler.c:222:IFDHCreateChannelByName() bPINSupport: 0x00
00000005 ifdhandler.c:223:IFDHCreateChannelByName() dwMaxCCIDMessageLength: 271
00000004 ifdhandler.c:224:IFDHCreateChannelByName() dwMaxIFSD: 256
00000005 ifdhandler.c:225:IFDHCreateChannelByName() dwDefaultClock: 4000
00000005 ifdhandler.c:226:IFDHCreateChannelByName() dwMaxDataRate: 250000
00000004 ifdhandler.c:227:IFDHCreateChannelByName() bMaxSlotIndex: 0
00000005 ifdhandler.c:228:IFDHCreateChannelByName() bCurrentSlotIndex: 0
00000017 ifdhandler.c:229:IFDHCreateChannelByName() bInterfaceProtocol: 0x00
00000005 ifdhandler.c:230:IFDHCreateChannelByName() bNumEndpoints: 3
00000004 ifdhandler.c:231:IFDHCreateChannelByName() bVoltageSupport: 0x07
00000009 ifdhandler.c:536:IFDHGetCapabilities() tag: 0xFB3, usb:072f/2200:libudev:0:/dev/bus/usb/007/002 (lun: 0)
00000006 readerfactory.c:327:RFAddReader() Using the pcscd polling thread
00015973 ifdhandler.c:536:IFDHGetCapabilities() tag: 0xFAE, usb:072f/2200:libudev:0:/dev/bus/usb/007/002 (lun: 0)
00000018 ifdhandler.c:631:IFDHGetCapabilities() Reader supports 1 slot(s)
00000195 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x1D6B, PID: 0x0001, path: /dev/bus/usb/008/001
00000108 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x1D6B, PID: 0x0001, path: /dev/bus/usb/008/001
00000111 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x04D9, PID: 0x1702, path: /dev/bus/usb/008/002
00000106 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x04D9, PID: 0x1702, path: /dev/bus/usb/008/002
00000140 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x1D6B, PID: 0x0002, path: /dev/bus/usb/002/001
00000103 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x1D6B, PID: 0x0002, path: /dev/bus/usb/002/001
00000106 hotplug_libudev.c:269:get_driver() Looking for a driver for VID: 0x058F, PID: 0x6362, path: /dev/bus/usb/002/002
00000047 readerfactory.c:1330:RFWaitForReaderInit() Waiting init for reader: ACS ACR122U 00 00
00010073 readerfactory.c:1330:RFWaitForReaderInit() Waiting init for reader: ACS ACR122U 00 00
00010079 readerfactory.c:1330:RFWaitForReaderInit() Waiting init for reader: ACS ACR122U 00 00
00010078 readerfactory.c:1330:RFWaitForReaderInit() Waiting init for reader: ACS ACR122U 00 00
00002745 ifdhandler.c:1355:IFDHPowerICC() action: PowerUp, usb:072f/2200:libudev:0:/dev/bus/usb/007/002 (lun: 0)
00001991 eventhandler.c:266:EHStatusHandlerThread() powerState: POWER_STATE_POWERED
00000014 Card ATR: 3B 8F 80 01 80 4F 0C A0 00 00 03 06 03 00 01 00 00 00 00 6A 
00429759 ifdhandler.c:1355:IFDHPowerICC() action: PowerDown, usb:072f/2200:libudev:0:/dev/bus/usb/007/002 (lun: 0)
00001995 eventhandler.c:455:EHStatusHandlerThread() powerState: POWER_STATE_UNPOWERED
00011372 ccid_usb.c:1485:InterruptRead() Reader: 007/002
00000018 ccid_usb.c:1503:InterruptRead() Slot 0: 0x00

Для работы с библиотекой libpcsclite потребуются хедеры (pcsclite.h и другие). Необходимые заголовочные файлы включены в пакет libpcsclite-dev. Установив его (sudo apt-get install libpcsclite-dev), мы получим файлы pcsclite.h, winscard.h, wintypes.h в папке /usr/include/PCSC.

Для настройки проекта Qt (pro-файла) для работы с библиотекой libpcsclite необходимо указать подключение библиотеки, добавить указанные пути к библиотеке и хедерам:

unix:{
  INCLUDEPATH += /usr/include/PCSC
  LIBS += -L"/lib/x86_64-linux-gnu/" -lpcsclite
}