質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.48%
Bluetooth

Bluetoothとは短距離の間でデータを交換するための無線通信規格である。固定・モバイル両方のデバイスから、短波の電波送信を行うことで、高いセキュリティをもつパーソナルエリアネットワーク(PAN)を構築する。

M5Stack

M5Stackは、小型のマイコンモジュールです。拡張モジュールが豊富に用意されており、センサと組み合わせることで測定機能を自由に追加することができます。

Python 3.x

Python 3はPythonプログラミング言語の最新バージョンであり、2008年12月3日にリリースされました。

Raspberry Pi

Raspberry Piは、ラズベリーパイ財団が開発した、名刺サイズのLinuxコンピュータです。 学校で基本的なコンピュータ科学の教育を促進することを意図しています。

Q&A

1回答

1433閲覧

M5stickC→Pi3のBLEにおいて,Failed to execute management command 'pasvend'と出て終了してしまう

soohoo

総合スコア22

Bluetooth

Bluetoothとは短距離の間でデータを交換するための無線通信規格である。固定・モバイル両方のデバイスから、短波の電波送信を行うことで、高いセキュリティをもつパーソナルエリアネットワーク(PAN)を構築する。

M5Stack

M5Stackは、小型のマイコンモジュールです。拡張モジュールが豊富に用意されており、センサと組み合わせることで測定機能を自由に追加することができます。

Python 3.x

Python 3はPythonプログラミング言語の最新バージョンであり、2008年12月3日にリリースされました。

Raspberry Pi

Raspberry Piは、ラズベリーパイ財団が開発した、名刺サイズのLinuxコンピュータです。 学校で基本的なコンピュータ科学の教育を促進することを意図しています。

0グッド

0クリップ

投稿2022/07/31 14:27

編集2022/07/31 14:34

前提

M5stickCに心拍センサを接続し,心拍数とM5の電源電圧をBLEでRaspberry Pi3に送信しています。

下記のソースコードで順調に動いているのですが,ラズパイのUSBポートに有線LANのUSB変換アダプタを接続してから以下のエラーが出て,プログラムが終了するようになりました。

bluepy.btle.BTLEManagementError: Failed to execute management command 'pasvend'

エラーが10分ほど動かすと出てしまい,一度出ると再起動しないと治らない場合もあります。

実現したいこと

bluepy.btle.BTLEManagementErrorの回避
今回のシステムはデモとして動けばいいので,数分ほど安定した動作ができれば目的を達成できます。

発生している問題・エラーメッセージ

Traceback (most recent call last): File "/home/pi/Emulator/ble_test.py", line 50, in <module> scanner.scan(3.0, passive=True) # 3秒間スキャンする(この間他の処理は止まる) File "/usr/local/lib/python3.9/dist-packages/bluepy/btle.py", line 854, in scan self.stop() File "/usr/local/lib/python3.9/dist-packages/bluepy/btle.py", line 803, in stop self._mgmtCmd(self._cmd()+"end") File "/usr/local/lib/python3.9/dist-packages/bluepy/btle.py", line 312, in _mgmtCmd raise BTLEManagementError("Failed to execute management command '%s'" % (cmd), rsp) bluepy.btle.BTLEManagementError: Failed to execute management command 'pasvend'

該当のソースコード

python

1# -*- coding: utf-8 -*- 2# 心拍数、電圧を取得してBLEでアドバタイズ(ブロードキャスト) 3# M5StickCは4秒:アドバタイズ、1秒:Deep Sleep 4# ラズパイ側は常時スキャンし、データーを取得したらprintする 5 6from bluepy.btle import DefaultDelegate, Scanner, BTLEException 7import sys 8import struct 9from datetime import datetime 10import subprocess 11 12class ScanDelegate(DefaultDelegate): 13 def __init__(self): # コンストラクタ 14 DefaultDelegate.__init__(self) 15 self.lastseq = None 16 self.lasttime = datetime.fromtimestamp(0) 17 print("init") 18 19 def handleDiscovery(self, dev, isNewDev, isNewData): 20 if isNewDev or isNewData: # 新しいデバイスまたは新しいデータ 21 for (adtype, desc, value) in dev.getScanData(): # データの数だけデータスキャンを繰り返す 22 # 'ffff' = テスト用companyID 23 # M5stickCからのデータを見つけたら 24 if desc == 'Manufacturer' and value[0:4] == 'ffff': 25 __delta = datetime.now() - self.lasttime # 前回取得時刻からの差分をとる 26 # アドバタイズする間に複数回測定されseqが加算されたものは捨てる(最初に取得された1個のみを使用する) 27 if value[4:6] != self.lastseq and __delta.total_seconds() > 5: 28 self.lastseq = value[4:6] # Seqと時刻を保存 時刻はどこにあるんだ 29 self.lasttime = datetime.now() 30 (bpm, volt) = struct.unpack_from('<hh', bytes.fromhex(value[6:])) 31 print('心拍数 = {0} bpm, 電圧 = {1} V' .format(bpm, volt/100)) 32 if bpm > 80: 33 loss_netem = (bpm - 80) * 2 34 if loss_netem > 70: 35 loss_netem = 70 36 cmd_netem = "sudo tc qdisc change dev eth0 root netem loss " + str(loss_netem) + "%" 37 subprocess.run( 38 cmd_netem, shell=True) 39 print("loss: " + str(loss_netem) + "%") 40 else: 41 subprocess.run(['sudo tc qdisc change dev eth0 root netem loss 0%'], shell=True) 42 43# 有線'eth0'から出ていくパケットにネットワークエミュレーションを追加 44subprocess.run(["sudo tc qdisc add dev eth0 root netem"], shell=True) 45 46scanner = Scanner().withDelegate(ScanDelegate()) 47try: 48 while True: 49 # try: 50 # スキャンする。デバイスを見つけた後の処理はScanDelegateに任せる 51 print("scan") 52 scanner.scan(5.0) # 5秒間スキャンする(この間他の処理は止まる) 53except KeyboardInterrupt as e: 54 print("Aborted!") 55finally: 56 # ネットワークエミュレータの削除 57 # ここで遅延を元に戻してから終了する 58 subprocess.run(["sudo tc qdisc del dev eth0 root"], shell=True)

