char * sr_core_stacktrace_to_json(struct sr_core_stacktrace *stacktrace) { struct sr_strbuf *strbuf = sr_strbuf_new(); sr_strbuf_append_strf(strbuf, "{ \"signal\": %"PRIu16"\n", stacktrace->signal); if (stacktrace->executable) { sr_strbuf_append_str(strbuf, ", \"executable\": "); sr_json_append_escaped(strbuf, stacktrace->executable); sr_strbuf_append_str(strbuf, "\n"); } if (stacktrace->only_crash_thread) sr_strbuf_append_str(strbuf, ", \"only_crash_thread\": true\n"); sr_strbuf_append_str(strbuf, ", \"stacktrace\":\n"); struct sr_core_thread *thread = stacktrace->threads; while (thread) { if (thread == stacktrace->threads) sr_strbuf_append_str(strbuf, " [ "); else sr_strbuf_append_str(strbuf, " , "); bool crash_thread = (thread == stacktrace->crash_thread); /* If we don't know the crash thread, just take the first one. */ crash_thread |= (stacktrace->crash_thread == NULL && thread == stacktrace->threads); char *thread_json = sr_core_thread_to_json(thread, crash_thread); char *indented_thread_json = sr_indent_except_first_line(thread_json, 8); sr_strbuf_append_str(strbuf, indented_thread_json); free(indented_thread_json); free(thread_json); thread = thread->next; if (thread) sr_strbuf_append_str(strbuf, "\n"); } sr_strbuf_append_str(strbuf, " ]\n"); sr_strbuf_append_char(strbuf, '}'); return sr_strbuf_free_nobuf(strbuf); }
char * sr_python_stacktrace_to_json(struct sr_python_stacktrace *stacktrace) { struct sr_strbuf *strbuf = sr_strbuf_new(); /* Exception class name. */ if (stacktrace->exception_name) { sr_strbuf_append_str(strbuf, ", \"exception_name\": "); sr_json_append_escaped(strbuf, stacktrace->exception_name); sr_strbuf_append_str(strbuf, "\n"); } /* Frames. */ if (stacktrace->frames) { struct sr_python_frame *frame = stacktrace->frames; sr_strbuf_append_str(strbuf, ", \"stacktrace\":\n"); while (frame) { if (frame == stacktrace->frames) sr_strbuf_append_str(strbuf, " [ "); else sr_strbuf_append_str(strbuf, " , "); char *frame_json = sr_python_frame_to_json(frame); char *indented_frame_json = sr_indent_except_first_line(frame_json, 8); sr_strbuf_append_str(strbuf, indented_frame_json); free(indented_frame_json); free(frame_json); frame = frame->next; if (frame) sr_strbuf_append_str(strbuf, "\n"); } sr_strbuf_append_str(strbuf, " ]\n"); } if (strbuf->len > 0) strbuf->buf[0] = '{'; else sr_strbuf_append_char(strbuf, '{'); sr_strbuf_append_char(strbuf, '}'); return sr_strbuf_free_nobuf(strbuf); }
char * sr_elf_fde_to_json(struct sr_elf_fde *fde, bool recursive) { struct sr_strbuf *strbuf = sr_strbuf_new(); if (recursive) { struct sr_elf_fde *loop = fde; while (loop) { if (loop == fde) sr_strbuf_append_str(strbuf, "[ "); else sr_strbuf_append_str(strbuf, ", "); char *fde_json = sr_elf_fde_to_json(loop, false); char *indented_fde_json = sr_indent_except_first_line(fde_json, 2); sr_strbuf_append_str(strbuf, indented_fde_json); free(indented_fde_json); free(fde_json); loop = loop->next; if (loop) sr_strbuf_append_str(strbuf, "\n"); } sr_strbuf_append_str(strbuf, " ]"); } else { /* Start address. */ sr_strbuf_append_strf(strbuf, "{ \"start_address\": %"PRIu64"\n", fde->start_address); /* Length. */ sr_strbuf_append_strf(strbuf, ", \"length\": %"PRIu64"\n", fde->length); sr_strbuf_append_str(strbuf, "}"); } return sr_strbuf_free_nobuf(strbuf); }
char * sr_koops_stacktrace_to_json(struct sr_koops_stacktrace *stacktrace) { struct sr_strbuf *strbuf = sr_strbuf_new(); /* Raw oops. */ if (stacktrace->raw_oops) { sr_strbuf_append_str(strbuf, ", \"raw_oops\": "); sr_json_append_escaped(strbuf, stacktrace->raw_oops); sr_strbuf_append_str(strbuf, "\n"); } /* Kernel version. */ if (stacktrace->version) { sr_strbuf_append_str(strbuf, ", \"version\": "); sr_json_append_escaped(strbuf, stacktrace->version); sr_strbuf_append_str(strbuf, "\n"); } /* Kernel taint flags. */ char *taint_flags = taint_flags_to_json(stacktrace); char *indented_taint_flags = sr_indent_except_first_line(taint_flags, strlen(", \"taint_flags\": ")); free(taint_flags); sr_strbuf_append_strf(strbuf, ", \"taint_flags\": %s\n", indented_taint_flags); free(indented_taint_flags); /* Modules. */ if (stacktrace->modules) { sr_strbuf_append_strf(strbuf, ", \"modules\":\n"); sr_strbuf_append_str(strbuf, " [ "); char **module = stacktrace->modules; while (*module) { if (module != stacktrace->modules) sr_strbuf_append_str(strbuf, " , "); sr_json_append_escaped(strbuf, *module); ++module; if (*module) sr_strbuf_append_str(strbuf, "\n"); } sr_strbuf_append_str(strbuf, " ]\n"); } /* Frames. */ if (stacktrace->frames) { struct sr_koops_frame *frame = stacktrace->frames; sr_strbuf_append_str(strbuf, ", \"frames\":\n"); while (frame) { if (frame == stacktrace->frames) sr_strbuf_append_str(strbuf, " [ "); else sr_strbuf_append_str(strbuf, " , "); char *frame_json = sr_koops_frame_to_json(frame); char *indented_frame_json = sr_indent_except_first_line(frame_json, 8); sr_strbuf_append_str(strbuf, indented_frame_json); free(indented_frame_json); free(frame_json); frame = frame->next; if (frame) sr_strbuf_append_str(strbuf, "\n"); } sr_strbuf_append_str(strbuf, " ]\n"); } if (strbuf->len > 0) strbuf->buf[0] = '{'; else sr_strbuf_append_char(strbuf, '{'); sr_strbuf_append_char(strbuf, '}'); return sr_strbuf_free_nobuf(strbuf); }