你的浏览器版本过低,可能导致网站不能正常访问!
为了你能正常使用网站功能,请使用这些浏览器。

【经验分享】STM32G070 移植一个shell,方便调试。基于FreeRTOS

[复制链接]
STMCU小助手 发布时间:2021-11-14 23:04
测试ST 官网的 FreeRTOS6 z" i5 H  O! Z+ d2 W

& N( v6 ~8 B6 T& y3 b" [4 U移植shell
, A5 i: Q( R) e" G* @主要是串口对接, 需要重写两个函数
( c3 d9 a5 v+ K" y6 m! e7 Z1 h+ E
  1. int fputc(int ch, FILE *f)4 H8 }) g) ^4 E8 l: O% j0 W  R
  2. {
    9 I, _+ ^, d5 Y, N9 m. |
  3.   /* Place your implementation of fputc here */
    6 i& K! D  @( a4 v" J
  4.   /* e.g. write a character to the EVAL_COM1 and Loop until the end of transmission */
    9 k9 \& N5 f0 v9 T
  5.   HAL_UART_Transmit(&huart1, (uint8_t *)&ch, 1, UART_TIMEOUT_VALUE);
    2 T. o4 a; z/ T, {
  6.   return ch;' u( a$ {9 ~6 X2 r( _8 [
  7. }
    , |8 \% x8 a4 P1 `
  8. // #endif
      X) ?# j! e  T0 P4 g( B; U8 ~

  9. & Y) ?8 p: L. M' f( h, p: K. m
  10. char shell_buf[RXBUFFERSIZE]={0};
    $ ~: m1 c$ H3 Y4 v
  11. char shell_len=0;  i& ~0 T( ~+ w5 Q# h+ T7 O
  12. char *shell_buf_head=NULL;) y1 w1 t% J* g+ o9 }$ H* @7 U

  13. - \  I/ i4 G( {

  14. & \1 A1 d! k' P9 v
  15. int fgetc(FILE *f)+ h, |# U% N* T- N+ V
  16. {: _9 N! c1 ?7 k/ H- L
  17. ; b. l7 J- G( n, J1 [9 M
  18.   while (0 == shell_len) {; ^* Y0 g, H; y
  19.     osDelay(1);
    9 p# Q- _' p1 `9 S4 T# E# A8 z
  20.   }9 w- \: t2 o) O  a$ X, [
  21.   char ch = *shell_buf_head;
    : \* M7 `: D! R/ D+ @& [8 M  P+ l
  22.   shell_buf_head ++;  G; e+ E. a* L( s' _* Q) `
  23.   shell_len --;
    ' }) @" e& B- Y- z

  24. - S; `/ \% V; F% J  v5 E
  25.   return ch;
    8 {. T; [: g" S, q, W2 u
  26. }
复制代码
0 ]) Z+ ~+ p3 u2 d8 V
增加了一个回调函数, 收到数据拷贝到shell_buf,  然后重新初始化串口中断接收参数,指针,size,count+ o1 A( p+ w( `/ q7 d: e
9 g( `' M6 ~# [* d# p( X( e& U
  1. void HAL_UART_RxCpltCallback(UART_HandleTypeDef *UartHandle)
    0 M6 o: x$ w* M# O
  2. {8 \0 L. b* v4 z( }, G$ p( l1 ~$ [
  3.   /* Set transmission flag: transfer complete */
    , N9 |5 ^, G" n+ n. N. p3 ^: U
  4.   if(UartHandle->Instance == USART1) {: O: D  I9 O1 w  }+ Q
  5.     // UartReady = SET;
    ; u2 ^+ H2 k3 ?) L7 }/ R3 y/ [
  6.     shell_len = UartHandle->pRxBuffPtr - aRxBuffer;  @( P$ a- s3 A& P
  7.     shell_buf_head = shell_buf;& h  @, v8 W; c' ~4 ^6 x+ @* v
  8.     memcpy(shell_buf, aRxBuffer, shell_len);, k, w% B& q- ^6 x8 Z4 J$ t
  9. - ?1 B$ q& G/ `% |4 q8 O
  10.     UartHandle->pRxBuffPtr = aRxBuffer;$ K. b1 ~0 v- ~
  11.     UartHandle->RxXferSize  = RXBUFFERSIZE;
    1 u  k- U7 @! T+ I% h2 P
  12.     UartHandle->RxXferCount = RXBUFFERSIZE;
    * Z% @+ Q" U  m/ k/ x
  13.   }, y/ X, e4 M5 U7 E& \$ k2 n, A
  14. ) H" \" J/ u8 x. @! r
  15. }
复制代码

) g$ E- Q  n$ t( r遇到的问题, 1. fgetc 不能直接调用HAL_UART_Receive, 否则会死等,导致其他任务无法运行。9 ^+ {8 ]9 A$ T0 r( N. B& L
# Z; S3 R5 G9 L" J% x
解决这个问题的方法是,接收采用中断方式。0 @- G  d8 R9 U( w# Y

" z1 U. o& ^2 E# \5 f+ K问题2. STM32CubeMX 生成的代码,串口中断接收是固定长度的方式, 对于shell 不适用。# \2 H$ v, W) g% a# \! k

# M! J8 q6 [3 ]解决这个问题的方法是,修改中断处理程序,如果是调试用的串口,直接处理接收数据1 ?  ]/ \5 o/ o7 |# A8 l7 J7 U
+ O! E! m3 ~) D
  1. static void UART_RxISR_8BIT(UART_HandleTypeDef *huart)' L4 Q0 d8 Y! y+ ^; n) s
  2. {
    1 ]! F7 z" d$ c, Y
  3.   uint16_t uhMask = huart->Mask;
    . y8 t1 Z) T& C/ i
  4.   uint16_t  uhdata;
    , V, Y: B! @+ }, F) a' n

  5. - K9 t1 b0 s9 R6 x6 s
  6.   /* Check that a Rx process is ongoing */7 d' \: |, `* V% ]
  7.   if (huart->RxState == HAL_UART_STATE_BUSY_RX)
    ! N3 n& x) S7 ?4 x
  8.   {8 v! U2 z/ \" }7 u. A3 ]
  9.     uhdata = (uint16_t) READ_REG(huart->Instance->RDR);( n0 [& w& [( ]2 N) X$ W
  10.     *huart->pRxBuffPtr = (uint8_t)(uhdata & (uint8_t)uhMask);
    7 U) M+ u0 h4 r! j2 f
  11.     huart->pRxBuffPtr++;
    % |' }( q+ s; W
  12.     huart->RxXferCount--;
    7 w) ?& y9 b; H+ X& x

  13. ! S8 s0 Z; P) G+ z" C3 r* ^
  14.     if(USART1 == huart->Instance) {+ Z/ t2 @" G; Z" O
  15.       HAL_UART_RxCpltCallback(huart);$ n% o* ]9 P! c! s. Y+ w) K7 V8 s
  16.     }
    $ Q% u& O9 n* V+ {; Q% i
  17.     if (huart->RxXferCount == 0U) {
    # z; J! ~+ w2 E( w
  18.       /* Disable the UART Parity Error Interrupt and RXNE interrupts */- O: Y; w! w7 D+ e' L7 X/ ]
  19.       CLEAR_BIT(huart->Instance->CR1, (USART_CR1_RXNEIE_RXFNEIE | USART_CR1_PEIE));
    : ^- V! H# s& X0 V4 J. }# d" j

  20. 5 ^% S3 k0 G' K% z5 D' ^7 ^
  21.       /* Disable the UART Error Interrupt: (Frame error, noise error, overrun error) */' }- n1 w* P0 [6 g5 H* m1 t0 A" z
  22.       CLEAR_BIT(huart->Instance->CR3, USART_CR3_EIE);9 z+ _! H: K( s* M8 e

  23. ) s% B+ R( L$ V; H5 j3 D8 ^+ {3 R
  24.       /* Rx process is completed, restore huart->RxState to Ready */
    + h- }4 W# P' \5 c4 s
  25.       huart->RxState = HAL_UART_STATE_READY;
    & a; L. c/ b+ h8 u

  26. : \- U& w" Q# t- i. \1 }
  27.       /* Clear RxISR function pointer */" K) C5 y* a8 X1 G& S" G) B
  28.       huart->RxISR = NULL;9 u4 J' H, J( E4 Y5 @

  29. + W* j+ ?0 P2 e7 x
  30. #if (USE_HAL_UART_REGISTER_CALLBACKS == 1)* i  Q# R! ~& Y9 s1 J3 O
  31.       /*Call registered Rx complete callback*/
    - _, h9 ~! G' P0 w
  32.       huart->RxCpltCallback(huart);& m4 P0 M2 c4 u, ^! j; ~4 r0 L9 N
  33. #else' J" Z3 K9 s) ?# k& Y
  34.       /*Call legacy weak Rx complete callback*/
    $ c; Z5 l& P- f9 e- i( @
  35.       HAL_UART_RxCpltCallback(huart);" |8 F4 q$ c, f9 S
  36. #endif /* USE_HAL_UART_REGISTER_CALLBACKS */
    4 p- C9 x$ p+ K% i& |
  37.     }
    1 J" x  o, g9 q, q( N" j$ W
  38.   }1 ?  C$ A5 i! M# Z" }* L$ H
  39.   else
    . `$ H+ a8 O* N8 z1 t9 L/ g
  40.   {
    7 }5 a" [  p8 S- c% ]
  41.     /* Clear RXNE interrupt flag */: u4 x% I3 k1 A. F9 q/ W4 U
  42.     __HAL_UART_SEND_REQ(huart, UART_RXDATA_FLUSH_REQUEST);
    / h: Q$ u" ~+ f  v
  43.   }: c' L' `8 Y, B* p
  44. }
复制代码
. q: Y  s, h+ R
问题3. shell 放在Mgr task里面,由于内存分配128*4 不够导致死机
* b* n8 a' m# E: M$ z. r- U( M8 ~
解决这个问题的方法是,去掉没有用的shell 指令,限制最多支持64条指令。 任务内存分配加大 256*4' \4 H: Q+ X) c8 U' L$ q
$ p5 {- {: g! w" e) u+ ]
最终效果图/ V" y/ U2 i* @
' X; Z' P# d: x
20201124190505583.png
5 O, G$ r: N7 |/ q( }2 ]

! |7 G4 r$ X3 p4 V" a( G$ Y$ A
; G2 ]' g3 ?) ^9 z
赞 收藏 评论0 发布时间:2021-11-14 23:04

举报

0个回答
关于
我们是谁
投资者关系
意法半导体可持续发展举措
创新与技术
意法半导体官网
联系我们
联系ST分支机构
寻找销售人员和分销渠道
社区
媒体中心
活动与培训
隐私策略
隐私策略
Cookies管理
行使您的权利
官方最新发布
人形机器人运动控制、感知与智能配电
半导体创新技术与应用方向
EE架构与软件定义汽车
12V/48V 汽车智能配电(SPD)
区域控制单元(ZCU)与分区架构
关注我们
st-img 微信公众号
st-img 手机版