TP-LINK Tapo P105/P110M のKlapプロトコル対応版 (Windows/Linux)

お待たせしました!って誰も待ってないか...v(-_-;)

P105/P110MのKlapプロトコル(最新ファーム)対応版を作ってみた。

【対応ファームウェア】
P110M: 1.1.0 Build 231009 Rel.155719 以降
P105: 1.4.1 Build 20231103 Rel. 36519 以降

※ESP32対応版は下記を参照。
TP-LINK Tapo P110M のKlapプロトコル対応版 (ESP32)

ちなみにKlapプロトコル専用なので古いファームには下記投稿のコマンドを使用する必要がある。
TP-LINK TAPO P100/P105/P110をLinux/Windowsから直接制御する

【既知の問題】
現状ではセッション開始後の最初のリクエストがときどきHTTP-403エラーになるという不具合が残されている。セッション開始のためのハンドシェーク処理は成功するもののその後のリクエストがなぜかエラーになってしまいハンドシェークからやり直さないとリカバリーできないという現象でリクエストが成功した場合にはその後も問題はない。時間をかけて調べてみたが今のところ原因不明...orz

【セッション復元機能】
試験では通常0~2回、まれに最大5回までのリトライで成功してはいるがコマンド実行毎に新たにセッションを開始するとリトライにより実行時間にかなり悪影響を与えてしまう。

改善策としてセッション情報を保存/復元できるようにしてみたところ効果バツグン。通常ならコマンド実行毎に3回の通信が必要なところセッション復元できれば1回の通信で済むから3倍速となる。

セッション情報は次の場所に”tapo2-xxx.xxx.xxx.xxx”の名前でデバイス毎に保存され間違って削除されても問題はない。

linux: /var/tmp
windows: TEMP或いはTMP環境変数が示すフォルダ

【参照ライブラリ】
libb64は変更なし。(というか変更してはいけない)
json-developを3.11.3にアップデート。
mbedtlsを2.28.6にアップデート。

※mbedtlsの現在の最新はV3系であるが環境依存ファイルを生成するためにpythonやperlが必須となってしまったため断念しV2系の最新にアップデート。

【コンパイルの事前準備】
適当なフォルダにsources.zipを展開する。展開されたmbedtls-2.28.6フォルダに入って次のコマンドを実行する。

linux: make no_test
windows(MSYS2-MinGW): make CC=gcc no_test WINDOWS=1

【コンパイル】
展開先フォルダでmakeを実行する。再コンパイルするときはmakeする前にmake cleanを実行する。

【ダウンロード】
sources.zip
tapo2.exe (windows-x64)

【修正履歴】
2024-03-18
HiroさんよりCrypt::random()が落ちるというフィードバックあり。ググッてみたらmbedtlsのmbedtls_ctr_drbg_seed()にメモリリークの可能性があるらしいのでとりあえずrand()関数による実装に変更。おまけとしてVisual C++でもコンパイルできるようなコードに修正してみた...試してないけど。(-_-;)

2024-01-13
昨日からP105を回し続けているがエラーもなく別端末からの排他制御エラー(-1012)も発生しなくなったようだ。ということは現状でOKということかな?ふと気になって参考にさせて頂いたplugp100で試してみたらP105の電源オンオフは出来なかった。もしかして世界初のP105のKlapプロトコル対応?...それはともかく昨日はお天気も良くロケットも気持ちよさそうに飛び立っていって良き日であった。(^o^)
と思っていたらいきなりP105がエラーばかり起こして何もできなくなった。TAPOアプリからの操作も出来ない。でも暫く待ってたら復旧した。普段はそう頻繁にオンオフすることはないだろうという前提であれば大丈夫なのかな...(-_-;)

2024-01-12
P105の挙動が怪しい。HTTPリクエストの送信処理を変更してみたところだいぶましにはなったような気もするがごくまれにP105がハングアップしてしまうことがある。P105にはタイミングバグがあるのかな?もしそうだとすると厄介だ。P110Mは一日中ぶん回しても問題ないのに...
P105の-1301エラーは処理遅延の警告みたいであるが頻繁に出てウザイので無視するように修正。

2024-01-11
昨日はうまく動作していたP105が今日はなぜか-1012エラーで動かない...orz
そういえばP105のon/off操作にはterminalUUID指定が必要なことを思い出し実装を追加してみたところうまく動作するようにはなったが端末Aからon/off操作した後に端末Bからon/off操作しようとしても2分経過しないと-1012エラーになってしまう。なぜだろう?
とりあえず動作するようにはなったので再公開。(-_-;)
ちなみにP105はHWの処理能力が足りないのか不安定っぽい。これから購入する人はP110Mのほうが安定してるのでお勧め。

2024-01-10
mbedtlsの使い方のミスによるメモリーリークの修正、及び、通信毎にソケットを接続切断するように修正。
★★★昨日までにDLした方は入れ替えをお願いします。★★★

