日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

MSP430 LIN总线编程

發布時間:2024/3/7 编程问答 59 豆豆
生活随笔 收集整理的這篇文章主要介紹了 MSP430 LIN总线编程 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?MSP430 LIN總線編程

? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?Lis, 2021-2-3

? ? ?時隔接近20年,CSDN我回來了...以下為本人原創. 如轉載,請注明出處!

? ? ? LIN總線在汽車領域應用十分的廣泛。汽車上的油泵,自動折疊反光鏡,大燈,鎖等等慢速通信都會有LIN總線的應用身影。但網絡上你幾乎找不到MSP430在這方面的應用,就算去TI的官方網站上去找,去問客服,也找不到,MSP430似乎沒有車規級型號,新能源汽車上幾乎清一色的使用TI的DSP車規級芯片,所以也基本沒有人在MSP430上使用LIN總線。但是掌握LIN總線的應用,會給我們在一些項目里帶來很大的幫助。至于什么是LIN,什么CAN這些的術語,大家自己百度應該可以找到很詳細介紹,這里不做過多的說明。

? ? ?以下是我做的一些筆記,為了避免重復勞動,浪費時間,就直接截圖上來了。

[1] LIN總線特點

[二]物理層連接

[三]接口電路

? ?這里我選擇了最小封裝的TJA1027,8腳芯片,以下為LIN master模式的配置電路。 詳細關于TJA1027請自行網上找它的datasheet

[四]LIN-BUS的幀格式

Break長度一般為為13位,我們稱之為:間隔場.(參考網上的一張比較不錯的圖)

示波下的真實waveform:

邏輯分析儀下的 讀某品牌油泵的時序:

[五]MSP430F24X下的LIN BUS配置