試したこと

python

1scanner.scan(5.0, passive = True)

パッシブスキャンをTrueにしたのですが,却ってエラーの頻度が増えました。。

また,エラーで強制終了したタイミングでbluetoothctlを開いて確認したところ,

[bluetooth]# scan on Failed to start discovery: org.bluez.Error.InProgress

と出ています。参考にしたページのコードよりもアドバタイズやスキャンの秒数を短くしているので、個人的にはスキャン中に追いスキャンしてしまってる(?)のかなと思ってます。。

補足情報(FW/ツールのバージョンなど)

M5stickCのソースコード(送信部分のみ抜粋)
心拍数を扱うにあたって、連続的に値を測定・送信したいと考え,deep sleepはさせずにloop()内でアドバタイズさせています。

C++

1#define T_PERIOD 4 // アドバタイジングパケットを送る秒数 2#define S_PERIOD 1 // Sleepする秒数 T+S秒ごとに送ることになる 3 4void setAdvData(BLEAdvertising *pAdvertising) 5{ // アドバタイジングパケットを整形する 6 BLEAdvertisementData oAdvertisementData = BLEAdvertisementData(); 7 8 oAdvertisementData.setFlags(0x06); // BR_EDR_NOT_SUPPORTED | General Discoverable Mode 9 // oAdvertisementData.setFlags(0x05); // BR_EDR_NOT_SUPPORTED | Limited Discoverable Mode 10 11 std::string strServiceData = ""; 12 strServiceData += (char)0x08; // 長さ(12Byte → 7Byte 0x07の方がいいかも): 0 13 strServiceData += (char)0xff; // AD Type 0xFF: Manufacturer specific data : 1 14 strServiceData += (char)0xff; // Test manufacture ID low byte : 2 15 strServiceData += (char)0xff; // Test manufacture ID high byte : 3 16 strServiceData += (char)seq; // シーケンス番号 : 4 17 strServiceData += (char)(myBPM & 0xff); // 心拍数の下位バイト(下位を前にして保存するリトルエンディアン形式) : 5 18 strServiceData += (char)((myBPM >> 8) & 0xff); // 心拍数の上位バイト : 6 19 strServiceData += (char)(vbat & 0xff); // 電池電圧の下位バイト 20 strServiceData += (char)((vbat >> 8) & 0xff); // 電池電圧の上位バイト 21 22 oAdvertisementData.addData(strServiceData); 23 pAdvertising->setAdvertisementData(oAdvertisementData); 24} 25 26 27void setup(){ 28 29 // M5と心拍センサの初期化等 30 31 // ここからBLE通信 32 BLEDevice::init("blepub-01"); // デバイスを初期化 33 BLEServer *pServer = BLEDevice::createServer(); // サーバーを生成 34 BLEAdvertising *pAdvertising = pServer->getAdvertising(); // アドバタイズオブジェクトを取得 35} 36 37void loop(){ 38 39 // センサ値測定後 40 41 BLEServer *pServer = BLEDevice::createServer(); // サーバーを生成 42 BLEAdvertising *pAdvertising = pServer->getAdvertising(); // アドバタイズオブジェクトを取得 43 setAdvData(pAdvertising); // アドバタイジングデーターをセット 44 45 pAdvertising->start(); // アドバタイズ起動 46 delay(T_PERIOD * 1000); // T_PERIOD秒アドバタイズする 47 // delay(20); // considered best practice in a simple sketch. 48 pAdvertising->stop(); // アドバタイズ停止 49 50 seq++; // シーケンス番号を更新 51 // delay(10); 52 delay(S_PERIOD * 1000); // considered best practice in a simple sketch. 53 54}

参考文献

M5StickCとラズパイ4とのBLE(Bluetooth Low Energy)通信を試してみた。 | そう備忘録

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答1

0

ラズパイのUSBポートに有線LANのUSB変換アダプタを接続してから以下のエラーが出て,プログラムが終了するようになりました。

というなら、まずはそのアダプタを別のものに交換してみることでは。

投稿2022/07/31 22:48

y_waiwai

総合スコア87774

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

soohoo

2022/08/01 07:01 編集

ご回答ありがとうございます! それで変わるものなんですかね。でもその可能性もなくはないので一応試してみます。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

まだベストアンサーが選ばれていません

会員登録して回答してみよう

アカウントをお持ちの方は

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.48%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問