void caml_stash_backtrace(value exn, code_t pc, value * sp, int reraise) { code_t end_code = (code_t) ((char *) caml_start_code + caml_code_size); if (pc != NULL) pc = pc - 1; if (exn != caml_backtrace_last_exn || !reraise) { caml_backtrace_pos = 0; caml_backtrace_last_exn = exn; } if (caml_backtrace_buffer == NULL) { Assert(caml_backtrace_pos == 0); caml_backtrace_buffer = malloc(BACKTRACE_BUFFER_SIZE * sizeof(code_t)); if (caml_backtrace_buffer == NULL) return; } if (caml_backtrace_pos >= BACKTRACE_BUFFER_SIZE) return; /* testing the code region is needed: PR#1554 */ if (find_debug_info(pc) != NULL) caml_backtrace_buffer[caml_backtrace_pos++] = pc; /* Traverse the stack and put all values pointing into bytecode into the backtrace buffer. */ for (/*nothing*/; sp < caml_stack_high + caml_trap_sp_off; sp++) { code_t p = Pc_val(*sp); if (Is_long(*sp) && Pc_val(*sp) >= caml_start_code && Pc_val(*sp) < end_code) { if (caml_backtrace_pos >= BACKTRACE_BUFFER_SIZE) break; if (find_debug_info(p) != NULL) caml_backtrace_buffer[caml_backtrace_pos++] = p; } } }
code_t caml_next_frame_pointer(value* stack_high, value ** sp, intnat * trap_spoff) { while (*sp < stack_high) { value* p = (*sp)++; if(&Trap_pc(stack_high + *trap_spoff) == p) { *trap_spoff = Trap_link(stack_high + *trap_spoff); continue; } if (Is_long(*p) && find_debug_info(Pc_val(*p)) != NULL) return Pc_val(*p); } return NULL; }
void caml_stash_backtrace(value exn, code_t pc, value * sp, int reraise) { if (pc != NULL) pc = pc - 1; if (exn != caml_read_root(Caml_state->backtrace_last_exn) || !reraise) { Caml_state->backtrace_pos = 0; caml_modify_root(Caml_state->backtrace_last_exn, exn); } if (Caml_state->backtrace_buffer == NULL && caml_alloc_backtrace_buffer() == -1) return; if (Caml_state->backtrace_pos >= BACKTRACE_BUFFER_SIZE) return; /* testing the code region is needed: PR#1554 */ if (find_debug_info(pc) != NULL) Caml_state->backtrace_buffer[Caml_state->backtrace_pos++] = pc; /* Traverse the stack and put all values pointing into bytecode into the backtrace buffer. */ value *trap_sp = Stack_high(Caml_state->current_stack) + Caml_state->trap_sp_off; for (/*nothing*/; sp < trap_sp; sp++) { if (Is_long(*sp)) { code_t p = Pc_val(*sp); if (Caml_state->backtrace_pos >= BACKTRACE_BUFFER_SIZE) break; if (find_debug_info(p) != NULL) Caml_state->backtrace_buffer[Caml_state->backtrace_pos++] = p; } } }
code_t caml_next_frame_pointer(value ** sp, intnat * trap_spoff) { code_t end_code = (code_t) ((char *) caml_start_code + caml_code_size); while (*sp < caml_stack_high) { value *p = (*sp)++; if(&Trap_pc(caml_stack_high + *trap_spoff) == p) { *trap_spoff = Trap_link(caml_stack_high + *trap_spoff); continue; } if (Is_long(*p) && Pc_val(*p) >= caml_start_code && Pc_val(*p) < end_code && find_debug_info((code_t)*p)) { return Pc_val(*p); } } return NULL; }