Сопряжение Bluetooth с использованием фиксированного PIN-кода на bluez 5

Я пытаюсь подключить 2 или более плат Raspberry Pi 3 через Bluetooth. Я ищу варианты установки безопасности при сопряжении. Я использую Raspian-stretch (последний доступный). Версия Bluez, доступная на RPI-3, — 5.23 (как видно из команды bluetoothd -v).

Я использую безголовую версию. Я хочу, чтобы сопряжение было защищено (имеется в виду, что должна быть какая-то аутентификация, которую я могу установить, например, PIN-код (4 цифры) или пароль (6 цифр)) без входа пользователя в систему. Поэтому, если мне нужно подключить свой телефон к RPI, мне не нужно входить в RPI, чтобы вводить PIN-код/пароль. Затем я хотел бы настроить сеть Bluetooth PAN, чтобы я мог общаться между устройствами, подключенными к сети PAN.

Я хочу соединить устройства с помощью PIN-кода, который доступен в файле в системе или где-то еще, куда я могу его указать. Скажем, например, файл pin.txt в каталоге /temp/ или запустив агент для установки PIN-кода. Я читал из других сообщений, что bluez5.x избавился от bluetooth-агента, который использовался в более ранней версии bluez, чтобы делать то, что я мог сделать.

Агенты в bluetoothctl, такие как DisplayOnly, KeyboardDisplay, NoInputNoOutput, DisplayYesNo, KeyboardOnly, либо устанавливают динамический ключ доступа, который необходимо вводить вручную, либо подтверждают ключ доступа, либо просто позволяют любому устройству соединяться и подключаться без какой-либо аутентификации в случае NoInputNoOutput.

Вот ссылка, которую я нашел на этом форуме, в которой говорится, что агент больше не доступен: https://www.raspberrypi.org/forums/viewtopic.php?t=133961 Я также ссылаюсь на некоторые примеры, которые показывают сопряжение устройств, но не относятся к тому, что я ищу.

На справочной странице тоже нет информации. https://manpages.debian.org/stretch/bluez/bluetoothctl.1.en.html

Вот что я нашел о командах, но все еще не то, что я ищу. https://wiki.archlinux.org/index.php/Bluetooth

Я также разместил этот форум Raspberry Pi. Вот ссылка: https://www.raspberrypi.org/forums/viewtopic.php?f=29&t=195090

Любая помощь или предложение обойти это или ссылки на документы, на которые я мог бы ссылаться, приветствуются.

Заранее спасибо.


person sachin    schedule 10.10.2017    source источник


Ответы (3)


После нескольких дней возни с BlueZ 5 это то, что у меня есть. Используя BlueZ 5.50 и Raspbian Stretch (Pi Zero W):

Запустите bluetoothd с --compat:

добавить к строке ExecStart в /etc/systemd/system/dbus-org.bluez.service

or

в rc.local: sudo bluetoothd --compat &


Следующие шаги обрабатываются кодом, размещенным ниже, но для уточнения необходимо установить для hciconfig значение:

sudo hciconfig hci0 sspmode 0

Примечание № 1. С помощью «sspmode 1» при сопряжении с Android вы получите запрос на ввод PIN-кода, но после этого Pi автоматически сгенерирует 6-значный пароль, и сопряжение завершится ошибкой.

Примечание № 2: hciconfig hci0 нельзя установить с помощью авторизации или шифрования, они фактически зарегистрируются агент DisplayOnly (мы создадим агент на следующем шаге) как KeyboardDisplay (sudo btmon для проверки), и при сопряжении не будет использоваться предопределенный PIN-код. Не уверен, есть ли причина, по которой DisplayOnly не может использовать аутентификацию, шифрование (возможно, это связано с установкой режима безопасности 3).

После этого мы будем использовать bluetoothctl:

pi@raspberrypi:~ $ bluetoothctl
Agent registered
[bluetooth]# agent off
Agent unregistered
[bluetooth]# agent DisplayOnly
Agent registered
[bluetooth]# default-agent
Default agent request successful
[bluetooth]# discoverable on
Changing discoverable on succeeded
[CHG] Controller 11:22:33:44:55:66 Discoverable: yes
[bluetooth]# pairable on
Changing pairable on succeeded
[CHG] Controller 11:22:33:44:55:66 Pairable: yes

// Initiate pairing on remote device //

[NEW] Device AA:BB:CC:DD:EE:FF Android_phone

// Enter any PIN on Device AA:BB:CC:DD:EE:FF

Request PIN code

