インストール - Bluetoothドライバ

提供: MochiuWiki : SUSE, EC, PCB

2026年5月24日 (日) 05:53時点におけるWiki (トーク | 投稿記録)による版
(差分) ← 古い版 | 最新版 (差分) | 新しい版 → (差分)

概要

LinuxでBluetoothデバイスを制御する場合、Realtek社等のBluetoothドライバを手動でのインストールが必要な可能性がある。

ここでは、Bluetoothデバイスの各チップにおいて、各チップベンダの専用ドライバのインストール手順を記載する。


BlueZのインストール

パッケージ管理システムからインストール

BlueZをインストールする。

sudo zypper install bluez bluez-util


BlueZサービスを開始する。

sudo systemctl start bluetooth


BlueZサービスを自動起動に設定する。

sudo systemctl enable bluetooth


ソースコードからインストール

BlueZのビルドに必要なライブラリをインストールする。

sudo zypper install dbus-1-devel glib2-devel libudev-devel libical-devel rst2html5


BlueZの公式Webサイトにアクセスして、BlueZのソースコードをダウンロードする。
ダウンロードしたファイルを解凍する。

tar xf bluez-<バージョン>.tar.xz
cd bluez-<バージョン>


BlueZをビルドおよびインストールする。

mkdir build && cd build

../configure --prefix=<BlueZのインストールディレクトリ> \
             --mandir=/<BlueZのインストールディレクトリ>/share/man \
             --sysconfdir=/<BlueZのインストールディレクトリ>/etc \
             --localstatedir=/<BlueZのインストールディレクトリ>/var \
             --libexecdir=/<BlueZのインストールディレクトリ>/lib
make -j $(nproc)
make install


~/.profileファイル等に、環境変数の設定を記述する。

vi ~/.profile


 # ~/.profileファイル
 
 export PATH="/<BlueZのインストールディレクトリ>/bin:$PATH"
 export LD_LIBRARY_PATH="/<BlueZのインストールディレクトリ>/lib64:/<BlueZのインストールディレクトリ>/lib:$LD_LIBRARY_PATH"



RTL8761BUドライバ

RTL8761BUドライバのインストール

Realtek社のRTL8761B(RTL8761BUV)チップを搭載したUSBドングルは、Linuxカーネル 2.6.32以降に対応している。

競合するBluetoothモジュールをブラックリストに入れるため、/etc/modprobe.dディレクトリに.confファイル作成して、以下の内容を記述する。
以下の例では、/etc/modprobe.d/50-bluetooth-blacklist.confファイルを作成している。

※注意
/etc/modprobe.d/50-bluetooth-blacklist.confファイルの作成において、環境によっては不要の可能性があることに注意する。

sudo vi /etc/modprobe.d/50-bluetooth-blacklist.conf


# /etc/modprobe.d/50-bluetooth-blacklist.confファイル

blacklist btrtl
blacklist btusb
blacklist btintel
blacklist btbcm


BluetoothのUSBドングルをPCに接続して、デバイスが認識されているかどうかを確認する。

sudo hwinfo --bluetooth


RTL8761BUドライバのソースコードをダウンロードする。

git clone https://github.com/Elif-dot/RTL8761BU.git
# または
git clone https://github.com/mohclips/realtek_bt_kernel_driver.git
# または
wget https://mpow.s3-us-west-1.amazonaws.com/mpow_BH519A_driver+for+Linux.7z
# または
https://drive.google.com/file/d/1FkzIOuNAc1HErqbhkmbkwEisviAQP2IC/view にアクセスしてダウンロードする。


ダウンロードしたファイルのディレクトリに移して、RTL8761BUドライバをビルドおよびインストールする。

cd <RTL8761BUドライバのソースディレクトリ>
sudo make install INTERFACE=usb

sudo cp rtkbt-firmware/lib/firmware/rtl8761bu_fw  rtkbt-firmware/lib/firmware/rtl8761bu_config \
        /lib/firmware/
