女人自慰AV免费观看内涵网,日韩国产剧情在线观看网址,神马电影网特片网,最新一级电影欧美,在线观看亚洲欧美日韩,黄色视频在线播放免费观看,ABO涨奶期羡澄,第一导航fulione,美女主播操b

0
  • 聊天消息
  • 系統消息
  • 評論與回復
登錄后你可以
  • 下載海量資料
  • 學習在線課程
  • 觀看技術視頻
  • 寫文章/發帖/加入社區
會員中心
創作中心

完善資料讓更多小伙伴認識你,還能領取20積分哦,立即完善>

3天內不再提示

STM32F1的SPI模塊協議介紹

冬至子 ? 來源:ITRelief ? 作者:Sachefgh Xu ? 2023-07-24 15:32 ? 次閱讀

SPI是是一種高速的,全雙工,同步的總線通信方式。STM32F1低中容量設備的SPI模塊支持主從兩種模式。

一、SPI協議介紹

1.硬件連接

SPI使用三條數據總線和一條片選線: MOSI、MISO、SCK、NSS(CS)

MOSI(SDO):主設備輸出/從設備輸入。用于將數據從主機輸出到從機。

MISO(SDI):主設備輸入/從設備輸出。數據經此由從機至主機,主機接收數據。

SCK:時鐘信號線,用于通訊同步。時鐘信號由主機提供

NSS:片選信號線。由主機通過此線使能從機。在一主多從的通訊模式下,只能同時有一個從機被使能。

SPI器件間的連接很簡單,如圖,只要名字相同線相連即可,主也可以比較方便地反轉。

圖片

2.通信時序

SPI傳輸模式的精髓在時鐘極性(CPOL)和時鐘相位(CPHA)

CPOL控制空閑狀態下時鐘總線SCK的電平:

CPOL=0(LOW);時鐘線空閑為低電平

CPOL=1(HIGH);時鐘線空閑為高

CPHA控制采樣位置和信號跳變位置:

圖片

※SPI傳輸從高位(MSB)開始還是低位(LSB)開始可以由用戶設置

二、STM32F1的SPI模塊

1.在CubeMX中進行配置

數據位可選擇8或16

CPHA可選擇從第一個數據沿開始(CPHA=0)或從第二個數據沿開始(CPHA=1)

可選擇高位先發送或是低位先發送

可選擇是否使用NSS以及NSS功能(輸入、輸出用)。用戶也可以用普通IO的中斷輸入/輸出功能模擬NSS,這種方法相對更加靈活。

按照個人開發經驗,SPI一般配置為雙線雙向全雙工情況比較多。

※STM32的 NSS引腳說明和工作極其復雜,建議開發者禁用硬件NSS,自行定義普通GPIO實現片選功能。(NSS腳禁用后可以進行GPIO配置當作普通IO控制實現CS功能)

2.相關寄存器

圖片

圖片

圖片

圖片

圖片

圖片

圖片

圖片

圖片

圖片

圖片

圖片

API:

1.初始化結構體LL_SPI_InitTypeDef

