(一) 工業(yè)現(xiàn)場總線 CAN 的基本介紹以及 STM32 的 CAN 模塊簡介
首先通讀手冊中關(guān)于CAN的文檔,必須精讀。
需要精讀的部分為 RCC 和 CAN 兩個章節(jié)。
為什么需要精讀 RCC 呢?因為我們將學(xué)習(xí) CAN 的波特率的設(shè)置,將要使用到 RCC 部分的設(shè)置,因此推薦大家先復(fù)習(xí)下這部分中的幾個時鐘。
關(guān)于 STM32 的 can 總線簡單介紹
bxCAN 是基本擴展 CAN (Basic Extended CAN) 的縮寫,它支持 CAN 協(xié)議 2.0A 和 2.0B 。它的設(shè)計目標是,以最小的 CPU 負荷來高效處理大量收到的報文。它也支持報文發(fā)送的優(yōu)先級要求(優(yōu)先級特性可軟件配置)。
對于安全緊要的應(yīng)用,bxCAN 提供所有支持時間觸發(fā)通信模式所需的硬件功能。
主要特點
支持 CAN 協(xié)議 2.0A 和 2.0B 主動模式
波特率最高可達 1 兆位 / 秒
支持時間觸發(fā)通信功能
發(fā)送
3 個發(fā)送郵箱
發(fā)送報文的優(yōu)先級特性可軟件配置
記錄發(fā)送 SOF 時刻的時間戳
接收
3 級深度的2個接收 FIFO
14 個位寬可變的過濾器組 - 由整個 CAN 共享
標識符列表
FIFO 溢出處理方式可配置
記錄接收 SOF 時刻的時間戳
可支持時間觸發(fā)通信模式
禁止自動重傳模式
16 位自由運行定時器
定時器分辨率可配置
可在最后 2 個數(shù)據(jù)字節(jié)發(fā)送時間戳
管理
中斷可屏蔽
郵箱占用單獨 1 塊地址空間,便于提高軟件效率
(二) STM32 CAN 模塊工作模式
STM32 的 can 的工作模式分為:
在此章我們的 Mini-STM32 教程中我們將使用到 CAN_Mode_LoopBack 和 CAN_Mode_Normal 兩種模式。
我們第一步做的就是使用運行在 CAN_Mode_LoopBack 下進行自測試。
在參考手冊中 CAN_Mode_LoopBack (環(huán)回模式) 的定義如下:
環(huán)回模式可用于自測試。為了避免外部的影響,在環(huán)回模式下 CAN 內(nèi)核忽略確認錯誤 (在數(shù)據(jù) / 遠程幀的確認位時刻,不檢測是否有顯性位) 。在環(huán)回模式下,bxCAN 在內(nèi)部把 Tx 輸出回饋到 Rx 輸入上,而完全忽略 CANRX 引腳的實際狀態(tài)。發(fā)送的報文可以在 CANTX 引腳上檢測到。
因此這種模式也特別適合大家做好硬件后自測程序。
(三) CAN 接口端口映射
STM32 中的 CAN 物理引腳腳位可以設(shè)置成三種:
默認模式,重定義地址1模式,重定義地址2模式
在我們的 Mini-STM32 上面沒有接出 CAN 的接口芯片, 所以我們可以利用
RealView MDK
的 CAN 軟件
模擬
模塊來做實驗.
------------------------------------------------------------------------
設(shè)置完 CAN 的引腳之后還需要打開 CAN 的時鐘:
(四) CAN 波特率設(shè)置
4、我們需要搞明白CAN波特率的設(shè)置,這個章節(jié)也是使用CAN的最重要的部分之一,因為這實際應(yīng)用中我們需要根據(jù)我們實際的場合來選擇 CAN 的波特率。
一般情況下面1M bps 的速率下可以最高可靠傳輸 40 米以內(nèi)的距離。
在 50K 以下的波特率中一般可以可靠傳輸數(shù)公里遠。
對于波特率的設(shè)置需要詳細學(xué)習(xí)參考手冊對應(yīng)部分的解釋。我們在調(diào)試軟件的時候可以使用示波器來測試 CANTX 引腳上的波形的波特率,這樣可以得到事半功倍的效果,大大的縮短調(diào)試學(xué)習(xí)的時間。
// ***************************************************************
// BaudRate = 1 / NominalBitTime
// NominalBitTime = 1tq + tBS1 + tBS2
// tq = (BRP[9:0] + 1) x tPCLK
// tPCLK = CAN's clock = APB1's clock
// ****************************************************************
也就是BaudRate = APB1 / ((BS1 + BS2 + 1) * Prescaler)
這里注意的是采用點的位置,也就時BS1,BS2的設(shè)置問題,這里我也找了一些資料,抄錄下來給大家,是 CANopen 協(xié)議中推薦的設(shè)置。
1Mbps 速率下,采用點的位置在6tq位置處,BS1=5, BS2=2
500kbps 速率下,采用點的位置在8tq位置處,BS1=7, BS2=3
250kbps 速率下,采用點的位置在14tq位置處,BS1=13, BS2=2
125k, 100k, 50k, 20k, 10k 的采用點位置與 250K 相同。
因此我們需要重視的有軟件中的這么幾個部分:
// 設(shè)置 AHB 時鐘(HCLK)
// RCC_SYSCLK_Div1 AHB 時鐘 = 系統(tǒng)時鐘
RCC_HCLKConfig(RCC_SYSCLK_Div8);
// 設(shè)置低速 AHB 時鐘(PCLK1)
// RCC_HCLK_Div2 APB1 時鐘 = HCLK / 2
RCC_PCLK1Config(RCC_HCLK_Div2);
// PLLCLK = 8MHz * 8 = 64 MHz
// 設(shè)置 PLL 時鐘源及倍頻系數(shù)
RCC_PLLConfig(RCC_PLLSource_HSE_Div1, RCC_PLLMul_8);
CAN 波特率設(shè)置中需要的就是PCLK1 的時鐘。
CAN_InitStructure.CAN_Mode=CAN_Mode_LoopBack;
CAN_InitStructure.CAN_SJW=CAN_SJW_1tq;
CAN_InitStructure.CAN_BS1=CAN_BS1_8tq;
CAN_InitStructure.CAN_BS2=CAN_BS2_7tq;
CAN_InitStructure.CAN_Prescaler=5;
通過上面部分的時鐘設(shè)置我們已經(jīng)可以算出我們的波特率了
CAN_bps = PCLK1 / ((1 + 7 + 8) * 5) = 25K bps
大家也可以實際測試中修改時鐘值來通過示波器測試我們需要的波特率是否正確例如將PLLCLK 設(shè)置降低一半:
// PLLCLK = 8MHz * 4 = 32 MHz
// 設(shè)置 PLL 時鐘源及倍頻系數(shù)
RCC_PLLConfig(RCC_PLLSource_HSE_Div1, RCC_PLLMul_4);
那么我們得到的CAN_bps也會降低一半。
接下來還可以修改 HCLK 和 PCLK1 ,其實最終這幾個分頻和倍頻值最終影響的都是 PCLK1。
通過幾次試驗,相信大家應(yīng)該很容易掌握波特率的設(shè)置了。
設(shè)置完波特率我們直接測試函數(shù):
大家可以仿真程序,當(dāng)程序中 Test 等于 Passed 那么說明 Loopback 模式測試通過了。
并且在 CAN 通訊框中我們可以看到發(fā)送和接收到的數(shù)據(jù):
到此時說明如果大家只有一塊CAN模塊的時候?qū)W習(xí)可以告一個段落了,不過這個并不代表大家就已經(jīng)掌握了 CAN 了,正真要掌握它,大家還是需要看大量的 CAN 部分的資料,參考手冊部分的也是不夠的,市面上有幾本專門介紹現(xiàn)場總線和CAN總線的書,推薦大家買來經(jīng)常翻翻看看,這樣到需要實際應(yīng)用的時候才可以做到 如魚得水。
(五) 正常模式
完成了 loopback 模式的測試之后接下來我們需要學(xué)習(xí)的就是多機通訊了,當(dāng)然由于我們的 Mini-STM32 沒有將 CAN 接口引出來, 所以我們沒有辦法在板子上面做這部分的試驗了,只能在 RealView MDK 的軟件中進行模擬。
如果您擁有兩塊帶 CAN 硬件的 STM32 的板子,您需要自己構(gòu)建硬件的物理層的連接, 使用三根線將 CANH,CANL,GND 三根線直連,當(dāng)然你要接好終端電阻才能保證通訊的正常通訊,當(dāng)兩塊板子都跳好后我們使用萬用表測量下 CANH和CANL之間的電阻是否為 60 歐姆。多塊板子多機通訊的是否你只需要在總線的主機端和最后一端接上終端電阻就可以了.
在初始化完成后,軟件應(yīng)該讓硬件進入正常模式,以便正常接收和發(fā)送報文。軟件可以通過對 CAN_MCR 寄存器的INRQ位清 '0',來請求從初始化模式進入正常模式,然后要等待硬件對 CAN_MSR 寄存器的 INAK 位置 '1' 的確認。在跟 CAN 總線取得同步,即在 CANRX 引腳上監(jiān)測到 11 個連續(xù)的隱性位 (等效于總線空閑) 后,bxCAN 才能正常接收和發(fā)送報文。
不需要在初始化模式下進行過濾器初值的設(shè)置,但必須在它處在非激活狀態(tài)下完成 (相應(yīng)的 FACT 位為 '0' ) 。而過濾器的位寬和模式的設(shè)置,則必須在初始化模式中進入正常模式前完成。
準備工作做完我們需要設(shè)置 CAN 通訊部份軟件。