Source-Changes-HG archive
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]
[src/trunk]: src/usr.bin/make Per sjg's suggestion, split filemon API into se...
details: https://anonhg.NetBSD.org/src/rev/d767b5dd17f7
branches: trunk
changeset: 1006578:d767b5dd17f7
user: riastradh <riastradh%NetBSD.org@localhost>
date: Sun Jan 19 19:49:36 2020 +0000
description:
Per sjg's suggestion, split filemon API into separate back ends.
By default we use the ktrace back end, but the /dev/filemon back end
is available as a compile-time option, by setting USE_FILEMON=dev in
make. sjg raised concerns about ktrace performance and would like to
continue using /dev/filemon on FreeBSD (which has seen more
maintenance kernel-side) without forking make.
diffstat:
usr.bin/make/Makefile | 7 +-
usr.bin/make/filemon.c | 870 ---------------------------------
usr.bin/make/filemon.h | 50 -
usr.bin/make/filemon/filemon.h | 53 ++
usr.bin/make/filemon/filemon_dev.c | 151 +++++
usr.bin/make/filemon/filemon_ktrace.c | 876 ++++++++++++++++++++++++++++++++++
usr.bin/make/meta.c | 8 +-
7 files changed, 1088 insertions(+), 927 deletions(-)
diffs (truncated from 2078 to 300 lines):
diff -r 4b91e7516fff -r d767b5dd17f7 usr.bin/make/Makefile
--- a/usr.bin/make/Makefile Sun Jan 19 19:42:32 2020 +0000
+++ b/usr.bin/make/Makefile Sun Jan 19 19:49:36 2020 +0000
@@ -1,4 +1,4 @@
-# $NetBSD: Makefile,v 1.66 2020/01/19 19:42:32 riastradh Exp $
+# $NetBSD: Makefile,v 1.67 2020/01/19 19:49:36 riastradh Exp $
# @(#)Makefile 5.2 (Berkeley) 12/28/90
PROG= make
@@ -17,9 +17,10 @@
.if ${USE_META:tl} != "no"
SRCS+= meta.c
CPPFLAGS+= -DUSE_META
-USE_FILEMON ?= yes
+USE_FILEMON ?= ktrace
.if ${USE_FILEMON:tl} != "no"
-SRCS+= filemon.c
+.PATH: ${.CURDIR}/filemon
+SRCS+= filemon_${USE_FILEMON}.c
CPPFLAGS+= -DUSE_FILEMON
.endif
.endif
diff -r 4b91e7516fff -r d767b5dd17f7 usr.bin/make/filemon.c
--- a/usr.bin/make/filemon.c Sun Jan 19 19:42:32 2020 +0000
+++ /dev/null Thu Jan 01 00:00:00 1970 +0000
@@ -1,870 +0,0 @@
-/* $NetBSD: filemon.c,v 1.1 2020/01/19 19:42:32 riastradh Exp $ */
-
-/*-
- * Copyright (c) 2019 The NetBSD Foundation, Inc.
- * All rights reserved.
- *
- * This code is derived from software contributed to The NetBSD Foundation
- * by Taylor R. Campbell.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- *
- * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
- * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
- * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
- * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
- * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
- * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
- * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
- * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
- * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
- * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
- * POSSIBILITY OF SUCH DAMAGE.
- */
-
-#ifdef USE_FILEMON
-
-#include "filemon.h"
-
-#include <sys/param.h>
-#include <sys/types.h>
-#include <sys/rbtree.h>
-#include <sys/syscall.h>
-#include <sys/time.h>
-#include <sys/uio.h>
-#include <sys/wait.h>
-
-#include <sys/ktrace.h>
-
-#include <assert.h>
-#include <err.h>
-#include <errno.h>
-#include <fcntl.h>
-#include <stdbool.h>
-#include <stddef.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-
-#include "make.h"
-
-#ifndef AT_CWD
-#define AT_CWD -1
-#endif
-
-struct filemon;
-struct filemon_key;
-struct filemon_state;
-
-typedef struct filemon_state *filemon_syscall_t(struct filemon *,
- const struct filemon_key *, const struct ktr_syscall *);
-
-static filemon_syscall_t filemon_sys_chdir;
-static filemon_syscall_t filemon_sys_execve;
-static filemon_syscall_t filemon_sys_exit;
-static filemon_syscall_t filemon_sys_fork;
-static filemon_syscall_t filemon_sys_link;
-static filemon_syscall_t filemon_sys_open;
-static filemon_syscall_t filemon_sys_openat;
-static filemon_syscall_t filemon_sys_symlink;
-static filemon_syscall_t filemon_sys_unlink;
-static filemon_syscall_t filemon_sys_rename;
-
-static filemon_syscall_t *const filemon_syscalls[] = {
- [SYS_chdir] = &filemon_sys_chdir,
- [SYS_execve] = &filemon_sys_execve,
- [SYS_exit] = &filemon_sys_exit,
- [SYS_fork] = &filemon_sys_fork,
- [SYS_link] = &filemon_sys_link,
- [SYS_open] = &filemon_sys_open,
- [SYS_openat] = &filemon_sys_openat,
- [SYS_symlink] = &filemon_sys_symlink,
- [SYS_unlink] = &filemon_sys_unlink,
- [SYS_rename] = &filemon_sys_rename,
-};
-
-struct filemon {
- int ktrfd; /* kernel writes ktrace events here */
- FILE *in; /* we read ktrace events from here */
- FILE *out; /* we write filemon events to here */
- rb_tree_t active;
- pid_t child;
-
- /* I/O state machine. */
- enum {
- FILEMON_START = 0,
- FILEMON_HEADER,
- FILEMON_PAYLOAD,
- FILEMON_ERROR,
- } state;
- unsigned char *p;
- size_t resid;
-
- /* I/O buffer. */
- struct ktr_header hdr;
- union {
- struct ktr_syscall syscall;
- struct ktr_sysret sysret;
- char namei[PATH_MAX];
- unsigned char buf[4096];
- } payload;
-};
-
-struct filemon_state {
- struct filemon_key {
- pid_t pid;
- lwpid_t lid;
- } key;
- struct rb_node node;
- int syscode;
- void (*show)(struct filemon *, const struct filemon_state *,
- const struct ktr_sysret *);
- unsigned i;
- unsigned npath;
- char *path[/*npath*/];
-};
-
-static int
-compare_filemon_states(void *cookie MAKE_ATTR_UNUSED, const void *na,
- const void *nb)
-{
- const struct filemon_state *Sa = na;
- const struct filemon_state *Sb = nb;
-
- if (Sa->key.pid < Sb->key.pid)
- return -1;
- if (Sa->key.pid > Sb->key.pid)
- return +1;
- if (Sa->key.lid < Sb->key.lid)
- return -1;
- if (Sa->key.lid > Sb->key.lid)
- return +1;
- return 0;
-}
-
-static int
-compare_filemon_key(void *cookie MAKE_ATTR_UNUSED, const void *n,
- const void *k)
-{
- const struct filemon_state *S = n;
- const struct filemon_key *key = k;
-
- if (S->key.pid < key->pid)
- return -1;
- if (S->key.pid > key->pid)
- return +1;
- if (S->key.lid < key->lid)
- return -1;
- if (S->key.lid > key->lid)
- return +1;
- return 0;
-}
-
-static const rb_tree_ops_t filemon_rb_ops = {
- .rbto_compare_nodes = &compare_filemon_states,
- .rbto_compare_key = &compare_filemon_key,
- .rbto_node_offset = offsetof(struct filemon_state, node),
- .rbto_context = NULL,
-};
-
-/*
- * filemon_open()
- *
- * Allocate a filemon descriptor. Returns NULL and sets errno on
- * failure.
- */
-struct filemon *
-filemon_open(void)
-{
- struct filemon *F;
- int ktrpipe[2];
- int error;
-
- /* Allocate and zero a struct filemon object. */
- F = calloc(1, sizeof(*F));
- if (F == NULL)
- return NULL;
-
- /* Create a pipe for ktrace events. */
- if (pipe2(ktrpipe, O_CLOEXEC|O_NONBLOCK) == -1) {
- error = errno;
- goto fail0;
- }
-
- /* Create a file stream for reading the ktrace events. */
- if ((F->in = fdopen(ktrpipe[0], "r")) == NULL) {
- error = errno;
- goto fail1;
- }
- ktrpipe[0] = -1; /* claimed by fdopen */
-
- /*
- * Set the fd for writing ktrace events and initialize the
- * rbtree. The rest can be safely initialized to zero.
- */
- F->ktrfd = ktrpipe[1];
- rb_tree_init(&F->active, &filemon_rb_ops);
-
- /* Success! */
- return F;
-
-fail2: __unused
- (void)fclose(F->in);
-fail1: (void)close(ktrpipe[0]);
- (void)close(ktrpipe[1]);
-fail0: free(F);
- errno = error;
- return NULL;
-}
-
-/*
- * filemon_closefd(F)
- *
- * Internal subroutine to try to flush and close the output file.
- * If F is not open for output, do nothing. Never leaves F open
- * for output even on failure. Returns 0 on success; sets errno
- * and return -1 on failure.
- */
-static int
-filemon_closefd(struct filemon *F)
-{
- int error = 0;
-
- /* If we're not open, nothing to do. */
- if (F->out == NULL)
- return 0;
-
- /*
- * Flush it, close it, and null it unconditionally, but be
- * careful to return the earliest error in errno.
- */
- if (fflush(F->out) == EOF && error == 0)
- error = errno;
- if (fclose(F->out) == EOF && error == 0)
- error = errno;
- F->out = NULL;
-
- /* Set errno and return -1 if anything went wrong. */
- if (error) {
- errno = error;
- return -1;
- }
-
- /* Success! */
- return 0;
-}
-
-/*
- * filemon_setfd(F, fd)
- *
- * Cause filemon activity on F to be sent to fd. Claims ownership
- * of fd; caller should not use fd afterward, and any duplicates
- * of fd may see their file positions changed.
- */
-int
-filemon_setfd(struct filemon *F, int fd)
-{
-
Home |
Main Index |
Thread Index |
Old Index