Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/trunk]: src/usr.bin/make Revert the filemon removal in bmake, as pointed...



details:   https://anonhg.NetBSD.org/src/rev/fffbd56e7fc1
branches:  trunk
changeset: 466369:fffbd56e7fc1
user:      maxv <maxv%NetBSD.org@localhost>
date:      Thu Dec 19 07:14:07 2019 +0000

description:
Revert the filemon removal in bmake, as pointed out by maya we do care
about not introducing divergence with FreeBSD, and the cost of unused
is acceptable here.

diffstat:

 usr.bin/make/Makefile |    6 +-
 usr.bin/make/compat.c |   11 ++-
 usr.bin/make/make.1   |   16 +++-
 usr.bin/make/meta.c   |  166 +++++++++++++++++++++++++++++++++++++++++++++++++-
 4 files changed, 190 insertions(+), 9 deletions(-)

diffs (truncated from 328 to 300 lines):

diff -r 825501ed17a0 -r fffbd56e7fc1 usr.bin/make/Makefile
--- a/usr.bin/make/Makefile     Thu Dec 19 00:52:29 2019 +0000
+++ b/usr.bin/make/Makefile     Thu Dec 19 07:14:07 2019 +0000
@@ -1,4 +1,4 @@
-#      $NetBSD: Makefile,v 1.64 2019/12/18 07:37:19 maxv Exp $
+#      $NetBSD: Makefile,v 1.65 2019/12/19 07:14:07 maxv Exp $
 #      @(#)Makefile    5.2 (Berkeley) 12/28/90
 
 PROG=  make
@@ -17,6 +17,10 @@
 .if ${USE_META:tl} != "no"
 SRCS+= meta.c
 CPPFLAGS+= -DUSE_META
+FILEMON_H ?= ${.CURDIR:H:H}/sys/dev/filemon/filemon.h
+.if exists(${FILEMON_H}) && ${FILEMON_H:T} == "filemon.h"
+COPTS.meta.c += -DHAVE_FILEMON_H -I${FILEMON_H:H}
+.endif
 .endif
 
 .PATH: ${.CURDIR}/lst.lib
diff -r 825501ed17a0 -r fffbd56e7fc1 usr.bin/make/compat.c
--- a/usr.bin/make/compat.c     Thu Dec 19 00:52:29 2019 +0000
+++ b/usr.bin/make/compat.c     Thu Dec 19 07:14:07 2019 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: compat.c,v 1.108 2019/12/18 07:37:19 maxv Exp $        */
+/*     $NetBSD: compat.c,v 1.109 2019/12/19 07:14:07 maxv Exp $        */
 
 /*
  * Copyright (c) 1988, 1989, 1990 The Regents of the University of California.
@@ -70,14 +70,14 @@
  */
 
 #ifndef MAKE_NATIVE
-static char rcsid[] = "$NetBSD: compat.c,v 1.108 2019/12/18 07:37:19 maxv Exp $";
+static char rcsid[] = "$NetBSD: compat.c,v 1.109 2019/12/19 07:14:07 maxv Exp $";
 #else
 #include <sys/cdefs.h>
 #ifndef lint
 #if 0
 static char sccsid[] = "@(#)compat.c   8.2 (Berkeley) 3/19/94";
 #else
-__RCSID("$NetBSD: compat.c,v 1.108 2019/12/18 07:37:19 maxv Exp $");
+__RCSID("$NetBSD: compat.c,v 1.109 2019/12/19 07:14:07 maxv Exp $");
 #endif
 #endif /* not lint */
 #endif