?這里我使用MSP430F249為例,UART模塊,需支持SCI功能。才可以支持LIN,所以不是所有的MSP430系列都支持LIN總線,查看Datasheet是最有效的方式。

  • 在Slave 模式下,UART需支持自動波特率檢測(在一些特定標準下,波特率是特定的)
  • UART=8 bit,LSB優先,無奇偶位,1停止位 。 這點和普通的串口單元設置基本一樣
  • 接口驅動芯片,這里我選用的是TJA1027,實現通信電平上面的轉換
  • 主模式: 自動生成間隔場(break)和同步碼(synch)
  • 選擇自動波特率檢測模式? UCTXBRK=1
  • DELIMx指定 break Delimiter的長度,默認為1位周期
  • 檢測TXBUF是否準備就緒,并向TXBUF寫入同步碼 0x55h
  • 傳輸13位間隔場后,然后就是break delimiter 和synch 同步場,UCTXBRK在同步載入TX移位寄存器后自動重設,寫入TXBUF的數據正常傳輸
  • [六]代碼部分

    ? 1.PID部分:ID只是高6個位,后兩個位為奇偶效驗碼.

    //---------------------------------------------------------------------------// // uchar LIN_GetPID(uchar id) // //Description: calculate odd and even parity for ID Frame // // ? Parity: // // ? ? ? ? ? ? P0= id0^id1^id2^id4 ? ==>Even ?bit6 // // ? ? ? ? ? ? p1=~(id1^id3^id4^id5) ? ?==>Odd ? bit7 // //---------------------------------------------------------------------------// uchar LIN_GetPID(uchar id) {uchar parity=0, p0,p1;p0 =id;p0^=id>>1;p0^=id>>2;p0^=id>>4;p0&=0x01;p1 =id>>1;p1^=id>>3;p1^=id>>4;p1^=id>>5;p1=~p1;p1&=0x01;parity=id|(p0<<6)|(p1<<7);return parity; }

    2.checksum

    LIN總線中的checksum算法為帶進位的累加。 在LIN總線里,有兩種校驗方式,一種稱為標準驗校,和增強型校驗。 代碼中我做了相關的說明。

    //---------------------------------------------------------------------------// // calculate checksum // //paremeters: uchar id: slaver id // // uchar *data array of data,maximum:8 bytes // // uchar len length of the data array // //---------------------------------------------------------------------------// uchar LIN_Checksum(uchar id,uchar *data,uchar len) {uint16 sum = 0;uchar i;//if it's not a diagnostic package | id==0x3c using normal checksum,otherwise using enhance checksum if (id!=0x3c) {sum=LIN_GetPID(id);}for(i = 0; i < len; i++){sum +=data[i];if(sum&0xff00){sum&=0x00ff;sum+=1;} }sum=~sum;return (uchar)sum; }

    3.添加發送間隔場和同步場

    我在代碼中加了宏代碼,以方便我配置LIN端口使用UART0 或UART1

    //----------------------------------------------------------------------------// // void USART_UCA0_Send_Byte(uchar data) //----------------------------------------------------------------------------// void USART_UCA0_Send_Byte(uchar data) {UCA0TXBUF = data;while(!Get_Bit(UC0IFG,UCA0TXIFG)); }//---------------------------------------------------------------------------// // LIN_Send_Break_Sync(void) // //---------------------------------------------------------------------------// void LIN_Send_Break_Sync(void) {UCA0CTL0_bit.UCMODE0=1;UCA0CTL0_bit.UCMODE1=1;//4bit stopUCA0ABCTL_bit.UCDELIM0=1;UCA0ABCTL_bit.UCDELIM1=1;UCA0CTL1_bit.UCTXBRK=1;USART_UCA0_Send_Byte(0x55);UCA0CTL1_bit.UCTXBRK=0; } 4.一個完整幀的發送: //---------------------------------------------------------------------------// // LIN_Sendbuf // // // //paremeters: uchar id: slaver id // // uchar *data array of data,maximum:8 bytes // // uchar len length of the data array // //---------------------------------------------------------------------------// void LIN_Sendbuf(uchar id,uchar *data,uchar len) {uchar check_sum, parity_id;uint16 i;LIN_Send_Break_Sync();parity_id=LIN_GetPID(id);USART_UCA0_Send_Byte(parity_id);for(i=0;i<len;i++){ USART_UCA0_Send_Byte(data[i]);} check_sum=LIN_Checksum(id,data,len);USART_UCA0_Send_Byte(check_sum); }

    5.發送讀操作幀

    //---------------------------------------------------------------------------// // void LIN_RX_Ask(uchar id) // // // //definition: Send Syn frame to slaver, Slaver will send back the data // //parameter: uchar id // //---------------------------------------------------------------------------// void LIN_RX_Ask(uchar id) {uchar parity_id;LIN_RX_Idx=0;LIN_Send_Break_Sync();parity_id=LIN_GetPID(id);USART_UCA0_Send_Byte(parity_id); }

    如這里的時序,master端發送Ask(break+sync+PID),然后slave同步并返回數據幀。 這個比較容易理解,類似于I2C,SPI,1 wire 總線。

    6.接收處理: 將接收處理部分寫成單獨的函數,然后放到串口接收中斷中 //----------------------------------------------------------------------------// // void USART_UCA0_Send_Byte(uchar data) //----------------------------------------------------------------------------// void USART_UCA0_Send_Byte(uchar data) {UCA0TXBUF = data;while(!Get_Bit(UC0IFG,UCA0TXIFG)); }//---------------------------------------------------------------------------// // void LIN_Readbuf_Pro(uchar data) // // put this function into RX intterruption // //---------------------------------------------------------------------------// void LIN_Readbuf_Pro(uchar data) {switch(LIN_RX_Idx){case 0:if(data==0x55){LIN_RX_Idx=1;} break;case 1:LIN_RX_Frame.id=data&0x3F;LIN_RX_Idx=2;break;case 2:case 3:case 4:case 5:case 6:case 7:case 8:case 9:LIN_RX_Frame.d[LIN_RX_Idx-2]= data;LIN_RX_Idx++;break;case 10: LIN_RX_Frame.chksum=data;LIN_RX_Idx=0;break;} }

    串口接收中斷:

    //----------------------------------------------------------------------------// // USCI0RX_ISR UCA0 Interruption //----------------------------------------------------------------------------// #pragma vector=USCIAB0RX_VECTOR __interrupt void USCI0RX_ISR(void) {uchar data=0;data = UCA0RXBUF;// if (UC0IFG&UCA0RXIFG) // {LIN_Readbuf_Pro(data); // } }

    7.串口設置

    #define BAUD_UCA0 10417//----------------------------------------------------------------------------// uchar Get_UCBRS(float baud) {return ((uchar)((baud-(uint16)baud)*8+0.5))<<1; }//----------------------------------------------------------------------------// // void Init_Serial_Ports(void) //----------------------------------------------------------------------------// void Init_Serial_Ports(void) {float tmp_baud;SetPinMode(UCA0_TXD_PIN);SetPinMode(UCA0_RXD_PIN); tmp_baud=CPU_F/2/BAUD_UCA0;UCA0CTL1 |= UCSSEL_2 + UCSWRST; //Set the clock of UCA0 =SMCL,UCSWRST Enable,initial all USCI registors UCA0BR0 =(uchar)(tmp_baud); //Low 8 bitsUCA0BR1 =(uchar)((uint16)tmp_baud>>8); // //High 8bits, NO parity check UCA0MCTL = Get_UCBRS(tmp_baud);UCA0CTL1 &= ~UCSWRST; //clear UCSWRST bitUC0IE |= UCA0RXIE; //Enable RX Interruptor }

    [7]測試板電路設計

    ? ? [1]電源部分

    ? ? ? ? ? ?先設計打算使用于24V電路,所以輸入端,和LIN總線電壓為24V,但是實際應用調試的油泵為12V,所以主供電也為12V。 這里做個說明.?

    ?

    ?[2]MSP430部分相對簡單,最小系統,然后把端口都引出去

    [3]LIN接口電路

    [4]調試用TTL串行口電路

    ? ?增加緩沖電路,能有效加強TTL串口的可靠,穩定性。

    [5]電路指示

    [6]預留的一個大功率IO驅動口,用于驅動外部電磁閥等器件

    [7]Layout

    ? ? 根據schematic,布好PWB后,生成工藝文件以及BOM發給PCB工廠進行打樣生產。

    [8]實際調試,正常驅動某品牌汽車油泵

    總結

    以上是生活随笔為你收集整理的MSP430 LIN总线编程的全部內容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。