! \7 f- |7 g9 s
2 M0 F0 b8 z* ?2 E n, S7 v9 O描述:# N0 t. F3 N6 i# m! @
我意识到我是垂死的人群中的一员,他们只使用emacs作为IDE。我决定和SystemWorkbench一起生活一段时间。很多事情需要处理,我的笔记可能会帮助你。
- `: v! t2 y: s: m! {4 B% m' p) H( q5 N r+ {/ Q: g; ]; k
) t3 l8 i1 M- N" }
- k9 v q' X4 n; z+ z i细节:
. u. x, x, S# c$ f. {# D基于http://hackaday.com/2017/03/30/t ... uino-with-debugging上的评论,我决定让SystemWorkbench试试。. ]8 D: j+ V) t
+ |$ P! N, t; S( K! `6 ], f
" |2 e6 O* h2 k' r- O项目日志:
9 H9 G& d1 ]2 ]3 E0 K0 |使用CDC USB串行接口的提示:7 e) {0 U0 B& x) i
当你把USBCDC序列添加到你的项目中时,对于下一步该做什么你得不到太多帮助。CDC发送fs的呼叫很明显。给它一条消息和一个长度,它就会发送它。够公平的。) D2 V. i6 R$ b2 a- r
: \* D6 v1 [. y W但是,接收是通过一个名为cdc_receive_fs的回调进行的。你不叫这个。框架为您调用它。) }; D; ^7 p$ Z" B
" Q- o* ^ H) l3 ^; F
这是我的版本:
% ^ k# r! K0 U5 r* Z! a* i& |9 A/ L/ K/ t- j
- static int8_t CDC_Receive_FS (uint8_t* Buf, uint32_t *Len)$ V0 Q- O7 G. R$ |5 V& B# b \
- : U; k) E6 g* d% V0 @
- {8 L3 W: G0 @9 m& R3 ?
% J* \* V8 m* {$ z- /* USER CODE BEGIN 6 */$ g+ |- {, c4 u! v
- uint32_t len=*Len; `" v( O# l4 J) ^' T( k
- if (hUsbDeviceFS.dev_state != USBD_STATE_CONFIGURED)! i! h" I/ u6 c1 k# t# y
- {7 O+ `, ^2 b. R. }/ D2 H% c2 s
- return USBD_FAIL;# L+ H, ?2 i7 r
- }
/ o$ U( X3 u0 f5 w0 R/ \2 u8 J9 K, n - ( G% r6 A* ~ R, W; f& g
- if (((Buf == NULL) || (Len == NULL)) || (*Len <= 0))2 n( M1 W* U4 H
- {- p8 L! e/ `( _
- return USBD_FAIL;
6 j: I" u) b2 ~2 o$ i( T, U4 y - }
5 ]$ p: j0 F5 t) E2 ~' G - 8 \" l& @/ L/ s# d
- /* Get data */2 o/ }7 H2 y# ]9 O y( W* F
- uint8_t result = USBD_OK;" E8 c* C- a& R* e
- do# q) U8 D/ v8 ^/ a* a
- {
! M4 Y, c+ j2 l: B0 o% z( |' e - result = USBD_CDC_SetRxBuffer(&hUsbDeviceFS, &Buf[0]);
" U$ v+ C8 _) z# t - }: y7 g' Y+ X+ ?5 q2 Y& b: F
- while(result != USBD_OK);- L: w4 |/ }8 l! n! M
8 X+ [: c3 |. y) r" o- do
5 _) P3 G5 Q& Y' O3 y7 l - {. P# }# [/ q. i+ X
- result = USBD_CDC_ReceivePacket(&hUsbDeviceFS);! a, Y9 H7 z$ x2 Z/ B$ X8 L* w3 u
- }: n2 }3 k5 S. T# |! m- y! }# o; W
- while(result != USBD_OK);
* o4 q% V6 d( q5 P' Z7 G
/ W- @1 a$ ]( G$ q# \- b- // add data to FIFO* n, B% w& {* x& |/ K! m% m/ y
- while (len--)0 x. q; z ^; e& v; u5 c5 C4 V
- if (FIFO_INCR(RX_FIFO.head)==RX_FIFO.tail)0 ]5 g" u/ W- `5 t+ f9 Q
- return USBD_FAIL; // overrun8 M$ j- `# k! d. ?/ B
- else: b8 w* U7 N5 Y0 v3 e4 D1 ^
- {
/ Q; i1 K. H3 f - RX_FIFO.data[RX_FIFO.head]=*Buf++;$ a" |7 f% g, E
- RX_FIFO.head=FIFO_INCR(RX_FIFO.head);
7 w* v! {5 S9 ?1 {# ~ - }
8 ]& J) P- S3 T; g( e: m - return (USBD_OK);
( s! k% h1 M& [6 Y! k - * U# R4 H9 j5 K+ C
- /* USER CODE END 6 */
* E' O3 L" Y) Z4 @5 o1 Y
) P( c, ^3 u- x% m8 L. }/ P- }
复制代码 在其中一个标题中:! Q4 e. s* g2 t
- #define FIFO_SIZE 32 // must be 2^N8 G7 p+ A3 G) L
* B: S+ r- q8 Z& G' A5 s- O- #define FIFO_INCR(x) (((x)+1)&((FIFO_SIZE)-1))
, s$ \8 d5 U2 m
6 l5 ^* o6 ]! n1 C2 t( `3 n! l8 K2 X- /* Structure of FIFO*/- v! |+ k/ w) ~
' G' l5 |7 A6 T# p6 V8 O- typedef struct FIFO
2 j1 B7 ^. F# D# O
6 ?1 m/ Y! {7 S) m" _" G" U; C- {
( k$ z8 H% v8 X1 g+ [* [ - uint32_t head;
$ w6 A3 u I: R - uint32_t tail;# r% ~7 `% I' b9 r
- uint8_t data[FIFO_SIZE];# `3 T" r+ a3 @0 j; I3 Q, z7 G
- } FIFO;5 W }' i3 O% ^( D. x* H# [1 u/ \
5 }. H. [5 P# O9 \4 Z' \: R ~- extern FIFO RX_FIFO;
复制代码 那你也需要一种方法来读出来。
' f2 ^& k1 ]! n- /* Create FIFO*/# k3 r5 ~% ]$ B
- FIFO RX_FIFO = {.head=0, .tail=0};
: ^8 a6 e; v% j* s# ?* X! x
& r8 w, @% l; L( k- // returns bytes read (could be zero)0 q. Y1 Q# V' W |% B
- // would be easy to make it end early on a stop char (e.g., \r or \n)4 B: }( W& q$ k) O* L
- uint8_t VCP_read(uint8_t* Buf, uint32_t Len)" x3 H, f0 f: Q. r9 o$ t
- {4 ~; ~; N) {- u3 g& B' ~
- uint32_t count=0;+ A/ N2 e' k- t% E' h4 Q
- /* Check inputs */
% _' X9 q$ N! H4 E3 ]8 g5 G$ u2 C - if ((Buf == NULL) || (Len == 0))5 c, ]# w9 M* K, t% C1 f, C
- {
- b8 d: x) @9 f - return 0;; O2 i4 e S- `- g
- }
( n& u' ]2 S9 D7 ^9 V9 Z5 [ - ; q1 n- C9 E5 N4 l$ b, z6 W/ W; w
- while (Len--)
; ^" @3 Z6 n, X$ C/ b3 f T - {: L9 b" |9 T$ X, ~1 Q
- if (RX_FIFO.head==RX_FIFO.tail) return count;
/ p: f! h, ^! b H - count++;
- X8 W. u: f" o+ S$ F" o - *Buf++=RX_FIFO.data[RX_FIFO.tail];
5 \4 E* c: U8 j/ _# q( _$ ^ - RX_FIFO.tail=FIFO_INCR(RX_FIFO.tail);
2 o, q4 l" a0 w$ q* s - }
; [$ C* V0 R* l8 a( l
: t7 }; F/ c, ]" i/ Z! D& j: i- return count;1 Y$ C6 z+ v1 `( K7 p o0 s/ a
- }
复制代码
~1 @* `* ?+ C# H启用半宿主printf6 w! f0 k6 q. e' l% k0 z
如果您不希望printf转到串行端口,那么您可能希望它重定向到gdb控制台(Eclipse内部)。- a1 \- _5 c& b3 y$ q2 S: ?
3 c" o: F. u6 ]/ k) F! D
1。添加到链接器选项:8 `8 v+ }2 M, {% Q+ ?5 Y' S
& w- i2 J) L* }! a# A
- -specs=rdimon.specs -lrdimon
复制代码 2。在调试配置中,找到运行命令并添加:; m2 l" k2 p, X/ \
- monitor arm semihosting enable
复制代码 3.在main()中,提前进行此调用(在调用printf之前):
* f2 G: S5 B" } `4 B8 O3 E( ]- initialise_monitor_handles();
复制代码 就是这样。现在,printf将转到您的控制台。
* I6 ]' `& _6 [" y7 [8 T& {4 Y$ n7 Q" v: T- M* `
4 T2 x" c+ t7 T- n
' E2 j3 Z+ c1 ^
将printf和朋友重新定位到UART0 `" H7 ^# M5 p6 ^0 C3 o6 j
- 确保您有足够的堆栈!如果您没有在项目生成时设置它,请在.ld文件中修复它(并确保在cubemx项目中修复它,以防重新生成。
- 另外,用IDE而不是cubemx创建一个虚拟项目。从该项目中窃取syscalls.c文件并将其放入项目中。
- 显然,你需要在cubemx设置UART。
- 添加:1 Y1 M/ v1 m9 q
- int __io_putchar(int ch)& C" |9 i4 g7 S* [2 S
- 0 f) U c+ A& e- b: g. E
- {0 z. r3 W$ H+ @) d3 H, _: Z5 E
- " E. z- U: R& J; ~% i9 E! ?
- uint8_t ch8=ch;
. e! x1 k; I# `; R! F, m* B' i
6 q* C7 n7 y8 B3 ?, R! r- HAL_UART_Transmit(&huart1,(uint8_t *)&ch8,1,HAL_MAX_DELAY);
! x F M9 V L4 \+ E
* ?! z# Q/ S. u) w1 W! I- return ch;
8 }1 v+ Q4 S, O - / f1 P/ F- ^0 O& A) I; U6 L
- }
9 ^1 W1 c! ` a
; M# j/ g. O# }+ _% T- int __io_getchar()% \1 q9 \) a1 J6 O" K
- - d2 p! v& F H9 g: L! C4 i
- {
7 E7 Q4 N" _8 s5 N$ w* p% f
1 A, B0 b- i2 r$ v7 n( _) e- uint8_t ch8;
! ~, X9 {4 u" C4 a
& S3 b) o1 Z6 u' v* M- HAL_UART_Receive(&huart1,&ch8,1,HAL_MAX_DELAY);
( H2 Z' y. e; E5 w( Z6 a - , i- z; L+ G( b: S
- return 0;7 `- N) \( Y( p: Z- u; D, N
- / p% B, d! k8 h( K7 S" i
- }
复制代码 完成!神秘的崩溃意味着你的堆栈太小,或者你让启动跳线设置得很有趣,而SP没有设置成你认为的那样。7 a# Y; e$ } Q2 Y# k( j" L( v
% ?4 J# b8 P- Y( o笔记; x4 {8 K- ^, I6 Q: s
- http://www.opensmt32.org/system+workbench+for+stm32
- 将cubemx从ST网站安装到Eclipse中。http://www.st.com/en/development-tools/stsw-stm32095.html
- 您必须具有用于此板的ST链接2或2-1。似乎不适用于ST链接1,即使其他工具可以处理。
- 如果你用PLL时钟的话,库贝姆有一个错误。在SystemClock_配置中,行应该如下所示:rcc_oscinitstruct.sociatortype=rcc_sociatortype_hse;
- 创建配置时,openocd的设置硬连接到项目目录中的.custom.cfg中。所以,如果你改变了任何东西,看起来你必须修改或编辑这个文件。
- 重要提示:除非您将openocd配置更改为仅使用:reset_config trst_,否则调试器将无法工作。默认值将不起作用。
- 如果将引导跳线设置为引导加载,则调试似乎可以工作。但是,您将得到引导装载程序stackpointer,它是一个非常小的堆栈,可能会覆盖您的C库数据。这将导致奇怪和不可预测的行为。
- 如果安装eGit,就可以获得Git集成。
- 如果安装tm终端,则可以在IDE中安装终端。据说它支持串行,但在Ubuntu上,RXTX配置是主机化的。我运行一个shell终端,在里面运行picocom,而不是修复它。工作良好。
; B3 ^1 O8 @' Y8 P; O ! Q# f4 M7 k% P) C
原创:Al Williams
1 j X( p% r. ^2 e; b' [1 L出处:http://hackaday.io/project/20879/logs
" t- K4 e1 @; J/ s1 f0 S# D
3 X7 h: L4 T% C$ J. J( h0 R3 a7 a9 G: s( ^( r7 |/ v
$ }3 J- ^1 e% t" [7 N& Z. s/ t9 H+ e* _" o! G
8 }! L3 u: ~+ }# q* F* b. R1 T6 N2 N |