# または
sudo cp 8761BU/rtl8761bu_fw  8761BU/rtl8761bu_config  /lib/firmware/


もし、インストールに失敗する場合は、Linuxカーネルを修復する。

cd /usr/src/linux

sudo make -j $(nproc) oldconfig
sudo make -j $(nproc) prepare


RTL8761BUドライバのソースディレクトリは、任意のディレクトリに保存する。

以下に示すコマンドは不要の可能性が高いが、記載しておく。

sudo modprobe rtk_btusb  # 不要の可能性あり


PCを再起動する。

※注意
Linuxカーネルをアップデートした場合は自動的にRTL8761BUドライバが削除されるため、再度、RTL8761BUドライバをインストールする必要がある。
もし、既にRTL8761BUモジュールのバックアップが存在する場合、
rtk_btusbモジュール、rtl8761bu_fwファイル、rtl8761bu_configファイルを以下のディレクトリにコピーして、モジュール群をデプロイすることもできる。

# RTL8761BUモジュールのコピー
sudo cp rtk_btusb.ko /lib/modules/$(uname -r)/kernel/drivers/bluetooth/
sudo cp rtl8761bu_fw  rtl8761bu_config  /lib/firmware/

# モジュール群のデプロイ
sudo depmod -a $(uname -r)


Bluetoothドングルと機器が正常に接続されている場合、ジャーナルを確認すると、以下に示すようなメッセージが出力される。

sudo journalctl --unit=bluetooth -f

# 出力例
# Xの箇所には、任意の数字またはアルファベットが入ることに注意する
<タイムスタンプ> <ホスト名> bluetoothd[<プロセス番号>]: Endpoint registered: sender=:X.XX path=/MediaEndpoint/A2DPSource/sbc
<タイムスタンプ> <ホスト名> bluetoothd[<プロセス番号>]: Endpoint registered: sender=:X.XX path=/MediaEndpoint/A2DPSink/sbc_xq
<タイムスタンプ> <ホスト名> bluetoothd[<プロセス番号>]: Endpoint registered: sender=:X.XX path=/MediaEndpoint/A2DPSource/sbc_xq
<タイムスタンプ> <ホスト名> bluetoothd[<プロセス番号>]: Endpoint registered: sender=:X.XX path=/MediaEndpoint/A2DPSource/faststream
<タイムスタンプ> <ホスト名> bluetoothd[<プロセス番号>]: Endpoint registered: sender=:X.XX path=/MediaEndpoint/A2DPSource/faststream_duplex
<タイムスタンプ> <ホスト名> bluetoothd[<プロセス番号>]: Endpoint registered: sender=:X.XX path=/MediaEndpoint/A2DPSink/opus_05
<タイムスタンプ> <ホスト名> bluetoothd[<プロセス番号>]: Endpoint registered: sender=:X.XX path=/MediaEndpoint/A2DPSource/opus_05
<タイムスタンプ> <ホスト名> bluetoothd[<プロセス番号>]: Endpoint registered: sender=:X.XX path=/MediaEndpoint/A2DPSink/opus_05_duplex
<タイムスタンプ> <ホスト名> bluetoothd[<プロセス番号>]: Endpoint registered: sender=:X.XX path=/MediaEndpoint/A2DPSource/opus_05_duplex
<タイムスタンプ> <ホスト名> bluetoothd[<プロセス番号>]: /org/bluez/hciX/dev_XX_XX_XX_XX_XX_XX/sepX/fdX: fd(XX) ready


RTL8761BUドライバのアンインストール

RTL8761BUドライバをアンインストールする。

cd /<RTL8761BUドライバのソースディレクトリ>/rtkbt-firmware/lib/firmware
sudo make uninstall


標準のBluetoothドライバを有効にする。

sudo rm /etc/modprobe.d/50-bluetooth-blacklist.conf


RTL8761BUドライバのファームウェアファイルおよびその設定ファイルを削除する。

