]> git.ozlabs.org Git - ccan/blobdiff - ccan/failtest/failtest.c
failtest: Remove memory leak
[ccan] / ccan / failtest / failtest.c
index 104628352dd580a61e22bb5ff0743b35e0267ad5..c61ce442a5d03b39444a87a468514f23c6f3c962 100644 (file)
@@ -5,7 +5,6 @@
 #include <stdio.h>
 #include <stdarg.h>
 #include <ctype.h>
-#include <err.h>
 #include <unistd.h>
 #include <poll.h>
 #include <errno.h>
@@ -17,6 +16,7 @@
 #include <sys/resource.h>
 #include <signal.h>
 #include <assert.h>
+#include <ccan/err/err.h>
 #include <ccan/time/time.h>
 #include <ccan/read_write_all/read_write_all.h>
 #include <ccan/failtest/failtest_proto.h>
@@ -91,7 +91,7 @@ static int control_fd = -1;
 /* If we're a child, this is the first call we did ourselves. */
 static struct failtest_call *our_history_start = NULL;
 /* For printing runtime with --trace. */
-static struct timeval start;
+static struct timeabs start;
 /* Set when failtest_hook returns FAIL_PROBE */
 static bool probing = false;
 /* Table to track duplicates. */
@@ -613,8 +613,10 @@ static NORETURN void failtest_cleanup(bool forced_cleanup, int status)
 
                /* But their program shouldn't leak, even on failure. */
                if (!forced_cleanup && i->can_leak) {
+                       char *p = failpath_string();
                        printf("Leak at %s:%u: --failpath=%s\n",
-                              i->file, i->line, failpath_string());
+                              i->file, i->line, p);
+                       free(p);
                        status = 1;
                }
        }
@@ -761,13 +763,13 @@ static bool should_fail(struct failtest_call *call)
        if (child == 0) {
                traceindent++;
                if (tracef) {
-                       struct timeval diff;
+                       struct timerel diff;
                        const char *p;
                        char *failpath;
                        struct failtest_call *c;
 
                        c = tlist_tail(&history, list);
-                       diff = time_sub(time_now(), start);
+                       diff = time_between(time_now(), start);
                        failpath = failpath_string();
                        p = strrchr(c->file, '/');
                        if (p)
@@ -776,7 +778,7 @@ static bool should_fail(struct failtest_call *call)
                                p = c->file;
                        trace("%u->%u (%u.%02u): %s (%s:%u)\n",
                              getppid(), getpid(),
-                             (int)diff.tv_sec, (int)diff.tv_usec / 10000,
+                             (int)diff.ts.tv_sec, (int)diff.ts.tv_nsec / 10000000,
                              failpath, p, c->line);
                        free(failpath);
                }
@@ -1085,8 +1087,8 @@ int failtest_open(const char *pathname,
        call.closed = false;
        if (call.flags & O_CREAT) {
                call.mode = va_arg(ap, int);
-               va_end(ap);
        }
+       va_end(ap);
        p = add_history(FAILTEST_OPEN, true, file, line, &call);
        /* Avoid memory leak! */
        if (p == &unrecorded_call)
@@ -1177,6 +1179,15 @@ void *failtest_mmap(void *addr, size_t length, int prot, int flags,
        return p->u.mmap.ret;
 }
 
+/* Since OpenBSD can't handle adding args, we use this file and line.
+ * This will make all mmaps look the same, reducing coverage. */
+void *failtest_mmap_noloc(void *addr, size_t length, int prot, int flags,
+                         int fd, off_t offset)
+{
+       return failtest_mmap(addr, length, prot, flags, fd, offset,
+                            __FILE__, __LINE__);
+}
+
 static void cleanup_pipe(struct pipe_call *call, bool restore)
 {
        trace("cleaning up pipe fd=%i%s,%i%s\n",
@@ -1251,7 +1262,7 @@ static ssize_t failtest_add_read(int fd, void *buf, size_t count, off_t off,
                                set_cleanup(p, cleanup_read, struct read_call);
                }
        }
-       trace("%sread %s:%u fd %i %zu@%llu -> %i\n",
+       trace("%sread %s:%u fd %i %zu@%llu -> %zi\n",
              is_pread ? "p" : "", file, line, fd, count, (long long)off,
              p->u.read.ret);
        errno = p->error;
@@ -1353,7 +1364,7 @@ static ssize_t failtest_add_write(int fd, const void *buf,
                else
                        p->u.write.ret = write(fd, buf, count);
        }
-       trace("%swrite %s:%i %zu@%llu on fd %i -> %i\n",
+       trace("%swrite %s:%i %zu@%llu on fd %i -> %zi\n",
              p->u.write.is_pwrite ? "p" : "",
              file, line, count, (long long)off, fd, p->u.write.ret);
        errno = p->error;