@@ -426,6 +426,11 @@
                status = WSTOPSIG(reason);              /* stopped */
            } else if (WIFEXITED(reason)) {
                status = WEXITSTATUS(reason);           /* exited */
+#if defined(USE_META) && defined(USE_FILEMON_ONCE)
+               if (useMeta) {
+                   meta_cmd_finish(NULL);
+               }
+#endif
                if (status != 0) {
                    if (DEBUG(ERROR)) {
                        fprintf(debug_file, "\n*** Failed target:  %s\n*** Failed command: ",
diff -r 825501ed17a0 -r fffbd56e7fc1 usr.bin/make/make.1
--- a/usr.bin/make/make.1       Thu Dec 19 00:52:29 2019 +0000
+++ b/usr.bin/make/make.1       Thu Dec 19 07:14:07 2019 +0000
@@ -1,4 +1,4 @@
-.\"    $NetBSD: make.1,v 1.275 2019/12/18 07:37:19 maxv Exp $
+.\"    $NetBSD: make.1,v 1.276 2019/12/19 07:14:07 maxv Exp $
 .\"
 .\" Copyright (c) 1990, 1993
 .\"    The Regents of the University of California.  All rights reserved.
@@ -29,7 +29,7 @@
 .\"
 .\"    from: @(#)make.1        8.4 (Berkeley) 3/19/94
 .\"
-.Dd December 17, 2019
+.Dd February 16, 2019
 .Dt MAKE 1
 .Os
 .Sh NAME
@@ -883,7 +883,10 @@
 Puts
 .Nm
 into "meta" mode, where meta files are created for each target
-to capture the command run.
+to capture the command run, the output generated and if
+.Xr filemon 4
+is available, the system calls which are of interest to
+.Nm .
 The captured output can be very useful when diagnosing errors.
 .It Pa curdirOk= Ar bf
 Normally
@@ -971,6 +974,13 @@
 is re-exported whenever
 .Ql Va .MAKEOVERRIDES
 is modified.
+.It Va .MAKE.PATH_FILEMON
+If
+.Nm
+was built with
+.Xr filemon 4
+support, this is set to the path of the device node.
+This allows makefiles to test for this support.
 .It Va .MAKE.PID
 The process-id of
 .Nm .
diff -r 825501ed17a0 -r fffbd56e7fc1 usr.bin/make/meta.c
--- a/usr.bin/make/meta.c       Thu Dec 19 00:52:29 2019 +0000
+++ b/usr.bin/make/meta.c       Thu Dec 19 07:14:07 2019 +0000
@@ -1,4 +1,4 @@
-/*      $NetBSD: meta.c,v 1.72 2019/12/18 10:30:23 martin Exp $ */
+/*      $NetBSD: meta.c,v 1.73 2019/12/19 07:14:07 maxv Exp $ */
 
 /*
  * Implement 'meta' mode.
@@ -46,6 +46,13 @@
 #include "make.h"
 #include "job.h"
 
+#ifdef HAVE_FILEMON_H
+# include <filemon.h>
+#endif
+#if !defined(USE_FILEMON) && defined(FILEMON_SET_FD)
+# define USE_FILEMON
+#endif
+
 static BuildMon Mybm;                  /* for compat */
 static Lst metaBailiwick;              /* our scope of control */
 static char *metaBailiwickStr;         /* string storage for the list */
@@ -93,6 +100,100 @@
 #endif
 
 /*
+ * Filemon is a kernel module which snoops certain syscalls.
+ *
+ * C chdir
+ * E exec
+ * F [v]fork
+ * L [sym]link
+ * M rename
+ * R read
+ * W write
+ * S stat
+ *
+ * See meta_oodate below - we mainly care about 'E' and 'R'.
+ *
+ * We can still use meta mode without filemon, but 
+ * the benefits are more limited.
+ */
+#ifdef USE_FILEMON
+# ifndef _PATH_FILEMON
+#   define _PATH_FILEMON "/dev/filemon"
+# endif
+
+/*
+ * Open the filemon device.
+ */
+static void
+filemon_open(BuildMon *pbm)
+{
+    int retry;
+    
+    pbm->mon_fd = pbm->filemon_fd = -1;
+    if (!useFilemon)
+       return;
+
+    for (retry = 5; retry >= 0; retry--) {
+       if ((pbm->filemon_fd = open(_PATH_FILEMON, O_RDWR)) >= 0)
+           break;
+    }
+
+    if (pbm->filemon_fd < 0) {
+       useFilemon = FALSE;
+       warn("Could not open %s", _PATH_FILEMON);
+       return;
+    }
+
+    /*
+     * We use a file outside of '.'
+     * to avoid a FreeBSD kernel bug where unlink invalidates
+     * cwd causing getcwd to do a lot more work.
+     * We only care about the descriptor.
+     */
+    pbm->mon_fd = mkTempFile("filemon.XXXXXX", NULL);
+    if (ioctl(pbm->filemon_fd, FILEMON_SET_FD, &pbm->mon_fd) < 0) {
+       err(1, "Could not set filemon file descriptor!");
+    }
+    /* we don't need these once we exec */
+    (void)fcntl(pbm->mon_fd, F_SETFD, FD_CLOEXEC);
+    (void)fcntl(pbm->filemon_fd, F_SETFD, FD_CLOEXEC);
+}
+
+/*
+ * Read the build monitor output file and write records to the target's
+ * metadata file.
+ */
+static int
+filemon_read(FILE *mfp, int fd)
+{
+    char buf[BUFSIZ];
+    int n;
+    int error;
+
+    /* Check if we're not writing to a meta data file.*/
+    if (mfp == NULL) {
+       if (fd >= 0)
+           close(fd);                  /* not interested */
+       return 0;
+    }
+    /* rewind */
+    (void)lseek(fd, (off_t)0, SEEK_SET);
+
+    error = 0;
+    fprintf(mfp, "\n-- filemon acquired metadata --\n");
+
+    while ((n = read(fd, buf, sizeof(buf))) > 0) {
+       if ((int)fwrite(buf, 1, n, mfp) < n)
+           error = EIO;
+    }
+    fflush(mfp);
+    if (close(fd) < 0)
+       error = errno;
+    return error;
+}
+#endif
+
+/*
  * when realpath() fails,
  * we use this, to clean up ./ and ../
  */
@@ -467,6 +568,10 @@
 void
 meta_init(void)
 {
+#ifdef USE_FILEMON
+       /* this allows makefiles to test if we have filemon support */
+       Var_Set(".MAKE.PATH_FILEMON", _PATH_FILEMON, VAR_GLOBAL, 0);
+#endif
 }
 
 
@@ -568,6 +673,18 @@
        pbm = &Mybm;
     }
     pbm->mfp = meta_create(pbm, gn);
+#ifdef USE_FILEMON_ONCE
+    /* compat mode we open the filemon dev once per command */
+    if (job == NULL)
+       return;
+#endif
+#ifdef USE_FILEMON
+    if (pbm->mfp != NULL && useFilemon) {
+       filemon_open(pbm);
+    } else {
+       pbm->mon_fd = pbm->filemon_fd = -1;
+    }
+#endif
 }
 
 /*
@@ -577,6 +694,26 @@
 void
 meta_job_child(Job *job)
 {
+#ifdef USE_FILEMON
+    BuildMon *pbm;
+
+    if (job != NULL) {
+       pbm = &job->bm;
+    } else {
+       pbm = &Mybm;
+    }
+    if (pbm->mfp != NULL) {
+       close(fileno(pbm->mfp));
+       if (useFilemon) {
+           pid_t pid;
+
+           pid = getpid();
+           if (ioctl(pbm->filemon_fd, FILEMON_SET_PID, &pid) < 0) {
+               err(1, "Could not set filemon pid!");
+           }
+       }
+    }
+#endif
 }
 
 void
@@ -649,11 +786,24 @@
 {
     int error = 0;
     BuildMon *pbm = pbmp;
+#ifdef USE_FILEMON
+    int x;
+#endif
 
     if (!pbm)
        pbm = &Mybm;
 
-    fprintf(pbm->mfp, "\n");   /* ensure end with newline */
+#ifdef USE_FILEMON
+    if (pbm->filemon_fd >= 0) {
+       if (close(pbm->filemon_fd) < 0)
+           error = errno;
+       x = filemon_read(pbm->mfp, pbm->mon_fd);



Home | Main Index | Thread Index | Old Index