LoginSignup
1
1

More than 3 years have passed since last update.

LoRaのGateway Protocolについて

Last updated at Posted at 2020-02-05

はじめに

趣味でLoraのGateway(GW)やEndDevice(Node)とか作っています.
その中で色々と調べたことをまとめておこうと思います.

Gateway Protocol とは

GatewayとNetwork Server(正確には窓口となるrouter)の間をインターネットでやり取りする部分のプロトコルです.
2つあり、一つはSemtechが策定したSemtech UDP protocolと呼ばれるものです.
二つめはTheThingsNetwork(TTN)が策定したGateway connector protocolです.
ここでは前者のSemtech UDP protocolについて書きます.

基本的な考え方

通信はUpstream/DownstreamともにGateway側から始めます.
大抵はNAT/Firewallを超える必要がありますし、Network Serverの負荷を最小限にできるのかなと思います.
各データグラム(ネット上のパケット)は2バイトのトークンで識別されます.トークンは往信ではランダムな値で、返信は同じ値としています.
なお以下の説明ではGatewayから見たやりとりです.

Upstream

往路

PUSH_DATA パケットを送信します.
フォーマットは次のようです.

Bytes 0 1-2 3 4-11 12-end
VERSION random token PUSH_DATA_ID GW_ID Payload

ここでVERSION=0x02,PUSH_DATA_ID=0x00,GW_ID=MAC_addressです.
PayloadはJSONに似た形式で.内容が規定されれています.

復路

PUSH_ACK パケットが返ってきます.
フォーマットは次のようです.

Bytes 0 1-2 3
VERSION 受信したtoken PUSH_ACK_ID

ここでPUSH_DATA_ID=0x01です.

JSON的形式のPayload

階層形式になっており、最上位(ルート)は受信したパケット情報を送る"rxpk" かGateway自身の情報を送る"stat"です.
どちらか一つでも両方を連続して送ることもできます.
その下に最低一つの内容を含むことになっており、それぞれ以下のものが規定されています.

rxpk

15項目が規定されていますがここではLORAの場合の項目を記します.

名前 内容
time 受信したUTC時刻
tmss 受信がGPS時刻
tmst 受信が完了した内部時刻
chan 無線部のIFチャネル
rfch 無線部のRFチャネル
freq 受信周波数
stat CRCの値、1=OK,-1=NG,0=noCRC
modu 変調形式、LORAかFSK
datr LoRaではデータレートID、SF7BW125など
codr 誤り訂正レート、4/5など
lsnr SNR信号雑音比
rssi 信号強度
size 受信したペイロードの長さ
data 受信したペイロード

ちなみにSingle_Chan_Packet_Forwarderではtime、tmssは送信していませんでした.
chanとrfchの違いがよく分かりませんがご存じの方は教えてください.

一例としてうちのGWのログから抜粋したものを示します.

rxpk
 {"rxpk":[{"tmst":52224633,"chan":0,"rfch":0,"freq":923.400000,"stat":1,"modu":"LORA","datr":"SF7BW125","codr":"4/5","lsnr":9,"rssi":-75,"size":24,"data":"QIgiBCYANwAB1b5iqBO3034LpwEwsMfO"}]}

dataは受信したデータです.
このdataはAESで暗号化されていますのでなんだかわかりませんがここではcayenneLPP形式のGPSデータで11byteです.ヘッダーや誤り検出コードがついてサイズは24byteになります.暗号化は16byte単位なのでPadが追加されて32文字になっています.

サーバに送るべき2つ以上の受信パケットがある場合は内容を連続して送ることもできます( SF10-12など低速の場合は送信時間制限に注意ですが 【2020-03-08】送信時間に注意するのは無線区間ですね..勘違いしてました.)

stat

名前 内容
time UTCシステム時刻
lati GWの緯度
long GWの経度
alti GWの高度
rxnb 無線受信したパケット数
rxok 無線受信しCRCがOKのパケット数
rxfw 無線受信しサーバに転送したパケット数
ackr サーバにUpしACKを受け取ったパーセント
dwnb サーバからDownしたデータグラムの数
txnb 無線送信したパケット数
pfrm Gatewayのプラットフォーム
mail Gatewayのオーナーの連絡先
desc Gatewayの説明