typedef struct
{
  uint32_t TransferDirection;/*
  數據線配置;通過調用LL_SPI_SetTransferDirection()實現;
  @ref:       LL_SPI_FULL_DUPLEX //全雙工,雙線雙向
              LL_SPI_SIMPLEX_RX  //雙線雙向模式下禁止輸出,僅能輸入
              LL_SPI_HALF_DUPLEX_RX //單線,僅能接收
              LL_SPI_HALF_DUPLEX_TX //單線,僅能發送
              ※單線模式下,工作于Master時使用MOSI腳;Slave時為MISO腳
  */
  uint32_t Mode;/*
  設置主從模式,通過LL_SPI_SetMode()實現;
  @ref:       LL_SPI_MODE_MASTER //主模式,配置時若NSS由軟件管理會將電平置高
              LL_SPI_MODE_SLAVE
  */
  uint32_t DataWidth;/*
  設置數據長度;通過LL_SPI_SetDataWidth()實現;
  @ref:       LL_SPI_DATAWIDTH_8BIT  //8位
              LL_SPI_DATAWIDTH_16BIT  //16位
  */
  uint32_t ClockPolarity;/*
  設置時鐘極性(CPOL),通過LL_SPI_SetClockPolarity()實現
  @ref:       LL_SPI_POLARITY_LOW //低電平(CPOL=0)
              LL_SPI_POLARITY_HIGH  //高電平(CPOL=1)
  */
  uint32_t ClockPhase;/*
  設置時鐘相位,通過LL_SPI_SetClockPhase()實現
  @ref:       LL_SPI_PHASE_1EDGE //CPHA =0
              LL_SPI_PHASE_2EDGE //CPHA=1
  */
  uint32_t NSS;/*
  配置NSS(CS),通過LL_SPI_SetNSSMode()實現;
  @ref:       LL_SPI_NSS_SOFT //通過軟件管理NSS;※此時NSS引腳無法進行I/O操作控制
                 //CubeMx配置為Disable時配置為此模式(相當于禁用了NSS)
                 //此時可以通過操作SPI_CR1- >SSI位控制該位電平;LL庫未提供函數;
              LL_SPI_NSS_HARD_INPUT //說不清除,手冊和庫函數說明沖突,建議不用
              LL_SPI_NSS_HARD_OUTPUT//同樣,不建議配置
              //鑒于片選復雜性,推薦開發者直接通過GPIO直接模擬NSS(CS)功能,可用原NSS
  */
  uint32_t BaudRate;/*
  配置波特率分頻,通過LL_SPI_SetBaudRatePrescaler()實現;
  @ref:        LL_SPI_BAUDRATEPRESCALER_DIVx //x2^n,max=128
*/
  uint32_t BitOrder;/*
  配置發送位順序,通過LL_SPI_SetTransferBitOrder()實現;
  @ref:      LL_SPI_LSB_FIRST  //低位先
             LL_SPI_MSB_FIRST  //高位先
  */
  uint32_t CRCCalculation;/*!< Specifies if the CRC calculation is enabled or not.
  This parameter can be a value of @ref SPI_LL_EC_CRC_CALCULATION.
This feature can be modified afterwards using unitary functions @ref LL_SPI_EnableCRC() and @ref LL_SPI_DisableCRC().*/

  uint32_t CRCPoly;/*!< Specifies the polynomial used for the CRC calculation.
This parameter must be a number between Min_Data = 0x00 and Max_Data = 0xFFFF.
 This feature can be modified afterwards using unitary function @ref LL_SPI_SetCRCPolynomial().*/
} LL_SPI_InitTypeDef;

2.初始化函數

ErrorStatus LL_SPI_Init(SPI_TypeDef *SPIx, LL_SPI_InitTypeDef *SPI_InitStruct);/*
初始化SPI;
*/
void LL_SPI_StructInit(LL_SPI_InitTypeDef *SPI_InitStruct)/*
初始化SPI配置結構體
*/
ErrorStatus LL_SPI_DeInit(SPI_TypeDef *SPIx)/*
初始化SPI模塊
*/

3.開啟/關閉模塊

__STATIC_INLINE void LL_SPI_Enable(SPI_TypeDef *SPIx);/*
開啟SPI模塊
*/
__STATIC_INLINE void LL_SPI_Disable(SPI_TypeDef *SPIx);/*
關閉SPI模塊
*/
__STATIC_INLINE uint32_t LL_SPI_IsEnabled(SPI_TypeDef *SPIx);/*
檢測開啟狀態
*/

※與UART不同,目前版本CubeMX自動生成代碼不會開啟SPI,需用戶手動開啟

關閉SPI需要在傳輸完成后

4.標志位/狀態位

圖片

MODF:主模式失效錯誤標志。在NSS引腳硬件模式管理下,主設備的NSS腳被拉低時;或者在NSS引腳軟件模式管理下,SSI位被置0時被置位。同時SPI模塊被關閉。 在使用LL庫時若不使用NSS功能,則不會出現置位情況