// retype your PIN below (on Pi)
[agent] Enter PIN code: <your PIN> 
[CHG] Device AA:BB:CC:DD:EE:FF Class: 0x005a020c
...
[CHG] Device AA:BB:CC:DD:EE:FF Paired: yes
[bluetooth]# quit

Примечание № 3. Регистрация агента с использованием pexpect (просто примечание, если вы попытаетесь запустить код, размещенный ниже) с BlueZ 5.43 (версия по умолчанию в Stretch) не удалась.


Ниже приведен код Python 2.7, который устанавливает sspmode и обрабатывает сопряжение с предварительно сгенерированным PIN-кодом:

#!/usr/bin/env python
# -*- coding: utf-8 -*-
from __future__ import print_function   # import print from python3: end=""
import time   
import re
import pexpect    # sudo apt-get install python-pexpect
import subprocess
import random
# !!! make sure bluetoothd runs in --compat mode before executing this script !!!
def pair_with_pin(start_time, pin, time_limit=60):  # int(time.time()), pin - \d{4}, time_limit - approximate pairing window time in seconds, it might take up to 2x (nested timeout conditions)
    "exectutes pairing with entered PIN on bluetooth adapter side"
    pairing_status = False
    try:
        subprocess.call(['sudo','hciconfig','hci0','sspmode', '0'])
        
        # bluetoothctl 
        child = pexpect.spawn('bluetoothctl')
        child.expect("#")
        child.sendline('agent off') # might be unnecessary
        child.expect("unregistered")
        
        child.sendline('agent DisplayOnly')
        child.expect("Agent registered")
        child.sendline('pairable on')
        child.expect("pairable on succeeded")
        child.sendline('discoverable on')
        child.expect("discoverable on succeeded")
        child.sendline('default-agent')
        print ('Please input PIN: ' + pin)              
        
        # waiting for Phone to send a pairing request... 
        child.expect('Enter PIN code:', timeout = time_limit )   # timeout <= PAIRING_TIME_LIMIT to keep some kind of logic
        while int(time.time()) < start_time + time_limit:   # allow multiple pairing attempts during pairing window            
            child.sendline(pin)
            i = child.expect(['Paired: yes', 'Enter PIN code:'], timeout = time_limit)
            if i == 0: # found 'Paired: yes' == successful pairing
                trust_mac = 'trust ' + re.search(r'(?:[0-9a-fA-F]:?){12}.+$', child.before).group(0)    # extract MAC from last line, one with 'Paired: Yes'
                child.sendline(trust_mac)   # optionally add device to trusted
                child.expect('trust succeeded', timeout = 10)                
                pairing_status = True
                break
            #else: # i == 1
                # print('wrong PIN, retrying if time will allow') 
    except pexpect.EOF:
        print ('!!!!!!!! EOF')
    except pexpect.TIMEOUT:
        print ('!!!!!!!! TIMEOUT')
        
    # hide Pi's bluetooth for security reasons
    child.sendline('pairable off')
    child.expect("pairable off succeeded")
    child.sendline('discoverable off')
    child.expect("discoverable off succeeded")    
    child.close()
    
    return pairing_status

#main program body
PAIRING_TIME_LIMIT = 60
BT_PIN = random.randint(1000,10000)    # generate random 4-digit PIN 1000..9999

status = pair_with_pin(int(time.time()), str(BT_PIN), PAIRING_TIME_LIMIT)
if status == True:
    print('Pairing successful')

Последнее примечание. После успешного сопряжения возможно можно включить шифрование, попробуйте:

hciconfig hci0 шифрование

or

hcitool enc $BDADD

person Fantomas    schedule 12.02.2019

Я смог заставить это работать с тестовыми сценариями.

Для всех, кому интересно узнать подробности, пожалуйста, обратитесь к моему сообщению на форуме Raspberry Pi. Ниже приведена ссылка.

https://www.raspberrypi.org/forums/viewtopic.php?f=29&t=195090&p=1221455#p1221455

person sachin    schedule 11.10.2017

Сначала вам нужно настроить sspmode 0 для запроса пин-кода: hciconfig hci0 sspmode 0

И используя приложение bt-agent (вы также можете работать как демон):

bt-agent -c NoInputNoOutput -p /root/bluethooth.cfg

Отредактируйте конфигурацию файла, вы можете указать MAC-адрес и пин-код: например: XX:XX:XX:XX:XX:XX 1234

Или если вы хотите пин ко всем устройствам с одинаковым пин кодом, например 1234, отредактируйте файл так: *1234

Эта работа для меня!

person Julio Matesanz    schedule 04.09.2018