sudo rm /lib/firmware/rtl8761bu_fw /lib/firmware/rtl8761bu_config



Realtek RTL8761BUモジュールの署名 (セキュアブートが有効の場合)

セキュアブートが有効の場合、Realtek RTL8761BUモジュールは署名済みの状態で読み込む必要がある。
MOK (Machine Owner Key) の登録は初回のみ必要であり、同じ鍵を使い続ける限り、Linuxカーネルの更新ごとにMOKを再登録する必要はない。

また、モジュールの圧縮は署名後に行う必要があることに注意する。

初回のみ必要なMOKの登録

まず、署名に必要な設定ファイルを作成する。

sudo mkdir -p /root/.MOK/RTL8761BU && cd /root/.MOK/RTL8761BU


sudo vi RTL8761BU.config


 # /root/.MOK/RTL8761BU/RTL8761BU.configファイル
 
 [ req ]
 default_bits = 4096
 distinguished_name = req_distinguished_name
 prompt = no
 string_mask = utf8only
 x509_extensions = myexts
 
 [ req_distinguished_name ]
 O = SUSE Linux Products GmbH (User Add RTL8761BU)
 CN = SUSE Linux Enterprise Secure Boot (User Add RTL8761BU)
 emailAddress = suse@localhost
 
 [ myexts ]
 basicConstraints=critical,CA:FALSE
 keyUsage=digitalSignature
 subjectKeyIdentifier=hash
 authorityKeyIdentifier=keyid


キーペアを作成する。

openssl req -x509 -new -nodes -utf8 -sha256 -days 36500 -batch -config ./RTL8761BU.config \
            -outform DER -out ./RTL8761BU.der -keyout ./RTL8761BU.priv \
            -addext "extendedKeyUsage=codeSigning"


MOKに公開鍵をインポートする。
--root-pw オプションを付加した場合、MokManagerでrootパスワードによる確認を行う。

sudo mokutil --import ./RTL8761BU.der --root-pw


PCを再起動して、MokManagerで登録を完了する。
この操作はファームウェア側の確認処理であり、自動化は困難である。

sudo systemctl reboot
MOKが正しく登録されているかどうかを確認する。

cd /root/.MOK/RTL8761BU
sudo mokutil --test-key ./RTL8761BU.der


正常に登録されている場合は、"RTL8761BU.der is already enrolled"のような内容が表示される。

手動で署名する場合

DKMSを使用せず、現在利用中のLinuxカーネル向けモジュールを手動で署名する手順を以下に示す。
まず、Realtek RTL8761BUモジュール(rtk_btusb.ko)を署名する。

sudo /lib/modules/$(uname -r)/build/scripts/sign-file sha256 \
     /root/.MOK/RTL8761BU/RTL8761BU.priv \
     /root/.MOK/RTL8761BU/RTL8761BU.der  \
     /lib/modules/$(uname -r)/kernel/drivers/bluetooth/rtk_btusb.ko


次に、Realtek RTL8761BUモジュールをZstandard形式に圧縮する。
この工程は、署名後かつdepmodmodprobeの直前に行う。

sudo zstd --rm /lib/modules/$(uname -r)/kernel/drivers/bluetooth/rtk_btusb.ko


最後に、モジュール依存リストを更新して、Realtek RTL8761BUモジュールを読み込む。

sudo depmod -a $(uname -r)
sudo modprobe -v rtk_btusb


Realtek RTL8761BUモジュールが正常に読み込まれているかどうかを確認する。

lsmod | grep rtk_btusb


作成したキーは信頼されるため、キーを適切に保存する必要がある。
このキーで署名されたものはシステムから信頼されるため、セキュリティリスクとなる可能性があることに注意する。

MOKの削除

登録済みのMOKを削除する場合、以下のコマンドを実行してから再起動する。

cd /root/.MOK/RTL8761BU
sudo mokutil --delete ./RTL8761BU.der --root-pw
sudo systemctl reboot