※RXNE:接收緩沖非空。與USART類似,當※接收數據寄存器完全完成一次數據接收時,該位被置位。※對讀取數據寄存器RDR的讀取操作可以硬件清零該位。

※TXE:發送緩沖空。當發送數據寄存器數據被送出時,該位被置位。對發送數據寄存器TDR的寫入操作可以硬件清零該位。

BSY:忙標志。SPI在通訊時該位為1。該位完全由硬件控制。在主模式的雙向接收模式下 (MSTR=1、BDM=1并且BDOE=0),在接收期間BSY標志保持為低。不要使用BSY標志處理每一個數據項的發送和接收,最好使用TXE和RXNE標志。

OVR:溢出錯誤。接收數據時,當發送端設備已經發送了數據字節,而STM32還沒有清除前一個數據字節產生的RXNE時,即為溢出錯誤。

當溢出時,讀SPI_DR寄存器返回的是之前未讀的數據,所有隨后傳送的數據都被丟棄。

※與USART不同,SPI模塊TXE與RXNE位是只讀的,其值由硬件管理。

__STATIC_INLINE uint32_t LL_SPI_IsActiveFlag_BSY(SPI_TypeDef *SPIx);/*
檢測BSY是否置位,該位無法軟件控制
*/
__STATIC_INLINE uint32_t LL_SPI_IsActiveFlag_OVR(SPI_TypeDef *SPIx);/*
檢測OVR是否置位(發生過載錯誤)
*/
__STATIC_INLINE void LL_SPI_ClearFlag_OVR(SPI_TypeDef *SPIx);/*
置位OVR
*/
__STATIC_INLINE uint32_t LL_SPI_IsActiveFlag_TXE(SPI_TypeDef *SPIx);/*
檢測TXE是否置位
*/
__STATIC_INLINE uint32_t LL_SPI_IsActiveFlag_RXNE(SPI_TypeDef *SPIx);/*
檢測RXNE是否置位
*/
__STATIC_INLINE uint32_t LL_SPI_IsActiveFlag_MODF(SPI_TypeDef *SPIx);
__STATIC_INLINE void LL_SPI_ClearFlag_MODF(SPI_TypeDef *SPIx);

5.中斷控制

__STATIC_INLINE void LL_SPI_EnableIT_ERR(SPI_TypeDef *SPIx);/*
使能ERR錯誤中斷*/
__STATIC_INLINE void LL_SPI_DisableIT_ERR(SPI_TypeDef *SPIx);/*
禁用ERR錯誤中斷*/
__STATIC_INLINE uint32_t LL_SPI_IsEnabledIT_ERR(SPI_TypeDef *SPIx);/*
檢測是否開啟ERR中斷*/

__STATIC_INLINE void LL_SPI_EnableIT_RXNE(SPI_TypeDef *SPIx);/*
使能RXNE接收緩沖非空中斷*/
__STATIC_INLINE void LL_SPI_DisableIT_RXNE(SPI_TypeDef *SPIx);/*
禁用RXNE接收緩沖非空中斷*/
__STATIC_INLINE uint32_t LL_SPI_IsEnabledIT_RXNE(SPI_TypeDef *SPIx)/*
檢測是否開啟RXNE接收緩沖非空中斷*/

__STATIC_INLINE void LL_SPI_EnableIT_TXE(SPI_TypeDef *SPIx);/*
使能TXE發送緩沖空中斷*/
__STATIC_INLINE void LL_SPI_DisableIT_TXE(SPI_TypeDef *SPIx);/*
禁用TXE發送緩沖空中斷*/
__STATIC_INLINE uint32_t LL_SPI_IsEnabledIT_TXE(SPI_TypeDef *SPIx)/*
檢測是否開啟TXE發送緩沖空中斷*/

6.SPI 收/發函數

