www.久久久久|狼友网站av天堂|精品国产无码a片|一级av色欲av|91在线播放视频|亚洲无码主播在线|国产精品草久在线|明星AV网站在线|污污内射久久一区|婷婷综合视频网站

當前位置:首頁 > 公眾號精選 > 嵌入式云IOT技術圈
[導讀]關于結構體對齊的設置,以GCC 32bit編譯為例,我們可以來看看下面這個例子: #include? ? //默認情況下,結構體一般在內存中的自動對齊格式是4個字節(jié)? ? //結構體設置手動對齊? //如果這里是4,那么下面的打印就是8????? //如果這里是2,那么下面的打

關于結構體對齊的設置,以GCC 32bit編譯為例,我們可以來看看下面這個例子:

#include <stdio.h>
 
//默認情況下,結構體一般在內存中的自動對齊格式是4個字節(jié) 
 
//結構體設置手動對齊 
//如果這里是4,那么下面的打印就是8     
//如果這里是2,那么下面的打印就是6    
//如果這里是1,那么下面的打印就是5 
struct mystu
{
     char a ; 
     int  b ;
};


#pragma pack(4)
struct mystu0
{
     char a ; 
     int  b ;
};
#pragma pack()
 
#pragma pack(2)
struct mystu1
{
     char a ; 
     int  b ;
};
#pragma pack()

#pragma pack(1)
struct mystu2
{
     char a ; 
     int  b ;
};
#pragma pack() 
 
int main(void)
{
     printf("mystu:%d\n",sizeof(struct mystu));
     printf("mystu0:%d\n",sizeof(struct mystu0));
     printf("mystu1:%d\n",sizeof(struct mystu1));
     printf("mystu2:%d\n",sizeof(struct mystu2));
     return 0 ;
}

運行結果:

根據(jù)這樣的原理,在MCU協(xié)議數(shù)據(jù)解析的時候就很有作用了,比如下面這個例子,目前在小車上用:

//結構體,用于存儲解析的數(shù)據(jù)
typedef struct
{
 //幀頭(固定解析為FF)
    uint8_t frame_top ;   
 //版本 A1
    uint8_t version ;
 //方向 01(前進) 02(后退) 03(左轉) 04(右轉)
    uint8_t car_direction ;
 //速度 01(低速檔) 02(中速檔) 03(高速檔)
    uint8_t car_speed ;
 //炮臺 00(回到中間) 01(炮臺左轉) 02(炮臺右轉)
    uint8_t car_fort_status ;
 //夾具 00(夾具夾緊) 01(夾具松開)
 uint8_t car_Fix_status ;
 //幀尾(固定解析為BB)
    uint8_t frame_tail ;
} Protocol;


//以下是串口回調的處理
/**
  * @brief This function handles USART1 global interrupt.
  */
void USART1_IRQHandler(void)
{
    /* USER CODE BEGIN USART1_IRQn 0 */
    /*自定義協(xié)議*/
    /*
     幀頭 版本 方向 速度 炮臺 夾具 幀尾
     ff   A1
    */
    uint8_t Res;

    if((__HAL_UART_GET_FLAG(&huart1, UART_FLAG_RXNE) != RESET))
    {
        HAL_UART_Receive(&huart1, &Res, 1, 1000);

        if(0xBB != Res)
        {
            rbBuf[rx_count++] = Res ;
        }
        else
        {
            rbBuf[rx_count] = 0xBB ;
            //接收到0xBB了,這時候認為已經接收到完整的一幀數(shù)據(jù),將接收標志置1
            Recv_Flag = 1 ;
        }

        /* USER CODE END USART1_IRQn 0 */
        HAL_UART_IRQHandler(&huart1);
        /* USER CODE BEGIN USART1_IRQn 1 */

        /* USER CODE END USART1_IRQn 1 */
    }

    /* USER CODE BEGIN 1 */

    /* USER CODE END 1 */
}
//在主函數(shù)中,進行數(shù)據(jù)解析
int main(void)
{
    HAL_Init();
    SystemClock_Config();
    MX_GPIO_Init();
    MX_USART1_UART_Init();
    while (1)
    {
        if(1 == Recv_Flag)
        {
            Recv_Flag = 0 ;
            //將接收緩沖區(qū)的數(shù)組強制轉換為一個結構體指針
            //通過結構體指針可訪問到每一個協(xié)議規(guī)格的數(shù)據(jù)
            Protocol *Car_Procol = (Protocol *)rbBuf;
            printf("幀頭:0x%x\n", Car_Procol->frame_top);
            printf("版本:0x%x\n", Car_Procol->version);
            printf("方向:0x%x\n", Car_Procol->car_direction);
            printf("速度:0x%x\n", Car_Procol->car_speed);
            printf("炮臺:0x%x\n", Car_Procol->car_fort_status);
            printf("夾具:0x%x\n", Car_Procol->car_Fix_status);
            printf("幀尾:0x%x\n", Car_Procol->frame_tail);
            rx_count = 0 ;
        }
    }
}

從這里可以看到,串口接收的數(shù)據(jù)是一個字節(jié)一個字節(jié)進行接收,所以接收的每個數(shù)據(jù)類型一致,我們就可以直接定義一個結構體,按照協(xié)議定義的順序,將數(shù)據(jù)緩沖區(qū)中的數(shù)據(jù)依次讀取出來。

在小熊派上的運行結果:

我在寫上位機涉及到與MCU進行協(xié)議通信的時候,經常都是這么干的,這個方法不得不說真的超方便。

案例下載

公眾號后臺回復:protocol 即可獲取本節(jié)案例的下載鏈接。

往期精彩

【為宏正名】本應寫入教科書的“世界設定”

【為宏正名】99%人都不知道的"##"里用法

學習嵌入式可以帶娃,不信你們看

ESP8266實戰(zhàn)貼:使用HTTP POST請求上傳數(shù)據(jù)到公有云OneNet

覺得本次分享的文章對您有幫助,隨手點[在看]并轉發(fā)分享,也是對我的支持。

免責聲明:本文內容由21ic獲得授權后發(fā)布,版權歸原作者所有,本平臺僅提供信息存儲服務。文章僅代表作者個人觀點,不代表本平臺立場,如有問題,請聯(lián)系我們,謝謝!

本站聲明: 本文章由作者或相關機構授權發(fā)布,目的在于傳遞更多信息,并不代表本站贊同其觀點,本站亦不保證或承諾內容真實性等。需要轉載請聯(lián)系該專欄作者,如若文章內容侵犯您的權益,請及時聯(lián)系本站刪除。
關閉
關閉