If the argument (-u PROBLEM) is used, abrt-dump-oops saves the data obtained from input in the passed problem directory.
Related to #662
Signed-off-by: Jakub Filak jfilak@redhat.com --- src/plugins/abrt-dump-oops.c | 129 +++++++++++++++++++++++++++---------------- 1 file changed, 80 insertions(+), 49 deletions(-)
diff --git a/src/plugins/abrt-dump-oops.c b/src/plugins/abrt-dump-oops.c index 2c8612e..6c4e8eb 100644 --- a/src/plugins/abrt-dump-oops.c +++ b/src/plugins/abrt-dump-oops.c @@ -108,6 +108,56 @@ static char *list_of_tainted_modules(const char *proc_modules) return strbuf_free_nobuf(result); }
+static void save_oops_data_in_dump_dir(struct dump_dir *dd, char *oops, const char *proc_modules) +{ + char *first_line = oops; + char *second_line = (char*)strchr(first_line, '\n'); /* never NULL */ + *second_line++ = '\0'; + + dd_save_text(dd, FILENAME_KERNEL, first_line); + dd_save_text(dd, FILENAME_BACKTRACE, second_line); + + /* check if trace doesn't have line: 'Your BIOS is broken' */ + char *broken_bios = strstr(second_line, "Your BIOS is broken"); + if (broken_bios) + dd_save_text(dd, FILENAME_NOT_REPORTABLE, "Your BIOS is broken."); + else + { + char *tainted_short = kernel_tainted_short(second_line); + if (tainted_short) + { + VERB1 log("Kernel is tainted '%s'", tainted_short); + dd_save_text(dd, FILENAME_TAINTED_SHORT, tainted_short); + + char *tnt_long = kernel_tainted_long(tainted_short); + dd_save_text(dd, FILENAME_TAINTED_LONG, tnt_long); + free(tnt_long); + + struct strbuf *reason = strbuf_new(); + const char *fmt = _("A kernel problem occurred, but your kernel has been " + "tainted (flags:%s). Kernel maintainers are unable to " + "diagnose tainted reports."); + strbuf_append_strf(reason, fmt, tainted_short); + + char *modlist = !proc_modules ? NULL : list_of_tainted_modules(proc_modules); + if (modlist) + { + strbuf_append_strf(reason, _(" Tainted modules: %s."), modlist); + free(modlist); + } + + dd_save_text(dd, FILENAME_NOT_REPORTABLE, reason->buf); + strbuf_free(reason); + free(tainted_short); + } + } + + // TODO: add "Kernel oops: " prefix, so that all oopses have recognizable FILENAME_REASON? + // kernel oops 1st line may look quite puzzling otherwise... + strchrnul(second_line, '\n')[0] = '\0'; + dd_save_text(dd, FILENAME_REASON, second_line); +} + /* returns number of errors */ static unsigned save_oops_to_dump_dir(GList *oops_list, unsigned oops_cnt) { @@ -137,10 +187,6 @@ static unsigned save_oops_to_dump_dir(GList *oops_list, unsigned oops_cnt) unsigned errors = 0; while (idx < oops_cnt && --countdown != 0) { - char *first_line = (char*)g_list_nth_data(oops_list, idx++); - char *second_line = (char*)strchr(first_line, '\n'); /* never NULL */ - *second_line++ = '\0'; - struct dump_dir *dd; { char base[sizeof("oops-YYYY-MM-DD-hh:mm:ss-%lu-%lu") + 2 * sizeof(long)*3]; @@ -152,12 +198,11 @@ static unsigned save_oops_to_dump_dir(GList *oops_list, unsigned oops_cnt)
if (dd) { + save_oops_data_in_dump_dir(dd, (char*)g_list_nth_data(oops_list, idx++), proc_modules); dd_create_basic_files(dd, /*uid:*/ my_euid, NULL); dd_save_text(dd, FILENAME_ABRT_VERSION, VERSION); dd_save_text(dd, FILENAME_ANALYZER, "Kerneloops"); dd_save_text(dd, FILENAME_TYPE, "Kerneloops"); - dd_save_text(dd, FILENAME_KERNEL, first_line); - dd_save_text(dd, FILENAME_BACKTRACE, second_line); if (cmdline_str) dd_save_text(dd, FILENAME_CMDLINE, cmdline_str); if (proc_modules) @@ -166,46 +211,6 @@ static unsigned save_oops_to_dump_dir(GList *oops_list, unsigned oops_cnt) dd_save_text(dd, "fips_enabled", fips_enabled); if (suspend_stats) dd_save_text(dd, "suspend_stats", suspend_stats); - - /* check if trace doesn't have line: 'Your BIOS is broken' */ - char *broken_bios = strstr(second_line, "Your BIOS is broken"); - if (broken_bios) - dd_save_text(dd, FILENAME_NOT_REPORTABLE, "Your BIOS is broken."); - else - { - char *tainted_short = kernel_tainted_short(second_line); - if (tainted_short) - { - VERB1 log("Kernel is tainted '%s'", tainted_short); - dd_save_text(dd, FILENAME_TAINTED_SHORT, tainted_short); - - char *tnt_long = kernel_tainted_long(tainted_short); - dd_save_text(dd, FILENAME_TAINTED_LONG, tnt_long); - free(tnt_long); - - struct strbuf *reason = strbuf_new(); - const char *fmt = _("A kernel problem occurred, but your kernel has been " - "tainted (flags:%s). Kernel maintainers are unable to " - "diagnose tainted reports."); - strbuf_append_strf(reason, fmt, tainted_short); - - char *modlist = !proc_modules ? NULL : list_of_tainted_modules(proc_modules); - if (modlist) - { - strbuf_append_strf(reason, _(" Tainted modules: %s."), modlist); - free(modlist); - } - - dd_save_text(dd, FILENAME_NOT_REPORTABLE, reason->buf); - strbuf_free(reason); - free(tainted_short); - } - } - -// TODO: add "Kernel oops: " prefix, so that all oopses have recognizable FILENAME_REASON? -// kernel oops 1st line may look quite puzzling otherwise... - strchrnul(second_line, '\n')[0] = '\0'; - dd_save_text(dd, FILENAME_REASON, second_line); dd_close(dd); } else @@ -233,7 +238,7 @@ int main(int argc, char **argv)
/* Can't keep these strings/structs static: _() doesn't support that */ const char *program_usage_string = _( - "& [-vsoxm] [-d DIR]/[-D] [FILE]\n" + "& [-vusoxm] [-d DIR]/[-D] [FILE]\n" "\n" "Extract oops from FILE (or standard input)" ); @@ -243,9 +248,11 @@ int main(int argc, char **argv) OPT_o = 1 << 2, OPT_d = 1 << 3, OPT_D = 1 << 4, - OPT_x = 1 << 5, - OPT_m = 1 << 6, + OPT_u = 1 << 5, + OPT_x = 1 << 6, + OPT_m = 1 << 7, }; + char *problem_dir = NULL; /* Keep enum above and order of options below in sync! */ struct options program_options[] = { OPT__VERBOSE(&g_verbose), @@ -256,6 +263,7 @@ int main(int argc, char **argv) */ OPT_STRING('d', NULL, &debug_dumps_dir, "DIR", _("Create new problem directory in DIR for every oops found")), OPT_BOOL( 'D', NULL, NULL, _("Same as -d DumpLocation, DumpLocation is specified in abrt.conf")), + OPT_STRING('u', NULL, &problem_dir, "PROBLEM", _("Save the extracted information in PROBLEM")), OPT_BOOL( 'x', NULL, NULL, _("Make the problem directory world readable")), OPT_BOOL( 'm', NULL, NULL, _("Print search string(s) to stdout and exit")), OPT_END() @@ -337,6 +345,29 @@ int main(int argc, char **argv) oops_cnt ); } + if (opts & OPT_u) + { + log("Updating problem directory"); + switch(g_list_length(oops_list)) + { + case 0: + error_msg(_("Cannot update the problem because of no oops found")); + break; + case 1: + { + struct dump_dir *dd = dd_opendir(problem_dir, /*open for writing*/0); + if (dd) + { + save_oops_data_in_dump_dir(dd, (char *)oops_list->data, /*no proc modules*/NULL); + dd_close(dd); + } + } + break; + default: + error_msg(_("Cannot update the problem because of more oopses were found")); + break; + } + } } list_free_with_free(oops_list); //oops_list = NULL;
Closes #662
Signed-off-by: Jakub Filak jfilak@redhat.com --- src/hooks/abrt-harvest-vmcore.in | 8 ++++++++ src/plugins/abrt-action-analyze-vmcore.in | 24 +----------------------- src/plugins/vmcore_event.conf | 14 ++++++++++++-- 3 files changed, 21 insertions(+), 25 deletions(-)
diff --git a/src/hooks/abrt-harvest-vmcore.in b/src/hooks/abrt-harvest-vmcore.in index 59bad31..99022d9 100644 --- a/src/hooks/abrt-harvest-vmcore.in +++ b/src/hooks/abrt-harvest-vmcore.in @@ -62,11 +62,19 @@ for d in *; do printf 'vmcore' >"$dst.new/type" printf 'kernel' >"$dst.new/component" printf '%s' "`date '+%s'`" >"$dst.new/time" + printf '%s' "`uname -i`" >"$dst.new/architecture" + cp "$dst.new/time" "$dst.new/last_occurrence" printf '0' >"$dst.new/uid" # TODO: need to generate *real* UUID, # one which has a real chance of catching dups! # This one generates different hashes even for similar cores: printf '%s' "`sha1sum <"$dst.new/vmcore" | cut -d" " -f1`" >"$dst.new/uuid" + cp /etc/system-release "$dst.new/os_release" || { + cp /etc/redhat-release "$dst.new/os_release" || { + cp /etc/SuSE-release "$dst.new/os_release" + } + } + cp /etc/os-release "$dst.new/os_info"
chown -R 0:0 -- "$dst.new" chmod -R u+rwX,go-rwxst -- "$dst.new" diff --git a/src/plugins/abrt-action-analyze-vmcore.in b/src/plugins/abrt-action-analyze-vmcore.in index c78ba03..9475137 100644 --- a/src/plugins/abrt-action-analyze-vmcore.in +++ b/src/plugins/abrt-action-analyze-vmcore.in @@ -129,29 +129,7 @@ if __name__ == "__main__": out, err = crash.communicate(input="log") log_file.close() backtrace_file = open("backtrace", "w") - dump_oops = Popen(["abrt-dump-oops", "-o", "kernel_log"], stdout=backtrace_file, bufsize=-1) + dump_oops = Popen(["abrt-dump-oops", "-u", ".", "kernel_log"], stdout=backtrace_file, bufsize=-1) backtrace_file.close() - ret = dump_oops.wait() - if ret != RETURN_OK: - sys.exit(ret) - - ret = RETURN_FAILURE - # Save kernel version in 'kernel' file (FILENAME_KERNEL) - # The code below expects that abrt-dump-oops generates file in the following format: - # <empty line> - # Version: 3.8.5-201.fc18.x86_64 - # <oops data> - # <EOF> - with open("backtrace", "r") as backtrace_file: - for line in backtrace_file: - # Please excuse the magic constant 9 => len('Version: '). This construction is more readable for me. - if line[:9] == "Version: ": - with open("kernel", "w") as kernel_file: - kernel_file.write(line[9:].rstrip()) - ret = RETURN_OK # set OK only if it was successfully written - break # break the loop, we support only one oops per vmcore - if ret != RETURN_OK: - print _("Garbled abrt-dump-oops output format. Can't find kernel version."); - sys.exit(ret) diff --git a/src/plugins/vmcore_event.conf b/src/plugins/vmcore_event.conf index 0e15b7f..f6e260e 100644 --- a/src/plugins/vmcore_event.conf +++ b/src/plugins/vmcore_event.conf @@ -1,7 +1,9 @@ # analyze EVENT=analyze_VMcore analyzer=vmcore - abrt-action-analyze-vmcore - abrt-action-generate-core-backtrace + abrt-action-analyze-vmcore && + abrt-action-analyze-oops && + abrt-action-generate-core-backtrace && + abrt-action-save-kernel-data
# If you want behavior similar to one provided by kerneloops daemon # distributed by kerneloops.org - that is, if you want @@ -14,6 +16,14 @@ EVENT=analyze_VMcore analyzer=vmcore EVENT=report_Kerneloops analyzer=vmcore reporter-kerneloops
+EVENT=report_Bugzilla analyzer=vmcore + reporter-bugzilla -b \ + -F /etc/libreport/plugins/bugzilla_format_kernel.conf + +# Send micro report +EVENT=report_uReport analyzer=vmcore + /usr/libexec/abrt-action-ureport + EVENT=report-gui analyzer=vmcore report-gtk -e analyze_VMcore -e report_uReport -e "collect_*" -e report_Bugzilla -e post_report -- "$DUMP_DIR"
All three patches seems to do what is expected so I pushed them - I took the liberty of renaming save_oops_to_dump_dir to create_oops_dump_dirs to avoid confusion with save_oops_data_in_dump_dir, hope it's OK.
Thanks, Martin
Thank you very much indeed!
I noticed the similarity between names but I didn't change the old name because of "minimum changes" approach.
Regards, Jakub
----- Original Message ----- From: "Martin Milata" mmilata@redhat.com To: "Jakub Filak" jfilak@redhat.com Cc: "Crash-Catcher" crash-catcher@lists.fedorahosted.org Sent: Friday, June 7, 2013 5:49:04 PM Subject: Re: [ABRT PATCH 1/2] a-d-oops: add 'update' command line argument
All three patches seems to do what is expected so I pushed them - I took the liberty of renaming save_oops_to_dump_dir to create_oops_dump_dirs to avoid confusion with save_oops_data_in_dump_dir, hope it's OK.
Thanks, Martin
crash-catcher@lists.fedorahosted.org