__STATIC_INLINE uint8_t LL_SPI_ReceiveData8(SPI_TypeDef *SPIx);/*
從接收寄存器(緩沖區)DR中讀取8位數據;
*/
__STATIC_INLINE uint16_t LL_SPI_ReceiveData16(SPI_TypeDef *SPIx);/*
從接收寄存器(緩沖區)DR中讀取16位數據;
*/

__STATIC_INLINE void LL_SPI_TransmitData8(SPI_TypeDef *SPIx, uint8_t TxData);/*
向發送寄存器(緩沖區)DR中寫入8位數據
*/
__STATIC_INLINE void LL_SPI_TransmitData16(SPI_TypeDef *SPIx, uint16_t TxData);/*
向發送寄存器(緩沖區)DR中寫入16位數據
*/

SPI模塊DMA的使用

相關函數:

待實驗

__STATIC_INLINE void LL_USART_EnableDMAReq_RX(USART_TypeDef *SPIx);/*
使能接收DMA,啟用后DR有數據時將允許發送DMA請求;具體見示例用法*/
__STATIC_INLINE void LL_USART_DisableDMAReq_RX(USART_TypeDef *SPIx);/*
禁用接收DMA*/
__STATIC_INLINE uint32_t LL_USART_IsEnabledDMAReq_RX(USART_TypeDef *SPIx);/*
檢測是否使能接收DMA*/

__STATIC_INLINE void LL_USART_EnableDMAReq_TX(USART_TypeDef *SPIx);/*
使能發送DMA*/
__STATIC_INLINE void LL_USART_DisableDMAReq_TX(USART_TypeDef *SPIx);/*
禁用發送DMA*/
__STATIC_INLINE uint32_t LL_USART_IsEnabledDMAReq_TX(USART_TypeDef *SPIx);/*
檢測是否使能發送DMA*/
/**************************************************/
__STATIC_INLINE uint32_t LL_USART_DMA_GetRegAddr(USART_TypeDef *SPIx);/*
返回SPI模塊數據寄存器DR地址;無論是否啟用DMA均可用
*/

發送時,在每次TXE被設置為’1’時發出DMA請求,此時軟件控制DMA寫數據至SPI_DR寄存器,TXE標志因此而被清除。

接收時,在每次RXNE被設置為’1’時發出DMA請求,在開啟情況下DMA控制器從SPI_DR寄存器讀出數據,RXNE標志因此而被清除。

LL的DMA使用與UART相似,可以參考之前的文章。

SPI在雙向全雙工傳輸數據的時候,每發出一字節數據的同時也會接收一字節數據,因此在作為主機接收的時候,應當考慮 如何處理接收到的無用數據。否則會出現OVR。

另外,由于在雙向模式下配置為主機時,只有當SPI在寫數據時時鐘信號才能產生。處于master工作模式下,SPI的時鐘只有在往DR寄存器里面寫數據的時候才會產生,讀是不會產生的。所以要讀取slave shift out的數據,master必須先發一個“DUMMY”數據以產生時鐘。

建議配置STM32為雙向主機、從機; 配置為主機接收前讀取一次DR,再發送DUMMY(建議發0x00或0xFF,不要增加沒必要的干擾)

聲明:本文內容及配圖由入駐作者撰寫或者入駐合作網站授權轉載。文章觀點僅代表作者本人,不代表電子發燒友網立場。文章及其配圖僅供工程師學習之用,如有內容侵權或者其他違規問題,請聯系本站處理。 舉報投訴
  • 數據寄存器
    +關注

    關注

    0

    文章

    33

    瀏覽量

    7966
  • SPI接口
    +關注

    關注

    0

    文章

    262

    瀏覽量

    35264
  • CPHA
    +關注

    關注

    0

    文章

    8

    瀏覽量

    9487
  • USART串口
    +關注

    關注

    0

    文章

    32

    瀏覽量

    7024
  • stm32f1
    +關注

    關注

    1

    文章

    58

    瀏覽量

    12438
