diff options
author | Denys Vlasenko <vda.linux@googlemail.com> | 2009-08-05 19:04:44 +0200 |
---|---|---|
committer | Denys Vlasenko <vda.linux@googlemail.com> | 2009-08-05 19:04:44 +0200 |
commit | 8336bbee624aa84b485e3f6b0984bce04b52e61d (patch) | |
tree | 7bd7ad50971d9029265bdc5cf03d2963c017326e | |
parent | 35d4ceb1fa329e2adba6af29cde8cb1a805522c1 (diff) | |
download | abrt-8336bbee624aa84b485e3f6b0984bce04b52e61d.tar.gz abrt-8336bbee624aa84b485e3f6b0984bce04b52e61d.tar.xz abrt-8336bbee624aa84b485e3f6b0984bce04b52e61d.zip |
Hooks/CCpp.cpp: don't dump executables with "/abrt" substring in the name
some cleanups and abrtlib work crept in too...
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
-rw-r--r-- | inc/abrtlib.h | 3 | ||||
-rw-r--r-- | lib/Utils/xfuncs.cpp | 30 | ||||
-rw-r--r-- | src/Hooks/CCpp.cpp | 93 |
3 files changed, 88 insertions, 38 deletions
diff --git a/inc/abrtlib.h b/inc/abrtlib.h index 65e8fb8f..29c8b5e8 100644 --- a/inc/abrtlib.h +++ b/inc/abrtlib.h @@ -36,6 +36,8 @@ #endif #include <pwd.h> #include <grp.h> +/* C++ bits */ +#include <string> /* Some libc's forget to declare these, do it ourself */ extern char **environ; @@ -103,6 +105,7 @@ void xstat(const char *name, struct stat *stat_buf); void xmove_fd(int from, int to); char* xasprintf(const char *format, ...); +std::string ssprintf(const char *format, ...); /* copyfd_XX print read/write errors and return -1 if they occur */ off_t copyfd_eof(int src_fd, int dst_fd); diff --git a/lib/Utils/xfuncs.cpp b/lib/Utils/xfuncs.cpp index ad67ec62..078c8045 100644 --- a/lib/Utils/xfuncs.cpp +++ b/lib/Utils/xfuncs.cpp @@ -158,6 +158,35 @@ char* xasprintf(const char *format, ...) return string_ptr; } +std::string ssprintf(const char *format, ...) +{ + va_list p; + int r; + char *string_ptr; + +#if 1 + // GNU extension + va_start(p, format); + r = vasprintf(&string_ptr, format, p); + va_end(p); +#else + // Bloat for systems that haven't got the GNU extension. + va_start(p, format); + r = vsnprintf(NULL, 0, format, p); + va_end(p); + string_ptr = xmalloc(r+1); + va_start(p, format); + r = vsnprintf(string_ptr, r+1, format, p); + va_end(p); +#endif + + if (r < 0) + error_msg_and_die(msg_memory_exhausted); + std::string res = string_ptr; + free(string_ptr); + return res; +} + void xsetenv(const char *key, const char *value) { if (setenv(key, value, 1)) @@ -170,7 +199,6 @@ int xsocket(int domain, int type, int protocol) int r = socket(domain, type, protocol); if (r < 0) { - /* Hijack vaguely related config option */ const char *s = "INET"; if (domain == AF_PACKET) s = "PACKET"; if (domain == AF_NETLINK) s = "NETLINK"; diff --git a/src/Hooks/CCpp.cpp b/src/Hooks/CCpp.cpp index ddbebf6f..9cce943e 100644 --- a/src/Hooks/CCpp.cpp +++ b/src/Hooks/CCpp.cpp @@ -31,12 +31,12 @@ #define VAR_RUN_PID_FILE VAR_RUN"/abrt.pid" -static char* get_executable(const char* pid) +static char* get_executable(pid_t pid) { char buf[PATH_MAX + 1]; int len; - snprintf(buf, sizeof(buf), "/proc/%s/exe", pid); + snprintf(buf, sizeof(buf), "/proc/%u/exe", (int)pid); len = readlink(buf, buf, sizeof(buf)-1); if (len >= 0) { @@ -49,31 +49,38 @@ static char* get_executable(const char* pid) // taken from kernel #define COMMAND_LINE_SIZE 2048 -static char* get_cmdline(const char* pid) +static char* get_cmdline(pid_t pid) { char path[PATH_MAX]; char cmdline[COMMAND_LINE_SIZE]; - snprintf(path, sizeof(path), "/proc/%s/cmdline", pid); - FILE* fp = fopen(path, "r"); - int ch; - int ii = 0; - if (fp) + snprintf(path, sizeof(path), "/proc/%u/cmdline", (int)pid); + int dst = 0; + + int fd = open(path, O_RDONLY); + if (fd >= 0) { - while ((ch = fgetc(fp)) != EOF && ii < COMMAND_LINE_SIZE-1) + int len = read(fd, cmdline, sizeof(cmdline) - 1); + if (len >= 0) { - if (ch == 0) - { - cmdline[ii] = ' '; - } - else if (isspace(ch) || (isascii(ch) && !iscntrl(ch))) + int src = 0; + while (src < len) { - cmdline[ii] = ch; + char ch = cmdline[src++]; + if (ch == '\0') + { + cmdline[dst++] = ' '; + } + /* TODO: maybe just ch >= ' '? */ + else if (isspace(ch) || (isascii(ch) && !iscntrl(ch))) + { + cmdline[dst++] = ch; + } } - ii++; } - fclose(fp); + close(fd); } - cmdline[ii] = '\0'; + cmdline[dst] = '\0'; + return xstrdup(cmdline); } @@ -118,20 +125,27 @@ int main(int argc, char** argv) logmode = LOGMODE_SYSLOG; const char* dddir = argv[1]; - const char* pid = argv[2]; - const char* signal = argv[3]; - const char* uid = argv[4]; - - if (strcmp(signal, "3") != 0 && // SIGQUIT - strcmp(signal, "4") != 0 && // SIGILL - strcmp(signal, "6") != 0 && // SIGABRT - strcmp(signal, "8") != 0 && // SIGFPE - strcmp(signal, "11") != 0) // SIGSEGV - { + pid_t pid = atoi(argv[2]); + const char* signal_str = argv[3]; + int signal = atoi(argv[3]); + uid_t uid = atoi(argv[4]); + + if (signal != SIGQUIT + && signal != SIGILL + && signal != SIGABRT + && signal != SIGFPE + && signal != SIGSEGV + ) { + /* not an error, exit silently */ return 0; } + if (pid <= 0 || uid < 0) + { + error_msg_and_die("pid '%s' or uid '%s' are bogus", argv[2], argv[4]); + } if (!daemon_is_ok()) { + /* not an error, exit with exitcode 0 */ log("abrt daemon is not running. If it crashed, " "/proc/sys/kernel/core_pattern contains a stale value, " "consider resetting it to 'core'" @@ -141,30 +155,35 @@ int main(int argc, char** argv) try { - int fd; - CDebugDump dd; - char path[PATH_MAX]; char* executable; char* cmdline; - executable = get_executable(pid); cmdline = get_cmdline(pid); if (executable == NULL || cmdline == NULL) { + error_msg_and_die("can not get proc info for pid %u", (int)pid); + } + if (strstr(executable, "/abrt")) + { /* free(executable); - why bother? */ /* free(cmdline); */ - error_msg_and_die("can not get proc info for pid %s", pid); + error_msg_and_die("pid %u is '%s', not dumping it to avoid abrt recursion", + (int)pid, executable); } - snprintf(path, sizeof(path), "%s/ccpp-%ld-%s", dddir, (long)time(NULL), pid); - dd.Create(path, uid); + char path[PATH_MAX]; + snprintf(path, sizeof(path), "%s/ccpp-%ld-%u", dddir, (long)time(NULL), (int)pid); + + CDebugDump dd; + dd.Create(path, ssprintf("%u", (int)uid)); dd.SaveText(FILENAME_ANALYZER, "CCpp"); dd.SaveText(FILENAME_EXECUTABLE, executable); dd.SaveText(FILENAME_CMDLINE, cmdline); - dd.SaveText(FILENAME_REASON, std::string("Process was terminated by signal ") + signal); + dd.SaveText(FILENAME_REASON, std::string("Process was terminated by signal ") + signal_str); snprintf(path + strlen(path), sizeof(path), "/%s", FILENAME_COREDUMP); + int fd; fd = open(path, O_WRONLY | O_CREAT | O_TRUNC, 0600); if (fd < 0) { @@ -185,7 +204,7 @@ int main(int argc, char** argv) /* free(executable); */ /* free(cmdline); */ dd.Close(); - log("saved core dump of pid %s to %s", pid, path); + log("saved core dump of pid %u to %s", (int)pid, path); } catch (CABRTException& e) { |