最後の3つはPROTOCOL.TXTには記載がありませんがSingle_Chan_Packet_Fowarderでは拡張されているのか送信しているので記載しました.TTNでは同様の内容をコンソールで設定するのでサーバによっては無くても良いのかも知れません.
同じく、うちのGWのログから抜粋したものを示します.(※一部文字、数字を入れ替えています.実際は半角です.)

stat
{"stat":{"time":"2020-02-04 10:07:22 GMT","lati":35.*****,"long":136.xxxxx,"alti":6,"rxnb":0,"rxok":0,"rxfw":0,"ackr":0.0,"dwnb":0,"txnb":0,"pfrm":"Bidirection 1ch Gateway","mail":"tsuyoshi.ohashi@gmail.com","desc":"Raspberry pi and Dragino GPS-HAT"}}

stat単独で送ることもrxpkと連続して送ることもできます.

Downstream

往路

往路は「データありませんか?」的な問い合わせで始まります.
フォーマットは次のようです.

Bytes 0 1-2 3 4-11
VERSION random token PULL_DATA_ID GW_ID

ここでPULL_DATA_ID=0x02です.
DownstreamのデータはGateway宛ではなく、EndDevice宛ですのでEndDeviceの近くにいると判断されればデータ配送が割り当てられるのだと思います.
EndDeviceのログを見ていると、知らない(失礼!)Node宛のデータが時々飛んできます.
【2020-02-06追記】
EndDeviceでデータを受け取れないことがあったのですがGWがPULL_DATAを送信していなかったのが原因でした...

復路(データがある場合)

PULL_RESP パケットが返ってきます.
フォーマットは次のようです.

Bytes 0 1-2 3 4-end
VERSION random token PULL_RESP_ID Payload

ここでPULL_RESP_ID=0x03です.
復路ですがランダムトークンが発行されているのはPULL_RESPに対して後でTX_ACKを返信するためです.
PayloadはUpstreamと同様にJSON的な形式です.

{
    "txpk": {...}
}

txpk

16項目が規定されていますがここではTTNからうちのGatewayに送信されてくる13項目を記します.

名前 内容
imme 即時転送するか否か
tmst 指定時刻で転送する
tmms GPS時刻で転送する
freq 送信周波数
rfch 無線部の送信チャネル
powe 送信電力
modu 変調形式、LORAかFSK
datr LoRaではデータレートID、SF7BW125など
codr 誤り訂正レート、4/5など
ipol Loraの変調極性
size 転送するペイロードの長さ
ncrc CRCつけない
data 転送するペイロード

EndDeviceがClassBだと即時送信になるのかな?(推測、未確認)
【2019-02-16追記】immeに対応するのはClass Cのようです.
同じく、tmstはClass A、tmmsはClass Bに対応.

一例としてTheThingsNetworkに接続したうちのGWのログから抜粋したものを示します.

txpk
 {"txpk":{"imme":false,"tmst":1618204691,"freq":923.4,"rfch":0,"powe":11,"modu":"LORA","datr":"SF7BW125","codr":"4/5","ipol":true,"size":18,"ncrc":true,"data":"oMwpBCYAAAABQ7mXXAIpyeBX"}}

dataはBase64でエンコードされています.ちなみに原文は「Qiita]の文字列です.
ここでは送信電力が11dBmと指定されていますがうちのGWでは反映してません.転送時刻も指定されていますがRX1のタイミングで転送しているので無視していることになる..

TX_ACK

サーバからデータを受け取ったらTX_ACKを返信します、
TX_ACKのフォーマットは次のようです.

Bytes 0 1-2 3 4-11 12-end
VERSION PULL_RESPと同じtoken TX_ACK_ID GW_ID Payload(Option)

ここでTX_ACK_ID=0x05です.
EndDeviceに送信できないなどのエラーがあればネットワークサーバにルートの名前を「txpk_ack」として情報を送ることもできますがここでは省略します.

復路(データがない場合)

PULL_ACKが返ってきます.
フォーマットは次のようです.

Bytes 0 1-2 3
VERSION PULL_DATAと同じtoken PULL_ACK_ID

ここでPULL_ACK_ID=0x04です.

最後に

趣味でGatewatyやEndDeviceをraspberryPiで作っています.
やっとOTAAができるようになりました.
このまとめたのを元にGatewayの機能をアップグレードさせたいです.

参考

1
1
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
1