Realtek RTL8761BUモジュールのDKMSによる自動再ビルドおよび自動署名

初回のみMOKを登録しておけば、その後はDKMSでモジュールの再ビルドおよび再署名を自動化できる。

RTL8761BUドライバをDKMSへ登録する

RTL8761BUドライバのソースコードをDKMS管理用のディレクトリに配置する。

以下の例では、バージョンを 1.0 としている。

sudo mkdir -p /usr/src/rtl8761bu-1.0
sudo cp -a <RTL8761BUドライバのソースディレクトリ>/* /usr/src/rtl8761bu-1.0/


/usr/src/rtl8761bu-1.0/dkms.conf ファイルを作成する。

※注意
DKMSは自動的に -j $(nproc) を付加するため記述する必要はない。

sudo vi /usr/src/rtl8761bu-1.0/dkms.conf


 # /usr/src/rtl8761bu-1.0/dkms.confファイル
 
 PACKAGE_NAME="rtl8761bu"
 PACKAGE_VERSION="1.0"
 BUILT_MODULE_NAME[0]="rtk_btusb"
 DEST_MODULE_LOCATION[0]="/kernel/drivers/bluetooth"
 AUTOINSTALL="yes"
 MAKE[0]="make INTERFACE=usb"
 CLEAN="make clean"


DKMSが署名に使用する鍵を設定する。

sudo vi /etc/dkms/framework.conf


# /etc/dkms/framework.confファイル

mok_signing_key="/root/.MOK/RTL8761BU/RTL8761BU.priv"
mok_certificate="/root/.MOK/RTL8761BU/RTL8761BU.der"


上記の設定により、DKMSは新しいLinuxカーネル向けにモジュールを再ビルドする時、同じ鍵を利用できる。
秘密鍵はrootのみが読み込めるように厳格に管理する。

DKMSへモジュールを登録して、ビルドおよびインストールする。

sudo dkms add -m rtl8761bu -v 1.0
sudo dkms build -m rtl8761bu -v 1.0
sudo dkms install -m rtl8761bu -v 1.0


DKMSのバージョンまたはディストリビューションによっては、自動署名が期待通りに行われない場合がある。
その場合は、以下のように手動で署名する。

sudo /lib/modules/$(uname -r)/build/scripts/sign-file sha256 \
     /root/.MOK/RTL8761BU/RTL8761BU.priv \
     /root/.MOK/RTL8761BU/RTL8761BU.der  \
     /lib/modules/$(uname -r)/updates/dkms/rtk_btusb.ko


次に、Realtek RTL8761BUモジュールをZstandard形式に圧縮する。
この工程は、署名後かつ depmodmodprobe の直前に行う。

sudo zstd --rm /lib/modules/$(uname -r)/updates/dkms/rtk_btusb.ko


最後に、モジュール依存リストを更新して、Realtek RTL8761BUモジュールを読み込む。

sudo depmod -a $(uname -r)
sudo modprobe -v rtk_btusb


Realtek RTL8761BUモジュールが正常に読み込まれているかどうかを確認する。

lsmod | grep rtk_btusb


共通鍵で複数モジュールを署名する場合

複数のDKMSモジュールを同じMOKで署名する場合、/etc/dkms/framework.conf に共通の鍵を記述する。
この方法では、MOKの登録は1回でよい。

設定例を以下に示す。

sudo vi /etc/dkms/framework.conf


 # /etc/dkms/framework.confファイル
 
 mok_signing_key="/root/.MOK/common/MOK.priv"
 mok_certificate="/root/.MOK/common/MOK.der"


上記の設定により、DKMSで管理される複数のモジュールは同じ鍵で署名される。
例えば、Bluetoothドライバの rtk_btusb モジュールと、Wi-Fiドライバの 8821au モジュールに対して同じ鍵を利用できる。

この方法は管理が容易であり、通常はこちらを推奨する。

モジュールごとに別鍵を使う場合

モジュールごとに別々の秘密鍵および公開鍵を使用する場合、/etc/dkms/framework.conf だけでは切り分けが難しい。

そのため、各モジュールの dkms.confPOST_BUILD を利用して、個別に sign-file コマンドを呼び出す。

例1: RTL8761BU向けのdkms.conf
sudo vi /usr/src/rtl8761bu-1.0/dkms.conf


 # /usr/src/rtl8761bu-1.0/dkms.confファイル
 
 PACKAGE_NAME="rtl8761bu"
 PACKAGE_VERSION="1.0"
 BUILT_MODULE_NAME[0]="rtk_btusb"
 DEST_MODULE_LOCATION[0]="/kernel/drivers/bluetooth"
 AUTOINSTALL="yes"
 MAKE[0]="make INTERFACE=usb"
 CLEAN="make clean"
 POST_BUILD="./sign-module.sh"


例2: RTL8761BU向けの署名スクリプト
sudo vi /usr/src/rtl8761bu-1.0/sign-module.sh


 # /usr/src/rtl8761bu-1.0/sign-module.shファイル
 
 #!/usr/bin/emv sh
 set -eu
 
 MODULE="/var/lib/dkms/rtl8761bu/1.0/${kernelver}/${arch}/module/rtk_btusb.ko"
 
 /lib/modules/${kernelver}/build/scripts/sign-file sha256 \
 /root/.MOK/rtl8761bu/RTL8761BU.priv \
 /root/.MOK/rtl8761bu/RTL8761BU.der  \
 "${MODULE}"


実行権限を付与する。

sudo chmod a+x /usr/src/rtl8761bu-1.0/sign-module.sh


例3: POST_BUILDで署名とZstandard圧縮をまとめて行う場合

POST_BUILD で署名とZstandard形式への圧縮をまとめて行うこともできる。

この場合、署名スクリプト内で sign-file コマンドを実行した後、zstd コマンドを実行する。

dkms.conf の例を以下に示す。

sudo vi /usr/src/rtl8761bu-1.0/dkms.conf


 # /usr/src/rtl8761bu-1.0/dkms.confファイル
 
 PACKAGE_NAME="rtl8761bu"
 PACKAGE_VERSION="1.0"
 BUILT_MODULE_NAME[0]="rtk_btusb"
 DEST_MODULE_LOCATION[0]="/kernel/drivers/bluetooth"
 AUTOINSTALL="yes"
 
 CLEAN="make clean"
 POST_BUILD="./sign-and-compress-module.sh"


次に、署名および圧縮用のスクリプトを作成する。

sudo vi /usr/src/rtl8761bu-1.0/sign-and-compress-module.sh


 # /usr/src/rtl8761bu-1.0/sign-and-compress-module.shファイル
 
 #!/usr/bin/env sh
 set -eu
 
 MODULE="/var/lib/dkms/rtl8761bu/1.0/${kernelver}/${arch}/module/rtk_btusb.ko"
 
 /lib/modules/${kernelver}/build/scripts/sign-file sha256 \
 /root/.MOK/rtl8761bu/RTL8761BU.priv \
 /root/.MOK/rtl8761bu/RTL8761BU.der \
 "${MODULE}"
 
 zstd --rm --ultra -22 -T0 "${MODULE}"


実行権限を付与する。

sudo chmod a+x /usr/src/rtl8761bu-1.0/sign-and-compress-module.sh


この方法では、DKMSのビルド完了後に署名および圧縮が連続して実行される。
その後、必要に応じて depmod および modprobe を実行する。

例4: 別モジュール側の考え方

例えば、Wi-Fiドライバ用に別鍵を使用する場合は、同様にそのモジュール専用の sign-module.sh を作成する。
その時、秘密鍵と公開鍵のパスのみを変更する。

# 例:

/root/.MOK/rtl8821au/RTL8821AU.priv
/root/.MOK/rtl8821au/RTL8821AU.der


注意事項
  • POST_BUILD で参照するモジュールパスは、DKMSのバージョンやディストリビューションによって差異が出る可能性がある。
    実際の環境で /var/lib/dkms/ ディレクトリ内の生成先を確認することが望ましい。
  • POST_BUILD でZstandard形式へ圧縮する場合、後続のインストール工程が圧縮済みモジュールを正しく扱うかどうかを事前に確認する。
    環境によっては、POST_INSTALL で最終配置先のモジュールを圧縮する方が安全な場合がある。
  • モジュールを圧縮する場合は、署名後に行う必要がある。
    例えば、Zstandard形式に圧縮する場合は以下のように実行する。
    sudo zstd --rm /lib/modules/$(uname -r)/updates/dkms/rtk_btusb.ko
  • 共通鍵方式の方が管理が簡単であり、通常はそちらを優先する。
  • モジュールごとに別鍵を使う方式は、用途ごとに信頼範囲を分離したい場合に有効である。


Linuxカーネルを更新した場合の扱い

Linuxカーネルを更新した場合、MOKの再登録は不要である。
同じ秘密鍵および公開鍵を使い続ける限り、必要なのは新しいLinuxカーネル向けに再ビルドされたモジュールへの再署名のみである。

DKMSを設定済みであれば、通常はLinuxカーネルの更新時に自動で再ビルドおよび再インストールが行われる。

必要に応じて、署名、Zstandard圧縮、depmodmodprobe を順に実行する。


リモートウェイクアップ機能

リモートウェイクアップ機能とは、ペアリングした端末からデータを受信をした場合、自動的にスリープ / サスペンド状態から復帰する機能である。

lsusbコマンドを実行して、Bluetoothデバイスのベンダ名と製品IDを確認する。
以下の例では、ベンダ名(idVendor)は0bda、製品ID(idProduct)は1724である。

lsusb

# 出力例
Bus 003 Device 001: ID 1d6b:0002 Linux Foundation 2.0 root hub
Bus 002 Device 001: ID 1d6b:0003 Linux Foundation 3.0 root hub
Bus 001 Device 003: ID 062a:4102 MosArt Semiconductor Corp. Wireless Mouse
Bus 001 Device 002: ID 0bda:1724 Realtek Semiconductor Corp.
Bus 001 Device 001: ID 1d6b:0002 Linux Foundation 2.0 root hub


/etc/udev/rules.dディレクトリに、新しいルールファイル(ファイル名は任意)を作成して、以下の内容を記述する。
echo enabledおよびecho disabledを記述することにより、リモートウェイクアップ機能の有効 / 無効を設定する。

sudo vi /etc/udev/rules.d/90-BluetoothWakeUp.rules


# /etc/udev/rules.d/90-BluetoothWakeUp.rulesファイル

SUBSYSTEM=="usb", ATTRS{idVendor}=="<ベンダ名>", ATTRS{idProduct}=="<製品ID>" RUN+="/bin/sh -c 'echo enabled > /sys$env{DEVPATH}/../power/wakeup'"


BluetoothデバイスのUSBドングルをPCに再接続して、リモートウェイクアップ機能が有効になっているかどうかを確認する。


エラー

送受信エラー

Bluetoothを通してファイルを送受信する場合、以下に示すようなエラーが出力される場合がある。

Failed to start org.bluez.obex service: Unit dbus-org.bluez.obex.service not found.


まず、Bluetooth向けObexライブラリをインストールする。

sudo zypper install bluez-obexd


次に、Bluetooth向けObexを有効にする。

sudo systemctl --global enable obex

# 出力
Created symlink /etc/systemd/user/dbus-org.bluez.obex.service → /usr/lib/systemd/user/obex.service.


最後に、Bluetooth向けObexを開始する。

systemctl --user start obex


もし、上記の手順を実行してもデータの送受信が出来ない場合は、ジャーナルを確認する。

sudo journalctl --unit=bluetooth -f