簡體   English   中英

python-can J1939過濾掩碼

[英]python-can J1939 filter mask

我一直在使用 MCP2515 CAN 總線設備在 Raspberry 中使用 python 在廣播中讀取 J1939 消息的整個值。

我想過濾 J1939 消息,但我不明白 can-mask 的含義以及我如何發現它。 python-can的文檔中說:

返回與至少一個過濾器匹配的所有消息。 如果過濾器是 None 或零長度序列,則匹配所有消息。

[{"can_id": 0x11, "can_mask": 0x21, "extended": False}]

即使我理解這個“無”部分,我也不明白如何識別我的 ID 消息的掩碼

例子:

我只想通過腳本獲取 ID 為“0xCF00400”和“0x18fee927”的消息

import can

# CAN Setting
can_interface = 'can0'
bus = can.interface.Bus(can_interface, bustype='socketcan_native')

while True:
     message = bus.recv()

     bus.set_filters([{"can_id":0xF004 , "can_mask": ?? , "extended": True},
                      {"can_id":0xfee9 , "can_mask": ?? , "extended": True}])

我應該如何填充每個變量以及如何確定 ID 的掩碼?

更新 2021 年 3 月 10 日

我已經嘗試了下面的代碼,但仍然返回所有消息

import can

# CAN Setting
can_interface = 'can0'

can_filters = [{"can_id":0xCF00400, "can_mask": 0, "extended": True},
               {"can_id":0x18fee927, "can_mask": 0, "extended": True}]

bus = can.interface.Bus(can_interface, bustype='socketcan_native',can_filters=can_filters)

while True:
     message = bus.recv()
     print(message)

Output:

Timestamp: 1615382511.238233    ID: 18fee500    X                DLC:  8    ff ff ff ff ff ff ff ff     Channel: can0
Timestamp: 1615382511.238893    ID: 18fef100    X                DLC:  8    ff ff ff ff ff ff ff ff     Channel: can0
Timestamp: 1615382511.247038    ID: 18fef100    X                DLC:  8    ff ff ff ff ff ff ff ff     Channel: can0
Timestamp: 1615382511.247611    ID: 18fee500    X                DLC:  8    ff ff ff ff ff ff ff ff     Channel: can0
Timestamp: 1615382511.248222    ID: 18fee900    X                DLC:  8    ff ff ff ff ff ff ff ff     Channel: can0
Timestamp: 1615382511.248868    ID: 0cf00400    X                DLC:  8    ff ff ff ff ff ff ff ff     Channel: can0
Timestamp: 1615382511.257056    ID: 0cf00400    X                DLC:  8    ff ff ff ff ff ff ff ff     Channel: can0
Timestamp: 1615382511.257623    ID: 18fee900    X                DLC:  8    ff ff ff ff ff ff ff ff     Channel: can0
Timestamp: 1615382511.258223    ID: 18fef100    X                DLC:  8    ff ff ff ff ff ff ff ff     Channel: can0
Timestamp: 1615382511.258827    ID: 18fee500    X                DLC:  8    ff ff ff ff ff ff ff ff     Channel: can0
Timestamp: 1615382511.267039    ID: 18fee500    X                DLC:  8    ff ff ff ff ff ff ff ff     Channel: can0
Timestamp: 1615382511.267624    ID: 18fef100    X                DLC:  8    ff ff ff ff ff ff ff ff     Channel: can0
Timestamp: 1615382511.268229    ID: 0cf00400    X                DLC:  8    ff ff ff ff ff ff ff ff     Channel: can0
Timestamp: 1615382511.268835    ID: 18fee900    X                DLC:  8    ff ff ff ff ff ff ff ff     Channel: can0
Timestamp: 1615382511.277035    ID: 18fee900    X                DLC:  8    ff ff ff ff ff ff ff ff     Channel: can0
Timestamp: 1615382511.277620    ID: 0cf00400    X                DLC:  8    ff ff ff ff ff ff ff ff     Channel: can0
Timestamp: 1615382511.278220    ID: 18fee500    X                DLC:  8    ff ff ff ff ff ff ff ff     Channel: can0
Timestamp: 1615382511.278823    ID: 18fef100    X                DLC:  8    ff ff ff ff ff ff ff ff     Channel: can0

您可以使用"can_id":0xCF00400, "can_mask": 0xFFFFFFF有效地過濾(在 kernel 級別)您想要的 cob ID,無需掩碼/過濾器。 0xFFFFFFF的掩碼(所有掩碼位設置為 1)需要與 can_id 完全匹配。

bus.set_filters([{"can_id":0xCF00400, "can_mask": 0xFFFFFFF, "extended": True},
                 {"can_id":0x18fee927, "can_mask": 0xFFFFFFF, "extended": True}])

例如,文檔說:

<received_can_id> & can_mask == can_id & can_mask時,過濾器匹配。 如果也設置了extended ,它只匹配<received_is_extended> == extended的消息。 否則,它僅根據仲裁 ID 和掩碼匹配每條消息。

舉個例子:

# The following just equals zero
0xCF00400 & 0 == 0 # True

# The following equals 0xCF00400 (217056256 in decimal) exactly
0xCF00400 & 0xFFFFFFF == 0xCF00400 # True
0xCF00400 & 0xFFFFFFF == 217056256 # True

# The following can_id would not get through the filter + mask:
0x18fee500 & 0xFFFFFFF == 0xCF00400 & 0xFFFFFFF # False

# The following obviously would get through the filter + mask:
0xCF00400 & 0xFFFFFFF == 0xCF00400 & 0xFFFFFFF # True

我將bus.set_filters()放在while True循環之前和bus.recv之前。 這是一個設置,所以你只需要在開始時設置一次。

最好在初始化總線時添加它,如下所示:

can_filters = [{"can_id":0xCF00400, "can_mask": 0xFFFFFFF, "extended": True},
               {"can_id":0x18fee927, "can_mask": 0xFFFFFFF, "extended": True}]

bus = can.Bus(
    interface="socketcan",
    channel="can0",
    can_filters=can_filters
)

另外,我相信bustype='socketcan_native'已被棄用,取而代之的是interface="socketcan" 我已經成功使用后者很長一段時間了,並且沒有警告消息。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM