can327:用於 Linux SocketCAN 的 ELM327 驅動程式¶
動機¶
此驅動程式旨在降低對 CAN 匯流排工作感興趣的駭客的初始成本。
CAN 介面卡價格昂貴、數量稀少。 ELM327 介面價格便宜且數量充足。讓我們使用 ELM327 作為 CAN 介面卡。
簡介¶
此驅動程式旨在將大量的基於 ELM327 的 OBD 介面轉換為完全成熟(儘可能)的 CAN 介面。
由於 ELM327 從來都不是獨立的 CAN 控制器,因此驅動程式必須儘可能快地在其模式之間切換,以偽造全雙工操作。
因此,can327 是盡力而為的驅動程式。但是,這足以實現簡單的請求-響應協議(例如 OBD II),並監視總線上的廣播訊息(例如在車輛中)。
大多數 ELM327 都是非描述性序列裝置,透過 USB 或藍牙連線。驅動程式無法自行識別它們,因此使用者有責任以 TTY 線路規程的形式附加它(類似於 PPP、SLIP、slcan 等)。
此驅動程式適用於 ELM327 版本 1.4b 及更高版本,請參閱下文,瞭解舊控制器和克隆版本的已知限制。
資料表¶
官方資料表可在 ELM electronics 的主頁上找到
如何附加線路規程¶
每個 ELM327 晶片都已在工廠程式設計為以 38400 波特/秒、8 個數據位、無奇偶校驗、1 個停止位的序列設定執行。
如果您保留了此預設配置,則可以在命令提示符下附加線路規程,如下所示
sudo ldattach \
--debug \
--speed 38400 \
--eightbits \
--noparity \
--onestopbit \
--iflag -ICRNL,INLCR,-IXOFF \
30 \
/dev/ttyUSB0
要更改 ELM327 的序列設定,請參閱其資料表。這需要在附加線路規程之前完成。
一旦附加了 ldisc,CAN 介面就開始未配置。在啟動之前設定速度
# The interface needs to be down to change parameters
sudo ip link set can0 down
sudo ip link set can0 type can bitrate 500000
sudo ip link set can0 up
500000 位/秒是 OBD-II 診斷的常用速率。如果您直接連線到汽車的 OBD 埠,那麼這是大多數汽車(但不是全部!)所期望的速度。
之後,您可以像往常一樣使用 candump、cansniffer 等。
如何檢查控制器版本¶
使用終端程式連線到控制器。
發出“AT WS”命令後,控制器將響應其版本
>AT WS
ELM327 v1.4b
>
請注意,克隆版本可能會聲稱是他們喜歡的任何版本。這並不表示他們的實際功能集。
通訊示例¶
這是關於如何與 ELM327 通訊的簡短而不完整的介紹。它旨在指導您瞭解控制器和驅動程式的限制(如下所列)以及手動測試。
ELM327 有兩種模式
命令模式
接收模式
在命令模式下,它期望每行一個命令,以 CR 結尾。預設情況下,提示符為“>”,之後可以輸入命令
>ATE1
OK
>
驅動程式中的 init 指令碼關閉了多個僅在晶片設計的原始 OBD 場景中才有意義的配置選項,實際上對 can327 是一種阻礙。
當無法識別命令時,例如透過舊版本的 ELM327,則會列印問號作為響應而不是 OK
>ATUNKNOWN
?
>
目前,can327 不評估此響應。有關詳細資訊,請參閱下面有關已知限制的部分。
當要傳送 CAN 幀時,配置目標地址,然後將幀作為命令傳送,該命令由資料的十六進位制轉儲組成
>ATSH123
OK
>DEADBEEF12345678
OK
>
上面的交互發送帶有(11 位)CAN ID 0x123 的 SFF 幀“DE AD BE EF 12 34 56 78”。為此,必須將控制器配置為 SFF 傳送模式(使用“AT PB”,請參閱程式碼或資料表)。
一旦傳送了幀並且啟用了等待回覆模式(ATR1,配置為 listen-only=off),或者當回覆超時到期並且驅動程式將控制器設定為監視模式(ATMA)時,ELM327 將為每個接收到的 CAN 幀傳送一行,包括 CAN ID、DLC 和資料
123 8 DEADBEEF12345678
對於 EFF(29 位)CAN 幀,地址格式略有不同,can327 使用此格式來區分兩者
12 34 56 78 8 DEADBEEF12345678
ELM327 將接收 SFF 和 EFF 幀 - 當前 CAN 配置(ATPB)無關緊要。
如果 ELM327 的內部 UART 傳送緩衝區已滿,它將中止監視模式,列印“BUFFER FULL”並返回到命令模式。請注意,在這種情況下,與其他錯誤訊息不同,錯誤訊息可能會與最後一個(通常是不完整的)資料幀出現在同一行
12 34 56 78 8 DEADBEEF123 BUFFER FULL
控制器的已知限制¶
克隆裝置(“v1.5”等)
不支援傳送 RTR 幀,並且會靜默丟棄它們。
接收 DLC 為 8 的 RTR 幀似乎是帶有最後接收到的幀的 DLC 和有效負載的常規幀。
不支援“
AT CSM”(CAN 靜默監視,即不傳送 CAN ACK),並且硬編碼為 ON。因此,幀在監聽時不會被 ACK:“AT MA”(監視所有)將始終是“靜默”的。但是,在傳送幀後立即,ELM327 將處於“接收回復”模式,在這種模式下,它會 ACK 任何接收到的幀。一旦匯流排靜默,或者發生錯誤(例如 BUFFER FULL),或者接收回復超時到期,ELM327 將自行結束回覆接收模式,can327 將回退到“AT MA”,以便繼續監視匯流排。其他限制可能適用,具體取決於克隆版本及其韌體質量。
所有版本
不支援全雙工操作。驅動程式將盡可能快地在輸入/輸出模式之間切換。
無法設定傳出 RTR 幀的長度。事實上,一些克隆版本(經過測試,標識為“
v1.5”)根本無法傳送 RTR 幀。我們沒有辦法獲得有關 CAN 錯誤的即時通知。雖然有一個命令(
AT CS)可以檢索一些基本統計資訊,但我們不會輪詢它,因為它會迫使我們中斷接收模式。1.4b 之前的版本
這些版本在監視模式 (AT MA) 下不傳送 CAN ACK。但是,它們在傳送幀後立即在等待回覆時傳送 ACK。驅動程式會最大化此時間,以使控制器儘可能有用。
從 1.4b 版本開始,ELM327 支援“
AT CSM”命令,“只監聽”CAN 選項將生效。1.4 之前的版本
這些晶片不支援“
AT PB”命令,因此無法動態更改位元率或 SFF/EFF 模式。這必須由使用者線上路規程附加之前進行程式設計。有關詳細資訊,請參閱資料表。1.3 之前的版本
這些晶片根本無法與 can327 一起使用。它們不支援“
AT D1”命令,這對於避免傳入資料的解析衝突以及區分 RTR 幀長度是必需的。具體來說,這允許輕鬆區分 SFF 和 EFF 幀,並檢查幀是否完整。雖然可以從 ELM327 傳送給我們的行的長度推斷型別和長度,但是當 ELM327 的 UART 輸出緩衝區溢位時,此方法會失敗。它可能會中止在行中間傳送,然後會被誤認為是其他內容。
驅動程式的已知限制¶
無 8/7 定時。
ELM327 只能設定 500000/n 形式的 CAN 位元率,其中 n 是整數除數。但是,有一個例外:使用單獨的標誌,它可以將速度設定為除數指示的速度的 8/7。當前未實現此模式。
不評估命令響應。
當理解命令時,ELM327 將回復 OK,當不理解命令時,將回復 ?。驅動程式當前不檢查此項,而只是假設晶片理解每個命令。驅動程式的構建方式是功能仍然可以優雅地降級。請參閱控制器已知限制部分。
不使用硬體 CAN ID 過濾
在重 CAN 匯流排負載下,ELM327 的 UART 傳送緩衝區很容易溢位,從而導致“
BUFFER FULL”訊息。使用透過“AT CF xxx”和“AT CM xxx”提供的硬體過濾器將有所幫助,但是 SocketCAN 目前不提供使用此類硬體功能的工具。
所選配置背後的原理¶
AT E1啟用回顯
我們需要這個才能可靠地獲得提示符。
AT S1啟用空格
我們需要這個來區分接收到的 11/29 位 CAN 地址。
注意:我們通常可以使用行長(奇數/偶數)來完成此操作,但是如果該行未完全傳輸到主機(BUFFER FULL),則此方法將失敗。
AT D1啟用 DLC
我們需要這個來告知 RTR 幀的“長度”。
關於 CAN 匯流排終端的說明¶
您的介面卡可能焊接有電阻,這些電阻用於端接匯流排。當它插入 OBD-II 插座時,這是正確的,但是在嘗試接入現有 CAN 匯流排的中間時,這沒有幫助。
如果連線介面卡後通訊不起作用,請檢查其 PCB 上的終端電阻,然後嘗試將其移除。