電子產(chǎn)業(yè)一站式賦能平臺(tái)

PCB聯(lián)盟網(wǎng)

搜索
查看: 74|回復(fù): 0
收起左側(cè)

嵌入式經(jīng)常用到串口,如何判斷串口數(shù)據(jù)接收完成?

[復(fù)制鏈接]

485

主題

485

帖子

1623

積分

三級(jí)會(huì)員

Rank: 3Rank: 3

積分
1623
跳轉(zhuǎn)到指定樓層
樓主
發(fā)表于 2024-12-1 17:50:00 | 只看該作者 |只看大圖 回帖獎(jiǎng)勵(lì) |倒序?yàn)g覽 |閱讀模式
我是老溫,一名熱愛(ài)學(xué)習(xí)的嵌入式工程師
1 \- V: K- H3 l" s* o  O0 Q* C. L關(guān)注我,一起變得更加優(yōu)秀!說(shuō)起通信,首先想到的肯定是串口,日常中232和485的使用比比皆是,數(shù)據(jù)的發(fā)送、接收是串口通信最基礎(chǔ)的內(nèi)容。這篇文章主要討論串口接收數(shù)據(jù)的斷幀操作?臻e中斷斷幀一些mcu(如:stm32f103)在出廠時(shí)就已經(jīng)在串口中封裝好了一種中斷——空閑幀中斷,用戶可以通過(guò)獲取該中斷標(biāo)志位來(lái)判斷數(shù)據(jù)是否接收完成,中斷標(biāo)志在中斷服務(wù)函數(shù)中獲取,使用起來(lái)相對(duì)簡(jiǎn)單。void UART4_IRQHandler(void)
% p1 N0 V9 j' X{$ i0 _5 H! ~: h9 ]6 m" y
    uint8_t data = 0;
9 f. T+ t2 c# b, q4 M7 v% _9 v    data = data;6 c& i! U8 t7 s% Y* b* s
    if(USART_GetITStatus(LoraUSARTx, USART_IT_RXNE) == SET)
