瀏覽代碼

[update]

rtthread_MCoreDump
huangyulong 2 月之前
父節點
當前提交
b9a36bc5e1

+ 12
- 4
Middlewares/MCoreDump/addr2line/addr2line.c 查看文件

@@ -2,7 +2,7 @@
2 2
 #include <rtthread.h>
3 3
 #include "addr2line.h"
4 4
 
5
-#define PROJECT_NAME "project"
5
+#define PROJECT_NAME "project.out"
6 6
 #define addr2line_print rt_kprintf
7 7
 
8 8
 // 错误类型打印
@@ -513,6 +513,7 @@ static bool disassembly_ins_is_bl_blx(uint32_t addr)
513 513
     }
514 514
 }
515 515
 
516
+// 只会找符合要求的lr,不能找pc值。所以要指定pc
516 517
 void addr2line_cmd_with_pc_print(uint32_t *thread_pc, uint32_t *addr, int size)
517 518
 {
518 519
     addr2line_print("addr2line -e " PROJECT_NAME " -a -f ");
@@ -532,18 +533,25 @@ void addr2line_cmd_with_pc_print(uint32_t *thread_pc, uint32_t *addr, int size)
532 533
 
533 534
         if (pc % 2 == 0) // thumb 指令pc寄存器值一定是偶数
534 535
             continue;
535
-        
536 536
 
537 537
         pc = lr - 1; // lr寄存器值保存的是pc+1
538 538
 
539 539
         if ((uint32_t)thread_pc == pc) // 忽略:已经指定打印过了
540 540
             continue;
541 541
 
542
-        if (true == disassembly_ins_is_bl_blx(pc - sizeof(size_t))) // pc 的上一条指令是跳转指令
542
+        if (true == disassembly_ins_is_bl_blx(pc - sizeof(size_t))) // pc 的上一条指令是跳转指
543
+        {
544
+//          if (i + 1 < size && pc != addr[i + 1] && true == is_in_text(addr[i + 1])) // 最后一次调用的情况:LR、PC还在CPU寄存器里面挨着的
545
+//          {
546
+//              addr2line_print("%08x ", addr[i + 1]);
547
+//              i++;
548
+//          }
549
+
543 550
             addr2line_print("%08x ", pc);
551
+        }
544 552
     }
545 553
 
546
-    addr2line_print("\n\n");
554
+    addr2line_print("\n");
547 555
 }
548 556
 
549 557
 void addr2line_cmd_print(uint32_t *addr, int size)

+ 21
- 1
Middlewares/MCoreDump/arch/armv7m/armv7m.c 查看文件

@@ -206,6 +206,8 @@ void mcd_multi_dump(void)
206 206
 void print_registers_armv7m(core_regset_type *reg, fp_regset_type *fp_reg, char *thread)
