summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDenys Vlasenko <vda.linux@googlemail.com>2009-07-30 22:04:53 +0200
committerDenys Vlasenko <vda.linux@googlemail.com>2009-07-30 22:04:53 +0200
commit9baaee5c7e32f28f8a1a3b4afc37f05e3a7234bb (patch)
tree0b45e5d42a631fa08dc37ded018b549809bef2b5
parent99561425a915178f3f747f0d32dd13862b069098 (diff)
downloadabrt-9baaee5c7e32f28f8a1a3b4afc37f05e3a7234bb.tar.gz
abrt-9baaee5c7e32f28f8a1a3b4afc37f05e3a7234bb.tar.xz
abrt-9baaee5c7e32f28f8a1a3b4afc37f05e3a7234bb.zip
add utility functions
Logging machinery provided by this patch consists of several functions: +extern void error_msg(const char *s, ...) __attribute__ ((format (printf, 1, 2))); +extern void error_msg_and_die(const char *s, ...) __attribute__ ((noreturn, format (printf, 1, 2))); +extern void perror_msg(const char *s, ...) __attribute__ ((format (printf, 1, 2))); +extern void perror_msg_and_die(const char *s, ...) __attribute__ ((noreturn, format (printf, 1, 2))); +/* This is a macro since it collides with log() from math.h */ +#undef log +#define log(...) error_msg(__VA_ARGS__) They are taking printf-style format strings. perror_msg_xxx functions append an errno string after the message: "xxx xxx xxx: No such file or directory" if errno is != 0. xxx_and_die functions do not return. All functions also ensure that the message ends with "\n", meaning that you do not need to add it into the message, but if you do, an extra "\n" will not be added. All functions ensure that the string is written in a single write() call, thus if two processes output to the same terminal or file, messages don't get intermingled. Ordinarily, messages go to the stderr. By setting global variable "logmode" to LOGMODE_SYSLOG or LOGMODE_NONE, they can be sent to syslog or be suppressed. Standard setting is LOGMODE_STDIO. LOGMODE_STDIO + LOGMODE_SYSLOG works too. Usually it is set by main() as needed, and then you can fearlessly use [p]error_msg[_and_die]() and be sure that message goes to the right place. +enum { + LOGMODE_NONE = 0, + LOGMODE_STDIO = (1 << 0), + LOGMODE_SYSLOG = (1 << 1), + LOGMODE_BOTH = LOGMODE_SYSLOG + LOGMODE_STDIO, +}; +extern int logmode; Exit code of xxx_and_die variants is controlled by the global variable +extern int xfunc_error_retval; By default it is = 1. Logging infrastructure uses a few other functions, which I find useful on their own, and since I discussed them with Zdenek and he thinks that they may be useful too, they are included in the patch also. The first group is "malloc or die" group: +void* malloc_or_warn(size_t size); +void* xmalloc(size_t size); +void* xrealloc(void *ptr, size_t size); +void* xzalloc(size_t size); +char* xstrdup(const char *s); +char* xstrndup(const char *s, int n); They are basically versions of malloc etc which exit on failure. The next group are simple I/O wrappers: +extern ssize_t safe_read(int fd, void *buf, size_t count); +extern ssize_t full_read(int fd, void *buf, size_t count); +extern void xread(int fd, void *buf, size_t count); +extern ssize_t safe_write(int fd, const void *buf, size_t count); +extern ssize_t full_write(int fd, const void *buf, size_t count); safe_xxx deal with the fact that read and write operations may "fail" with EINTR and in many cases we want to just repeat the operation. full_xxx deal with the fact that read and write are not guaranteed to read or write exact amount, they may to transfer less bytes. In this case we need to loop. The next group are the "x functions": +extern void xwrite(int fd, const void *buf, size_t count); +extern void xwrite_str(int fd, const char *str); +void xpipe(int filedes[2]); +void xdup2(int from, int to); +off_t xlseek(int fd, off_t offset, int whence); +void xsetenv(const char *key, const char *value); +int xsocket(int domain, int type, int protocol); +void xbind(int sockfd, struct sockaddr *my_addr, socklen_t addrlen); +void xlisten(int s, int backlog); +ssize_t xsendto(int s, const void *buf, size_t len, const struct sockaddr *to, socklen_t tolen); +void xstat(const char *name, struct stat *stat_buf); +void xmove_fd(int from, int to); +char* xasprintf(const char *format, ...); They are similar to xmalloc in a sense that they exit on the failure. Most of them closely resemble corresponding libc functions. xmove_fd() is a wrapper for typical idiom "if (fd1!=fd2) dup2(fd1,fd2)", with error checking on dup2 failure added. xasprintf() is a "strcat on steroids". It's a printf-like function which returns a malloced string. In my experience, it is surprisingly useful: it makes complex concatenations easy in C. All these functions are declared in a new header, inc/abrtlib.h. It also contains a list of #includes: +#include <ctype.h> +#include <dirent.h> +#include <errno.h> +#include <fcntl.h> +#include <inttypes.h> +#include <setjmp.h> +#include <signal.h> +#include <stdio.h> +#include <stdlib.h> +#include <stdarg.h> +#include <stddef.h> +#include <string.h> +#include <sys/poll.h> +#include <sys/mman.h> +#include <sys/socket.h> +#include <sys/stat.h> +#include <sys/time.h> +#include <sys/types.h> +#include <sys/wait.h> +#include <termios.h> +#include <time.h> +#include <unistd.h> +/* Try to pull in PATH_MAX */ +#include <limits.h> +#include <sys/param.h> +#ifndef PATH_MAX +# define PATH_MAX 256 +#endif +#include <pwd.h> +#include <grp.h> The rationale to do so is that these headers are pretty standard, and by having them included in this one file, we won't need to add #includes into many .c[pp] files later. The slowdown from gcc parsing these headers even if they are not needed is not worth spending time on optimizing out. Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
-rw-r--r--inc/abrtlib.h102
-rw-r--r--lib/Plugins/CCpp.cpp27
-rw-r--r--lib/Utils/Makefile.am2
-rw-r--r--lib/Utils/logging.cpp119
-rw-r--r--lib/Utils/read_write.cpp93
-rw-r--r--lib/Utils/xfuncs.cpp214
-rw-r--r--src/Hooks/CCpp.cpp23
7 files changed, 556 insertions, 24 deletions
diff --git a/inc/abrtlib.h b/inc/abrtlib.h
new file mode 100644
index 00000000..82ad3443
--- /dev/null
+++ b/inc/abrtlib.h
@@ -0,0 +1,102 @@
+/*
+ * Utility routines.
+ *
+ * Licensed under GPLv2, see file COPYING in this tarball for details.
+ */
+#include <ctype.h>
+#include <dirent.h>
+#include <errno.h>
+#include <fcntl.h>
+#include <inttypes.h>
+#include <setjmp.h>
+#include <signal.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <stdarg.h>
+#include <stddef.h>
+#include <string.h>
+#include <sys/poll.h>
+#include <sys/mman.h>
+#include <sys/socket.h>
+#include <sys/stat.h>
+#include <sys/time.h>
+#include <sys/types.h>
+#include <sys/wait.h>
+#include <termios.h>
+#include <time.h>
+#include <unistd.h>
+/* Try to pull in PATH_MAX */
+#include <limits.h>
+#include <sys/param.h>
+#ifndef PATH_MAX
+# define PATH_MAX 256
+#endif
+#include <pwd.h>
+#include <grp.h>
+
+/* Some libc's forget to declare these, do it ourself */
+extern char **environ;
+#if defined(__GLIBC__) && __GLIBC__ < 2
+int vdprintf(int d, const char *format, va_list ap);
+#endif
+
+
+#define NORETURN __attribute__ ((noreturn))
+
+
+/* Logging */
+enum {
+ LOGMODE_NONE = 0,
+ LOGMODE_STDIO = (1 << 0),
+ LOGMODE_SYSLOG = (1 << 1),
+ LOGMODE_BOTH = LOGMODE_SYSLOG + LOGMODE_STDIO,
+};
+extern const char *msg_prefix;
+extern const char *msg_eol;
+extern int logmode;
+extern int xfunc_error_retval;
+extern void xfunc_die(void) NORETURN;
+extern void error_msg(const char *s, ...) __attribute__ ((format (printf, 1, 2)));
+extern void error_msg_and_die(const char *s, ...) __attribute__ ((noreturn, format (printf, 1, 2)));
+extern void perror_msg(const char *s, ...) __attribute__ ((format (printf, 1, 2)));
+extern void simple_perror_msg(const char *s);
+extern void perror_msg_and_die(const char *s, ...) __attribute__ ((noreturn, format (printf, 1, 2)));
+extern void simple_perror_msg_and_die(const char *s) NORETURN;
+extern void perror_nomsg_and_die(void) NORETURN;
+extern void perror_nomsg(void);
+extern void verror_msg(const char *s, va_list p, const char *strerr);
+/* This is a macro since it collides with log() from math.h */
+#undef log
+#define log(...) error_msg(__VA_ARGS__)
+
+void* malloc_or_warn(size_t size);
+void* xmalloc(size_t size);
+void* xrealloc(void *ptr, size_t size);
+void* xzalloc(size_t size);
+char* xstrdup(const char *s);
+char* xstrndup(const char *s, int n);
+
+extern ssize_t safe_read(int fd, void *buf, size_t count);
+// NB: will return short read on error, not -1,
+// if some data was read before error occurred
+extern ssize_t full_read(int fd, void *buf, size_t count);
+extern void xread(int fd, void *buf, size_t count);
+extern ssize_t safe_write(int fd, const void *buf, size_t count);
+// NB: will return short write on error, not -1,
+// if some data was written before error occurred
+extern ssize_t full_write(int fd, const void *buf, size_t count);
+extern void xwrite(int fd, const void *buf, size_t count);
+extern void xwrite_str(int fd, const char *str);
+
+void xpipe(int filedes[2]);
+void xdup2(int from, int to);
+off_t xlseek(int fd, off_t offset, int whence);
+void xsetenv(const char *key, const char *value);
+int xsocket(int domain, int type, int protocol);
+void xbind(int sockfd, struct sockaddr *my_addr, socklen_t addrlen);
+void xlisten(int s, int backlog);
+ssize_t xsendto(int s, const void *buf, size_t len, const struct sockaddr *to, socklen_t tolen);
+void xstat(const char *name, struct stat *stat_buf);
+
+void xmove_fd(int from, int to);
+char* xasprintf(const char *format, ...);
diff --git a/lib/Plugins/CCpp.cpp b/lib/Plugins/CCpp.cpp
index 1d442d6a..c38f19b9 100644
--- a/lib/Plugins/CCpp.cpp
+++ b/lib/Plugins/CCpp.cpp
@@ -18,6 +18,7 @@
with this program; if not, write to the Free Software Foundation, Inc.,
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
+#include "abrtlib.h"
#include "CCpp.h"
#include "ABRTException.h"
@@ -26,16 +27,16 @@
#include "CommLayerInner.h"
#include <fstream>
#include <sstream>
-#include <ctype.h>
-#include <unistd.h>
-#include <sys/types.h>
-#include <sys/wait.h>
-#include <fcntl.h>
-#include <stdlib.h>
-#include <string.h>
+//#include <ctype.h>
+//#include <unistd.h>
+//#include <sys/types.h>
+//#include <sys/wait.h>
+//#include <fcntl.h>
+//#include <stdlib.h>
+//#include <string.h>
#include <iomanip>
-#include <grp.h>
-#include <pwd.h>
+//#include <grp.h>
+//#include <pwd.h>
#include <nss.h>
#include <sechash.h>
@@ -537,16 +538,16 @@ void CAnalyzerCCpp::Init()
{
if (m_sOldCorePattern == CORE_PATTERN)
{
- fprintf(stderr, "warning: %s already contains %s, "
- "did abrt daemon crash recently?\n",
+ log("warning: %s already contains %s, "
+ "did abrt daemon crash recently?",
CORE_PATTERN_IFACE, CORE_PATTERN);
/* There is no point in "restoring" CORE_PATTERN_IFACE
* to CORE_PATTERN on exit. Will restore to a default value:
*/
m_sOldCorePattern = "core";
}
- fprintf(stderr, "warning: %s was already set to run a crash analyser (%s), "
- "abrt may interfere with it\b",
+ log("warning: %s was already set to run a crash analyser (%s), "
+ "abrt may interfere with it",
CORE_PATTERN_IFACE, CORE_PATTERN);
}
diff --git a/lib/Utils/Makefile.am b/lib/Utils/Makefile.am
index 0412e7ec..fb4f578a 100644
--- a/lib/Utils/Makefile.am
+++ b/lib/Utils/Makefile.am
@@ -1,5 +1,5 @@
lib_LTLIBRARIES = libABRTUtils.la
-libABRTUtils_la_SOURCES = DebugDump.cpp DebugDump.h
+libABRTUtils_la_SOURCES = DebugDump.cpp DebugDump.h logging.cpp read_write.cpp xfuncs.cpp
libABRTUtils_la_LDFLAGS = -version-info 0:1:0
libABRTUtils_la_LIBADD = -lmagic
libABRTUtils_la_CPPFLAGS = -I$(srcdir)/../../inc -I$(srcdir)/../../lib/CommLayer
diff --git a/lib/Utils/logging.cpp b/lib/Utils/logging.cpp
new file mode 100644
index 00000000..15104b8c
--- /dev/null
+++ b/lib/Utils/logging.cpp
@@ -0,0 +1,119 @@
+/*
+ * Utility routines.
+ *
+ * Licensed under GPLv2, see file COPYING in this tarball for details.
+ */
+#include "abrtlib.h"
+#include <syslog.h>
+
+int xfunc_error_retval = EXIT_FAILURE;
+
+void xfunc_die(void)
+{
+ exit(xfunc_error_retval);
+}
+
+const char *msg_prefix = "";
+const char *msg_eol = "\n";
+int logmode = LOGMODE_STDIO;
+
+void verror_msg(const char *s, va_list p, const char* strerr)
+{
+ char *msg;
+ int prefix_len, strerr_len, msgeol_len, used;
+
+ if (!logmode)
+ return;
+
+ if (!s) /* nomsg[_and_die] uses NULL fmt */
+ s = ""; /* some libc don't like printf(NULL) */
+
+ used = vasprintf(&msg, s, p);
+ if (used < 0)
+ return;
+
+ /* This is ugly and costs +60 bytes compared to multiple
+ * fprintf's, but is guaranteed to do a single write.
+ * This is needed for e.g. when multiple children
+ * can produce log messages simultaneously. */
+
+ prefix_len = strlen(msg_prefix);
+ strerr_len = strerr ? strlen(strerr) : 0;
+ msgeol_len = strlen(msg_eol);
+ /* +3 is for ": " before strerr and for terminating NUL */
+ msg = (char*) xrealloc(msg, prefix_len + used + strerr_len + msgeol_len + 3);
+ /* TODO: maybe use writev instead of memmoving? Need full_writev? */
+ if (prefix_len) {
+ memmove(msg + prefix_len, msg, used);
+ used += prefix_len;
+ strcpy(msg, msg_prefix);
+ }
+ if (strerr) {
+ if (s[0]) { /* not perror_nomsg? */
+ msg[used++] = ':';
+ msg[used++] = ' ';
+ }
+ strcpy(&msg[used], strerr);
+ used += strerr_len;
+ }
+ strcpy(&msg[used], msg_eol);
+
+ if (logmode & LOGMODE_STDIO) {
+ fflush(stdout);
+ full_write(STDERR_FILENO, msg, used + msgeol_len);
+ }
+ if (logmode & LOGMODE_SYSLOG) {
+ syslog(LOG_ERR, "%s", msg + prefix_len);
+ }
+ free(msg);
+}
+
+void error_msg_and_die(const char *s, ...)
+{
+ va_list p;
+
+ va_start(p, s);
+ verror_msg(s, p, NULL);
+ va_end(p);
+ xfunc_die();
+}
+
+void error_msg(const char *s, ...)
+{
+ va_list p;
+
+ va_start(p, s);
+ verror_msg(s, p, NULL);
+ va_end(p);
+}
+
+void perror_msg_and_die(const char *s, ...)
+{
+ va_list p;
+
+ va_start(p, s);
+ /* Guard against "<error message>: Success" */
+ verror_msg(s, p, errno ? strerror(errno) : NULL);
+ va_end(p);
+ xfunc_die();
+}
+
+void perror_msg(const char *s, ...)
+{
+ va_list p;
+
+ va_start(p, s);
+ /* Guard against "<error message>: Success" */
+ verror_msg(s, p, errno ? strerror(errno) : NULL);
+ va_end(p);
+}
+
+void simple_perror_msg_and_die(const char *s)
+{
+ perror_msg_and_die("%s", s);
+}
+
+void simple_perror_msg(const char *s)
+{
+ perror_msg("%s", s);
+}
diff --git a/lib/Utils/read_write.cpp b/lib/Utils/read_write.cpp
new file mode 100644
index 00000000..38907aa9
--- /dev/null
+++ b/lib/Utils/read_write.cpp
@@ -0,0 +1,93 @@
+/*
+ * Utility routines.
+ *
+ * Licensed under GPLv2 or later, see file COPYING in this tarball for details.
+ */
+#include "abrtlib.h"
+
+ssize_t safe_read(int fd, void *buf, size_t count)
+{
+ ssize_t n;
+
+ do {
+ n = read(fd, buf, count);
+ } while (n < 0 && errno == EINTR);
+
+ return n;
+}
+
+ssize_t full_read(int fd, void *buf, size_t len)
+{
+ ssize_t cc;
+ ssize_t total;
+
+ total = 0;
+
+ while (len) {
+ cc = safe_read(fd, buf, len);
+
+ if (cc < 0) {
+ if (total) {
+ /* we already have some! */
+ /* user can do another read to know the error code */
+ return total;
+ }
+ return cc; /* read() returns -1 on failure. */
+ }
+ if (cc == 0)
+ break;
+ buf = ((char *)buf) + cc;
+ total += cc;
+ len -= cc;
+ }
+
+ return total;
+}
+
+/* Die with an error message if we can't read the entire buffer. */
+void xread(int fd, void *buf, size_t count)
+{
+ if (count) {
+ ssize_t size = full_read(fd, buf, count);
+ if ((size_t)size != count)
+ error_msg_and_die("short read");
+ }
+}
+
+ssize_t safe_write(int fd, const void *buf, size_t count)
+{
+ ssize_t n;
+
+ do {
+ n = write(fd, buf, count);
+ } while (n < 0 && errno == EINTR);
+
+ return n;
+}
+
+ssize_t full_write(int fd, const void *buf, size_t len)
+{
+ ssize_t cc;
+ ssize_t total;
+
+ total = 0;
+
+ while (len) {
+ cc = safe_write(fd, buf, len);
+
+ if (cc < 0) {
+ if (total) {
+ /* we already wrote some! */
+ /* user can do another write to know the error code */
+ return total;
+ }
+ return cc; /* write() returns -1 on failure. */
+ }
+
+ total += cc;
+ buf = ((const char *)buf) + cc;
+ len -= cc;
+ }
+
+ return total;
+}
diff --git a/lib/Utils/xfuncs.cpp b/lib/Utils/xfuncs.cpp
new file mode 100644
index 00000000..ad67ec62
--- /dev/null
+++ b/lib/Utils/xfuncs.cpp
@@ -0,0 +1,214 @@
+/*
+ * Utility routines.
+ *
+ * Licensed under GPLv2, see file COPYING in this tarball for details.
+ */
+#include "abrtlib.h"
+
+static const char msg_memory_exhausted[] = "memory exhausted";
+
+void* malloc_or_warn(size_t size)
+{
+ void *ptr = malloc(size);
+ if (ptr == NULL && size != 0)
+ error_msg(msg_memory_exhausted);
+ return ptr;
+}
+
+// Die if we can't allocate size bytes of memory.
+void* xmalloc(size_t size)
+{
+ void *ptr = malloc(size);
+ if (ptr == NULL && size != 0)
+ error_msg_and_die(msg_memory_exhausted);
+ return ptr;
+}
+
+// Die if we can't resize previously allocated memory. (This returns a pointer
+// to the new memory, which may or may not be the same as the old memory.
+// It'll copy the contents to a new chunk and free the old one if necessary.)
+void* xrealloc(void *ptr, size_t size)
+{
+ ptr = realloc(ptr, size);
+ if (ptr == NULL && size != 0)
+ error_msg_and_die(msg_memory_exhausted);
+ return ptr;
+}
+
+// Die if we can't allocate and zero size bytes of memory.
+void* xzalloc(size_t size)
+{
+ void *ptr = xmalloc(size);
+ memset(ptr, 0, size);
+ return ptr;
+}
+
+// Die if we can't copy a string to freshly allocated memory.
+char* xstrdup(const char *s)
+{
+ char *t;
+
+ if (s == NULL)
+ return NULL;
+
+ t = strdup(s);
+
+ if (t == NULL)
+ error_msg_and_die(msg_memory_exhausted);
+
+ return t;
+}
+
+// Die if we can't allocate n+1 bytes (space for the null terminator) and copy
+// the (possibly truncated to length n) string into it.
+char* xstrndup(const char *s, int n)
+{
+ int m;
+ char *t;
+
+ /* We can just xmalloc(n+1) and strncpy into it, */
+ /* but think about xstrndup("abc", 10000) wastage! */
+ m = n;
+ t = (char*) s;
+ while (m) {
+ if (!*t) break;
+ m--;
+ t++;
+ }
+ n -= m;
+ t = (char*) xmalloc(n + 1);
+ t[n] = '\0';
+
+ return (char*) memcpy(t, s, n);
+}
+
+void xpipe(int filedes[2])
+{
+ if (pipe(filedes))
+ perror_msg_and_die("can't create pipe");
+}
+
+void xdup2(int from, int to)
+{
+ if (dup2(from, to) != to)
+ perror_msg_and_die("can't duplicate file descriptor");
+}
+
+// "Renumber" opened fd
+void xmove_fd(int from, int to)
+{
+ if (from == to)
+ return;
+ xdup2(from, to);
+ close(from);
+}
+
+// Die with an error message if we can't write the entire buffer.
+void xwrite(int fd, const void *buf, size_t count)
+{
+ if (count) {
+ ssize_t size = full_write(fd, buf, count);
+ if ((size_t)size != count)
+ error_msg_and_die("short write");
+ }
+}
+void xwrite_str(int fd, const char *str)
+{
+ xwrite(fd, str, strlen(str));
+}
+
+// Die with an error message if we can't lseek to the right spot.
+off_t xlseek(int fd, off_t offset, int whence)
+{
+ off_t off = lseek(fd, offset, whence);
+ if (off == (off_t)-1) {
+ if (whence == SEEK_SET)
+ perror_msg_and_die("lseek(%llu)", (long long)offset);
+ perror_msg_and_die("lseek");
+ }
+ return off;
+}
+
+// Die with an error message if we can't malloc() enough space and do an
+// sprintf() into that space.
+char* xasprintf(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);
+ return string_ptr;
+}
+
+void xsetenv(const char *key, const char *value)
+{
+ if (setenv(key, value, 1))
+ error_msg_and_die(msg_memory_exhausted);
+}
+
+// Die with an error message if we can't open a new socket.
+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";
+ if (domain == AF_INET6) s = "INET6";
+ perror_msg_and_die("socket(AF_%s)", s);
+ }
+
+ return r;
+}
+
+// Die with an error message if we can't bind a socket to an address.
+void xbind(int sockfd, struct sockaddr *my_addr, socklen_t addrlen)
+{
+ if (bind(sockfd, my_addr, addrlen)) perror_msg_and_die("bind");
+}
+
+// Die with an error message if we can't listen for connections on a socket.
+void xlisten(int s, int backlog)
+{
+ if (listen(s, backlog)) perror_msg_and_die("listen");
+}
+
+// Die with an error message if sendto failed.
+// Return bytes sent otherwise
+ssize_t xsendto(int s, const void *buf, size_t len, const struct sockaddr *to,
+ socklen_t tolen)
+{
+ ssize_t ret = sendto(s, buf, len, 0, to, tolen);
+ if (ret < 0) {
+ close(s);
+ perror_msg_and_die("sendto");
+ }
+ return ret;
+}
+
+// xstat() - a stat() which dies on failure with meaningful error message
+void xstat(const char *name, struct stat *stat_buf)
+{
+ if (stat(name, stat_buf))
+ perror_msg_and_die("can't stat '%s'", name);
+}
diff --git a/src/Hooks/CCpp.cpp b/src/Hooks/CCpp.cpp
index 017ecc42..ad6f30eb 100644
--- a/src/Hooks/CCpp.cpp
+++ b/src/Hooks/CCpp.cpp
@@ -18,17 +18,18 @@
with this program; if not, write to the Free Software Foundation, Inc.,
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
+#include "abrtlib.h"
#include "DebugDump.h"
#include "ABRTException.h"
-#include <stdlib.h>
-#include <string.h>
-#include <limits.h>
-#include <stdio.h>
-#include <sys/types.h>
-#include <sys/stat.h>
-#include <unistd.h>
-#include <time.h>
+//#include <stdlib.h>
+//#include <string.h>
+//#include <limits.h>
+//#include <stdio.h>
+//#include <sys/types.h>
+//#include <sys/stat.h>
+//#include <unistd.h>
+//#include <time.h>
#include <syslog.h>
#include <string>
@@ -132,6 +133,8 @@ int main(int argc, char** argv)
program_name);
return -1;
}
+ logmode = LOGMODE_SYSLOG;
+
const char* dddir = argv[1];
const char* pid = argv[2];
const char* signal = argv[3];
@@ -147,9 +150,9 @@ int main(int argc, char** argv)
}
if (!daemon_is_ok())
{
- fprintf(stderr, "abrt daemon is not running. If it crashed, "
+ log("abrt daemon is not running. If it crashed, "
"/proc/sys/kernel/core_pattern contains a stale value, "
- "consider resetting it to 'core'\n"
+ "consider resetting it to 'core'"
);
return 0;
}