2 z9 E2 v, h/ O    {
6 H2 ?, h9 ?: G( i$ {        USART_ClearITPendingBit(LoraUSARTx, USART_IT_RXNE);
0 b7 L& Y$ t9 H- R, m4 |4 h        if(Lora_RecvData.Rx_over == 0)/ h! H! L  c! {( ~& g6 J! \
            Lora_RecvData.RxBuf[Lora_RecvData.Rx_count++] = LoraUSARTx->DR;
/ I. D: F9 V  i& Y    }$ ~# [1 Q) _+ W* _  K0 _
    if(USART_GetITStatus(LoraUSARTx, USART_IT_IDLE) == SET)! b% ~" x) Y4 E/ x  V( c; \
    {% A& l3 @' w; I# Y3 R
        data = LoraUSARTx->SR;
4 a! ?0 u  b) d- k" f/ s* ]        data = LoraUSARTx->DR;- W* F5 O5 Q) {9 K
        
+ v' H/ P7 @$ l4 W4 s        Lora_RecvData.Rx_over = 1; //接收完成4 @5 X9 l1 r5 R
    }: X( W! G# U9 Q( {# [% r
}例程中,當(dāng)接收完成標(biāo)志 Lora_RecvData.Rx_over 為1時(shí),就可以獲取 uart4 接收到的一幀數(shù)據(jù),該數(shù)據(jù)存放在 Lora_RecvData.RxBuf 中。5 N% |% \2 H" D  B9 s5 t
超時(shí)斷幀空閑幀中斷的使用固然方便,但是并不是每個(gè)mcu都有這種中斷存在(只有個(gè)別高端mcu才有),那么這個(gè)時(shí)候就可以考慮使用超時(shí)斷幀了。6 M2 v* c  k, n% u
Modbus協(xié)議中規(guī)定一幀數(shù)據(jù)的結(jié)束標(biāo)志為3.5個(gè)字符時(shí)長(zhǎng),那么同樣的可以把這種斷幀方式類(lèi)比到串口的接收上,這種方法需要搭配定時(shí)器使用。
9 o4 Z/ q/ I) ?其作用原理就是:串口進(jìn)一次接收中斷,就打開(kāi)定時(shí)器超時(shí)中斷,同時(shí)裝載值清零(具體的裝載值可以自行定義),只要觸發(fā)了定時(shí)器的超時(shí)中斷,說(shuō)明在用戶規(guī)定的時(shí)間間隔內(nèi)串口接收中斷里沒(méi)有新的數(shù)據(jù)進(jìn)來(lái),可以認(rèn)為數(shù)據(jù)接收完成。! b! J5 I" W3 [" B% r
uint16_t Time3_CntValue = 0;//計(jì)數(shù)器初值
" ?: g  d6 Q4 k4 R; J
. H9 \6 Y- [* m: q4 W7 u% R/*******************************************************************************3 V, g% i  J8 }; [3 w% h
* TIM3中斷服務(wù)函數(shù)
! H4 p, a$ p$ @/ E ******************************************************************************/3 B* `$ k0 G8 N6 A$ q& h
void Tim3_IRQHandler(void)5 r! F" m  ~! K( \3 u. ]. K' l
{
- y9 L8 U3 D2 y. {    if(TRUE == Tim3_GetIntFlag(Tim3UevIrq))& @1 B7 E) I+ X
    {1 l7 M5 j9 q9 S' O- o4 u# f
        Tim3_M0_Stop();    //關(guān)閉定時(shí)器34 G; i' P# u/ N% y/ ]4 U
        Uart0_Rec_Count = 0;//接收計(jì)數(shù)清零% a8 l1 R/ P# ~
        Uart0_Rec_Flag = 1; //接收完成標(biāo)志
: G9 k1 ~' [) g! X4 f        Tim3_ClearIntFlag(Tim3UevIrq); //清除定時(shí)器中斷3 G9 }+ z5 {! X
    }6 y. U# S5 }/ G0 w  E# b
}
, S/ N( r" r7 W( \& C2 T- o) S : a8 y9 X' ]: s; z( C. x9 e
void Time3_Init(uint16_t Frame_Spacing)
( j! {( E- ]4 x; C) F4 n{
  a8 e& L9 L  H+ |    uint16_t u16ArrValue;//自動(dòng)重載值  G3 F' H% o2 u' s  o# @2 e; g
    uint32_t u32PclkValue;//PCLK頻率" A3 `" U. u( r, e; w
   
% o3 s# x2 V- U: m. Q    stc_tim3_mode0_cfg_t     stcTim3BaseCfg;
/ ]( r# }, ]4 R9 ^( N/ U   
9 a8 C+ e% _# }( R( t    //結(jié)構(gòu)體初始化清零
2 ^. i9 d5 o* t5 x    DDL_ZERO_STRUCT(stcTim3BaseCfg);
- k+ [8 J& `+ Z, F& b    1 s2 W2 w* R; t6 I6 t, V
    Sysctrl_SetPeripheralGate(SysctrlPeripheralTim3, TRUE); //Base Timer外設(shè)時(shí)鐘使能
9 Q  y4 t& {9 C   
$ B( ~9 H5 x3 S) o2 o& c    stcTim3BaseCfg.enWorkMode = Tim3WorkMode0;              //定時(shí)器模式
0 e5 G+ W# T1 j) A$ G+ l    stcTim3BaseCfg.enCT       = Tim3Timer;                  //定時(shí)器功能,計(jì)數(shù)時(shí)鐘為內(nèi)部PCLK
1 I5 |' v4 n7 |4 s    stcTim3BaseCfg.enPRS      = Tim3PCLKDiv1;               //不分頻4 v/ l& c4 D1 M6 |+ Z# p! J
    stcTim3BaseCfg.enCntMode  = Tim316bitArrMode;           //自動(dòng)重載16位計(jì)數(shù)器/定時(shí)器
4 k6 y/ A- ^0 ]    stcTim3BaseCfg.bEnTog     = FALSE;8 l8 l' b8 S' B, Y
    stcTim3BaseCfg.bEnGate    = FALSE;) S0 r  h7 r9 |1 z( T8 _' Y4 m; D
    stcTim3BaseCfg.enGateP    = Tim3GatePositive;
" y0 t" x( J$ G! a6 Z2 B- o    - F4 v5 c! I( I  g& R- z
    Tim3_Mode0_Init(&stcTim3BaseCfg);             //TIM3 的模式0功能初始化- h- Z# Q8 C; @) D" W$ E: `8 B' k+ z
        ; w( B% }+ z. v/ ~6 k0 l& X
    u32PclkValue = Sysctrl_GetPClkFreq();          //獲取Pclk的值/ Q: y  M0 C0 Y9 O" d4 S  l
   //u16ArrValue = 65535-(u32PclkValue/1000);      //1ms測(cè)試7 e% w0 j7 l% e5 c- m3 _  o& u( S5 H
    u16ArrValue = 65536 - (uint16_t)((float)(Frame_Spacing*10)/RS485_BAUDRATE*u32PclkValue);//根據(jù)幀間隔計(jì)算超時(shí)時(shí)間
* _# l" z5 g3 q    Time3_CntValue = u16ArrValue;             //計(jì)數(shù)初值
1 M7 ^4 Z5 ^0 {: V+ a2 k: |1 Z! [    Tim3_M0_ARRSet(u16ArrValue);              //設(shè)置重載值
# J- B" |! D% `" f    Tim3_M0_Cnt16Set(u16ArrValue);            //設(shè)置計(jì)數(shù)初值
, J: L* i5 I+ f. Y4 q1 r, i% q7 d    0 I& Y* @. I2 [, T; B
    Tim3_ClearIntFlag(Tim3UevIrq);            //清中斷標(biāo)志" J9 N6 O  H  M, j2 f
    Tim3_Mode0_EnableIrq();                   //使能TIM3中斷(模式0時(shí)只有一個(gè)中斷)
& o6 U( W+ e  |4 z, i    EnableNvic(TIM3_IRQn, IrqLevel3, TRUE);   //TIM3 開(kāi)中斷  ' I! [9 u' A/ a. n1 u7 \: l
}
  M; u8 E; ], |! @9 {3 k, V ! F5 o6 v+ y: O3 u6 W
/**************************此處省略串口初始化部分************************/& S$ {  K" |, Y* `# {/ F* w
//串口0中斷服務(wù)函數(shù)  }6 X8 I3 p# |) t3 N
void Uart0_IRQHandler(void)% u, \5 l+ {/ }9 D) l0 D! }
{1 u2 R* s( q/ q, K+ z* y
    uint8_t rec_data=0;
6 `- P( R$ O/ S' G( r8 V- P$ t    % g* u; ]3 C- H% h6 S
    if(Uart_GetStatus(M0P_UART0, UartRC))         $ w' P5 B# t' G- N
    {
" c, o7 u" C/ b9 }) \. t- u        Uart_ClrStatus(M0P_UART0, UartRC);        9 U  P$ _+ c; v/ z
        rec_data = Uart_ReceiveData(M0P_UART0);     
* S1 d* J: D4 l/ C6 c5 P        if(Uart0_Rec_Count[U]//幀長(zhǎng)度
5 J* [( R8 n: ?, [9 _        {
7 s: P% j+ ?. w7 @. \/ d            Uart0_Rec_Buffer[Uart0_Rec_Count++] = rec_data;        % e: o8 v- o2 t; l0 q2 b
        }6 w' S1 P: x+ D2 q+ W
        Tim3_M0_Cnt16Set(Time3_CntValue);//設(shè)置計(jì)數(shù)初值 : A" }: A2 J* z& ]8 W  ~2 C
        Tim3_M0_Run();   //開(kāi)啟定時(shí)器3 超時(shí)即認(rèn)為一幀接收完成- Q- v. v" [% C( `, O
    }, f# c" V* q( R) c2 q# ^( o$ ]0 N6 k
}例程所用的是華大的hc32l130系列mcu,其它類(lèi)型的mcu也可以參考這種寫(xiě)法。其中超時(shí)時(shí)間的計(jì)算尤其要注意數(shù)據(jù)類(lèi)型的問(wèn)題,u16ArrValue = 65536 - (uint16_t)((float)(Frame_Spacing * 10)/RS485_BAUDRATE * u32PclkValue);其中Frame_Spacing為用戶設(shè)置的字符個(gè)數(shù),uart模式為一個(gè)“1+8+1”共10bits。9 U8 |) S0 a# k& ]( q9 {  `
狀態(tài)機(jī)斷幀狀態(tài)機(jī),狀態(tài)機(jī),又是狀態(tài)機(jī),沒(méi)辦法!誰(shuí)讓它使用起來(lái)方便呢?其實(shí)這種方法我用的也不多,但是狀態(tài)機(jī)的思想還是要有的,很多邏輯用狀態(tài)機(jī)梳理起來(lái)會(huì)更加的清晰。
% G7 m: g$ `6 \5 T3 m9 q: ]相對(duì)于超時(shí)斷幀,狀態(tài)機(jī)斷幀的方法節(jié)約了一個(gè)定時(shí)器資源,一般的mcu外設(shè)資源是足夠的,但是做一些資源冗余也未嘗不是一件好事,萬(wàn)一呢?對(duì)吧。
; J. Q' f$ C0 |//狀態(tài)機(jī)斷幀
6 i, P0 u. G# l: B1 Jvoid UART_IRQHandler(void)  //作為485的接收中斷. `& B) e3 P2 M/ i2 P
{
- z4 P8 \: Z4 w, V    uint8_t count = 0;
6 L5 W" w2 Y: _3 u  J0 j" X' @" V    unsigned char lRecDat = 0;
/ D1 n# y% t. }* E! u4 D' f9 }
1 }6 u9 T$ R5 O6 X# {& v. g% C    if(/*觸發(fā)接收中斷標(biāo)志*/)  
5 K5 l' a& w" q* s    {5 J& `# H; M  E4 D% |2 m& n
        //清中斷狀態(tài)位+ b, p7 x# x: a  S! ^" ]; |- o
        rec_timeout = 5;
! B0 t/ R, Q1 X. E  h' E5 |        if((count == 0)) //接收數(shù)據(jù)頭,長(zhǎng)度可以自定義
: C" B4 `7 ?- J4 ~9 q        {3 q2 n& a; o, B3 y
            RUart0485_DataC[count++] = /*串口接收到的數(shù)據(jù)*/;
" }1 u7 Q9 w6 E$ N: g) |            gRecStartFlag = 1;
+ i, N4 g2 L+ D: L            return;
% J2 P. C9 `' i) f( z+ D        }/ r1 k2 R7 P' L) r0 j
        if(gRecStartFlag == 1)4 M1 w0 |1 k- K4 U. h# n! A2 N
        {) F# R  a1 a4 Z! I( j
            RUart0485_DataC[count++] = /*串口接收到的數(shù)據(jù)*/;4 a3 L2 A: @$ \
        * s: J* k( d" S. i8 i
            if(count > MAXLEN) //一幀數(shù)據(jù)接收完成
3 s( w8 h; ]5 }7 Q4 n: O0 k0 s0 ?            {
& I- Y( f, o2 \1 {' B5 F* Y                count=0;
& r- e8 x& |" l                gRecStartFlag = 0;5 t  \/ L1 X# f; j
               
, N; ^+ P. ^% W  _( E2 D                if(RUart0485_DataC[MAXLEN]==CRC16(RUart0485_DataC,MAXLEN))
: r: @9 J! W' v* j5 d                {
* D( i: }0 w' {& @                    memcpy(&gRecFinshData,RUart0485_DataC,13);6 m) a& k( V+ I
                    gRcvFlag = 1; //接收完成標(biāo)志位                    / M: _1 j6 X/ x( V6 z2 B# h
                }
2 e  |+ E1 h9 q4 t            }   
; c* x* }% c/ R0 M. w        }* w1 d* D6 `2 |, V" L
        return;
& Z! S. K& N/ p: i! o1 |    }
2 C# w$ F* n+ @1 x$ h    return ;8 ~8 U- E4 C. n3 ?  }
}這種做法適合用在一直有數(shù)據(jù)接收的場(chǎng)合,每次接收完一幀有效數(shù)據(jù)后就把數(shù)據(jù)放到緩沖區(qū)中去解析,同時(shí)還不影響下一幀數(shù)據(jù)的接收。  x  j6 [3 P9 x3 R- B3 c
整個(gè)接收狀態(tài)分為兩個(gè)狀態(tài)——接收數(shù)據(jù)頭和接收數(shù)據(jù)塊,如果一幀數(shù)據(jù)存在多個(gè)部分的話還可以在此基礎(chǔ)上再增加幾種狀態(tài),這樣不僅可以提高數(shù)據(jù)接收的實(shí)時(shí)性,還能夠隨時(shí)看到數(shù)據(jù)接收到哪一部分,還是比較實(shí)用的。
2 f9 b" @; P5 h( ^) }6 v"狀態(tài)機(jī)+FIFO"斷幀記得剛畢業(yè)面試的時(shí)候,面試官還問(wèn)過(guò)我一個(gè)問(wèn)題:如果串口有大量數(shù)據(jù)要接收,同時(shí)又沒(méi)有空閑幀中斷你會(huì)怎么做?
0 C7 ?4 t1 O1 W: G8 v, C% o+ Q, z沒(méi)錯(cuò),就是FIFO(當(dāng)時(shí)并沒(méi)有回答上來(lái),因?yàn)闆](méi)用過(guò)),說(shuō)白了就是開(kāi)辟一個(gè)緩沖區(qū),每次接收到的數(shù)據(jù)都放到這個(gè)緩沖區(qū)里,同時(shí)記錄數(shù)據(jù)在緩沖區(qū)中的位置,當(dāng)數(shù)據(jù)到達(dá)要求的長(zhǎng)度的時(shí)候再把數(shù)據(jù)取出來(lái),然后放到狀態(tài)機(jī)中去解析。當(dāng)然FIFO的使用場(chǎng)合有很多,很多數(shù)據(jù)處理都可以用FIFO去做,有興趣的可以多去了解一下。/********************串口初始化省略,華大mcu hc32l130******************/6 ]" @- [3 U8 J! g' h. D; L
void Uart1_IRQHandler(void)( Q9 ~( L8 I: ~3 x
{5 j  q6 i" L4 B: d. x. G" ^
    uint8_t data;
' k' [6 Z7 \0 E6 n5 @6 C    if(Uart_GetStatus(M0P_UART1, UartRC))      //UART0數(shù)據(jù)接收
& {( i! ~, P3 q$ L6 W  V    {
: @. C3 M6 q3 k        Uart_ClrStatus(M0P_UART1, UartRC);    //清中斷狀態(tài)位& S$ `: u# i0 b* l# g4 N
        data = Uart_ReceiveData(M0P_UART1);   //接收數(shù)據(jù)字節(jié)/ V- w2 \6 H* K' d7 D
        comFIFO(&data,1);/ @5 |1 l$ S) k
    } ( J' j% Z7 O' m% d
}
. l+ Z; ^& z7 l" a" L: L$ z8 w
2 e( m" R! ]5 [: N  y9 q8 a/******************************FIFO*******************************/
/ ?" S6 O; N- R0 E* B, H% Cvolatile uint8_t     fifodata[FIFOLEN],fifoempty,fifofull;
- R3 y1 V6 u0 \# T. x  S( Qvolatile uint8_t     uart_datatemp=0;
0 Z* e- B% P/ D6 T' F $ I! c7 `* r! V5 a  _0 p& E
uint8_t comFIFO(uint8_t *data,uint8_t cmd); z  k( h4 r5 V+ o4 k: G4 ?
{
, X2 x9 t7 K! }! `    static uint8_t rpos=0;  //當(dāng)前寫(xiě)的位置 position 0--99
  H( D; q3 b6 V5 K5 O$ p    static uint8_t wpos=0; //當(dāng)前讀的位置, a) E. z5 c! L0 G1 Z

  a( r* n. d7 n5 w. ]    if(cmd==0) //寫(xiě)數(shù)據(jù)6 a' B6 B$ d+ ?0 d' r9 A! v
    {0 _' `& Q% |4 V8 l# X/ N
        if(fifoempty!=0)       //1 表示有數(shù)據(jù) 不為空,0表示空, T  {. X  b/ [
        {9 a  W. U2 @% d1 ?/ i( M
            *data=fifodata[rpos];* `; c9 v  Y! V
            fifofull=0;
5 K' p" k% q$ T            rpos++;  m, J0 L) V; s$ f  C
            if(rpos==FIFOLEN) " R6 X0 z- @$ F" |3 i" V/ X3 i' E' o
                rpos=0;
! r5 G4 U, B7 L8 A  K1 Y            if(rpos==wpos)
2 [7 O0 y; d1 T5 j7 b4 ~% B# e9 i                fifoempty=0;
& _" ~" R2 S  F) X5 A( g            return 0x01;
0 h( h9 T( T9 t        } 2 W; n" [6 x/ w. g. p% @' E
        else! d' [+ P* I5 {, L& g. G
            return 0x00;2 H' _4 j, C& C$ l/ r# B- J
# h5 x/ Y" ?6 H7 L. G
    }
5 V* _" [% h; [1 D& m7 U& C    else if(cmd==1) //讀數(shù)據(jù)
: W% y6 ~; L% W. k, t    {
+ ?# S  Y' ?6 e" b; Q        if(fifofull==0)! Z2 G7 L7 \7 g7 x) P  Z
        {
) [$ g+ q2 j+ [* g: x: G            fifodata[wpos]=*data;
# M# t9 |, U( L  c4 M4 ^            fifoempty=1;: }2 J# _0 q2 S8 E$ n
            wpos++;) q5 b0 R6 k4 w/ y) G; Z  d, t
            if(wpos==FIFOLEN) ' H4 y: P" l( K1 }% q8 W
                wpos=0;/ P5 r8 T5 C7 M4 F6 j  W+ }+ [
            if(wpos==rpos)
9 ^* S, @( O3 C5 {1 o$ S$ H2 n! F9 u                fifofull=1;# M+ W8 X( q: W0 ~( X' ~% g
            return 0x01;
/ r6 }4 [) w% W0 f        } else
  P; }2 ]/ N. Y: o; k            return 0x00;7 u. q% T! o& E- y+ b" Y8 n
    }
8 q- F! w8 g1 g; _' g2 g0 i    return 0x02;
8 S; V4 Q: u/ i0 A% [+ W}
* _% N: n7 b5 C; x: Q
% y) l0 l6 b5 \1 f/********************************狀態(tài)機(jī)處理*******************************/9 {2 d* @9 j2 R# X( P0 r
void LoopFor485ReadCom(void)
3 o. @( K$ ~! W. {0 S! U{+ w5 m7 [' {% G- ?# I' J
    uint8_t data;
9 U% U) {' z' E  `$ Q 2 [& H$ j; F4 x# }
    while(comFIFO(&data,0)==0x01)8 G2 \: p& f* F! P& z0 L# A$ I
    {- h2 I: K# L3 `% [3 x' p5 g
        if(rEadFlag==SAVE_HEADER_STATUS) //讀取頭2 z* p7 E$ ?" ?+ V7 y* {3 y! Q
        {8 D" W" }" l2 k. Z# s7 Y3 s
            if(data==Header_H)& Z) a+ z3 r* A+ F
            {
$ V, B4 F, N2 `% D+ O  z% u+ k. _                buffread[0]=data;) A& Z+ Z% h  A/ \$ K- w
                continue;
7 G9 ^3 U3 D; o9 V8 W            }/ W2 j5 K: ^( V" [: n
            if(data==Header_L)
0 q* b. l6 O0 Z; e+ t9 g            {
3 M4 c4 L0 F* A1 {: x                buffread[1]=data;
) d4 i5 \: z  N                if(buffread[0]==Header_H)
5 p% L, `, T  Q+ z% ]6 z6 B                {
( `1 {9 I9 O8 w0 h* G0 c; J& w                    rEadFlag=SAVE_DATA_STATUS;- \! N5 s/ A1 s% L8 ]; L
                }- ~( f, n/ D  \5 ]9 m, f5 r
            } * |2 m2 B: d0 z' U4 Q. A  P: a
            else; K- l% ~. v% R- f/ _1 T+ \
            {
$ A  L% G' f/ k* w# m- a* a( l: X                memset(buffread,0,Length_Data);
" X# v0 b1 E6 s0 h8 q1 d" }/ W            }. H8 J0 c( K2 ?6 z8 Z5 D5 A* B
        }
# g7 g  s( ~" k' H( j8 w        else if(rEadFlag==SAVE_DATA_STATUS)  //讀取數(shù)據(jù)
! j8 b" w- U6 O1 r. ?0 q! e+ Q4 Q8 u" I        {% H5 f' Y: I) z9 d  _2 a5 N
            buffread[i485+2]=data;
) x3 r: k* U  n) H            i485++;
/ h3 l; s) a) r, l9 w            if(i485==(Length_Data-2)) //數(shù)據(jù)幀除去頭
% u8 F. i2 P0 I$ M7 c            {
3 [: i2 c3 K4 A% C; K                unsigned short crc16=CRC16_MODBUS(buffread,Length_Data-2);5 d, S6 c9 m: d3 R
                if((buffread[Length_Data-2]==(crc16>>8))&&(buffread[Length_Data-1]==(crc16&0xff)))
# G* D. b8 v+ i; ~; @9 s                {6 d5 A8 C7 _( X' `" m
                    rEadFlag=SAVE_OVER_STATUS;8 d9 e6 t1 n3 r* J) _! z5 J* b
                    memcpy(&cmddata,buffread,Length_Data);  //拷貝Length_Struct個(gè)字節(jié),完整的結(jié)構(gòu)體' X5 m1 O, P8 e: _1 k
                }
, Y7 K8 M3 I6 p2 z                else1 O* A: ^0 ?6 b! r( S
                {
- P  g) R. ~6 j4 Q! n                    rEadFlag=SAVE_HEADER_STATUS;8 w' H  E* O/ W7 h* {
                }
' U) n- f2 l3 q        
7 N' O7 t, m- V% f                memset(buffread,0,Length_Data);6 D6 U7 {9 q6 \
                i485=0;+ P4 k$ N7 v; u
                break;
* g9 k# N# ~8 X  X- O  ]$ g+ J            }) x5 H5 K9 o% D2 ]* W3 c0 h
        }, n4 D  w9 m/ b& \
    }% [* y% Q! O3 Z: @
}原文:https://blog.csdn.net/qq_56527127/article/details/123018515
! |8 {4 e& V) ]5 g, W 5 x/ e' y" r# o$ U. }1 t
-END-
$ h' z8 `0 L2 g/ j, t( P往期推薦:點(diǎn)擊圖片即可跳轉(zhuǎn)閱讀
5 t9 H/ @& K+ S
' ~/ Z: v. b9 k8 |                                                        0 f" G, i$ d4 a9 z
                                                                % {1 x7 S2 Z7 y) q
                                                                       
% v% [6 Y, y/ g* u$ i                                                                                " A, O  b* s) a% _1 i+ ?$ Y: L& i
: @$ G) `6 v2 O* g( d; x/ R! H/ {- R
                                                                               
/ R  \+ n% h7 O0 R! A' B5 e& l                                                                                        嵌入式軟件調(diào)試,如何計(jì)算任務(wù)的運(yùn)行周期?
/ ^- b# J1 Q% H: m) f                                                                                * r  C, Q) A. e+ M9 g
                                                                       
7 }3 R) ?) L! U. |! t9 B3 `                                                                " ~9 n. Z. Z) `! f8 _
                                                        - S7 f; ]- `! Q' q1 t1 G9 l
                                               
4 ?( O! w! S: p/ i; W. ?- e9 H2 p& h0 b1 Z
                                                        ' S; U; V; A- N2 J
                                                                4 ~* E& o: y$ t- _$ z: j
                                                                        % r; l1 g8 V& k' O; H1 m$ _
                                                                                ) g5 p! F  a, k$ o  W( v- |
7 E5 d# x; z& k
                                                                               
6 E  |: H- Z+ ~" R- B- D; ]0 U                                                                                        嵌入式軟件,如何把編譯時(shí)間加入到bin文件,進(jìn)行版本管理?
9 ], H0 d  N$ ^  X4 B                                                                               
+ U- t( h( d0 S0 l                                                                        1 ?1 `5 j; r9 o, w' y
                                                                ( o- S' j4 z' R. Y' P
                                                       
) E0 ]& ?4 F+ Z5 l  I                                               
4 y! t  M- a$ r2 e
& {; G0 E- o% q' R- D                                                       
0 X" O, B5 K& B/ L1 o' m% [* _                                                               
  E. t1 }) ^! e$ S                                                                       
* @: P2 D5 `- g8 a: C                                                                                1 F5 O- ~4 h$ n: p

+ ]1 K+ a6 A0 R# S; d                                                                                4 A9 W- R8 f: V  D9 t' X! M
                                                                                        嵌入式初學(xué)者入門(mén)后,應(yīng)該如何開(kāi)始進(jìn)階學(xué)習(xí)?
' {3 f+ L: X9 G7 K  a% }, s                                                                                % E3 L' I9 v. |2 `0 s
                                                                       
& d4 K) C0 `' n* f) g                                                               
5 S$ E: P8 m0 Q* v3 s0 F* f$ U                                                        - E; s9 N# h! V( ~5 `- D- `" s8 f$ {1 ?
                                               
, e/ V0 D5 G  l! Y' m7 |" @我是老溫,一名熱愛(ài)學(xué)習(xí)的嵌入式工程師
' s- I! d; s+ h' p關(guān)注我,一起變得更加優(yōu)秀!

發(fā)表回復(fù)

本版積分規(guī)則


聯(lián)系客服 關(guān)注微信 下載APP 返回頂部 返回列表