收藏 人收藏

    評論

    相關推薦
    熱點推薦

    STM32F1的I2C模塊協議簡介

    I2C是一種多主從的串行通訊協議STM32F1的I2C模塊支持標速(最高100kHz)和高速(最高400kHz)兩種工作模式。
    發表于 07-25 14:49 ?4972次閱讀
    <b class='flag-5'>STM32F1</b>的I2C<b class='flag-5'>模塊</b><b class='flag-5'>協議</b>簡介

    STM32F1的MPU6050模塊軟件卡爾曼濾波資料

    STM32F1的MPU6050模塊軟件卡爾曼濾波資料
    發表于 11-13 14:54 ?25次下載

    STM32F1系列的HAL庫手冊免費下載

    本文檔的主要內容詳細介紹的是STM32F1系列單片機的HAL庫手冊免費下載。
    發表于 11-19 14:36 ?477次下載
    <b class='flag-5'>STM32F1</b>系列的HAL庫手冊免費下載

    STM32F1的固件庫免費下載

    本文檔的主要內容詳細介紹的是STM32F1的固件庫免費下載。
    發表于 12-26 17:22 ?156次下載
    <b class='flag-5'>STM32F1</b>的固件庫免費下載

    STM32F1系列芯片中文參考手冊

    STM32F1系列芯片中文參考手冊(嵌入式開發培訓教程)-STM32F1系列芯片的中文用戶手冊
    發表于 07-30 09:32 ?218次下載
    <b class='flag-5'>STM32F1</b>系列芯片中文參考手冊

    STM32F1官方手冊資料(中英文)

    STM32F1官方手冊資料(中英文)
    發表于 11-05 16:28 ?69次下載

    STM32F1F4的區別

    STM32F1F4的區別
    發表于 12-04 13:51 ?24次下載
    <b class='flag-5'>STM32F1</b>和<b class='flag-5'>F</b>4的區別

    STM32F1 & SHT3x溫濕度模塊

    STM32F1 & SHT3x溫濕度模塊提示:以下程序是基于STM32F103和SHT3x系列硬件文章目錄STM32F1 & SHT3x溫濕度
    發表于 12-04 18:36 ?34次下載
    <b class='flag-5'>STM32F1</b> & SHT3x溫濕度<b class='flag-5'>模塊</b>

    STM32F1雙DMA提高串口速度

    STM32F1雙DMA,提高串口速度
    發表于 09-26 16:11 ?5次下載

    AN3422_從STM32F1移植到STM32L1的應用手冊

    AN3422_從STM32F1移植到STM32L1的應用手冊
    發表于 11-21 17:06 ?4次下載
    AN3422_從<b class='flag-5'>STM32F1</b>移植到<b class='flag-5'>STM32L1</b>的應用手冊

    AN3427_從STM32F1移植到STM32F2的應用手冊

    AN3427_從STM32F1移植到STM32F2的應用手冊
    發表于 11-21 17:06 ?10次下載
    AN3427_從<b class='flag-5'>STM32F1</b>移植到<b class='flag-5'>STM32F</b>2的應用手冊

    AN4904_從STM32F1STM32F4的軟件移植

    AN4904_從STM32F1STM32F4的軟件移植
    發表于 11-21 17:06 ?4次下載
    AN4904_從<b class='flag-5'>STM32F1</b>到<b class='flag-5'>STM32F</b>4的軟件移植

    UM1847_基于STM32F1系列的STM32CubeF1軟件庫使用入門

    UM1847_基于STM32F1系列的STM32CubeF1軟件庫使用入門
    發表于 11-22 08:22 ?4次下載
    UM1847_基于<b class='flag-5'>STM32F1</b>系列的<b class='flag-5'>STM32CubeF1</b>軟件庫使用入門

    AN2629 STM32F1低功耗模式

    AN2629 STM32F1低功耗模式
    發表于 11-24 08:30 ?0次下載
    AN2629 <b class='flag-5'>STM32F1</b>低功耗模式

    單片機STM32F1資料分享

    單片機STM32F1資料分享
    發表于 05-16 18:04 ?16次下載