2024-01-09
httpclint.hが、ごちゃごちゃしてだいぶ見苦しなってきたので整理整頓&修正を行った。

2024-01-08
細かな改良。

2023-12-28
HTTP処理を改良しリトライの処理時間を短縮してみた。リトライしたのがわからないぐらいにはなった。かな。

2023-12-26
軽微なバグを修正。RaspberryPi/Ubuntu/Windowsで動作を確認。

2023-12-25
セッションタイムアウト値が間違っていたので修正。

【ソースコード】

“TP-LINK Tapo P105/P110M のKlapプロトコル対応版 (Windows/Linux)” への22件の返信

  1. おお!素晴らしいソフトウェアを見つけた!と思い
    早速使わせていただきましが。が…

    P105を使っています。
    ファームウェアは
    1.4.1 Build 20231103 Rel. 36519
    です。

    tapo.exe だと
    TAPO Status: [1003]
    でダメなようでした。

    tapo2.exe(2024-01-09) だと
    [tapo2.h:309] HttpClient::request(292, “POST”, “app/handshake2”, 000000c8略, 32) = -1
    [tapo2.h:246] HttpClient::request(292, “POST”, “app/handshake1”, 00007ff6略, 16) = -1
    [tapo2.h:246] HttpClient::request(292, “POST”, “app/handshake1”, 00007ff6略, 16) = -1
    [tapo2.h:246] HttpClient::request(292, “POST”, “app/handshake1”, 00007ff6略, 16) = -1
    [tapo2.h:246] HttpClient::request(292, “POST”, “app/handshake1”, 00007ff6略, 16) = -2
    [tapo2.h:246] HttpClient::request(292, “POST”, “app/handshake1”, 00007ff6略, 16) = -2
    [tapo2.h:246] HttpClient::request(292, “POST”, “app/handshake1”, 00007ff6略, 16) = -2
    [tapo2.h:246] HttpClient::request(292, “POST”, “app/handshake1”, 00007ff6略, 16) = -2
    [tapo2.h:246] HttpClient::request(292, “POST”, “app/handshake1”, 00007ff6略, 16) = -2
    [tapo2.h:246] HttpClient::request(292, “POST”, “app/handshake1”, 00007ff6略, 16) = -2
    と表示され、ダメなようでした。
    (何の数字かかりませんが念の為、数値を略しました。)

    このファームウェアもKlapとやらなのでしょうか?
    何とか動作させることはできませんでしょうか?

    ( https://github.com/achetronic/tapogo も何でか動かないし…泣)

    1. コメントありがとうございます。
      P105の最新ファームでは試したことはありませんが、tapo.exeで1003エラーが出るということは新しいプロトコル(Klap)に変更されたものと思われます。
      調べてみると日本以外では数年前からKasa/Tapoとも既に変更されているみたいですが、なぜか日本だけ?が昨年から変更されつつあるようです。
      P110Mでも原因不明なエラーは出ますがリトライにより解消されるとの判断から公開したのですがまだまだ何かあるようですね...
      handshake1/handshake2での-1エラーはデバイス側からいきなり接続を切られると発生します。デバイスをコンセントから抜き差しすると正常に動作するようになることがありますが、それはさておき現状ではリトライ中の接続断には対応できていないのでそのへんの改良が必要みたいですね。検討してみたいと思いますのでお待ちください。

    2. 手持ちのP105のファームを”1.4.1 Build 20231103 Rel. 36519″にアッブデートし、ついさきほど公開した最新版で試したところうまく動作しました。
      P110は通信毎に接続を切らないタイプのサーバーですがP105は通信毎に接続を切るタイプのサーバーですのでどちらにも対応できるようにしてみました。
      試してみてください。

  2. 超早の対応、ありがとうございます!
    P105
    1.4.1 Build 20231103 Rel. 36519
    にて一応動作しました。

    なのですがどうも、一度でもAndroidのTapoアプリ(3.1.605)からON/OFFを行うと、以降 tapo2.exe にて
    [tapo2.h:105] TAPO Error Code (-1012)
    というエラーが出て、ON/OFF操作できなくなってしまいました。

    その後、P105をコンセントプラグから一度抜いて挿し直すと、再び tapo2.exe にてON/OFF可能になります。

    なお同じ上記ファームウェアの3台のP105で試しましたが、どれも同じ動作でした。
    ちなみにON/OFF操作できない状態でもINFOは取れます。

    他の方はどうでしょうか?

    1. 試して頂いてありがとうございます。
      -1012はP105の仕様みたいで2分経過するまで待つ必要があります。誤動作ではないため回避方法はありません。
      また、動作には問題ないようなのですがP105はHWの処理性能が低すぎて内部処理が間に合わない状況になると-1301エラーが返されることがあります。
      それらが気になるようなら安定して動作するP110Mをお勧めします。

    2. ごめんなさい。間違ってました。
      もう一度動作確認してみたらtapoアプリから操作後でも問題ありませんでした。
      本日、気になる点があり何度か更新&UPしたため途中の版を試されたのだと思います。
      再度DLして試してみてください。

    3. たびたびすいません。
      TAPOアプリ操作後に-1012が出ることもあるようです。
      条件はわかりませんが...

  3. はじめまして。ずっと前からお礼を言わななくちゃと思っていました。
    前のプロトコルからありがたく利用させて頂いています。
    本当に、待っていました!です。
    VisualStudio2022に移植して、1/13版にて複数端末からP105を制御できました。
    ファームは1.4.1 Build 20231103 Rel. 36519です。
    うちにはP105が10台以上あって生活機能の一部になっているのでこの神ツールが無ければ途方に暮れるところでした。ありがとうございます。
    今後のキャッチアップにもご期待しております。

    1. コメント&使って頂いてありがとうございます。
      P110Mのほうがいいですよ!とお勧めしたいところですがP105が10台とは...それだけ数があると買い替えるのも大変ですね。P105はクセがありすぎるので個人的には安心して使えるHS105を今でもメインで使っているのですが入手が難しくなったのと電力モニターが可能になるといろいろ面白そうなことができそうなので対応してみました。クラウドベースだと停電などインターネットが使えない緊急時に役に立たないのが辛すぎるので個人的に調べて作ってみたのが始まりです。何かのお役に立てれば幸いです。

  4. ネットの海をさまよっていましたところ発見。
    今、自作の状況をモニターできるツールを自作し提案す。
    手始めにBルートから自宅の総消費電力を引っ張ってWEBアプリで表示しており、温湿度などとも連動したいな…と思っている次第です。時間から気温から消費電力から、直近のゴミの日から何でもわかるツールを目指しています。

    現状全コンセントの合計値しか取れないので、エアコンとネットワーク機器・PCなどのコンセントは個別で計測し表示したいと思い、だれかP110Mを解析してる方いないかな~と探したところドンピシャ。まさに神に出会えた気分です。

    お給料入ったら何台か購入して試してみようと思います。ありがとうございます。頑張ってPythonに移植できたらいいのですが。

    1. コメントありがとうございます。
      なにやら楽しそうなことをされているようですね。

      TP-LinkのプロトコルについてはK4CZP3Rという方がHAのために解析したのをpythonで公開されていて現在公開されているpython以外のプログラムの原本となっているようですのでpythonがお望みであれば元サイトを参考にされたほうが良いかもです。但し、P110Mで動作することは確認していますがP105(klap)には非対応です。

      https://github.com/petretiandrea/plugp100

      何かの参考になれば幸いです。頑張ってください!

      1. すぐにお返事いただいていたのにすみません。巡回が遅くなってしまいました。なんとさらに元ネタが公開されているとは知りませんでした。こちらもさっそく、チェックしてみます!

        とりあえず、Bルートから瞬間消費電力と積算電力量を引っこ抜いてpostgresqlに突っ込むところはなんとかなり、次はP110Mかゴミ捨日表示機能の実装か、というところです。

        最終的に、ネットの海のどなたかが解析しているClova deskに表示できれば面白そうです。また来ます!

  5. 👆のVS2022に移植した者です。お久しぶりです。少しフィードバックを。
    しばらく快調だったのですがある時からP105を制御できなくなり、調べると最初のhandshake1の中、
     _crypt.random(_localSeed, sizeof(_localSeed));
    のところで強制終了が起こっていました。それからなぜか我が家の環境では再現100%なのです。
    それで、特に意図せず上記をコメントアウトしたところ、何事もなかったかのように動作している現在です。
    (なんらかの乱数初期化はされていないのでしょうが・・・)
    お心当たりはあったりしますでしょうか?

    お勧めのP110M導入してみました。確かにこれは便利で楽しいです!
    L510も加え、今のところ上記応急処置版ですべて制御できています。

    1. フィードバックありがとうございます。
       _crypt.random(_localSeed, sizeof(_localSeed));
      これはバッファをランダムな値で埋めるだけなのでコメントアウトしても動作的には何も問題はありません。セキュリティ的は弱くなるのでしょうがセッション継続中に同じシード値を再利用することを考えると気にする必要もないかと思います。そういえば開発当初によく落ちていた処理のような気もするのでmbedtlsの使い方の問題或いはバグなのかもしれませんね...とりあえずrandom(時刻)を使って実装しなおしても良いのですが、あとで調べてみて何かわかりましたら連絡します。

    2. ググッてみたらmbedtlsにメモリリークの可能性があるようなのでrand()関数による実装に変更しておきました。
      詳細な内容のフィードバックは大変助かります。Hiroさん、ありがとうございました。<(_ _)>

      1. こちらこそお早いご対応ありがとうございます。3-18版でコンパイルし、安定しています!
        なるほどどうにかして_localSeedの中をランダマイズしてやれば良いところだったのですね。
        拙宅の3機種全12台を1本で制御できて、このツールやはり最高です。主にCGI化してWEBからの制御に使わせて頂いています。
        長らくarduinoから遠ざかっていましたが、ESP32でも使ってクローズドな何かもやってみたくなります☺

  6. Hiro様 ご無沙汰しております。kunyです。下記、Ubuntu 22.04上で試行しております。

    かなり時間がかかってしまいましたが、自宅の電気メータからwi-sunで情報を引っこ抜いてきて、現状値・日時値・月間値・今月の推定請求額などをgrafanaで算出できるダッシュボードができてきました。各部屋の温湿度取得もswitchbot経由で対応させています。

    本筋ではないですが、自作のダッシュボードは契約している電力会社のプランと毎月の燃料調整費などを反映しておりかなり高精度にできています。

    このダッシュボードの最後の作りこみとして、自宅全体だけでなく電気代が嵩みそうなエアコンやサーバといった箇所の消費電力量をtapoで取得したく、mihai-dinculescu/tapoというライブラリを使ってみたいのですが全く安定しません。そこでHiroさんのソースをコンパイルして実行してみています。

    ./tapo2 192.168.50.81 “hoge@example.com” “Abcd123456” info といった感じで入力していますが(内容はダミー)
    [tapo2.h:257] Login failed と帰ってきます。

    ダブルクオートを抜いても状況が変わらず、これはtapo側がフリーズしているのでしょうか。初歩的で申し訳ございませんがお返事頂戴できますと幸甚です。

  7. researcher 様
    kunyです。連投してしまい申し訳ございません。
    宛名がHiro様となっておりました。
    盆休み1日目、序盤から徹夜しており判断力がなくなっており、大変なご無礼を失礼しました。内容については先ほど投稿のとおりです。

  8. researcher 様
    kunyです。先ほど6~7時ごろに誤ってHiro様宛として投稿した内容が反映されていないようで、
    改めて投稿します。

    環境:Ubuntu 22.04 LTS
    状況:ソースをコンパイルし実行。
    ./tapo2 192.168.50.81 “hoge@example.com” “Abcd123456” info (メール・PWはダミー)
    [tapo2.h:257] Login failed
    となりログインできません。

    経緯:前回書き込みで話していたダッシュボードを作りこみました。
    自宅全体の電力消費量表示・年間&月間&日時集計と燃料調整費を反映した
    精緻な請求額シミュレーション機能を実装しました。

    switchbotの温湿度取得にも対応させています。ダッシュボードの新機能として、
    自宅全体ではなく特定のコンセントの消費電力量をP110Mで監視しようとしています。

    試しにmihai-dinculescu/tapoというライブラリを使っています。
    おそらくissueにあるバグを踏んでいるらしく安定しません。
    そこでresearcher 様のプログラムを組み込む形での実装を考えております。
    初歩的なエラーで恐縮ですが、こいつはP110M側が悪いのでしょうか。
    徹夜で頭がボケーっとしておりますので、いったん寝ようと思います(笑

    1. 徹夜でそうとうお疲れのようですね。v(-_-;)
      徹夜なんてなんだか懐かしい気がしますが...って、それはともかくエラーの個所から考えられるとしたらP110Mのファームが古いままアップデートされていない、つまり古いプロトコルで動作しているのではないかということです。まずはファームのバージョンを確認してみてください。

      【対応ファームウェア】
      P110M: 1.1.0 Build 231009 Rel.155719 以降
      P105: 1.4.1 Build 20231103 Rel. 36519 以降

  9. researcher様
    お世話になっております。kunyです。
    先ほどは乱文大変失礼いたしました。
    アドバイスのとおりファームアップを行ったところ、見事動作いたしました!ありがとうございます。わざとUpdateを止めておりました。

    どこかで製作記事を書こうかと思っているのですが、ドキュメントは全く書いておらずという状況です。qiitaに画像だけ張ってみようかと悩んだのですが、とりあえず下記のUploadしてみました。

    https://f.yourl.jp/9a20a7ec/

    取り急ぎ、お礼とご報告を申し上げます!
    引き続き、Lineでの通知機能などを作っていこうかなと思っています。

    1. kuny様
      動作して良かったですね。
      それと画像見ました。デザイン・センスがない私には絶対作れないカッコいい画面ですね。v(-_-;)

コメントを残す

メールアドレスが公開されることはありません。 が付いている欄は必須項目です

CAPTCHA


このサイトはスパムを低減するために Akismet を使っています。コメントデータの処理方法の詳細はこちらをご覧ください