207 207
 {
208 208
     mcd_print("Registers@%s\n", thread);
209
+    mcd_print("R13(SP): 0x%08x\n", reg->sp);
210
+#if 0
209 211
     mcd_print("R0: 0x%08x\n", reg->r0);
210 212
     mcd_print("R1: 0x%08x\n", reg->r1);
211 213
     mcd_print("R2: 0x%08x\n", reg->r2);
@@ -223,6 +225,24 @@ void print_registers_armv7m(core_regset_type *reg, fp_regset_type *fp_reg, char
223 225
     mcd_print("R14(LR): 0x%08x\n", reg->lr);
224 226
     mcd_print("R15(PC): 0x%08x\n", reg->pc);
225 227
     mcd_print("xPSR: 0x%08x\n", reg->xpsr);
228
+#else // 按压栈顺序打印
229
+    mcd_print("xPSR: 0x%08x\n", reg->xpsr);
230
+    mcd_print("R15(PC): 0x%08x\n", reg->pc);
231
+    mcd_print("R14(LR): 0x%08x\n", reg->lr);
232
+    mcd_print("R12: 0x%08x\n", reg->r12);
233
+    mcd_print("R3: 0x%08x\n", reg->r3);
234
+    mcd_print("R2: 0x%08x\n", reg->r2);
235
+    mcd_print("R1: 0x%08x\n", reg->r1);
236
+    mcd_print("R0: 0x%08x\n", reg->r0);
237
+    mcd_print("R11: 0x%08x\n", reg->r11);
238
+    mcd_print("R10: 0x%08x\n", reg->r10);
239
+    mcd_print("R9: 0x%08x\n", reg->r9);
240
+    mcd_print("R8: 0x%08x\n", reg->r8);
241
+    mcd_print("R7: 0x%08x\n", reg->r7);
242
+    mcd_print("R6: 0x%08x\n", reg->r6);
243
+    mcd_print("R5: 0x%08x\n", reg->r5);
244
+    mcd_print("R4: 0x%08x\n", reg->r4);
245
+#endif
226 246
 }
227 247
 
228 248
 /**
@@ -401,7 +421,7 @@ int armv7m_hard_fault_exception_hook(void *context)
401 421
 #else
402 422
     uint32_t *stack_ptr = context;
403 423
     stack_ptr += 1; /* 跳过:exc_return */
404
-//  stack_ptr += 1; // 如开启fpuflag
424
+    //  stack_ptr += 1; // 如开启fpuflag
405 425
 #endif
406 426
 
407 427
     /*

+ 31
- 5
Middlewares/MCoreDump/rtthread_port.c 查看文件

@@ -14,6 +14,8 @@
14 14
 #include "addr2line/addr2line.h"
15 15
 
16 16
 #define PRINT_COREDUMP_INFO_STRING 1 // 打印字符串格式的coredump信息
17
+#define STACK_CORE_REG_SIZE (17 * 4) // 16个自动+手动压栈寄存器 + exe_return
18
+#define STACK_FPU_REG_SIZE (17 * 4) // 17个自动压栈的浮点寄存器
17 19
 
18 20
 /*
19 21
  * RT-Thread OS abstraction layer implementation for MCoreDump
@@ -161,7 +163,20 @@ static int32_t rtthread_get_memarea(struct thread_info_ops *ops, int32_t idx,
161 163
                 {
162 164
                     *addr = get_cur_core_regset_address()->sp;  // 异常中填充
163 165
                     *memlen = (rt_uint32_t)thread->stack_addr + thread->stack_size - (rt_uint32_t)thread->sp;
164
-
166
+                    *addr -= STACK_CORE_REG_SIZE; // 异常中断里面已经压栈了但还没更新tcb里面的sp指针
167
+                    *memlen += STACK_CORE_REG_SIZE * 2; // 前后括大两倍:实际可能更多局部变量在死机前还没来得及向下增长sp
168
+#if MCD_FPU_SUPPORT
169
+                    /* Read FPU flag first - indicates if FPU context was saved */
170
+                    uint32_t fpu_flag = *(uint32_t *)thread->sp;
171
+                    *addr -= 1;
172
+                    *memlen += 1;
173
+
174
+                    if (fpu_flag)
175
+                    {
176
+                        *addr -= STACK_FPU_REG_SIZE; // 异常中断里面已经压栈了但还没更新tcb里面的sp指针
177
+                        *memlen += STACK_FPU_REG_SIZE;
178
+                    }
179
+#endif
165 180
                     if (*memlen > thread->stack_size)
166 181
                     {
167 182
                         mcd_println("The stack may overflow!!!");
@@ -209,7 +224,20 @@ static int mcd_print_coredump_info_string(struct thread_info_ops *ops)
209 224
             {
210 225
                 addr = (rt_uint32_t)get_cur_core_regset_address()->sp;      // 异常中填充
211 226
                 memlen = (rt_uint32_t)thread->stack_addr + thread->stack_size - (rt_uint32_t)thread->sp;
212
-
227
+                addr -= STACK_CORE_REG_SIZE; // 异常中断里面已经压栈了但还没更新tcb里面的sp指针
228
+                memlen += STACK_CORE_REG_SIZE * 2; // 前后括大两倍:实际可能更多局部变量在死机前还没来得及向下增长sp
229
+#if MCD_FPU_SUPPORT
230
+                /* Read FPU flag first - indicates if FPU context was saved */
231
+                uint32_t fpu_flag = *(uint32_t *)thread->sp;
232
+                addr -= 1;
233
+                memlen += 1;
234
+
235
+                if (fpu_flag)
236
+                {
237
+                    addr -= STACK_FPU_REG_SIZE; // 异常中断里面已经压栈了但还没更新tcb里面的sp指针
238
+                    memlen += STACK_FPU_REG_SIZE;
239
+                }
240
+#endif
213 241
                 if (memlen > thread->stack_size)
214 242
                 {
215 243
                     mcd_println("The stack may overflow!!!");
@@ -217,9 +245,7 @@ static int mcd_print_coredump_info_string(struct thread_info_ops *ops)
217 245
                 }
218 246
 
219 247
                 print_registers((void *)get_cur_core_regset_address(), get_cur_fp_regset_address(), thread->name);
220
-#define STACK_FRAME_SIZE (17 * 4) // 17个寄存器
221
-                rt_uint32_t addr2 = (rt_uint32_t)thread->sp - STACK_FRAME_SIZE;
222
-                addr2line_cmd_with_pc_print((rt_uint32_t *)get_cur_core_regset_address()->pc, (uint32_t *)addr2, memlen + STACK_FRAME_SIZE);
248
+                addr2line_cmd_with_pc_print((rt_uint32_t *)get_cur_core_regset_address()->pc, (uint32_t *)addr, memlen);
223 249
             }
224 250
             else
225 251
             {

Loading…
取消
儲存