diff options
author | rwatson <rwatson@FreeBSD.org> | 2012-12-01 11:58:08 +0000 |
---|---|---|
committer | rwatson <rwatson@FreeBSD.org> | 2012-12-01 11:58:08 +0000 |
commit | 946ac5071e3d600a9df487c53b2cff2d10678a88 (patch) | |
tree | 6ec8d83f07a4534def35774b9687d13b3262b2a1 /contrib/openbsm/bin | |
parent | c6ea39d1ef9125a0055d6ecdcad5aeec2400eb03 (diff) | |
parent | d819e8c880521e04966ae5c3633e0c46e88d6d47 (diff) | |
download | FreeBSD-src-946ac5071e3d600a9df487c53b2cff2d10678a88.zip FreeBSD-src-946ac5071e3d600a9df487c53b2cff2d10678a88.tar.gz |
Merge OpenBSM 1.2-alpha2 from vendor branch to FreeBSD 10-CURRENT; the
primary new feature is auditdistd.
Obtained from: TrustedBSD Project
Sponsored by: The FreeBSD Foundation (auditdistd)
Diffstat (limited to 'contrib/openbsm/bin')
52 files changed, 12428 insertions, 772 deletions
diff --git a/contrib/openbsm/bin/Makefile.am b/contrib/openbsm/bin/Makefile.am index 735c241..16073e9 100644 --- a/contrib/openbsm/bin/Makefile.am +++ b/contrib/openbsm/bin/Makefile.am @@ -1,8 +1,9 @@ -# -# $P4: //depot/projects/trustedbsd/openbsm/bin/Makefile.am#3 $ -# +## +## $P4: //depot/projects/trustedbsd/openbsm/bin/Makefile.am#4 $ +## SUBDIRS = \ + auditdistd \ auditfilterd \ auditreduce \ praudit diff --git a/contrib/openbsm/bin/Makefile.in b/contrib/openbsm/bin/Makefile.in index 4bb342a..e2b3754 100644 --- a/contrib/openbsm/bin/Makefile.in +++ b/contrib/openbsm/bin/Makefile.in @@ -1,8 +1,8 @@ -# Makefile.in generated by automake 1.10.1 from Makefile.am. +# Makefile.in generated by automake 1.12.2 from Makefile.am. # @configure_input@ -# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008 Free Software Foundation, Inc. +# Copyright (C) 1994-2012 Free Software Foundation, Inc. + # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -13,14 +13,28 @@ # PARTICULAR PURPOSE. @SET_MAKE@ - -# -# $P4: //depot/projects/trustedbsd/openbsm/bin/Makefile.in#11 $ -# VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ -pkglibdir = $(libdir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ +pkglibdir = $(libdir)/@PACKAGE@ +pkglibexecdir = $(libexecdir)/@PACKAGE@ am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd install_sh_DATA = $(install_sh) -c -m 644 install_sh_PROGRAM = $(install_sh) -c @@ -48,6 +62,7 @@ am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ mkinstalldirs = $(install_sh) -d CONFIG_HEADER = $(top_builddir)/config/config.h CONFIG_CLEAN_FILES = +CONFIG_CLEAN_VPATH_FILES = SOURCES = DIST_SOURCES = RECURSIVE_TARGETS = all-recursive check-recursive dvi-recursive \ @@ -57,12 +72,46 @@ RECURSIVE_TARGETS = all-recursive check-recursive dvi-recursive \ install-pdf-recursive install-ps-recursive install-recursive \ installcheck-recursive installdirs-recursive pdf-recursive \ ps-recursive uninstall-recursive +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac RECURSIVE_CLEAN_TARGETS = mostlyclean-recursive clean-recursive \ distclean-recursive maintainer-clean-recursive +AM_RECURSIVE_TARGETS = $(RECURSIVE_TARGETS:-recursive=) \ + $(RECURSIVE_CLEAN_TARGETS:-recursive=) tags TAGS ctags CTAGS \ + distdir ETAGS = etags CTAGS = ctags -DIST_SUBDIRS = auditfilterd auditreduce praudit audit auditd +DIST_SUBDIRS = auditdistd auditfilterd auditreduce praudit audit \ + auditd DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) +am__relativize = \ + dir0=`pwd`; \ + sed_first='s,^\([^/]*\)/.*$$,\1,'; \ + sed_rest='s,^[^/]*/*,,'; \ + sed_last='s,^.*/\([^/]*\)$$,\1,'; \ + sed_butlast='s,/*[^/]*$$,,'; \ + while test -n "$$dir1"; do \ + first=`echo "$$dir1" | sed -e "$$sed_first"`; \ + if test "$$first" != "."; then \ + if test "$$first" = ".."; then \ + dir2=`echo "$$dir0" | sed -e "$$sed_last"`/"$$dir2"; \ + dir0=`echo "$$dir0" | sed -e "$$sed_butlast"`; \ + else \ + first2=`echo "$$dir2" | sed -e "$$sed_first"`; \ + if test "$$first2" = "$$first"; then \ + dir2=`echo "$$dir2" | sed -e "$$sed_rest"`; \ + else \ + dir2="../$$dir2"; \ + fi; \ + dir0="$$dir0"/"$$first"; \ + fi; \ + fi; \ + dir1=`echo "$$dir1" | sed -e "$$sed_rest"`; \ + done; \ + reldir="$$dir2" ACLOCAL = @ACLOCAL@ AMTAR = @AMTAR@ AR = @AR@ @@ -75,45 +124,52 @@ CCDEPMODE = @CCDEPMODE@ CFLAGS = @CFLAGS@ CPP = @CPP@ CPPFLAGS = @CPPFLAGS@ -CXX = @CXX@ -CXXCPP = @CXXCPP@ -CXXDEPMODE = @CXXDEPMODE@ -CXXFLAGS = @CXXFLAGS@ CYGPATH_W = @CYGPATH_W@ DEFS = @DEFS@ DEPDIR = @DEPDIR@ +DLLTOOL = @DLLTOOL@ DSYMUTIL = @DSYMUTIL@ -ECHO = @ECHO@ +DUMPBIN = @DUMPBIN@ ECHO_C = @ECHO_C@ ECHO_N = @ECHO_N@ ECHO_T = @ECHO_T@ EGREP = @EGREP@ EXEEXT = @EXEEXT@ -F77 = @F77@ -FFLAGS = @FFLAGS@ +FGREP = @FGREP@ GREP = @GREP@ INSTALL = @INSTALL@ INSTALL_DATA = @INSTALL_DATA@ INSTALL_PROGRAM = @INSTALL_PROGRAM@ INSTALL_SCRIPT = @INSTALL_SCRIPT@ INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@ +LD = @LD@ LDFLAGS = @LDFLAGS@ +LEX = @LEX@ +LEXLIB = @LEXLIB@ +LEX_OUTPUT_ROOT = @LEX_OUTPUT_ROOT@ LIBOBJS = @LIBOBJS@ LIBS = @LIBS@ LIBTOOL = @LIBTOOL@ +LIPO = @LIPO@ LN_S = @LN_S@ LTLIBOBJS = @LTLIBOBJS@ MAINT = @MAINT@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MIG = @MIG@ MKDIR_P = @MKDIR_P@ +NM = @NM@ NMEDIT = @NMEDIT@ +OBJDUMP = @OBJDUMP@ OBJEXT = @OBJEXT@ +OTOOL = @OTOOL@ +OTOOL64 = @OTOOL64@ PACKAGE = @PACKAGE@ PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@ PACKAGE_NAME = @PACKAGE_NAME@ PACKAGE_STRING = @PACKAGE_STRING@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ +PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ RANLIB = @RANLIB@ @@ -122,13 +178,15 @@ SET_MAKE = @SET_MAKE@ SHELL = @SHELL@ STRIP = @STRIP@ VERSION = @VERSION@ +YACC = @YACC@ +YFLAGS = @YFLAGS@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ -ac_ct_CXX = @ac_ct_CXX@ -ac_ct_F77 = @ac_ct_F77@ +ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ am__include = @am__include@ am__leading_dot = @am__leading_dot@ am__quote = @am__quote@ @@ -174,7 +232,7 @@ target_alias = @target_alias@ top_build_prefix = @top_build_prefix@ top_builddir = @top_builddir@ top_srcdir = @top_srcdir@ -SUBDIRS = auditfilterd auditreduce praudit $(am__append_1) +SUBDIRS = auditdistd auditfilterd auditreduce praudit $(am__append_1) all: all-recursive .SUFFIXES: @@ -182,14 +240,14 @@ $(srcdir)/Makefile.in: @MAINTAINER_MODE_TRUE@ $(srcdir)/Makefile.am $(am__confi @for dep in $?; do \ case '$(am__configure_deps)' in \ *$$dep*) \ - cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh \ - && exit 0; \ + ( cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh ) \ + && { if test -f $@; then exit 0; else break; fi; }; \ exit 1;; \ esac; \ done; \ - echo ' cd $(top_srcdir) && $(AUTOMAKE) --foreign bin/Makefile'; \ - cd $(top_srcdir) && \ - $(AUTOMAKE) --foreign bin/Makefile + echo ' cd $(top_srcdir) && $(AUTOMAKE) --foreign bin/Makefile'; \ + $(am__cd) $(top_srcdir) && \ + $(AUTOMAKE) --foreign bin/Makefile .PRECIOUS: Makefile Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status @case '$?' in \ @@ -207,6 +265,7 @@ $(top_srcdir)/configure: @MAINTAINER_MODE_TRUE@ $(am__configure_deps) cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh $(ACLOCAL_M4): @MAINTAINER_MODE_TRUE@ $(am__aclocal_m4_deps) cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh +$(am__aclocal_m4_deps): mostlyclean-libtool: -rm -f *.lo @@ -215,13 +274,13 @@ clean-libtool: -rm -rf .libs _libs # This directory's subdirectories are mostly independent; you can cd -# into them and run `make' without going through this Makefile. -# To change the values of `make' variables: instead of editing Makefiles, -# (1) if the variable is set in `config.status', edit `config.status' -# (which will cause the Makefiles to be regenerated when you run `make'); -# (2) otherwise, pass the desired values on the `make' command line. -$(RECURSIVE_TARGETS): - @failcom='exit 1'; \ +# into them and run 'make' without going through this Makefile. +# To change the values of 'make' variables: instead of editing Makefiles, +# (1) if the variable is set in 'config.status', edit 'config.status' +# (which will cause the Makefiles to be regenerated when you run 'make'); +# (2) otherwise, pass the desired values on the 'make' command line. +$(RECURSIVE_TARGETS) $(RECURSIVE_CLEAN_TARGETS): + @fail= failcom='exit 1'; \ for f in x $$MAKEFLAGS; do \ case $$f in \ *=* | --[!k]*);; \ @@ -230,7 +289,11 @@ $(RECURSIVE_TARGETS): done; \ dot_seen=no; \ target=`echo $@ | sed s/-recursive//`; \ - list='$(SUBDIRS)'; for subdir in $$list; do \ + case "$@" in \ + distclean-* | maintainer-clean-*) list='$(DIST_SUBDIRS)' ;; \ + *) list='$(SUBDIRS)' ;; \ + esac; \ + for subdir in $$list; do \ echo "Making $$target in $$subdir"; \ if test "$$subdir" = "."; then \ dot_seen=yes; \ @@ -238,50 +301,23 @@ $(RECURSIVE_TARGETS): else \ local_target="$$target"; \ fi; \ - (cd $$subdir && $(MAKE) $(AM_MAKEFLAGS) $$local_target) \ + ($(am__cd) $$subdir && $(MAKE) $(AM_MAKEFLAGS) $$local_target) \ || eval $$failcom; \ done; \ if test "$$dot_seen" = "no"; then \ $(MAKE) $(AM_MAKEFLAGS) "$$target-am" || exit 1; \ fi; test -z "$$fail" - -$(RECURSIVE_CLEAN_TARGETS): - @failcom='exit 1'; \ - for f in x $$MAKEFLAGS; do \ - case $$f in \ - *=* | --[!k]*);; \ - *k*) failcom='fail=yes';; \ - esac; \ - done; \ - dot_seen=no; \ - case "$@" in \ - distclean-* | maintainer-clean-*) list='$(DIST_SUBDIRS)' ;; \ - *) list='$(SUBDIRS)' ;; \ - esac; \ - rev=''; for subdir in $$list; do \ - if test "$$subdir" = "."; then :; else \ - rev="$$subdir $$rev"; \ - fi; \ - done; \ - rev="$$rev ."; \ - target=`echo $@ | sed s/-recursive//`; \ - for subdir in $$rev; do \ - echo "Making $$target in $$subdir"; \ - if test "$$subdir" = "."; then \ - local_target="$$target-am"; \ - else \ - local_target="$$target"; \ - fi; \ - (cd $$subdir && $(MAKE) $(AM_MAKEFLAGS) $$local_target) \ - || eval $$failcom; \ - done && test -z "$$fail" tags-recursive: list='$(SUBDIRS)'; for subdir in $$list; do \ - test "$$subdir" = . || (cd $$subdir && $(MAKE) $(AM_MAKEFLAGS) tags); \ + test "$$subdir" = . || ($(am__cd) $$subdir && $(MAKE) $(AM_MAKEFLAGS) tags); \ done ctags-recursive: list='$(SUBDIRS)'; for subdir in $$list; do \ - test "$$subdir" = . || (cd $$subdir && $(MAKE) $(AM_MAKEFLAGS) ctags); \ + test "$$subdir" = . || ($(am__cd) $$subdir && $(MAKE) $(AM_MAKEFLAGS) ctags); \ + done +cscopelist-recursive: + list='$(SUBDIRS)'; for subdir in $$list; do \ + test "$$subdir" = . || ($(am__cd) $$subdir && $(MAKE) $(AM_MAKEFLAGS) cscopelist); \ done ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) @@ -289,14 +325,14 @@ ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) unique=`for i in $$list; do \ if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ done | \ - $(AWK) '{ files[$$0] = 1; nonemtpy = 1; } \ + $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ END { if (nonempty) { for (i in files) print i; }; }'`; \ mkid -fID $$unique tags: TAGS TAGS: tags-recursive $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ $(TAGS_FILES) $(LISP) - tags=; \ + set x; \ here=`pwd`; \ if ($(ETAGS) --etags-include --version) >/dev/null 2>&1; then \ include_option=--etags-include; \ @@ -308,7 +344,7 @@ TAGS: tags-recursive $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ list='$(SUBDIRS)'; for subdir in $$list; do \ if test "$$subdir" = .; then :; else \ test ! -f $$subdir/TAGS || \ - tags="$$tags $$include_option=$$here/$$subdir/TAGS"; \ + set "$$@" "$$include_option=$$here/$$subdir/TAGS"; \ fi; \ done; \ list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ @@ -317,29 +353,48 @@ TAGS: tags-recursive $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ done | \ $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ END { if (nonempty) { for (i in files) print i; }; }'`; \ - if test -z "$(ETAGS_ARGS)$$tags$$unique"; then :; else \ + shift; \ + if test -z "$(ETAGS_ARGS)$$*$$unique"; then :; else \ test -n "$$unique" || unique=$$empty_fix; \ - $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ - $$tags $$unique; \ + if test $$# -gt 0; then \ + $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ + "$$@" $$unique; \ + else \ + $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ + $$unique; \ + fi; \ fi ctags: CTAGS CTAGS: ctags-recursive $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ $(TAGS_FILES) $(LISP) - tags=; \ list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ unique=`for i in $$list; do \ if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ done | \ $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ END { if (nonempty) { for (i in files) print i; }; }'`; \ - test -z "$(CTAGS_ARGS)$$tags$$unique" \ + test -z "$(CTAGS_ARGS)$$unique" \ || $(CTAGS) $(CTAGSFLAGS) $(AM_CTAGSFLAGS) $(CTAGS_ARGS) \ - $$tags $$unique + $$unique GTAGS: here=`$(am__cd) $(top_builddir) && pwd` \ - && cd $(top_srcdir) \ - && gtags -i $(GTAGS_ARGS) $$here + && $(am__cd) $(top_srcdir) \ + && gtags -i $(GTAGS_ARGS) "$$here" + +cscopelist: cscopelist-recursive $(HEADERS) $(SOURCES) $(LISP) + list='$(SOURCES) $(HEADERS) $(LISP)'; \ + case "$(srcdir)" in \ + [\\/]* | ?:[\\/]*) sdir="$(srcdir)" ;; \ + *) sdir=$(subdir)/$(srcdir) ;; \ + esac; \ + for i in $$list; do \ + if test -f "$$i"; then \ + echo "$(subdir)/$$i"; \ + else \ + echo "$$sdir/$$i"; \ + fi; \ + done >> $(top_builddir)/cscope.files distclean-tags: -rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags @@ -360,29 +415,41 @@ distdir: $(DISTFILES) if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \ if test -d $$d/$$file; then \ dir=`echo "/$$file" | sed -e 's,/[^/]*$$,,'`; \ + if test -d "$(distdir)/$$file"; then \ + find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \ + fi; \ if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \ - cp -pR $(srcdir)/$$file $(distdir)$$dir || exit 1; \ + cp -fpR $(srcdir)/$$file "$(distdir)$$dir" || exit 1; \ + find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \ fi; \ - cp -pR $$d/$$file $(distdir)$$dir || exit 1; \ + cp -fpR $$d/$$file "$(distdir)$$dir" || exit 1; \ else \ - test -f $(distdir)/$$file \ - || cp -p $$d/$$file $(distdir)/$$file \ + test -f "$(distdir)/$$file" \ + || cp -p $$d/$$file "$(distdir)/$$file" \ || exit 1; \ fi; \ done - list='$(DIST_SUBDIRS)'; for subdir in $$list; do \ + @list='$(DIST_SUBDIRS)'; for subdir in $$list; do \ if test "$$subdir" = .; then :; else \ - test -d "$(distdir)/$$subdir" \ - || $(MKDIR_P) "$(distdir)/$$subdir" \ - || exit 1; \ - distdir=`$(am__cd) $(distdir) && pwd`; \ - top_distdir=`$(am__cd) $(top_distdir) && pwd`; \ - (cd $$subdir && \ + $(am__make_dryrun) \ + || test -d "$(distdir)/$$subdir" \ + || $(MKDIR_P) "$(distdir)/$$subdir" \ + || exit 1; \ + dir1=$$subdir; dir2="$(distdir)/$$subdir"; \ + $(am__relativize); \ + new_distdir=$$reldir; \ + dir1=$$subdir; dir2="$(top_distdir)"; \ + $(am__relativize); \ + new_top_distdir=$$reldir; \ + echo " (cd $$subdir && $(MAKE) $(AM_MAKEFLAGS) top_distdir="$$new_top_distdir" distdir="$$new_distdir" \\"; \ + echo " am__remove_distdir=: am__skip_length_check=: am__skip_mode_fix=: distdir)"; \ + ($(am__cd) $$subdir && \ $(MAKE) $(AM_MAKEFLAGS) \ - top_distdir="$$top_distdir" \ - distdir="$$distdir/$$subdir" \ + top_distdir="$$new_top_distdir" \ + distdir="$$new_distdir" \ am__remove_distdir=: \ am__skip_length_check=: \ + am__skip_mode_fix=: \ distdir) \ || exit 1; \ fi; \ @@ -402,16 +469,22 @@ install-am: all-am installcheck: installcheck-recursive install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: distclean-generic: -test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES) + -test . = "$(srcdir)" || test -z "$(CONFIG_CLEAN_VPATH_FILES)" || rm -f $(CONFIG_CLEAN_VPATH_FILES) maintainer-clean-generic: @echo "This command is intended for maintainers to use" @@ -430,6 +503,8 @@ dvi-am: html: html-recursive +html-am: + info: info-recursive info-am: @@ -438,18 +513,28 @@ install-data-am: install-dvi: install-dvi-recursive +install-dvi-am: + install-exec-am: install-html: install-html-recursive +install-html-am: + install-info: install-info-recursive +install-info-am: + install-man: install-pdf: install-pdf-recursive +install-pdf-am: + install-ps: install-ps-recursive +install-ps-am: + installcheck-am: maintainer-clean: maintainer-clean-recursive @@ -470,22 +555,24 @@ ps-am: uninstall-am: -.MAKE: $(RECURSIVE_CLEAN_TARGETS) $(RECURSIVE_TARGETS) install-am \ - install-strip +.MAKE: $(RECURSIVE_CLEAN_TARGETS) $(RECURSIVE_TARGETS) \ + cscopelist-recursive ctags-recursive install-am install-strip \ + tags-recursive .PHONY: $(RECURSIVE_CLEAN_TARGETS) $(RECURSIVE_TARGETS) CTAGS GTAGS \ all all-am check check-am clean clean-generic clean-libtool \ - ctags ctags-recursive distclean distclean-generic \ - distclean-libtool distclean-tags distdir dvi dvi-am html \ - html-am info info-am install install-am install-data \ - install-data-am install-dvi install-dvi-am install-exec \ - install-exec-am install-html install-html-am install-info \ - install-info-am install-man install-pdf install-pdf-am \ - install-ps install-ps-am install-strip installcheck \ - installcheck-am installdirs installdirs-am maintainer-clean \ - maintainer-clean-generic mostlyclean mostlyclean-generic \ - mostlyclean-libtool pdf pdf-am ps ps-am tags tags-recursive \ - uninstall uninstall-am + cscopelist cscopelist-recursive ctags ctags-recursive \ + distclean distclean-generic distclean-libtool distclean-tags \ + distdir dvi dvi-am html html-am info info-am install \ + install-am install-data install-data-am install-dvi \ + install-dvi-am install-exec install-exec-am install-html \ + install-html-am install-info install-info-am install-man \ + install-pdf install-pdf-am install-ps install-ps-am \ + install-strip installcheck installcheck-am installdirs \ + installdirs-am maintainer-clean maintainer-clean-generic \ + mostlyclean mostlyclean-generic mostlyclean-libtool pdf pdf-am \ + ps ps-am tags tags-recursive uninstall uninstall-am + # Tell versions [3.59,3.63) of GNU make to not export all variables. # Otherwise a system limit (for SysV at least) may be exceeded. diff --git a/contrib/openbsm/bin/audit/Makefile.am b/contrib/openbsm/bin/audit/Makefile.am index 1b5d554..e797783 100644 --- a/contrib/openbsm/bin/audit/Makefile.am +++ b/contrib/openbsm/bin/audit/Makefile.am @@ -1,6 +1,6 @@ -# -# $P4: //depot/projects/trustedbsd/openbsm/bin/audit/Makefile.am#6 $ -# +## +## $P4: //depot/projects/trustedbsd/openbsm/bin/audit/Makefile.am#7 $ +## if USE_NATIVE_INCLUDES INCLUDES = -I$(top_builddir) -I$(top_srcdir) diff --git a/contrib/openbsm/bin/audit/Makefile.in b/contrib/openbsm/bin/audit/Makefile.in index c374cba..b7b8361 100644 --- a/contrib/openbsm/bin/audit/Makefile.in +++ b/contrib/openbsm/bin/audit/Makefile.in @@ -1,8 +1,8 @@ -# Makefile.in generated by automake 1.10.1 from Makefile.am. +# Makefile.in generated by automake 1.12.2 from Makefile.am. # @configure_input@ -# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008 Free Software Foundation, Inc. +# Copyright (C) 1994-2012 Free Software Foundation, Inc. + # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -14,14 +14,28 @@ @SET_MAKE@ -# -# $P4: //depot/projects/trustedbsd/openbsm/bin/audit/Makefile.in#12 $ -# - VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ -pkglibdir = $(libdir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ +pkglibdir = $(libdir)/@PACKAGE@ +pkglibexecdir = $(libexecdir)/@PACKAGE@ am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd install_sh_DATA = $(install_sh) -c -m 644 install_sh_PROGRAM = $(install_sh) -c @@ -38,7 +52,8 @@ build_triplet = @build@ host_triplet = @host@ sbin_PROGRAMS = audit$(EXEEXT) subdir = bin/audit -DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in +DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ + $(top_srcdir)/config/depcomp ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -46,8 +61,8 @@ am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ mkinstalldirs = $(install_sh) -d CONFIG_HEADER = $(top_builddir)/config/config.h CONFIG_CLEAN_FILES = +CONFIG_CLEAN_VPATH_FILES = am__installdirs = "$(DESTDIR)$(sbindir)" "$(DESTDIR)$(man8dir)" -sbinPROGRAMS_INSTALL = $(INSTALL_PROGRAM) PROGRAMS = $(sbin_PROGRAMS) am__audit_SOURCES_DIST = audit.c auditd_controlUser.c @USE_MACH_IPC_FALSE@am_audit_OBJECTS = audit.$(OBJEXT) @@ -58,6 +73,7 @@ audit_DEPENDENCIES = $(top_builddir)/libbsm/libbsm.la DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir)/config depcomp = $(SHELL) $(top_srcdir)/config/depcomp am__depfiles_maybe = depfiles +am__mv = mv -f COMPILE = $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) \ $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) LTCOMPILE = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) \ @@ -69,6 +85,38 @@ LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) \ $(LDFLAGS) -o $@ SOURCES = $(audit_SOURCES) DIST_SOURCES = $(am__audit_SOURCES_DIST) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac +am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; +am__vpath_adj = case $$p in \ + $(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \ + *) f=$$p;; \ + esac; +am__strip_dir = f=`echo $$p | sed -e 's|^.*/||'`; +am__install_max = 40 +am__nobase_strip_setup = \ + srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*|]/\\\\&/g'` +am__nobase_strip = \ + for p in $$list; do echo "$$p"; done | sed -e "s|$$srcdirstrip/||" +am__nobase_list = $(am__nobase_strip_setup); \ + for p in $$list; do echo "$$p $$p"; done | \ + sed "s| $$srcdirstrip/| |;"' / .*\//!s/ .*/ ./; s,\( .*\)/[^/]*$$,\1,' | \ + $(AWK) 'BEGIN { files["."] = "" } { files[$$2] = files[$$2] " " $$1; \ + if (++n[$$2] == $(am__install_max)) \ + { print $$2, files[$$2]; n[$$2] = 0; files[$$2] = "" } } \ + END { for (dir in files) print dir, files[dir] }' +am__base_list = \ + sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ + sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } man8dir = $(mandir)/man8 NROFF = nroff MANS = $(man8_MANS) @@ -87,45 +135,52 @@ CCDEPMODE = @CCDEPMODE@ CFLAGS = @CFLAGS@ CPP = @CPP@ CPPFLAGS = @CPPFLAGS@ -CXX = @CXX@ -CXXCPP = @CXXCPP@ -CXXDEPMODE = @CXXDEPMODE@ -CXXFLAGS = @CXXFLAGS@ CYGPATH_W = @CYGPATH_W@ DEFS = @DEFS@ DEPDIR = @DEPDIR@ +DLLTOOL = @DLLTOOL@ DSYMUTIL = @DSYMUTIL@ -ECHO = @ECHO@ +DUMPBIN = @DUMPBIN@ ECHO_C = @ECHO_C@ ECHO_N = @ECHO_N@ ECHO_T = @ECHO_T@ EGREP = @EGREP@ EXEEXT = @EXEEXT@ -F77 = @F77@ -FFLAGS = @FFLAGS@ +FGREP = @FGREP@ GREP = @GREP@ INSTALL = @INSTALL@ INSTALL_DATA = @INSTALL_DATA@ INSTALL_PROGRAM = @INSTALL_PROGRAM@ INSTALL_SCRIPT = @INSTALL_SCRIPT@ INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@ +LD = @LD@ LDFLAGS = @LDFLAGS@ +LEX = @LEX@ +LEXLIB = @LEXLIB@ +LEX_OUTPUT_ROOT = @LEX_OUTPUT_ROOT@ LIBOBJS = @LIBOBJS@ LIBS = @LIBS@ LIBTOOL = @LIBTOOL@ +LIPO = @LIPO@ LN_S = @LN_S@ LTLIBOBJS = @LTLIBOBJS@ MAINT = @MAINT@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MIG = @MIG@ MKDIR_P = @MKDIR_P@ +NM = @NM@ NMEDIT = @NMEDIT@ +OBJDUMP = @OBJDUMP@ OBJEXT = @OBJEXT@ +OTOOL = @OTOOL@ +OTOOL64 = @OTOOL64@ PACKAGE = @PACKAGE@ PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@ PACKAGE_NAME = @PACKAGE_NAME@ PACKAGE_STRING = @PACKAGE_STRING@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ +PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ RANLIB = @RANLIB@ @@ -134,13 +189,15 @@ SET_MAKE = @SET_MAKE@ SHELL = @SHELL@ STRIP = @STRIP@ VERSION = @VERSION@ +YACC = @YACC@ +YFLAGS = @YFLAGS@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ -ac_ct_CXX = @ac_ct_CXX@ -ac_ct_F77 = @ac_ct_F77@ +ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ am__include = @am__include@ am__leading_dot = @am__leading_dot@ am__quote = @am__quote@ @@ -201,14 +258,14 @@ $(srcdir)/Makefile.in: @MAINTAINER_MODE_TRUE@ $(srcdir)/Makefile.am $(am__confi @for dep in $?; do \ case '$(am__configure_deps)' in \ *$$dep*) \ - cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh \ - && exit 0; \ + ( cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh ) \ + && { if test -f $@; then exit 0; else break; fi; }; \ exit 1;; \ esac; \ done; \ - echo ' cd $(top_srcdir) && $(AUTOMAKE) --foreign bin/audit/Makefile'; \ - cd $(top_srcdir) && \ - $(AUTOMAKE) --foreign bin/audit/Makefile + echo ' cd $(top_srcdir) && $(AUTOMAKE) --foreign bin/audit/Makefile'; \ + $(am__cd) $(top_srcdir) && \ + $(AUTOMAKE) --foreign bin/audit/Makefile .PRECIOUS: Makefile Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status @case '$?' in \ @@ -226,35 +283,54 @@ $(top_srcdir)/configure: @MAINTAINER_MODE_TRUE@ $(am__configure_deps) cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh $(ACLOCAL_M4): @MAINTAINER_MODE_TRUE@ $(am__aclocal_m4_deps) cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh +$(am__aclocal_m4_deps): install-sbinPROGRAMS: $(sbin_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(sbindir)" || $(MKDIR_P) "$(DESTDIR)$(sbindir)" - @list='$(sbin_PROGRAMS)'; for p in $$list; do \ - p1=`echo $$p|sed 's/$(EXEEXT)$$//'`; \ - if test -f $$p \ - || test -f $$p1 \ - ; then \ - f=`echo "$$p1" | sed 's,^.*/,,;$(transform);s/$$/$(EXEEXT)/'`; \ - echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(sbinPROGRAMS_INSTALL) '$$p' '$(DESTDIR)$(sbindir)/$$f'"; \ - $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(sbinPROGRAMS_INSTALL) "$$p" "$(DESTDIR)$(sbindir)/$$f" || exit 1; \ - else :; fi; \ - done + @list='$(sbin_PROGRAMS)'; test -n "$(sbindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(sbindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(sbindir)" || exit 1; \ + fi; \ + for p in $$list; do echo "$$p $$p"; done | \ + sed 's/$(EXEEXT)$$//' | \ + while read p p1; do if test -f $$p || test -f $$p1; \ + then echo "$$p"; echo "$$p"; else :; fi; \ + done | \ + sed -e 'p;s,.*/,,;n;h' -e 's|.*|.|' \ + -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ + sed 'N;N;N;s,\n, ,g' | \ + $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ + { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ + if ($$2 == $$4) files[d] = files[d] " " $$1; \ + else { print "f", $$3 "/" $$4, $$1; } } \ + END { for (d in files) print "f", d, files[d] }' | \ + while read type dir files; do \ + if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ + test -z "$$files" || { \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(sbindir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(sbindir)$$dir" || exit $$?; \ + } \ + ; done uninstall-sbinPROGRAMS: @$(NORMAL_UNINSTALL) - @list='$(sbin_PROGRAMS)'; for p in $$list; do \ - f=`echo "$$p" | sed 's,^.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/'`; \ - echo " rm -f '$(DESTDIR)$(sbindir)/$$f'"; \ - rm -f "$(DESTDIR)$(sbindir)/$$f"; \ - done + @list='$(sbin_PROGRAMS)'; test -n "$(sbindir)" || list=; \ + files=`for p in $$list; do echo "$$p"; done | \ + sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ + -e 's/$$/$(EXEEXT)/' `; \ + test -n "$$list" || exit 0; \ + echo " ( cd '$(DESTDIR)$(sbindir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(sbindir)" && rm -f $$files clean-sbinPROGRAMS: - @list='$(sbin_PROGRAMS)'; for p in $$list; do \ - f=`echo $$p|sed 's/$(EXEEXT)$$//'`; \ - echo " rm -f $$p $$f"; \ - rm -f $$p $$f ; \ - done -audit$(EXEEXT): $(audit_OBJECTS) $(audit_DEPENDENCIES) + @list='$(sbin_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +audit$(EXEEXT): $(audit_OBJECTS) $(audit_DEPENDENCIES) $(EXTRA_audit_DEPENDENCIES) @rm -f audit$(EXEEXT) $(LINK) $(audit_OBJECTS) $(audit_LDADD) $(LIBS) @@ -269,21 +345,21 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< -@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po +@am__fastdepCC_TRUE@ $(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po @AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` -@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po +@am__fastdepCC_TRUE@ $(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po @AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< -@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo +@am__fastdepCC_TRUE@ $(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< @@ -293,65 +369,61 @@ mostlyclean-libtool: clean-libtool: -rm -rf .libs _libs -install-man8: $(man8_MANS) $(man_MANS) +install-man8: $(man8_MANS) @$(NORMAL_INSTALL) - test -z "$(man8dir)" || $(MKDIR_P) "$(DESTDIR)$(man8dir)" - @list='$(man8_MANS) $(dist_man8_MANS) $(nodist_man8_MANS)'; \ - l2='$(man_MANS) $(dist_man_MANS) $(nodist_man_MANS)'; \ - for i in $$l2; do \ - case "$$i" in \ - *.8*) list="$$list $$i" ;; \ - esac; \ + @list1='$(man8_MANS)'; \ + list2=''; \ + test -n "$(man8dir)" \ + && test -n "`echo $$list1$$list2`" \ + || exit 0; \ + echo " $(MKDIR_P) '$(DESTDIR)$(man8dir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(man8dir)" || exit 1; \ + { for i in $$list1; do echo "$$i"; done; \ + if test -n "$$list2"; then \ + for i in $$list2; do echo "$$i"; done \ + | sed -n '/\.8[a-z]*$$/p'; \ + fi; \ + } | while read p; do \ + if test -f $$p; then d=; else d="$(srcdir)/"; fi; \ + echo "$$d$$p"; echo "$$p"; \ + done | \ + sed -e 'n;s,.*/,,;p;h;s,.*\.,,;s,^[^8][0-9a-z]*$$,8,;x' \ + -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,' | \ + sed 'N;N;s,\n, ,g' | { \ + list=; while read file base inst; do \ + if test "$$base" = "$$inst"; then list="$$list $$file"; else \ + echo " $(INSTALL_DATA) '$$file' '$(DESTDIR)$(man8dir)/$$inst'"; \ + $(INSTALL_DATA) "$$file" "$(DESTDIR)$(man8dir)/$$inst" || exit $$?; \ + fi; \ done; \ - for i in $$list; do \ - if test -f $(srcdir)/$$i; then file=$(srcdir)/$$i; \ - else file=$$i; fi; \ - ext=`echo $$i | sed -e 's/^.*\\.//'`; \ - case "$$ext" in \ - 8*) ;; \ - *) ext='8' ;; \ - esac; \ - inst=`echo $$i | sed -e 's/\\.[0-9a-z]*$$//'`; \ - inst=`echo $$inst | sed -e 's/^.*\///'`; \ - inst=`echo $$inst | sed '$(transform)'`.$$ext; \ - echo " $(INSTALL_DATA) '$$file' '$(DESTDIR)$(man8dir)/$$inst'"; \ - $(INSTALL_DATA) "$$file" "$(DESTDIR)$(man8dir)/$$inst"; \ - done + for i in $$list; do echo "$$i"; done | $(am__base_list) | \ + while read files; do \ + test -z "$$files" || { \ + echo " $(INSTALL_DATA) $$files '$(DESTDIR)$(man8dir)'"; \ + $(INSTALL_DATA) $$files "$(DESTDIR)$(man8dir)" || exit $$?; }; \ + done; } + uninstall-man8: @$(NORMAL_UNINSTALL) - @list='$(man8_MANS) $(dist_man8_MANS) $(nodist_man8_MANS)'; \ - l2='$(man_MANS) $(dist_man_MANS) $(nodist_man_MANS)'; \ - for i in $$l2; do \ - case "$$i" in \ - *.8*) list="$$list $$i" ;; \ - esac; \ - done; \ - for i in $$list; do \ - ext=`echo $$i | sed -e 's/^.*\\.//'`; \ - case "$$ext" in \ - 8*) ;; \ - *) ext='8' ;; \ - esac; \ - inst=`echo $$i | sed -e 's/\\.[0-9a-z]*$$//'`; \ - inst=`echo $$inst | sed -e 's/^.*\///'`; \ - inst=`echo $$inst | sed '$(transform)'`.$$ext; \ - echo " rm -f '$(DESTDIR)$(man8dir)/$$inst'"; \ - rm -f "$(DESTDIR)$(man8dir)/$$inst"; \ - done + @list='$(man8_MANS)'; test -n "$(man8dir)" || exit 0; \ + files=`{ for i in $$list; do echo "$$i"; done; \ + } | sed -e 's,.*/,,;h;s,.*\.,,;s,^[^8][0-9a-z]*$$,8,;x' \ + -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,'`; \ + dir='$(DESTDIR)$(man8dir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ unique=`for i in $$list; do \ if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ done | \ - $(AWK) '{ files[$$0] = 1; nonemtpy = 1; } \ + $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ END { if (nonempty) { for (i in files) print i; }; }'`; \ mkid -fID $$unique tags: TAGS TAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ $(TAGS_FILES) $(LISP) - tags=; \ + set x; \ here=`pwd`; \ list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ unique=`for i in $$list; do \ @@ -359,34 +431,66 @@ TAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ done | \ $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ END { if (nonempty) { for (i in files) print i; }; }'`; \ - if test -z "$(ETAGS_ARGS)$$tags$$unique"; then :; else \ + shift; \ + if test -z "$(ETAGS_ARGS)$$*$$unique"; then :; else \ test -n "$$unique" || unique=$$empty_fix; \ - $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ - $$tags $$unique; \ + if test $$# -gt 0; then \ + $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ + "$$@" $$unique; \ + else \ + $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ + $$unique; \ + fi; \ fi ctags: CTAGS CTAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ $(TAGS_FILES) $(LISP) - tags=; \ list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ unique=`for i in $$list; do \ if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ done | \ $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ END { if (nonempty) { for (i in files) print i; }; }'`; \ - test -z "$(CTAGS_ARGS)$$tags$$unique" \ + test -z "$(CTAGS_ARGS)$$unique" \ || $(CTAGS) $(CTAGSFLAGS) $(AM_CTAGSFLAGS) $(CTAGS_ARGS) \ - $$tags $$unique + $$unique GTAGS: here=`$(am__cd) $(top_builddir) && pwd` \ - && cd $(top_srcdir) \ - && gtags -i $(GTAGS_ARGS) $$here + && $(am__cd) $(top_srcdir) \ + && gtags -i $(GTAGS_ARGS) "$$here" + +cscopelist: $(HEADERS) $(SOURCES) $(LISP) + list='$(SOURCES) $(HEADERS) $(LISP)'; \ + case "$(srcdir)" in \ + [\\/]* | ?:[\\/]*) sdir="$(srcdir)" ;; \ + *) sdir=$(subdir)/$(srcdir) ;; \ + esac; \ + for i in $$list; do \ + if test -f "$$i"; then \ + echo "$(subdir)/$$i"; \ + else \ + echo "$$sdir/$$i"; \ + fi; \ + done >> $(top_builddir)/cscope.files distclean-tags: -rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags distdir: $(DISTFILES) + @list='$(MANS)'; if test -n "$$list"; then \ + list=`for p in $$list; do \ + if test -f $$p; then d=; else d="$(srcdir)/"; fi; \ + if test -f "$$d$$p"; then echo "$$d$$p"; else :; fi; done`; \ + if test -n "$$list" && \ + grep 'ab help2man is required to generate this page' $$list >/dev/null; then \ + echo "error: found man pages containing the 'missing help2man' replacement text:" >&2; \ + grep -l 'ab help2man is required to generate this page' $$list | sed 's/^/ /' >&2; \ + echo " to fix them, install help2man, remove and regenerate the man pages;" >&2; \ + echo " typically 'make maintainer-clean' will remove them" >&2; \ + exit 1; \ + else :; fi; \ + else :; fi @srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ topsrcdirstrip=`echo "$(top_srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ list='$(DISTFILES)'; \ @@ -402,13 +506,17 @@ distdir: $(DISTFILES) if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \ if test -d $$d/$$file; then \ dir=`echo "/$$file" | sed -e 's,/[^/]*$$,,'`; \ + if test -d "$(distdir)/$$file"; then \ + find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \ + fi; \ if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \ - cp -pR $(srcdir)/$$file $(distdir)$$dir || exit 1; \ + cp -fpR $(srcdir)/$$file "$(distdir)$$dir" || exit 1; \ + find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \ fi; \ - cp -pR $$d/$$file $(distdir)$$dir || exit 1; \ + cp -fpR $$d/$$file "$(distdir)$$dir" || exit 1; \ else \ - test -f $(distdir)/$$file \ - || cp -p $$d/$$file $(distdir)/$$file \ + test -f "$(distdir)/$$file" \ + || cp -p $$d/$$file "$(distdir)/$$file" \ || exit 1; \ fi; \ done @@ -429,10 +537,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -440,6 +553,7 @@ clean-generic: distclean-generic: -test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES) + -test . = "$(srcdir)" || test -z "$(CONFIG_CLEAN_VPATH_FILES)" || rm -f $(CONFIG_CLEAN_VPATH_FILES) maintainer-clean-generic: @echo "This command is intended for maintainers to use" @@ -461,6 +575,8 @@ dvi-am: html: html-am +html-am: + info: info-am info-am: @@ -469,18 +585,28 @@ install-data-am: install-man install-dvi: install-dvi-am +install-dvi-am: + install-exec-am: install-sbinPROGRAMS install-html: install-html-am +install-html-am: + install-info: install-info-am +install-info-am: + install-man: install-man8 install-pdf: install-pdf-am +install-pdf-am: + install-ps: install-ps-am +install-ps-am: + installcheck-am: maintainer-clean: maintainer-clean-am @@ -508,7 +634,7 @@ uninstall-man: uninstall-man8 .MAKE: install-am install-strip .PHONY: CTAGS GTAGS all all-am check check-am clean clean-generic \ - clean-libtool clean-sbinPROGRAMS ctags distclean \ + clean-libtool clean-sbinPROGRAMS cscopelist ctags distclean \ distclean-compile distclean-generic distclean-libtool \ distclean-tags distdir dvi dvi-am html html-am info info-am \ install install-am install-data install-data-am install-dvi \ @@ -525,6 +651,7 @@ uninstall-man: uninstall-man8 @USE_MACH_IPC_TRUE@auditd_controlUser.c auditd_control.h: $(top_srcdir)/bin/auditd/auditd_control.defs @USE_MACH_IPC_TRUE@ $(MIG) -user auditd_controlUser.c -header auditd_control.h -server /dev/null -sheader /dev/null $(top_srcdir)/bin/auditd/auditd_control.defs + # Tell versions [3.59,3.63) of GNU make to not export all variables. # Otherwise a system limit (for SysV at least) may be exceeded. .NOEXPORT: diff --git a/contrib/openbsm/bin/audit/audit.8 b/contrib/openbsm/bin/audit/audit.8 index ff3c52d..d5b2960 100644 --- a/contrib/openbsm/bin/audit/audit.8 +++ b/contrib/openbsm/bin/audit/audit.8 @@ -25,7 +25,7 @@ .\" (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF .\" THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. .\" -.\" $P4: //depot/projects/trustedbsd/openbsm/bin/audit/audit.8#15 $ +.\" $P4: //depot/projects/trustedbsd/openbsm/bin/audit/audit.8#16 $ .\" .Dd January 29, 2009 .Dt AUDIT 8 @@ -46,18 +46,18 @@ One of the following flags is required as an argument to .It Fl e Forces the audit system to immediately remove audit log files that meet the expiration criteria specified in the audit control file without -doing a log rotation. +doing a log rotation. .It Fl i Initializes and starts auditing. This option is currently for Mac OS X only and requires .Xr auditd 8 -to be configured to run under +to be configured to run under .Xr launchd 8 . .It Fl n Forces the audit system to close the existing audit log file and rotate to a new log file in a location specified in the audit control file. -Also, audit log files that meet the expiration criteria specified in the +Also, audit log files that meet the expiration criteria specified in the audit control file will be removed. .It Fl s Specifies that the audit system should [re]synchronize its @@ -77,7 +77,7 @@ on-demand by .Xr launchd 8 (Mac OS X only). The -.Nm +.Nm utility requires audit administrator privileges for successful operation. .Sh FILES .Bl -tag -width ".Pa /etc/security/audit_control" -compact diff --git a/contrib/openbsm/bin/auditd/Makefile.am b/contrib/openbsm/bin/auditd/Makefile.am index 2372fa6..2a187db 100644 --- a/contrib/openbsm/bin/auditd/Makefile.am +++ b/contrib/openbsm/bin/auditd/Makefile.am @@ -1,6 +1,6 @@ -# -# $P4: //depot/projects/trustedbsd/openbsm/bin/auditd/Makefile.am#5 $ -# +## +## $P4: //depot/projects/trustedbsd/openbsm/bin/auditd/Makefile.am#6 $ +## if USE_NATIVE_INCLUDES INCLUDES = -I$(top_builddir) -I$(top_srcdir) diff --git a/contrib/openbsm/bin/auditd/Makefile.in b/contrib/openbsm/bin/auditd/Makefile.in index 4b2a6cb..3fa44f1 100644 --- a/contrib/openbsm/bin/auditd/Makefile.in +++ b/contrib/openbsm/bin/auditd/Makefile.in @@ -1,8 +1,8 @@ -# Makefile.in generated by automake 1.10.1 from Makefile.am. +# Makefile.in generated by automake 1.12.2 from Makefile.am. # @configure_input@ -# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008 Free Software Foundation, Inc. +# Copyright (C) 1994-2012 Free Software Foundation, Inc. + # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -14,14 +14,28 @@ @SET_MAKE@ -# -# $P4: //depot/projects/trustedbsd/openbsm/bin/auditd/Makefile.in#11 $ -# - VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ -pkglibdir = $(libdir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ +pkglibdir = $(libdir)/@PACKAGE@ +pkglibexecdir = $(libexecdir)/@PACKAGE@ am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd install_sh_DATA = $(install_sh) -c -m 644 install_sh_PROGRAM = $(install_sh) -c @@ -38,7 +52,8 @@ build_triplet = @build@ host_triplet = @host@ sbin_PROGRAMS = auditd$(EXEEXT) subdir = bin/auditd -DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in +DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ + $(top_srcdir)/config/depcomp ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -46,8 +61,8 @@ am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ mkinstalldirs = $(install_sh) -d CONFIG_HEADER = $(top_builddir)/config/config.h CONFIG_CLEAN_FILES = +CONFIG_CLEAN_VPATH_FILES = am__installdirs = "$(DESTDIR)$(sbindir)" "$(DESTDIR)$(man8dir)" -sbinPROGRAMS_INSTALL = $(INSTALL_PROGRAM) PROGRAMS = $(sbin_PROGRAMS) am__auditd_SOURCES_DIST = audit_warn.c auditd.c auditd_fbsd.c \ auditd_controlServer.c audit_triggersServer.c auditd_darwin.c @@ -63,6 +78,7 @@ auditd_DEPENDENCIES = $(top_builddir)/libbsm/libbsm.la \ DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir)/config depcomp = $(SHELL) $(top_srcdir)/config/depcomp am__depfiles_maybe = depfiles +am__mv = mv -f COMPILE = $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) \ $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) LTCOMPILE = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) \ @@ -74,6 +90,38 @@ LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) \ $(LDFLAGS) -o $@ SOURCES = $(auditd_SOURCES) DIST_SOURCES = $(am__auditd_SOURCES_DIST) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac +am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; +am__vpath_adj = case $$p in \ + $(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \ + *) f=$$p;; \ + esac; +am__strip_dir = f=`echo $$p | sed -e 's|^.*/||'`; +am__install_max = 40 +am__nobase_strip_setup = \ + srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*|]/\\\\&/g'` +am__nobase_strip = \ + for p in $$list; do echo "$$p"; done | sed -e "s|$$srcdirstrip/||" +am__nobase_list = $(am__nobase_strip_setup); \ + for p in $$list; do echo "$$p $$p"; done | \ + sed "s| $$srcdirstrip/| |;"' / .*\//!s/ .*/ ./; s,\( .*\)/[^/]*$$,\1,' | \ + $(AWK) 'BEGIN { files["."] = "" } { files[$$2] = files[$$2] " " $$1; \ + if (++n[$$2] == $(am__install_max)) \ + { print $$2, files[$$2]; n[$$2] = 0; files[$$2] = "" } } \ + END { for (dir in files) print dir, files[dir] }' +am__base_list = \ + sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ + sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } man8dir = $(mandir)/man8 NROFF = nroff MANS = $(man8_MANS) @@ -92,45 +140,52 @@ CCDEPMODE = @CCDEPMODE@ CFLAGS = @CFLAGS@ CPP = @CPP@ CPPFLAGS = @CPPFLAGS@ -CXX = @CXX@ -CXXCPP = @CXXCPP@ -CXXDEPMODE = @CXXDEPMODE@ -CXXFLAGS = @CXXFLAGS@ CYGPATH_W = @CYGPATH_W@ DEFS = @DEFS@ DEPDIR = @DEPDIR@ +DLLTOOL = @DLLTOOL@ DSYMUTIL = @DSYMUTIL@ -ECHO = @ECHO@ +DUMPBIN = @DUMPBIN@ ECHO_C = @ECHO_C@ ECHO_N = @ECHO_N@ ECHO_T = @ECHO_T@ EGREP = @EGREP@ EXEEXT = @EXEEXT@ -F77 = @F77@ -FFLAGS = @FFLAGS@ +FGREP = @FGREP@ GREP = @GREP@ INSTALL = @INSTALL@ INSTALL_DATA = @INSTALL_DATA@ INSTALL_PROGRAM = @INSTALL_PROGRAM@ INSTALL_SCRIPT = @INSTALL_SCRIPT@ INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@ +LD = @LD@ LDFLAGS = @LDFLAGS@ +LEX = @LEX@ +LEXLIB = @LEXLIB@ +LEX_OUTPUT_ROOT = @LEX_OUTPUT_ROOT@ LIBOBJS = @LIBOBJS@ LIBS = @LIBS@ LIBTOOL = @LIBTOOL@ +LIPO = @LIPO@ LN_S = @LN_S@ LTLIBOBJS = @LTLIBOBJS@ MAINT = @MAINT@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MIG = @MIG@ MKDIR_P = @MKDIR_P@ +NM = @NM@ NMEDIT = @NMEDIT@ +OBJDUMP = @OBJDUMP@ OBJEXT = @OBJEXT@ +OTOOL = @OTOOL@ +OTOOL64 = @OTOOL64@ PACKAGE = @PACKAGE@ PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@ PACKAGE_NAME = @PACKAGE_NAME@ PACKAGE_STRING = @PACKAGE_STRING@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ +PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ RANLIB = @RANLIB@ @@ -139,13 +194,15 @@ SET_MAKE = @SET_MAKE@ SHELL = @SHELL@ STRIP = @STRIP@ VERSION = @VERSION@ +YACC = @YACC@ +YFLAGS = @YFLAGS@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ -ac_ct_CXX = @ac_ct_CXX@ -ac_ct_F77 = @ac_ct_F77@ +ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ am__include = @am__include@ am__leading_dot = @am__leading_dot@ am__quote = @am__quote@ @@ -206,14 +263,14 @@ $(srcdir)/Makefile.in: @MAINTAINER_MODE_TRUE@ $(srcdir)/Makefile.am $(am__confi @for dep in $?; do \ case '$(am__configure_deps)' in \ *$$dep*) \ - cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh \ - && exit 0; \ + ( cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh ) \ + && { if test -f $@; then exit 0; else break; fi; }; \ exit 1;; \ esac; \ done; \ - echo ' cd $(top_srcdir) && $(AUTOMAKE) --foreign bin/auditd/Makefile'; \ - cd $(top_srcdir) && \ - $(AUTOMAKE) --foreign bin/auditd/Makefile + echo ' cd $(top_srcdir) && $(AUTOMAKE) --foreign bin/auditd/Makefile'; \ + $(am__cd) $(top_srcdir) && \ + $(AUTOMAKE) --foreign bin/auditd/Makefile .PRECIOUS: Makefile Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status @case '$?' in \ @@ -231,35 +288,54 @@ $(top_srcdir)/configure: @MAINTAINER_MODE_TRUE@ $(am__configure_deps) cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh $(ACLOCAL_M4): @MAINTAINER_MODE_TRUE@ $(am__aclocal_m4_deps) cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh +$(am__aclocal_m4_deps): install-sbinPROGRAMS: $(sbin_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(sbindir)" || $(MKDIR_P) "$(DESTDIR)$(sbindir)" - @list='$(sbin_PROGRAMS)'; for p in $$list; do \ - p1=`echo $$p|sed 's/$(EXEEXT)$$//'`; \ - if test -f $$p \ - || test -f $$p1 \ - ; then \ - f=`echo "$$p1" | sed 's,^.*/,,;$(transform);s/$$/$(EXEEXT)/'`; \ - echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(sbinPROGRAMS_INSTALL) '$$p' '$(DESTDIR)$(sbindir)/$$f'"; \ - $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(sbinPROGRAMS_INSTALL) "$$p" "$(DESTDIR)$(sbindir)/$$f" || exit 1; \ - else :; fi; \ - done + @list='$(sbin_PROGRAMS)'; test -n "$(sbindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(sbindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(sbindir)" || exit 1; \ + fi; \ + for p in $$list; do echo "$$p $$p"; done | \ + sed 's/$(EXEEXT)$$//' | \ + while read p p1; do if test -f $$p || test -f $$p1; \ + then echo "$$p"; echo "$$p"; else :; fi; \ + done | \ + sed -e 'p;s,.*/,,;n;h' -e 's|.*|.|' \ + -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ + sed 'N;N;N;s,\n, ,g' | \ + $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ + { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ + if ($$2 == $$4) files[d] = files[d] " " $$1; \ + else { print "f", $$3 "/" $$4, $$1; } } \ + END { for (d in files) print "f", d, files[d] }' | \ + while read type dir files; do \ + if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ + test -z "$$files" || { \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(sbindir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(sbindir)$$dir" || exit $$?; \ + } \ + ; done uninstall-sbinPROGRAMS: @$(NORMAL_UNINSTALL) - @list='$(sbin_PROGRAMS)'; for p in $$list; do \ - f=`echo "$$p" | sed 's,^.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/'`; \ - echo " rm -f '$(DESTDIR)$(sbindir)/$$f'"; \ - rm -f "$(DESTDIR)$(sbindir)/$$f"; \ - done + @list='$(sbin_PROGRAMS)'; test -n "$(sbindir)" || list=; \ + files=`for p in $$list; do echo "$$p"; done | \ + sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ + -e 's/$$/$(EXEEXT)/' `; \ + test -n "$$list" || exit 0; \ + echo " ( cd '$(DESTDIR)$(sbindir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(sbindir)" && rm -f $$files clean-sbinPROGRAMS: - @list='$(sbin_PROGRAMS)'; for p in $$list; do \ - f=`echo $$p|sed 's/$(EXEEXT)$$//'`; \ - echo " rm -f $$p $$f"; \ - rm -f $$p $$f ; \ - done -auditd$(EXEEXT): $(auditd_OBJECTS) $(auditd_DEPENDENCIES) + @list='$(sbin_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +auditd$(EXEEXT): $(auditd_OBJECTS) $(auditd_DEPENDENCIES) $(EXTRA_auditd_DEPENDENCIES) @rm -f auditd$(EXEEXT) $(LINK) $(auditd_OBJECTS) $(auditd_LDADD) $(LIBS) @@ -278,21 +354,21 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< -@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po +@am__fastdepCC_TRUE@ $(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po @AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` -@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po +@am__fastdepCC_TRUE@ $(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po @AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< -@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo +@am__fastdepCC_TRUE@ $(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< @@ -302,65 +378,61 @@ mostlyclean-libtool: clean-libtool: -rm -rf .libs _libs -install-man8: $(man8_MANS) $(man_MANS) +install-man8: $(man8_MANS) @$(NORMAL_INSTALL) - test -z "$(man8dir)" || $(MKDIR_P) "$(DESTDIR)$(man8dir)" - @list='$(man8_MANS) $(dist_man8_MANS) $(nodist_man8_MANS)'; \ - l2='$(man_MANS) $(dist_man_MANS) $(nodist_man_MANS)'; \ - for i in $$l2; do \ - case "$$i" in \ - *.8*) list="$$list $$i" ;; \ - esac; \ + @list1='$(man8_MANS)'; \ + list2=''; \ + test -n "$(man8dir)" \ + && test -n "`echo $$list1$$list2`" \ + || exit 0; \ + echo " $(MKDIR_P) '$(DESTDIR)$(man8dir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(man8dir)" || exit 1; \ + { for i in $$list1; do echo "$$i"; done; \ + if test -n "$$list2"; then \ + for i in $$list2; do echo "$$i"; done \ + | sed -n '/\.8[a-z]*$$/p'; \ + fi; \ + } | while read p; do \ + if test -f $$p; then d=; else d="$(srcdir)/"; fi; \ + echo "$$d$$p"; echo "$$p"; \ + done | \ + sed -e 'n;s,.*/,,;p;h;s,.*\.,,;s,^[^8][0-9a-z]*$$,8,;x' \ + -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,' | \ + sed 'N;N;s,\n, ,g' | { \ + list=; while read file base inst; do \ + if test "$$base" = "$$inst"; then list="$$list $$file"; else \ + echo " $(INSTALL_DATA) '$$file' '$(DESTDIR)$(man8dir)/$$inst'"; \ + $(INSTALL_DATA) "$$file" "$(DESTDIR)$(man8dir)/$$inst" || exit $$?; \ + fi; \ done; \ - for i in $$list; do \ - if test -f $(srcdir)/$$i; then file=$(srcdir)/$$i; \ - else file=$$i; fi; \ - ext=`echo $$i | sed -e 's/^.*\\.//'`; \ - case "$$ext" in \ - 8*) ;; \ - *) ext='8' ;; \ - esac; \ - inst=`echo $$i | sed -e 's/\\.[0-9a-z]*$$//'`; \ - inst=`echo $$inst | sed -e 's/^.*\///'`; \ - inst=`echo $$inst | sed '$(transform)'`.$$ext; \ - echo " $(INSTALL_DATA) '$$file' '$(DESTDIR)$(man8dir)/$$inst'"; \ - $(INSTALL_DATA) "$$file" "$(DESTDIR)$(man8dir)/$$inst"; \ - done + for i in $$list; do echo "$$i"; done | $(am__base_list) | \ + while read files; do \ + test -z "$$files" || { \ + echo " $(INSTALL_DATA) $$files '$(DESTDIR)$(man8dir)'"; \ + $(INSTALL_DATA) $$files "$(DESTDIR)$(man8dir)" || exit $$?; }; \ + done; } + uninstall-man8: @$(NORMAL_UNINSTALL) - @list='$(man8_MANS) $(dist_man8_MANS) $(nodist_man8_MANS)'; \ - l2='$(man_MANS) $(dist_man_MANS) $(nodist_man_MANS)'; \ - for i in $$l2; do \ - case "$$i" in \ - *.8*) list="$$list $$i" ;; \ - esac; \ - done; \ - for i in $$list; do \ - ext=`echo $$i | sed -e 's/^.*\\.//'`; \ - case "$$ext" in \ - 8*) ;; \ - *) ext='8' ;; \ - esac; \ - inst=`echo $$i | sed -e 's/\\.[0-9a-z]*$$//'`; \ - inst=`echo $$inst | sed -e 's/^.*\///'`; \ - inst=`echo $$inst | sed '$(transform)'`.$$ext; \ - echo " rm -f '$(DESTDIR)$(man8dir)/$$inst'"; \ - rm -f "$(DESTDIR)$(man8dir)/$$inst"; \ - done + @list='$(man8_MANS)'; test -n "$(man8dir)" || exit 0; \ + files=`{ for i in $$list; do echo "$$i"; done; \ + } | sed -e 's,.*/,,;h;s,.*\.,,;s,^[^8][0-9a-z]*$$,8,;x' \ + -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,'`; \ + dir='$(DESTDIR)$(man8dir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ unique=`for i in $$list; do \ if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ done | \ - $(AWK) '{ files[$$0] = 1; nonemtpy = 1; } \ + $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ END { if (nonempty) { for (i in files) print i; }; }'`; \ mkid -fID $$unique tags: TAGS TAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ $(TAGS_FILES) $(LISP) - tags=; \ + set x; \ here=`pwd`; \ list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ unique=`for i in $$list; do \ @@ -368,34 +440,66 @@ TAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ done | \ $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ END { if (nonempty) { for (i in files) print i; }; }'`; \ - if test -z "$(ETAGS_ARGS)$$tags$$unique"; then :; else \ + shift; \ + if test -z "$(ETAGS_ARGS)$$*$$unique"; then :; else \ test -n "$$unique" || unique=$$empty_fix; \ - $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ - $$tags $$unique; \ + if test $$# -gt 0; then \ + $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ + "$$@" $$unique; \ + else \ + $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ + $$unique; \ + fi; \ fi ctags: CTAGS CTAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ $(TAGS_FILES) $(LISP) - tags=; \ list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ unique=`for i in $$list; do \ if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ done | \ $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ END { if (nonempty) { for (i in files) print i; }; }'`; \ - test -z "$(CTAGS_ARGS)$$tags$$unique" \ + test -z "$(CTAGS_ARGS)$$unique" \ || $(CTAGS) $(CTAGSFLAGS) $(AM_CTAGSFLAGS) $(CTAGS_ARGS) \ - $$tags $$unique + $$unique GTAGS: here=`$(am__cd) $(top_builddir) && pwd` \ - && cd $(top_srcdir) \ - && gtags -i $(GTAGS_ARGS) $$here + && $(am__cd) $(top_srcdir) \ + && gtags -i $(GTAGS_ARGS) "$$here" + +cscopelist: $(HEADERS) $(SOURCES) $(LISP) + list='$(SOURCES) $(HEADERS) $(LISP)'; \ + case "$(srcdir)" in \ + [\\/]* | ?:[\\/]*) sdir="$(srcdir)" ;; \ + *) sdir=$(subdir)/$(srcdir) ;; \ + esac; \ + for i in $$list; do \ + if test -f "$$i"; then \ + echo "$(subdir)/$$i"; \ + else \ + echo "$$sdir/$$i"; \ + fi; \ + done >> $(top_builddir)/cscope.files distclean-tags: -rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags distdir: $(DISTFILES) + @list='$(MANS)'; if test -n "$$list"; then \ + list=`for p in $$list; do \ + if test -f $$p; then d=; else d="$(srcdir)/"; fi; \ + if test -f "$$d$$p"; then echo "$$d$$p"; else :; fi; done`; \ + if test -n "$$list" && \ + grep 'ab help2man is required to generate this page' $$list >/dev/null; then \ + echo "error: found man pages containing the 'missing help2man' replacement text:" >&2; \ + grep -l 'ab help2man is required to generate this page' $$list | sed 's/^/ /' >&2; \ + echo " to fix them, install help2man, remove and regenerate the man pages;" >&2; \ + echo " typically 'make maintainer-clean' will remove them" >&2; \ + exit 1; \ + else :; fi; \ + else :; fi @srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ topsrcdirstrip=`echo "$(top_srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ list='$(DISTFILES)'; \ @@ -411,13 +515,17 @@ distdir: $(DISTFILES) if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \ if test -d $$d/$$file; then \ dir=`echo "/$$file" | sed -e 's,/[^/]*$$,,'`; \ + if test -d "$(distdir)/$$file"; then \ + find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \ + fi; \ if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \ - cp -pR $(srcdir)/$$file $(distdir)$$dir || exit 1; \ + cp -fpR $(srcdir)/$$file "$(distdir)$$dir" || exit 1; \ + find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \ fi; \ - cp -pR $$d/$$file $(distdir)$$dir || exit 1; \ + cp -fpR $$d/$$file "$(distdir)$$dir" || exit 1; \ else \ - test -f $(distdir)/$$file \ - || cp -p $$d/$$file $(distdir)/$$file \ + test -f "$(distdir)/$$file" \ + || cp -p $$d/$$file "$(distdir)/$$file" \ || exit 1; \ fi; \ done @@ -438,10 +546,15 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: @@ -449,6 +562,7 @@ clean-generic: distclean-generic: -test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES) + -test . = "$(srcdir)" || test -z "$(CONFIG_CLEAN_VPATH_FILES)" || rm -f $(CONFIG_CLEAN_VPATH_FILES) maintainer-clean-generic: @echo "This command is intended for maintainers to use" @@ -470,6 +584,8 @@ dvi-am: html: html-am +html-am: + info: info-am info-am: @@ -478,18 +594,28 @@ install-data-am: install-man install-dvi: install-dvi-am +install-dvi-am: + install-exec-am: install-sbinPROGRAMS install-html: install-html-am +install-html-am: + install-info: install-info-am +install-info-am: + install-man: install-man8 install-pdf: install-pdf-am +install-pdf-am: + install-ps: install-ps-am +install-ps-am: + installcheck-am: maintainer-clean: maintainer-clean-am @@ -517,7 +643,7 @@ uninstall-man: uninstall-man8 .MAKE: install-am install-strip .PHONY: CTAGS GTAGS all all-am check check-am clean clean-generic \ - clean-libtool clean-sbinPROGRAMS ctags distclean \ + clean-libtool clean-sbinPROGRAMS cscopelist ctags distclean \ distclean-compile distclean-generic distclean-libtool \ distclean-tags distdir dvi dvi-am html html-am info info-am \ install install-am install-data install-data-am install-dvi \ @@ -537,6 +663,7 @@ uninstall-man: uninstall-man8 @USE_MACH_IPC_TRUE@audit_triggersServer.c audit_triggersServer.h: audit_triggers.defs @USE_MACH_IPC_TRUE@ $(MIG) -user /dev/null -header /dev/null -server audit_triggersServer.c -sheader audit_triggersServer.h $(top_srcdir)/bin/auditd/audit_triggers.defs + # Tell versions [3.59,3.63) of GNU make to not export all variables. # Otherwise a system limit (for SysV at least) may be exceeded. .NOEXPORT: diff --git a/contrib/openbsm/bin/auditd/auditd.8 b/contrib/openbsm/bin/auditd/auditd.8 index d680edd..b437524 100644 --- a/contrib/openbsm/bin/auditd/auditd.8 +++ b/contrib/openbsm/bin/auditd/auditd.8 @@ -25,7 +25,7 @@ .\" (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF .\" THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. .\" -.\" $P4: //depot/projects/trustedbsd/openbsm/bin/auditd/auditd.8#17 $ +.\" $P4: //depot/projects/trustedbsd/openbsm/bin/auditd/auditd.8#19 $ .\" .Dd December 11, 2008 .Dt AUDITD 8 @@ -59,7 +59,7 @@ is configured to start on-demand using .Pp Optionally, the audit review group "audit" may be created. Non-privileged -users that are members of this group may read the audit trail log files. +users that are members of this group may read the audit trail log files. .Sh NOTE To assure uninterrupted audit support, the .Nm @@ -72,33 +72,33 @@ the .Pa audit_control file. .Pp -If +If .Nm is started on-demand by -.Xr launchd 8 +.Xr launchd 8 then auditing should only be started and stopped with .Xr audit 8 . .Pp -On Mac OS X, +On Mac OS X, .Nm -uses the +uses the .Xr asl 3 API for writing system log messages. -Therefore, only the audit administrator +Therefore, only the audit administrator and members of the audit review group will be able to read the -system log entries. +system log entries. .Sh FILES .Bl -tag -width ".Pa /etc/security" -compact .It Pa /var/audit Default directory for storing audit log files. .Pp .It Pa /etc/security -The directory containing the auditing configuration files +The directory containing the auditing configuration files .Xr audit_class 5 , .Xr audit_control 5 , .Xr audit_event 5 , and -.Xr audit_warn 5 . +.Xr audit_warn 5 . .El .Sh COMPATIBILITY The historical @@ -122,6 +122,7 @@ and are no longer available as arguments to .Xr audit_event 5 , .Xr audit_warn 5 , .Xr audit 8 , +.Xr auditdistd 8 , .Xr launchd 8 .Sh HISTORY The OpenBSM implementation was created by McAfee Research, the security diff --git a/contrib/openbsm/bin/auditd/auditd.c b/contrib/openbsm/bin/auditd/auditd.c index 233f821..26a0d07 100644 --- a/contrib/openbsm/bin/auditd/auditd.c +++ b/contrib/openbsm/bin/auditd/auditd.c @@ -26,7 +26,7 @@ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. * - * $P4: //depot/projects/trustedbsd/openbsm/bin/auditd/auditd.c#46 $ + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditd/auditd.c#50 $ */ #include <sys/types.h> @@ -36,9 +36,9 @@ #include <sys/dirent.h> #ifdef HAVE_FULL_QUEUE_H #include <sys/queue.h> -#else /* !HAVE_FULL_QUEUE_H */ +#else /* !HAVE_FULL_QUEUE_H */ #include <compat/queue.h> -#endif /* !HAVE_FULL_QUEUE_H */ +#endif /* !HAVE_FULL_QUEUE_H */ #include <sys/mman.h> #include <sys/param.h> #include <sys/stat.h> @@ -79,21 +79,21 @@ /* - * LaunchD flag (Mac OS X and, maybe, FreeBSD only.) See launchd(8) and + * LaunchD flag (Mac OS X and, maybe, FreeBSD only.) See launchd(8) and * http://wiki.freebsd.org/launchd for more information. * - * In order for auditd to work "on demand" with launchd(8) it can't: - * call daemon(3) - * call fork and having the parent process exit - * change uids or gids. - * set up the current working directory or chroot. - * set the session id - * change stdio to /dev/null. - * call setrusage(2) - * call setpriority(2) - * Ignore SIGTERM. - * auditd (in 'launchd mode') is launched on demand so it must catch - * SIGTERM to exit cleanly. + * In order for auditd to work "on demand" with launchd(8) it can't: + * call daemon(3) + * call fork and having the parent process exit + * change uids or gids. + * set up the current working directory or chroot. + * set the session id + * change stdio to /dev/null. + * call setrusage(2) + * call setpriority(2) + * Ignore SIGTERM. + * auditd (in 'launchd mode') is launched on demand so it must catch + * SIGTERM to exit cleanly. */ static int launchd_flag = 0; @@ -133,7 +133,7 @@ get_curfile(void) if (cf == NULL) { auditd_log_err("malloc failed: %m"); return (NULL); - } + } len = readlink(AUDIT_CURRENT_LINK, cf, MAXPATHLEN - 1); if (len < 0) { @@ -142,7 +142,7 @@ get_curfile(void) } /* readlink() doesn't terminate string. */ - cf[len] = '\0'; + cf[len] = '\0'; return (cf); } @@ -155,38 +155,35 @@ close_lastfile(char *TS) { char *ptr; char *oldname; - size_t len; /* If lastfile is NULL try to get it from the 'current' link. */ if (lastfile == NULL) lastfile = get_curfile(); - + if (lastfile != NULL) { - len = strlen(lastfile) + 1; - oldname = (char *)malloc(len); + oldname = strdup(lastfile); if (oldname == NULL) return (-1); - strlcpy(oldname, lastfile, len); /* Rename the last file -- append timestamp. */ if ((ptr = strstr(lastfile, NOT_TERMINATED)) != NULL) { memcpy(ptr, TS, POSTFIX_LEN); - if (rename(oldname, lastfile) != 0) + if (auditd_rename(oldname, lastfile) != 0) auditd_log_err( "Could not rename %s to %s: %m", oldname, lastfile); else { - /* + /* * Remove the 'current' symlink since the link - * is now invalid. + * is now invalid. */ (void) unlink(AUDIT_CURRENT_LINK); - auditd_log_notice( "renamed %s to %s", + auditd_log_notice("renamed %s to %s", oldname, lastfile); audit_warn_closefile(lastfile); } - } else - auditd_log_err( "Could not rename %s to %s", oldname, + } else + auditd_log_err("Could not rename %s to %s", oldname, lastfile); free(lastfile); free(oldname); @@ -202,16 +199,39 @@ static int swap_audit_file(void) { int err; - char *newfile; - char TS[TIMESTAMP_LEN]; + char *newfile, *name; + char TS[TIMESTAMP_LEN + 1]; time_t tt; - if (getTSstr(tt, TS, TIMESTAMP_LEN) != 0) + if (getTSstr(tt, TS, sizeof(TS)) != 0) return (-1); + /* + * If prefix and suffix are the same, it means that records are + * being produced too fast. We don't want to rename now, because + * next trail file can get the same name and once that one is + * terminated also within one second it will overwrite the current + * one. Just keep writing to the same trail and wait for the next + * trigger from the kernel. + * FREEBSD KERNEL WAS UPDATED TO KEEP SENDING TRIGGERS, WHICH MIGHT + * NOT BE THE CASE FOR OTHER OSES. + * If the kernel will not keep sending triggers, trail file will not + * be terminated. + */ + if (lastfile == NULL) { + name = NULL; + } else { + name = strrchr(lastfile, '/'); + if (name != NULL) + name++; + } + if (name != NULL && strncmp(name, TS, TIMESTAMP_LEN) == 0) { + auditd_log_debug("Not ready to terminate trail file yet."); + return (0); + } err = auditd_swap_trail(TS, &newfile, audit_review_gid, audit_warn_getacdir); if (err != ADE_NOERR) { - auditd_log_err( "%s: %m", auditd_strerror(err)); + auditd_log_err("%s: %m", auditd_strerror(err)); if (err != ADE_ACTL) return (-1); } @@ -229,13 +249,13 @@ swap_audit_file(void) * enabled) so updated the cached state as well. */ auditd_set_state(AUD_STATE_ENABLED); - + /* * Create 'current' symlink. Recover from crash, if needed. */ if (auditd_new_curlink(newfile) != 0) - auditd_log_err("auditd_new_curlink(\"%s\") failed: %s: %m", - newfile, auditd_strerror(err)); + auditd_log_err("auditd_new_curlink(\"%s\") failed: %s: %m", + newfile, auditd_strerror(err)); lastfile = newfile; auditd_log_notice("New audit file is %s", newfile); @@ -298,6 +318,14 @@ audit_setup(void) { int err; + /* Configure trail files distribution. */ + err = auditd_set_dist(); + if (err) { + auditd_log_err("auditd_set_dist() %s: %m", + auditd_strerror(err)); + } else + auditd_log_debug("Configured trail files distribution."); + if (do_trail_file() == -1) { auditd_log_err("Error creating audit trail file"); fail_exit(); @@ -306,19 +334,18 @@ audit_setup(void) /* Generate an audit record. */ err = auditd_gen_record(AUE_audit_startup, NULL); if (err) - auditd_log_err("auditd_gen_record(AUE_audit_startup) %s: %m", + auditd_log_err("auditd_gen_record(AUE_audit_startup) %s: %m", auditd_strerror(err)); - + if (auditd_config_controls() == 0) auditd_log_info("Audit controls init successful"); else auditd_log_err("Audit controls init failed"); - } /* - * Close auditd pid file and trigger mechanism. + * Close auditd pid file and trigger mechanism. */ static int close_misc(void) @@ -345,14 +372,14 @@ static int close_all(void) { int err_ret = 0; - char TS[TIMESTAMP_LEN]; + char TS[TIMESTAMP_LEN + 1]; int err; int cond; time_t tt; err = auditd_gen_record(AUE_audit_shutdown, NULL); if (err) - auditd_log_err("auditd_gen_record(AUE_audit_shutdown) %s: %m", + auditd_log_err("auditd_gen_record(AUE_audit_shutdown) %s: %m", auditd_strerror(err)); /* Flush contents. */ @@ -368,7 +395,7 @@ close_all(void) */ auditd_set_state(AUD_STATE_DISABLED); - if (getTSstr(tt, TS, TIMESTAMP_LEN) == 0) + if (getTSstr(tt, TS, sizeof(TS)) == 0) close_lastfile(TS); if (lastfile != NULL) free(lastfile); @@ -513,7 +540,7 @@ auditd_handle_trigger(int trigger) /* * Message processing is done here. - */ + */ switch(trigger) { case AUDIT_TRIGGER_LOW_SPACE: auditd_log_notice("Got low space trigger"); @@ -554,7 +581,7 @@ auditd_handle_trigger(int trigger) * send SIGTERM. */ if (!launchd_flag) { - auditd_log_info("auditd exiting."); + auditd_log_info("auditd exiting."); exit (err); } break; @@ -570,7 +597,7 @@ auditd_handle_trigger(int trigger) err = auditd_expire_trails(audit_warn_expired); if (err) auditd_log_err("auditd_expire_trails(): %s", - auditd_strerror(err)); + auditd_strerror(err)); break; default: @@ -609,7 +636,7 @@ auditd_terminate(void) int ret; auditd_reap_children(); - + if (launchd_flag) ret = close_misc(); else @@ -630,7 +657,7 @@ auditd_config_controls(void) /* * Configure event to class mappings in kernel. - */ + */ cnt = auditd_set_evcmap(); if (cnt < 0) { auditd_log_err("auditd_set_evcmap() failed: %m"); @@ -646,7 +673,7 @@ auditd_config_controls(void) */ err = auditd_set_namask(); if (err) { - auditd_log_err("auditd_set_namask() %s: %m", + auditd_log_err("auditd_set_namask() %s: %m", auditd_strerror(err)); ret = -1; } else @@ -657,12 +684,12 @@ auditd_config_controls(void) */ err = auditd_set_policy(); if (err) { - auditd_log_err("auditd_set_policy() %s: %m", + auditd_log_err("auditd_set_policy() %s: %m", auditd_strerror(err)); ret = -1; } else auditd_log_debug("Set audit policy in kernel."); - + /* * Configure audit trail log size in kernel. */ @@ -673,9 +700,9 @@ auditd_config_controls(void) ret = -1; } else auditd_log_debug("Set audit trail size in kernel."); - + /* - * Configure audit trail volume minimum free percentage of blocks in + * Configure audit trail volume minimum free percentage of blocks in * kernel. */ err = auditd_set_minfree(); @@ -684,11 +711,11 @@ auditd_config_controls(void) auditd_strerror(err)); ret = -1; } else - auditd_log_debug( + auditd_log_debug( "Set audit trail min free percent in kernel."); /* - * Configure host address in the audit kernel information. + * Configure host address in the audit kernel information. */ err = auditd_set_host(); if (err) { @@ -730,7 +757,7 @@ setup(void) */ err = auditd_prevent_audit(); if (err) { - auditd_log_err("auditd_prevent_audit() %s: %m", + auditd_log_err("auditd_prevent_audit() %s: %m", auditd_strerror(err)); fail_exit(); } @@ -785,7 +812,7 @@ main(int argc, char **argv) * likely the wheel group. Is there a better way to deal with this? */ grp = getgrnam(AUDIT_REVIEW_GROUP); - if (grp != NULL) + if (grp != NULL) audit_review_gid = grp->gr_gid; #endif @@ -815,7 +842,7 @@ main(int argc, char **argv) setup(); /* - * auditd_wait_for_events() shouldn't return unless something is wrong. + * auditd_wait_for_events() shouldn't return unless something is wrong. */ auditd_wait_for_events(); diff --git a/contrib/openbsm/bin/auditdistd/Makefile.am b/contrib/openbsm/bin/auditdistd/Makefile.am new file mode 100644 index 0000000..88f2584 --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/Makefile.am @@ -0,0 +1,33 @@ +## +## $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/Makefile.am#1 $ +## + +if USE_NATIVE_INCLUDES +INCLUDES = -I$(top_builddir) -I$(top_srcdir) +else +INCLUDES = -I$(top_builddir) -I$(top_srcdir) -I$(top_srcdir)/sys +endif + +sbin_PROGRAMS = auditdistd +man5_MANS = auditdistd.conf.5 +man8_MANS = auditdistd.8 +CFLAGS = -Wno-format +YFLAGS = -d +auditdistd_LDFLAGS = -lcrypto + +auditdistd_SOURCES = \ + auditdistd.c \ + parse.y \ + pjdlog.c \ + proto.c \ + proto_common.c \ + proto_socketpair.c \ + proto_tcp.c \ + proto_tls.c \ + proto_uds.c \ + receiver.c \ + sandbox.c \ + sender.c \ + subr.c \ + token.l \ + trail.c diff --git a/contrib/openbsm/bin/auditdistd/Makefile.in b/contrib/openbsm/bin/auditdistd/Makefile.in new file mode 100644 index 0000000..b6228fd --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/Makefile.in @@ -0,0 +1,753 @@ +# Makefile.in generated by automake 1.12.2 from Makefile.am. +# @configure_input@ + +# Copyright (C) 1994-2012 Free Software Foundation, Inc. + +# This Makefile.in is free software; the Free Software Foundation +# gives unlimited permission to copy and/or distribute it, +# with or without modifications, as long as this notice is preserved. + +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY, to the extent permitted by law; without +# even the implied warranty of MERCHANTABILITY or FITNESS FOR A +# PARTICULAR PURPOSE. + +@SET_MAKE@ + +VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } +pkgdatadir = $(datadir)/@PACKAGE@ +pkgincludedir = $(includedir)/@PACKAGE@ +pkglibdir = $(libdir)/@PACKAGE@ +pkglibexecdir = $(libexecdir)/@PACKAGE@ +am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd +install_sh_DATA = $(install_sh) -c -m 644 +install_sh_PROGRAM = $(install_sh) -c +install_sh_SCRIPT = $(install_sh) -c +INSTALL_HEADER = $(INSTALL_DATA) +transform = $(program_transform_name) +NORMAL_INSTALL = : +PRE_INSTALL = : +POST_INSTALL = : +NORMAL_UNINSTALL = : +PRE_UNINSTALL = : +POST_UNINSTALL = : +build_triplet = @build@ +host_triplet = @host@ +sbin_PROGRAMS = auditdistd$(EXEEXT) +subdir = bin/auditdistd +DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ + $(top_srcdir)/config/depcomp $(top_srcdir)/config/ylwrap \ + parse.c parse.h token.c +ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 +am__aclocal_m4_deps = $(top_srcdir)/configure.ac +am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ + $(ACLOCAL_M4) +mkinstalldirs = $(install_sh) -d +CONFIG_HEADER = $(top_builddir)/config/config.h +CONFIG_CLEAN_FILES = +CONFIG_CLEAN_VPATH_FILES = +am__installdirs = "$(DESTDIR)$(sbindir)" "$(DESTDIR)$(man5dir)" \ + "$(DESTDIR)$(man8dir)" +PROGRAMS = $(sbin_PROGRAMS) +am_auditdistd_OBJECTS = auditdistd.$(OBJEXT) parse.$(OBJEXT) \ + pjdlog.$(OBJEXT) proto.$(OBJEXT) proto_common.$(OBJEXT) \ + proto_socketpair.$(OBJEXT) proto_tcp.$(OBJEXT) \ + proto_tls.$(OBJEXT) proto_uds.$(OBJEXT) receiver.$(OBJEXT) \ + sandbox.$(OBJEXT) sender.$(OBJEXT) subr.$(OBJEXT) \ + token.$(OBJEXT) trail.$(OBJEXT) +auditdistd_OBJECTS = $(am_auditdistd_OBJECTS) +auditdistd_LDADD = $(LDADD) +auditdistd_LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) \ + $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ + $(auditdistd_LDFLAGS) $(LDFLAGS) -o $@ +DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir)/config +depcomp = $(SHELL) $(top_srcdir)/config/depcomp +am__depfiles_maybe = depfiles +am__mv = mv -f +COMPILE = $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) \ + $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) +LTCOMPILE = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) \ + --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) \ + $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) +CCLD = $(CC) +LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) \ + --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) $(AM_LDFLAGS) \ + $(LDFLAGS) -o $@ +@MAINTAINER_MODE_FALSE@am__skiplex = test -f $@ || +LEXCOMPILE = $(LEX) $(AM_LFLAGS) $(LFLAGS) +LTLEXCOMPILE = $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) \ + --mode=compile $(LEX) $(AM_LFLAGS) $(LFLAGS) +YLWRAP = $(top_srcdir)/config/ylwrap +@MAINTAINER_MODE_FALSE@am__skipyacc = test -f $@ || +am__yacc_c2h = sed -e s/cc$$/hh/ -e s/cpp$$/hpp/ -e s/cxx$$/hxx/ \ + -e s/c++$$/h++/ -e s/c$$/h/ +YACCCOMPILE = $(YACC) $(AM_YFLAGS) $(YFLAGS) +LTYACCCOMPILE = $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) \ + --mode=compile $(YACC) $(AM_YFLAGS) $(YFLAGS) +SOURCES = $(auditdistd_SOURCES) +DIST_SOURCES = $(auditdistd_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac +am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; +am__vpath_adj = case $$p in \ + $(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \ + *) f=$$p;; \ + esac; +am__strip_dir = f=`echo $$p | sed -e 's|^.*/||'`; +am__install_max = 40 +am__nobase_strip_setup = \ + srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*|]/\\\\&/g'` +am__nobase_strip = \ + for p in $$list; do echo "$$p"; done | sed -e "s|$$srcdirstrip/||" +am__nobase_list = $(am__nobase_strip_setup); \ + for p in $$list; do echo "$$p $$p"; done | \ + sed "s| $$srcdirstrip/| |;"' / .*\//!s/ .*/ ./; s,\( .*\)/[^/]*$$,\1,' | \ + $(AWK) 'BEGIN { files["."] = "" } { files[$$2] = files[$$2] " " $$1; \ + if (++n[$$2] == $(am__install_max)) \ + { print $$2, files[$$2]; n[$$2] = 0; files[$$2] = "" } } \ + END { for (dir in files) print dir, files[dir] }' +am__base_list = \ + sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ + sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } +man5dir = $(mandir)/man5 +man8dir = $(mandir)/man8 +NROFF = nroff +MANS = $(man5_MANS) $(man8_MANS) +ETAGS = etags +CTAGS = ctags +DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) +ACLOCAL = @ACLOCAL@ +AMTAR = @AMTAR@ +AR = @AR@ +AUTOCONF = @AUTOCONF@ +AUTOHEADER = @AUTOHEADER@ +AUTOMAKE = @AUTOMAKE@ +AWK = @AWK@ +CC = @CC@ +CCDEPMODE = @CCDEPMODE@ +CFLAGS = -Wno-format +CPP = @CPP@ +CPPFLAGS = @CPPFLAGS@ +CYGPATH_W = @CYGPATH_W@ +DEFS = @DEFS@ +DEPDIR = @DEPDIR@ +DLLTOOL = @DLLTOOL@ +DSYMUTIL = @DSYMUTIL@ +DUMPBIN = @DUMPBIN@ +ECHO_C = @ECHO_C@ +ECHO_N = @ECHO_N@ +ECHO_T = @ECHO_T@ +EGREP = @EGREP@ +EXEEXT = @EXEEXT@ +FGREP = @FGREP@ +GREP = @GREP@ +INSTALL = @INSTALL@ +INSTALL_DATA = @INSTALL_DATA@ +INSTALL_PROGRAM = @INSTALL_PROGRAM@ +INSTALL_SCRIPT = @INSTALL_SCRIPT@ +INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@ +LD = @LD@ +LDFLAGS = @LDFLAGS@ +LEX = @LEX@ +LEXLIB = @LEXLIB@ +LEX_OUTPUT_ROOT = @LEX_OUTPUT_ROOT@ +LIBOBJS = @LIBOBJS@ +LIBS = @LIBS@ +LIBTOOL = @LIBTOOL@ +LIPO = @LIPO@ +LN_S = @LN_S@ +LTLIBOBJS = @LTLIBOBJS@ +MAINT = @MAINT@ +MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ +MIG = @MIG@ +MKDIR_P = @MKDIR_P@ +NM = @NM@ +NMEDIT = @NMEDIT@ +OBJDUMP = @OBJDUMP@ +OBJEXT = @OBJEXT@ +OTOOL = @OTOOL@ +OTOOL64 = @OTOOL64@ +PACKAGE = @PACKAGE@ +PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@ +PACKAGE_NAME = @PACKAGE_NAME@ +PACKAGE_STRING = @PACKAGE_STRING@ +PACKAGE_TARNAME = @PACKAGE_TARNAME@ +PACKAGE_URL = @PACKAGE_URL@ +PACKAGE_VERSION = @PACKAGE_VERSION@ +PATH_SEPARATOR = @PATH_SEPARATOR@ +RANLIB = @RANLIB@ +SED = @SED@ +SET_MAKE = @SET_MAKE@ +SHELL = @SHELL@ +STRIP = @STRIP@ +VERSION = @VERSION@ +YACC = @YACC@ +YFLAGS = -d +abs_builddir = @abs_builddir@ +abs_srcdir = @abs_srcdir@ +abs_top_builddir = @abs_top_builddir@ +abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ +ac_ct_CC = @ac_ct_CC@ +ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ +am__include = @am__include@ +am__leading_dot = @am__leading_dot@ +am__quote = @am__quote@ +am__tar = @am__tar@ +am__untar = @am__untar@ +bindir = @bindir@ +build = @build@ +build_alias = @build_alias@ +build_cpu = @build_cpu@ +build_os = @build_os@ +build_vendor = @build_vendor@ +builddir = @builddir@ +datadir = @datadir@ +datarootdir = @datarootdir@ +docdir = @docdir@ +dvidir = @dvidir@ +exec_prefix = @exec_prefix@ +host = @host@ +host_alias = @host_alias@ +host_cpu = @host_cpu@ +host_os = @host_os@ +host_vendor = @host_vendor@ +htmldir = @htmldir@ +includedir = @includedir@ +infodir = @infodir@ +install_sh = @install_sh@ +libdir = @libdir@ +libexecdir = @libexecdir@ +localedir = @localedir@ +localstatedir = @localstatedir@ +mandir = @mandir@ +mkdir_p = @mkdir_p@ +oldincludedir = @oldincludedir@ +pdfdir = @pdfdir@ +prefix = @prefix@ +program_transform_name = @program_transform_name@ +psdir = @psdir@ +sbindir = @sbindir@ +sharedstatedir = @sharedstatedir@ +srcdir = @srcdir@ +sysconfdir = @sysconfdir@ +target_alias = @target_alias@ +top_build_prefix = @top_build_prefix@ +top_builddir = @top_builddir@ +top_srcdir = @top_srcdir@ +@USE_NATIVE_INCLUDES_FALSE@INCLUDES = -I$(top_builddir) -I$(top_srcdir) -I$(top_srcdir)/sys +@USE_NATIVE_INCLUDES_TRUE@INCLUDES = -I$(top_builddir) -I$(top_srcdir) +man5_MANS = auditdistd.conf.5 +man8_MANS = auditdistd.8 +auditdistd_LDFLAGS = -lcrypto +auditdistd_SOURCES = \ + auditdistd.c \ + parse.y \ + pjdlog.c \ + proto.c \ + proto_common.c \ + proto_socketpair.c \ + proto_tcp.c \ + proto_tls.c \ + proto_uds.c \ + receiver.c \ + sandbox.c \ + sender.c \ + subr.c \ + token.l \ + trail.c + +all: all-am + +.SUFFIXES: +.SUFFIXES: .c .l .lo .o .obj .y +$(srcdir)/Makefile.in: @MAINTAINER_MODE_TRUE@ $(srcdir)/Makefile.am $(am__configure_deps) + @for dep in $?; do \ + case '$(am__configure_deps)' in \ + *$$dep*) \ + ( cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh ) \ + && { if test -f $@; then exit 0; else break; fi; }; \ + exit 1;; \ + esac; \ + done; \ + echo ' cd $(top_srcdir) && $(AUTOMAKE) --foreign bin/auditdistd/Makefile'; \ + $(am__cd) $(top_srcdir) && \ + $(AUTOMAKE) --foreign bin/auditdistd/Makefile +.PRECIOUS: Makefile +Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status + @case '$?' in \ + *config.status*) \ + cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh;; \ + *) \ + echo ' cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe)'; \ + cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe);; \ + esac; + +$(top_builddir)/config.status: $(top_srcdir)/configure $(CONFIG_STATUS_DEPENDENCIES) + cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh + +$(top_srcdir)/configure: @MAINTAINER_MODE_TRUE@ $(am__configure_deps) + cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh +$(ACLOCAL_M4): @MAINTAINER_MODE_TRUE@ $(am__aclocal_m4_deps) + cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh +$(am__aclocal_m4_deps): +install-sbinPROGRAMS: $(sbin_PROGRAMS) + @$(NORMAL_INSTALL) + @list='$(sbin_PROGRAMS)'; test -n "$(sbindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(sbindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(sbindir)" || exit 1; \ + fi; \ + for p in $$list; do echo "$$p $$p"; done | \ + sed 's/$(EXEEXT)$$//' | \ + while read p p1; do if test -f $$p || test -f $$p1; \ + then echo "$$p"; echo "$$p"; else :; fi; \ + done | \ + sed -e 'p;s,.*/,,;n;h' -e 's|.*|.|' \ + -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ + sed 'N;N;N;s,\n, ,g' | \ + $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ + { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ + if ($$2 == $$4) files[d] = files[d] " " $$1; \ + else { print "f", $$3 "/" $$4, $$1; } } \ + END { for (d in files) print "f", d, files[d] }' | \ + while read type dir files; do \ + if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ + test -z "$$files" || { \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(sbindir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(sbindir)$$dir" || exit $$?; \ + } \ + ; done + +uninstall-sbinPROGRAMS: + @$(NORMAL_UNINSTALL) + @list='$(sbin_PROGRAMS)'; test -n "$(sbindir)" || list=; \ + files=`for p in $$list; do echo "$$p"; done | \ + sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ + -e 's/$$/$(EXEEXT)/' `; \ + test -n "$$list" || exit 0; \ + echo " ( cd '$(DESTDIR)$(sbindir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(sbindir)" && rm -f $$files + +clean-sbinPROGRAMS: + @list='$(sbin_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +parse.h: parse.c + @if test ! -f $@; then rm -f parse.c; else :; fi + @if test ! -f $@; then $(MAKE) $(AM_MAKEFLAGS) parse.c; else :; fi +auditdistd$(EXEEXT): $(auditdistd_OBJECTS) $(auditdistd_DEPENDENCIES) $(EXTRA_auditdistd_DEPENDENCIES) + @rm -f auditdistd$(EXEEXT) + $(auditdistd_LINK) $(auditdistd_OBJECTS) $(auditdistd_LDADD) $(LIBS) + +mostlyclean-compile: + -rm -f *.$(OBJEXT) + +distclean-compile: + -rm -f *.tab.c + +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/auditdistd.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/parse.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/pjdlog.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/proto.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/proto_common.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/proto_socketpair.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/proto_tcp.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/proto_tls.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/proto_uds.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/receiver.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/sandbox.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/sender.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/subr.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/token.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/trail.Po@am__quote@ + +.c.o: +@am__fastdepCC_TRUE@ $(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< +@am__fastdepCC_TRUE@ $(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(COMPILE) -c $< + +.c.obj: +@am__fastdepCC_TRUE@ $(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` +@am__fastdepCC_TRUE@ $(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` + +.c.lo: +@am__fastdepCC_TRUE@ $(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< +@am__fastdepCC_TRUE@ $(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo +@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< + +.l.c: + $(am__skiplex) $(SHELL) $(YLWRAP) $< $(LEX_OUTPUT_ROOT).c $@ -- $(LEXCOMPILE) + +.y.c: + $(am__skipyacc) $(SHELL) $(YLWRAP) $< y.tab.c $@ y.tab.h `echo $@ | $(am__yacc_c2h)` y.output $*.output -- $(YACCCOMPILE) + +mostlyclean-libtool: + -rm -f *.lo + +clean-libtool: + -rm -rf .libs _libs +install-man5: $(man5_MANS) + @$(NORMAL_INSTALL) + @list1='$(man5_MANS)'; \ + list2=''; \ + test -n "$(man5dir)" \ + && test -n "`echo $$list1$$list2`" \ + || exit 0; \ + echo " $(MKDIR_P) '$(DESTDIR)$(man5dir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(man5dir)" || exit 1; \ + { for i in $$list1; do echo "$$i"; done; \ + if test -n "$$list2"; then \ + for i in $$list2; do echo "$$i"; done \ + | sed -n '/\.5[a-z]*$$/p'; \ + fi; \ + } | while read p; do \ + if test -f $$p; then d=; else d="$(srcdir)/"; fi; \ + echo "$$d$$p"; echo "$$p"; \ + done | \ + sed -e 'n;s,.*/,,;p;h;s,.*\.,,;s,^[^5][0-9a-z]*$$,5,;x' \ + -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,' | \ + sed 'N;N;s,\n, ,g' | { \ + list=; while read file base inst; do \ + if test "$$base" = "$$inst"; then list="$$list $$file"; else \ + echo " $(INSTALL_DATA) '$$file' '$(DESTDIR)$(man5dir)/$$inst'"; \ + $(INSTALL_DATA) "$$file" "$(DESTDIR)$(man5dir)/$$inst" || exit $$?; \ + fi; \ + done; \ + for i in $$list; do echo "$$i"; done | $(am__base_list) | \ + while read files; do \ + test -z "$$files" || { \ + echo " $(INSTALL_DATA) $$files '$(DESTDIR)$(man5dir)'"; \ + $(INSTALL_DATA) $$files "$(DESTDIR)$(man5dir)" || exit $$?; }; \ + done; } + +uninstall-man5: + @$(NORMAL_UNINSTALL) + @list='$(man5_MANS)'; test -n "$(man5dir)" || exit 0; \ + files=`{ for i in $$list; do echo "$$i"; done; \ + } | sed -e 's,.*/,,;h;s,.*\.,,;s,^[^5][0-9a-z]*$$,5,;x' \ + -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,'`; \ + dir='$(DESTDIR)$(man5dir)'; $(am__uninstall_files_from_dir) +install-man8: $(man8_MANS) + @$(NORMAL_INSTALL) + @list1='$(man8_MANS)'; \ + list2=''; \ + test -n "$(man8dir)" \ + && test -n "`echo $$list1$$list2`" \ + || exit 0; \ + echo " $(MKDIR_P) '$(DESTDIR)$(man8dir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(man8dir)" || exit 1; \ + { for i in $$list1; do echo "$$i"; done; \ + if test -n "$$list2"; then \ + for i in $$list2; do echo "$$i"; done \ + | sed -n '/\.8[a-z]*$$/p'; \ + fi; \ + } | while read p; do \ + if test -f $$p; then d=; else d="$(srcdir)/"; fi; \ + echo "$$d$$p"; echo "$$p"; \ + done | \ + sed -e 'n;s,.*/,,;p;h;s,.*\.,,;s,^[^8][0-9a-z]*$$,8,;x' \ + -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,' | \ + sed 'N;N;s,\n, ,g' | { \ + list=; while read file base inst; do \ + if test "$$base" = "$$inst"; then list="$$list $$file"; else \ + echo " $(INSTALL_DATA) '$$file' '$(DESTDIR)$(man8dir)/$$inst'"; \ + $(INSTALL_DATA) "$$file" "$(DESTDIR)$(man8dir)/$$inst" || exit $$?; \ + fi; \ + done; \ + for i in $$list; do echo "$$i"; done | $(am__base_list) | \ + while read files; do \ + test -z "$$files" || { \ + echo " $(INSTALL_DATA) $$files '$(DESTDIR)$(man8dir)'"; \ + $(INSTALL_DATA) $$files "$(DESTDIR)$(man8dir)" || exit $$?; }; \ + done; } + +uninstall-man8: + @$(NORMAL_UNINSTALL) + @list='$(man8_MANS)'; test -n "$(man8dir)" || exit 0; \ + files=`{ for i in $$list; do echo "$$i"; done; \ + } | sed -e 's,.*/,,;h;s,.*\.,,;s,^[^8][0-9a-z]*$$,8,;x' \ + -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,'`; \ + dir='$(DESTDIR)$(man8dir)'; $(am__uninstall_files_from_dir) + +ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) + list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ + unique=`for i in $$list; do \ + if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ + done | \ + $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ + END { if (nonempty) { for (i in files) print i; }; }'`; \ + mkid -fID $$unique +tags: TAGS + +TAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ + $(TAGS_FILES) $(LISP) + set x; \ + here=`pwd`; \ + list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ + unique=`for i in $$list; do \ + if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ + done | \ + $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ + END { if (nonempty) { for (i in files) print i; }; }'`; \ + shift; \ + if test -z "$(ETAGS_ARGS)$$*$$unique"; then :; else \ + test -n "$$unique" || unique=$$empty_fix; \ + if test $$# -gt 0; then \ + $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ + "$$@" $$unique; \ + else \ + $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ + $$unique; \ + fi; \ + fi +ctags: CTAGS +CTAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ + $(TAGS_FILES) $(LISP) + list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ + unique=`for i in $$list; do \ + if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ + done | \ + $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ + END { if (nonempty) { for (i in files) print i; }; }'`; \ + test -z "$(CTAGS_ARGS)$$unique" \ + || $(CTAGS) $(CTAGSFLAGS) $(AM_CTAGSFLAGS) $(CTAGS_ARGS) \ + $$unique + +GTAGS: + here=`$(am__cd) $(top_builddir) && pwd` \ + && $(am__cd) $(top_srcdir) \ + && gtags -i $(GTAGS_ARGS) "$$here" + +cscopelist: $(HEADERS) $(SOURCES) $(LISP) + list='$(SOURCES) $(HEADERS) $(LISP)'; \ + case "$(srcdir)" in \ + [\\/]* | ?:[\\/]*) sdir="$(srcdir)" ;; \ + *) sdir=$(subdir)/$(srcdir) ;; \ + esac; \ + for i in $$list; do \ + if test -f "$$i"; then \ + echo "$(subdir)/$$i"; \ + else \ + echo "$$sdir/$$i"; \ + fi; \ + done >> $(top_builddir)/cscope.files + +distclean-tags: + -rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags + +distdir: $(DISTFILES) + @list='$(MANS)'; if test -n "$$list"; then \ + list=`for p in $$list; do \ + if test -f $$p; then d=; else d="$(srcdir)/"; fi; \ + if test -f "$$d$$p"; then echo "$$d$$p"; else :; fi; done`; \ + if test -n "$$list" && \ + grep 'ab help2man is required to generate this page' $$list >/dev/null; then \ + echo "error: found man pages containing the 'missing help2man' replacement text:" >&2; \ + grep -l 'ab help2man is required to generate this page' $$list | sed 's/^/ /' >&2; \ + echo " to fix them, install help2man, remove and regenerate the man pages;" >&2; \ + echo " typically 'make maintainer-clean' will remove them" >&2; \ + exit 1; \ + else :; fi; \ + else :; fi + @srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ + topsrcdirstrip=`echo "$(top_srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ + list='$(DISTFILES)'; \ + dist_files=`for file in $$list; do echo $$file; done | \ + sed -e "s|^$$srcdirstrip/||;t" \ + -e "s|^$$topsrcdirstrip/|$(top_builddir)/|;t"`; \ + case $$dist_files in \ + */*) $(MKDIR_P) `echo "$$dist_files" | \ + sed '/\//!d;s|^|$(distdir)/|;s,/[^/]*$$,,' | \ + sort -u` ;; \ + esac; \ + for file in $$dist_files; do \ + if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \ + if test -d $$d/$$file; then \ + dir=`echo "/$$file" | sed -e 's,/[^/]*$$,,'`; \ + if test -d "$(distdir)/$$file"; then \ + find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \ + fi; \ + if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \ + cp -fpR $(srcdir)/$$file "$(distdir)$$dir" || exit 1; \ + find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \ + fi; \ + cp -fpR $$d/$$file "$(distdir)$$dir" || exit 1; \ + else \ + test -f "$(distdir)/$$file" \ + || cp -p $$d/$$file "$(distdir)/$$file" \ + || exit 1; \ + fi; \ + done +check-am: all-am +check: check-am +all-am: Makefile $(PROGRAMS) $(MANS) +installdirs: + for dir in "$(DESTDIR)$(sbindir)" "$(DESTDIR)$(man5dir)" "$(DESTDIR)$(man8dir)"; do \ + test -z "$$dir" || $(MKDIR_P) "$$dir"; \ + done +install: install-am +install-exec: install-exec-am +install-data: install-data-am +uninstall: uninstall-am + +install-am: all-am + @$(MAKE) $(AM_MAKEFLAGS) install-exec-am install-data-am + +installcheck: installcheck-am +install-strip: + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi +mostlyclean-generic: + +clean-generic: + +distclean-generic: + -test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES) + -test . = "$(srcdir)" || test -z "$(CONFIG_CLEAN_VPATH_FILES)" || rm -f $(CONFIG_CLEAN_VPATH_FILES) + +maintainer-clean-generic: + @echo "This command is intended for maintainers to use" + @echo "it deletes files that may require special tools to rebuild." + -rm -f parse.c + -rm -f parse.h + -rm -f token.c +clean: clean-am + +clean-am: clean-generic clean-libtool clean-sbinPROGRAMS \ + mostlyclean-am + +distclean: distclean-am + -rm -rf ./$(DEPDIR) + -rm -f Makefile +distclean-am: clean-am distclean-compile distclean-generic \ + distclean-tags + +dvi: dvi-am + +dvi-am: + +html: html-am + +html-am: + +info: info-am + +info-am: + +install-data-am: install-man + +install-dvi: install-dvi-am + +install-dvi-am: + +install-exec-am: install-sbinPROGRAMS + +install-html: install-html-am + +install-html-am: + +install-info: install-info-am + +install-info-am: + +install-man: install-man5 install-man8 + +install-pdf: install-pdf-am + +install-pdf-am: + +install-ps: install-ps-am + +install-ps-am: + +installcheck-am: + +maintainer-clean: maintainer-clean-am + -rm -rf ./$(DEPDIR) + -rm -f Makefile +maintainer-clean-am: distclean-am maintainer-clean-generic + +mostlyclean: mostlyclean-am + +mostlyclean-am: mostlyclean-compile mostlyclean-generic \ + mostlyclean-libtool + +pdf: pdf-am + +pdf-am: + +ps: ps-am + +ps-am: + +uninstall-am: uninstall-man uninstall-sbinPROGRAMS + +uninstall-man: uninstall-man5 uninstall-man8 + +.MAKE: install-am install-strip + +.PHONY: CTAGS GTAGS all all-am check check-am clean clean-generic \ + clean-libtool clean-sbinPROGRAMS cscopelist ctags distclean \ + distclean-compile distclean-generic distclean-libtool \ + distclean-tags distdir dvi dvi-am html html-am info info-am \ + install install-am install-data install-data-am install-dvi \ + install-dvi-am install-exec install-exec-am install-html \ + install-html-am install-info install-info-am install-man \ + install-man5 install-man8 install-pdf install-pdf-am \ + install-ps install-ps-am install-sbinPROGRAMS install-strip \ + installcheck installcheck-am installdirs maintainer-clean \ + maintainer-clean-generic mostlyclean mostlyclean-compile \ + mostlyclean-generic mostlyclean-libtool pdf pdf-am ps ps-am \ + tags uninstall uninstall-am uninstall-man uninstall-man5 \ + uninstall-man8 uninstall-sbinPROGRAMS + + +# Tell versions [3.59,3.63) of GNU make to not export all variables. +# Otherwise a system limit (for SysV at least) may be exceeded. +.NOEXPORT: diff --git a/contrib/openbsm/bin/auditdistd/auditdistd.8 b/contrib/openbsm/bin/auditdistd/auditdistd.8 new file mode 100644 index 0000000..299cde4 --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/auditdistd.8 @@ -0,0 +1,106 @@ +.\" Copyright (c) 2012 The FreeBSD Foundation +.\" All rights reserved. +.\" +.\" This documentation was written by Pawel Jakub Dawidek under sponsorship +.\" from the FreeBSD Foundation. +.\" +.\" 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 AUTHORS 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 AUTHORS 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. +.\" +.\" $FreeBSD$ +.\" +.Dd March 5, 2012 +.Dt AUDITDISTD 8 +.Os +.Sh NAME +.Nm auditdistd +.Nd "Audit trail files distribution daemon" +.Sh SYNOPSIS +.Nm +.Op Fl dFhl +.Op Fl c Ar config +.Op Fl P Ar pidfile +.Sh DESCRIPTION +The +.Nm +daemon is responsible for distributing audit trail files over TCP/IP network in +a secure and reliable way. +.Pp +The +.Nm +daemon can be started with the following command line arguments: +.Bl -tag -width ".Fl P Ar pidfile" +.It Fl c Ar config +Specify alternative location of the configuration file. +The default location is +.Pa /etc/security/auditdistd.conf . +Note: the configuration file may contain passwords. +Care should be taken to configure proper permissions on this file +.Li ( eg. 0600 ) . +.It Fl d +Print or log debugging information. +This option can be specified multiple times to raise the verbosity +level. +.It Fl F +Start the +.Nm +daemon in the foreground. +By default +.Nm +starts in the background. +.It Fl h +Print the +.Nm +usage message. +.It Fl l +Start in a launchd-friendly mode, ie. do not use +.Xr daemon 3 . +.It Fl P Ar pidfile +Specify alternative location of a file where main process PID will be +stored. +The default location is +.Pa /var/run/auditdistd.pid . +.El +.Sh FILES +.Bl -tag -width ".Pa /etc/security/auditdistd.conf" -compact +.It Pa /etc/security/auditdistd.conf +The configuration file for +.Nm . +.It Pa /var/run/auditdistd.pid +The default location of the +.Nm +PID file. +.El +.Sh EXIT STATUS +Exit status is 0 on success, or one of the values described in +.Xr sysexits 3 +on failure. +.Sh SEE ALSO +.Xr sysexits 3 , +.Xr audit 4 , +.Xr auditdistd.conf 5 , +.Xr auditd 8 +.Sh AUTHORS +The +.Nm +was developed by +.An Pawel Jakub Dawidek Aq pawel@dawidek.net +under sponsorship of the FreeBSD Foundation. diff --git a/contrib/openbsm/bin/auditdistd/auditdistd.c b/contrib/openbsm/bin/auditdistd/auditdistd.c new file mode 100644 index 0000000..436531d --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/auditdistd.c @@ -0,0 +1,800 @@ +/*- + * Copyright (c) 2012 The FreeBSD Foundation + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/auditdistd.c#3 $ + */ + +#include <config/config.h> + +#include <sys/param.h> +#if defined(HAVE_SYS_ENDIAN_H) && defined(HAVE_BSWAP) +#include <sys/endian.h> +#else /* !HAVE_SYS_ENDIAN_H || !HAVE_BSWAP */ +#ifdef HAVE_MACHINE_ENDIAN_H +#include <machine/endian.h> +#else /* !HAVE_MACHINE_ENDIAN_H */ +#ifdef HAVE_ENDIAN_H +#include <endian.h> +#else /* !HAVE_ENDIAN_H */ +#error "No supported endian.h" +#endif /* !HAVE_ENDIAN_H */ +#endif /* !HAVE_MACHINE_ENDIAN_H */ +#include <compat/endian.h> +#endif /* !HAVE_SYS_ENDIAN_H || !HAVE_BSWAP */ +#include <sys/queue.h> +#include <sys/wait.h> + +#include <ctype.h> +#include <err.h> +#include <errno.h> +#include <fcntl.h> +#ifdef HAVE_LIBUTIL_H +#include <libutil.h> +#endif +#include <signal.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <strings.h> +#include <unistd.h> + +#include <openssl/hmac.h> + +#ifndef HAVE_PIDFILE_OPEN +#include <compat/pidfile.h> +#endif +#ifndef HAVE_STRLCPY +#include <compat/strlcpy.h> +#endif +#ifndef HAVE_SIGTIMEDWAIT +#include "sigtimedwait.h" +#endif + +#include "auditdistd.h" +#include "pjdlog.h" +#include "proto.h" +#include "subr.h" +#include "synch.h" + +/* Path to configuration file. */ +const char *cfgpath = ADIST_CONFIG; +/* Auditdistd configuration. */ +static struct adist_config *adcfg; +/* Was SIGINT or SIGTERM signal received? */ +bool sigexit_received = false; +/* PID file handle. */ +struct pidfh *pfh; + +/* How often check for hooks running for too long. */ +#define SIGNALS_CHECK_INTERVAL 5 + +static void +usage(void) +{ + + errx(EX_USAGE, "[-dFhl] [-c config] [-P pidfile]"); +} + +void +descriptors_cleanup(struct adist_host *adhost) +{ + struct adist_host *adh; + struct adist_listen *lst; + + TAILQ_FOREACH(adh, &adcfg->adc_hosts, adh_next) { + if (adh == adhost) + continue; + if (adh->adh_remote != NULL) { + proto_close(adh->adh_remote); + adh->adh_remote = NULL; + } + } + TAILQ_FOREACH(lst, &adcfg->adc_listen, adl_next) { + if (lst->adl_conn != NULL) + proto_close(lst->adl_conn); + } + (void)pidfile_close(pfh); + pjdlog_fini(); +} + +static void +child_cleanup(struct adist_host *adhost) +{ + + if (adhost->adh_conn != NULL) { + PJDLOG_ASSERT(adhost->adh_role == ADIST_ROLE_SENDER); + proto_close(adhost->adh_conn); + adhost->adh_conn = NULL; + } + adhost->adh_worker_pid = 0; +} + +static void +child_exit_log(const char *type, unsigned int pid, int status) +{ + + if (WIFEXITED(status) && WEXITSTATUS(status) == 0) { + pjdlog_debug(1, "%s process exited gracefully (pid=%u).", + type, pid); + } else if (WIFSIGNALED(status)) { + pjdlog_error("%s process killed (pid=%u, signal=%d).", + type, pid, WTERMSIG(status)); + } else { + pjdlog_error("%s process exited ungracefully (pid=%u, exitcode=%d).", + type, pid, WIFEXITED(status) ? WEXITSTATUS(status) : -1); + } +} + +static void +child_exit(void) +{ + struct adist_host *adhost; + bool restart; + int status; + pid_t pid; + + restart = false; + while ((pid = wait3(&status, WNOHANG, NULL)) > 0) { + /* Find host related to the process that just exited. */ + TAILQ_FOREACH(adhost, &adcfg->adc_hosts, adh_next) { + if (pid == adhost->adh_worker_pid) + break; + } + if (adhost == NULL) { + child_exit_log("Sandbox", pid, status); + } else { + if (adhost->adh_role == ADIST_ROLE_SENDER) + restart = true; + pjdlog_prefix_set("[%s] (%s) ", adhost->adh_name, + role2str(adhost->adh_role)); + child_exit_log("Worker", pid, status); + child_cleanup(adhost); + pjdlog_prefix_set("%s", ""); + } + } + if (!restart) + return; + /* We have some sender processes to restart. */ + sleep(1); + TAILQ_FOREACH(adhost, &adcfg->adc_hosts, adh_next) { + if (adhost->adh_role != ADIST_ROLE_SENDER) + continue; + if (adhost->adh_worker_pid != 0) + continue; + pjdlog_prefix_set("[%s] (%s) ", adhost->adh_name, + role2str(adhost->adh_role)); + pjdlog_info("Restarting sender process."); + adist_sender(adcfg, adhost); + pjdlog_prefix_set("%s", ""); + } +} + +/* TODO */ +static void +adist_reload(void) +{ + + pjdlog_info("Reloading configuration is not yet implemented."); +} + +static void +terminate_workers(void) +{ + struct adist_host *adhost; + + pjdlog_info("Termination signal received, exiting."); + TAILQ_FOREACH(adhost, &adcfg->adc_hosts, adh_next) { + if (adhost->adh_worker_pid == 0) + continue; + pjdlog_info("Terminating worker process (adhost=%s, role=%s, pid=%u).", + adhost->adh_name, role2str(adhost->adh_role), + adhost->adh_worker_pid); + if (kill(adhost->adh_worker_pid, SIGTERM) == 0) + continue; + pjdlog_errno(LOG_WARNING, + "Unable to send signal to worker process (adhost=%s, role=%s, pid=%u).", + adhost->adh_name, role2str(adhost->adh_role), + adhost->adh_worker_pid); + } +} + +static void +listen_accept(struct adist_listen *lst) +{ + unsigned char rnd[32], hash[32], resp[32]; + struct adist_host *adhost; + struct proto_conn *conn; + char adname[ADIST_HOSTSIZE]; + char laddr[256], raddr[256]; + char welcome[8]; + int status, version; + pid_t pid; + + proto_local_address(lst->adl_conn, laddr, sizeof(laddr)); + pjdlog_debug(1, "Accepting connection to %s.", laddr); + + if (proto_accept(lst->adl_conn, &conn) == -1) { + pjdlog_errno(LOG_ERR, "Unable to accept connection to %s", + laddr); + return; + } + + proto_local_address(conn, laddr, sizeof(laddr)); + proto_remote_address(conn, raddr, sizeof(raddr)); + pjdlog_info("Connection from %s to %s.", raddr, laddr); + + /* Error in setting timeout is not critical, but why should it fail? */ + if (proto_timeout(conn, ADIST_TIMEOUT) < 0) + pjdlog_errno(LOG_WARNING, "Unable to set connection timeout"); + + /* + * Before receiving any data see if remote host is known. + */ + TAILQ_FOREACH(adhost, &adcfg->adc_hosts, adh_next) { + if (adhost->adh_role != ADIST_ROLE_RECEIVER) + continue; + if (!proto_address_match(conn, adhost->adh_remoteaddr)) + continue; + break; + } + if (adhost == NULL) { + pjdlog_error("Client %s is not known.", raddr); + goto close; + } + /* Ok, remote host is known. */ + + /* Exchange welcome message, which include version number. */ + bzero(welcome, sizeof(welcome)); + if (proto_recv(conn, welcome, sizeof(welcome)) == -1) { + pjdlog_errno(LOG_WARNING, + "Unable to receive welcome message from %s", + adhost->adh_remoteaddr); + goto close; + } + if (strncmp(welcome, "ADIST", 5) != 0 || !isdigit(welcome[5]) || + !isdigit(welcome[6]) || welcome[7] != '\0') { + pjdlog_warning("Invalid welcome message from %s.", + adhost->adh_remoteaddr); + goto close; + } + + version = MIN(ADIST_VERSION, atoi(welcome + 5)); + + (void)snprintf(welcome, sizeof(welcome), "ADIST%02d", version); + if (proto_send(conn, welcome, sizeof(welcome)) == -1) { + pjdlog_errno(LOG_WARNING, + "Unable to send welcome message to %s", + adhost->adh_remoteaddr); + goto close; + } + + if (proto_recv(conn, adname, sizeof(adhost->adh_name)) < 0) { + pjdlog_errno(LOG_ERR, "Unable to receive hostname from %s", + raddr); + goto close; + } + + /* Find host now that we have hostname. */ + TAILQ_FOREACH(adhost, &adcfg->adc_hosts, adh_next) { + if (adhost->adh_role != ADIST_ROLE_RECEIVER) + continue; + if (!proto_address_match(conn, adhost->adh_remoteaddr)) + continue; + if (strcmp(adhost->adh_name, adname) != 0) + continue; + break; + } + if (adhost == NULL) { + pjdlog_error("No configuration for host %s from address %s.", + adname, raddr); + goto close; + } + + adhost->adh_version = version; + pjdlog_debug(1, "Version %d negotiated with %s.", adhost->adh_version, + adhost->adh_remoteaddr); + + /* Now that we know host name setup log prefix. */ + pjdlog_prefix_set("[%s] (%s) ", adhost->adh_name, + role2str(adhost->adh_role)); + + if (adist_random(rnd, sizeof(rnd)) == -1) { + pjdlog_error("Unable to generate challenge."); + goto close; + } + pjdlog_debug(1, "Challenge generated."); + + if (proto_send(conn, rnd, sizeof(rnd)) == -1) { + pjdlog_errno(LOG_ERR, "Unable to send challenge to %s", + adhost->adh_remoteaddr); + goto close; + } + pjdlog_debug(1, "Challenge sent."); + + if (proto_recv(conn, resp, sizeof(resp)) == -1) { + pjdlog_errno(LOG_ERR, "Unable to receive response from %s", + adhost->adh_remoteaddr); + goto close; + } + pjdlog_debug(1, "Response received."); + + if (HMAC(EVP_sha256(), adhost->adh_password, + (int)strlen(adhost->adh_password), rnd, (int)sizeof(rnd), hash, + NULL) == NULL) { + pjdlog_error("Unable to generate hash."); + goto close; + } + pjdlog_debug(1, "Hash generated."); + + if (memcmp(resp, hash, sizeof(hash)) != 0) { + pjdlog_error("Invalid response from %s (wrong password?).", + adhost->adh_remoteaddr); + goto close; + } + pjdlog_info("Sender authenticated."); + + if (proto_recv(conn, rnd, sizeof(rnd)) == -1) { + pjdlog_errno(LOG_ERR, "Unable to receive challenge from %s", + adhost->adh_remoteaddr); + goto close; + } + pjdlog_debug(1, "Challenge received."); + + if (HMAC(EVP_sha256(), adhost->adh_password, + (int)strlen(adhost->adh_password), rnd, (int)sizeof(rnd), hash, + NULL) == NULL) { + pjdlog_error("Unable to generate response."); + goto close; + } + pjdlog_debug(1, "Response generated."); + + if (proto_send(conn, hash, sizeof(hash)) == -1) { + pjdlog_errno(LOG_ERR, "Unable to send response to %s", + adhost->adh_remoteaddr); + goto close; + } + pjdlog_debug(1, "Response sent."); + + if (adhost->adh_worker_pid != 0) { + pjdlog_debug(1, + "Receiver process exists (pid=%u), stopping it.", + (unsigned int)adhost->adh_worker_pid); + /* Stop child process. */ + if (kill(adhost->adh_worker_pid, SIGINT) == -1) { + pjdlog_errno(LOG_ERR, + "Unable to stop worker process (pid=%u)", + (unsigned int)adhost->adh_worker_pid); + /* + * Other than logging the problem we + * ignore it - nothing smart to do. + */ + } + /* Wait for it to exit. */ + else if ((pid = waitpid(adhost->adh_worker_pid, + &status, 0)) != adhost->adh_worker_pid) { + /* We can only log the problem. */ + pjdlog_errno(LOG_ERR, + "Waiting for worker process (pid=%u) failed", + (unsigned int)adhost->adh_worker_pid); + } else { + child_exit_log("Worker", adhost->adh_worker_pid, + status); + } + child_cleanup(adhost); + } + + adhost->adh_remote = conn; + adist_receiver(adcfg, adhost); + + pjdlog_prefix_set("%s", ""); + return; +close: + proto_close(conn); + pjdlog_prefix_set("%s", ""); +} + +static void +connection_migrate(struct adist_host *adhost) +{ + struct proto_conn *conn; + int16_t val = 0; + + pjdlog_prefix_set("[%s] (%s) ", adhost->adh_name, + role2str(adhost->adh_role)); + + PJDLOG_ASSERT(adhost->adh_role == ADIST_ROLE_SENDER); + + if (proto_recv(adhost->adh_conn, &val, sizeof(val)) < 0) { + pjdlog_errno(LOG_WARNING, + "Unable to receive connection command"); + return; + } + if (proto_set("tls:fingerprint", adhost->adh_fingerprint) == -1) { + val = errno; + pjdlog_errno(LOG_WARNING, "Unable to set fingerprint"); + goto out; + } + if (proto_connect(adhost->adh_localaddr[0] != '\0' ? + adhost->adh_localaddr : NULL, + adhost->adh_remoteaddr, -1, &conn) < 0) { + val = errno; + pjdlog_errno(LOG_WARNING, "Unable to connect to %s", + adhost->adh_remoteaddr); + goto out; + } + val = 0; +out: + if (proto_send(adhost->adh_conn, &val, sizeof(val)) < 0) { + pjdlog_errno(LOG_WARNING, + "Unable to send reply to connection request"); + } + if (val == 0 && proto_connection_send(adhost->adh_conn, conn) < 0) + pjdlog_errno(LOG_WARNING, "Unable to send connection"); + + pjdlog_prefix_set("%s", ""); +} + +static void +check_signals(void) +{ + struct timespec sigtimeout; + sigset_t mask; + int signo; + + sigtimeout.tv_sec = 0; + sigtimeout.tv_nsec = 0; + + PJDLOG_VERIFY(sigemptyset(&mask) == 0); + PJDLOG_VERIFY(sigaddset(&mask, SIGHUP) == 0); + PJDLOG_VERIFY(sigaddset(&mask, SIGINT) == 0); + PJDLOG_VERIFY(sigaddset(&mask, SIGTERM) == 0); + PJDLOG_VERIFY(sigaddset(&mask, SIGCHLD) == 0); + + while ((signo = sigtimedwait(&mask, NULL, &sigtimeout)) != -1) { + switch (signo) { + case SIGINT: + case SIGTERM: + sigexit_received = true; + terminate_workers(); + exit(EX_OK); + break; + case SIGCHLD: + child_exit(); + break; + case SIGHUP: + adist_reload(); + break; + default: + PJDLOG_ABORT("Unexpected signal (%d).", signo); + } + } +} + +static void +main_loop(void) +{ + struct adist_host *adhost; + struct adist_listen *lst; + struct timeval seltimeout; + int fd, maxfd, ret; + fd_set rfds; + + seltimeout.tv_sec = SIGNALS_CHECK_INTERVAL; + seltimeout.tv_usec = 0; + + pjdlog_info("Started successfully."); + + for (;;) { + check_signals(); + + /* Setup descriptors for select(2). */ + FD_ZERO(&rfds); + maxfd = -1; + TAILQ_FOREACH(lst, &adcfg->adc_listen, adl_next) { + if (lst->adl_conn == NULL) + continue; + fd = proto_descriptor(lst->adl_conn); + PJDLOG_ASSERT(fd >= 0); + FD_SET(fd, &rfds); + maxfd = fd > maxfd ? fd : maxfd; + } + TAILQ_FOREACH(adhost, &adcfg->adc_hosts, adh_next) { + if (adhost->adh_role == ADIST_ROLE_SENDER) { + /* Only sender workers asks for connections. */ + PJDLOG_ASSERT(adhost->adh_conn != NULL); + fd = proto_descriptor(adhost->adh_conn); + PJDLOG_ASSERT(fd >= 0); + FD_SET(fd, &rfds); + maxfd = fd > maxfd ? fd : maxfd; + } else { + PJDLOG_ASSERT(adhost->adh_conn == NULL); + } + } + + PJDLOG_ASSERT(maxfd + 1 <= (int)FD_SETSIZE); + ret = select(maxfd + 1, &rfds, NULL, NULL, &seltimeout); + if (ret == 0) { + /* + * select(2) timed out, so there should be no + * descriptors to check. + */ + continue; + } else if (ret == -1) { + if (errno == EINTR) + continue; + KEEP_ERRNO((void)pidfile_remove(pfh)); + pjdlog_exit(EX_OSERR, "select() failed"); + } + PJDLOG_ASSERT(ret > 0); + + /* + * Check for signals before we do anything to update our + * info about terminated workers in the meantime. + */ + check_signals(); + + TAILQ_FOREACH(lst, &adcfg->adc_listen, adl_next) { + if (lst->adl_conn == NULL) + continue; + if (FD_ISSET(proto_descriptor(lst->adl_conn), &rfds)) + listen_accept(lst); + } + TAILQ_FOREACH(adhost, &adcfg->adc_hosts, adh_next) { + if (adhost->adh_role == ADIST_ROLE_SENDER) { + PJDLOG_ASSERT(adhost->adh_conn != NULL); + if (FD_ISSET(proto_descriptor(adhost->adh_conn), + &rfds)) { + connection_migrate(adhost); + } + } else { + PJDLOG_ASSERT(adhost->adh_conn == NULL); + } + } + } +} + +static void +adist_config_dump(struct adist_config *cfg) +{ + struct adist_host *adhost; + struct adist_listen *lst; + + pjdlog_debug(2, "Configuration:"); + pjdlog_debug(2, " Global:"); + pjdlog_debug(2, " pidfile: %s", cfg->adc_pidfile); + pjdlog_debug(2, " timeout: %d", cfg->adc_timeout); + if (TAILQ_EMPTY(&cfg->adc_listen)) { + pjdlog_debug(2, " Sender only, not listening."); + } else { + pjdlog_debug(2, " Listening on:"); + TAILQ_FOREACH(lst, &cfg->adc_listen, adl_next) { + pjdlog_debug(2, " listen: %s", lst->adl_addr); + pjdlog_debug(2, " conn: %p", lst->adl_conn); + } + } + pjdlog_debug(2, " Hosts:"); + TAILQ_FOREACH(adhost, &cfg->adc_hosts, adh_next) { + pjdlog_debug(2, " name: %s", adhost->adh_name); + pjdlog_debug(2, " role: %s", role2str(adhost->adh_role)); + pjdlog_debug(2, " version: %d", adhost->adh_version); + pjdlog_debug(2, " localaddr: %s", adhost->adh_localaddr); + pjdlog_debug(2, " remoteaddr: %s", adhost->adh_remoteaddr); + pjdlog_debug(2, " remote: %p", adhost->adh_remote); + pjdlog_debug(2, " directory: %s", adhost->adh_directory); + pjdlog_debug(2, " compression: %d", adhost->adh_compression); + pjdlog_debug(2, " checksum: %d", adhost->adh_checksum); + pjdlog_debug(2, " pid: %ld", (long)adhost->adh_worker_pid); + pjdlog_debug(2, " conn: %p", adhost->adh_conn); + } +} + +static void +dummy_sighandler(int sig __unused) +{ + /* Nothing to do. */ +} + +int +main(int argc, char *argv[]) +{ + struct adist_host *adhost; + struct adist_listen *lst; + const char *execpath, *pidfile; + bool foreground, launchd; + pid_t otherpid; + int debuglevel; + sigset_t mask; + + execpath = argv[0]; + if (execpath[0] != '/') { + errx(EX_USAGE, + "auditdistd requires execution with an absolute path."); + } + + /* + * We are executed from proto to create sandbox. + */ + if (argc > 1 && strcmp(argv[1], "proto") == 0) { + argc -= 2; + argv += 2; + if (proto_exec(argc, argv) == -1) + err(EX_USAGE, "Unable to execute proto"); + } + + foreground = false; + debuglevel = 0; + launchd = false; + pidfile = NULL; + + for (;;) { + int ch; + + ch = getopt(argc, argv, "c:dFhlP:"); + if (ch == -1) + break; + switch (ch) { + case 'c': + cfgpath = optarg; + break; + case 'd': + debuglevel++; + break; + case 'F': + foreground = true; + break; + case 'l': + launchd = true; + break; + case 'P': + pidfile = optarg; + break; + case 'h': + default: + usage(); + } + } + argc -= optind; + argv += optind; + + pjdlog_init(PJDLOG_MODE_STD); + pjdlog_debug_set(debuglevel); + + if (proto_set("execpath", execpath) == -1) + pjdlog_exit(EX_TEMPFAIL, "Unable to set executable name"); + if (proto_set("user", ADIST_USER) == -1) + pjdlog_exit(EX_TEMPFAIL, "Unable to set proto user"); + if (proto_set("tcp:port", ADIST_TCP_PORT) == -1) + pjdlog_exit(EX_TEMPFAIL, "Unable to set default TCP port"); + + /* + * When path to the configuration file is relative, obtain full path, + * so we can always find the file, even after daemonizing and changing + * working directory to /. + */ + if (cfgpath[0] != '/') { + const char *newcfgpath; + + newcfgpath = realpath(cfgpath, NULL); + if (newcfgpath == NULL) { + pjdlog_exit(EX_CONFIG, + "Unable to obtain full path of %s", cfgpath); + } + cfgpath = newcfgpath; + } + + adcfg = yy_config_parse(cfgpath, true); + PJDLOG_ASSERT(adcfg != NULL); + adist_config_dump(adcfg); + + if (proto_set("tls:certfile", adcfg->adc_certfile) == -1) + pjdlog_exit(EX_TEMPFAIL, "Unable to set certfile path"); + if (proto_set("tls:keyfile", adcfg->adc_keyfile) == -1) + pjdlog_exit(EX_TEMPFAIL, "Unable to set keyfile path"); + + if (pidfile != NULL) { + if (strlcpy(adcfg->adc_pidfile, pidfile, + sizeof(adcfg->adc_pidfile)) >= + sizeof(adcfg->adc_pidfile)) { + pjdlog_exitx(EX_CONFIG, "Pidfile path is too long."); + } + } + if (foreground && pidfile == NULL) { + pfh = NULL; + } else { + pfh = pidfile_open(adcfg->adc_pidfile, 0600, &otherpid); + if (pfh == NULL) { + if (errno == EEXIST) { + pjdlog_exitx(EX_TEMPFAIL, + "Another auditdistd is already running, pid: %jd.", + (intmax_t)otherpid); + } + /* + * If we cannot create pidfile from other reasons, + * only warn. + */ + pjdlog_errno(LOG_WARNING, + "Unable to open or create pidfile %s", + adcfg->adc_pidfile); + } + } + + /* + * Restore default actions for interesting signals in case parent + * process (like init(8)) decided to ignore some of them (like SIGHUP). + */ + PJDLOG_VERIFY(signal(SIGHUP, SIG_DFL) != SIG_ERR); + PJDLOG_VERIFY(signal(SIGINT, SIG_DFL) != SIG_ERR); + PJDLOG_VERIFY(signal(SIGTERM, SIG_DFL) != SIG_ERR); + /* + * Because SIGCHLD is ignored by default, setup dummy handler for it, + * so we can mask it. + */ + PJDLOG_VERIFY(signal(SIGCHLD, dummy_sighandler) != SIG_ERR); + + PJDLOG_VERIFY(sigemptyset(&mask) == 0); + PJDLOG_VERIFY(sigaddset(&mask, SIGHUP) == 0); + PJDLOG_VERIFY(sigaddset(&mask, SIGINT) == 0); + PJDLOG_VERIFY(sigaddset(&mask, SIGTERM) == 0); + PJDLOG_VERIFY(sigaddset(&mask, SIGCHLD) == 0); + PJDLOG_VERIFY(sigprocmask(SIG_SETMASK, &mask, NULL) == 0); + + /* Listen for remote connections. */ + TAILQ_FOREACH(lst, &adcfg->adc_listen, adl_next) { + if (proto_server(lst->adl_addr, &lst->adl_conn) == -1) { + KEEP_ERRNO((void)pidfile_remove(pfh)); + pjdlog_exit(EX_OSERR, "Unable to listen on address %s", + lst->adl_addr); + } + } + + if (!foreground) { + if (!launchd && daemon(0, 0) == -1) { + KEEP_ERRNO((void)pidfile_remove(pfh)); + pjdlog_exit(EX_OSERR, "Unable to daemonize"); + } + + /* Start logging to syslog. */ + pjdlog_mode_set(PJDLOG_MODE_SYSLOG); + } + if (pfh != NULL) { + /* Write PID to a file. */ + if (pidfile_write(pfh) < 0) { + pjdlog_errno(LOG_WARNING, + "Unable to write PID to a file"); + } + } + + TAILQ_FOREACH(adhost, &adcfg->adc_hosts, adh_next) { + if (adhost->adh_role == ADIST_ROLE_SENDER) + adist_sender(adcfg, adhost); + } + + main_loop(); + + exit(0); +} diff --git a/contrib/openbsm/bin/auditdistd/auditdistd.conf.5 b/contrib/openbsm/bin/auditdistd/auditdistd.conf.5 new file mode 100644 index 0000000..46356df --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/auditdistd.conf.5 @@ -0,0 +1,361 @@ +.\" Copyright (c) 2012 The FreeBSD Foundation +.\" All rights reserved. +.\" +.\" This documentation was written by Pawel Jakub Dawidek under sponsorship +.\" from the FreeBSD Foundation. +.\" +.\" 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 AUTHORS 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 AUTHORS 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. +.\" +.\" $FreeBSD$ +.\" +.Dd March 22, 2011 +.Dt AUDITDISTD.CONF 5 +.Os +.Sh NAME +.Nm auditdistd.conf +.Nd configuration file for the +.Xr auditdistd 8 +daemon. +.Sh DESCRIPTION +Note: the configuration file may contain passwords. +Care should be taken to configure proper permissions on this file +.Li ( eg. 0600 ) . +.Pp +Every line starting with # is treated as comment and ignored. +.Sh CONFIGURATION FILE SYNTAX +General syntax of the +.Nm +file is following: +.Bd -literal -offset +## Global section. + +# Our name. +# The default is first part of the hostname. +name "<name>" + +# Connection timeout. +# The default is 5. +timeout <seconds> + +# Path to pidfile. +# The default is "/var/run/auditdistd.pid". +pidfile "<path>" + +sender { + ## Sender section. + + # Source address for connections. + # Optional. + source "<addr>" + + # Directory with audit trail files managed by auditdistd. + # The default is /var/audit/dist. + directory "<dir>" +.\" +.\" # Checksum algorithm for data send over the wire. +.\" # The default is none. +.\" checksum "<algorithm>" +.\" +.\" # Compression algorithm for data send over the wire. +.\" # The default is none. +.\" compression "<algorithm>" + + # Configuration for the target system we want to send audit trail + # files to. + host "<name>" { + # Source address for connections. + # Optional. + source "<addr>" + + # Address of auditdistd receiver. + # No default. Obligatory. + remote "<addr>" + + # Directory with audit trail files managed by auditdistd. + # The default is /var/audit/dist. + directory "<dir>" + + # Fingerprint of the receiver's public key when using TLS + # for connection. + # Example fingerprint: + # SHA256=8F:0A:FC:8A:3D:09:80:AF:D9:AA:38:CC:8A:86:53:E6:8F:B6:1C:55:30:14:D7:F9:AA:8B:3E:73:CD:F5:76:2B + fingerprint "<algorithm=hash>" + + # Password used to authenticate in front of the receiver. + password "<password>" +.\" +.\" # Checksum algorithm for data send over the wire. +.\" # The default is none. +.\" checksum "<algorithm>" +.\" +.\" # Compression algorithm for data send over the wire. +.\" # The default is none. +.\" compression "<algorithm>" + } + + # Currently local audit trail files can be send only to one remote + # auditdistd receiver, but this can change in the future. +} + +receiver { + ## Receiver section. + + # Address to listen on. Multiple listen addresses might be specified. + # The defaults are "tcp4://0.0.0.0:7878" and "tcp6://[::]:7878". + listen "<addr>" + + # Base directory. + # If directory in host section is no absolute, it will be concatenated + # with this base directory. + # The default is "/var/audit/remote". + directory "<basedir>" + + # Path to receiver's certificate file. + # The default is "/etc/security/auditdistd.cert.pem". + certfile "<path>" + + # Path to receiver's private key file. + # The default is "/etc/security/auditdistd.key.pem". + keyfile "<path>" + + # Configuration for a source system we want to receive audit trail + # files from. + host "<name>" { + # Sender address. + # No default. Obligatory. + remote "<addr>" + + # Directory where to store audit trail files received + # from system <name>. + # The default is "<basedir>/<name>". + directory "<dir>" + + # Password used by the sender to authenticate. + password "<password>" + } + + # Multiple hosts to receive from can be configured. +} +.Ed +.Pp +Most of the various available configuration parameters are optional. +If parameter is not defined in the particular section, it will be +inherited from the parent section if possible. +For example, if the +.Ic source +parameter is not defined in the +.Ic host +section, it will be inherited from the +.Ic sender +section. +In case the +.Ic global +section does not define the +.Ic source +parameter at all, the default value will be used. +.Sh CONFIGURATION FILE DESCRIPTION +The following statements are available: +.Bl -tag -width ".Ic xxxx" +.It Ic name Aq name +.Pp +This host's name. +It is send to the receiver, so it can properly recognize us if there are +more than one sender coming from the same IP address. +.It Ic timeout Aq seconds +.Pp +Connection timeout in seconds. +The default value is +.Va 5 . +.It Ic pidfile Aq path +.Pp +File in which to store the process ID of the main +.Xr auditdistd 8 +process. +.Pp +The default value is +.Pa /var/run/auditdistd.pid . +.It Ic source Aq addr +.Pp +Local address to bind to before connecting to the remote +.Nm auditdistd +daemon. +Format is the same as for the +.Ic listen +statement. +.It Ic directory Aq path +.Pp +Directory where to look for audit trail files in case of sender mode or +directory where to store received audit trail files. +The provided path has to be an absolute path. +The only exception is when directory is provided in the +.Ic receiver +section, then path provided in the +.Ic host +subsections can be relative to the directory in the +.Ic receiver +section. +The default value is +.Pa /var/audit/dist +for the entire +.Ic sender +section, +.Pa /var/audit/remote +for the non-host +.Ic receiver +section and +.Pa /var/audit/remote/<name> +for the +.Ic host +subsections in the +.Ic receiver +section where +.Aq name +is host's name. +.\".It Ic checksum Aq algorithm +.\".Pp +.\"Checksum algorithm should be one of the following: +.\".Bl -tag -width ".Ic sha256" +.\".It Ic none +.\"No checksum will be calculated for the data being send over the network. +.\"This is the default setting. +.\".It Ic crc32 +.\"CRC32 checksum will be calculated. +.\".It Ic sha256 +.\"SHA256 checksum will be calculated. +.\".El +.\".It Ic compression Aq algorithm +.\".Pp +.\"Compression algorithm should be one of the following: +.\".Bl -tag -width ".Ic none" +.\".It Ic none +.\"Data send over the network will not be compressed. +.\"This is the default setting. +.\".It Ic lzf +.\"The +.\".Nm LZF +.\"algorithm by +.\".An Marc Alexander Lehmann +.\"will be used to compress the data send over the network. +.\".Nm LZF +.\"is very fast, general purpose compression algorithm. +.\".El +.It Ic remote Aq addr +.Pp +Address of the remote +.Nm auditdistd +daemon. +Format is the same as for the +.Ic listen +statement. +When operating in the +.Ic sender +mode this address will be used to connect to the +.Ic receiver . +When operating in the +.Ic receiver +mode only connections from this address will be accepted. +.It Ic listen Aq addr +.Pp +Address to listen on in form of: +.Bd -literal -offset indent +protocol://protocol-specific-address +.Ed +.Pp +Each of the following examples defines the same listen address: +.Bd -literal -offset indent +0.0.0.0 +0.0.0.0:7878 +tcp://0.0.0.0 +tcp://0.0.0.0:7878 +tcp4://0.0.0.0 +tcp4://0.0.0.0:7878 +.Ed +.Pp +Multiple listen addresses can be specified. +By default +.Nm auditdistd +listens on +.Pa tcp4://0.0.0.0:7878 +and +.Pa tcp6://[::]:7878 +if kernel supports IPv4 and IPv6 respectively. +.It Ic keyfile Aq path +.Pp +Path to a file that contains private key for TLS communication. +.It Ic certfile Aq path +.Pp +Path to a file that contains certificate for TLS communication. +.It Ic fingerprint Aq algo=hash +.Pp +Finger print of the receiver's public key. +Currently only SHA256 algorithm is supported. +Certificate public key's fingerprint ready to be pasted into auditdistd +configuration file can be obtained by running: +.Bd -literal -offset +# openssl x509 -in /etc/security/auditdistd.cert.pem -noout -fingerprint -sha256 | awk -F '[ =]' '{printf("%s=%s\\n", $1, $3)}' +.Ed +.It Ic password Aq password +.Pp +Password used to authenticate the sender in front of the receiver. +.El +.Sh FILES +.Bl -tag -width ".Pa /etc/security/auditdistd.conf" -compact +.It Pa /etc/security/auditdistd.conf +The default +.Nm auditdistd +configuration file. +.El +.Sh EXAMPLES +The example configuration files can look as follows. +.Pp +Web server: +.Bd -literal -offset indent +sender { + host backup { + remote 10.0.0.4 + } +} +.Ed +.Pp +Audit backup server: +.Bd -literal -offset indent +receiver { + host webserv { + remote 10.0.0.1 + } + host mailserv { + remote 10.0.0.2 + } + host dnsserv { + remote 10.0.0.3 + } +} +.Ed +.Sh SEE ALSO +.Xr audit 4 , +.Xr auditdistd 8 . +.Sh AUTHORS +The +.Nm +was written by +.An Pawel Jakub Dawidek Aq pawel@dawidek.net +under sponsorship of the FreeBSD Foundation. diff --git a/contrib/openbsm/bin/auditdistd/auditdistd.h b/contrib/openbsm/bin/auditdistd/auditdistd.h new file mode 100644 index 0000000..9ac2850 --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/auditdistd.h @@ -0,0 +1,276 @@ +/*- + * Copyright (c) 2012 The FreeBSD Foundation + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/auditdistd.h#2 $ + */ + +#ifndef _AUDITDISTD_H_ +#define _AUDITDISTD_H_ + +#include <sys/param.h> +#include <sys/queue.h> +#include <sys/socket.h> + +#include <arpa/inet.h> + +#include <netinet/in.h> + +#include <dirent.h> +#include <limits.h> +#include <pthread.h> +#include <stdbool.h> +#include <stdint.h> + +#include <compat/compat.h> + +#include "proto.h" + +/* + * Version history: + * 0 - initial version + */ +#define ADIST_VERSION 0 + +#define ADIST_ROLE_UNDEF 0 +#define ADIST_ROLE_SENDER 1 +#define ADIST_ROLE_RECEIVER 2 + +#define ADIST_USER "auditdistd" +#define ADIST_TIMEOUT 20 +#define ADIST_CONFIG "/etc/security/auditdistd.conf" +#define ADIST_TCP_PORT "7878" +#define ADIST_LISTEN_TLS_TCP4 "tls://0.0.0.0:" ADIST_TCP_PORT +#define ADIST_LISTEN_TLS_TCP6 "tls://[::]:" ADIST_TCP_PORT +#define ADIST_PIDFILE "/var/run/auditdistd.pid" +#define ADIST_DIRECTORY_SENDER "/var/audit/dist" +#define ADIST_DIRECTORY_RECEIVER "/var/audit/remote" +#define ADIST_CERTFILE "/etc/security/auditdistd.cert.pem" +#define ADIST_KEYFILE "/etc/security/auditdistd.key.pem" + +#define ADIST_ERROR_WRONG_ORDER 1 +#define ADIST_ERROR_INVALID_NAME 2 +#define ADIST_ERROR_OPEN_OLD 3 +#define ADIST_ERROR_CREATE 4 +#define ADIST_ERROR_OPEN 5 +#define ADIST_ERROR_READ 6 +#define ADIST_ERROR_WRITE 7 +#define ADIST_ERROR_RENAME 8 + +#define ADIST_ADDRSIZE 1024 +#define ADIST_HOSTSIZE 256 +#define ADIST_PATHSIZE 256 +#define ADIST_PASSWORDSIZE 128 +#define ADIST_FINGERPRINTSIZE 256 + +/* Number of seconds to sleep between reconnect retries or keepalive packets. */ +#define ADIST_KEEPALIVE 10 + +struct adist_listen { + /* Address to listen on. */ + char adl_addr[ADIST_ADDRSIZE]; + /* Protocol-specific data. */ + struct proto_conn *adl_conn; + TAILQ_ENTRY(adist_listen) adl_next; +}; + +struct adist_config { + /* Our name. */ + char adc_name[ADIST_HOSTSIZE]; + /* PID file path. */ + char adc_pidfile[PATH_MAX]; + /* Connection timeout. */ + int adc_timeout; + /* Path to receiver's certificate file. */ + char adc_certfile[PATH_MAX]; + /* Path to receiver's private key file. */ + char adc_keyfile[PATH_MAX]; + /* List of addresses to listen on. */ + TAILQ_HEAD(, adist_listen) adc_listen; + /* List of hosts. */ + TAILQ_HEAD(, adist_host) adc_hosts; +}; + +#define ADIST_COMPRESSION_NONE 0 +#define ADIST_COMPRESSION_LZF 1 + +#define ADIST_CHECKSUM_NONE 0 +#define ADIST_CHECKSUM_CRC32 1 +#define ADIST_CHECKSUM_SHA256 2 + +/* + * Structure that describes single host (either sender or receiver). + */ +struct adist_host { + /* Host name. */ + char adh_name[ADIST_HOSTSIZE]; + /* Host role: ADIST_ROLE_{SENDER,RECEIVER}. */ + int adh_role; + /* Protocol version negotiated. */ + int adh_version; + + /* Local address to bind to. */ + char adh_localaddr[ADIST_ADDRSIZE]; + /* Address of the remote component. */ + char adh_remoteaddr[ADIST_ADDRSIZE]; + /* Connection with remote host. */ + struct proto_conn *adh_remote; + /* Connection was reestablished, reset the state. */ + bool adh_reset; + + /* + * Directory from which audit trail files should be send in + * ADIST_ROLE_SENDER case or stored into in ADIST_ROLE_RECEIVER case. + */ + char adh_directory[PATH_MAX]; + /* Compression algorithm. Currently unused. */ + int adh_compression; + /* Checksum algorithm. Currently unused. */ + int adh_checksum; + + /* Sender's password. */ + char adh_password[ADIST_PASSWORDSIZE]; + /* Fingerprint of receiver's public key. */ + char adh_fingerprint[ADIST_FINGERPRINTSIZE]; + + /* PID of child worker process. 0 - no child. */ + pid_t adh_worker_pid; + /* Connection requests from sender to main. */ + struct proto_conn *adh_conn; + + /* Receiver-specific fields. */ + char adh_trail_name[ADIST_PATHSIZE]; + int adh_trail_fd; + int adh_trail_dirfd; + DIR *adh_trail_dirfp; + /* Sender-specific fields. */ + uint64_t adh_trail_offset; + + /* Next resource. */ + TAILQ_ENTRY(adist_host) adh_next; +}; + +#define ADIST_BYTEORDER_UNDEFINED 0 +#define ADIST_BYTEORDER_LITTLE_ENDIAN 1 +#define ADIST_BYTEORDER_BIG_ENDIAN 2 + +#if _BYTE_ORDER == _LITTLE_ENDIAN +#define ADIST_BYTEORDER ADIST_BYTEORDER_LITTLE_ENDIAN +#elif _BYTE_ORDER == _BIG_ENDIAN +#define ADIST_BYTEORDER ADIST_BYTEORDER_BIG_ENDIAN +#else +#error Unknown byte order. +#endif + +struct adpkt { + uint8_t adp_byteorder; +#define ADIST_CMD_UNDEFINED 0 +#define ADIST_CMD_OPEN 1 +#define ADIST_CMD_APPEND 2 +#define ADIST_CMD_CLOSE 3 +#define ADIST_CMD_KEEPALIVE 4 +#define ADIST_CMD_ERROR 5 + uint8_t adp_cmd; + uint64_t adp_seq; + uint32_t adp_datasize; + unsigned char adp_data[0]; +} __packed; + +struct adreq { + int adr_error; + TAILQ_ENTRY(adreq) adr_next; + struct adpkt adr_packet; +}; + +#define adr_byteorder adr_packet.adp_byteorder +#define adr_cmd adr_packet.adp_cmd +#define adr_seq adr_packet.adp_seq +#define adr_datasize adr_packet.adp_datasize +#define adr_data adr_packet.adp_data + +#define ADPKT_SIZE(adreq) (sizeof((adreq)->adr_packet) + (adreq)->adr_datasize) + +struct adrep { + uint8_t adrp_byteorder; + uint64_t adrp_seq; + uint16_t adrp_error; +} __packed; + +#define ADIST_QUEUE_SIZE 16 +#define ADIST_BUF_SIZE 65536 + +#define QUEUE_TAKE(adreq, list, timeout) do { \ + mtx_lock(list##_lock); \ + if ((timeout) == 0) { \ + while (((adreq) = TAILQ_FIRST(list)) == NULL) \ + cv_wait(list##_cond, list##_lock); \ + } else { \ + (adreq) = TAILQ_FIRST(list); \ + if ((adreq) == NULL) { \ + cv_timedwait(list##_cond, list##_lock, \ + (timeout)); \ + (adreq) = TAILQ_FIRST(list); \ + } \ + } \ + if ((adreq) != NULL) \ + TAILQ_REMOVE((list), (adreq), adr_next); \ + mtx_unlock(list##_lock); \ +} while (0) +#define QUEUE_INSERT(adreq, list) do { \ + bool _wakeup; \ + \ + mtx_lock(list##_lock); \ + _wakeup = TAILQ_EMPTY(list); \ + TAILQ_INSERT_TAIL((list), (adreq), adr_next); \ + mtx_unlock(list##_lock); \ + if (_wakeup) \ + cv_signal(list##_cond); \ +} while (0) +#define QUEUE_WAIT(list) do { \ + mtx_lock(list##_lock); \ + while (TAILQ_EMPTY(list)) \ + cv_wait(list##_cond, list##_lock); \ + mtx_unlock(list##_lock); \ +} while (0) + +extern const char *cfgpath; +extern bool sigexit_received; +extern struct pidfh *pfh; + +void descriptors_cleanup(struct adist_host *adhost); +void descriptors_assert(const struct adist_host *adhost, int pjdlogmode); + +void adist_sender(struct adist_config *config, struct adist_host *adhost); +void adist_receiver(struct adist_config *config, struct adist_host *adhost); + +struct adist_config *yy_config_parse(const char *config, bool exitonerror); +void yy_config_free(struct adist_config *config); + +void yyerror(const char *); +int yylex(void); + +#endif /* !_AUDITDISTD_H_ */ diff --git a/contrib/openbsm/bin/auditdistd/faccessat.h b/contrib/openbsm/bin/auditdistd/faccessat.h new file mode 100644 index 0000000..37d8b89 --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/faccessat.h @@ -0,0 +1,69 @@ +/*- + * Copyright (c) 2012 The FreeBSD Foundation + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/faccessat.h#1 $ + */ + +#ifndef _FACCESSAT_H_ +#define _FACCESSAT_H_ + +#include <unistd.h> + +#define AT_EACCESS 0x01 + +static int +faccessat(int fd, const char *path, int mode, int flag) +{ + int cfd, error, ret; + + if (flag == AT_EACCESS) { + errno = EINVAL; + return (-1); + } + + cfd = open(".", O_RDONLY | O_DIRECTORY); + if (cfd == -1) + return (-1); + + if (fchdir(fd) == -1) { + error = errno; + (void)close(cfd); + errno = error; + return (-1); + } + + ret = access(path, mode); + + error = errno; + (void)fchdir(cfd); + (void)close(cfd); + errno = error; + return (ret); +} + +#endif /* !_FACCESSAT_H_ */ diff --git a/contrib/openbsm/bin/auditdistd/fstatat.h b/contrib/openbsm/bin/auditdistd/fstatat.h new file mode 100644 index 0000000..a2716b9 --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/fstatat.h @@ -0,0 +1,69 @@ +/*- + * Copyright (c) 2012 The FreeBSD Foundation + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/fstatat.h#1 $ + */ + +#ifndef _FSTATAT_H_ +#define _FSTATAT_H_ + +#include <sys/stat.h> + +#include <unistd.h> + +#define AT_SYMLINK_NOFOLLOW 0x01 + +static int +fstatat(int fd, const char *path, struct stat *buf, int flag) +{ + int cfd, error, ret; + + cfd = open(".", O_RDONLY | O_DIRECTORY); + if (cfd == -1) + return (-1); + + if (fchdir(fd) == -1) { + error = errno; + (void)close(cfd); + errno = error; + return (-1); + } + + if (flag == AT_SYMLINK_NOFOLLOW) + ret = lstat(path, buf); + else + ret = stat(path, buf); + + error = errno; + (void)fchdir(cfd); + (void)close(cfd); + errno = error; + return (ret); +} + +#endif /* !_FSTATAT_H_ */ diff --git a/contrib/openbsm/bin/auditdistd/openat.h b/contrib/openbsm/bin/auditdistd/openat.h new file mode 100644 index 0000000..defb947 --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/openat.h @@ -0,0 +1,75 @@ +/*- + * Copyright (c) 2012 The FreeBSD Foundation + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/openat.h#1 $ + */ + +#ifndef _OPENAT_H_ +#define _OPENAT_H_ + +#include <fcntl.h> +#include <stdarg.h> +#include <unistd.h> + +static int +openat(int fd, const char *path, int flags, ...) +{ + int cfd, ffd, error; + + cfd = open(".", O_RDONLY | O_DIRECTORY); + if (cfd == -1) + return (-1); + + if (fchdir(fd) == -1) { + error = errno; + (void)close(cfd); + errno = error; + return (-1); + } + + if ((flags & O_CREAT) != 0) { + va_list ap; + int mode; + + va_start(ap, flags); + mode = va_arg(ap, int); + va_end(ap); + + ffd = open(path, flags, mode); + } else { + ffd = open(path, flags); + } + + error = errno; + (void)fchdir(cfd); + (void)close(cfd); + errno = error; + return (ffd); +} + +#endif /* !_OPENAT_H_ */ diff --git a/contrib/openbsm/bin/auditdistd/parse.y b/contrib/openbsm/bin/auditdistd/parse.y new file mode 100644 index 0000000..fbe1000 --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/parse.y @@ -0,0 +1,856 @@ +%{ +/*- + * Copyright (c) 2012 The FreeBSD Foundation + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/parse.y#5 $ + */ + +#include <config/config.h> + +#include <sys/types.h> +#include <sys/queue.h> +#include <sys/sysctl.h> + +#include <arpa/inet.h> + +#include <err.h> +#include <errno.h> +#include <stdio.h> +#include <string.h> +#include <sysexits.h> +#include <unistd.h> +#ifndef HAVE_STRLCPY +#include <compat/strlcpy.h> +#endif + +#include "auditdistd.h" +#include "pjdlog.h" + +extern int depth; +extern int lineno; + +extern FILE *yyin; +extern char *yytext; + +static struct adist_config *lconfig; +static struct adist_host *curhost; +#define SECTION_GLOBAL 0 +#define SECTION_SENDER 1 +#define SECTION_RECEIVER 2 +static int cursection; + +/* Sender section. */ +static char depth1_source[ADIST_ADDRSIZE]; +static int depth1_checksum; +static int depth1_compression; +/* Sender and receiver sections. */ +static char depth1_directory[PATH_MAX]; + +static bool adjust_directory(char *path); +static bool family_supported(int family); + +extern void yyrestart(FILE *); +%} + +%token CB +%token CERTFILE +%token DIRECTORY +%token FINGERPRINT +%token HOST +%token KEYFILE +%token LISTEN +%token NAME +%token OB +%token PASSWORD +%token PIDFILE +%token RECEIVER REMOTE +%token SENDER SOURCE +%token TIMEOUT + +/* +%type <num> checksum_type +%type <num> compression_type +*/ + +%union +{ + int num; + char *str; +} + +%token <num> NUM +%token <str> STR + +%% + +statements: + | + statements statement + ; + +statement: + name_statement + | + pidfile_statement + | + timeout_statement + | + sender_statement + | + receiver_statement + ; + +name_statement: NAME STR + { + PJDLOG_RASSERT(depth == 0, + "The name variable can only be specificed in the global section."); + + if (lconfig->adc_name[0] != '\0') { + pjdlog_error("The name variable is specified twice."); + free($2); + return (1); + } + if (strlcpy(lconfig->adc_name, $2, + sizeof(lconfig->adc_name)) >= + sizeof(lconfig->adc_name)) { + pjdlog_error("The name value is too long."); + free($2); + return (1); + } + free($2); + } + ; + +pidfile_statement: PIDFILE STR + { + PJDLOG_RASSERT(depth == 0, + "The pidfile variable can only be specificed in the global section."); + + if (lconfig->adc_pidfile[0] != '\0') { + pjdlog_error("The pidfile variable is specified twice."); + free($2); + return (1); + } + if (strcmp($2, "none") != 0 && $2[0] != '/') { + pjdlog_error("The pidfile variable must be set to absolute pathname or \"none\"."); + free($2); + return (1); + } + if (strlcpy(lconfig->adc_pidfile, $2, + sizeof(lconfig->adc_pidfile)) >= + sizeof(lconfig->adc_pidfile)) { + pjdlog_error("The pidfile value is too long."); + free($2); + return (1); + } + free($2); + } + ; + +timeout_statement: TIMEOUT NUM + { + PJDLOG_ASSERT(depth == 0); + + lconfig->adc_timeout = $2; + } + ; + +sender_statement: SENDER sender_start sender_entries CB + { + PJDLOG_ASSERT(depth == 0); + PJDLOG_ASSERT(cursection == SECTION_SENDER); + + /* Configure defaults. */ + if (depth1_checksum == -1) + depth1_checksum = ADIST_CHECKSUM_NONE; + if (depth1_compression == -1) + depth1_compression = ADIST_COMPRESSION_NONE; + if (depth1_directory[0] == '\0') { + (void)strlcpy(depth1_directory, ADIST_DIRECTORY_SENDER, + sizeof(depth1_directory)); + } + /* Empty depth1_source is ok. */ + TAILQ_FOREACH(curhost, &lconfig->adc_hosts, adh_next) { + if (curhost->adh_role != ADIST_ROLE_SENDER) + continue; + if (curhost->adh_checksum == -1) + curhost->adh_checksum = depth1_checksum; + if (curhost->adh_compression == -1) + curhost->adh_compression = depth1_compression; + if (curhost->adh_directory[0] == '\0') { + (void)strlcpy(curhost->adh_directory, + depth1_directory, + sizeof(curhost->adh_directory)); + } + if (curhost->adh_localaddr[0] == '\0') { + (void)strlcpy(curhost->adh_localaddr, + depth1_source, + sizeof(curhost->adh_localaddr)); + } + } + cursection = SECTION_GLOBAL; + } + ; + +sender_start: OB + { + PJDLOG_ASSERT(depth == 1); + PJDLOG_ASSERT(cursection == SECTION_GLOBAL); + + cursection = SECTION_SENDER; + depth1_checksum = -1; + depth1_compression = -1; + depth1_source[0] = '\0'; + depth1_directory[0] = '\0'; + +#ifndef HAVE_AUDIT_SYSCALLS + pjdlog_error("Sender functionality is not available."); + return (1); +#endif + } + ; + +sender_entries: + | + sender_entries sender_entry + ; + +sender_entry: + source_statement + | + directory_statement +/* + | + checksum_statement + | + compression_statement +*/ + | + sender_host_statement + ; + +receiver_statement: RECEIVER receiver_start receiver_entries CB + { + PJDLOG_ASSERT(depth == 0); + PJDLOG_ASSERT(cursection == SECTION_RECEIVER); + + /* + * If not listen addresses were specified, + * configure default ones. + */ + if (TAILQ_EMPTY(&lconfig->adc_listen)) { + struct adist_listen *lst; + + if (family_supported(AF_INET)) { + lst = calloc(1, sizeof(*lst)); + if (lst == NULL) { + pjdlog_error("Unable to allocate memory for listen address."); + return (1); + } + (void)strlcpy(lst->adl_addr, + ADIST_LISTEN_TLS_TCP4, + sizeof(lst->adl_addr)); + TAILQ_INSERT_TAIL(&lconfig->adc_listen, lst, adl_next); + } else { + pjdlog_debug(1, + "No IPv4 support in the kernel, not listening on IPv4 address."); + } + if (family_supported(AF_INET6)) { + lst = calloc(1, sizeof(*lst)); + if (lst == NULL) { + pjdlog_error("Unable to allocate memory for listen address."); + return (1); + } + (void)strlcpy(lst->adl_addr, + ADIST_LISTEN_TLS_TCP6, + sizeof(lst->adl_addr)); + TAILQ_INSERT_TAIL(&lconfig->adc_listen, lst, adl_next); + } else { + pjdlog_debug(1, + "No IPv6 support in the kernel, not listening on IPv6 address."); + } + if (TAILQ_EMPTY(&lconfig->adc_listen)) { + pjdlog_error("No address to listen on."); + return (1); + } + } + /* Configure defaults. */ + if (depth1_directory[0] == '\0') { + (void)strlcpy(depth1_directory, + ADIST_DIRECTORY_RECEIVER, + sizeof(depth1_directory)); + } + TAILQ_FOREACH(curhost, &lconfig->adc_hosts, adh_next) { + if (curhost->adh_role != ADIST_ROLE_RECEIVER) + continue; + if (curhost->adh_directory[0] == '\0') { + if (snprintf(curhost->adh_directory, + sizeof(curhost->adh_directory), "%s/%s", + depth1_directory, curhost->adh_name) >= + (ssize_t)sizeof(curhost->adh_directory)) { + pjdlog_error("Directory value is too long."); + return (1); + } + } + } + cursection = SECTION_GLOBAL; + } + ; + +receiver_start: OB + { + PJDLOG_ASSERT(depth == 1); + PJDLOG_ASSERT(cursection == SECTION_GLOBAL); + + cursection = SECTION_RECEIVER; + depth1_directory[0] = '\0'; + } + ; + +receiver_entries: + | + receiver_entries receiver_entry + ; + +receiver_entry: + listen_statement + | + directory_statement + | + certfile_statement + | + keyfile_statement + | + receiver_host_statement + ; + +/* +checksum_statement: CHECKSUM checksum_type + { + PJDLOG_ASSERT(cursection == SECTION_SENDER); + + switch (depth) { + case 1: + depth1_checksum = $2; + break; + case 2: + PJDLOG_ASSERT(curhost != NULL); + curhost->adh_checksum = $2; + break; + default: + PJDLOG_ABORT("checksum at wrong depth level"); + } + } + ; + +checksum_type: + NONE { $$ = ADIST_CHECKSUM_NONE; } + | + CRC32 { $$ = ADIST_CHECKSUM_CRC32; } + | + SHA256 { $$ = ADIST_CHECKSUM_SHA256; } + ; + +compression_statement: COMPRESSION compression_type + { + PJDLOG_ASSERT(cursection == SECTION_SENDER); + + switch (depth) { + case 1: + depth1_compression = $2; + break; + case 2: + PJDLOG_ASSERT(curhost != NULL); + curhost->adh_compression = $2; + break; + default: + PJDLOG_ABORT("compression at wrong depth level"); + } + } + ; + +compression_type: + NONE { $$ = ADIST_COMPRESSION_NONE; } + | + LZF { $$ = ADIST_COMPRESSION_LZF; } + ; +*/ + +directory_statement: DIRECTORY STR + { + PJDLOG_ASSERT(cursection == SECTION_SENDER || + cursection == SECTION_RECEIVER); + + switch (depth) { + case 1: + if (strlcpy(depth1_directory, $2, + sizeof(depth1_directory)) >= + sizeof(depth1_directory)) { + pjdlog_error("Directory value is too long."); + free($2); + return (1); + } + if (!adjust_directory(depth1_directory)) + return (1); + break; + case 2: + if (cursection == SECTION_SENDER || $2[0] == '/') { + if (strlcpy(curhost->adh_directory, $2, + sizeof(curhost->adh_directory)) >= + sizeof(curhost->adh_directory)) { + pjdlog_error("Directory value is too long."); + free($2); + return (1); + } + } else /* if (cursection == SECTION_RECEIVER) */ { + if (depth1_directory[0] == '\0') { + pjdlog_error("Directory path must be absolute."); + free($2); + return (1); + } + if (snprintf(curhost->adh_directory, + sizeof(curhost->adh_directory), "%s/%s", + depth1_directory, $2) >= + (ssize_t)sizeof(curhost->adh_directory)) { + pjdlog_error("Directory value is too long."); + free($2); + return (1); + } + } + break; + default: + PJDLOG_ABORT("directory at wrong depth level"); + } + free($2); + } + ; + +source_statement: SOURCE STR + { + PJDLOG_RASSERT(cursection == SECTION_SENDER, + "The source variable must be in sender section."); + + switch (depth) { + case 1: + if (strlcpy(depth1_source, $2, + sizeof(depth1_source)) >= + sizeof(depth1_source)) { + pjdlog_error("Source value is too long."); + free($2); + return (1); + } + break; + case 2: + if (strlcpy(curhost->adh_localaddr, $2, + sizeof(curhost->adh_localaddr)) >= + sizeof(curhost->adh_localaddr)) { + pjdlog_error("Source value is too long."); + free($2); + return (1); + } + break; + } + free($2); + } + ; + +fingerprint_statement: FINGERPRINT STR + { + PJDLOG_ASSERT(cursection == SECTION_SENDER); + PJDLOG_ASSERT(depth == 2); + + if (strncasecmp($2, "SHA256=", 7) != 0) { + pjdlog_error("Invalid fingerprint value."); + free($2); + return (1); + } + if (strlcpy(curhost->adh_fingerprint, $2, + sizeof(curhost->adh_fingerprint)) >= + sizeof(curhost->adh_fingerprint)) { + pjdlog_error("Fingerprint value is too long."); + free($2); + return (1); + } + free($2); + } + ; + +password_statement: PASSWORD STR + { + PJDLOG_ASSERT(cursection == SECTION_SENDER || + cursection == SECTION_RECEIVER); + PJDLOG_ASSERT(depth == 2); + + if (strlcpy(curhost->adh_password, $2, + sizeof(curhost->adh_password)) >= + sizeof(curhost->adh_password)) { + pjdlog_error("Password value is too long."); + bzero($2, strlen($2)); + free($2); + return (1); + } + bzero($2, strlen($2)); + free($2); + } + ; + +certfile_statement: CERTFILE STR + { + PJDLOG_ASSERT(cursection == SECTION_RECEIVER); + PJDLOG_ASSERT(depth == 1); + + if (strlcpy(lconfig->adc_certfile, $2, + sizeof(lconfig->adc_certfile)) >= + sizeof(lconfig->adc_certfile)) { + pjdlog_error("Certfile value is too long."); + free($2); + return (1); + } + free($2); + } + ; + +keyfile_statement: KEYFILE STR + { + PJDLOG_ASSERT(cursection == SECTION_RECEIVER); + PJDLOG_ASSERT(depth == 1); + + if (strlcpy(lconfig->adc_keyfile, $2, + sizeof(lconfig->adc_keyfile)) >= + sizeof(lconfig->adc_keyfile)) { + pjdlog_error("Keyfile value is too long."); + free($2); + return (1); + } + free($2); + } + ; + +listen_statement: LISTEN STR + { + struct adist_listen *lst; + + PJDLOG_ASSERT(depth == 1); + PJDLOG_ASSERT(cursection == SECTION_RECEIVER); + + lst = calloc(1, sizeof(*lst)); + if (lst == NULL) { + pjdlog_error("Unable to allocate memory for listen address."); + free($2); + return (1); + } + if (strlcpy(lst->adl_addr, $2, sizeof(lst->adl_addr)) >= + sizeof(lst->adl_addr)) { + pjdlog_error("listen argument is too long."); + free($2); + free(lst); + return (1); + } + TAILQ_INSERT_TAIL(&lconfig->adc_listen, lst, adl_next); + free($2); + } + ; + +sender_host_statement: HOST host_start OB sender_host_entries CB + { + /* Put it onto host list. */ + TAILQ_INSERT_TAIL(&lconfig->adc_hosts, curhost, adh_next); + curhost = NULL; + } + ; + +receiver_host_statement: HOST host_start OB receiver_host_entries CB + { + /* Put it onto host list. */ + TAILQ_INSERT_TAIL(&lconfig->adc_hosts, curhost, adh_next); + curhost = NULL; + } + ; + +host_start: STR + { + /* Check if there is no duplicate entry. */ + TAILQ_FOREACH(curhost, &lconfig->adc_hosts, adh_next) { + if (strcmp(curhost->adh_name, $1) != 0) + continue; + if (curhost->adh_role == ADIST_ROLE_SENDER && + cursection == SECTION_RECEIVER) { + continue; + } + if (curhost->adh_role == ADIST_ROLE_RECEIVER && + cursection == SECTION_SENDER) { + continue; + } + pjdlog_error("%s host %s is configured more than once.", + curhost->adh_role == ADIST_ROLE_SENDER ? + "Sender" : "Receiver", curhost->adh_name); + free($1); + return (1); + } + + curhost = calloc(1, sizeof(*curhost)); + if (curhost == NULL) { + pjdlog_error("Unable to allocate memory for host configuration."); + free($1); + return (1); + } + if (strlcpy(curhost->adh_name, $1, sizeof(curhost->adh_name)) >= + sizeof(curhost->adh_name)) { + pjdlog_error("Host name is too long."); + free($1); + return (1); + } + free($1); + curhost->adh_role = cursection == SECTION_SENDER ? + ADIST_ROLE_SENDER : ADIST_ROLE_RECEIVER; + curhost->adh_version = ADIST_VERSION; + curhost->adh_localaddr[0] = '\0'; + curhost->adh_remoteaddr[0] = '\0'; + curhost->adh_remote = NULL; + curhost->adh_directory[0] = '\0'; + curhost->adh_password[0] = '\0'; + curhost->adh_fingerprint[0] = '\0'; + curhost->adh_worker_pid = 0; + curhost->adh_conn = NULL; + } + ; + +sender_host_entries: + | + sender_host_entries sender_host_entry + ; + +sender_host_entry: + source_statement + | + remote_statement + | + directory_statement + | + fingerprint_statement + | + password_statement +/* + | + checksum_statement + | + compression_statement +*/ + ; + +receiver_host_entries: + | + receiver_host_entries receiver_host_entry + ; + +receiver_host_entry: + remote_statement + | + directory_statement + | + password_statement + ; + +remote_statement: REMOTE STR + { + PJDLOG_ASSERT(depth == 2); + PJDLOG_ASSERT(cursection == SECTION_SENDER || + cursection == SECTION_RECEIVER); + + if (strlcpy(curhost->adh_remoteaddr, $2, + sizeof(curhost->adh_remoteaddr)) >= + sizeof(curhost->adh_remoteaddr)) { + pjdlog_error("Remote value is too long."); + free($2); + return (1); + } + free($2); + } + ; + +%% + +static bool +family_supported(int family) +{ + int sock; + + sock = socket(family, SOCK_STREAM, 0); + if (sock == -1 && errno == EPROTONOSUPPORT) + return (false); + if (sock >= 0) + (void)close(sock); + return (true); +} + +static bool +adjust_directory(char *path) +{ + size_t len; + + len = strlen(path); + for (;;) { + if (len == 0) { + pjdlog_error("Directory path is empty."); + return (false); + } + if (path[len - 1] != '/') + break; + len--; + path[len] = '\0'; + } + if (path[0] != '/') { + pjdlog_error("Directory path must be absolute."); + return (false); + } + return (true); +} + +static int +my_name(char *name, size_t size) +{ + char buf[MAXHOSTNAMELEN]; + char *pos; + + if (gethostname(buf, sizeof(buf)) < 0) { + pjdlog_errno(LOG_ERR, "gethostname() failed"); + return (-1); + } + + /* First component of the host name. */ + pos = strchr(buf, '.'); + if (pos == NULL) + (void)strlcpy(name, buf, size); + else + (void)strlcpy(name, buf, MIN((size_t)(pos - buf + 1), size)); + + if (name[0] == '\0') { + pjdlog_error("Empty host name."); + return (-1); + } + + return (0); +} + +void +yyerror(const char *str) +{ + + pjdlog_error("Unable to parse configuration file at line %d near '%s': %s", + lineno, yytext, str); +} + +struct adist_config * +yy_config_parse(const char *config, bool exitonerror) +{ + int ret; + + curhost = NULL; + cursection = SECTION_GLOBAL; + depth = 0; + lineno = 0; + + lconfig = calloc(1, sizeof(*lconfig)); + if (lconfig == NULL) { + pjdlog_error("Unable to allocate memory for configuration."); + if (exitonerror) + exit(EX_TEMPFAIL); + return (NULL); + } + TAILQ_INIT(&lconfig->adc_hosts); + TAILQ_INIT(&lconfig->adc_listen); + lconfig->adc_name[0] = '\0'; + lconfig->adc_timeout = -1; + lconfig->adc_pidfile[0] = '\0'; + lconfig->adc_certfile[0] = '\0'; + lconfig->adc_keyfile[0] = '\0'; + + yyin = fopen(config, "r"); + if (yyin == NULL) { + pjdlog_errno(LOG_ERR, "Unable to open configuration file %s", + config); + yy_config_free(lconfig); + if (exitonerror) + exit(EX_OSFILE); + return (NULL); + } + yyrestart(yyin); + ret = yyparse(); + fclose(yyin); + if (ret != 0) { + yy_config_free(lconfig); + if (exitonerror) + exit(EX_CONFIG); + return (NULL); + } + + /* + * Let's see if everything is set up. + */ + if (lconfig->adc_name[0] == '\0' && my_name(lconfig->adc_name, + sizeof(lconfig->adc_name)) == -1) { + yy_config_free(lconfig); + if (exitonerror) + exit(EX_CONFIG); + return (NULL); + } + if (lconfig->adc_timeout == -1) + lconfig->adc_timeout = ADIST_TIMEOUT; + if (lconfig->adc_pidfile[0] == '\0') { + (void)strlcpy(lconfig->adc_pidfile, ADIST_PIDFILE, + sizeof(lconfig->adc_pidfile)); + } + if (lconfig->adc_certfile[0] == '\0') { + (void)strlcpy(lconfig->adc_certfile, ADIST_CERTFILE, + sizeof(lconfig->adc_certfile)); + } + if (lconfig->adc_keyfile[0] == '\0') { + (void)strlcpy(lconfig->adc_keyfile, ADIST_KEYFILE, + sizeof(lconfig->adc_keyfile)); + } + + return (lconfig); +} + +void +yy_config_free(struct adist_config *config) +{ + struct adist_host *adhost; + struct adist_listen *lst; + + while ((lst = TAILQ_FIRST(&config->adc_listen)) != NULL) { + TAILQ_REMOVE(&config->adc_listen, lst, adl_next); + free(lst); + } + while ((adhost = TAILQ_FIRST(&config->adc_hosts)) != NULL) { + TAILQ_REMOVE(&config->adc_hosts, adhost, adh_next); + bzero(adhost, sizeof(*adhost)); + free(adhost); + } + free(config); +} diff --git a/contrib/openbsm/bin/auditdistd/pjdlog.c b/contrib/openbsm/bin/auditdistd/pjdlog.c new file mode 100644 index 0000000..e8d5876 --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/pjdlog.c @@ -0,0 +1,621 @@ +/*- + * Copyright (c) 2009-2010 The FreeBSD Foundation + * Copyright (c) 2011 Pawel Jakub Dawidek <pjd@FreeBSD.org> + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/pjdlog.c#1 $ + */ + +#include <sys/types.h> +#include <sys/socket.h> +#include <netinet/in.h> +#include <arpa/inet.h> + +#include <assert.h> +#include <errno.h> +#ifdef __FreeBSD__ +#include <libutil.h> +#include <printf.h> +#endif +#include <stdarg.h> +#include <stdint.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <syslog.h> +#include <unistd.h> + +#include "pjdlog.h" + +#define PJDLOG_NEVER_INITIALIZED 0 +#define PJDLOG_NOT_INITIALIZED 1 +#define PJDLOG_INITIALIZED 2 + +static int pjdlog_initialized = PJDLOG_NEVER_INITIALIZED; +static int pjdlog_mode, pjdlog_debug_level; +static char pjdlog_prefix[128]; + +#ifdef __FreeBSD__ +static int +pjdlog_printf_arginfo_humanized_number(const struct printf_info *pi __unused, + size_t n, int *argt) +{ + + assert(n >= 1); + argt[0] = PA_INT | PA_FLAG_INTMAX; + return (1); +} + +static int +pjdlog_printf_render_humanized_number(struct __printf_io *io, + const struct printf_info *pi, const void * const *arg) +{ + char buf[5]; + intmax_t num; + int ret; + + num = *(const intmax_t *)arg[0]; + humanize_number(buf, sizeof(buf), (int64_t)num, "", HN_AUTOSCALE, + HN_NOSPACE | HN_DECIMAL); + ret = __printf_out(io, pi, buf, strlen(buf)); + __printf_flush(io); + return (ret); +} + +static int +pjdlog_printf_arginfo_sockaddr(const struct printf_info *pi __unused, + size_t n, int *argt) +{ + + assert(n >= 1); + argt[0] = PA_POINTER; + return (1); +} + +static int +pjdlog_printf_render_sockaddr(struct __printf_io *io, + const struct printf_info *pi, const void * const *arg) +{ + const struct sockaddr_storage *ss; + char buf[64]; + int ret; + + ss = *(const struct sockaddr_storage * const *)arg[0]; + switch (ss->ss_family) { + case AF_INET: + { + char addr[INET_ADDRSTRLEN]; + const struct sockaddr_in *sin; + unsigned int port; + + sin = (const struct sockaddr_in *)ss; + port = ntohs(sin->sin_port); + if (inet_ntop(ss->ss_family, &sin->sin_addr, addr, + sizeof(addr)) == NULL) { + PJDLOG_ABORT("inet_ntop(AF_INET) failed: %s.", + strerror(errno)); + } + snprintf(buf, sizeof(buf), "%s:%u", addr, port); + break; + } + case AF_INET6: + { + char addr[INET6_ADDRSTRLEN]; + const struct sockaddr_in6 *sin; + unsigned int port; + + sin = (const struct sockaddr_in6 *)ss; + port = ntohs(sin->sin6_port); + if (inet_ntop(ss->ss_family, &sin->sin6_addr, addr, + sizeof(addr)) == NULL) { + PJDLOG_ABORT("inet_ntop(AF_INET6) failed: %s.", + strerror(errno)); + } + snprintf(buf, sizeof(buf), "[%s]:%u", addr, port); + break; + } + default: + snprintf(buf, sizeof(buf), "[unsupported family %hhu]", + ss->ss_family); + break; + } + ret = __printf_out(io, pi, buf, strlen(buf)); + __printf_flush(io); + return (ret); +} +#endif /* __FreeBSD__ */ + +void +pjdlog_init(int mode) +{ + int saved_errno; + + assert(pjdlog_initialized == PJDLOG_NEVER_INITIALIZED || + pjdlog_initialized == PJDLOG_NOT_INITIALIZED); + assert(mode == PJDLOG_MODE_STD || mode == PJDLOG_MODE_SYSLOG); + + saved_errno = errno; + + if (pjdlog_initialized == PJDLOG_NEVER_INITIALIZED) { +#ifdef __FreeBSD__ + __use_xprintf = 1; + register_printf_render_std("T"); + register_printf_render('N', + pjdlog_printf_render_humanized_number, + pjdlog_printf_arginfo_humanized_number); + register_printf_render('S', + pjdlog_printf_render_sockaddr, + pjdlog_printf_arginfo_sockaddr); +#endif + } + + if (mode == PJDLOG_MODE_SYSLOG) + openlog(NULL, LOG_PID | LOG_NDELAY, LOG_DAEMON); + pjdlog_mode = mode; + pjdlog_debug_level = 0; + bzero(pjdlog_prefix, sizeof(pjdlog_prefix)); + + pjdlog_initialized = PJDLOG_INITIALIZED; + + errno = saved_errno; +} + +void +pjdlog_fini(void) +{ + int saved_errno; + + assert(pjdlog_initialized == PJDLOG_INITIALIZED); + + saved_errno = errno; + + if (pjdlog_mode == PJDLOG_MODE_SYSLOG) + closelog(); + + pjdlog_initialized = PJDLOG_NOT_INITIALIZED; + + errno = saved_errno; +} + +/* + * Configure where the logs should go. + * By default they are send to stdout/stderr, but after going into background + * (eg. by calling daemon(3)) application is responsible for changing mode to + * PJDLOG_MODE_SYSLOG, so logs will be send to syslog. + */ +void +pjdlog_mode_set(int mode) +{ + int saved_errno; + + assert(pjdlog_initialized == PJDLOG_INITIALIZED); + assert(mode == PJDLOG_MODE_STD || mode == PJDLOG_MODE_SYSLOG); + + if (pjdlog_mode == mode) + return; + + saved_errno = errno; + + if (mode == PJDLOG_MODE_SYSLOG) + openlog(NULL, LOG_PID | LOG_NDELAY, LOG_DAEMON); + else /* if (mode == PJDLOG_MODE_STD) */ + closelog(); + + pjdlog_mode = mode; + + errno = saved_errno; +} + +/* + * Return current mode. + */ +int +pjdlog_mode_get(void) +{ + + assert(pjdlog_initialized == PJDLOG_INITIALIZED); + + return (pjdlog_mode); +} + +/* + * Set debug level. All the logs above the level specified here will be + * ignored. + */ +void +pjdlog_debug_set(int level) +{ + + assert(pjdlog_initialized == PJDLOG_INITIALIZED); + assert(level >= 0); + + pjdlog_debug_level = level; +} + +/* + * Return current debug level. + */ +int +pjdlog_debug_get(void) +{ + + assert(pjdlog_initialized == PJDLOG_INITIALIZED); + + return (pjdlog_debug_level); +} + +/* + * Set prefix that will be used before each log. + * Setting prefix to NULL will remove it. + */ +void +pjdlog_prefix_set(const char *fmt, ...) +{ + va_list ap; + + assert(pjdlog_initialized == PJDLOG_INITIALIZED); + + va_start(ap, fmt); + pjdlogv_prefix_set(fmt, ap); + va_end(ap); +} + +/* + * Set prefix that will be used before each log. + * Setting prefix to NULL will remove it. + */ +void +pjdlogv_prefix_set(const char *fmt, va_list ap) +{ + int saved_errno; + + assert(pjdlog_initialized == PJDLOG_INITIALIZED); + assert(fmt != NULL); + + saved_errno = errno; + + vsnprintf(pjdlog_prefix, sizeof(pjdlog_prefix), fmt, ap); + + errno = saved_errno; +} + +/* + * Convert log level into string. + */ +static const char * +pjdlog_level_string(int loglevel) +{ + + switch (loglevel) { + case LOG_EMERG: + return ("EMERG"); + case LOG_ALERT: + return ("ALERT"); + case LOG_CRIT: + return ("CRIT"); + case LOG_ERR: + return ("ERROR"); + case LOG_WARNING: + return ("WARNING"); + case LOG_NOTICE: + return ("NOTICE"); + case LOG_INFO: + return ("INFO"); + case LOG_DEBUG: + return ("DEBUG"); + } + assert(!"Invalid log level."); + abort(); /* XXX: gcc */ +} + +/* + * Common log routine. + */ +void +pjdlog_common(int loglevel, int debuglevel, int error, const char *fmt, ...) +{ + va_list ap; + + assert(pjdlog_initialized == PJDLOG_INITIALIZED); + + va_start(ap, fmt); + pjdlogv_common(loglevel, debuglevel, error, fmt, ap); + va_end(ap); +} + +/* + * Common log routine, which can handle regular log level as well as debug + * level. We decide here where to send the logs (stdout/stderr or syslog). + */ +void +pjdlogv_common(int loglevel, int debuglevel, int error, const char *fmt, + va_list ap) +{ + int saved_errno; + + assert(pjdlog_initialized == PJDLOG_INITIALIZED); + assert(loglevel == LOG_EMERG || loglevel == LOG_ALERT || + loglevel == LOG_CRIT || loglevel == LOG_ERR || + loglevel == LOG_WARNING || loglevel == LOG_NOTICE || + loglevel == LOG_INFO || loglevel == LOG_DEBUG); + assert(loglevel != LOG_DEBUG || debuglevel > 0); + assert(error >= -1); + + /* Ignore debug above configured level. */ + if (loglevel == LOG_DEBUG && debuglevel > pjdlog_debug_level) + return; + + saved_errno = errno; + + switch (pjdlog_mode) { + case PJDLOG_MODE_STD: + { + FILE *out; + + /* + * We send errors and warning to stderr and the rest to stdout. + */ + switch (loglevel) { + case LOG_EMERG: + case LOG_ALERT: + case LOG_CRIT: + case LOG_ERR: + case LOG_WARNING: + out = stderr; + break; + case LOG_NOTICE: + case LOG_INFO: + case LOG_DEBUG: + out = stdout; + break; + default: + assert(!"Invalid loglevel."); + abort(); /* XXX: gcc */ + } + + fprintf(out, "(%d) ", getpid()); + fprintf(out, "[%s]", pjdlog_level_string(loglevel)); + /* Attach debuglevel if this is debug log. */ + if (loglevel == LOG_DEBUG) + fprintf(out, "[%d]", debuglevel); + fprintf(out, " %s", pjdlog_prefix); + vfprintf(out, fmt, ap); + if (error != -1) + fprintf(out, ": %s.", strerror(error)); + fprintf(out, "\n"); + fflush(out); + break; + } + case PJDLOG_MODE_SYSLOG: + { + char log[1024]; + int len; + + len = snprintf(log, sizeof(log), "%s", pjdlog_prefix); + if ((size_t)len < sizeof(log)) + len += vsnprintf(log + len, sizeof(log) - len, fmt, ap); + if (error != -1 && (size_t)len < sizeof(log)) { + (void)snprintf(log + len, sizeof(log) - len, ": %s.", + strerror(error)); + } + syslog(loglevel, "%s", log); + break; + } + default: + assert(!"Invalid mode."); + } + + errno = saved_errno; +} + +/* + * Regular logs. + */ +void +pjdlogv(int loglevel, const char *fmt, va_list ap) +{ + + assert(pjdlog_initialized == PJDLOG_INITIALIZED); + + /* LOG_DEBUG is invalid here, pjdlogv?_debug() should be used. */ + assert(loglevel == LOG_EMERG || loglevel == LOG_ALERT || + loglevel == LOG_CRIT || loglevel == LOG_ERR || + loglevel == LOG_WARNING || loglevel == LOG_NOTICE || + loglevel == LOG_INFO); + + pjdlogv_common(loglevel, 0, -1, fmt, ap); +} + +/* + * Regular logs. + */ +void +pjdlog(int loglevel, const char *fmt, ...) +{ + va_list ap; + + assert(pjdlog_initialized == PJDLOG_INITIALIZED); + + va_start(ap, fmt); + pjdlogv(loglevel, fmt, ap); + va_end(ap); +} + +/* + * Debug logs. + */ +void +pjdlogv_debug(int debuglevel, const char *fmt, va_list ap) +{ + + assert(pjdlog_initialized == PJDLOG_INITIALIZED); + + pjdlogv_common(LOG_DEBUG, debuglevel, -1, fmt, ap); +} + +/* + * Debug logs. + */ +void +pjdlog_debug(int debuglevel, const char *fmt, ...) +{ + va_list ap; + + assert(pjdlog_initialized == PJDLOG_INITIALIZED); + + va_start(ap, fmt); + pjdlogv_debug(debuglevel, fmt, ap); + va_end(ap); +} + +/* + * Error logs with errno logging. + */ +void +pjdlogv_errno(int loglevel, const char *fmt, va_list ap) +{ + + assert(pjdlog_initialized == PJDLOG_INITIALIZED); + + pjdlogv_common(loglevel, 0, errno, fmt, ap); +} + +/* + * Error logs with errno logging. + */ +void +pjdlog_errno(int loglevel, const char *fmt, ...) +{ + va_list ap; + + assert(pjdlog_initialized == PJDLOG_INITIALIZED); + + va_start(ap, fmt); + pjdlogv_errno(loglevel, fmt, ap); + va_end(ap); +} + +/* + * Log error, errno and exit. + */ +void +pjdlogv_exit(int exitcode, const char *fmt, va_list ap) +{ + + assert(pjdlog_initialized == PJDLOG_INITIALIZED); + + pjdlogv_errno(LOG_ERR, fmt, ap); + exit(exitcode); + /* NOTREACHED */ +} + +/* + * Log error, errno and exit. + */ +void +pjdlog_exit(int exitcode, const char *fmt, ...) +{ + va_list ap; + + assert(pjdlog_initialized == PJDLOG_INITIALIZED); + + va_start(ap, fmt); + pjdlogv_exit(exitcode, fmt, ap); + /* NOTREACHED */ + va_end(ap); +} + +/* + * Log error and exit. + */ +void +pjdlogv_exitx(int exitcode, const char *fmt, va_list ap) +{ + + assert(pjdlog_initialized == PJDLOG_INITIALIZED); + + pjdlogv(LOG_ERR, fmt, ap); + exit(exitcode); + /* NOTREACHED */ +} + +/* + * Log error and exit. + */ +void +pjdlog_exitx(int exitcode, const char *fmt, ...) +{ + va_list ap; + + assert(pjdlog_initialized == PJDLOG_INITIALIZED); + + va_start(ap, fmt); + pjdlogv_exitx(exitcode, fmt, ap); + /* NOTREACHED */ + va_end(ap); +} + +/* + * Log failure message and exit. + */ +void +pjdlog_abort(const char *func, const char *file, int line, + const char *failedexpr, const char *fmt, ...) +{ + va_list ap; + + assert(pjdlog_initialized == PJDLOG_INITIALIZED); + + /* + * When there is no message we pass __func__ as 'fmt'. + * It would be cleaner to pass NULL or "", but gcc generates a warning + * for both of those. + */ + if (fmt != func) { + va_start(ap, fmt); + pjdlogv_critical(fmt, ap); + va_end(ap); + } + if (failedexpr == NULL) { + if (func == NULL) { + pjdlog_critical("Aborted at file %s, line %d.", file, + line); + } else { + pjdlog_critical("Aborted at function %s, file %s, line %d.", + func, file, line); + } + } else { + if (func == NULL) { + pjdlog_critical("Assertion failed: (%s), file %s, line %d.", + failedexpr, file, line); + } else { + pjdlog_critical("Assertion failed: (%s), function %s, file %s, line %d.", + failedexpr, func, file, line); + } + } + abort(); +} diff --git a/contrib/openbsm/bin/auditdistd/pjdlog.h b/contrib/openbsm/bin/auditdistd/pjdlog.h new file mode 100644 index 0000000..0cb6121 --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/pjdlog.h @@ -0,0 +1,119 @@ +/*- + * Copyright (c) 2009-2010 The FreeBSD Foundation + * Copyright (c) 2011 Pawel Jakub Dawidek <pjd@FreeBSD.org> + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/pjdlog.h#1 $ + */ + +#ifndef _PJDLOG_H_ +#define _PJDLOG_H_ + +#include <sys/cdefs.h> + +#include <stdarg.h> +#include <sysexits.h> +#include <syslog.h> + +#include <compat/compat.h> + +#define PJDLOG_MODE_STD 0 +#define PJDLOG_MODE_SYSLOG 1 + +void pjdlog_init(int mode); +void pjdlog_fini(void); + +void pjdlog_mode_set(int mode); +int pjdlog_mode_get(void); + +void pjdlog_debug_set(int level); +int pjdlog_debug_get(void); + +void pjdlog_prefix_set(const char *fmt, ...) __printflike(1, 2); +void pjdlogv_prefix_set(const char *fmt, va_list ap) __printflike(1, 0); + +void pjdlog_common(int loglevel, int debuglevel, int error, const char *fmt, + ...) __printflike(4, 5); +void pjdlogv_common(int loglevel, int debuglevel, int error, const char *fmt, + va_list ap) __printflike(4, 0); + +void pjdlog(int loglevel, const char *fmt, ...) __printflike(2, 3); +void pjdlogv(int loglevel, const char *fmt, va_list ap) __printflike(2, 0); + +#define pjdlogv_emergency(fmt, ap) pjdlogv(LOG_EMERG, (fmt), (ap)) +#define pjdlog_emergency(...) pjdlog(LOG_EMERG, __VA_ARGS__) +#define pjdlogv_alert(fmt, ap) pjdlogv(LOG_ALERT, (fmt), (ap)) +#define pjdlog_alert(...) pjdlog(LOG_ALERT, __VA_ARGS__) +#define pjdlogv_critical(fmt, ap) pjdlogv(LOG_CRIT, (fmt), (ap)) +#define pjdlog_critical(...) pjdlog(LOG_CRIT, __VA_ARGS__) +#define pjdlogv_error(fmt, ap) pjdlogv(LOG_ERR, (fmt), (ap)) +#define pjdlog_error(...) pjdlog(LOG_ERR, __VA_ARGS__) +#define pjdlogv_warning(fmt, ap) pjdlogv(LOG_WARNING, (fmt), (ap)) +#define pjdlog_warning(...) pjdlog(LOG_WARNING, __VA_ARGS__) +#define pjdlogv_notice(fmt, ap) pjdlogv(LOG_NOTICE, (fmt), (ap)) +#define pjdlog_notice(...) pjdlog(LOG_NOTICE, __VA_ARGS__) +#define pjdlogv_info(fmt, ap) pjdlogv(LOG_INFO, (fmt), (ap)) +#define pjdlog_info(...) pjdlog(LOG_INFO, __VA_ARGS__) + +void pjdlog_debug(int debuglevel, const char *fmt, ...) __printflike(2, 3); +void pjdlogv_debug(int debuglevel, const char *fmt, va_list ap) __printflike(2, 0); + +void pjdlog_errno(int loglevel, const char *fmt, ...) __printflike(2, 3); +void pjdlogv_errno(int loglevel, const char *fmt, va_list ap) __printflike(2, 0); + +void pjdlog_exit(int exitcode, const char *fmt, ...) __printflike(2, 3) __dead2; +void pjdlogv_exit(int exitcode, const char *fmt, va_list ap) __printflike(2, 0) __dead2; + +void pjdlog_exitx(int exitcode, const char *fmt, ...) __printflike(2, 3) __dead2; +void pjdlogv_exitx(int exitcode, const char *fmt, va_list ap) __printflike(2, 0) __dead2; + +void pjdlog_abort(const char *func, const char *file, int line, + const char *failedexpr, const char *fmt, ...) __printflike(5, 6) __dead2; + +#define PJDLOG_VERIFY(expr) do { \ + if (!(expr)) { \ + pjdlog_abort(__func__, __FILE__, __LINE__, #expr, \ + "%s", __func__); \ + } \ +} while (0) +#define PJDLOG_RVERIFY(expr, ...) do { \ + if (!(expr)) { \ + pjdlog_abort(__func__, __FILE__, __LINE__, #expr, \ + __VA_ARGS__); \ + } \ +} while (0) +#define PJDLOG_ABORT(...) pjdlog_abort(__func__, __FILE__, \ + __LINE__, NULL, __VA_ARGS__) +#ifdef NDEBUG +#define PJDLOG_ASSERT(expr) do { } while (0) +#define PJDLOG_RASSERT(...) do { } while (0) +#else +#define PJDLOG_ASSERT(expr) PJDLOG_VERIFY(expr) +#define PJDLOG_RASSERT(...) PJDLOG_RVERIFY(__VA_ARGS__) +#endif + +#endif /* !_PJDLOG_H_ */ diff --git a/contrib/openbsm/bin/auditdistd/proto.c b/contrib/openbsm/bin/auditdistd/proto.c new file mode 100644 index 0000000..25daf0c --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/proto.c @@ -0,0 +1,529 @@ +/*- + * Copyright (c) 2009-2010 The FreeBSD Foundation + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/proto.c#1 $ + */ + +#include <sys/types.h> +#include <sys/queue.h> +#include <sys/socket.h> + +#include <errno.h> +#include <stdint.h> +#include <string.h> +#include <strings.h> + +#include "pjdlog.h" +#include "proto.h" +#include "proto_impl.h" + +#define PROTO_CONN_MAGIC 0x907041c +struct proto_conn { + int pc_magic; + struct proto *pc_proto; + void *pc_ctx; + int pc_side; +#define PROTO_SIDE_CLIENT 0 +#define PROTO_SIDE_SERVER_LISTEN 1 +#define PROTO_SIDE_SERVER_WORK 2 +}; + +static TAILQ_HEAD(, proto) protos = TAILQ_HEAD_INITIALIZER(protos); + +void +proto_register(struct proto *proto, bool isdefault) +{ + static bool seen_default = false; + + if (!isdefault) + TAILQ_INSERT_HEAD(&protos, proto, prt_next); + else { + PJDLOG_ASSERT(!seen_default); + seen_default = true; + TAILQ_INSERT_TAIL(&protos, proto, prt_next); + } +} + +static struct proto_conn * +proto_alloc(struct proto *proto, int side) +{ + struct proto_conn *conn; + + PJDLOG_ASSERT(proto != NULL); + PJDLOG_ASSERT(side == PROTO_SIDE_CLIENT || + side == PROTO_SIDE_SERVER_LISTEN || + side == PROTO_SIDE_SERVER_WORK); + + conn = malloc(sizeof(*conn)); + if (conn != NULL) { + conn->pc_proto = proto; + conn->pc_side = side; + conn->pc_magic = PROTO_CONN_MAGIC; + } + return (conn); +} + +static void +proto_free(struct proto_conn *conn) +{ + + PJDLOG_ASSERT(conn != NULL); + PJDLOG_ASSERT(conn->pc_magic == PROTO_CONN_MAGIC); + PJDLOG_ASSERT(conn->pc_side == PROTO_SIDE_CLIENT || + conn->pc_side == PROTO_SIDE_SERVER_LISTEN || + conn->pc_side == PROTO_SIDE_SERVER_WORK); + PJDLOG_ASSERT(conn->pc_proto != NULL); + + bzero(conn, sizeof(*conn)); + free(conn); +} + +static int +proto_common_setup(const char *srcaddr, const char *dstaddr, int timeout, + int side, struct proto_conn **connp) +{ + struct proto *proto; + struct proto_conn *conn; + void *ctx; + int ret; + + PJDLOG_ASSERT(side == PROTO_SIDE_CLIENT || + side == PROTO_SIDE_SERVER_LISTEN); + + TAILQ_FOREACH(proto, &protos, prt_next) { + if (side == PROTO_SIDE_CLIENT) { + if (proto->prt_connect == NULL) { + ret = -1; + } else { + ret = proto->prt_connect(srcaddr, dstaddr, + timeout, &ctx); + } + } else /* if (side == PROTO_SIDE_SERVER_LISTEN) */ { + if (proto->prt_server == NULL) + ret = -1; + else + ret = proto->prt_server(dstaddr, &ctx); + } + /* + * ret == 0 - success + * ret == -1 - dstaddr is not for this protocol + * ret > 0 - right protocol, but an error occured + */ + if (ret >= 0) + break; + } + if (proto == NULL) { + /* Unrecognized address. */ + errno = EINVAL; + return (-1); + } + if (ret > 0) { + /* An error occured. */ + errno = ret; + return (-1); + } + conn = proto_alloc(proto, side); + if (conn == NULL) { + if (proto->prt_close != NULL) + proto->prt_close(ctx); + errno = ENOMEM; + return (-1); + } + conn->pc_ctx = ctx; + *connp = conn; + + return (0); +} + +int +proto_connect(const char *srcaddr, const char *dstaddr, int timeout, + struct proto_conn **connp) +{ + + PJDLOG_ASSERT(srcaddr == NULL || srcaddr[0] != '\0'); + PJDLOG_ASSERT(dstaddr != NULL); + PJDLOG_ASSERT(timeout >= -1); + + return (proto_common_setup(srcaddr, dstaddr, timeout, + PROTO_SIDE_CLIENT, connp)); +} + +int +proto_connect_wait(struct proto_conn *conn, int timeout) +{ + int error; + + PJDLOG_ASSERT(conn != NULL); + PJDLOG_ASSERT(conn->pc_magic == PROTO_CONN_MAGIC); + PJDLOG_ASSERT(conn->pc_side == PROTO_SIDE_CLIENT); + PJDLOG_ASSERT(conn->pc_proto != NULL); + PJDLOG_ASSERT(conn->pc_proto->prt_connect_wait != NULL); + PJDLOG_ASSERT(timeout >= 0); + + error = conn->pc_proto->prt_connect_wait(conn->pc_ctx, timeout); + if (error != 0) { + errno = error; + return (-1); + } + + return (0); +} + +int +proto_server(const char *addr, struct proto_conn **connp) +{ + + PJDLOG_ASSERT(addr != NULL); + + return (proto_common_setup(NULL, addr, -1, PROTO_SIDE_SERVER_LISTEN, + connp)); +} + +int +proto_accept(struct proto_conn *conn, struct proto_conn **newconnp) +{ + struct proto_conn *newconn; + int error; + + PJDLOG_ASSERT(conn != NULL); + PJDLOG_ASSERT(conn->pc_magic == PROTO_CONN_MAGIC); + PJDLOG_ASSERT(conn->pc_side == PROTO_SIDE_SERVER_LISTEN); + PJDLOG_ASSERT(conn->pc_proto != NULL); + PJDLOG_ASSERT(conn->pc_proto->prt_accept != NULL); + + newconn = proto_alloc(conn->pc_proto, PROTO_SIDE_SERVER_WORK); + if (newconn == NULL) + return (-1); + + error = conn->pc_proto->prt_accept(conn->pc_ctx, &newconn->pc_ctx); + if (error != 0) { + proto_free(newconn); + errno = error; + return (-1); + } + + *newconnp = newconn; + + return (0); +} + +int +proto_send(const struct proto_conn *conn, const void *data, size_t size) +{ + int error; + + PJDLOG_ASSERT(conn != NULL); + PJDLOG_ASSERT(conn->pc_magic == PROTO_CONN_MAGIC); + PJDLOG_ASSERT(conn->pc_proto != NULL); + PJDLOG_ASSERT(conn->pc_proto->prt_send != NULL); + + error = conn->pc_proto->prt_send(conn->pc_ctx, data, size, -1); + if (error != 0) { + errno = error; + return (-1); + } + return (0); +} + +int +proto_recv(const struct proto_conn *conn, void *data, size_t size) +{ + int error; + + PJDLOG_ASSERT(conn != NULL); + PJDLOG_ASSERT(conn->pc_magic == PROTO_CONN_MAGIC); + PJDLOG_ASSERT(conn->pc_proto != NULL); + PJDLOG_ASSERT(conn->pc_proto->prt_recv != NULL); + + error = conn->pc_proto->prt_recv(conn->pc_ctx, data, size, NULL); + if (error != 0) { + errno = error; + return (-1); + } + return (0); +} + +int +proto_connection_send(const struct proto_conn *conn, struct proto_conn *mconn) +{ + const char *protoname; + int error, fd; + + PJDLOG_ASSERT(conn != NULL); + PJDLOG_ASSERT(conn->pc_magic == PROTO_CONN_MAGIC); + PJDLOG_ASSERT(conn->pc_proto != NULL); + PJDLOG_ASSERT(conn->pc_proto->prt_send != NULL); + PJDLOG_ASSERT(mconn != NULL); + PJDLOG_ASSERT(mconn->pc_magic == PROTO_CONN_MAGIC); + PJDLOG_ASSERT(mconn->pc_proto != NULL); + fd = proto_descriptor(mconn); + PJDLOG_ASSERT(fd >= 0); + protoname = mconn->pc_proto->prt_name; + PJDLOG_ASSERT(protoname != NULL); + + error = conn->pc_proto->prt_send(conn->pc_ctx, + (const unsigned char *)protoname, strlen(protoname) + 1, fd); + proto_close(mconn); + if (error != 0) { + errno = error; + return (-1); + } + return (0); +} + +int +proto_wrap(const char *protoname, bool client, int fd, + struct proto_conn **newconnp) +{ + struct proto *proto; + struct proto_conn *newconn; + int error; + + TAILQ_FOREACH(proto, &protos, prt_next) { + if (strcmp(proto->prt_name, protoname) == 0) + break; + } + if (proto == NULL) { + errno = EINVAL; + return (-1); + } + + newconn = proto_alloc(proto, + client ? PROTO_SIDE_CLIENT : PROTO_SIDE_SERVER_WORK); + if (newconn == NULL) + return (-1); + PJDLOG_ASSERT(newconn->pc_proto->prt_wrap != NULL); + error = newconn->pc_proto->prt_wrap(fd, client, &newconn->pc_ctx); + if (error != 0) { + proto_free(newconn); + errno = error; + return (-1); + } + + *newconnp = newconn; + + return (0); +} + +int +proto_connection_recv(const struct proto_conn *conn, bool client, + struct proto_conn **newconnp) +{ + char protoname[128]; + int error, fd; + + PJDLOG_ASSERT(conn != NULL); + PJDLOG_ASSERT(conn->pc_magic == PROTO_CONN_MAGIC); + PJDLOG_ASSERT(conn->pc_proto != NULL); + PJDLOG_ASSERT(conn->pc_proto->prt_recv != NULL); + PJDLOG_ASSERT(newconnp != NULL); + + bzero(protoname, sizeof(protoname)); + + error = conn->pc_proto->prt_recv(conn->pc_ctx, + (unsigned char *)protoname, sizeof(protoname) - 1, &fd); + if (error != 0) { + errno = error; + return (-1); + } + + PJDLOG_ASSERT(fd >= 0); + + return (proto_wrap(protoname, client, fd, newconnp)); +} + +int +proto_descriptor(const struct proto_conn *conn) +{ + + PJDLOG_ASSERT(conn != NULL); + PJDLOG_ASSERT(conn->pc_magic == PROTO_CONN_MAGIC); + PJDLOG_ASSERT(conn->pc_proto != NULL); + PJDLOG_ASSERT(conn->pc_proto->prt_descriptor != NULL); + + return (conn->pc_proto->prt_descriptor(conn->pc_ctx)); +} + +bool +proto_address_match(const struct proto_conn *conn, const char *addr) +{ + + PJDLOG_ASSERT(conn != NULL); + PJDLOG_ASSERT(conn->pc_magic == PROTO_CONN_MAGIC); + PJDLOG_ASSERT(conn->pc_proto != NULL); + PJDLOG_ASSERT(conn->pc_proto->prt_address_match != NULL); + + return (conn->pc_proto->prt_address_match(conn->pc_ctx, addr)); +} + +void +proto_local_address(const struct proto_conn *conn, char *addr, size_t size) +{ + + PJDLOG_ASSERT(conn != NULL); + PJDLOG_ASSERT(conn->pc_magic == PROTO_CONN_MAGIC); + PJDLOG_ASSERT(conn->pc_proto != NULL); + PJDLOG_ASSERT(conn->pc_proto->prt_local_address != NULL); + + conn->pc_proto->prt_local_address(conn->pc_ctx, addr, size); +} + +void +proto_remote_address(const struct proto_conn *conn, char *addr, size_t size) +{ + + PJDLOG_ASSERT(conn != NULL); + PJDLOG_ASSERT(conn->pc_magic == PROTO_CONN_MAGIC); + PJDLOG_ASSERT(conn->pc_proto != NULL); + PJDLOG_ASSERT(conn->pc_proto->prt_remote_address != NULL); + + conn->pc_proto->prt_remote_address(conn->pc_ctx, addr, size); +} + +int +proto_timeout(const struct proto_conn *conn, int timeout) +{ + struct timeval tv; + int fd; + + PJDLOG_ASSERT(conn != NULL); + PJDLOG_ASSERT(conn->pc_magic == PROTO_CONN_MAGIC); + PJDLOG_ASSERT(conn->pc_proto != NULL); + + fd = proto_descriptor(conn); + if (fd < 0) + return (-1); + + tv.tv_sec = timeout; + tv.tv_usec = 0; + if (setsockopt(fd, SOL_SOCKET, SO_SNDTIMEO, &tv, sizeof(tv)) < 0) + return (-1); + if (setsockopt(fd, SOL_SOCKET, SO_RCVTIMEO, &tv, sizeof(tv)) < 0) + return (-1); + + return (0); +} + +void +proto_close(struct proto_conn *conn) +{ + + PJDLOG_ASSERT(conn != NULL); + PJDLOG_ASSERT(conn->pc_magic == PROTO_CONN_MAGIC); + PJDLOG_ASSERT(conn->pc_proto != NULL); + PJDLOG_ASSERT(conn->pc_proto->prt_close != NULL); + + conn->pc_proto->prt_close(conn->pc_ctx); + proto_free(conn); +} + +int +proto_exec(int argc, char *argv[]) +{ + struct proto *proto; + int error; + + if (argc == 0) { + errno = EINVAL; + return (-1); + } + TAILQ_FOREACH(proto, &protos, prt_next) { + if (strcmp(proto->prt_name, argv[0]) == 0) + break; + } + if (proto == NULL) { + errno = EINVAL; + return (-1); + } + if (proto->prt_exec == NULL) { + errno = EOPNOTSUPP; + return (-1); + } + error = proto->prt_exec(argc, argv); + if (error != 0) { + errno = error; + return (-1); + } + /* NOTREACHED */ + return (0); +} + +struct proto_nvpair { + char *pnv_name; + char *pnv_value; + TAILQ_ENTRY(proto_nvpair) pnv_next; +}; + +static TAILQ_HEAD(, proto_nvpair) proto_nvpairs = + TAILQ_HEAD_INITIALIZER(proto_nvpairs); + +int +proto_set(const char *name, const char *value) +{ + struct proto_nvpair *pnv; + + TAILQ_FOREACH(pnv, &proto_nvpairs, pnv_next) { + if (strcmp(pnv->pnv_name, name) == 0) + break; + } + if (pnv != NULL) { + TAILQ_REMOVE(&proto_nvpairs, pnv, pnv_next); + free(pnv->pnv_value); + } else { + pnv = malloc(sizeof(*pnv)); + if (pnv == NULL) + return (-1); + pnv->pnv_name = strdup(name); + if (pnv->pnv_name == NULL) { + free(pnv); + return (-1); + } + } + pnv->pnv_value = strdup(value); + if (pnv->pnv_value == NULL) { + free(pnv->pnv_name); + free(pnv); + return (-1); + } + TAILQ_INSERT_TAIL(&proto_nvpairs, pnv, pnv_next); + return (0); +} + +const char * +proto_get(const char *name) +{ + struct proto_nvpair *pnv; + + TAILQ_FOREACH(pnv, &proto_nvpairs, pnv_next) { + if (strcmp(pnv->pnv_name, name) == 0) + break; + } + if (pnv != NULL) + return (pnv->pnv_value); + return (NULL); +} diff --git a/contrib/openbsm/bin/auditdistd/proto.h b/contrib/openbsm/bin/auditdistd/proto.h new file mode 100644 index 0000000..79047b0 --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/proto.h @@ -0,0 +1,63 @@ +/*- + * Copyright (c) 2009-2010 The FreeBSD Foundation + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/proto.h#1 $ + */ + +#ifndef _PROTO_H_ +#define _PROTO_H_ + +#include <stdbool.h> /* bool */ +#include <stdlib.h> /* size_t */ + +struct proto_conn; + +int proto_connect(const char *srcaddr, const char *dstaddr, int timeout, + struct proto_conn **connp); +int proto_connect_wait(struct proto_conn *conn, int timeout); +int proto_server(const char *addr, struct proto_conn **connp); +int proto_accept(struct proto_conn *conn, struct proto_conn **newconnp); +int proto_send(const struct proto_conn *conn, const void *data, size_t size); +int proto_recv(const struct proto_conn *conn, void *data, size_t size); +int proto_connection_send(const struct proto_conn *conn, + struct proto_conn *mconn); +int proto_connection_recv(const struct proto_conn *conn, bool client, + struct proto_conn **newconnp); +int proto_descriptor(const struct proto_conn *conn); +bool proto_address_match(const struct proto_conn *conn, const char *addr); +void proto_local_address(const struct proto_conn *conn, char *addr, + size_t size); +void proto_remote_address(const struct proto_conn *conn, char *addr, + size_t size); +int proto_timeout(const struct proto_conn *conn, int timeout); +void proto_close(struct proto_conn *conn); +int proto_exec(int argc, char *argv[]); +int proto_set(const char *name, const char *value); +const char *proto_get(const char *name); + +#endif /* !_PROTO_H_ */ diff --git a/contrib/openbsm/bin/auditdistd/proto_common.c b/contrib/openbsm/bin/auditdistd/proto_common.c new file mode 100644 index 0000000..0fa4d3c --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/proto_common.c @@ -0,0 +1,233 @@ +/*- + * Copyright (c) 2009-2010 The FreeBSD Foundation + * Copyright (c) 2011 Pawel Jakub Dawidek <pawel@dawidek.net> + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/proto_common.c#1 $ + */ + +#include <sys/types.h> +#include <sys/socket.h> + +#include <errno.h> +#include <fcntl.h> +#include <stdbool.h> +#include <stdlib.h> +#include <strings.h> +#include <unistd.h> + +#include <compat/compat.h> + +#include "pjdlog.h" +#include "proto_impl.h" + +/* Maximum size of packet we want to use when sending data. */ +#ifndef MAX_SEND_SIZE +#define MAX_SEND_SIZE 32768 +#endif + +static bool +blocking_socket(int sock) +{ + int flags; + + flags = fcntl(sock, F_GETFL); + PJDLOG_ASSERT(flags >= 0); + return ((flags & O_NONBLOCK) == 0); +} + +static int +proto_descriptor_send(int sock, int fd) +{ + unsigned char ctrl[CMSG_SPACE(sizeof(fd))]; + struct msghdr msg; + struct cmsghdr *cmsg; + + PJDLOG_ASSERT(sock >= 0); + PJDLOG_ASSERT(fd >= 0); + + bzero(&msg, sizeof(msg)); + bzero(&ctrl, sizeof(ctrl)); + + msg.msg_iov = NULL; + msg.msg_iovlen = 0; + msg.msg_control = ctrl; + msg.msg_controllen = sizeof(ctrl); + + cmsg = CMSG_FIRSTHDR(&msg); + cmsg->cmsg_level = SOL_SOCKET; + cmsg->cmsg_type = SCM_RIGHTS; + cmsg->cmsg_len = CMSG_LEN(sizeof(fd)); + bcopy(&fd, CMSG_DATA(cmsg), sizeof(fd)); + + if (sendmsg(sock, &msg, 0) == -1) + return (errno); + + return (0); +} + +int +proto_common_send(int sock, const unsigned char *data, size_t size, int fd) +{ + ssize_t done; + size_t sendsize; + int errcount = 0; + + PJDLOG_ASSERT(sock >= 0); + + if (data == NULL) { + /* The caller is just trying to decide about direction. */ + + PJDLOG_ASSERT(size == 0); + + if (shutdown(sock, SHUT_RD) == -1) + return (errno); + return (0); + } + + PJDLOG_ASSERT(data != NULL); + PJDLOG_ASSERT(size > 0); + + do { + sendsize = size < MAX_SEND_SIZE ? size : MAX_SEND_SIZE; + done = send(sock, data, sendsize, MSG_NOSIGNAL); + if (done == 0) { + return (ENOTCONN); + } else if (done < 0) { + if (errno == EINTR) + continue; + if (errno == ENOBUFS) { + /* + * If there are no buffers we retry. + * After each try we increase delay before the + * next one and we give up after fifteen times. + * This gives 11s of total wait time. + */ + if (errcount == 15) { + pjdlog_warning("Getting ENOBUFS errors for 11s on send(), giving up."); + } else { + if (errcount == 0) + pjdlog_warning("Got ENOBUFS error on send(), retrying for a bit."); + errcount++; + usleep(100000 * errcount); + continue; + } + } + /* + * If this is blocking socket and we got EAGAIN, this + * means the request timed out. Translate errno to + * ETIMEDOUT, to give administrator a hint to + * eventually increase timeout. + */ + if (errno == EAGAIN && blocking_socket(sock)) + errno = ETIMEDOUT; + return (errno); + } + data += done; + size -= done; + } while (size > 0); + if (errcount > 0) { + pjdlog_info("Data sent successfully after %d ENOBUFS error%s.", + errcount, errcount == 1 ? "" : "s"); + } + + if (fd == -1) + return (0); + return (proto_descriptor_send(sock, fd)); +} + +static int +proto_descriptor_recv(int sock, int *fdp) +{ + unsigned char ctrl[CMSG_SPACE(sizeof(*fdp))]; + struct msghdr msg; + struct cmsghdr *cmsg; + + PJDLOG_ASSERT(sock >= 0); + PJDLOG_ASSERT(fdp != NULL); + + bzero(&msg, sizeof(msg)); + bzero(&ctrl, sizeof(ctrl)); + + msg.msg_iov = NULL; + msg.msg_iovlen = 0; + msg.msg_control = ctrl; + msg.msg_controllen = sizeof(ctrl); + + if (recvmsg(sock, &msg, 0) == -1) + return (errno); + + cmsg = CMSG_FIRSTHDR(&msg); + if (cmsg->cmsg_level != SOL_SOCKET || + cmsg->cmsg_type != SCM_RIGHTS) { + return (EINVAL); + } + bcopy(CMSG_DATA(cmsg), fdp, sizeof(*fdp)); + + return (0); +} + +int +proto_common_recv(int sock, unsigned char *data, size_t size, int *fdp) +{ + ssize_t done; + + PJDLOG_ASSERT(sock >= 0); + + if (data == NULL) { + /* The caller is just trying to decide about direction. */ + + PJDLOG_ASSERT(size == 0); + + if (shutdown(sock, SHUT_WR) == -1) + return (errno); + return (0); + } + + PJDLOG_ASSERT(data != NULL); + PJDLOG_ASSERT(size > 0); + + do { + done = recv(sock, data, size, MSG_WAITALL); + } while (done == -1 && errno == EINTR); + if (done == 0) { + return (ENOTCONN); + } else if (done < 0) { + /* + * If this is blocking socket and we got EAGAIN, this + * means the request timed out. Translate errno to + * ETIMEDOUT, to give administrator a hint to + * eventually increase timeout. + */ + if (errno == EAGAIN && blocking_socket(sock)) + errno = ETIMEDOUT; + return (errno); + } + if (fdp == NULL) + return (0); + return (proto_descriptor_recv(sock, fdp)); +} diff --git a/contrib/openbsm/bin/auditdistd/proto_impl.h b/contrib/openbsm/bin/auditdistd/proto_impl.h new file mode 100644 index 0000000..c2ce2d9 --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/proto_impl.h @@ -0,0 +1,84 @@ +/*- + * Copyright (c) 2009-2010 The FreeBSD Foundation + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/proto_impl.h#1 $ + */ + +#ifndef _PROTO_IMPL_H_ +#define _PROTO_IMPL_H_ + +#include <sys/queue.h> + +#include <stdbool.h> /* bool */ +#include <stdlib.h> /* size_t */ + +#define __constructor __attribute__((constructor)) + +struct proto_conn; + +typedef int prt_connect_t(const char *, const char *, int, void **); +typedef int prt_connect_wait_t(void *, int); +typedef int prt_server_t(const char *, void **); +typedef int prt_accept_t(void *, void **); +typedef int prt_wrap_t(int, bool, void **); +typedef int prt_send_t(void *, const unsigned char *, size_t, int); +typedef int prt_recv_t(void *, unsigned char *, size_t, int *); +typedef int prt_descriptor_t(const void *); +typedef bool prt_address_match_t(const void *, const char *); +typedef void prt_local_address_t(const void *, char *, size_t); +typedef void prt_remote_address_t(const void *, char *, size_t); +typedef void prt_close_t(void *); +typedef int prt_exec_t(int, char *[]); + +struct proto { + const char *prt_name; + prt_connect_t *prt_connect; + prt_connect_wait_t *prt_connect_wait; + prt_server_t *prt_server; + prt_accept_t *prt_accept; + prt_wrap_t *prt_wrap; + prt_send_t *prt_send; + prt_recv_t *prt_recv; + prt_descriptor_t *prt_descriptor; + prt_address_match_t *prt_address_match; + prt_local_address_t *prt_local_address; + prt_remote_address_t *prt_remote_address; + prt_close_t *prt_close; + prt_exec_t *prt_exec; + TAILQ_ENTRY(proto) prt_next; +}; + +void proto_register(struct proto *proto, bool isdefault); + +int proto_wrap(const char *protoname, bool client, int fd, + struct proto_conn **newconnp); + +int proto_common_send(int sock, const unsigned char *data, size_t size, int fd); +int proto_common_recv(int sock, unsigned char *data, size_t size, int *fdp); + +#endif /* !_PROTO_IMPL_H_ */ diff --git a/contrib/openbsm/bin/auditdistd/proto_socketpair.c b/contrib/openbsm/bin/auditdistd/proto_socketpair.c new file mode 100644 index 0000000..8d04c49 --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/proto_socketpair.c @@ -0,0 +1,266 @@ +/*- + * Copyright (c) 2009-2010 The FreeBSD Foundation + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/proto_socketpair.c#1 $ + */ + +#include <sys/types.h> +#include <sys/socket.h> + +#include <errno.h> +#include <stdbool.h> +#include <stdint.h> +#include <stdio.h> +#include <string.h> +#include <unistd.h> + +#include "pjdlog.h" +#include "proto_impl.h" + +#define SP_CTX_MAGIC 0x50c3741 +struct sp_ctx { + int sp_magic; + int sp_fd[2]; + int sp_side; +#define SP_SIDE_UNDEF 0 +#define SP_SIDE_CLIENT 1 +#define SP_SIDE_SERVER 2 +}; + +static void sp_close(void *ctx); + +static int +sp_connect(const char *srcaddr, const char *dstaddr, int timeout, void **ctxp) +{ + struct sp_ctx *spctx; + int error; + + PJDLOG_ASSERT(dstaddr != NULL); + PJDLOG_ASSERT(timeout >= -1); + + if (strcmp(dstaddr, "socketpair://") != 0) + return (-1); + + PJDLOG_ASSERT(srcaddr == NULL); + + spctx = malloc(sizeof(*spctx)); + if (spctx == NULL) + return (errno); + + if (socketpair(PF_UNIX, SOCK_STREAM, 0, spctx->sp_fd) == -1) { + error = errno; + free(spctx); + return (error); + } + + spctx->sp_side = SP_SIDE_UNDEF; + spctx->sp_magic = SP_CTX_MAGIC; + *ctxp = spctx; + + return (0); +} + +static int +sp_wrap(int fd, bool client, void **ctxp) +{ + struct sp_ctx *spctx; + + PJDLOG_ASSERT(fd >= 0); + + spctx = malloc(sizeof(*spctx)); + if (spctx == NULL) + return (errno); + + if (client) { + spctx->sp_side = SP_SIDE_CLIENT; + spctx->sp_fd[0] = fd; + spctx->sp_fd[1] = -1; + } else { + spctx->sp_side = SP_SIDE_SERVER; + spctx->sp_fd[0] = -1; + spctx->sp_fd[1] = fd; + } + spctx->sp_magic = SP_CTX_MAGIC; + *ctxp = spctx; + + return (0); +} + +static int +sp_send(void *ctx, const unsigned char *data, size_t size, int fd) +{ + struct sp_ctx *spctx = ctx; + int sock; + + PJDLOG_ASSERT(spctx != NULL); + PJDLOG_ASSERT(spctx->sp_magic == SP_CTX_MAGIC); + + switch (spctx->sp_side) { + case SP_SIDE_UNDEF: + /* + * If the first operation done by the caller is proto_send(), + * we assume this is the client. + */ + /* FALLTHROUGH */ + spctx->sp_side = SP_SIDE_CLIENT; + /* Close other end. */ + close(spctx->sp_fd[1]); + spctx->sp_fd[1] = -1; + case SP_SIDE_CLIENT: + PJDLOG_ASSERT(spctx->sp_fd[0] >= 0); + sock = spctx->sp_fd[0]; + break; + case SP_SIDE_SERVER: + PJDLOG_ASSERT(spctx->sp_fd[1] >= 0); + sock = spctx->sp_fd[1]; + break; + default: + PJDLOG_ABORT("Invalid socket side (%d).", spctx->sp_side); + } + + /* Someone is just trying to decide about side. */ + if (data == NULL) + return (0); + + return (proto_common_send(sock, data, size, fd)); +} + +static int +sp_recv(void *ctx, unsigned char *data, size_t size, int *fdp) +{ + struct sp_ctx *spctx = ctx; + int sock; + + PJDLOG_ASSERT(spctx != NULL); + PJDLOG_ASSERT(spctx->sp_magic == SP_CTX_MAGIC); + + switch (spctx->sp_side) { + case SP_SIDE_UNDEF: + /* + * If the first operation done by the caller is proto_recv(), + * we assume this is the server. + */ + /* FALLTHROUGH */ + spctx->sp_side = SP_SIDE_SERVER; + /* Close other end. */ + close(spctx->sp_fd[0]); + spctx->sp_fd[0] = -1; + case SP_SIDE_SERVER: + PJDLOG_ASSERT(spctx->sp_fd[1] >= 0); + sock = spctx->sp_fd[1]; + break; + case SP_SIDE_CLIENT: + PJDLOG_ASSERT(spctx->sp_fd[0] >= 0); + sock = spctx->sp_fd[0]; + break; + default: + PJDLOG_ABORT("Invalid socket side (%d).", spctx->sp_side); + } + + /* Someone is just trying to decide about side. */ + if (data == NULL) + return (0); + + return (proto_common_recv(sock, data, size, fdp)); +} + +static int +sp_descriptor(const void *ctx) +{ + const struct sp_ctx *spctx = ctx; + + PJDLOG_ASSERT(spctx != NULL); + PJDLOG_ASSERT(spctx->sp_magic == SP_CTX_MAGIC); + PJDLOG_ASSERT(spctx->sp_side == SP_SIDE_CLIENT || + spctx->sp_side == SP_SIDE_SERVER); + + switch (spctx->sp_side) { + case SP_SIDE_CLIENT: + PJDLOG_ASSERT(spctx->sp_fd[0] >= 0); + return (spctx->sp_fd[0]); + case SP_SIDE_SERVER: + PJDLOG_ASSERT(spctx->sp_fd[1] >= 0); + return (spctx->sp_fd[1]); + } + + PJDLOG_ABORT("Invalid socket side (%d).", spctx->sp_side); +} + +static void +sp_close(void *ctx) +{ + struct sp_ctx *spctx = ctx; + + PJDLOG_ASSERT(spctx != NULL); + PJDLOG_ASSERT(spctx->sp_magic == SP_CTX_MAGIC); + + switch (spctx->sp_side) { + case SP_SIDE_UNDEF: + PJDLOG_ASSERT(spctx->sp_fd[0] >= 0); + close(spctx->sp_fd[0]); + spctx->sp_fd[0] = -1; + PJDLOG_ASSERT(spctx->sp_fd[1] >= 0); + close(spctx->sp_fd[1]); + spctx->sp_fd[1] = -1; + break; + case SP_SIDE_CLIENT: + PJDLOG_ASSERT(spctx->sp_fd[0] >= 0); + close(spctx->sp_fd[0]); + spctx->sp_fd[0] = -1; + PJDLOG_ASSERT(spctx->sp_fd[1] == -1); + break; + case SP_SIDE_SERVER: + PJDLOG_ASSERT(spctx->sp_fd[1] >= 0); + close(spctx->sp_fd[1]); + spctx->sp_fd[1] = -1; + PJDLOG_ASSERT(spctx->sp_fd[0] == -1); + break; + default: + PJDLOG_ABORT("Invalid socket side (%d).", spctx->sp_side); + } + + spctx->sp_magic = 0; + free(spctx); +} + +static struct proto sp_proto = { + .prt_name = "socketpair", + .prt_connect = sp_connect, + .prt_wrap = sp_wrap, + .prt_send = sp_send, + .prt_recv = sp_recv, + .prt_descriptor = sp_descriptor, + .prt_close = sp_close +}; + +static __constructor void +sp_ctor(void) +{ + + proto_register(&sp_proto, false); +} diff --git a/contrib/openbsm/bin/auditdistd/proto_tcp.c b/contrib/openbsm/bin/auditdistd/proto_tcp.c new file mode 100644 index 0000000..74d5cd4 --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/proto_tcp.c @@ -0,0 +1,723 @@ +/*- + * Copyright (c) 2009-2010 The FreeBSD Foundation + * Copyright (c) 2011 Pawel Jakub Dawidek <pawel@dawidek.net> + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/proto_tcp.c#2 $ + */ + +#include <config/config.h> + +#include <sys/param.h> /* MAXHOSTNAMELEN */ +#include <sys/socket.h> + +#include <arpa/inet.h> + +#include <netinet/in.h> +#include <netinet/tcp.h> + +#include <errno.h> +#include <fcntl.h> +#include <netdb.h> +#include <stdbool.h> +#include <stdint.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> + +#ifndef HAVE_STRLCPY +#include <compat/strlcpy.h> +#endif + +#include "pjdlog.h" +#include "proto_impl.h" +#include "subr.h" + +#define TCP_CTX_MAGIC 0x7c41c +struct tcp_ctx { + int tc_magic; + struct sockaddr_storage tc_sa; + int tc_fd; + int tc_side; +#define TCP_SIDE_CLIENT 0 +#define TCP_SIDE_SERVER_LISTEN 1 +#define TCP_SIDE_SERVER_WORK 2 + bool tc_wait_called; +}; + +static int tcp_connect_wait(void *ctx, int timeout); +static void tcp_close(void *ctx); + +/* + * Function converts the given string to unsigned number. + */ +static int +numfromstr(const char *str, intmax_t minnum, intmax_t maxnum, intmax_t *nump) +{ + intmax_t digit, num; + + if (str[0] == '\0') + goto invalid; /* Empty string. */ + num = 0; + for (; *str != '\0'; str++) { + if (*str < '0' || *str > '9') + goto invalid; /* Non-digit character. */ + digit = *str - '0'; + if (num > num * 10 + digit) + goto invalid; /* Overflow. */ + num = num * 10 + digit; + if (num > maxnum) + goto invalid; /* Too big. */ + } + if (num < minnum) + goto invalid; /* Too small. */ + *nump = num; + return (0); +invalid: + errno = EINVAL; + return (-1); +} + +static int +tcp_addr(const char *addr, int defport, struct sockaddr_storage *sap) +{ + char iporhost[MAXHOSTNAMELEN], portstr[6]; + struct addrinfo hints; + struct addrinfo *res; + const char *pp; + intmax_t port; + size_t size; + int error; + + if (addr == NULL) + return (-1); + + bzero(&hints, sizeof(hints)); + hints.ai_flags = AI_ADDRCONFIG | AI_NUMERICSERV; + hints.ai_family = PF_UNSPEC; + hints.ai_socktype = SOCK_STREAM; + hints.ai_protocol = IPPROTO_TCP; + + if (strncasecmp(addr, "tcp4://", 7) == 0) { + addr += 7; + hints.ai_family = PF_INET; + } else if (strncasecmp(addr, "tcp6://", 7) == 0) { + addr += 7; + hints.ai_family = PF_INET6; + } else if (strncasecmp(addr, "tcp://", 6) == 0) { + addr += 6; + } else { + /* + * Because TCP is the default assume IP or host is given without + * prefix. + */ + } + + /* + * Extract optional port. + * There are three cases to consider. + * 1. hostname with port, eg. freefall.freebsd.org:8457 + * 2. IPv4 address with port, eg. 192.168.0.101:8457 + * 3. IPv6 address with port, eg. [fe80::1]:8457 + * We discover IPv6 address by checking for two colons and if port is + * given, the address has to start with [. + */ + pp = NULL; + if (strchr(addr, ':') != strrchr(addr, ':')) { + if (addr[0] == '[') + pp = strrchr(addr, ':'); + } else { + pp = strrchr(addr, ':'); + } + if (pp == NULL) { + /* Port not given, use the default. */ + port = defport; + } else { + if (numfromstr(pp + 1, 1, 65535, &port) < 0) + return (errno); + } + (void)snprintf(portstr, sizeof(portstr), "%jd", (intmax_t)port); + /* Extract host name or IP address. */ + if (pp == NULL) { + size = sizeof(iporhost); + if (strlcpy(iporhost, addr, size) >= size) + return (ENAMETOOLONG); + } else if (addr[0] == '[' && pp[-1] == ']') { + size = (size_t)(pp - addr - 2 + 1); + if (size > sizeof(iporhost)) + return (ENAMETOOLONG); + (void)strlcpy(iporhost, addr + 1, size); + } else { + size = (size_t)(pp - addr + 1); + if (size > sizeof(iporhost)) + return (ENAMETOOLONG); + (void)strlcpy(iporhost, addr, size); + } + + error = getaddrinfo(iporhost, portstr, &hints, &res); + if (error != 0) { + pjdlog_debug(1, "getaddrinfo(%s, %s) failed: %s.", iporhost, + portstr, gai_strerror(error)); + return (EINVAL); + } + if (res == NULL) + return (ENOENT); + + memcpy(sap, res->ai_addr, res->ai_addrlen); + + freeaddrinfo(res); + + return (0); +} + +static int +tcp_setup_new(const char *addr, int side, struct tcp_ctx **tctxp) +{ + struct tcp_ctx *tctx; + int error, nodelay; + + PJDLOG_ASSERT(addr != NULL); + PJDLOG_ASSERT(side == TCP_SIDE_CLIENT || + side == TCP_SIDE_SERVER_LISTEN); + PJDLOG_ASSERT(tctxp != NULL); + + tctx = malloc(sizeof(*tctx)); + if (tctx == NULL) + return (errno); + + /* Parse given address. */ + error = tcp_addr(addr, atoi(proto_get("tcp:port")), &tctx->tc_sa); + if (error != 0) { + free(tctx); + return (error); + } + + PJDLOG_ASSERT(tctx->tc_sa.ss_family != AF_UNSPEC); + + tctx->tc_fd = socket(tctx->tc_sa.ss_family, SOCK_STREAM, 0); + if (tctx->tc_fd == -1) { + error = errno; + free(tctx); + return (error); + } + + PJDLOG_ASSERT(tctx->tc_sa.ss_family != AF_UNSPEC); + + /* Socket settings. */ + nodelay = 1; + if (setsockopt(tctx->tc_fd, IPPROTO_TCP, TCP_NODELAY, &nodelay, + sizeof(nodelay)) == -1) { + pjdlog_errno(LOG_WARNING, "Unable to set TCP_NOELAY"); + } + + tctx->tc_wait_called = (side == TCP_SIDE_CLIENT ? false : true); + tctx->tc_side = side; + tctx->tc_magic = TCP_CTX_MAGIC; + *tctxp = tctx; + + return (0); +} + +static socklen_t +sockaddr_len(const struct sockaddr_storage *ss) +{ + +#ifdef HAVE_SOCKADDR_STORAGE_SS_LEN + return (ss->ss_len); +#else + switch (ss->ss_family) { + case AF_INET: + return (sizeof(struct sockaddr_in)); + case AF_INET6: + return (sizeof(struct sockaddr_in6)); + default: + PJDLOG_ABORT("Unexpected family %hhu.", ss->ss_family); + } +#endif +} + +static int +tcp_connect(const char *srcaddr, const char *dstaddr, int timeout, void **ctxp) +{ + struct tcp_ctx *tctx; + struct sockaddr_storage sa; + int error, flags, ret; + + PJDLOG_ASSERT(srcaddr == NULL || srcaddr[0] != '\0'); + PJDLOG_ASSERT(dstaddr != NULL); + PJDLOG_ASSERT(timeout >= -1); + + error = tcp_setup_new(dstaddr, TCP_SIDE_CLIENT, &tctx); + if (error != 0) + return (error); + if (srcaddr != NULL) { + error = tcp_addr(srcaddr, 0, &sa); + if (error != 0) + goto fail; + if (bind(tctx->tc_fd, (struct sockaddr *)&sa, + sockaddr_len(&sa)) == -1) { + error = errno; + goto fail; + } + } + + flags = fcntl(tctx->tc_fd, F_GETFL); + if (flags == -1) { + error = errno; + pjdlog_common(LOG_DEBUG, 1, errno, "fcntl(F_GETFL) failed"); + goto fail; + } + /* + * We make socket non-blocking so we can handle connection timeout + * manually. + */ + flags |= O_NONBLOCK; + if (fcntl(tctx->tc_fd, F_SETFL, flags) == -1) { + error = errno; + pjdlog_common(LOG_DEBUG, 1, errno, + "fcntl(F_SETFL, O_NONBLOCK) failed"); + goto fail; + } + + ret = connect(tctx->tc_fd, (struct sockaddr *)&tctx->tc_sa, + sockaddr_len(&tctx->tc_sa)); + if (ret == -1 && errno != EINPROGRESS) { + error = errno; + pjdlog_common(LOG_DEBUG, 1, errno, "connect() failed"); + goto fail; + } + + if (timeout >= 0) { + if (ret == -1) { + /* Connection still in progress. Wait for it. */ + error = tcp_connect_wait(tctx, timeout); + if (error != 0) + goto fail; + } else { + /* Connection already complete. */ + flags &= ~O_NONBLOCK; + if (fcntl(tctx->tc_fd, F_SETFL, flags) == -1) { + error = errno; + pjdlog_common(LOG_DEBUG, 1, errno, + "fcntl(F_SETFL, ~O_NONBLOCK) failed"); + goto fail; + } + } + } + + *ctxp = tctx; + return (0); +fail: + tcp_close(tctx); + return (error); +} + +static int +tcp_connect_wait(void *ctx, int timeout) +{ + struct tcp_ctx *tctx = ctx; + struct timeval tv; + fd_set fdset; + socklen_t esize; + int error, flags, ret; + + PJDLOG_ASSERT(tctx != NULL); + PJDLOG_ASSERT(tctx->tc_magic == TCP_CTX_MAGIC); + PJDLOG_ASSERT(tctx->tc_side == TCP_SIDE_CLIENT); + PJDLOG_ASSERT(!tctx->tc_wait_called); + PJDLOG_ASSERT(tctx->tc_fd >= 0); + PJDLOG_ASSERT(timeout >= 0); + + tv.tv_sec = timeout; + tv.tv_usec = 0; +again: + FD_ZERO(&fdset); + FD_SET(tctx->tc_fd, &fdset); + ret = select(tctx->tc_fd + 1, NULL, &fdset, NULL, &tv); + if (ret == 0) { + error = ETIMEDOUT; + goto done; + } else if (ret == -1) { + if (errno == EINTR) + goto again; + error = errno; + pjdlog_common(LOG_DEBUG, 1, errno, "select() failed"); + goto done; + } + PJDLOG_ASSERT(ret > 0); + PJDLOG_ASSERT(FD_ISSET(tctx->tc_fd, &fdset)); + esize = sizeof(error); + if (getsockopt(tctx->tc_fd, SOL_SOCKET, SO_ERROR, &error, + &esize) == -1) { + error = errno; + pjdlog_common(LOG_DEBUG, 1, errno, + "getsockopt(SO_ERROR) failed"); + goto done; + } + if (error != 0) { + pjdlog_common(LOG_DEBUG, 1, error, + "getsockopt(SO_ERROR) returned error"); + goto done; + } + error = 0; + tctx->tc_wait_called = true; +done: + flags = fcntl(tctx->tc_fd, F_GETFL); + if (flags == -1) { + if (error == 0) + error = errno; + pjdlog_common(LOG_DEBUG, 1, errno, "fcntl(F_GETFL) failed"); + return (error); + } + flags &= ~O_NONBLOCK; + if (fcntl(tctx->tc_fd, F_SETFL, flags) == -1) { + if (error == 0) + error = errno; + pjdlog_common(LOG_DEBUG, 1, errno, + "fcntl(F_SETFL, ~O_NONBLOCK) failed"); + } + return (error); +} + +static int +tcp_server(const char *addr, void **ctxp) +{ + struct tcp_ctx *tctx; + int error, val; + + error = tcp_setup_new(addr, TCP_SIDE_SERVER_LISTEN, &tctx); + if (error != 0) + return (error); + + val = 1; + /* Ignore failure. */ + (void)setsockopt(tctx->tc_fd, SOL_SOCKET, SO_REUSEADDR, &val, + sizeof(val)); + + PJDLOG_ASSERT(tctx->tc_sa.ss_family != AF_UNSPEC); + + if (bind(tctx->tc_fd, (struct sockaddr *)&tctx->tc_sa, + sockaddr_len(&tctx->tc_sa)) == -1) { + error = errno; + tcp_close(tctx); + return (error); + } + if (listen(tctx->tc_fd, 8) == -1) { + error = errno; + tcp_close(tctx); + return (error); + } + + *ctxp = tctx; + + return (0); +} + +static int +tcp_accept(void *ctx, void **newctxp) +{ + struct tcp_ctx *tctx = ctx; + struct tcp_ctx *newtctx; + socklen_t fromlen; + int ret; + + PJDLOG_ASSERT(tctx != NULL); + PJDLOG_ASSERT(tctx->tc_magic == TCP_CTX_MAGIC); + PJDLOG_ASSERT(tctx->tc_side == TCP_SIDE_SERVER_LISTEN); + PJDLOG_ASSERT(tctx->tc_fd >= 0); + PJDLOG_ASSERT(tctx->tc_sa.ss_family != AF_UNSPEC); + + newtctx = malloc(sizeof(*newtctx)); + if (newtctx == NULL) + return (errno); + + fromlen = sockaddr_len(&tctx->tc_sa); + newtctx->tc_fd = accept(tctx->tc_fd, (struct sockaddr *)&tctx->tc_sa, + &fromlen); + if (newtctx->tc_fd < 0) { + ret = errno; + free(newtctx); + return (ret); + } + + newtctx->tc_wait_called = true; + newtctx->tc_side = TCP_SIDE_SERVER_WORK; + newtctx->tc_magic = TCP_CTX_MAGIC; + *newctxp = newtctx; + + return (0); +} + +static int +tcp_wrap(int fd, bool client, void **ctxp) +{ + struct tcp_ctx *tctx; + + PJDLOG_ASSERT(fd >= 0); + PJDLOG_ASSERT(ctxp != NULL); + + tctx = malloc(sizeof(*tctx)); + if (tctx == NULL) + return (errno); + + tctx->tc_fd = fd; + tctx->tc_sa.ss_family = AF_UNSPEC; + tctx->tc_wait_called = (client ? false : true); + tctx->tc_side = (client ? TCP_SIDE_CLIENT : TCP_SIDE_SERVER_WORK); + tctx->tc_magic = TCP_CTX_MAGIC; + *ctxp = tctx; + + return (0); +} + +static int +tcp_send(void *ctx, const unsigned char *data, size_t size, int fd) +{ + struct tcp_ctx *tctx = ctx; + + PJDLOG_ASSERT(tctx != NULL); + PJDLOG_ASSERT(tctx->tc_magic == TCP_CTX_MAGIC); + PJDLOG_ASSERT(tctx->tc_side == TCP_SIDE_CLIENT || + tctx->tc_side == TCP_SIDE_SERVER_WORK); + PJDLOG_ASSERT(tctx->tc_wait_called); + PJDLOG_ASSERT(tctx->tc_fd >= 0); + PJDLOG_ASSERT(fd == -1); + + return (proto_common_send(tctx->tc_fd, data, size, -1)); +} + +static int +tcp_recv(void *ctx, unsigned char *data, size_t size, int *fdp) +{ + struct tcp_ctx *tctx = ctx; + + PJDLOG_ASSERT(tctx != NULL); + PJDLOG_ASSERT(tctx->tc_magic == TCP_CTX_MAGIC); + PJDLOG_ASSERT(tctx->tc_side == TCP_SIDE_CLIENT || + tctx->tc_side == TCP_SIDE_SERVER_WORK); + PJDLOG_ASSERT(tctx->tc_wait_called); + PJDLOG_ASSERT(tctx->tc_fd >= 0); + PJDLOG_ASSERT(fdp == NULL); + + return (proto_common_recv(tctx->tc_fd, data, size, NULL)); +} + +static int +tcp_descriptor(const void *ctx) +{ + const struct tcp_ctx *tctx = ctx; + + PJDLOG_ASSERT(tctx != NULL); + PJDLOG_ASSERT(tctx->tc_magic == TCP_CTX_MAGIC); + + return (tctx->tc_fd); +} + +static bool +tcp_address_match(const void *ctx, const char *addr) +{ + const struct tcp_ctx *tctx = ctx; + struct sockaddr_storage sa1, sa2; + socklen_t salen; + + PJDLOG_ASSERT(tctx != NULL); + PJDLOG_ASSERT(tctx->tc_magic == TCP_CTX_MAGIC); + + if (tcp_addr(addr, atoi(proto_get("tcp:port")), &sa1) != 0) + return (false); + + salen = sizeof(sa2); + if (getpeername(tctx->tc_fd, (struct sockaddr *)&sa2, &salen) < 0) + return (false); + + if (sa1.ss_family != sa2.ss_family) + return (false); + +#ifdef HAVE_SOCKADDR_STORAGE_SS_LEN + if (sa1.ss_len != sa2.ss_len) + return (false); +#endif + + switch (sa1.ss_family) { + case AF_INET: + { + struct sockaddr_in *sin1, *sin2; + + sin1 = (struct sockaddr_in *)&sa1; + sin2 = (struct sockaddr_in *)&sa2; + + return (memcmp(&sin1->sin_addr, &sin2->sin_addr, + sizeof(sin1->sin_addr)) == 0); + } + case AF_INET6: + { + struct sockaddr_in6 *sin1, *sin2; + + sin1 = (struct sockaddr_in6 *)&sa1; + sin2 = (struct sockaddr_in6 *)&sa2; + + return (memcmp(&sin1->sin6_addr, &sin2->sin6_addr, + sizeof(sin1->sin6_addr)) == 0); + } + default: + return (false); + } +} + +#ifndef __FreeBSD__ +static void +sockaddr_to_string(const void *sa, char *buf, size_t size) +{ + const struct sockaddr_storage *ss; + + ss = (const struct sockaddr_storage * const *)sa; + switch (ss->ss_family) { + case AF_INET: + { + char addr[INET_ADDRSTRLEN]; + const struct sockaddr_in *sin; + unsigned int port; + + sin = (const struct sockaddr_in *)ss; + port = ntohs(sin->sin_port); + if (inet_ntop(ss->ss_family, &sin->sin_addr, addr, + sizeof(addr)) == NULL) { + PJDLOG_ABORT("inet_ntop(AF_INET) failed: %s.", + strerror(errno)); + } + snprintf(buf, size, "%s:%u", addr, port); + break; + } + case AF_INET6: + { + char addr[INET6_ADDRSTRLEN]; + const struct sockaddr_in6 *sin; + unsigned int port; + + sin = (const struct sockaddr_in6 *)ss; + port = ntohs(sin->sin6_port); + if (inet_ntop(ss->ss_family, &sin->sin6_addr, addr, + sizeof(addr)) == NULL) { + PJDLOG_ABORT("inet_ntop(AF_INET6) failed: %s.", + strerror(errno)); + } + snprintf(buf, size, "[%s]:%u", addr, port); + break; + } + default: + snprintf(buf, size, "[unsupported family %hhu]", + ss->ss_family); + break; + } +} +#endif /* !__FreeBSD__ */ + +static void +tcp_local_address(const void *ctx, char *addr, size_t size) +{ + const struct tcp_ctx *tctx = ctx; + struct sockaddr_storage sa; + socklen_t salen; + + PJDLOG_ASSERT(tctx != NULL); + PJDLOG_ASSERT(tctx->tc_magic == TCP_CTX_MAGIC); + + salen = sizeof(sa); + if (getsockname(tctx->tc_fd, (struct sockaddr *)&sa, &salen) < 0) { + PJDLOG_VERIFY(strlcpy(addr, "N/A", size) < size); + return; + } +#ifdef __FreeBSD__ + PJDLOG_VERIFY(snprintf(addr, size, "tcp://%S", &sa) < (ssize_t)size); +#else + strlcpy(addr, "tcp://", size); + if (size > 6) + sockaddr_to_string(&sa, addr + 6, size - 6); +#endif +} + +static void +tcp_remote_address(const void *ctx, char *addr, size_t size) +{ + const struct tcp_ctx *tctx = ctx; + struct sockaddr_storage sa; + socklen_t salen; + + PJDLOG_ASSERT(tctx != NULL); + PJDLOG_ASSERT(tctx->tc_magic == TCP_CTX_MAGIC); + + salen = sizeof(sa); + if (getpeername(tctx->tc_fd, (struct sockaddr *)&sa, &salen) < 0) { + PJDLOG_VERIFY(strlcpy(addr, "N/A", size) < size); + return; + } +#ifdef __FreeBSD__ + PJDLOG_VERIFY(snprintf(addr, size, "tcp://%S", &sa) < (ssize_t)size); +#else + strlcpy(addr, "tcp://", size); + if (size > 6) + sockaddr_to_string(&sa, addr + 6, size - 6); +#endif +} + +static void +tcp_close(void *ctx) +{ + struct tcp_ctx *tctx = ctx; + + PJDLOG_ASSERT(tctx != NULL); + PJDLOG_ASSERT(tctx->tc_magic == TCP_CTX_MAGIC); + + if (tctx->tc_fd >= 0) + close(tctx->tc_fd); + tctx->tc_magic = 0; + free(tctx); +} + +static struct proto tcp_proto = { + .prt_name = "tcp", + .prt_connect = tcp_connect, + .prt_connect_wait = tcp_connect_wait, + .prt_server = tcp_server, + .prt_accept = tcp_accept, + .prt_wrap = tcp_wrap, + .prt_send = tcp_send, + .prt_recv = tcp_recv, + .prt_descriptor = tcp_descriptor, + .prt_address_match = tcp_address_match, + .prt_local_address = tcp_local_address, + .prt_remote_address = tcp_remote_address, + .prt_close = tcp_close +}; + +static __constructor void +tcp_ctor(void) +{ + + proto_register(&tcp_proto, true); +} diff --git a/contrib/openbsm/bin/auditdistd/proto_tls.c b/contrib/openbsm/bin/auditdistd/proto_tls.c new file mode 100644 index 0000000..faeb3d8 --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/proto_tls.c @@ -0,0 +1,1076 @@ +/*- + * Copyright (c) 2011 The FreeBSD Foundation + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/proto_tls.c#2 $ + */ + +#include <config/config.h> + +#include <sys/param.h> /* MAXHOSTNAMELEN */ +#include <sys/socket.h> + +#include <arpa/inet.h> + +#include <netinet/in.h> +#include <netinet/tcp.h> + +#include <errno.h> +#include <fcntl.h> +#include <netdb.h> +#include <signal.h> +#include <stdbool.h> +#include <stdint.h> +#include <stdio.h> +#include <string.h> +#include <unistd.h> + +#include <openssl/err.h> +#include <openssl/ssl.h> + +#include <compat/compat.h> +#ifndef HAVE_CLOSEFROM +#include <compat/closefrom.h> +#endif +#ifndef HAVE_STRLCPY +#include <compat/strlcpy.h> +#endif + +#include "pjdlog.h" +#include "proto_impl.h" +#include "sandbox.h" +#include "subr.h" + +#define TLS_CTX_MAGIC 0x715c7 +struct tls_ctx { + int tls_magic; + struct proto_conn *tls_sock; + struct proto_conn *tls_tcp; + char tls_laddr[256]; + char tls_raddr[256]; + int tls_side; +#define TLS_SIDE_CLIENT 0 +#define TLS_SIDE_SERVER_LISTEN 1 +#define TLS_SIDE_SERVER_WORK 2 + bool tls_wait_called; +}; + +#define TLS_DEFAULT_TIMEOUT 30 + +static int tls_connect_wait(void *ctx, int timeout); +static void tls_close(void *ctx); + +static void +block(int fd) +{ + int flags; + + flags = fcntl(fd, F_GETFL); + if (flags == -1) + pjdlog_exit(EX_TEMPFAIL, "fcntl(F_GETFL) failed"); + flags &= ~O_NONBLOCK; + if (fcntl(fd, F_SETFL, flags) == -1) + pjdlog_exit(EX_TEMPFAIL, "fcntl(F_SETFL) failed"); +} + +static void +nonblock(int fd) +{ + int flags; + + flags = fcntl(fd, F_GETFL); + if (flags == -1) + pjdlog_exit(EX_TEMPFAIL, "fcntl(F_GETFL) failed"); + flags |= O_NONBLOCK; + if (fcntl(fd, F_SETFL, flags) == -1) + pjdlog_exit(EX_TEMPFAIL, "fcntl(F_SETFL) failed"); +} + +static int +wait_for_fd(int fd, int timeout) +{ + struct timeval tv; + fd_set fdset; + int error, ret; + + error = 0; + + for (;;) { + FD_ZERO(&fdset); + FD_SET(fd, &fdset); + + tv.tv_sec = timeout; + tv.tv_usec = 0; + + ret = select(fd + 1, NULL, &fdset, NULL, + timeout == -1 ? NULL : &tv); + if (ret == 0) { + error = ETIMEDOUT; + break; + } else if (ret == -1) { + if (errno == EINTR) + continue; + error = errno; + break; + } + PJDLOG_ASSERT(ret > 0); + PJDLOG_ASSERT(FD_ISSET(fd, &fdset)); + break; + } + + return (error); +} + +static void +ssl_log_errors(void) +{ + unsigned long error; + + while ((error = ERR_get_error()) != 0) + pjdlog_error("SSL error: %s", ERR_error_string(error, NULL)); +} + +static int +ssl_check_error(SSL *ssl, int ret) +{ + int error; + + error = SSL_get_error(ssl, ret); + + switch (error) { + case SSL_ERROR_NONE: + return (0); + case SSL_ERROR_WANT_READ: + pjdlog_debug(2, "SSL_ERROR_WANT_READ"); + return (-1); + case SSL_ERROR_WANT_WRITE: + pjdlog_debug(2, "SSL_ERROR_WANT_WRITE"); + return (-1); + case SSL_ERROR_ZERO_RETURN: + pjdlog_exitx(EX_OK, "Connection closed."); + case SSL_ERROR_SYSCALL: + ssl_log_errors(); + pjdlog_exitx(EX_TEMPFAIL, "SSL I/O error."); + case SSL_ERROR_SSL: + ssl_log_errors(); + pjdlog_exitx(EX_TEMPFAIL, "SSL protocol error."); + default: + ssl_log_errors(); + pjdlog_exitx(EX_TEMPFAIL, "Unknown SSL error (%d).", error); + } +} + +static void +tcp_recv_ssl_send(int recvfd, SSL *sendssl) +{ + static unsigned char buf[65536]; + ssize_t tcpdone; + int sendfd, ssldone; + + sendfd = SSL_get_fd(sendssl); + PJDLOG_ASSERT(sendfd >= 0); + pjdlog_debug(2, "%s: start %d -> %d", __func__, recvfd, sendfd); + for (;;) { + tcpdone = recv(recvfd, buf, sizeof(buf), 0); + pjdlog_debug(2, "%s: recv() returned %zd", __func__, tcpdone); + if (tcpdone == 0) { + pjdlog_debug(1, "Connection terminated."); + exit(0); + } else if (tcpdone == -1) { + if (errno == EINTR) + continue; + else if (errno == EAGAIN) + break; + pjdlog_exit(EX_TEMPFAIL, "recv() failed"); + } + for (;;) { + ssldone = SSL_write(sendssl, buf, (int)tcpdone); + pjdlog_debug(2, "%s: send() returned %d", __func__, + ssldone); + if (ssl_check_error(sendssl, ssldone) == -1) { + (void)wait_for_fd(sendfd, -1); + continue; + } + PJDLOG_ASSERT(ssldone == tcpdone); + break; + } + } + pjdlog_debug(2, "%s: done %d -> %d", __func__, recvfd, sendfd); +} + +static void +ssl_recv_tcp_send(SSL *recvssl, int sendfd) +{ + static unsigned char buf[65536]; + unsigned char *ptr; + ssize_t tcpdone; + size_t todo; + int recvfd, ssldone; + + recvfd = SSL_get_fd(recvssl); + PJDLOG_ASSERT(recvfd >= 0); + pjdlog_debug(2, "%s: start %d -> %d", __func__, recvfd, sendfd); + for (;;) { + ssldone = SSL_read(recvssl, buf, sizeof(buf)); + pjdlog_debug(2, "%s: SSL_read() returned %d", __func__, + ssldone); + if (ssl_check_error(recvssl, ssldone) == -1) + break; + todo = (size_t)ssldone; + ptr = buf; + do { + tcpdone = send(sendfd, ptr, todo, MSG_NOSIGNAL); + pjdlog_debug(2, "%s: send() returned %zd", __func__, + tcpdone); + if (tcpdone == 0) { + pjdlog_debug(1, "Connection terminated."); + exit(0); + } else if (tcpdone == -1) { + if (errno == EINTR || errno == ENOBUFS) + continue; + if (errno == EAGAIN) { + (void)wait_for_fd(sendfd, -1); + continue; + } + pjdlog_exit(EX_TEMPFAIL, "send() failed"); + } + todo -= tcpdone; + ptr += tcpdone; + } while (todo > 0); + } + pjdlog_debug(2, "%s: done %d -> %d", __func__, recvfd, sendfd); +} + +static void +tls_loop(int sockfd, SSL *tcpssl) +{ + fd_set fds; + int maxfd, tcpfd; + + tcpfd = SSL_get_fd(tcpssl); + PJDLOG_ASSERT(tcpfd >= 0); + + for (;;) { + FD_ZERO(&fds); + FD_SET(sockfd, &fds); + FD_SET(tcpfd, &fds); + maxfd = MAX(sockfd, tcpfd); + + PJDLOG_ASSERT(maxfd + 1 <= (int)FD_SETSIZE); + if (select(maxfd + 1, &fds, NULL, NULL, NULL) == -1) { + if (errno == EINTR) + continue; + pjdlog_exit(EX_TEMPFAIL, "select() failed"); + } + if (FD_ISSET(sockfd, &fds)) + tcp_recv_ssl_send(sockfd, tcpssl); + if (FD_ISSET(tcpfd, &fds)) + ssl_recv_tcp_send(tcpssl, sockfd); + } +} + +static void +tls_certificate_verify(SSL *ssl, const char *fingerprint) +{ + unsigned char md[EVP_MAX_MD_SIZE]; + char mdstr[sizeof("SHA256=") - 1 + EVP_MAX_MD_SIZE * 3]; + char *mdstrp; + unsigned int i, mdsize; + X509 *cert; + + if (fingerprint[0] == '\0') { + pjdlog_debug(1, "No fingerprint verification requested."); + return; + } + + cert = SSL_get_peer_certificate(ssl); + if (cert == NULL) + pjdlog_exitx(EX_TEMPFAIL, "No peer certificate received."); + + if (X509_digest(cert, EVP_sha256(), md, &mdsize) != 1) + pjdlog_exitx(EX_TEMPFAIL, "X509_digest() failed."); + PJDLOG_ASSERT(mdsize <= EVP_MAX_MD_SIZE); + + X509_free(cert); + + (void)strlcpy(mdstr, "SHA256=", sizeof(mdstr)); + mdstrp = mdstr + strlen(mdstr); + for (i = 0; i < mdsize; i++) { + PJDLOG_VERIFY(mdstrp + 3 <= mdstr + sizeof(mdstr)); + (void)sprintf(mdstrp, "%02hhX:", md[i]); + mdstrp += 3; + } + /* Clear last colon. */ + mdstrp[-1] = '\0'; + if (strcasecmp(mdstr, fingerprint) != 0) { + pjdlog_exitx(EX_NOPERM, + "Finger print doesn't match. Received \"%s\", expected \"%s\"", + mdstr, fingerprint); + } +} + +static void +tls_exec_client(const char *user, int startfd, const char *srcaddr, + const char *dstaddr, const char *fingerprint, const char *defport, + int timeout, int debuglevel) +{ + struct proto_conn *tcp; + char *saddr, *daddr; + SSL_CTX *sslctx; + SSL *ssl; + long ret; + int sockfd, tcpfd; + uint8_t connected; + + pjdlog_debug_set(debuglevel); + pjdlog_prefix_set("[TLS sandbox] (client) "); +#ifdef HAVE_SETPROCTITLE + setproctitle("[TLS sandbox] (client) "); +#endif + proto_set("tcp:port", defport); + + sockfd = startfd; + + /* Change tls:// to tcp://. */ + if (srcaddr == NULL) { + saddr = NULL; + } else { + saddr = strdup(srcaddr); + if (saddr == NULL) + pjdlog_exitx(EX_TEMPFAIL, "Unable to allocate memory."); + bcopy("tcp://", saddr, 6); + } + daddr = strdup(dstaddr); + if (daddr == NULL) + pjdlog_exitx(EX_TEMPFAIL, "Unable to allocate memory."); + bcopy("tcp://", daddr, 6); + + /* Establish TCP connection. */ + if (proto_connect(saddr, daddr, timeout, &tcp) == -1) + exit(EX_TEMPFAIL); + + SSL_load_error_strings(); + SSL_library_init(); + + /* + * TODO: On FreeBSD we could move this below sandbox() once libc and + * libcrypto use sysctl kern.arandom to obtain random data + * instead of /dev/urandom and friends. + */ + sslctx = SSL_CTX_new(TLSv1_client_method()); + if (sslctx == NULL) + pjdlog_exitx(EX_TEMPFAIL, "SSL_CTX_new() failed."); + + if (sandbox(user, true, "proto_tls client: %s", dstaddr) != 0) + pjdlog_exitx(EX_CONFIG, "Unable to sandbox TLS client."); + pjdlog_debug(1, "Privileges successfully dropped."); + + SSL_CTX_set_options(sslctx, SSL_OP_NO_SSLv2 | SSL_OP_NO_SSLv3); + + /* Load CA certs. */ + /* TODO */ + //SSL_CTX_load_verify_locations(sslctx, cacerts_file, NULL); + + ssl = SSL_new(sslctx); + if (ssl == NULL) + pjdlog_exitx(EX_TEMPFAIL, "SSL_new() failed."); + + tcpfd = proto_descriptor(tcp); + + block(tcpfd); + + if (SSL_set_fd(ssl, tcpfd) != 1) + pjdlog_exitx(EX_TEMPFAIL, "SSL_set_fd() failed."); + + ret = SSL_connect(ssl); + ssl_check_error(ssl, (int)ret); + + nonblock(sockfd); + nonblock(tcpfd); + + tls_certificate_verify(ssl, fingerprint); + + /* + * The following byte is send to make proto_connect_wait() to work. + */ + connected = 1; + for (;;) { + switch (send(sockfd, &connected, sizeof(connected), 0)) { + case -1: + if (errno == EINTR || errno == ENOBUFS) + continue; + if (errno == EAGAIN) { + (void)wait_for_fd(sockfd, -1); + continue; + } + pjdlog_exit(EX_TEMPFAIL, "send() failed"); + case 0: + pjdlog_debug(1, "Connection terminated."); + exit(0); + case 1: + break; + } + break; + } + + tls_loop(sockfd, ssl); +} + +static void +tls_call_exec_client(struct proto_conn *sock, const char *srcaddr, + const char *dstaddr, int timeout) +{ + char *timeoutstr, *startfdstr, *debugstr; + int startfd; + + /* Declare that we are receiver. */ + proto_recv(sock, NULL, 0); + + if (pjdlog_mode_get() == PJDLOG_MODE_STD) + startfd = 3; + else /* if (pjdlog_mode_get() == PJDLOG_MODE_SYSLOG) */ + startfd = 0; + + if (proto_descriptor(sock) != startfd) { + /* Move socketpair descriptor to descriptor number startfd. */ + if (dup2(proto_descriptor(sock), startfd) == -1) + pjdlog_exit(EX_OSERR, "dup2() failed"); + proto_close(sock); + } else { + /* + * The FD_CLOEXEC is cleared by dup2(2), so when we not + * call it, we have to clear it by hand in case it is set. + */ + if (fcntl(startfd, F_SETFD, 0) == -1) + pjdlog_exit(EX_OSERR, "fcntl() failed"); + } + + closefrom(startfd + 1); + + if (asprintf(&startfdstr, "%d", startfd) == -1) + pjdlog_exit(EX_TEMPFAIL, "asprintf() failed"); + if (timeout == -1) + timeout = TLS_DEFAULT_TIMEOUT; + if (asprintf(&timeoutstr, "%d", timeout) == -1) + pjdlog_exit(EX_TEMPFAIL, "asprintf() failed"); + if (asprintf(&debugstr, "%d", pjdlog_debug_get()) == -1) + pjdlog_exit(EX_TEMPFAIL, "asprintf() failed"); + + execl(proto_get("execpath"), proto_get("execpath"), "proto", "tls", + proto_get("user"), "client", startfdstr, + srcaddr == NULL ? "" : srcaddr, dstaddr, + proto_get("tls:fingerprint"), proto_get("tcp:port"), timeoutstr, + debugstr, NULL); + pjdlog_exit(EX_SOFTWARE, "execl() failed"); +} + +static int +tls_connect(const char *srcaddr, const char *dstaddr, int timeout, void **ctxp) +{ + struct tls_ctx *tlsctx; + struct proto_conn *sock; + pid_t pid; + int error; + + PJDLOG_ASSERT(srcaddr == NULL || srcaddr[0] != '\0'); + PJDLOG_ASSERT(dstaddr != NULL); + PJDLOG_ASSERT(timeout >= -1); + PJDLOG_ASSERT(ctxp != NULL); + + if (strncmp(dstaddr, "tls://", 6) != 0) + return (-1); + if (srcaddr != NULL && strncmp(srcaddr, "tls://", 6) != 0) + return (-1); + + if (proto_connect(NULL, "socketpair://", -1, &sock) == -1) + return (errno); + +#if 0 + /* + * We use rfork() with the following flags to disable SIGCHLD + * delivery upon the sandbox process exit. + */ + pid = rfork(RFFDG | RFPROC | RFTSIGZMB | RFTSIGFLAGS(0)); +#else + /* + * We don't use rfork() to be able to log information about sandbox + * process exiting. + */ + pid = fork(); +#endif + switch (pid) { + case -1: + /* Failure. */ + error = errno; + proto_close(sock); + return (error); + case 0: + /* Child. */ + pjdlog_prefix_set("[TLS sandbox] (client) "); +#ifdef HAVE_SETPROCTITLE + setproctitle("[TLS sandbox] (client) "); +#endif + tls_call_exec_client(sock, srcaddr, dstaddr, timeout); + /* NOTREACHED */ + default: + /* Parent. */ + tlsctx = calloc(1, sizeof(*tlsctx)); + if (tlsctx == NULL) { + error = errno; + proto_close(sock); + (void)kill(pid, SIGKILL); + return (error); + } + proto_send(sock, NULL, 0); + tlsctx->tls_sock = sock; + tlsctx->tls_tcp = NULL; + tlsctx->tls_side = TLS_SIDE_CLIENT; + tlsctx->tls_wait_called = false; + tlsctx->tls_magic = TLS_CTX_MAGIC; + if (timeout >= 0) { + error = tls_connect_wait(tlsctx, timeout); + if (error != 0) { + (void)kill(pid, SIGKILL); + tls_close(tlsctx); + return (error); + } + } + *ctxp = tlsctx; + return (0); + } +} + +static int +tls_connect_wait(void *ctx, int timeout) +{ + struct tls_ctx *tlsctx = ctx; + int error, sockfd; + uint8_t connected; + + PJDLOG_ASSERT(tlsctx != NULL); + PJDLOG_ASSERT(tlsctx->tls_magic == TLS_CTX_MAGIC); + PJDLOG_ASSERT(tlsctx->tls_side == TLS_SIDE_CLIENT); + PJDLOG_ASSERT(tlsctx->tls_sock != NULL); + PJDLOG_ASSERT(!tlsctx->tls_wait_called); + PJDLOG_ASSERT(timeout >= 0); + + sockfd = proto_descriptor(tlsctx->tls_sock); + error = wait_for_fd(sockfd, timeout); + if (error != 0) + return (error); + + for (;;) { + switch (recv(sockfd, &connected, sizeof(connected), + MSG_WAITALL)) { + case -1: + if (errno == EINTR || errno == ENOBUFS) + continue; + error = errno; + break; + case 0: + pjdlog_debug(1, "Connection terminated."); + error = ENOTCONN; + break; + case 1: + tlsctx->tls_wait_called = true; + break; + } + break; + } + + return (error); +} + +static int +tls_server(const char *lstaddr, void **ctxp) +{ + struct proto_conn *tcp; + struct tls_ctx *tlsctx; + char *laddr; + int error; + + if (strncmp(lstaddr, "tls://", 6) != 0) + return (-1); + + tlsctx = malloc(sizeof(*tlsctx)); + if (tlsctx == NULL) { + pjdlog_warning("Unable to allocate memory."); + return (ENOMEM); + } + + laddr = strdup(lstaddr); + if (laddr == NULL) { + free(tlsctx); + pjdlog_warning("Unable to allocate memory."); + return (ENOMEM); + } + bcopy("tcp://", laddr, 6); + + if (proto_server(laddr, &tcp) == -1) { + error = errno; + free(tlsctx); + free(laddr); + return (error); + } + free(laddr); + + tlsctx->tls_sock = NULL; + tlsctx->tls_tcp = tcp; + tlsctx->tls_side = TLS_SIDE_SERVER_LISTEN; + tlsctx->tls_wait_called = true; + tlsctx->tls_magic = TLS_CTX_MAGIC; + *ctxp = tlsctx; + + return (0); +} + +static void +tls_exec_server(const char *user, int startfd, const char *privkey, + const char *cert, int debuglevel) +{ + SSL_CTX *sslctx; + SSL *ssl; + int sockfd, tcpfd, ret; + + pjdlog_debug_set(debuglevel); + pjdlog_prefix_set("[TLS sandbox] (server) "); +#ifdef HAVE_SETPROCTITLE + setproctitle("[TLS sandbox] (server) "); +#endif + + sockfd = startfd; + tcpfd = startfd + 1; + + SSL_load_error_strings(); + SSL_library_init(); + + sslctx = SSL_CTX_new(TLSv1_server_method()); + if (sslctx == NULL) + pjdlog_exitx(EX_TEMPFAIL, "SSL_CTX_new() failed."); + + SSL_CTX_set_options(sslctx, SSL_OP_NO_SSLv2 | SSL_OP_NO_SSLv3); + + ssl = SSL_new(sslctx); + if (ssl == NULL) + pjdlog_exitx(EX_TEMPFAIL, "SSL_new() failed."); + + if (SSL_use_RSAPrivateKey_file(ssl, privkey, SSL_FILETYPE_PEM) != 1) { + ssl_log_errors(); + pjdlog_exitx(EX_CONFIG, + "SSL_use_RSAPrivateKey_file(%s) failed.", privkey); + } + + if (SSL_use_certificate_file(ssl, cert, SSL_FILETYPE_PEM) != 1) { + ssl_log_errors(); + pjdlog_exitx(EX_CONFIG, "SSL_use_certificate_file(%s) failed.", + cert); + } + + if (sandbox(user, true, "proto_tls server") != 0) + pjdlog_exitx(EX_CONFIG, "Unable to sandbox TLS server."); + pjdlog_debug(1, "Privileges successfully dropped."); + + nonblock(sockfd); + nonblock(tcpfd); + + if (SSL_set_fd(ssl, tcpfd) != 1) + pjdlog_exitx(EX_TEMPFAIL, "SSL_set_fd() failed."); + + ret = SSL_accept(ssl); + ssl_check_error(ssl, ret); + + tls_loop(sockfd, ssl); +} + +static void +tls_call_exec_server(struct proto_conn *sock, struct proto_conn *tcp) +{ + int startfd, sockfd, tcpfd, safefd; + char *startfdstr, *debugstr; + + if (pjdlog_mode_get() == PJDLOG_MODE_STD) + startfd = 3; + else /* if (pjdlog_mode_get() == PJDLOG_MODE_SYSLOG) */ + startfd = 0; + + /* Declare that we are receiver. */ + proto_send(sock, NULL, 0); + + sockfd = proto_descriptor(sock); + tcpfd = proto_descriptor(tcp); + + safefd = MAX(sockfd, tcpfd); + safefd = MAX(safefd, startfd); + safefd++; + + /* Move sockfd and tcpfd to safe numbers first. */ + if (dup2(sockfd, safefd) == -1) + pjdlog_exit(EX_OSERR, "dup2() failed"); + proto_close(sock); + sockfd = safefd; + if (dup2(tcpfd, safefd + 1) == -1) + pjdlog_exit(EX_OSERR, "dup2() failed"); + proto_close(tcp); + tcpfd = safefd + 1; + + /* Move socketpair descriptor to descriptor number startfd. */ + if (dup2(sockfd, startfd) == -1) + pjdlog_exit(EX_OSERR, "dup2() failed"); + (void)close(sockfd); + /* Move tcp descriptor to descriptor number startfd + 1. */ + if (dup2(tcpfd, startfd + 1) == -1) + pjdlog_exit(EX_OSERR, "dup2() failed"); + (void)close(tcpfd); + + closefrom(startfd + 2); + + /* + * Even if FD_CLOEXEC was set on descriptors before dup2(), it should + * have been cleared on dup2(), but better be safe than sorry. + */ + if (fcntl(startfd, F_SETFD, 0) == -1) + pjdlog_exit(EX_OSERR, "fcntl() failed"); + if (fcntl(startfd + 1, F_SETFD, 0) == -1) + pjdlog_exit(EX_OSERR, "fcntl() failed"); + + if (asprintf(&startfdstr, "%d", startfd) == -1) + pjdlog_exit(EX_TEMPFAIL, "asprintf() failed"); + if (asprintf(&debugstr, "%d", pjdlog_debug_get()) == -1) + pjdlog_exit(EX_TEMPFAIL, "asprintf() failed"); + + execl(proto_get("execpath"), proto_get("execpath"), "proto", "tls", + proto_get("user"), "server", startfdstr, proto_get("tls:keyfile"), + proto_get("tls:certfile"), debugstr, NULL); + pjdlog_exit(EX_SOFTWARE, "execl() failed"); +} + +static int +tls_accept(void *ctx, void **newctxp) +{ + struct tls_ctx *tlsctx = ctx; + struct tls_ctx *newtlsctx; + struct proto_conn *sock, *tcp; + pid_t pid; + int error; + + PJDLOG_ASSERT(tlsctx != NULL); + PJDLOG_ASSERT(tlsctx->tls_magic == TLS_CTX_MAGIC); + PJDLOG_ASSERT(tlsctx->tls_side == TLS_SIDE_SERVER_LISTEN); + + if (proto_connect(NULL, "socketpair://", -1, &sock) == -1) + return (errno); + + /* Accept TCP connection. */ + if (proto_accept(tlsctx->tls_tcp, &tcp) == -1) { + error = errno; + proto_close(sock); + return (error); + } + + pid = fork(); + switch (pid) { + case -1: + /* Failure. */ + error = errno; + proto_close(sock); + return (error); + case 0: + /* Child. */ + pjdlog_prefix_set("[TLS sandbox] (server) "); +#ifdef HAVE_SETPROCTITLE + setproctitle("[TLS sandbox] (server) "); +#endif + /* Close listen socket. */ + proto_close(tlsctx->tls_tcp); + tls_call_exec_server(sock, tcp); + /* NOTREACHED */ + PJDLOG_ABORT("Unreachable."); + default: + /* Parent. */ + newtlsctx = calloc(1, sizeof(*tlsctx)); + if (newtlsctx == NULL) { + error = errno; + proto_close(sock); + proto_close(tcp); + (void)kill(pid, SIGKILL); + return (error); + } + proto_local_address(tcp, newtlsctx->tls_laddr, + sizeof(newtlsctx->tls_laddr)); + PJDLOG_ASSERT(strncmp(newtlsctx->tls_laddr, "tcp://", 6) == 0); + bcopy("tls://", newtlsctx->tls_laddr, 6); + *strrchr(newtlsctx->tls_laddr, ':') = '\0'; + proto_remote_address(tcp, newtlsctx->tls_raddr, + sizeof(newtlsctx->tls_raddr)); + PJDLOG_ASSERT(strncmp(newtlsctx->tls_raddr, "tcp://", 6) == 0); + bcopy("tls://", newtlsctx->tls_raddr, 6); + *strrchr(newtlsctx->tls_raddr, ':') = '\0'; + proto_close(tcp); + proto_recv(sock, NULL, 0); + newtlsctx->tls_sock = sock; + newtlsctx->tls_tcp = NULL; + newtlsctx->tls_wait_called = true; + newtlsctx->tls_side = TLS_SIDE_SERVER_WORK; + newtlsctx->tls_magic = TLS_CTX_MAGIC; + *newctxp = newtlsctx; + return (0); + } +} + +static int +tls_wrap(int fd, bool client, void **ctxp) +{ + struct tls_ctx *tlsctx; + struct proto_conn *sock; + int error; + + tlsctx = calloc(1, sizeof(*tlsctx)); + if (tlsctx == NULL) + return (errno); + + if (proto_wrap("socketpair", client, fd, &sock) == -1) { + error = errno; + free(tlsctx); + return (error); + } + + tlsctx->tls_sock = sock; + tlsctx->tls_tcp = NULL; + tlsctx->tls_wait_called = (client ? false : true); + tlsctx->tls_side = (client ? TLS_SIDE_CLIENT : TLS_SIDE_SERVER_WORK); + tlsctx->tls_magic = TLS_CTX_MAGIC; + *ctxp = tlsctx; + + return (0); +} + +static int +tls_send(void *ctx, const unsigned char *data, size_t size, int fd) +{ + struct tls_ctx *tlsctx = ctx; + + PJDLOG_ASSERT(tlsctx != NULL); + PJDLOG_ASSERT(tlsctx->tls_magic == TLS_CTX_MAGIC); + PJDLOG_ASSERT(tlsctx->tls_side == TLS_SIDE_CLIENT || + tlsctx->tls_side == TLS_SIDE_SERVER_WORK); + PJDLOG_ASSERT(tlsctx->tls_sock != NULL); + PJDLOG_ASSERT(tlsctx->tls_wait_called); + PJDLOG_ASSERT(fd == -1); + + if (proto_send(tlsctx->tls_sock, data, size) == -1) + return (errno); + + return (0); +} + +static int +tls_recv(void *ctx, unsigned char *data, size_t size, int *fdp) +{ + struct tls_ctx *tlsctx = ctx; + + PJDLOG_ASSERT(tlsctx != NULL); + PJDLOG_ASSERT(tlsctx->tls_magic == TLS_CTX_MAGIC); + PJDLOG_ASSERT(tlsctx->tls_side == TLS_SIDE_CLIENT || + tlsctx->tls_side == TLS_SIDE_SERVER_WORK); + PJDLOG_ASSERT(tlsctx->tls_sock != NULL); + PJDLOG_ASSERT(tlsctx->tls_wait_called); + PJDLOG_ASSERT(fdp == NULL); + + if (proto_recv(tlsctx->tls_sock, data, size) == -1) + return (errno); + + return (0); +} + +static int +tls_descriptor(const void *ctx) +{ + const struct tls_ctx *tlsctx = ctx; + + PJDLOG_ASSERT(tlsctx != NULL); + PJDLOG_ASSERT(tlsctx->tls_magic == TLS_CTX_MAGIC); + + switch (tlsctx->tls_side) { + case TLS_SIDE_CLIENT: + case TLS_SIDE_SERVER_WORK: + PJDLOG_ASSERT(tlsctx->tls_sock != NULL); + + return (proto_descriptor(tlsctx->tls_sock)); + case TLS_SIDE_SERVER_LISTEN: + PJDLOG_ASSERT(tlsctx->tls_tcp != NULL); + + return (proto_descriptor(tlsctx->tls_tcp)); + default: + PJDLOG_ABORT("Invalid side (%d).", tlsctx->tls_side); + } +} + +static bool +tcp_address_match(const void *ctx, const char *addr) +{ + const struct tls_ctx *tlsctx = ctx; + + PJDLOG_ASSERT(tlsctx != NULL); + PJDLOG_ASSERT(tlsctx->tls_magic == TLS_CTX_MAGIC); + + return (strcmp(tlsctx->tls_raddr, addr) == 0); +} + +static void +tls_local_address(const void *ctx, char *addr, size_t size) +{ + const struct tls_ctx *tlsctx = ctx; + + PJDLOG_ASSERT(tlsctx != NULL); + PJDLOG_ASSERT(tlsctx->tls_magic == TLS_CTX_MAGIC); + PJDLOG_ASSERT(tlsctx->tls_wait_called); + + switch (tlsctx->tls_side) { + case TLS_SIDE_CLIENT: + PJDLOG_ASSERT(tlsctx->tls_sock != NULL); + + PJDLOG_VERIFY(strlcpy(addr, "tls://N/A", size) < size); + break; + case TLS_SIDE_SERVER_WORK: + PJDLOG_ASSERT(tlsctx->tls_sock != NULL); + + PJDLOG_VERIFY(strlcpy(addr, tlsctx->tls_laddr, size) < size); + break; + case TLS_SIDE_SERVER_LISTEN: + PJDLOG_ASSERT(tlsctx->tls_tcp != NULL); + + proto_local_address(tlsctx->tls_tcp, addr, size); + PJDLOG_ASSERT(strncmp(addr, "tcp://", 6) == 0); + /* Replace tcp:// prefix with tls:// */ + bcopy("tls://", addr, 6); + break; + default: + PJDLOG_ABORT("Invalid side (%d).", tlsctx->tls_side); + } +} + +static void +tls_remote_address(const void *ctx, char *addr, size_t size) +{ + const struct tls_ctx *tlsctx = ctx; + + PJDLOG_ASSERT(tlsctx != NULL); + PJDLOG_ASSERT(tlsctx->tls_magic == TLS_CTX_MAGIC); + PJDLOG_ASSERT(tlsctx->tls_wait_called); + + switch (tlsctx->tls_side) { + case TLS_SIDE_CLIENT: + PJDLOG_ASSERT(tlsctx->tls_sock != NULL); + + PJDLOG_VERIFY(strlcpy(addr, "tls://N/A", size) < size); + break; + case TLS_SIDE_SERVER_WORK: + PJDLOG_ASSERT(tlsctx->tls_sock != NULL); + + PJDLOG_VERIFY(strlcpy(addr, tlsctx->tls_raddr, size) < size); + break; + case TLS_SIDE_SERVER_LISTEN: + PJDLOG_ASSERT(tlsctx->tls_tcp != NULL); + + proto_remote_address(tlsctx->tls_tcp, addr, size); + PJDLOG_ASSERT(strncmp(addr, "tcp://", 6) == 0); + /* Replace tcp:// prefix with tls:// */ + bcopy("tls://", addr, 6); + break; + default: + PJDLOG_ABORT("Invalid side (%d).", tlsctx->tls_side); + } +} + +static void +tls_close(void *ctx) +{ + struct tls_ctx *tlsctx = ctx; + + PJDLOG_ASSERT(tlsctx != NULL); + PJDLOG_ASSERT(tlsctx->tls_magic == TLS_CTX_MAGIC); + + if (tlsctx->tls_sock != NULL) { + proto_close(tlsctx->tls_sock); + tlsctx->tls_sock = NULL; + } + if (tlsctx->tls_tcp != NULL) { + proto_close(tlsctx->tls_tcp); + tlsctx->tls_tcp = NULL; + } + tlsctx->tls_side = 0; + tlsctx->tls_magic = 0; + free(tlsctx); +} + +static int +tls_exec(int argc, char *argv[]) +{ + + PJDLOG_ASSERT(argc > 3); + PJDLOG_ASSERT(strcmp(argv[0], "tls") == 0); + + pjdlog_init(atoi(argv[3]) == 0 ? PJDLOG_MODE_SYSLOG : PJDLOG_MODE_STD); + + if (strcmp(argv[2], "client") == 0) { + if (argc != 10) + return (EINVAL); + tls_exec_client(argv[1], atoi(argv[3]), + argv[4][0] == '\0' ? NULL : argv[4], argv[5], argv[6], + argv[7], atoi(argv[8]), atoi(argv[9])); + } else if (strcmp(argv[2], "server") == 0) { + if (argc != 7) + return (EINVAL); + tls_exec_server(argv[1], atoi(argv[3]), argv[4], argv[5], + atoi(argv[6])); + } + return (EINVAL); +} + +static struct proto tls_proto = { + .prt_name = "tls", + .prt_connect = tls_connect, + .prt_connect_wait = tls_connect_wait, + .prt_server = tls_server, + .prt_accept = tls_accept, + .prt_wrap = tls_wrap, + .prt_send = tls_send, + .prt_recv = tls_recv, + .prt_descriptor = tls_descriptor, + .prt_address_match = tcp_address_match, + .prt_local_address = tls_local_address, + .prt_remote_address = tls_remote_address, + .prt_close = tls_close, + .prt_exec = tls_exec +}; + +static __constructor void +tls_ctor(void) +{ + + proto_register(&tls_proto, false); +} diff --git a/contrib/openbsm/bin/auditdistd/proto_uds.c b/contrib/openbsm/bin/auditdistd/proto_uds.c new file mode 100644 index 0000000..3b3dfb7 --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/proto_uds.c @@ -0,0 +1,362 @@ +/*- + * Copyright (c) 2009-2010 The FreeBSD Foundation + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/proto_uds.c#2 $ + */ + +/* UDS - UNIX Domain Socket */ + +#include <config/config.h> + +#include <sys/types.h> +#include <sys/socket.h> +#include <sys/un.h> + +#include <errno.h> +#include <stdbool.h> +#include <stdint.h> +#include <stdio.h> +#include <string.h> +#include <unistd.h> + +#ifndef HAVE_STRLCPY +#include <compat/strlcpy.h> +#endif + +#include "pjdlog.h" +#include "proto_impl.h" + +#define UDS_CTX_MAGIC 0xd541c +struct uds_ctx { + int uc_magic; + struct sockaddr_un uc_sun; + int uc_fd; + int uc_side; +#define UDS_SIDE_CLIENT 0 +#define UDS_SIDE_SERVER_LISTEN 1 +#define UDS_SIDE_SERVER_WORK 2 + pid_t uc_owner; +}; + +static void uds_close(void *ctx); + +static int +uds_addr(const char *addr, struct sockaddr_un *sunp) +{ + + if (addr == NULL) + return (-1); + + if (strncasecmp(addr, "uds://", 6) == 0) + addr += 6; + else if (strncasecmp(addr, "unix://", 7) == 0) + addr += 7; + else if (addr[0] == '/' && /* If it starts from /... */ + strstr(addr, "://") == NULL)/* ...and there is no prefix... */ + ; /* ...we assume its us. */ + else + return (-1); + + sunp->sun_family = AF_UNIX; + if (strlcpy(sunp->sun_path, addr, sizeof(sunp->sun_path)) >= + sizeof(sunp->sun_path)) { + return (ENAMETOOLONG); + } +#ifdef HAVE_SOCKADDR_STORAGE_SS_LEN + sunp->sun_len = SUN_LEN(sunp); +#endif + + return (0); +} + +static int +uds_common_setup(const char *addr, int side, struct uds_ctx **uctxp) +{ + struct uds_ctx *uctx; + int error; + + uctx = malloc(sizeof(*uctx)); + if (uctx == NULL) + return (errno); + + /* Parse given address. */ + error = uds_addr(addr, &uctx->uc_sun); + if (error != 0) { + free(uctx); + return (error); + } + + uctx->uc_fd = socket(AF_UNIX, SOCK_STREAM, 0); + if (uctx->uc_fd == -1) { + error = errno; + free(uctx); + return (error); + } + + uctx->uc_side = side; + uctx->uc_owner = 0; + uctx->uc_magic = UDS_CTX_MAGIC; + *uctxp = uctx; + + return (0); +} + +static int +uds_connect(const char *srcaddr, const char *dstaddr, int timeout, void **ctxp) +{ + struct uds_ctx *uctx; + int error; + + PJDLOG_ASSERT(dstaddr != NULL); + PJDLOG_ASSERT(timeout >= -1); + + error = uds_common_setup(dstaddr, UDS_SIDE_CLIENT, &uctx); + if (error != 0) + return (error); + + PJDLOG_ASSERT(srcaddr == NULL); + + if (connect(uctx->uc_fd, (struct sockaddr *)&uctx->uc_sun, + sizeof(uctx->uc_sun)) == -1) { + error = errno; + uds_close(uctx); + return (error); + } + + *ctxp = uctx; + + return (0); +} + +static int +uds_connect_wait(void *ctx, int timeout) +{ + struct uds_ctx *uctx = ctx; + + PJDLOG_ASSERT(uctx != NULL); + PJDLOG_ASSERT(uctx->uc_magic == UDS_CTX_MAGIC); + PJDLOG_ASSERT(uctx->uc_side == UDS_SIDE_CLIENT); + PJDLOG_ASSERT(uctx->uc_fd >= 0); + PJDLOG_ASSERT(timeout >= 0); + + return (0); +} + +static int +uds_server(const char *addr, void **ctxp) +{ + struct uds_ctx *uctx; + int error; + + error = uds_common_setup(addr, UDS_SIDE_SERVER_LISTEN, &uctx); + if (error != 0) + return (error); + + (void)unlink(uctx->uc_sun.sun_path); + if (bind(uctx->uc_fd, (struct sockaddr *)&uctx->uc_sun, + sizeof(uctx->uc_sun)) == -1) { + error = errno; + uds_close(uctx); + return (error); + } + uctx->uc_owner = getpid(); + if (listen(uctx->uc_fd, 8) == -1) { + error = errno; + uds_close(uctx); + return (error); + } + + *ctxp = uctx; + + return (0); +} + +static int +uds_accept(void *ctx, void **newctxp) +{ + struct uds_ctx *uctx = ctx; + struct uds_ctx *newuctx; + socklen_t fromlen; + int error; + + PJDLOG_ASSERT(uctx != NULL); + PJDLOG_ASSERT(uctx->uc_magic == UDS_CTX_MAGIC); + PJDLOG_ASSERT(uctx->uc_side == UDS_SIDE_SERVER_LISTEN); + PJDLOG_ASSERT(uctx->uc_fd >= 0); + + newuctx = malloc(sizeof(*newuctx)); + if (newuctx == NULL) + return (errno); + + fromlen = sizeof(newuctx->uc_sun); + newuctx->uc_fd = accept(uctx->uc_fd, + (struct sockaddr *)&newuctx->uc_sun, &fromlen); + if (newuctx->uc_fd < 0) { + error = errno; + free(newuctx); + return (error); + } + + newuctx->uc_side = UDS_SIDE_SERVER_WORK; + newuctx->uc_magic = UDS_CTX_MAGIC; + *newctxp = newuctx; + + return (0); +} + +static int +uds_send(void *ctx, const unsigned char *data, size_t size, int fd) +{ + struct uds_ctx *uctx = ctx; + + PJDLOG_ASSERT(uctx != NULL); + PJDLOG_ASSERT(uctx->uc_magic == UDS_CTX_MAGIC); + PJDLOG_ASSERT(uctx->uc_fd >= 0); + + return (proto_common_send(uctx->uc_fd, data, size, fd)); +} + +static int +uds_recv(void *ctx, unsigned char *data, size_t size, int *fdp) +{ + struct uds_ctx *uctx = ctx; + + PJDLOG_ASSERT(uctx != NULL); + PJDLOG_ASSERT(uctx->uc_magic == UDS_CTX_MAGIC); + PJDLOG_ASSERT(uctx->uc_fd >= 0); + + return (proto_common_recv(uctx->uc_fd, data, size, fdp)); +} + +static int +uds_descriptor(const void *ctx) +{ + const struct uds_ctx *uctx = ctx; + + PJDLOG_ASSERT(uctx != NULL); + PJDLOG_ASSERT(uctx->uc_magic == UDS_CTX_MAGIC); + + return (uctx->uc_fd); +} + +static void +uds_local_address(const void *ctx, char *addr, size_t size) +{ + const struct uds_ctx *uctx = ctx; + struct sockaddr_un sun; + socklen_t sunlen; + + PJDLOG_ASSERT(uctx != NULL); + PJDLOG_ASSERT(uctx->uc_magic == UDS_CTX_MAGIC); + PJDLOG_ASSERT(addr != NULL); + + sunlen = sizeof(sun); + if (getsockname(uctx->uc_fd, (struct sockaddr *)&sun, &sunlen) < 0) { + PJDLOG_VERIFY(strlcpy(addr, "N/A", size) < size); + return; + } + PJDLOG_ASSERT(sun.sun_family == AF_UNIX); + if (sun.sun_path[0] == '\0') { + PJDLOG_VERIFY(strlcpy(addr, "N/A", size) < size); + return; + } + PJDLOG_VERIFY(snprintf(addr, size, "uds://%s", sun.sun_path) < (ssize_t)size); +} + +static void +uds_remote_address(const void *ctx, char *addr, size_t size) +{ + const struct uds_ctx *uctx = ctx; + struct sockaddr_un sun; + socklen_t sunlen; + + PJDLOG_ASSERT(uctx != NULL); + PJDLOG_ASSERT(uctx->uc_magic == UDS_CTX_MAGIC); + PJDLOG_ASSERT(addr != NULL); + + sunlen = sizeof(sun); + if (getpeername(uctx->uc_fd, (struct sockaddr *)&sun, &sunlen) < 0) { + PJDLOG_VERIFY(strlcpy(addr, "N/A", size) < size); + return; + } + PJDLOG_ASSERT(sun.sun_family == AF_UNIX); + if (sun.sun_path[0] == '\0') { + PJDLOG_VERIFY(strlcpy(addr, "N/A", size) < size); + return; + } + snprintf(addr, size, "uds://%s", sun.sun_path); +} + +static void +uds_close(void *ctx) +{ + struct uds_ctx *uctx = ctx; + + PJDLOG_ASSERT(uctx != NULL); + PJDLOG_ASSERT(uctx->uc_magic == UDS_CTX_MAGIC); + + if (uctx->uc_fd >= 0) + close(uctx->uc_fd); + /* + * Unlink the socket only if we are the owner and this is descriptor + * we listen on. + */ + if (uctx->uc_side == UDS_SIDE_SERVER_LISTEN && + uctx->uc_owner == getpid()) { + PJDLOG_ASSERT(uctx->uc_sun.sun_path[0] != '\0'); + if (unlink(uctx->uc_sun.sun_path) == -1) { + pjdlog_errno(LOG_WARNING, + "Unable to unlink socket file %s", + uctx->uc_sun.sun_path); + } + } + uctx->uc_owner = 0; + uctx->uc_magic = 0; + free(uctx); +} + +static struct proto uds_proto = { + .prt_name = "uds", + .prt_connect = uds_connect, + .prt_connect_wait = uds_connect_wait, + .prt_server = uds_server, + .prt_accept = uds_accept, + .prt_send = uds_send, + .prt_recv = uds_recv, + .prt_descriptor = uds_descriptor, + .prt_local_address = uds_local_address, + .prt_remote_address = uds_remote_address, + .prt_close = uds_close +}; + +static __constructor void +uds_ctor(void) +{ + + proto_register(&uds_proto, false); +} diff --git a/contrib/openbsm/bin/auditdistd/receiver.c b/contrib/openbsm/bin/auditdistd/receiver.c new file mode 100644 index 0000000..698619d --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/receiver.c @@ -0,0 +1,714 @@ +/*- + * Copyright (c) 2012 The FreeBSD Foundation + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/receiver.c#3 $ + */ + +#include <config/config.h> + +#include <sys/param.h> +#if defined(HAVE_SYS_ENDIAN_H) && defined(HAVE_BSWAP) +#include <sys/endian.h> +#else /* !HAVE_SYS_ENDIAN_H || !HAVE_BSWAP */ +#ifdef HAVE_MACHINE_ENDIAN_H +#include <machine/endian.h> +#else /* !HAVE_MACHINE_ENDIAN_H */ +#ifdef HAVE_ENDIAN_H +#include <endian.h> +#else /* !HAVE_ENDIAN_H */ +#error "No supported endian.h" +#endif /* !HAVE_ENDIAN_H */ +#endif /* !HAVE_MACHINE_ENDIAN_H */ +#include <compat/endian.h> +#endif /* !HAVE_SYS_ENDIAN_H || !HAVE_BSWAP */ +#include <sys/queue.h> +#include <sys/stat.h> +#include <sys/time.h> + +#include <err.h> +#include <errno.h> +#include <fcntl.h> +#ifdef HAVE_LIBUTIL_H +#include <libutil.h> +#endif +#include <pthread.h> +#include <pwd.h> +#include <signal.h> +#include <stdint.h> +#include <stdio.h> +#include <string.h> +#include <sysexits.h> +#include <unistd.h> + +#ifndef HAVE_STRLCPY +#include <compat/strlcpy.h> +#endif +#ifndef HAVE_FSTATAT +#include "fstatat.h" +#endif +#ifndef HAVE_OPENAT +#include "openat.h" +#endif +#ifndef HAVE_RENAMEAT +#include "renameat.h" +#endif + +#include "auditdistd.h" +#include "pjdlog.h" +#include "proto.h" +#include "sandbox.h" +#include "subr.h" +#include "synch.h" +#include "trail.h" + +static struct adist_config *adcfg; +static struct adist_host *adhost; + +static TAILQ_HEAD(, adreq) adist_free_list; +static pthread_mutex_t adist_free_list_lock; +static pthread_cond_t adist_free_list_cond; +static TAILQ_HEAD(, adreq) adist_disk_list; +static pthread_mutex_t adist_disk_list_lock; +static pthread_cond_t adist_disk_list_cond; +static TAILQ_HEAD(, adreq) adist_send_list; +static pthread_mutex_t adist_send_list_lock; +static pthread_cond_t adist_send_list_cond; + +static void +adreq_clear(struct adreq *adreq) +{ + + adreq->adr_error = -1; + adreq->adr_byteorder = ADIST_BYTEORDER_UNDEFINED; + adreq->adr_cmd = ADIST_CMD_UNDEFINED; + adreq->adr_seq = 0; + adreq->adr_datasize = 0; +} + +static void +init_environment(void) +{ + struct adreq *adreq; + unsigned int ii; + + TAILQ_INIT(&adist_free_list); + mtx_init(&adist_free_list_lock); + cv_init(&adist_free_list_cond); + TAILQ_INIT(&adist_disk_list); + mtx_init(&adist_disk_list_lock); + cv_init(&adist_disk_list_cond); + TAILQ_INIT(&adist_send_list); + mtx_init(&adist_send_list_lock); + cv_init(&adist_send_list_cond); + + for (ii = 0; ii < ADIST_QUEUE_SIZE; ii++) { + adreq = malloc(sizeof(*adreq) + ADIST_BUF_SIZE); + if (adreq == NULL) { + pjdlog_exitx(EX_TEMPFAIL, + "Unable to allocate %zu bytes of memory for adreq object.", + sizeof(*adreq) + ADIST_BUF_SIZE); + } + adreq_clear(adreq); + TAILQ_INSERT_TAIL(&adist_free_list, adreq, adr_next); + } +} + +static void +adreq_decode_and_validate_header(struct adreq *adreq) +{ + + /* Byte-swap only is the sender is using different byte order. */ + if (adreq->adr_byteorder != ADIST_BYTEORDER) { + adreq->adr_byteorder = ADIST_BYTEORDER; + adreq->adr_seq = bswap64(adreq->adr_seq); + adreq->adr_datasize = bswap32(adreq->adr_datasize); + } + + /* Validate packet header. */ + + if (adreq->adr_datasize > ADIST_BUF_SIZE) { + pjdlog_exitx(EX_PROTOCOL, "Invalid datasize received (%ju).", + (uintmax_t)adreq->adr_datasize); + } + + switch (adreq->adr_cmd) { + case ADIST_CMD_OPEN: + case ADIST_CMD_APPEND: + case ADIST_CMD_CLOSE: + if (adreq->adr_datasize == 0) { + pjdlog_exitx(EX_PROTOCOL, + "Invalid datasize received (%ju).", + (uintmax_t)adreq->adr_datasize); + } + break; + case ADIST_CMD_KEEPALIVE: + case ADIST_CMD_ERROR: + if (adreq->adr_datasize > 0) { + pjdlog_exitx(EX_PROTOCOL, + "Invalid datasize received (%ju).", + (uintmax_t)adreq->adr_datasize); + } + break; + default: + pjdlog_exitx(EX_PROTOCOL, "Invalid command received (%hhu).", + adreq->adr_cmd); + } +} + +static void +adreq_validate_data(const struct adreq *adreq) +{ + + /* Validate packet data. */ + + switch (adreq->adr_cmd) { + case ADIST_CMD_OPEN: + case ADIST_CMD_CLOSE: + /* + * File name must end up with '\0' and there must be no '\0' + * in the middle. + */ + if (adreq->adr_data[adreq->adr_datasize - 1] != '\0' || + strchr(adreq->adr_data, '\0') != + (const char *)adreq->adr_data + adreq->adr_datasize - 1) { + pjdlog_exitx(EX_PROTOCOL, + "Invalid file name received."); + } + break; + } +} + +/* + * Thread receives requests from the sender. + */ +static void * +recv_thread(void *arg __unused) +{ + struct adreq *adreq; + + for (;;) { + pjdlog_debug(3, "recv: Taking free request."); + QUEUE_TAKE(adreq, &adist_free_list, 0); + pjdlog_debug(3, "recv: (%p) Got request.", adreq); + + if (proto_recv(adhost->adh_remote, &adreq->adr_packet, + sizeof(adreq->adr_packet)) == -1) { + pjdlog_exit(EX_TEMPFAIL, + "Unable to receive request header"); + } + adreq_decode_and_validate_header(adreq); + + switch (adreq->adr_cmd) { + case ADIST_CMD_KEEPALIVE: + adreq->adr_error = 0; + adreq_log(LOG_DEBUG, 2, -1, adreq, + "recv: (%p) Got request header: ", adreq); + pjdlog_debug(3, + "recv: (%p) Moving request to the send queue.", + adreq); + QUEUE_INSERT(adreq, &adist_send_list); + continue; + case ADIST_CMD_ERROR: + pjdlog_error("An error occured on the sender while reading \"%s/%s\".", + adhost->adh_directory, adhost->adh_trail_name); + adreq_log(LOG_DEBUG, 2, ADIST_ERROR_READ, adreq, + "recv: (%p) Got request header: ", adreq); + pjdlog_debug(3, + "recv: (%p) Moving request to the send queue.", + adreq); + QUEUE_INSERT(adreq, &adist_disk_list); + continue; + case ADIST_CMD_OPEN: + case ADIST_CMD_APPEND: + case ADIST_CMD_CLOSE: + if (proto_recv(adhost->adh_remote, adreq->adr_data, + adreq->adr_datasize) == -1) { + pjdlog_exit(EX_TEMPFAIL, + "Unable to receive request data"); + } + adreq_validate_data(adreq); + adreq_log(LOG_DEBUG, 2, -1, adreq, + "recv: (%p) Got request header: ", adreq); + pjdlog_debug(3, + "recv: (%p) Moving request to the disk queue.", + adreq); + QUEUE_INSERT(adreq, &adist_disk_list); + break; + default: + PJDLOG_ABORT("Invalid condition."); + } + } + /* NOTREACHED */ + return (NULL); +} + +/* + * Function that opens trail file requested by the sender. + * If the file already exist, it has to be the most recent file and it can + * only be open for append. + * If the file doesn't already exist, it has to be "older" than all existing + * files. + */ +static int +receiver_open(const char *filename) +{ + int fd; + + /* + * Previous file should be closed by now. Sending OPEN request without + * sending CLOSE for the previous file is a sender bug. + */ + if (adhost->adh_trail_fd != -1) { + pjdlog_error("Sender requested opening file \"%s\" without first closing \"%s\".", + filename, adhost->adh_trail_name); + return (ADIST_ERROR_WRONG_ORDER); + } + + if (!trail_validate_name(filename, NULL)) { + pjdlog_error("Sender wants to open file \"%s\", which has invalid name.", + filename); + return (ADIST_ERROR_INVALID_NAME); + } + + switch (trail_name_compare(filename, adhost->adh_trail_name)) { + case TRAIL_RENAMED: + if (!trail_is_not_terminated(adhost->adh_trail_name)) { + pjdlog_error("Terminated trail \"%s/%s\" was unterminated on the sender as \"%s/%s\"?", + adhost->adh_directory, adhost->adh_trail_name, + adhost->adh_directory, filename); + return (ADIST_ERROR_INVALID_NAME); + } + if (renameat(adhost->adh_trail_dirfd, adhost->adh_trail_name, + adhost->adh_trail_dirfd, filename) == -1) { + pjdlog_errno(LOG_ERR, + "Unable to rename file \"%s/%s\" to \"%s/%s\"", + adhost->adh_directory, adhost->adh_trail_name, + adhost->adh_directory, filename); + PJDLOG_ASSERT(errno > 0); + return (ADIST_ERROR_RENAME); + } + pjdlog_debug(1, "Renamed file \"%s/%s\" to \"%s/%s\".", + adhost->adh_directory, adhost->adh_trail_name, + adhost->adh_directory, filename); + /* FALLTHROUGH */ + case TRAIL_IDENTICAL: + /* Opening existing file. */ + fd = openat(adhost->adh_trail_dirfd, filename, + O_WRONLY | O_APPEND | O_NOFOLLOW); + if (fd == -1) { + pjdlog_errno(LOG_ERR, + "Unable to open file \"%s/%s\" for append", + adhost->adh_directory, filename); + PJDLOG_ASSERT(errno > 0); + return (ADIST_ERROR_OPEN); + } + pjdlog_debug(1, "Opened file \"%s/%s\".", + adhost->adh_directory, filename); + break; + case TRAIL_NEWER: + /* Opening new file. */ + fd = openat(adhost->adh_trail_dirfd, filename, + O_WRONLY | O_CREAT | O_EXCL | O_NOFOLLOW, 0600); + if (fd == -1) { + pjdlog_errno(LOG_ERR, + "Unable to create file \"%s/%s\"", + adhost->adh_directory, filename); + PJDLOG_ASSERT(errno > 0); + return (ADIST_ERROR_CREATE); + } + pjdlog_debug(1, "Created file \"%s/%s\".", + adhost->adh_directory, filename); + break; + case TRAIL_OLDER: + /* Trying to open old file. */ + pjdlog_error("Sender wants to open an old file \"%s\".", filename); + return (ADIST_ERROR_OPEN_OLD); + default: + PJDLOG_ABORT("Unknown return value from trail_name_compare()."); + } + PJDLOG_VERIFY(strlcpy(adhost->adh_trail_name, filename, + sizeof(adhost->adh_trail_name)) < sizeof(adhost->adh_trail_name)); + adhost->adh_trail_fd = fd; + return (0); +} + +/* + * Function appends data to the trail file that is currently open. + */ +static int +receiver_append(const unsigned char *data, size_t size) +{ + ssize_t done; + size_t osize; + + /* We should have opened trail file. */ + if (adhost->adh_trail_fd == -1) { + pjdlog_error("Sender requested append without first opening file."); + return (ADIST_ERROR_WRONG_ORDER); + } + + osize = size; + while (size > 0) { + done = write(adhost->adh_trail_fd, data, size); + if (done == -1) { + if (errno == EINTR) + continue; + pjdlog_errno(LOG_ERR, "Write to \"%s/%s\" failed", + adhost->adh_directory, adhost->adh_trail_name); + PJDLOG_ASSERT(errno > 0); + return (ADIST_ERROR_WRITE); + } + pjdlog_debug(3, "Wrote %zd bytes into \"%s/%s\".", done, + adhost->adh_directory, adhost->adh_trail_name); + size -= done; + } + pjdlog_debug(2, "Appended %zu bytes to file \"%s/%s\".", + osize, adhost->adh_directory, adhost->adh_trail_name); + return (0); +} + +static int +receiver_close(const char *filename) +{ + + /* We should have opened trail file. */ + if (adhost->adh_trail_fd == -1) { + pjdlog_error("Sender requested closing file without first opening it."); + return (ADIST_ERROR_WRONG_ORDER); + } + + /* Validate if we can do the rename. */ + if (!trail_validate_name(adhost->adh_trail_name, filename)) { + pjdlog_error("Sender wants to close file \"%s\" using name \"%s\".", + adhost->adh_trail_name, filename); + return (ADIST_ERROR_INVALID_NAME); + } + + PJDLOG_VERIFY(close(adhost->adh_trail_fd) == 0); + adhost->adh_trail_fd = -1; + + pjdlog_debug(1, "Closed file \"%s/%s\".", adhost->adh_directory, + adhost->adh_trail_name); + + if (strcmp(adhost->adh_trail_name, filename) == 0) { + /* File name didn't change, we are done here. */ + return (0); + } + + if (renameat(adhost->adh_trail_dirfd, adhost->adh_trail_name, + adhost->adh_trail_dirfd, filename) == -1) { + pjdlog_errno(LOG_ERR, "Unable to rename \"%s\" to \"%s\"", + adhost->adh_trail_name, filename); + PJDLOG_ASSERT(errno > 0); + return (ADIST_ERROR_RENAME); + } + pjdlog_debug(1, "Renamed file \"%s/%s\" to \"%s/%s\".", + adhost->adh_directory, adhost->adh_trail_name, + adhost->adh_directory, filename); + PJDLOG_VERIFY(strlcpy(adhost->adh_trail_name, filename, + sizeof(adhost->adh_trail_name)) < sizeof(adhost->adh_trail_name)); + + return (0); +} + +static int +receiver_error(void) +{ + + /* We should have opened trail file. */ + if (adhost->adh_trail_fd == -1) { + pjdlog_error("Sender send read error, but file is not open."); + return (ADIST_ERROR_WRONG_ORDER); + } + + PJDLOG_VERIFY(close(adhost->adh_trail_fd) == 0); + adhost->adh_trail_fd = -1; + + pjdlog_debug(1, "Closed file \"%s/%s\".", adhost->adh_directory, + adhost->adh_trail_name); + + return (0); +} + +static void * +disk_thread(void *arg __unused) +{ + struct adreq *adreq; + + for (;;) { + pjdlog_debug(3, "disk: Taking request."); + QUEUE_TAKE(adreq, &adist_disk_list, 0); + adreq_log(LOG_DEBUG, 3, -1, adreq, "disk: (%p) Got request: ", + adreq); + /* Handle the actual request. */ + switch (adreq->adr_cmd) { + case ADIST_CMD_OPEN: + adreq->adr_error = receiver_open(adreq->adr_data); + break; + case ADIST_CMD_APPEND: + adreq->adr_error = receiver_append(adreq->adr_data, + adreq->adr_datasize); + break; + case ADIST_CMD_CLOSE: + adreq->adr_error = receiver_close(adreq->adr_data); + break; + case ADIST_CMD_ERROR: + adreq->adr_error = receiver_error(); + break; + default: + PJDLOG_ABORT("Unexpected command (cmd=%hhu).", + adreq->adr_cmd); + } + if (adreq->adr_error != 0) { + adreq_log(LOG_ERR, 0, adreq->adr_error, adreq, + "Request failed: "); + } + pjdlog_debug(3, "disk: (%p) Moving request to the send queue.", + adreq); + QUEUE_INSERT(adreq, &adist_send_list); + } + /* NOTREACHED */ + return (NULL); +} + +/* + * Thread sends requests back to primary node. + */ +static void * +send_thread(void *arg __unused) +{ + struct adreq *adreq; + struct adrep adrep; + + for (;;) { + pjdlog_debug(3, "send: Taking request."); + QUEUE_TAKE(adreq, &adist_send_list, 0); + adreq_log(LOG_DEBUG, 3, -1, adreq, "send: (%p) Got request: ", + adreq); + adrep.adrp_byteorder = ADIST_BYTEORDER; + adrep.adrp_seq = adreq->adr_seq; + adrep.adrp_error = adreq->adr_error; + if (proto_send(adhost->adh_remote, &adrep, + sizeof(adrep)) == -1) { + pjdlog_exit(EX_TEMPFAIL, "Unable to send reply"); + } + pjdlog_debug(3, "send: (%p) Moving request to the free queue.", + adreq); + adreq_clear(adreq); + QUEUE_INSERT(adreq, &adist_free_list); + } + /* NOTREACHED */ + return (NULL); +} + +static void +receiver_directory_create(void) +{ + struct passwd *pw; + + /* + * According to getpwnam(3) we have to clear errno before calling the + * function to be able to distinguish between an error and missing + * entry (with is not treated as error by getpwnam(3)). + */ + errno = 0; + pw = getpwnam(ADIST_USER); + if (pw == NULL) { + if (errno != 0) { + pjdlog_exit(EX_NOUSER, + "Unable to find info about '%s' user", ADIST_USER); + } else { + pjdlog_exitx(EX_NOUSER, "User '%s' doesn't exist.", + ADIST_USER); + } + } + + if (mkdir(adhost->adh_directory, 0700) == -1) { + pjdlog_exit(EX_OSFILE, "Unable to create directory \"%s\"", + adhost->adh_directory); + } + if (chown(adhost->adh_directory, pw->pw_uid, pw->pw_gid) == -1) { + pjdlog_errno(LOG_ERR, + "Unable to change owner of the directory \"%s\"", + adhost->adh_directory); + (void)rmdir(adhost->adh_directory); + exit(EX_OSFILE); + } +} + +static void +receiver_directory_open(void) +{ + +#ifdef HAVE_FDOPENDIR + adhost->adh_trail_dirfd = open(adhost->adh_directory, + O_RDONLY | O_DIRECTORY); + if (adhost->adh_trail_dirfd == -1) { + if (errno == ENOENT) { + receiver_directory_create(); + adhost->adh_trail_dirfd = open(adhost->adh_directory, + O_RDONLY | O_DIRECTORY); + } + if (adhost->adh_trail_dirfd == -1) { + pjdlog_exit(EX_CONFIG, + "Unable to open directory \"%s\"", + adhost->adh_directory); + } + } + adhost->adh_trail_dirfp = fdopendir(adhost->adh_trail_dirfd); + if (adhost->adh_trail_dirfp == NULL) { + pjdlog_exit(EX_CONFIG, "Unable to fdopen directory \"%s\"", + adhost->adh_directory); + } +#else + struct stat sb; + + if (stat(adhost->adh_directory, &sb) == -1) { + if (errno == ENOENT) { + receiver_directory_create(); + } else { + pjdlog_exit(EX_CONFIG, + "Unable to stat directory \"%s\"", + adhost->adh_directory); + } + } + adhost->adh_trail_dirfp = opendir(adhost->adh_directory); + if (adhost->adh_trail_dirfp == NULL) { + pjdlog_exit(EX_CONFIG, "Unable to open directory \"%s\"", + adhost->adh_directory); + } + adhost->adh_trail_dirfd = dirfd(adhost->adh_trail_dirfp); +#endif +} + +static void +receiver_connect(void) +{ + uint64_t trail_size; + struct stat sb; + + PJDLOG_ASSERT(adhost->adh_trail_dirfp != NULL); + + trail_last(adhost->adh_trail_dirfp, adhost->adh_trail_name, + sizeof(adhost->adh_trail_name)); + + if (adhost->adh_trail_name[0] == '\0') { + trail_size = 0; + } else { + if (fstatat(adhost->adh_trail_dirfd, adhost->adh_trail_name, + &sb, AT_SYMLINK_NOFOLLOW) == -1) { + pjdlog_exit(EX_CONFIG, "Unable to stat \"%s/%s\"", + adhost->adh_directory, adhost->adh_trail_name); + } + if (!S_ISREG(sb.st_mode)) { + pjdlog_exitx(EX_CONFIG, + "File \"%s/%s\" is not a regular file.", + adhost->adh_directory, adhost->adh_trail_name); + } + trail_size = sb.st_size; + } + trail_size = htole64(trail_size); + if (proto_send(adhost->adh_remote, &trail_size, + sizeof(trail_size)) == -1) { + pjdlog_exit(EX_TEMPFAIL, + "Unable to send size of the most recent trail file"); + } + if (proto_send(adhost->adh_remote, adhost->adh_trail_name, + sizeof(adhost->adh_trail_name)) == -1) { + pjdlog_exit(EX_TEMPFAIL, + "Unable to send name of the most recent trail file"); + } +} + +void +adist_receiver(struct adist_config *config, struct adist_host *adh) +{ + sigset_t mask; + pthread_t td; + pid_t pid; + int error, mode, debuglevel; + + pid = fork(); + if (pid == -1) { + pjdlog_errno(LOG_ERR, "Unable to fork"); + proto_close(adh->adh_remote); + adh->adh_remote = NULL; + return; + } + + if (pid > 0) { + /* This is parent. */ + proto_close(adh->adh_remote); + adh->adh_remote = NULL; + adh->adh_worker_pid = pid; + return; + } + + adcfg = config; + adhost = adh; + mode = pjdlog_mode_get(); + debuglevel = pjdlog_debug_get(); + + descriptors_cleanup(adhost); + +// descriptors_assert(adhost, mode); + + pjdlog_init(mode); + pjdlog_debug_set(debuglevel); + pjdlog_prefix_set("[%s] (%s) ", adhost->adh_name, + role2str(adhost->adh_role)); +#ifdef HAVE_SETPROCTITLE + setproctitle("%s (%s)", adhost->adh_name, role2str(adhost->adh_role)); +#endif + + PJDLOG_VERIFY(sigemptyset(&mask) == 0); + PJDLOG_VERIFY(sigprocmask(SIG_SETMASK, &mask, NULL) == 0); + + /* Error in setting timeout is not critical, but why should it fail? */ + if (proto_timeout(adhost->adh_remote, adcfg->adc_timeout) == -1) + pjdlog_errno(LOG_WARNING, "Unable to set connection timeout"); + + init_environment(); + + adhost->adh_trail_fd = -1; + receiver_directory_open(); + + if (sandbox(ADIST_USER, true, "auditdistd: %s (%s)", + role2str(adhost->adh_role), adhost->adh_name) != 0) { + exit(EX_CONFIG); + } + pjdlog_info("Privileges successfully dropped."); + + receiver_connect(); + + error = pthread_create(&td, NULL, recv_thread, adhost); + PJDLOG_ASSERT(error == 0); + error = pthread_create(&td, NULL, disk_thread, adhost); + PJDLOG_ASSERT(error == 0); + (void)send_thread(adhost); +} diff --git a/contrib/openbsm/bin/auditdistd/renameat.h b/contrib/openbsm/bin/auditdistd/renameat.h new file mode 100644 index 0000000..a6a67f8 --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/renameat.h @@ -0,0 +1,68 @@ +/*- + * Copyright (c) 2012 The FreeBSD Foundation + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/renameat.h#1 $ + */ + +#ifndef _RENAMEAT_H_ +#define _RENAMEAT_H_ + +#include <stdio.h> +#include <unistd.h> + +static int +renameat(int fromfd, const char *from, int tofd, const char *to) +{ + int cfd, error, ret; + + if (fromfd != tofd) { + errno = EINVAL; + return (-1); + } + + cfd = open(".", O_RDONLY | O_DIRECTORY); + if (cfd == -1) + return (-1); + + if (fchdir(fromfd) == -1) { + error = errno; + (void)close(cfd); + errno = error; + return (-1); + } + + ret = rename(from, to); + + error = errno; + (void)fchdir(cfd); + (void)close(cfd); + errno = error; + return (ret); +} + +#endif /* !_RENAMEAT_H_ */ diff --git a/contrib/openbsm/bin/auditdistd/sandbox.c b/contrib/openbsm/bin/auditdistd/sandbox.c new file mode 100644 index 0000000..9e4f134 --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/sandbox.c @@ -0,0 +1,234 @@ +/*- + * Copyright (c) 2012 The FreeBSD Foundation + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/sandbox.c#3 $ + */ + +#include <config/config.h> + +#include <sys/param.h> +#ifdef HAVE_JAIL +#include <sys/jail.h> +#endif +#ifdef HAVE_CAP_ENTER +#include <sys/capability.h> +#endif + +#include <errno.h> +#include <pwd.h> +#include <stdarg.h> +#include <stdbool.h> +#include <stdio.h> +#include <stdlib.h> +#include <strings.h> +#include <unistd.h> + +#include "pjdlog.h" +#include "sandbox.h" + +static int +groups_compare(const void *grp0, const void *grp1) +{ + gid_t gr0 = *(const gid_t *)grp0; + gid_t gr1 = *(const gid_t *)grp1; + + return (gr0 <= gr1 ? (gr0 < gr1 ? -1 : 0) : 1); + +} + +int +sandbox(const char *user, bool capsicum, const char *fmt, ...) +{ +#ifdef HAVE_JAIL + struct jail jailst; + char *jailhost; + va_list ap; +#endif + struct passwd *pw; + uid_t ruid, euid; + gid_t rgid, egid; +#ifdef HAVE_GETRESUID + uid_t suid; +#endif +#ifdef HAVE_GETRESGID + gid_t sgid; +#endif + gid_t *groups, *ggroups; + bool jailed; + int ngroups, ret; + + PJDLOG_ASSERT(user != NULL); + PJDLOG_ASSERT(fmt != NULL); + + ret = -1; + groups = NULL; + ggroups = NULL; + + /* + * According to getpwnam(3) we have to clear errno before calling the + * function to be able to distinguish between an error and missing + * entry (with is not treated as error by getpwnam(3)). + */ + errno = 0; + pw = getpwnam(user); + if (pw == NULL) { + if (errno != 0) { + pjdlog_errno(LOG_ERR, + "Unable to find info about '%s' user", user); + goto out; + } else { + pjdlog_error("'%s' user doesn't exist.", user); + errno = ENOENT; + goto out; + } + } + + ngroups = sysconf(_SC_NGROUPS_MAX); + if (ngroups == -1) { + pjdlog_errno(LOG_WARNING, + "Unable to obtain maximum number of groups"); + ngroups = NGROUPS_MAX; + } + ngroups++; /* For base gid. */ + groups = malloc(sizeof(groups[0]) * ngroups); + if (groups == NULL) { + pjdlog_error("Unable to allocate memory for %d groups.", + ngroups); + goto out; + } + if (getgrouplist(user, pw->pw_gid, groups, &ngroups) == -1) { + pjdlog_error("Unable to obtain groups of user %s.", user); + goto out; + } + +#ifdef HAVE_JAIL + va_start(ap, fmt); + (void)vasprintf(&jailhost, fmt, ap); + va_end(ap); + if (jailhost == NULL) { + pjdlog_error("Unable to allocate memory for jail host name."); + goto out; + } + bzero(&jailst, sizeof(jailst)); + jailst.version = JAIL_API_VERSION; + jailst.path = pw->pw_dir; + jailst.hostname = jailhost; + if (jail(&jailst) >= 0) { + jailed = true; + } else { + jailed = false; + pjdlog_errno(LOG_WARNING, + "Unable to jail to directory %s", pw->pw_dir); + } + free(jailhost); +#else /* !HAVE_JAIL */ + jailed = false; +#endif /* !HAVE_JAIL */ + + if (!jailed) { + if (chroot(pw->pw_dir) == -1) { + pjdlog_errno(LOG_ERR, + "Unable to change root directory to %s", + pw->pw_dir); + goto out; + } + } + PJDLOG_VERIFY(chdir("/") == 0); + + if (setgroups(ngroups, groups) == -1) { + pjdlog_errno(LOG_ERR, "Unable to set groups"); + goto out; + } + if (setgid(pw->pw_gid) == -1) { + pjdlog_errno(LOG_ERR, "Unable to set gid to %u", + (unsigned int)pw->pw_gid); + goto out; + } + if (setuid(pw->pw_uid) == -1) { + pjdlog_errno(LOG_ERR, "Unable to set uid to %u", + (unsigned int)pw->pw_uid); + goto out; + } + +#ifdef HAVE_CAP_ENTER + if (capsicum) { + capsicum = (cap_enter() == 0); + if (!capsicum) { + pjdlog_common(LOG_DEBUG, 1, errno, + "Unable to sandbox using capsicum"); + } + } +#else /* !HAVE_CAP_ENTER */ + capsicum = false; +#endif /* !HAVE_CAP_ENTER */ + + /* + * Better be sure that everything succeeded. + */ +#ifdef HAVE_GETRESUID + PJDLOG_VERIFY(getresuid(&ruid, &euid, &suid) == 0); + PJDLOG_VERIFY(suid == pw->pw_uid); +#else + ruid = getuid(); + euid = geteuid(); +#endif + PJDLOG_VERIFY(ruid == pw->pw_uid); + PJDLOG_VERIFY(euid == pw->pw_uid); +#ifdef HAVE_GETRESGID + PJDLOG_VERIFY(getresgid(&rgid, &egid, &sgid) == 0); + PJDLOG_VERIFY(sgid == pw->pw_gid); +#else + rgid = getgid(); + egid = getegid(); +#endif + PJDLOG_VERIFY(rgid == pw->pw_gid); + PJDLOG_VERIFY(egid == pw->pw_gid); + PJDLOG_VERIFY(getgroups(0, NULL) == ngroups); + ggroups = malloc(sizeof(ggroups[0]) * ngroups); + if (ggroups == NULL) { + pjdlog_error("Unable to allocate memory for %d groups.", + ngroups); + goto out; + } + PJDLOG_VERIFY(getgroups(ngroups, ggroups) == ngroups); + qsort(groups, (size_t)ngroups, sizeof(groups[0]), groups_compare); + qsort(ggroups, (size_t)ngroups, sizeof(ggroups[0]), groups_compare); + PJDLOG_VERIFY(bcmp(groups, ggroups, sizeof(groups[0]) * ngroups) == 0); + + pjdlog_debug(1, + "Privileges successfully dropped using %s%s+setgid+setuid.", + capsicum ? "capsicum+" : "", jailed ? "jail" : "chroot"); + + ret = 0; +out: + if (groups != NULL) + free(groups); + if (ggroups != NULL) + free(ggroups); + return (ret); +} diff --git a/contrib/openbsm/bin/auditdistd/sandbox.h b/contrib/openbsm/bin/auditdistd/sandbox.h new file mode 100644 index 0000000..2dc59e4 --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/sandbox.h @@ -0,0 +1,39 @@ +/*- + * Copyright (c) 2012 The FreeBSD Foundation + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/sandbox.h#1 $ + */ + +#ifndef _SANDBOX_H_ +#define _SANDBOX_H_ + +#include <stdbool.h> + +int sandbox(const char *user, bool capsicum, const char *fmt, ...); + +#endif /* !_SANDBOX_H_ */ diff --git a/contrib/openbsm/bin/auditdistd/sender.c b/contrib/openbsm/bin/auditdistd/sender.c new file mode 100644 index 0000000..256fbb1 --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/sender.c @@ -0,0 +1,838 @@ +/*- + * Copyright (c) 2012 The FreeBSD Foundation + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/sender.c#3 $ + */ + +#include <config/config.h> + +#include <sys/param.h> +#if defined(HAVE_SYS_ENDIAN_H) && defined(HAVE_BSWAP) +#include <sys/endian.h> +#else /* !HAVE_SYS_ENDIAN_H || !HAVE_BSWAP */ +#ifdef HAVE_MACHINE_ENDIAN_H +#include <machine/endian.h> +#else /* !HAVE_MACHINE_ENDIAN_H */ +#ifdef HAVE_ENDIAN_H +#include <endian.h> +#else /* !HAVE_ENDIAN_H */ +#error "No supported endian.h" +#endif /* !HAVE_ENDIAN_H */ +#endif /* !HAVE_MACHINE_ENDIAN_H */ +#include <compat/endian.h> +#endif /* !HAVE_SYS_ENDIAN_H || !HAVE_BSWAP */ +#include <sys/queue.h> +#include <sys/stat.h> +#include <sys/wait.h> + +#include <stdio.h> +#include <stdlib.h> +#include <unistd.h> + +#include <ctype.h> +#include <dirent.h> +#include <err.h> +#include <errno.h> +#include <fcntl.h> +#ifdef HAVE_LIBUTIL_H +#include <libutil.h> +#endif +#include <signal.h> +#include <string.h> +#include <strings.h> + +#include <openssl/hmac.h> + +#ifndef HAVE_SIGTIMEDWAIT +#include "sigtimedwait.h" +#endif + +#include "auditdistd.h" +#include "pjdlog.h" +#include "proto.h" +#include "sandbox.h" +#include "subr.h" +#include "synch.h" +#include "trail.h" + +static struct adist_config *adcfg; +static struct adist_host *adhost; + +static pthread_rwlock_t adist_remote_lock; +static pthread_mutex_t adist_remote_mtx; +static pthread_cond_t adist_remote_cond; +static struct trail *adist_trail; + +static TAILQ_HEAD(, adreq) adist_free_list; +static pthread_mutex_t adist_free_list_lock; +static pthread_cond_t adist_free_list_cond; +static TAILQ_HEAD(, adreq) adist_send_list; +static pthread_mutex_t adist_send_list_lock; +static pthread_cond_t adist_send_list_cond; +static TAILQ_HEAD(, adreq) adist_recv_list; +static pthread_mutex_t adist_recv_list_lock; +static pthread_cond_t adist_recv_list_cond; + +static void +init_environment(void) +{ + struct adreq *adreq; + unsigned int ii; + + rw_init(&adist_remote_lock); + mtx_init(&adist_remote_mtx); + cv_init(&adist_remote_cond); + TAILQ_INIT(&adist_free_list); + mtx_init(&adist_free_list_lock); + cv_init(&adist_free_list_cond); + TAILQ_INIT(&adist_send_list); + mtx_init(&adist_send_list_lock); + cv_init(&adist_send_list_cond); + TAILQ_INIT(&adist_recv_list); + mtx_init(&adist_recv_list_lock); + cv_init(&adist_recv_list_cond); + + for (ii = 0; ii < ADIST_QUEUE_SIZE; ii++) { + adreq = malloc(sizeof(*adreq) + ADIST_BUF_SIZE); + if (adreq == NULL) { + pjdlog_exitx(EX_TEMPFAIL, + "Unable to allocate %zu bytes of memory for adreq object.", + sizeof(*adreq) + ADIST_BUF_SIZE); + } + adreq->adr_byteorder = ADIST_BYTEORDER; + adreq->adr_cmd = ADIST_CMD_UNDEFINED; + adreq->adr_seq = 0; + adreq->adr_datasize = 0; + TAILQ_INSERT_TAIL(&adist_free_list, adreq, adr_next); + } +} + +static int +sender_connect(void) +{ + unsigned char rnd[32], hash[32], resp[32]; + struct proto_conn *conn; + char welcome[8]; + int16_t val; + + val = 1; + if (proto_send(adhost->adh_conn, &val, sizeof(val)) < 0) { + pjdlog_exit(EX_TEMPFAIL, + "Unable to send connection request to parent"); + } + if (proto_recv(adhost->adh_conn, &val, sizeof(val)) < 0) { + pjdlog_exit(EX_TEMPFAIL, + "Unable to receive reply to connection request from parent"); + } + if (val != 0) { + errno = val; + pjdlog_errno(LOG_WARNING, "Unable to connect to %s", + adhost->adh_remoteaddr); + return (-1); + } + if (proto_connection_recv(adhost->adh_conn, true, &conn) < 0) { + pjdlog_exit(EX_TEMPFAIL, + "Unable to receive connection from parent"); + } + if (proto_connect_wait(conn, adcfg->adc_timeout) < 0) { + pjdlog_errno(LOG_WARNING, "Unable to connect to %s", + adhost->adh_remoteaddr); + proto_close(conn); + return (-1); + } + pjdlog_debug(1, "Connected to %s.", adhost->adh_remoteaddr); + /* Error in setting timeout is not critical, but why should it fail? */ + if (proto_timeout(conn, adcfg->adc_timeout) < 0) + pjdlog_errno(LOG_WARNING, "Unable to set connection timeout"); + else + pjdlog_debug(1, "Timeout set to %d.", adcfg->adc_timeout); + + /* Exchange welcome message, which includes version number. */ + (void)snprintf(welcome, sizeof(welcome), "ADIST%02d", ADIST_VERSION); + if (proto_send(conn, welcome, sizeof(welcome)) < 0) { + pjdlog_errno(LOG_WARNING, + "Unable to send welcome message to %s", + adhost->adh_remoteaddr); + proto_close(conn); + return (-1); + } + pjdlog_debug(1, "Welcome message sent (%s).", welcome); + bzero(welcome, sizeof(welcome)); + if (proto_recv(conn, welcome, sizeof(welcome)) < 0) { + pjdlog_errno(LOG_WARNING, + "Unable to receive welcome message from %s", + adhost->adh_remoteaddr); + proto_close(conn); + return (-1); + } + if (strncmp(welcome, "ADIST", 5) != 0 || !isdigit(welcome[5]) || + !isdigit(welcome[6]) || welcome[7] != '\0') { + pjdlog_warning("Invalid welcome message from %s.", + adhost->adh_remoteaddr); + proto_close(conn); + return (-1); + } + pjdlog_debug(1, "Welcome message received (%s).", welcome); + /* + * Receiver can only reply with version number lower or equal to + * the one we sent. + */ + adhost->adh_version = atoi(welcome + 5); + if (adhost->adh_version > ADIST_VERSION) { + pjdlog_warning("Invalid version number from %s (%d received, up to %d supported).", + adhost->adh_remoteaddr, adhost->adh_version, ADIST_VERSION); + proto_close(conn); + return (-1); + } + + pjdlog_debug(1, "Version %d negotiated with %s.", adhost->adh_version, + adhost->adh_remoteaddr); + + if (proto_send(conn, adcfg->adc_name, sizeof(adcfg->adc_name)) == -1) { + pjdlog_errno(LOG_WARNING, "Unable to send name to %s", + adhost->adh_remoteaddr); + proto_close(conn); + return (-1); + } + pjdlog_debug(1, "Name (%s) sent.", adcfg->adc_name); + + if (proto_recv(conn, rnd, sizeof(rnd)) == -1) { + pjdlog_errno(LOG_WARNING, "Unable to receive challenge from %s", + adhost->adh_remoteaddr); + proto_close(conn); + return (-1); + } + pjdlog_debug(1, "Challenge received."); + + if (HMAC(EVP_sha256(), adhost->adh_password, + (int)strlen(adhost->adh_password), rnd, (int)sizeof(rnd), hash, + NULL) == NULL) { + pjdlog_warning("Unable to generate response."); + proto_close(conn); + return (-1); + } + pjdlog_debug(1, "Response generated."); + + if (proto_send(conn, hash, sizeof(hash)) == -1) { + pjdlog_errno(LOG_WARNING, "Unable to send response to %s", + adhost->adh_remoteaddr); + proto_close(conn); + return (-1); + } + pjdlog_debug(1, "Response sent."); + + if (adist_random(rnd, sizeof(rnd)) == -1) { + pjdlog_warning("Unable to generate challenge."); + proto_close(conn); + return (-1); + } + pjdlog_debug(1, "Challenge generated."); + + if (proto_send(conn, rnd, sizeof(rnd)) == -1) { + pjdlog_errno(LOG_WARNING, "Unable to send challenge to %s", + adhost->adh_remoteaddr); + proto_close(conn); + return (-1); + } + pjdlog_debug(1, "Challenge sent."); + + if (proto_recv(conn, resp, sizeof(resp)) == -1) { + pjdlog_errno(LOG_WARNING, "Unable to receive response from %s", + adhost->adh_remoteaddr); + proto_close(conn); + return (-1); + } + pjdlog_debug(1, "Response received."); + + if (HMAC(EVP_sha256(), adhost->adh_password, + (int)strlen(adhost->adh_password), rnd, (int)sizeof(rnd), hash, + NULL) == NULL) { + pjdlog_warning("Unable to generate hash."); + proto_close(conn); + return (-1); + } + pjdlog_debug(1, "Hash generated."); + + if (memcmp(resp, hash, sizeof(hash)) != 0) { + pjdlog_warning("Invalid response from %s (wrong password?).", + adhost->adh_remoteaddr); + proto_close(conn); + return (-1); + } + pjdlog_info("Receiver authenticated."); + + if (proto_recv(conn, &adhost->adh_trail_offset, + sizeof(adhost->adh_trail_offset)) == -1) { + pjdlog_errno(LOG_WARNING, + "Unable to receive size of the most recent trail file from %s", + adhost->adh_remoteaddr); + proto_close(conn); + return (-1); + } + adhost->adh_trail_offset = le64toh(adhost->adh_trail_offset); + if (proto_recv(conn, &adhost->adh_trail_name, + sizeof(adhost->adh_trail_name)) == -1) { + pjdlog_errno(LOG_WARNING, + "Unable to receive name of the most recent trail file from %s", + adhost->adh_remoteaddr); + proto_close(conn); + return (-1); + } + pjdlog_debug(1, "Trail name (%s) and offset (%ju) received.", + adhost->adh_trail_name, (uintmax_t)adhost->adh_trail_offset); + + rw_wlock(&adist_remote_lock); + mtx_lock(&adist_remote_mtx); + PJDLOG_ASSERT(adhost->adh_remote == NULL); + PJDLOG_ASSERT(conn != NULL); + adhost->adh_remote = conn; + mtx_unlock(&adist_remote_mtx); + rw_unlock(&adist_remote_lock); + cv_signal(&adist_remote_cond); + + return (0); +} + +static void +sender_disconnect(void) +{ + + rw_wlock(&adist_remote_lock); + /* + * Check for a race between dropping rlock and acquiring wlock - + * another thread can close connection in-between. + */ + if (adhost->adh_remote == NULL) { + rw_unlock(&adist_remote_lock); + return; + } + pjdlog_debug(2, "Closing connection to %s.", adhost->adh_remoteaddr); + proto_close(adhost->adh_remote); + mtx_lock(&adist_remote_mtx); + adhost->adh_remote = NULL; + adhost->adh_reset = true; + adhost->adh_trail_name[0] = '\0'; + adhost->adh_trail_offset = 0; + mtx_unlock(&adist_remote_mtx); + rw_unlock(&adist_remote_lock); + + pjdlog_warning("Disconnected from %s.", adhost->adh_remoteaddr); + + /* Move all in-flight requests back onto free list. */ + mtx_lock(&adist_free_list_lock); + mtx_lock(&adist_send_list_lock); + TAILQ_CONCAT(&adist_free_list, &adist_send_list, adr_next); + mtx_unlock(&adist_send_list_lock); + mtx_lock(&adist_recv_list_lock); + TAILQ_CONCAT(&adist_free_list, &adist_recv_list, adr_next); + mtx_unlock(&adist_recv_list_lock); + mtx_unlock(&adist_free_list_lock); +} + +static void +adreq_fill(struct adreq *adreq, uint8_t cmd, const unsigned char *data, + size_t size) +{ + static uint64_t seq = 1; + + PJDLOG_ASSERT(size <= ADIST_BUF_SIZE); + + switch (cmd) { + case ADIST_CMD_OPEN: + case ADIST_CMD_CLOSE: + PJDLOG_ASSERT(data != NULL && size == 0); + size = strlen(data) + 1; + break; + case ADIST_CMD_APPEND: + PJDLOG_ASSERT(data != NULL && size > 0); + break; + case ADIST_CMD_KEEPALIVE: + case ADIST_CMD_ERROR: + PJDLOG_ASSERT(data == NULL && size == 0); + break; + default: + PJDLOG_ABORT("Invalid command (%hhu).", cmd); + } + + adreq->adr_cmd = cmd; + adreq->adr_seq = seq++; + adreq->adr_datasize = size; + /* Don't copy if data is already in out buffer. */ + if (data != NULL && data != adreq->adr_data) + bcopy(data, adreq->adr_data, size); +} + +static bool +read_thread_wait(void) +{ + bool newfile = false; + + mtx_lock(&adist_remote_mtx); + if (adhost->adh_reset) { + adhost->adh_reset = false; + if (trail_filefd(adist_trail) != -1) + trail_close(adist_trail); + trail_reset(adist_trail); + while (adhost->adh_remote == NULL) + cv_wait(&adist_remote_cond, &adist_remote_mtx); + trail_start(adist_trail, adhost->adh_trail_name, + adhost->adh_trail_offset); + newfile = true; + } + mtx_unlock(&adist_remote_mtx); + while (trail_filefd(adist_trail) == -1) { + newfile = true; + wait_for_dir(); + if (trail_filefd(adist_trail) == -1) + trail_next(adist_trail); + } + if (newfile) { + pjdlog_debug(1, "Trail file \"%s/%s\" opened.", + adhost->adh_directory, + trail_filename(adist_trail)); + (void)wait_for_file_init(trail_filefd(adist_trail)); + } + return (newfile); +} + +static void * +read_thread(void *arg __unused) +{ + struct adreq *adreq; + ssize_t done; + bool newfile; + + pjdlog_debug(1, "%s started.", __func__); + + for (;;) { + newfile = read_thread_wait(); + QUEUE_TAKE(adreq, &adist_free_list, 0); + if (newfile) { + adreq_fill(adreq, ADIST_CMD_OPEN, + trail_filename(adist_trail), 0); + newfile = false; + goto move; + } + + done = read(trail_filefd(adist_trail), adreq->adr_data, + ADIST_BUF_SIZE); + if (done == -1) { + off_t offset; + int error; + + error = errno; + offset = lseek(trail_filefd(adist_trail), 0, SEEK_CUR); + errno = error; + pjdlog_errno(LOG_ERR, + "Error while reading \"%s/%s\" at offset %jd", + adhost->adh_directory, trail_filename(adist_trail), + offset); + trail_close(adist_trail); + adreq_fill(adreq, ADIST_CMD_ERROR, NULL, 0); + goto move; + } else if (done == 0) { + /* End of file. */ + pjdlog_debug(3, "End of \"%s/%s\".", + adhost->adh_directory, trail_filename(adist_trail)); + if (!trail_switch(adist_trail)) { + /* More audit records can arrive. */ + mtx_lock(&adist_free_list_lock); + TAILQ_INSERT_TAIL(&adist_free_list, adreq, + adr_next); + mtx_unlock(&adist_free_list_lock); + wait_for_file(); + continue; + } + adreq_fill(adreq, ADIST_CMD_CLOSE, + trail_filename(adist_trail), 0); + trail_close(adist_trail); + goto move; + } + + adreq_fill(adreq, ADIST_CMD_APPEND, adreq->adr_data, done); +move: + pjdlog_debug(3, + "read thread: Moving request %p to the send queue (%hhu).", + adreq, adreq->adr_cmd); + QUEUE_INSERT(adreq, &adist_send_list); + } + /* NOTREACHED */ + return (NULL); +} + +static void +keepalive_send(void) +{ + struct adreq *adreq; + + rw_rlock(&adist_remote_lock); + if (adhost->adh_remote == NULL) { + rw_unlock(&adist_remote_lock); + return; + } + rw_unlock(&adist_remote_lock); + + mtx_lock(&adist_free_list_lock); + adreq = TAILQ_FIRST(&adist_free_list); + if (adreq != NULL) + TAILQ_REMOVE(&adist_free_list, adreq, adr_next); + mtx_unlock(&adist_free_list_lock); + if (adreq == NULL) + return; + + adreq_fill(adreq, ADIST_CMD_KEEPALIVE, NULL, 0); + + QUEUE_INSERT(adreq, &adist_send_list); + + pjdlog_debug(3, "keepalive_send: Request sent."); +} + +/* + * Thread sends request to secondary node. + */ +static void * +send_thread(void *arg __unused) +{ + time_t lastcheck, now; + struct adreq *adreq; + + pjdlog_debug(1, "%s started.", __func__); + + lastcheck = time(NULL); + + for (;;) { + pjdlog_debug(3, "send thread: Taking request."); + for (;;) { + QUEUE_TAKE(adreq, &adist_send_list, ADIST_KEEPALIVE); + if (adreq != NULL) + break; + now = time(NULL); + if (lastcheck + ADIST_KEEPALIVE <= now) { + keepalive_send(); + lastcheck = now; + } + } + PJDLOG_ASSERT(adreq != NULL); + pjdlog_debug(3, "send thread: (%p) Got request %hhu.", adreq, + adreq->adr_cmd); + /* + * Protect connection from disappearing. + */ + rw_rlock(&adist_remote_lock); + /* + * Move the request to the recv queue first to avoid race + * where the recv thread receives the reply before we move + * the request to the recv queue. + */ + QUEUE_INSERT(adreq, &adist_recv_list); + if (adhost->adh_remote == NULL || + proto_send(adhost->adh_remote, &adreq->adr_packet, + ADPKT_SIZE(adreq)) == -1) { + rw_unlock(&adist_remote_lock); + pjdlog_debug(1, + "send thread: (%p) Unable to send request.", adreq); + if (adhost->adh_remote != NULL) + sender_disconnect(); + continue; + } else { + pjdlog_debug(3, "Request %p sent successfully.", adreq); + adreq_log(LOG_DEBUG, 2, -1, adreq, + "send: (%p) Request sent: ", adreq); + rw_unlock(&adist_remote_lock); + } + } + /* NOTREACHED */ + return (NULL); +} + +static void +adrep_decode_header(struct adrep *adrep) +{ + + /* Byte-swap only is the receiver is using different byte order. */ + if (adrep->adrp_byteorder != ADIST_BYTEORDER) { + adrep->adrp_byteorder = ADIST_BYTEORDER; + adrep->adrp_seq = bswap64(adrep->adrp_seq); + adrep->adrp_error = bswap16(adrep->adrp_error); + } +} + +/* + * Thread receives answer from secondary node and passes it to ggate_send + * thread. + */ +static void * +recv_thread(void *arg __unused) +{ + struct adrep adrep; + struct adreq *adreq; + + pjdlog_debug(1, "%s started.", __func__); + + for (;;) { + /* Wait until there is anything to receive. */ + QUEUE_WAIT(&adist_recv_list); + pjdlog_debug(3, "recv thread: Got something."); + rw_rlock(&adist_remote_lock); + if (adhost->adh_remote == NULL) { + /* + * Connection is dead. + * XXX: We shouldn't be here. + */ + rw_unlock(&adist_remote_lock); + continue; + } + if (proto_recv(adhost->adh_remote, &adrep, + sizeof(adrep)) == -1) { + rw_unlock(&adist_remote_lock); + pjdlog_errno(LOG_ERR, "Unable to receive reply"); + sender_disconnect(); + continue; + } + rw_unlock(&adist_remote_lock); + adrep_decode_header(&adrep); + /* + * Find the request that was just confirmed. + */ + mtx_lock(&adist_recv_list_lock); + TAILQ_FOREACH(adreq, &adist_recv_list, adr_next) { + if (adreq->adr_seq == adrep.adrp_seq) { + TAILQ_REMOVE(&adist_recv_list, adreq, + adr_next); + break; + } + } + if (adreq == NULL) { + /* + * If we disconnected in the meantime, just continue. + * On disconnect sender_disconnect() clears the queue, + * we can use that. + */ + if (TAILQ_EMPTY(&adist_recv_list)) { + rw_unlock(&adist_remote_lock); + continue; + } + mtx_unlock(&adist_recv_list_lock); + pjdlog_error("Found no request matching received 'seq' field (%ju).", + (uintmax_t)adrep.adrp_seq); + sender_disconnect(); + continue; + } + mtx_unlock(&adist_recv_list_lock); + adreq_log(LOG_DEBUG, 2, -1, adreq, + "recv thread: (%p) Request confirmed: ", adreq); + pjdlog_debug(3, "recv thread: (%p) Got request %hhu.", adreq, + adreq->adr_cmd); + if (adrep.adrp_error != 0) { + pjdlog_error("Receiver returned error (%s), disconnecting.", + adist_errstr((int)adrep.adrp_error)); + sender_disconnect(); + continue; + } + if (adreq->adr_cmd == ADIST_CMD_CLOSE) + trail_unlink(adist_trail, adreq->adr_data); + pjdlog_debug(3, "Request received successfully."); + QUEUE_INSERT(adreq, &adist_free_list); + } + /* NOTREACHED */ + return (NULL); +} + +static void +guard_check_connection(void) +{ + + PJDLOG_ASSERT(adhost->adh_role == ADIST_ROLE_SENDER); + + rw_rlock(&adist_remote_lock); + if (adhost->adh_remote != NULL) { + rw_unlock(&adist_remote_lock); + pjdlog_debug(3, "remote_guard: Connection to %s is ok.", + adhost->adh_remoteaddr); + return; + } + + /* + * Upgrade the lock. It doesn't have to be atomic as no other thread + * can change connection status from disconnected to connected. + */ + rw_unlock(&adist_remote_lock); + pjdlog_debug(1, "remote_guard: Reconnecting to %s.", + adhost->adh_remoteaddr); + if (sender_connect() == 0) { + pjdlog_info("Successfully reconnected to %s.", + adhost->adh_remoteaddr); + } else { + pjdlog_debug(1, "remote_guard: Reconnect to %s failed.", + adhost->adh_remoteaddr); + } +} + +/* + * Thread guards remote connections and reconnects when needed, handles + * signals, etc. + */ +static void * +guard_thread(void *arg __unused) +{ + struct timespec timeout; + time_t lastcheck, now; + sigset_t mask; + int signo; + + lastcheck = time(NULL); + + PJDLOG_VERIFY(sigemptyset(&mask) == 0); + PJDLOG_VERIFY(sigaddset(&mask, SIGINT) == 0); + PJDLOG_VERIFY(sigaddset(&mask, SIGTERM) == 0); + + timeout.tv_sec = ADIST_KEEPALIVE; + timeout.tv_nsec = 0; + signo = -1; + + for (;;) { + switch (signo) { + case SIGINT: + case SIGTERM: + sigexit_received = true; + pjdlog_exitx(EX_OK, + "Termination signal received, exiting."); + break; + default: + break; + } + + pjdlog_debug(3, "remote_guard: Checking connections."); + now = time(NULL); + if (lastcheck + ADIST_KEEPALIVE <= now) { + guard_check_connection(); + lastcheck = now; + } + signo = sigtimedwait(&mask, NULL, &timeout); + } + /* NOTREACHED */ + return (NULL); +} + +void +adist_sender(struct adist_config *config, struct adist_host *adh) +{ + pthread_t td; + pid_t pid; + int error, mode, debuglevel; + + /* + * Create communication channel for sending connection requests from + * child to parent. + */ + if (proto_connect(NULL, "socketpair://", -1, &adh->adh_conn) == -1) { + pjdlog_errno(LOG_ERR, + "Unable to create connection sockets between child and parent"); + return; + } + + pid = fork(); + if (pid == -1) { + pjdlog_errno(LOG_ERR, "Unable to fork"); + proto_close(adh->adh_conn); + adh->adh_conn = NULL; + return; + } + + if (pid > 0) { + /* This is parent. */ + adh->adh_worker_pid = pid; + /* Declare that we are receiver. */ + proto_recv(adh->adh_conn, NULL, 0); + return; + } + + adcfg = config; + adhost = adh; + + mode = pjdlog_mode_get(); + debuglevel = pjdlog_debug_get(); + + /* Declare that we are sender. */ + proto_send(adhost->adh_conn, NULL, 0); + + descriptors_cleanup(adhost); + +#ifdef TODO + descriptors_assert(adhost, mode); +#endif + + pjdlog_init(mode); + pjdlog_debug_set(debuglevel); + pjdlog_prefix_set("[%s] (%s) ", adhost->adh_name, + role2str(adhost->adh_role)); +#ifdef HAVE_SETPROCTITLE + setproctitle("[%s] (%s) ", adhost->adh_name, + role2str(adhost->adh_role)); +#endif + + /* + * The sender process should be able to remove entries from its + * trail directory, but it should not be able to write to the + * trail files, only read from them. + */ + adist_trail = trail_new(adhost->adh_directory, false); + if (adist_trail == NULL) + exit(EX_OSFILE); + + if (sandbox(ADIST_USER, true, "auditdistd: %s (%s)", + role2str(adhost->adh_role), adhost->adh_name) != 0) { + exit(EX_CONFIG); + } + pjdlog_info("Privileges successfully dropped."); + + /* + * We can ignore wait_for_dir_init() failures. It will fall back to + * using sleep(3). + */ + (void)wait_for_dir_init(trail_dirfd(adist_trail)); + + init_environment(); + if (sender_connect() == 0) { + pjdlog_info("Successfully connected to %s.", + adhost->adh_remoteaddr); + } + adhost->adh_reset = true; + + /* + * Create the guard thread first, so we can handle signals from the + * very begining. + */ + error = pthread_create(&td, NULL, guard_thread, NULL); + PJDLOG_ASSERT(error == 0); + error = pthread_create(&td, NULL, send_thread, NULL); + PJDLOG_ASSERT(error == 0); + error = pthread_create(&td, NULL, recv_thread, NULL); + PJDLOG_ASSERT(error == 0); + (void)read_thread(NULL); +} diff --git a/contrib/openbsm/bin/auditdistd/sigtimedwait.h b/contrib/openbsm/bin/auditdistd/sigtimedwait.h new file mode 100644 index 0000000..187c6d6 --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/sigtimedwait.h @@ -0,0 +1,92 @@ +/*- + * Copyright (c) 2012 The FreeBSD Foundation + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/sigtimedwait.h#2 $ + */ + +#ifndef _SIGTIMEDWAIT_H_ +#define _SIGTIMEDWAIT_H_ + +#include <sys/types.h> +#include <sys/time.h> + +#include <assert.h> +#include <errno.h> +#include <signal.h> +#include <stdio.h> +#include <string.h> +#include <unistd.h> + +#include "pjdlog.h" + +static int +sigtimedwait(const sigset_t *set, siginfo_t *info, + const struct timespec *timeout) +{ + struct itimerval it; + sigset_t mask; + int error, signo; + + PJDLOG_ASSERT(info == NULL); + + PJDLOG_VERIFY(sigemptyset(&mask) == 0); + PJDLOG_VERIFY(sigaddset(&mask, SIGALRM) == 0); + PJDLOG_VERIFY(sigprocmask(SIG_BLOCK, &mask, NULL) == 0); + + timerclear(&it.it_interval); + it.it_value.tv_sec = timeout->tv_sec; + it.it_value.tv_usec = timeout->tv_nsec / 1000; + if (it.it_value.tv_sec == 0 && it.it_value.tv_usec == 0) + it.it_value.tv_usec = 1; + PJDLOG_VERIFY(setitimer(ITIMER_REAL, &it, NULL) == 0); + + bcopy(set, &mask, sizeof(mask)); + PJDLOG_VERIFY(sigaddset(&mask, SIGALRM) == 0); + + PJDLOG_VERIFY(sigwait(&mask, &signo) == 0); + error = errno; + + timerclear(&it.it_interval); + timerclear(&it.it_value); + PJDLOG_VERIFY(setitimer(ITIMER_REAL, &it, NULL) == 0); + + PJDLOG_VERIFY(sigemptyset(&mask) == 0); + PJDLOG_VERIFY(sigaddset(&mask, SIGALRM) == 0); + PJDLOG_VERIFY(sigprocmask(SIG_UNBLOCK, &mask, NULL) == 0); + + if (signo == SIGALRM) { + errno = EAGAIN; + signo = -1; + } else { + errno = error; + } + + return (signo); +} + +#endif /* !_SIGTIMEDWAIT_H_ */ diff --git a/contrib/openbsm/bin/auditdistd/strndup.h b/contrib/openbsm/bin/auditdistd/strndup.h new file mode 100644 index 0000000..6cf3c95 --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/strndup.h @@ -0,0 +1,55 @@ +/*- + * Copyright (c) 2012 The FreeBSD Foundation + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/strndup.h#1 $ + */ + +#ifndef _STRNDUP_H_ +#define _STRNDUP_H_ + +#include <stdlib.h> +#include <string.h> + +static char * +strndup(const char *str, size_t len) +{ + size_t outlen; + char *outstr; + + outlen = strlen(str); + if (outlen > len) + outlen = len; + outstr = malloc(outlen + 1); + if (outstr != NULL) { + memcpy(outstr, str, outlen); + outstr[outlen] = '\0'; + } + return (outstr); +} + +#endif /* !_STRNDUP_H_ */ diff --git a/contrib/openbsm/bin/auditdistd/subr.c b/contrib/openbsm/bin/auditdistd/subr.c new file mode 100644 index 0000000..e98ed1e --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/subr.c @@ -0,0 +1,301 @@ +/*- + * Copyright (c) 2011-2012 Pawel Jakub Dawidek <pawel@dawidek.net> + * All rights reserved. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/subr.c#3 $ + */ + +#include <config/config.h> + +#ifdef HAVE_KQUEUE +#include <sys/types.h> +#include <sys/event.h> +#include <sys/time.h> +#endif + +#include <errno.h> +#include <stdarg.h> +#include <stdio.h> +#include <string.h> +#include <unistd.h> + +#ifndef HAVE_ARC4RANDOM +#include <openssl/rand.h> +#endif + +#ifndef HAVE_STRLCAT +#include <compat/strlcat.h> +#endif + +#include "auditdistd.h" +#include "pjdlog.h" +#include "subr.h" + +int +vsnprlcat(char *str, size_t size, const char *fmt, va_list ap) +{ + size_t len; + + len = strlen(str); + return (vsnprintf(str + len, size - len, fmt, ap)); +} + +int +snprlcat(char *str, size_t size, const char *fmt, ...) +{ + va_list ap; + int result; + + va_start(ap, fmt); + result = vsnprlcat(str, size, fmt, ap); + va_end(ap); + return (result); +} + +const char * +role2str(int role) +{ + + switch (role) { + case ADIST_ROLE_SENDER: + return ("sender"); + case ADIST_ROLE_RECEIVER: + return ("receiver"); + } + return ("unknown"); +} + +const char * +adist_errstr(int error) +{ + + switch (error) { + case ADIST_ERROR_WRONG_ORDER: + return ("wrong operations order"); + case ADIST_ERROR_INVALID_NAME: + return ("invalid trail file name"); + case ADIST_ERROR_OPEN_OLD: + return ("attempt to open an old trail file"); + case ADIST_ERROR_CREATE: + return ("creation of new trail file failed"); + case ADIST_ERROR_OPEN: + return ("open of existing trail file failed"); + case ADIST_ERROR_READ: + return ("read failed"); + case ADIST_ERROR_WRITE: + return ("write failed"); + case ADIST_ERROR_RENAME: + return ("rename of a trail file failed"); + default: + return ("unknown error"); + } +} + +void +adreq_log(int loglevel, int debuglevel, int error, struct adreq *adreq, + const char *fmt, ...) +{ + char msg[1024]; + va_list ap; + + va_start(ap, fmt); + (void)vsnprintf(msg, sizeof(msg), fmt, ap); + va_end(ap); + (void)snprlcat(msg, sizeof(msg), "(seq=%ju) ", + (uintmax_t)adreq->adr_seq); + switch (adreq->adr_cmd) { + case ADIST_CMD_OPEN: + (void)snprlcat(msg, sizeof(msg), "OPEN(%s)", + adreq->adr_data); + break; + case ADIST_CMD_APPEND: + (void)snprlcat(msg, sizeof(msg), "APPEND(%ju)", + (uintmax_t)adreq->adr_datasize); + break; + case ADIST_CMD_CLOSE: + (void)snprlcat(msg, sizeof(msg), "CLOSE(%s)", + adreq->adr_data); + break; + case ADIST_CMD_KEEPALIVE: + (void)snprlcat(msg, sizeof(msg), "KEEPALIVE"); + break; + case ADIST_CMD_ERROR: + (void)snprlcat(msg, sizeof(msg), "ERROR"); + break; + default: + (void)snprlcat(msg, sizeof(msg), "UNKNOWN(%hhu)", + adreq->adr_cmd); + break; + } + if (error != -1) + (void)snprlcat(msg, sizeof(msg), ": %s", adist_errstr(error)); + (void)strlcat(msg, ".", sizeof(msg)); + pjdlog_common(loglevel, debuglevel, -1, "%s", msg); +} + +int +adist_random(unsigned char *buf, size_t size) +{ +#ifdef HAVE_ARC4RANDOM_BUF + arc4random_buf(buf, size); + return (0); +#elif defined(HAVE_ARC4RANDOM) + uint32_t val; + + PJDLOG_ASSERT(size > 0); + PJDLOG_ASSERT((size % sizeof(val)) == 0); + + do { + val = arc4random(); + bcopy(&val, buf, sizeof(val)); + buf += sizeof(val); + size -= sizeof(val); + } while (size > 0); + + return (0); +#else + if (RAND_bytes(buf, (int)size) == 0) + return (-1); + return (0); +#endif +} + +static int wait_for_dir_kq = -1; +static int wait_for_file_kq = -1; + +int +wait_for_dir_init(int fd) +{ +#ifdef HAVE_KQUEUE + struct kevent ev; + int error, kq; + + PJDLOG_ASSERT(wait_for_dir_kq == -1); +#endif + + PJDLOG_ASSERT(fd != -1); + +#ifdef HAVE_KQUEUE + kq = kqueue(); + if (kq == -1) { + pjdlog_errno(LOG_WARNING, "kqueue() failed"); + return (-1); + } + EV_SET(&ev, fd, EVFILT_VNODE, EV_ADD | EV_ENABLE | EV_CLEAR, + NOTE_WRITE, 0, 0); + if (kevent(kq, &ev, 1, NULL, 0, NULL) == -1) { + error = errno; + pjdlog_errno(LOG_WARNING, "kevent() failed"); + (void)close(kq); + errno = error; + return (-1); + } + wait_for_dir_kq = kq; +#endif + + return (0); +} + +int +wait_for_file_init(int fd) +{ +#ifdef HAVE_KQUEUE + struct kevent ev[2]; + int error, kq; +#endif + + PJDLOG_ASSERT(fd != -1); + +#ifdef HAVE_KQUEUE + kq = kqueue(); + if (kq == -1) { + pjdlog_errno(LOG_WARNING, "kqueue() failed"); + return (-1); + } + EV_SET(&ev[0], fd, EVFILT_VNODE, EV_ADD | EV_ENABLE | EV_CLEAR, + NOTE_RENAME, 0, 0); + EV_SET(&ev[1], fd, EVFILT_READ, EV_ADD | EV_ENABLE | EV_CLEAR, + 0, 0, 0); + if (kevent(kq, ev, 2, NULL, 0, NULL) == -1) { + error = errno; + pjdlog_errno(LOG_WARNING, "kevent() failed"); + (void)close(kq); + errno = error; + return (-1); + } + wait_for_file_kq = kq; +#endif + + return (0); +} + +/* + * Wait for new file to appear in directory. + */ +void +wait_for_dir(void) +{ +#ifdef HAVE_KQUEUE + struct kevent ev; +#endif + + if (wait_for_dir_kq == -1) { + sleep(1); + return; + } + +#ifdef HAVE_KQUEUE + PJDLOG_ASSERT(wait_for_dir_kq != -1); + + if (kevent(wait_for_dir_kq, NULL, 0, &ev, 1, NULL) == -1) { + pjdlog_errno(LOG_WARNING, "kevent() failed"); + sleep(1); + } +#endif +} + +/* + * Wait for file growth or rename. + */ +void +wait_for_file(void) +{ +#ifdef HAVE_KQUEUE + struct kevent ev[2]; +#endif + + if (wait_for_file_kq == -1) { + sleep(1); + return; + } + +#ifdef HAVE_KQUEUE + PJDLOG_ASSERT(wait_for_file_kq != -1); + + if (kevent(wait_for_file_kq, NULL, 0, ev, 2, NULL) == -1) { + pjdlog_errno(LOG_WARNING, "kevent() failed"); + sleep(1); + } +#endif +} diff --git a/contrib/openbsm/bin/auditdistd/subr.h b/contrib/openbsm/bin/auditdistd/subr.h new file mode 100644 index 0000000..2f11b65 --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/subr.h @@ -0,0 +1,60 @@ +/*- + * Copyright (c) 2011 Pawel Jakub Dawidek <pawel@dawidek.net> + * All rights reserved. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/subr.h#1 $ + */ + +#ifndef _AUDITDISTD_SUBR_H_ +#define _AUDITDISTD_SUBR_H_ + +#include <sys/types.h> + +#include "auditdistd.h" + +#define KEEP_ERRNO(work) do { \ + int _rerrno; \ + \ + _rerrno = errno; \ + work; \ + errno = _rerrno; \ +} while (0) + +int vsnprlcat(char *str, size_t size, const char *fmt, va_list ap); +int snprlcat(char *str, size_t size, const char *fmt, ...); + +const char *role2str(int role); +const char *adist_errstr(int error); + +void adreq_log(int loglevel, int debuglevel, int error, struct adreq *adreq, + const char *fmt, ...); + +int adist_random(unsigned char *buf, size_t size); + +int wait_for_dir_init(int fd); +int wait_for_file_init(int fd); +void wait_for_dir(void); +void wait_for_file(void); + +#endif /* !_AUDITDISTD_SUBR_H_ */ diff --git a/contrib/openbsm/bin/auditdistd/synch.h b/contrib/openbsm/bin/auditdistd/synch.h new file mode 100644 index 0000000..e6fe19d --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/synch.h @@ -0,0 +1,206 @@ +/*- + * Copyright (c) 2009-2010 The FreeBSD Foundation + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/synch.h#3 $ + */ + +#ifndef _SYNCH_H_ +#define _SYNCH_H_ + +#include <errno.h> +#include <pthread.h> +#ifdef HAVE_PTHREAD_NP_H +#include <pthread_np.h> +#endif +#include <stdbool.h> +#include <time.h> + +#include "pjdlog.h" + +#ifndef PJDLOG_ASSERT +#include <assert.h> +#define PJDLOG_ASSERT(...) assert(__VA_ARGS__) +#endif + +static __inline void +mtx_init(pthread_mutex_t *lock) +{ + int error; + + error = pthread_mutex_init(lock, NULL); + PJDLOG_ASSERT(error == 0); +} +static __inline void +mtx_destroy(pthread_mutex_t *lock) +{ + int error; + + error = pthread_mutex_destroy(lock); + PJDLOG_ASSERT(error == 0); +} +static __inline void +mtx_lock(pthread_mutex_t *lock) +{ + int error; + + error = pthread_mutex_lock(lock); + PJDLOG_ASSERT(error == 0); +} +static __inline bool +mtx_trylock(pthread_mutex_t *lock) +{ + int error; + + error = pthread_mutex_trylock(lock); + PJDLOG_ASSERT(error == 0 || error == EBUSY); + return (error == 0); +} +static __inline void +mtx_unlock(pthread_mutex_t *lock) +{ + int error; + + error = pthread_mutex_unlock(lock); + PJDLOG_ASSERT(error == 0); +} +static __inline bool +mtx_owned(pthread_mutex_t *lock) +{ + + return (pthread_mutex_isowned_np(lock) != 0); +} + +static __inline void +rw_init(pthread_rwlock_t *lock) +{ + int error; + + error = pthread_rwlock_init(lock, NULL); + PJDLOG_ASSERT(error == 0); +} +static __inline void +rw_destroy(pthread_rwlock_t *lock) +{ + int error; + + error = pthread_rwlock_destroy(lock); + PJDLOG_ASSERT(error == 0); +} +static __inline void +rw_rlock(pthread_rwlock_t *lock) +{ + int error; + + error = pthread_rwlock_rdlock(lock); + PJDLOG_ASSERT(error == 0); +} +static __inline void +rw_wlock(pthread_rwlock_t *lock) +{ + int error; + + error = pthread_rwlock_wrlock(lock); + PJDLOG_ASSERT(error == 0); +} +static __inline void +rw_unlock(pthread_rwlock_t *lock) +{ + int error; + + error = pthread_rwlock_unlock(lock); + PJDLOG_ASSERT(error == 0); +} + +static __inline void +cv_init(pthread_cond_t *cv) +{ + pthread_condattr_t attr; + int error; + + error = pthread_condattr_init(&attr); + PJDLOG_ASSERT(error == 0); +#ifdef HAVE_PTHREAD_CONDATTR_SETCLOCK + error = pthread_condattr_setclock(&attr, CLOCK_MONOTONIC); + PJDLOG_ASSERT(error == 0); +#endif + error = pthread_cond_init(cv, &attr); + PJDLOG_ASSERT(error == 0); + error = pthread_condattr_destroy(&attr); + PJDLOG_ASSERT(error == 0); +} +static __inline void +cv_wait(pthread_cond_t *cv, pthread_mutex_t *lock) +{ + int error; + + error = pthread_cond_wait(cv, lock); + PJDLOG_ASSERT(error == 0); +} +static __inline bool +cv_timedwait(pthread_cond_t *cv, pthread_mutex_t *lock, int timeout) +{ + struct timespec ts; + int error; + + if (timeout == 0) { + cv_wait(cv, lock); + return (false); + } + +#ifdef HAVE_PTHREAD_CONDATTR_SETCLOCK + error = clock_gettime(CLOCK_MONOTONIC, &ts); + PJDLOG_ASSERT(error == 0); + ts.tv_sec += timeout; + error = pthread_cond_timedwait(cv, lock, &ts); +#elif HAVE_PTHREAD_COND_TIMEDWAIT_RELATIVE_NP + ts.tv_sec = timeout; + ts.tv_nsec = 0; + error = pthread_cond_timedwait_relative_np(cv, lock, &ts); +#else +#error Neither pthread_condattr_setclock nor pthread_cond_timedwait_relative_np is available. +#endif + PJDLOG_ASSERT(error == 0 || error == ETIMEDOUT); + return (error == ETIMEDOUT); +} +static __inline void +cv_signal(pthread_cond_t *cv) +{ + int error; + + error = pthread_cond_signal(cv); + PJDLOG_ASSERT(error == 0); +} +static __inline void +cv_broadcast(pthread_cond_t *cv) +{ + int error; + + error = pthread_cond_broadcast(cv); + PJDLOG_ASSERT(error == 0); +} +#endif /* !_SYNCH_H_ */ diff --git a/contrib/openbsm/bin/auditdistd/token.l b/contrib/openbsm/bin/auditdistd/token.l new file mode 100644 index 0000000..9cebac1 --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/token.l @@ -0,0 +1,83 @@ +%{ +/*- + * Copyright (c) 2012 The FreeBSD Foundation + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/token.l#2 $ + */ + +#include <config/config.h> + +#include <stdio.h> +#include <string.h> + +#ifndef HAVE_STRNDUP +#include "strndup.h" +#endif + +#include "auditdistd.h" + +#include "parse.h" + +#define SECTION_GLOBAL 0 +#define SECTION_SENDER 1 +#define SECTION_RECEIVER 2 + +int cursection; +int depth; +int lineno; + +#define DP do { } while (0) +%} + +%option noinput +%option nounput +%option noyywrap + +%% +certfile { DP; return CERTFILE; } +directory { DP; return DIRECTORY; } +fingerprint { DP; return FINGERPRINT; } +host { DP; return HOST; } +keyfile { DP; return KEYFILE; } +listen { DP; return LISTEN; } +name { DP; return NAME; } +password { DP; return PASSWORD; } +pidfile { DP; return PIDFILE; } +receiver { DP; return RECEIVER; } +remote { DP; return REMOTE; } +sender { DP; return SENDER; } +source { DP; return SOURCE; } +timeout { DP; return TIMEOUT; } +[0-9]+ { DP; yylval.num = atoi(yytext); return NUM; } +\"[a-zA-Z0-9_/ !@#\$%\^\&\*\(\)\+\=\|\;\?\,\.\-\:]*\" { DP; yylval.str = strndup(yytext + 1, strlen(yytext) - 2); return STR; } +\{ { DP; depth++; return OB; } +\} { DP; depth--; return CB; } +#.*$ /* ignore comments */; +\n { lineno++; } +[ \t]+ /* ignore whitespace */; +%% diff --git a/contrib/openbsm/bin/auditdistd/trail.c b/contrib/openbsm/bin/auditdistd/trail.c new file mode 100644 index 0000000..d4be51e --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/trail.c @@ -0,0 +1,611 @@ +/*- + * Copyright (c) 2012 The FreeBSD Foundation + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/trail.c#3 $ + */ + +#include <config/config.h> + +#include <sys/param.h> +#include <sys/stat.h> + +#include <dirent.h> +#include <errno.h> +#include <fcntl.h> +#include <stdbool.h> +#include <stdint.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> + +#include <compat/compat.h> +#ifndef HAVE_STRLCPY +#include <compat/strlcpy.h> +#endif +#ifndef HAVE_FACCESSAT +#include "faccessat.h" +#endif +#ifndef HAVE_FSTATAT +#include "fstatat.h" +#endif +#ifndef HAVE_OPENAT +#include "openat.h" +#endif +#ifndef HAVE_UNLINKAT +#include "unlinkat.h" +#endif + +#include "pjdlog.h" +#include "trail.h" + +#define TRAIL_MAGIC 0x79a11 +struct trail { + int tr_magic; + /* Path usually to /var/audit/dist/ directory. */ + char tr_dirname[PATH_MAX]; + /* Descriptor to td_dirname directory. */ + DIR *tr_dirfp; + /* Path to audit trail file. */ + char tr_filename[PATH_MAX]; + /* Descriptor to audit trail file. */ + int tr_filefd; +}; + +#define HALF_LEN 14 + +bool +trail_is_not_terminated(const char *filename) +{ + + return (strcmp(filename + HALF_LEN, ".not_terminated") == 0); +} + +bool +trail_is_crash_recovery(const char *filename) +{ + + return (strcmp(filename + HALF_LEN, ".crash_recovery") == 0); +} + +struct trail * +trail_new(const char *dirname, bool create) +{ + struct trail *trail; + + trail = calloc(1, sizeof(*trail)); + + if (strlcpy(trail->tr_dirname, dirname, sizeof(trail->tr_dirname)) >= + sizeof(trail->tr_dirname)) { + free(trail); + pjdlog_error("Directory name too long (\"%s\").", dirname); + errno = ENAMETOOLONG; + return (NULL); + } + trail->tr_dirfp = opendir(dirname); + if (trail->tr_dirfp == NULL) { + if (create && errno == ENOENT) { + if (mkdir(dirname, 0700) == -1) { + pjdlog_errno(LOG_ERR, + "Unable to create directory \"%s\"", + dirname); + free(trail); + return (NULL); + } + /* TODO: Set directory ownership. */ + } else { + pjdlog_errno(LOG_ERR, + "Unable to open directory \"%s\"", + dirname); + free(trail); + return (NULL); + } + trail->tr_dirfp = opendir(dirname); + if (trail->tr_dirfp == NULL) { + pjdlog_errno(LOG_ERR, + "Unable to open directory \"%s\"", + dirname); + free(trail); + return (NULL); + } + } + trail->tr_filefd = -1; + trail->tr_magic = TRAIL_MAGIC; + return (trail); +} + +void +trail_free(struct trail *trail) +{ + + PJDLOG_ASSERT(trail->tr_magic == TRAIL_MAGIC); + + if (trail->tr_filefd != -1) + trail_close(trail); + closedir(trail->tr_dirfp); + bzero(trail, sizeof(*trail)); + trail->tr_magic = 0; + trail->tr_filefd = -1; + free(trail); +} + +static uint8_t +trail_type(DIR *dirfp, const char *filename) +{ + struct stat sb; + int dfd; + + PJDLOG_ASSERT(dirfp != NULL); + + dfd = dirfd(dirfp); + PJDLOG_ASSERT(dfd >= 0); + if (fstatat(dfd, filename, &sb, AT_SYMLINK_NOFOLLOW) == -1) { + pjdlog_errno(LOG_ERR, "Unable to stat \"%s\"", filename); + return (DT_UNKNOWN); + } + return (IFTODT(sb.st_mode)); +} + +/* + * Find trail file by first part of the name in case it was renamed. + * First part of the trail file name never changes, but trail file + * can be renamed when hosts are disconnected from .not_terminated + * to .[0-9]{14} or to .crash_recovery. + */ +static bool +trail_find(struct trail *trail) +{ + struct dirent *dp; + + PJDLOG_ASSERT(trail->tr_magic == TRAIL_MAGIC); + PJDLOG_ASSERT(trail_is_not_terminated(trail->tr_filename)); + + rewinddir(trail->tr_dirfp); + while ((dp = readdir(trail->tr_dirfp)) != NULL) { + if (strncmp(dp->d_name, trail->tr_filename, HALF_LEN + 1) == 0) + break; + } + if (dp == NULL) + return (false); + PJDLOG_VERIFY(strlcpy(trail->tr_filename, dp->d_name, + sizeof(trail->tr_filename)) < sizeof(trail->tr_filename)); + return (true); +} + +/* + * Open the given trail file and move pointer at the given offset, as this is + * where receiver finished the last time. + * If the file doesn't exist or the given offset is equal to the file size, + * move to the next trail file. + */ +void +trail_start(struct trail *trail, const char *filename, off_t offset) +{ + struct stat sb; + int dfd, fd; + + PJDLOG_ASSERT(trail->tr_magic == TRAIL_MAGIC); + + PJDLOG_VERIFY(strlcpy(trail->tr_filename, filename, + sizeof(trail->tr_filename)) < sizeof(trail->tr_filename)); + trail->tr_filefd = -1; + + if (trail->tr_filename[0] == '\0') { + PJDLOG_ASSERT(offset == 0); + trail_next(trail); + return; + } + + dfd = dirfd(trail->tr_dirfp); + PJDLOG_ASSERT(dfd >= 0); +again: + fd = openat(dfd, trail->tr_filename, O_RDONLY); + if (fd == -1) { + if (errno == ENOENT && + trail_is_not_terminated(trail->tr_filename) && + trail_find(trail)) { + /* File was renamed. Retry with new name. */ + pjdlog_debug(1, + "Trail file was renamed since last connection to \"%s/%s\".", + trail->tr_dirname, trail->tr_filename); + goto again; + } else if (errno == ENOENT) { + /* File disappeared. */ + pjdlog_debug(1, "File \"%s/%s\" doesn't exist.", + trail->tr_dirname, trail->tr_filename); + } else { + pjdlog_errno(LOG_ERR, + "Unable to open file \"%s/%s\", skipping", + trail->tr_dirname, trail->tr_filename); + } + trail_next(trail); + return; + } + if (fstat(fd, &sb) == -1) { + pjdlog_errno(LOG_ERR, + "Unable to stat file \"%s/%s\", skipping", + trail->tr_dirname, trail->tr_filename); + close(fd); + trail_next(trail); + return; + } + if (!S_ISREG(sb.st_mode)) { + pjdlog_warning("File \"%s/%s\" is not a regular file, skipping.", + trail->tr_dirname, trail->tr_filename); + close(fd); + trail_next(trail); + return; + } + /* + * We continue sending requested file if: + * 1. It is not fully sent yet, or + * 2. It is fully sent, but is not terminated, so new data can be + * appended still, or + * 3. It is fully sent but file name has changed. + * + * Note that we are fine if our .not_terminated or .crash_recovery file + * is smaller than the one on the receiver side, as it is possible that + * more data was send to the receiver than was safely stored on disk. + * We accept .not_terminated only because auditdistd can start before + * auditd manage to rename it to .crash_recovery. + */ + if (offset < sb.st_size || + (offset >= sb.st_size && + trail_is_not_terminated(trail->tr_filename)) || + (offset >= sb.st_size && trail_is_not_terminated(filename) && + trail_is_crash_recovery(trail->tr_filename))) { + /* File was not fully send. Let's finish it. */ + if (lseek(fd, offset, SEEK_SET) == -1) { + pjdlog_errno(LOG_ERR, + "Unable to move to offset %jd within file \"%s/%s\", skipping", + (intmax_t)offset, trail->tr_dirname, + trail->tr_filename); + close(fd); + trail_next(trail); + return; + } + if (!trail_is_crash_recovery(trail->tr_filename)) { + pjdlog_debug(1, + "Restarting file \"%s/%s\" at offset %jd.", + trail->tr_dirname, trail->tr_filename, + (intmax_t)offset); + } + trail->tr_filefd = fd; + return; + } + close(fd); + if (offset > sb.st_size) { + pjdlog_warning("File \"%s/%s\" shrinked, removing it.", + trail->tr_dirname, trail->tr_filename); + } else { + pjdlog_debug(1, "File \"%s/%s\" is already sent, removing it.", + trail->tr_dirname, trail->tr_filename); + } + /* Entire file is already sent or it shirnked, we can remove it. */ + if (unlinkat(dfd, trail->tr_filename, 0) == -1) { + pjdlog_errno(LOG_WARNING, "Unable to remove file \"%s/%s\"", + trail->tr_dirname, trail->tr_filename); + } + trail_next(trail); +} + +/* + * Set next file in the trail->tr_dirname directory and open it for reading. + */ +void +trail_next(struct trail *trail) +{ + char curfile[PATH_MAX]; + struct dirent *dp; + int dfd; + + PJDLOG_ASSERT(trail->tr_magic == TRAIL_MAGIC); + PJDLOG_ASSERT(trail->tr_filefd == -1); + +again: + curfile[0] = '\0'; + + rewinddir(trail->tr_dirfp); + while ((dp = readdir(trail->tr_dirfp)) != NULL) { + if (dp->d_name[0] < '0' || dp->d_name[0] > '9') + continue; + if (dp->d_type == DT_UNKNOWN) + dp->d_type = trail_type(trail->tr_dirfp, dp->d_name); + /* We are only interested in regular files, skip the rest. */ + if (dp->d_type != DT_REG) { + pjdlog_debug(1, + "File \"%s/%s\" is not a regular file, skipping.", + trail->tr_dirname, dp->d_name); + continue; + } + /* Skip all files "greater" than curfile. */ + if (curfile[0] != '\0' && strcmp(dp->d_name, curfile) > 0) + continue; + /* Skip all files "smaller" than the current trail_filename. */ + if (trail->tr_filename[0] != '\0' && + strcmp(dp->d_name, trail->tr_filename) <= 0) { + continue; + } + PJDLOG_VERIFY(strlcpy(curfile, dp->d_name, sizeof(curfile)) < + sizeof(curfile)); + } + if (curfile[0] == '\0') { + /* + * There are no new trail files, so we return. + * We don't clear trail_filename string, to know where to + * start when new file appears. + */ + PJDLOG_ASSERT(trail->tr_filefd == -1); + pjdlog_debug(1, "No new trail files."); + return; + } + PJDLOG_VERIFY(strlcpy(trail->tr_filename, curfile, + sizeof(trail->tr_filename)) < sizeof(trail->tr_filename)); + dfd = dirfd(trail->tr_dirfp); + PJDLOG_ASSERT(dfd >= 0); + trail->tr_filefd = openat(dfd, trail->tr_filename, O_RDONLY); + if (trail->tr_filefd == -1) { + pjdlog_errno(LOG_ERR, + "Unable to open file \"%s/%s\", skipping", + trail->tr_dirname, trail->tr_filename); + goto again; + } + pjdlog_debug(1, "Found next trail file: \"%s/%s\".", trail->tr_dirname, + trail->tr_filename); +} + +/* + * Close current trial file. + */ +void +trail_close(struct trail *trail) +{ + + PJDLOG_ASSERT(trail->tr_magic == TRAIL_MAGIC); + PJDLOG_ASSERT(trail->tr_filefd >= 0); + PJDLOG_ASSERT(trail->tr_filename[0] != '\0'); + + PJDLOG_VERIFY(close(trail->tr_filefd) == 0); + trail->tr_filefd = -1; +} + +/* + * Reset trail state. Used when connection is disconnected and we will + * need to start over after reconnect. Trail needs to be already closed. + */ +void +trail_reset(struct trail *trail) +{ + + PJDLOG_ASSERT(trail->tr_magic == TRAIL_MAGIC); + PJDLOG_ASSERT(trail->tr_filefd == -1); + + trail->tr_filename[0] = '\0'; +} + +/* + * Unlink current trial file. + */ +void +trail_unlink(struct trail *trail, const char *filename) +{ + int dfd; + + PJDLOG_ASSERT(trail->tr_magic == TRAIL_MAGIC); + PJDLOG_ASSERT(filename != NULL); + PJDLOG_ASSERT(filename[0] != '\0'); + + dfd = dirfd(trail->tr_dirfp); + PJDLOG_ASSERT(dfd >= 0); + + if (unlinkat(dfd, filename, 0) == -1) { + pjdlog_errno(LOG_ERR, "Unable to remove \"%s/%s\"", + trail->tr_dirname, filename); + } else { + pjdlog_debug(1, "Trail file \"%s/%s\" removed.", + trail->tr_dirname, filename); + } +} + +/* + * Return true if we should switch to next trail file. + * We don't switch if our file name ends with ".not_terminated" and it + * exists (ie. wasn't renamed). + */ +bool +trail_switch(struct trail *trail) +{ + char filename[PATH_MAX]; + int fd; + + PJDLOG_ASSERT(trail->tr_magic == TRAIL_MAGIC); + PJDLOG_ASSERT(trail->tr_filefd >= 0); + + if (!trail_is_not_terminated(trail->tr_filename)) + return (true); + fd = dirfd(trail->tr_dirfp); + PJDLOG_ASSERT(fd >= 0); + if (faccessat(fd, trail->tr_filename, F_OK, 0) == 0) + return (false); + if (errno != ENOENT) { + pjdlog_errno(LOG_ERR, "Unable to access file \"%s/%s\"", + trail->tr_dirname, trail->tr_filename); + } + strlcpy(filename, trail->tr_filename, sizeof(filename)); + if (!trail_find(trail)) { + pjdlog_error("Trail file \"%s/%s\" disappeared.", + trail->tr_dirname, trail->tr_filename); + return (true); + } + pjdlog_debug(1, "Trail file \"%s/%s\" was renamed to \"%s/%s\".", + trail->tr_dirname, filename, trail->tr_dirname, + trail->tr_filename); + return (true); +} + +const char * +trail_filename(const struct trail *trail) +{ + + PJDLOG_ASSERT(trail->tr_magic == TRAIL_MAGIC); + + return (trail->tr_filename); +} + +int +trail_filefd(const struct trail *trail) +{ + + PJDLOG_ASSERT(trail->tr_magic == TRAIL_MAGIC); + + return (trail->tr_filefd); +} + +int +trail_dirfd(const struct trail *trail) +{ + + PJDLOG_ASSERT(trail->tr_magic == TRAIL_MAGIC); + + return (dirfd(trail->tr_dirfp)); +} + +/* + * Find the last file in the directory opened under dirfp. + */ +void +trail_last(DIR *dirfp, char *filename, size_t filenamesize) +{ + char curfile[PATH_MAX]; + struct dirent *dp; + + PJDLOG_ASSERT(dirfp != NULL); + + curfile[0] = '\0'; + + rewinddir(dirfp); + while ((dp = readdir(dirfp)) != NULL) { + if (dp->d_name[0] < '0' || dp->d_name[0] > '9') + continue; + if (dp->d_type == DT_UNKNOWN) + dp->d_type = trail_type(dirfp, dp->d_name); + /* We are only interested in regular files, skip the rest. */ + if (dp->d_type != DT_REG) + continue; + /* Skip all files "greater" than curfile. */ + if (curfile[0] != '\0' && strcmp(dp->d_name, curfile) < 0) + continue; + PJDLOG_VERIFY(strlcpy(curfile, dp->d_name, sizeof(curfile)) < + sizeof(curfile)); + } + if (curfile[0] == '\0') { + /* + * There are no trail files, so we return. + */ + pjdlog_debug(1, "No trail files."); + bzero(filename, filenamesize); + return; + } + PJDLOG_VERIFY(strlcpy(filename, curfile, filenamesize) < filenamesize); + pjdlog_debug(1, "Found the most recent trail file: \"%s\".", filename); +} + +/* + * Check if the given file name is a valid audit trail file name. + * Possible names: + * 20120106132657.20120106132805 + * 20120106132657.not_terminated + * 20120106132657.crash_recovery + * If two names are given, check if the first name can be renamed + * to the second name. When renaming, first part of the name has + * to be identical and only the following renames are valid: + * 20120106132657.not_terminated -> 20120106132657.20120106132805 + * 20120106132657.not_terminated -> 20120106132657.crash_recovery + */ +bool +trail_validate_name(const char *srcname, const char *dstname) +{ + int i; + + PJDLOG_ASSERT(srcname != NULL); + + if (strlen(srcname) != 2 * HALF_LEN + 1) + return (false); + if (srcname[HALF_LEN] != '.') + return (false); + for (i = 0; i < HALF_LEN; i++) { + if (srcname[i] < '0' || srcname[i] > '9') + return (false); + } + for (i = HALF_LEN + 1; i < 2 * HALF_LEN - 1; i++) { + if (srcname[i] < '0' || srcname[i] > '9') + break; + } + if (i < 2 * HALF_LEN - 1 && + strcmp(srcname + HALF_LEN + 1, "not_terminated") != 0 && + strcmp(srcname + HALF_LEN + 1, "crash_recovery") != 0) { + return (false); + } + + if (dstname == NULL) + return (true); + + /* We tolarate if both names are identical. */ + if (strcmp(srcname, dstname) == 0) + return (true); + + /* We can only rename not_terminated files. */ + if (strcmp(srcname + HALF_LEN + 1, "not_terminated") != 0) + return (false); + if (strlen(dstname) != 2 * HALF_LEN + 1) + return (false); + if (strncmp(srcname, dstname, HALF_LEN + 1) != 0) + return (false); + for (i = HALF_LEN + 1; i < 2 * HALF_LEN - 1; i++) { + if (dstname[i] < '0' || dstname[i] > '9') + break; + } + if (i < 2 * HALF_LEN - 1 && + strcmp(dstname + HALF_LEN + 1, "crash_recovery") != 0) { + return (false); + } + + return (true); +} + +int +trail_name_compare(const char *name0, const char *name1) +{ + int ret; + + ret = strcmp(name0, name1); + if (ret == 0) + return (TRAIL_IDENTICAL); + if (strncmp(name0, name1, HALF_LEN + 1) == 0) + return (TRAIL_RENAMED); + return (ret < 0 ? TRAIL_OLDER : TRAIL_NEWER); +} diff --git a/contrib/openbsm/bin/auditdistd/trail.h b/contrib/openbsm/bin/auditdistd/trail.h new file mode 100644 index 0000000..33c88b2 --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/trail.h @@ -0,0 +1,62 @@ +/*- + * Copyright (c) 2012 The FreeBSD Foundation + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/trail.h#1 $ + */ + +#ifndef _AUDITDISTD_TRAIL_H_ +#define _AUDITDISTD_TRAIL_H_ + +#include <stdbool.h> +#include <unistd.h> /* off_t */ + +#define TRAIL_IDENTICAL 0 +#define TRAIL_RENAMED 1 +#define TRAIL_OLDER 2 +#define TRAIL_NEWER 3 + +struct trail; + +struct trail *trail_new(const char *dirname, bool create); +void trail_free(struct trail *trail); +bool trail_is_not_terminated(const char *filename); +bool trail_is_crash_recovery(const char *filename); +void trail_start(struct trail *trail, const char *filename, off_t offset); +void trail_next(struct trail *trail); +void trail_close(struct trail *trail); +void trail_reset(struct trail *trail); +void trail_unlink(struct trail *trail, const char *filename); +bool trail_switch(struct trail *trail); +const char *trail_filename(const struct trail *trail); +int trail_filefd(const struct trail *trail); +int trail_dirfd(const struct trail *trail); +void trail_last(DIR *dirfp, char *filename, size_t filenamesize); +bool trail_validate_name(const char *srcname, const char *dstname); +int trail_name_compare(const char *name0, const char *name1); + +#endif /* !_AUDITDISTD_TRAIL_H_ */ diff --git a/contrib/openbsm/bin/auditdistd/unlinkat.h b/contrib/openbsm/bin/auditdistd/unlinkat.h new file mode 100644 index 0000000..ee9c023 --- /dev/null +++ b/contrib/openbsm/bin/auditdistd/unlinkat.h @@ -0,0 +1,68 @@ +/*- + * Copyright (c) 2012 The FreeBSD Foundation + * All rights reserved. + * + * This software was developed by Pawel Jakub Dawidek under sponsorship from + * the FreeBSD Foundation. + * + * 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 AUTHORS 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 AUTHORS 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. + * + * $P4: //depot/projects/trustedbsd/openbsm/bin/auditdistd/unlinkat.h#1 $ + */ + +#ifndef _UNLINKAT_H_ +#define _UNLINKAT_H_ + +#include <fcntl.h> +#include <unistd.h> + +#define AT_REMOVEDIR 0x01 + +static int +unlinkat(int fd, const char *path, int flag) +{ + int cfd, error, ret; + + cfd = open(".", O_RDONLY | O_DIRECTORY); + if (cfd == -1) + return (-1); + + if (fchdir(fd) == -1) { + error = errno; + (void)close(cfd); + errno = error; + return (-1); + } + + if (flag == AT_REMOVEDIR) + ret = rmdir(path); + else + ret = unlink(path); + + error = errno; + (void)fchdir(cfd); + (void)close(cfd); + errno = error; + return (ret); +} + +#endif /* !_UNLINKAT_H_ */ diff --git a/contrib/openbsm/bin/auditfilterd/Makefile.am b/contrib/openbsm/bin/auditfilterd/Makefile.am index 83399f1..81d4fb5 100644 --- a/contrib/openbsm/bin/auditfilterd/Makefile.am +++ b/contrib/openbsm/bin/auditfilterd/Makefile.am @@ -1,6 +1,6 @@ -# -# $P4: //depot/projects/trustedbsd/openbsm/bin/auditfilterd/Makefile.am#3 $ -# +## +## $P4: //depot/projects/trustedbsd/openbsm/bin/auditfilterd/Makefile.am#4 $ +## if USE_NATIVE_INCLUDES INCLUDES = -I$(top_builddir) -I$(top_srcdir) diff --git a/contrib/openbsm/bin/auditfilterd/Makefile.in b/contrib/openbsm/bin/auditfilterd/Makefile.in index 6436aa0..e90f7d7 100644 --- a/contrib/openbsm/bin/auditfilterd/Makefile.in +++ b/contrib/openbsm/bin/auditfilterd/Makefile.in @@ -1,8 +1,8 @@ -# Makefile.in generated by automake 1.10.1 from Makefile.am. +# Makefile.in generated by automake 1.12.2 from Makefile.am. # @configure_input@ -# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008 Free Software Foundation, Inc. +# Copyright (C) 1994-2012 Free Software Foundation, Inc. + # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -14,14 +14,28 @@ @SET_MAKE@ -# -# $P4: //depot/projects/trustedbsd/openbsm/bin/auditfilterd/Makefile.in#8 $ -# - VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ -pkglibdir = $(libdir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ +pkglibdir = $(libdir)/@PACKAGE@ +pkglibexecdir = $(libexecdir)/@PACKAGE@ am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd install_sh_DATA = $(install_sh) -c -m 644 install_sh_PROGRAM = $(install_sh) -c @@ -38,7 +52,8 @@ build_triplet = @build@ host_triplet = @host@ sbin_PROGRAMS = auditfilterd$(EXEEXT) subdir = bin/auditfilterd -DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in +DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ + $(top_srcdir)/config/depcomp ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -46,8 +61,8 @@ am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ mkinstalldirs = $(install_sh) -d CONFIG_HEADER = $(top_builddir)/config/config.h CONFIG_CLEAN_FILES = +CONFIG_CLEAN_VPATH_FILES = am__installdirs = "$(DESTDIR)$(sbindir)" "$(DESTDIR)$(man8dir)" -sbinPROGRAMS_INSTALL = $(INSTALL_PROGRAM) PROGRAMS = $(sbin_PROGRAMS) am_auditfilterd_OBJECTS = auditfilterd_conf.$(OBJEXT) \ auditfilterd.$(OBJEXT) @@ -56,6 +71,7 @@ auditfilterd_DEPENDENCIES = $(top_builddir)/libbsm/libbsm.la DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir)/config depcomp = $(SHELL) $(top_srcdir)/config/depcomp am__depfiles_maybe = depfiles +am__mv = mv -f COMPILE = $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) \ $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) LTCOMPILE = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) \ @@ -67,6 +83,38 @@ LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) \ $(LDFLAGS) -o $@ SOURCES = $(auditfilterd_SOURCES) DIST_SOURCES = $(auditfilterd_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac +am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; +am__vpath_adj = case $$p in \ + $(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \ + *) f=$$p;; \ + esac; +am__strip_dir = f=`echo $$p | sed -e 's|^.*/||'`; +am__install_max = 40 +am__nobase_strip_setup = \ + srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*|]/\\\\&/g'` +am__nobase_strip = \ + for p in $$list; do echo "$$p"; done | sed -e "s|$$srcdirstrip/||" +am__nobase_list = $(am__nobase_strip_setup); \ + for p in $$list; do echo "$$p $$p"; done | \ + sed "s| $$srcdirstrip/| |;"' / .*\//!s/ .*/ ./; s,\( .*\)/[^/]*$$,\1,' | \ + $(AWK) 'BEGIN { files["."] = "" } { files[$$2] = files[$$2] " " $$1; \ + if (++n[$$2] == $(am__install_max)) \ + { print $$2, files[$$2]; n[$$2] = 0; files[$$2] = "" } } \ + END { for (dir in files) print dir, files[dir] }' +am__base_list = \ + sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ + sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } man8dir = $(mandir)/man8 NROFF = nroff MANS = $(man8_MANS) @@ -85,45 +133,52 @@ CCDEPMODE = @CCDEPMODE@ CFLAGS = @CFLAGS@ CPP = @CPP@ CPPFLAGS = @CPPFLAGS@ -CXX = @CXX@ -CXXCPP = @CXXCPP@ -CXXDEPMODE = @CXXDEPMODE@ -CXXFLAGS = @CXXFLAGS@ CYGPATH_W = @CYGPATH_W@ DEFS = @DEFS@ DEPDIR = @DEPDIR@ +DLLTOOL = @DLLTOOL@ DSYMUTIL = @DSYMUTIL@ -ECHO = @ECHO@ +DUMPBIN = @DUMPBIN@ ECHO_C = @ECHO_C@ ECHO_N = @ECHO_N@ ECHO_T = @ECHO_T@ EGREP = @EGREP@ EXEEXT = @EXEEXT@ -F77 = @F77@ -FFLAGS = @FFLAGS@ +FGREP = @FGREP@ GREP = @GREP@ INSTALL = @INSTALL@ INSTALL_DATA = @INSTALL_DATA@ INSTALL_PROGRAM = @INSTALL_PROGRAM@ INSTALL_SCRIPT = @INSTALL_SCRIPT@ INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@ +LD = @LD@ LDFLAGS = @LDFLAGS@ +LEX = @LEX@ +LEXLIB = @LEXLIB@ +LEX_OUTPUT_ROOT = @LEX_OUTPUT_ROOT@ LIBOBJS = @LIBOBJS@ LIBS = @LIBS@ LIBTOOL = @LIBTOOL@ +LIPO = @LIPO@ LN_S = @LN_S@ LTLIBOBJS = @LTLIBOBJS@ MAINT = @MAINT@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MIG = @MIG@ MKDIR_P = @MKDIR_P@ +NM = @NM@ NMEDIT = @NMEDIT@ +OBJDUMP = @OBJDUMP@ OBJEXT = @OBJEXT@ +OTOOL = @OTOOL@ +OTOOL64 = @OTOOL64@ PACKAGE = @PACKAGE@ PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@ PACKAGE_NAME = @PACKAGE_NAME@ PACKAGE_STRING = @PACKAGE_STRING@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ +PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ RANLIB = @RANLIB@ @@ -132,13 +187,15 @@ SET_MAKE = @SET_MAKE@ SHELL = @SHELL@ STRIP = @STRIP@ VERSION = @VERSION@ +YACC = @YACC@ +YFLAGS = @YFLAGS@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ -ac_ct_CXX = @ac_ct_CXX@ -ac_ct_F77 = @ac_ct_F77@ +ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ am__include = @am__include@ am__leading_dot = @am__leading_dot@ am__quote = @am__quote@ @@ -197,14 +254,14 @@ $(srcdir)/Makefile.in: @MAINTAINER_MODE_TRUE@ $(srcdir)/Makefile.am $(am__confi @for dep in $?; do \ case '$(am__configure_deps)' in \ *$$dep*) \ - cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh \ - && exit 0; \ + ( cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh ) \ + && { if test -f $@; then exit 0; else break; fi; }; \ exit 1;; \ esac; \ done; \ - echo ' cd $(top_srcdir) && $(AUTOMAKE) --foreign bin/auditfilterd/Makefile'; \ - cd $(top_srcdir) && \ - $(AUTOMAKE) --foreign bin/auditfilterd/Makefile + echo ' cd $(top_srcdir) && $(AUTOMAKE) --foreign bin/auditfilterd/Makefile'; \ + $(am__cd) $(top_srcdir) && \ + $(AUTOMAKE) --foreign bin/auditfilterd/Makefile .PRECIOUS: Makefile Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status @case '$?' in \ @@ -222,35 +279,54 @@ $(top_srcdir)/configure: @MAINTAINER_MODE_TRUE@ $(am__configure_deps) cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh $(ACLOCAL_M4): @MAINTAINER_MODE_TRUE@ $(am__aclocal_m4_deps) cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh +$(am__aclocal_m4_deps): install-sbinPROGRAMS: $(sbin_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(sbindir)" || $(MKDIR_P) "$(DESTDIR)$(sbindir)" - @list='$(sbin_PROGRAMS)'; for p in $$list; do \ - p1=`echo $$p|sed 's/$(EXEEXT)$$//'`; \ - if test -f $$p \ - || test -f $$p1 \ - ; then \ - f=`echo "$$p1" | sed 's,^.*/,,;$(transform);s/$$/$(EXEEXT)/'`; \ - echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(sbinPROGRAMS_INSTALL) '$$p' '$(DESTDIR)$(sbindir)/$$f'"; \ - $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(sbinPROGRAMS_INSTALL) "$$p" "$(DESTDIR)$(sbindir)/$$f" || exit 1; \ - else :; fi; \ - done + @list='$(sbin_PROGRAMS)'; test -n "$(sbindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(sbindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(sbindir)" || exit 1; \ + fi; \ + for p in $$list; do echo "$$p $$p"; done | \ + sed 's/$(EXEEXT)$$//' | \ + while read p p1; do if test -f $$p || test -f $$p1; \ + then echo "$$p"; echo "$$p"; else :; fi; \ + done | \ + sed -e 'p;s,.*/,,;n;h' -e 's|.*|.|' \ + -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ + sed 'N;N;N;s,\n, ,g' | \ + $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ + { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ + if ($$2 == $$4) files[d] = files[d] " " $$1; \ + else { print "f", $$3 "/" $$4, $$1; } } \ + END { for (d in files) print "f", d, files[d] }' | \ + while read type dir files; do \ + if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ + test -z "$$files" || { \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(sbindir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(sbindir)$$dir" || exit $$?; \ + } \ + ; done uninstall-sbinPROGRAMS: @$(NORMAL_UNINSTALL) - @list='$(sbin_PROGRAMS)'; for p in $$list; do \ - f=`echo "$$p" | sed 's,^.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/'`; \ - echo " rm -f '$(DESTDIR)$(sbindir)/$$f'"; \ - rm -f "$(DESTDIR)$(sbindir)/$$f"; \ - done + @list='$(sbin_PROGRAMS)'; test -n "$(sbindir)" || list=; \ + files=`for p in $$list; do echo "$$p"; done | \ + sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ + -e 's/$$/$(EXEEXT)/' `; \ + test -n "$$list" || exit 0; \ + echo " ( cd '$(DESTDIR)$(sbindir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(sbindir)" && rm -f $$files clean-sbinPROGRAMS: - @list='$(sbin_PROGRAMS)'; for p in $$list; do \ - f=`echo $$p|sed 's/$(EXEEXT)$$//'`; \ - echo " rm -f $$p $$f"; \ - rm -f $$p $$f ; \ - done -auditfilterd$(EXEEXT): $(auditfilterd_OBJECTS) $(auditfilterd_DEPENDENCIES) + @list='$(sbin_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +auditfilterd$(EXEEXT): $(auditfilterd_OBJECTS) $(auditfilterd_DEPENDENCIES) $(EXTRA_auditfilterd_DEPENDENCIES) @rm -f auditfilterd$(EXEEXT) $(LINK) $(auditfilterd_OBJECTS) $(auditfilterd_LDADD) $(LIBS) @@ -265,21 +341,21 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< -@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po +@am__fastdepCC_TRUE@ $(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po @AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` -@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po +@am__fastdepCC_TRUE@ $(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po @AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< -@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo +@am__fastdepCC_TRUE@ $(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< @@ -289,65 +365,61 @@ mostlyclean-libtool: clean-libtool: -rm -rf .libs _libs -install-man8: $(man8_MANS) $(man_MANS) +install-man8: $(man8_MANS) @$(NORMAL_INSTALL) - test -z "$(man8dir)" || $(MKDIR_P) "$(DESTDIR)$(man8dir)" - @list='$(man8_MANS) $(dist_man8_MANS) $(nodist_man8_MANS)'; \ - l2='$(man_MANS) $(dist_man_MANS) $(nodist_man_MANS)'; \ - for i in $$l2; do \ - case "$$i" in \ - *.8*) list="$$list $$i" ;; \ - esac; \ + @list1='$(man8_MANS)'; \ + list2=''; \ + test -n "$(man8dir)" \ + && test -n "`echo $$list1$$list2`" \ + || exit 0; \ + echo " $(MKDIR_P) '$(DESTDIR)$(man8dir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(man8dir)" || exit 1; \ + { for i in $$list1; do echo "$$i"; done; \ + if test -n "$$list2"; then \ + for i in $$list2; do echo "$$i"; done \ + | sed -n '/\.8[a-z]*$$/p'; \ + fi; \ + } | while read p; do \ + if test -f $$p; then d=; else d="$(srcdir)/"; fi; \ + echo "$$d$$p"; echo "$$p"; \ + done | \ + sed -e 'n;s,.*/,,;p;h;s,.*\.,,;s,^[^8][0-9a-z]*$$,8,;x' \ + -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,' | \ + sed 'N;N;s,\n, ,g' | { \ + list=; while read file base inst; do \ + if test "$$base" = "$$inst"; then list="$$list $$file"; else \ + echo " $(INSTALL_DATA) '$$file' '$(DESTDIR)$(man8dir)/$$inst'"; \ + $(INSTALL_DATA) "$$file" "$(DESTDIR)$(man8dir)/$$inst" || exit $$?; \ + fi; \ done; \ - for i in $$list; do \ - if test -f $(srcdir)/$$i; then file=$(srcdir)/$$i; \ - else file=$$i; fi; \ - ext=`echo $$i | sed -e 's/^.*\\.//'`; \ - case "$$ext" in \ - 8*) ;; \ - *) ext='8' ;; \ - esac; \ - inst=`echo $$i | sed -e 's/\\.[0-9a-z]*$$//'`; \ - inst=`echo $$inst | sed -e 's/^.*\///'`; \ - inst=`echo $$inst | sed '$(transform)'`.$$ext; \ - echo " $(INSTALL_DATA) '$$file' '$(DESTDIR)$(man8dir)/$$inst'"; \ - $(INSTALL_DATA) "$$file" "$(DESTDIR)$(man8dir)/$$inst"; \ - done + for i in $$list; do echo "$$i"; done | $(am__base_list) | \ + while read files; do \ + test -z "$$files" || { \ + echo " $(INSTALL_DATA) $$files '$(DESTDIR)$(man8dir)'"; \ + $(INSTALL_DATA) $$files "$(DESTDIR)$(man8dir)" || exit $$?; }; \ + done; } + uninstall-man8: @$(NORMAL_UNINSTALL) - @list='$(man8_MANS) $(dist_man8_MANS) $(nodist_man8_MANS)'; \ - l2='$(man_MANS) $(dist_man_MANS) $(nodist_man_MANS)'; \ - for i in $$l2; do \ - case "$$i" in \ - *.8*) list="$$list $$i" ;; \ - esac; \ - done; \ - for i in $$list; do \ - ext=`echo $$i | sed -e 's/^.*\\.//'`; \ - case "$$ext" in \ - 8*) ;; \ - *) ext='8' ;; \ - esac; \ - inst=`echo $$i | sed -e 's/\\.[0-9a-z]*$$//'`; \ - inst=`echo $$inst | sed -e 's/^.*\///'`; \ - inst=`echo $$inst | sed '$(transform)'`.$$ext; \ - echo " rm -f '$(DESTDIR)$(man8dir)/$$inst'"; \ - rm -f "$(DESTDIR)$(man8dir)/$$inst"; \ - done + @list='$(man8_MANS)'; test -n "$(man8dir)" || exit 0; \ + files=`{ for i in $$list; do echo "$$i"; done; \ + } | sed -e 's,.*/,,;h;s,.*\.,,;s,^[^8][0-9a-z]*$$,8,;x' \ + -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,'`; \ + dir='$(DESTDIR)$(man8dir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ unique=`for i in $$list; do \ if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ done | \ - $(AWK) '{ files[$$0] = 1; nonemtpy = 1; } \ + $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ END { if (nonempty) { for (i in files) print i; }; }'`; \ mkid -fID $$unique tags: TAGS TAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ $(TAGS_FILES) $(LISP) - tags=; \ + set x; \ here=`pwd`; \ list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ unique=`for i in $$list; do \ @@ -355,34 +427,66 @@ TAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ done | \ $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ END { if (nonempty) { for (i in files) print i; }; }'`; \ - if test -z "$(ETAGS_ARGS)$$tags$$unique"; then :; else \ + shift; \ + if test -z "$(ETAGS_ARGS)$$*$$unique"; then :; else \ test -n "$$unique" || unique=$$empty_fix; \ - $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ - $$tags $$unique; \ + if test $$# -gt 0; then \ + $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ + "$$@" $$unique; \ + else \ + $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ + $$unique; \ + fi; \ fi ctags: CTAGS CTAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ $(TAGS_FILES) $(LISP) - tags=; \ list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ unique=`for i in $$list; do \ if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ done | \ $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ END { if (nonempty) { for (i in files) print i; }; }'`; \ - test -z "$(CTAGS_ARGS)$$tags$$unique" \ + test -z "$(CTAGS_ARGS)$$unique" \ || $(CTAGS) $(CTAGSFLAGS) $(AM_CTAGSFLAGS) $(CTAGS_ARGS) \ - $$tags $$unique + $$unique GTAGS: here=`$(am__cd) $(top_builddir) && pwd` \ - && cd $(top_srcdir) \ - && gtags -i $(GTAGS_ARGS) $$here + && $(am__cd) $(top_srcdir) \ + && gtags -i $(GTAGS_ARGS) "$$here" + +cscopelist: $(HEADERS) $(SOURCES) $(LISP) + list='$(SOURCES) $(HEADERS) $(LISP)'; \ + case "$(srcdir)" in \ + [\\/]* | ?:[\\/]*) sdir="$(srcdir)" ;; \ + *) sdir=$(subdir)/$(srcdir) ;; \ + esac; \ + for i in $$list; do \ + if test -f "$$i"; then \ + echo "$(subdir)/$$i"; \ + else \ + echo "$$sdir/$$i"; \ + fi; \ + done >> $(top_builddir)/cscope.files distclean-tags: -rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags distdir: $(DISTFILES) + @list='$(MANS)'; if test -n "$$list"; then \ + list=`for p in $$list; do \ + if test -f $$p; then d=; else d="$(srcdir)/"; fi; \ + if test -f "$$d$$p"; then echo "$$d$$p"; else :; fi; done`; \ + if test -n "$$list" && \ + grep 'ab help2man is required to generate this page' $$list >/dev/null; then \ + echo "error: found man pages containing the 'missing help2man' replacement text:" >&2; \ + grep -l 'ab help2man is required to generate this page' $$list | sed 's/^/ /' >&2; \ + echo " to fix them, install help2man, remove and regenerate the man pages;" >&2; \ + echo " typically 'make maintainer-clean' will remove them" >&2; \ + exit 1; \ + else :; fi; \ + else :; fi @srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ topsrcdirstrip=`echo "$(top_srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ list='$(DISTFILES)'; \ @@ -398,13 +502,17 @@ distdir: $(DISTFILES) if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \ if test -d $$d/$$file; then \ dir=`echo "/$$file" | sed -e 's,/[^/]*$$,,'`; \ + if test -d "$(distdir)/$$file"; then \ + find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \ + fi; \ if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \ - cp -pR $(srcdir)/$$file $(distdir)$$dir || exit 1; \ + cp -fpR $(srcdir)/$$file "$(distdir)$$dir" || exit 1; \ + find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \ fi; \ - cp -pR $$d/$$file $(distdir)$$dir || exit 1; \ + cp -fpR $$d/$$file "$(distdir)$$dir" || exit 1; \ else \ - test -f $(distdir)/$$file \ - || cp -p $$d/$$file $(distdir)/$$file \ + test -f "$(distdir)/$$file" \ + || cp -p $$d/$$file "$(distdir)/$$file" \ || exit 1; \ fi; \ done @@ -425,16 +533,22 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: distclean-generic: -test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES) + -test . = "$(srcdir)" || test -z "$(CONFIG_CLEAN_VPATH_FILES)" || rm -f $(CONFIG_CLEAN_VPATH_FILES) maintainer-clean-generic: @echo "This command is intended for maintainers to use" @@ -456,6 +570,8 @@ dvi-am: html: html-am +html-am: + info: info-am info-am: @@ -464,18 +580,28 @@ install-data-am: install-man install-dvi: install-dvi-am +install-dvi-am: + install-exec-am: install-sbinPROGRAMS install-html: install-html-am +install-html-am: + install-info: install-info-am +install-info-am: + install-man: install-man8 install-pdf: install-pdf-am +install-pdf-am: + install-ps: install-ps-am +install-ps-am: + installcheck-am: maintainer-clean: maintainer-clean-am @@ -503,7 +629,7 @@ uninstall-man: uninstall-man8 .MAKE: install-am install-strip .PHONY: CTAGS GTAGS all all-am check check-am clean clean-generic \ - clean-libtool clean-sbinPROGRAMS ctags distclean \ + clean-libtool clean-sbinPROGRAMS cscopelist ctags distclean \ distclean-compile distclean-generic distclean-libtool \ distclean-tags distdir dvi dvi-am html html-am info info-am \ install install-am install-data install-data-am install-dvi \ @@ -517,6 +643,7 @@ uninstall-man: uninstall-man8 tags uninstall uninstall-am uninstall-man uninstall-man8 \ uninstall-sbinPROGRAMS + # Tell versions [3.59,3.63) of GNU make to not export all variables. # Otherwise a system limit (for SysV at least) may be exceeded. .NOEXPORT: diff --git a/contrib/openbsm/bin/auditreduce/Makefile.am b/contrib/openbsm/bin/auditreduce/Makefile.am index 8cd4b62..a02178b 100644 --- a/contrib/openbsm/bin/auditreduce/Makefile.am +++ b/contrib/openbsm/bin/auditreduce/Makefile.am @@ -1,6 +1,6 @@ -# -# $P4: //depot/projects/trustedbsd/openbsm/bin/auditreduce/Makefile.am#3 $ -# +## +## $P4: //depot/projects/trustedbsd/openbsm/bin/auditreduce/Makefile.am#4 $ +## if USE_NATIVE_INCLUDES INCLUDES = -I$(top_builddir) -I$(top_srcdir) diff --git a/contrib/openbsm/bin/auditreduce/Makefile.in b/contrib/openbsm/bin/auditreduce/Makefile.in index 21cedd8..53090e2 100644 --- a/contrib/openbsm/bin/auditreduce/Makefile.in +++ b/contrib/openbsm/bin/auditreduce/Makefile.in @@ -1,8 +1,8 @@ -# Makefile.in generated by automake 1.10.1 from Makefile.am. +# Makefile.in generated by automake 1.12.2 from Makefile.am. # @configure_input@ -# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008 Free Software Foundation, Inc. +# Copyright (C) 1994-2012 Free Software Foundation, Inc. + # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -14,14 +14,28 @@ @SET_MAKE@ -# -# $P4: //depot/projects/trustedbsd/openbsm/bin/auditreduce/Makefile.in#10 $ -# - VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ -pkglibdir = $(libdir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ +pkglibdir = $(libdir)/@PACKAGE@ +pkglibexecdir = $(libexecdir)/@PACKAGE@ am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd install_sh_DATA = $(install_sh) -c -m 644 install_sh_PROGRAM = $(install_sh) -c @@ -38,7 +52,8 @@ build_triplet = @build@ host_triplet = @host@ sbin_PROGRAMS = auditreduce$(EXEEXT) subdir = bin/auditreduce -DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in +DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ + $(top_srcdir)/config/depcomp ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -46,8 +61,8 @@ am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ mkinstalldirs = $(install_sh) -d CONFIG_HEADER = $(top_builddir)/config/config.h CONFIG_CLEAN_FILES = +CONFIG_CLEAN_VPATH_FILES = am__installdirs = "$(DESTDIR)$(sbindir)" "$(DESTDIR)$(man1dir)" -sbinPROGRAMS_INSTALL = $(INSTALL_PROGRAM) PROGRAMS = $(sbin_PROGRAMS) am_auditreduce_OBJECTS = auditreduce.$(OBJEXT) auditreduce_OBJECTS = $(am_auditreduce_OBJECTS) @@ -55,6 +70,7 @@ auditreduce_DEPENDENCIES = $(top_builddir)/libbsm/libbsm.la DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir)/config depcomp = $(SHELL) $(top_srcdir)/config/depcomp am__depfiles_maybe = depfiles +am__mv = mv -f COMPILE = $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) \ $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) LTCOMPILE = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) \ @@ -66,6 +82,38 @@ LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) \ $(LDFLAGS) -o $@ SOURCES = $(auditreduce_SOURCES) DIST_SOURCES = $(auditreduce_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac +am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; +am__vpath_adj = case $$p in \ + $(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \ + *) f=$$p;; \ + esac; +am__strip_dir = f=`echo $$p | sed -e 's|^.*/||'`; +am__install_max = 40 +am__nobase_strip_setup = \ + srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*|]/\\\\&/g'` +am__nobase_strip = \ + for p in $$list; do echo "$$p"; done | sed -e "s|$$srcdirstrip/||" +am__nobase_list = $(am__nobase_strip_setup); \ + for p in $$list; do echo "$$p $$p"; done | \ + sed "s| $$srcdirstrip/| |;"' / .*\//!s/ .*/ ./; s,\( .*\)/[^/]*$$,\1,' | \ + $(AWK) 'BEGIN { files["."] = "" } { files[$$2] = files[$$2] " " $$1; \ + if (++n[$$2] == $(am__install_max)) \ + { print $$2, files[$$2]; n[$$2] = 0; files[$$2] = "" } } \ + END { for (dir in files) print dir, files[dir] }' +am__base_list = \ + sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ + sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } man1dir = $(mandir)/man1 NROFF = nroff MANS = $(man1_MANS) @@ -84,45 +132,52 @@ CCDEPMODE = @CCDEPMODE@ CFLAGS = @CFLAGS@ CPP = @CPP@ CPPFLAGS = @CPPFLAGS@ -CXX = @CXX@ -CXXCPP = @CXXCPP@ -CXXDEPMODE = @CXXDEPMODE@ -CXXFLAGS = @CXXFLAGS@ CYGPATH_W = @CYGPATH_W@ DEFS = @DEFS@ DEPDIR = @DEPDIR@ +DLLTOOL = @DLLTOOL@ DSYMUTIL = @DSYMUTIL@ -ECHO = @ECHO@ +DUMPBIN = @DUMPBIN@ ECHO_C = @ECHO_C@ ECHO_N = @ECHO_N@ ECHO_T = @ECHO_T@ EGREP = @EGREP@ EXEEXT = @EXEEXT@ -F77 = @F77@ -FFLAGS = @FFLAGS@ +FGREP = @FGREP@ GREP = @GREP@ INSTALL = @INSTALL@ INSTALL_DATA = @INSTALL_DATA@ INSTALL_PROGRAM = @INSTALL_PROGRAM@ INSTALL_SCRIPT = @INSTALL_SCRIPT@ INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@ +LD = @LD@ LDFLAGS = @LDFLAGS@ +LEX = @LEX@ +LEXLIB = @LEXLIB@ +LEX_OUTPUT_ROOT = @LEX_OUTPUT_ROOT@ LIBOBJS = @LIBOBJS@ LIBS = @LIBS@ LIBTOOL = @LIBTOOL@ +LIPO = @LIPO@ LN_S = @LN_S@ LTLIBOBJS = @LTLIBOBJS@ MAINT = @MAINT@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MIG = @MIG@ MKDIR_P = @MKDIR_P@ +NM = @NM@ NMEDIT = @NMEDIT@ +OBJDUMP = @OBJDUMP@ OBJEXT = @OBJEXT@ +OTOOL = @OTOOL@ +OTOOL64 = @OTOOL64@ PACKAGE = @PACKAGE@ PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@ PACKAGE_NAME = @PACKAGE_NAME@ PACKAGE_STRING = @PACKAGE_STRING@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ +PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ RANLIB = @RANLIB@ @@ -131,13 +186,15 @@ SET_MAKE = @SET_MAKE@ SHELL = @SHELL@ STRIP = @STRIP@ VERSION = @VERSION@ +YACC = @YACC@ +YFLAGS = @YFLAGS@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ -ac_ct_CXX = @ac_ct_CXX@ -ac_ct_F77 = @ac_ct_F77@ +ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ am__include = @am__include@ am__leading_dot = @am__leading_dot@ am__quote = @am__quote@ @@ -196,14 +253,14 @@ $(srcdir)/Makefile.in: @MAINTAINER_MODE_TRUE@ $(srcdir)/Makefile.am $(am__confi @for dep in $?; do \ case '$(am__configure_deps)' in \ *$$dep*) \ - cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh \ - && exit 0; \ + ( cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh ) \ + && { if test -f $@; then exit 0; else break; fi; }; \ exit 1;; \ esac; \ done; \ - echo ' cd $(top_srcdir) && $(AUTOMAKE) --foreign bin/auditreduce/Makefile'; \ - cd $(top_srcdir) && \ - $(AUTOMAKE) --foreign bin/auditreduce/Makefile + echo ' cd $(top_srcdir) && $(AUTOMAKE) --foreign bin/auditreduce/Makefile'; \ + $(am__cd) $(top_srcdir) && \ + $(AUTOMAKE) --foreign bin/auditreduce/Makefile .PRECIOUS: Makefile Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status @case '$?' in \ @@ -221,35 +278,54 @@ $(top_srcdir)/configure: @MAINTAINER_MODE_TRUE@ $(am__configure_deps) cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh $(ACLOCAL_M4): @MAINTAINER_MODE_TRUE@ $(am__aclocal_m4_deps) cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh +$(am__aclocal_m4_deps): install-sbinPROGRAMS: $(sbin_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(sbindir)" || $(MKDIR_P) "$(DESTDIR)$(sbindir)" - @list='$(sbin_PROGRAMS)'; for p in $$list; do \ - p1=`echo $$p|sed 's/$(EXEEXT)$$//'`; \ - if test -f $$p \ - || test -f $$p1 \ - ; then \ - f=`echo "$$p1" | sed 's,^.*/,,;$(transform);s/$$/$(EXEEXT)/'`; \ - echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(sbinPROGRAMS_INSTALL) '$$p' '$(DESTDIR)$(sbindir)/$$f'"; \ - $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(sbinPROGRAMS_INSTALL) "$$p" "$(DESTDIR)$(sbindir)/$$f" || exit 1; \ - else :; fi; \ - done + @list='$(sbin_PROGRAMS)'; test -n "$(sbindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(sbindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(sbindir)" || exit 1; \ + fi; \ + for p in $$list; do echo "$$p $$p"; done | \ + sed 's/$(EXEEXT)$$//' | \ + while read p p1; do if test -f $$p || test -f $$p1; \ + then echo "$$p"; echo "$$p"; else :; fi; \ + done | \ + sed -e 'p;s,.*/,,;n;h' -e 's|.*|.|' \ + -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ + sed 'N;N;N;s,\n, ,g' | \ + $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ + { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ + if ($$2 == $$4) files[d] = files[d] " " $$1; \ + else { print "f", $$3 "/" $$4, $$1; } } \ + END { for (d in files) print "f", d, files[d] }' | \ + while read type dir files; do \ + if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ + test -z "$$files" || { \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(sbindir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(sbindir)$$dir" || exit $$?; \ + } \ + ; done uninstall-sbinPROGRAMS: @$(NORMAL_UNINSTALL) - @list='$(sbin_PROGRAMS)'; for p in $$list; do \ - f=`echo "$$p" | sed 's,^.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/'`; \ - echo " rm -f '$(DESTDIR)$(sbindir)/$$f'"; \ - rm -f "$(DESTDIR)$(sbindir)/$$f"; \ - done + @list='$(sbin_PROGRAMS)'; test -n "$(sbindir)" || list=; \ + files=`for p in $$list; do echo "$$p"; done | \ + sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ + -e 's/$$/$(EXEEXT)/' `; \ + test -n "$$list" || exit 0; \ + echo " ( cd '$(DESTDIR)$(sbindir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(sbindir)" && rm -f $$files clean-sbinPROGRAMS: - @list='$(sbin_PROGRAMS)'; for p in $$list; do \ - f=`echo $$p|sed 's/$(EXEEXT)$$//'`; \ - echo " rm -f $$p $$f"; \ - rm -f $$p $$f ; \ - done -auditreduce$(EXEEXT): $(auditreduce_OBJECTS) $(auditreduce_DEPENDENCIES) + @list='$(sbin_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +auditreduce$(EXEEXT): $(auditreduce_OBJECTS) $(auditreduce_DEPENDENCIES) $(EXTRA_auditreduce_DEPENDENCIES) @rm -f auditreduce$(EXEEXT) $(LINK) $(auditreduce_OBJECTS) $(auditreduce_LDADD) $(LIBS) @@ -263,21 +339,21 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< -@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po +@am__fastdepCC_TRUE@ $(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po @AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` -@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po +@am__fastdepCC_TRUE@ $(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po @AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< -@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo +@am__fastdepCC_TRUE@ $(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< @@ -287,65 +363,61 @@ mostlyclean-libtool: clean-libtool: -rm -rf .libs _libs -install-man1: $(man1_MANS) $(man_MANS) +install-man1: $(man1_MANS) @$(NORMAL_INSTALL) - test -z "$(man1dir)" || $(MKDIR_P) "$(DESTDIR)$(man1dir)" - @list='$(man1_MANS) $(dist_man1_MANS) $(nodist_man1_MANS)'; \ - l2='$(man_MANS) $(dist_man_MANS) $(nodist_man_MANS)'; \ - for i in $$l2; do \ - case "$$i" in \ - *.1*) list="$$list $$i" ;; \ - esac; \ + @list1='$(man1_MANS)'; \ + list2=''; \ + test -n "$(man1dir)" \ + && test -n "`echo $$list1$$list2`" \ + || exit 0; \ + echo " $(MKDIR_P) '$(DESTDIR)$(man1dir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(man1dir)" || exit 1; \ + { for i in $$list1; do echo "$$i"; done; \ + if test -n "$$list2"; then \ + for i in $$list2; do echo "$$i"; done \ + | sed -n '/\.1[a-z]*$$/p'; \ + fi; \ + } | while read p; do \ + if test -f $$p; then d=; else d="$(srcdir)/"; fi; \ + echo "$$d$$p"; echo "$$p"; \ + done | \ + sed -e 'n;s,.*/,,;p;h;s,.*\.,,;s,^[^1][0-9a-z]*$$,1,;x' \ + -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,' | \ + sed 'N;N;s,\n, ,g' | { \ + list=; while read file base inst; do \ + if test "$$base" = "$$inst"; then list="$$list $$file"; else \ + echo " $(INSTALL_DATA) '$$file' '$(DESTDIR)$(man1dir)/$$inst'"; \ + $(INSTALL_DATA) "$$file" "$(DESTDIR)$(man1dir)/$$inst" || exit $$?; \ + fi; \ done; \ - for i in $$list; do \ - if test -f $(srcdir)/$$i; then file=$(srcdir)/$$i; \ - else file=$$i; fi; \ - ext=`echo $$i | sed -e 's/^.*\\.//'`; \ - case "$$ext" in \ - 1*) ;; \ - *) ext='1' ;; \ - esac; \ - inst=`echo $$i | sed -e 's/\\.[0-9a-z]*$$//'`; \ - inst=`echo $$inst | sed -e 's/^.*\///'`; \ - inst=`echo $$inst | sed '$(transform)'`.$$ext; \ - echo " $(INSTALL_DATA) '$$file' '$(DESTDIR)$(man1dir)/$$inst'"; \ - $(INSTALL_DATA) "$$file" "$(DESTDIR)$(man1dir)/$$inst"; \ - done + for i in $$list; do echo "$$i"; done | $(am__base_list) | \ + while read files; do \ + test -z "$$files" || { \ + echo " $(INSTALL_DATA) $$files '$(DESTDIR)$(man1dir)'"; \ + $(INSTALL_DATA) $$files "$(DESTDIR)$(man1dir)" || exit $$?; }; \ + done; } + uninstall-man1: @$(NORMAL_UNINSTALL) - @list='$(man1_MANS) $(dist_man1_MANS) $(nodist_man1_MANS)'; \ - l2='$(man_MANS) $(dist_man_MANS) $(nodist_man_MANS)'; \ - for i in $$l2; do \ - case "$$i" in \ - *.1*) list="$$list $$i" ;; \ - esac; \ - done; \ - for i in $$list; do \ - ext=`echo $$i | sed -e 's/^.*\\.//'`; \ - case "$$ext" in \ - 1*) ;; \ - *) ext='1' ;; \ - esac; \ - inst=`echo $$i | sed -e 's/\\.[0-9a-z]*$$//'`; \ - inst=`echo $$inst | sed -e 's/^.*\///'`; \ - inst=`echo $$inst | sed '$(transform)'`.$$ext; \ - echo " rm -f '$(DESTDIR)$(man1dir)/$$inst'"; \ - rm -f "$(DESTDIR)$(man1dir)/$$inst"; \ - done + @list='$(man1_MANS)'; test -n "$(man1dir)" || exit 0; \ + files=`{ for i in $$list; do echo "$$i"; done; \ + } | sed -e 's,.*/,,;h;s,.*\.,,;s,^[^1][0-9a-z]*$$,1,;x' \ + -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,'`; \ + dir='$(DESTDIR)$(man1dir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ unique=`for i in $$list; do \ if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ done | \ - $(AWK) '{ files[$$0] = 1; nonemtpy = 1; } \ + $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ END { if (nonempty) { for (i in files) print i; }; }'`; \ mkid -fID $$unique tags: TAGS TAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ $(TAGS_FILES) $(LISP) - tags=; \ + set x; \ here=`pwd`; \ list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ unique=`for i in $$list; do \ @@ -353,34 +425,66 @@ TAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ done | \ $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ END { if (nonempty) { for (i in files) print i; }; }'`; \ - if test -z "$(ETAGS_ARGS)$$tags$$unique"; then :; else \ + shift; \ + if test -z "$(ETAGS_ARGS)$$*$$unique"; then :; else \ test -n "$$unique" || unique=$$empty_fix; \ - $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ - $$tags $$unique; \ + if test $$# -gt 0; then \ + $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ + "$$@" $$unique; \ + else \ + $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ + $$unique; \ + fi; \ fi ctags: CTAGS CTAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ $(TAGS_FILES) $(LISP) - tags=; \ list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ unique=`for i in $$list; do \ if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ done | \ $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ END { if (nonempty) { for (i in files) print i; }; }'`; \ - test -z "$(CTAGS_ARGS)$$tags$$unique" \ + test -z "$(CTAGS_ARGS)$$unique" \ || $(CTAGS) $(CTAGSFLAGS) $(AM_CTAGSFLAGS) $(CTAGS_ARGS) \ - $$tags $$unique + $$unique GTAGS: here=`$(am__cd) $(top_builddir) && pwd` \ - && cd $(top_srcdir) \ - && gtags -i $(GTAGS_ARGS) $$here + && $(am__cd) $(top_srcdir) \ + && gtags -i $(GTAGS_ARGS) "$$here" + +cscopelist: $(HEADERS) $(SOURCES) $(LISP) + list='$(SOURCES) $(HEADERS) $(LISP)'; \ + case "$(srcdir)" in \ + [\\/]* | ?:[\\/]*) sdir="$(srcdir)" ;; \ + *) sdir=$(subdir)/$(srcdir) ;; \ + esac; \ + for i in $$list; do \ + if test -f "$$i"; then \ + echo "$(subdir)/$$i"; \ + else \ + echo "$$sdir/$$i"; \ + fi; \ + done >> $(top_builddir)/cscope.files distclean-tags: -rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags distdir: $(DISTFILES) + @list='$(MANS)'; if test -n "$$list"; then \ + list=`for p in $$list; do \ + if test -f $$p; then d=; else d="$(srcdir)/"; fi; \ + if test -f "$$d$$p"; then echo "$$d$$p"; else :; fi; done`; \ + if test -n "$$list" && \ + grep 'ab help2man is required to generate this page' $$list >/dev/null; then \ + echo "error: found man pages containing the 'missing help2man' replacement text:" >&2; \ + grep -l 'ab help2man is required to generate this page' $$list | sed 's/^/ /' >&2; \ + echo " to fix them, install help2man, remove and regenerate the man pages;" >&2; \ + echo " typically 'make maintainer-clean' will remove them" >&2; \ + exit 1; \ + else :; fi; \ + else :; fi @srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ topsrcdirstrip=`echo "$(top_srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ list='$(DISTFILES)'; \ @@ -396,13 +500,17 @@ distdir: $(DISTFILES) if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \ if test -d $$d/$$file; then \ dir=`echo "/$$file" | sed -e 's,/[^/]*$$,,'`; \ + if test -d "$(distdir)/$$file"; then \ + find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \ + fi; \ if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \ - cp -pR $(srcdir)/$$file $(distdir)$$dir || exit 1; \ + cp -fpR $(srcdir)/$$file "$(distdir)$$dir" || exit 1; \ + find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \ fi; \ - cp -pR $$d/$$file $(distdir)$$dir || exit 1; \ + cp -fpR $$d/$$file "$(distdir)$$dir" || exit 1; \ else \ - test -f $(distdir)/$$file \ - || cp -p $$d/$$file $(distdir)/$$file \ + test -f "$(distdir)/$$file" \ + || cp -p $$d/$$file "$(distdir)/$$file" \ || exit 1; \ fi; \ done @@ -423,16 +531,22 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: distclean-generic: -test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES) + -test . = "$(srcdir)" || test -z "$(CONFIG_CLEAN_VPATH_FILES)" || rm -f $(CONFIG_CLEAN_VPATH_FILES) maintainer-clean-generic: @echo "This command is intended for maintainers to use" @@ -454,6 +568,8 @@ dvi-am: html: html-am +html-am: + info: info-am info-am: @@ -462,18 +578,28 @@ install-data-am: install-man install-dvi: install-dvi-am +install-dvi-am: + install-exec-am: install-sbinPROGRAMS install-html: install-html-am +install-html-am: + install-info: install-info-am +install-info-am: + install-man: install-man1 install-pdf: install-pdf-am +install-pdf-am: + install-ps: install-ps-am +install-ps-am: + installcheck-am: maintainer-clean: maintainer-clean-am @@ -501,7 +627,7 @@ uninstall-man: uninstall-man1 .MAKE: install-am install-strip .PHONY: CTAGS GTAGS all all-am check check-am clean clean-generic \ - clean-libtool clean-sbinPROGRAMS ctags distclean \ + clean-libtool clean-sbinPROGRAMS cscopelist ctags distclean \ distclean-compile distclean-generic distclean-libtool \ distclean-tags distdir dvi dvi-am html html-am info info-am \ install install-am install-data install-data-am install-dvi \ @@ -515,6 +641,7 @@ uninstall-man: uninstall-man1 tags uninstall uninstall-am uninstall-man uninstall-man1 \ uninstall-sbinPROGRAMS + # Tell versions [3.59,3.63) of GNU make to not export all variables. # Otherwise a system limit (for SysV at least) may be exceeded. .NOEXPORT: diff --git a/contrib/openbsm/bin/auditreduce/auditreduce.1 b/contrib/openbsm/bin/auditreduce/auditreduce.1 index 6151f6e..157f31d 100644 --- a/contrib/openbsm/bin/auditreduce/auditreduce.1 +++ b/contrib/openbsm/bin/auditreduce/auditreduce.1 @@ -25,7 +25,7 @@ .\" IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE .\" POSSIBILITY OF SUCH DAMAGE. .\" -.\" $P4: //depot/projects/trustedbsd/openbsm/bin/auditreduce/auditreduce.1#17 $ +.\" $P4: //depot/projects/trustedbsd/openbsm/bin/auditreduce/auditreduce.1#18 $ .\" .Dd January 24, 2004 .Dt AUDITREDUCE 1 @@ -92,7 +92,7 @@ Select records with the given effective group ID or name. .It Fl g Ar rgid Select records with the given real group ID or name. .It Fl j Ar id -Select records having a subject token with matching ID. +Select records having a subject token with matching ID, where ID is a process ID. .It Fl m Ar event Select records with the given event name or number. This option can be used more then once to select records of multiple event types. diff --git a/contrib/openbsm/bin/praudit/Makefile.am b/contrib/openbsm/bin/praudit/Makefile.am index a362cea..c28afd4 100644 --- a/contrib/openbsm/bin/praudit/Makefile.am +++ b/contrib/openbsm/bin/praudit/Makefile.am @@ -1,6 +1,6 @@ -# -# $P4: //depot/projects/trustedbsd/openbsm/bin/praudit/Makefile.am#3 $ -# +## +## $P4: //depot/projects/trustedbsd/openbsm/bin/praudit/Makefile.am#4 $ +## if USE_NATIVE_INCLUDES INCLUDES = -I$(top_builddir) -I$(top_srcdir) diff --git a/contrib/openbsm/bin/praudit/Makefile.in b/contrib/openbsm/bin/praudit/Makefile.in index 4d88abf..d8469bb 100644 --- a/contrib/openbsm/bin/praudit/Makefile.in +++ b/contrib/openbsm/bin/praudit/Makefile.in @@ -1,8 +1,8 @@ -# Makefile.in generated by automake 1.10.1 from Makefile.am. +# Makefile.in generated by automake 1.12.2 from Makefile.am. # @configure_input@ -# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, -# 2003, 2004, 2005, 2006, 2007, 2008 Free Software Foundation, Inc. +# Copyright (C) 1994-2012 Free Software Foundation, Inc. + # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -14,14 +14,28 @@ @SET_MAKE@ -# -# $P4: //depot/projects/trustedbsd/openbsm/bin/praudit/Makefile.in#10 $ -# - VPATH = @srcdir@ +am__make_dryrun = \ + { \ + am__dry=no; \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + echo 'am--echo: ; @echo "AM" OK' | $(MAKE) -f - 2>/dev/null \ + | grep '^AM OK$$' >/dev/null || am__dry=yes;; \ + *) \ + for am__flg in $$MAKEFLAGS; do \ + case $$am__flg in \ + *=*|--*) ;; \ + *n*) am__dry=yes; break;; \ + esac; \ + done;; \ + esac; \ + test $$am__dry = yes; \ + } pkgdatadir = $(datadir)/@PACKAGE@ -pkglibdir = $(libdir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ +pkglibdir = $(libdir)/@PACKAGE@ +pkglibexecdir = $(libexecdir)/@PACKAGE@ am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd install_sh_DATA = $(install_sh) -c -m 644 install_sh_PROGRAM = $(install_sh) -c @@ -38,7 +52,8 @@ build_triplet = @build@ host_triplet = @host@ sbin_PROGRAMS = praudit$(EXEEXT) subdir = bin/praudit -DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in +DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in \ + $(top_srcdir)/config/depcomp ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ @@ -46,8 +61,8 @@ am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ mkinstalldirs = $(install_sh) -d CONFIG_HEADER = $(top_builddir)/config/config.h CONFIG_CLEAN_FILES = +CONFIG_CLEAN_VPATH_FILES = am__installdirs = "$(DESTDIR)$(sbindir)" "$(DESTDIR)$(man1dir)" -sbinPROGRAMS_INSTALL = $(INSTALL_PROGRAM) PROGRAMS = $(sbin_PROGRAMS) am_praudit_OBJECTS = praudit.$(OBJEXT) praudit_OBJECTS = $(am_praudit_OBJECTS) @@ -55,6 +70,7 @@ praudit_DEPENDENCIES = $(top_builddir)/libbsm/libbsm.la DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir)/config depcomp = $(SHELL) $(top_srcdir)/config/depcomp am__depfiles_maybe = depfiles +am__mv = mv -f COMPILE = $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) \ $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) LTCOMPILE = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) \ @@ -66,6 +82,38 @@ LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) \ $(LDFLAGS) -o $@ SOURCES = $(praudit_SOURCES) DIST_SOURCES = $(praudit_SOURCES) +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac +am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; +am__vpath_adj = case $$p in \ + $(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \ + *) f=$$p;; \ + esac; +am__strip_dir = f=`echo $$p | sed -e 's|^.*/||'`; +am__install_max = 40 +am__nobase_strip_setup = \ + srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*|]/\\\\&/g'` +am__nobase_strip = \ + for p in $$list; do echo "$$p"; done | sed -e "s|$$srcdirstrip/||" +am__nobase_list = $(am__nobase_strip_setup); \ + for p in $$list; do echo "$$p $$p"; done | \ + sed "s| $$srcdirstrip/| |;"' / .*\//!s/ .*/ ./; s,\( .*\)/[^/]*$$,\1,' | \ + $(AWK) 'BEGIN { files["."] = "" } { files[$$2] = files[$$2] " " $$1; \ + if (++n[$$2] == $(am__install_max)) \ + { print $$2, files[$$2]; n[$$2] = 0; files[$$2] = "" } } \ + END { for (dir in files) print dir, files[dir] }' +am__base_list = \ + sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ + sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } man1dir = $(mandir)/man1 NROFF = nroff MANS = $(man1_MANS) @@ -84,45 +132,52 @@ CCDEPMODE = @CCDEPMODE@ CFLAGS = @CFLAGS@ CPP = @CPP@ CPPFLAGS = @CPPFLAGS@ -CXX = @CXX@ -CXXCPP = @CXXCPP@ -CXXDEPMODE = @CXXDEPMODE@ -CXXFLAGS = @CXXFLAGS@ CYGPATH_W = @CYGPATH_W@ DEFS = @DEFS@ DEPDIR = @DEPDIR@ +DLLTOOL = @DLLTOOL@ DSYMUTIL = @DSYMUTIL@ -ECHO = @ECHO@ +DUMPBIN = @DUMPBIN@ ECHO_C = @ECHO_C@ ECHO_N = @ECHO_N@ ECHO_T = @ECHO_T@ EGREP = @EGREP@ EXEEXT = @EXEEXT@ -F77 = @F77@ -FFLAGS = @FFLAGS@ +FGREP = @FGREP@ GREP = @GREP@ INSTALL = @INSTALL@ INSTALL_DATA = @INSTALL_DATA@ INSTALL_PROGRAM = @INSTALL_PROGRAM@ INSTALL_SCRIPT = @INSTALL_SCRIPT@ INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@ +LD = @LD@ LDFLAGS = @LDFLAGS@ +LEX = @LEX@ +LEXLIB = @LEXLIB@ +LEX_OUTPUT_ROOT = @LEX_OUTPUT_ROOT@ LIBOBJS = @LIBOBJS@ LIBS = @LIBS@ LIBTOOL = @LIBTOOL@ +LIPO = @LIPO@ LN_S = @LN_S@ LTLIBOBJS = @LTLIBOBJS@ MAINT = @MAINT@ MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ MIG = @MIG@ MKDIR_P = @MKDIR_P@ +NM = @NM@ NMEDIT = @NMEDIT@ +OBJDUMP = @OBJDUMP@ OBJEXT = @OBJEXT@ +OTOOL = @OTOOL@ +OTOOL64 = @OTOOL64@ PACKAGE = @PACKAGE@ PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@ PACKAGE_NAME = @PACKAGE_NAME@ PACKAGE_STRING = @PACKAGE_STRING@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ +PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ RANLIB = @RANLIB@ @@ -131,13 +186,15 @@ SET_MAKE = @SET_MAKE@ SHELL = @SHELL@ STRIP = @STRIP@ VERSION = @VERSION@ +YACC = @YACC@ +YFLAGS = @YFLAGS@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ -ac_ct_CXX = @ac_ct_CXX@ -ac_ct_F77 = @ac_ct_F77@ +ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ am__include = @am__include@ am__leading_dot = @am__leading_dot@ am__quote = @am__quote@ @@ -196,14 +253,14 @@ $(srcdir)/Makefile.in: @MAINTAINER_MODE_TRUE@ $(srcdir)/Makefile.am $(am__confi @for dep in $?; do \ case '$(am__configure_deps)' in \ *$$dep*) \ - cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh \ - && exit 0; \ + ( cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh ) \ + && { if test -f $@; then exit 0; else break; fi; }; \ exit 1;; \ esac; \ done; \ - echo ' cd $(top_srcdir) && $(AUTOMAKE) --foreign bin/praudit/Makefile'; \ - cd $(top_srcdir) && \ - $(AUTOMAKE) --foreign bin/praudit/Makefile + echo ' cd $(top_srcdir) && $(AUTOMAKE) --foreign bin/praudit/Makefile'; \ + $(am__cd) $(top_srcdir) && \ + $(AUTOMAKE) --foreign bin/praudit/Makefile .PRECIOUS: Makefile Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status @case '$?' in \ @@ -221,35 +278,54 @@ $(top_srcdir)/configure: @MAINTAINER_MODE_TRUE@ $(am__configure_deps) cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh $(ACLOCAL_M4): @MAINTAINER_MODE_TRUE@ $(am__aclocal_m4_deps) cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh +$(am__aclocal_m4_deps): install-sbinPROGRAMS: $(sbin_PROGRAMS) @$(NORMAL_INSTALL) - test -z "$(sbindir)" || $(MKDIR_P) "$(DESTDIR)$(sbindir)" - @list='$(sbin_PROGRAMS)'; for p in $$list; do \ - p1=`echo $$p|sed 's/$(EXEEXT)$$//'`; \ - if test -f $$p \ - || test -f $$p1 \ - ; then \ - f=`echo "$$p1" | sed 's,^.*/,,;$(transform);s/$$/$(EXEEXT)/'`; \ - echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(sbinPROGRAMS_INSTALL) '$$p' '$(DESTDIR)$(sbindir)/$$f'"; \ - $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(sbinPROGRAMS_INSTALL) "$$p" "$(DESTDIR)$(sbindir)/$$f" || exit 1; \ - else :; fi; \ - done + @list='$(sbin_PROGRAMS)'; test -n "$(sbindir)" || list=; \ + if test -n "$$list"; then \ + echo " $(MKDIR_P) '$(DESTDIR)$(sbindir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(sbindir)" || exit 1; \ + fi; \ + for p in $$list; do echo "$$p $$p"; done | \ + sed 's/$(EXEEXT)$$//' | \ + while read p p1; do if test -f $$p || test -f $$p1; \ + then echo "$$p"; echo "$$p"; else :; fi; \ + done | \ + sed -e 'p;s,.*/,,;n;h' -e 's|.*|.|' \ + -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ + sed 'N;N;N;s,\n, ,g' | \ + $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ + { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ + if ($$2 == $$4) files[d] = files[d] " " $$1; \ + else { print "f", $$3 "/" $$4, $$1; } } \ + END { for (d in files) print "f", d, files[d] }' | \ + while read type dir files; do \ + if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ + test -z "$$files" || { \ + echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(sbindir)$$dir'"; \ + $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(sbindir)$$dir" || exit $$?; \ + } \ + ; done uninstall-sbinPROGRAMS: @$(NORMAL_UNINSTALL) - @list='$(sbin_PROGRAMS)'; for p in $$list; do \ - f=`echo "$$p" | sed 's,^.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/'`; \ - echo " rm -f '$(DESTDIR)$(sbindir)/$$f'"; \ - rm -f "$(DESTDIR)$(sbindir)/$$f"; \ - done + @list='$(sbin_PROGRAMS)'; test -n "$(sbindir)" || list=; \ + files=`for p in $$list; do echo "$$p"; done | \ + sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ + -e 's/$$/$(EXEEXT)/' `; \ + test -n "$$list" || exit 0; \ + echo " ( cd '$(DESTDIR)$(sbindir)' && rm -f" $$files ")"; \ + cd "$(DESTDIR)$(sbindir)" && rm -f $$files clean-sbinPROGRAMS: - @list='$(sbin_PROGRAMS)'; for p in $$list; do \ - f=`echo $$p|sed 's/$(EXEEXT)$$//'`; \ - echo " rm -f $$p $$f"; \ - rm -f $$p $$f ; \ - done -praudit$(EXEEXT): $(praudit_OBJECTS) $(praudit_DEPENDENCIES) + @list='$(sbin_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list +praudit$(EXEEXT): $(praudit_OBJECTS) $(praudit_DEPENDENCIES) $(EXTRA_praudit_DEPENDENCIES) @rm -f praudit$(EXEEXT) $(LINK) $(praudit_OBJECTS) $(praudit_LDADD) $(LIBS) @@ -263,21 +339,21 @@ distclean-compile: .c.o: @am__fastdepCC_TRUE@ $(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< -@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po +@am__fastdepCC_TRUE@ $(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po @AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(COMPILE) -c $< .c.obj: @am__fastdepCC_TRUE@ $(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` -@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po +@am__fastdepCC_TRUE@ $(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po @AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(COMPILE) -c `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< -@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo +@am__fastdepCC_TRUE@ $(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(LTCOMPILE) -c -o $@ $< @@ -287,65 +363,61 @@ mostlyclean-libtool: clean-libtool: -rm -rf .libs _libs -install-man1: $(man1_MANS) $(man_MANS) +install-man1: $(man1_MANS) @$(NORMAL_INSTALL) - test -z "$(man1dir)" || $(MKDIR_P) "$(DESTDIR)$(man1dir)" - @list='$(man1_MANS) $(dist_man1_MANS) $(nodist_man1_MANS)'; \ - l2='$(man_MANS) $(dist_man_MANS) $(nodist_man_MANS)'; \ - for i in $$l2; do \ - case "$$i" in \ - *.1*) list="$$list $$i" ;; \ - esac; \ + @list1='$(man1_MANS)'; \ + list2=''; \ + test -n "$(man1dir)" \ + && test -n "`echo $$list1$$list2`" \ + || exit 0; \ + echo " $(MKDIR_P) '$(DESTDIR)$(man1dir)'"; \ + $(MKDIR_P) "$(DESTDIR)$(man1dir)" || exit 1; \ + { for i in $$list1; do echo "$$i"; done; \ + if test -n "$$list2"; then \ + for i in $$list2; do echo "$$i"; done \ + | sed -n '/\.1[a-z]*$$/p'; \ + fi; \ + } | while read p; do \ + if test -f $$p; then d=; else d="$(srcdir)/"; fi; \ + echo "$$d$$p"; echo "$$p"; \ + done | \ + sed -e 'n;s,.*/,,;p;h;s,.*\.,,;s,^[^1][0-9a-z]*$$,1,;x' \ + -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,' | \ + sed 'N;N;s,\n, ,g' | { \ + list=; while read file base inst; do \ + if test "$$base" = "$$inst"; then list="$$list $$file"; else \ + echo " $(INSTALL_DATA) '$$file' '$(DESTDIR)$(man1dir)/$$inst'"; \ + $(INSTALL_DATA) "$$file" "$(DESTDIR)$(man1dir)/$$inst" || exit $$?; \ + fi; \ done; \ - for i in $$list; do \ - if test -f $(srcdir)/$$i; then file=$(srcdir)/$$i; \ - else file=$$i; fi; \ - ext=`echo $$i | sed -e 's/^.*\\.//'`; \ - case "$$ext" in \ - 1*) ;; \ - *) ext='1' ;; \ - esac; \ - inst=`echo $$i | sed -e 's/\\.[0-9a-z]*$$//'`; \ - inst=`echo $$inst | sed -e 's/^.*\///'`; \ - inst=`echo $$inst | sed '$(transform)'`.$$ext; \ - echo " $(INSTALL_DATA) '$$file' '$(DESTDIR)$(man1dir)/$$inst'"; \ - $(INSTALL_DATA) "$$file" "$(DESTDIR)$(man1dir)/$$inst"; \ - done + for i in $$list; do echo "$$i"; done | $(am__base_list) | \ + while read files; do \ + test -z "$$files" || { \ + echo " $(INSTALL_DATA) $$files '$(DESTDIR)$(man1dir)'"; \ + $(INSTALL_DATA) $$files "$(DESTDIR)$(man1dir)" || exit $$?; }; \ + done; } + uninstall-man1: @$(NORMAL_UNINSTALL) - @list='$(man1_MANS) $(dist_man1_MANS) $(nodist_man1_MANS)'; \ - l2='$(man_MANS) $(dist_man_MANS) $(nodist_man_MANS)'; \ - for i in $$l2; do \ - case "$$i" in \ - *.1*) list="$$list $$i" ;; \ - esac; \ - done; \ - for i in $$list; do \ - ext=`echo $$i | sed -e 's/^.*\\.//'`; \ - case "$$ext" in \ - 1*) ;; \ - *) ext='1' ;; \ - esac; \ - inst=`echo $$i | sed -e 's/\\.[0-9a-z]*$$//'`; \ - inst=`echo $$inst | sed -e 's/^.*\///'`; \ - inst=`echo $$inst | sed '$(transform)'`.$$ext; \ - echo " rm -f '$(DESTDIR)$(man1dir)/$$inst'"; \ - rm -f "$(DESTDIR)$(man1dir)/$$inst"; \ - done + @list='$(man1_MANS)'; test -n "$(man1dir)" || exit 0; \ + files=`{ for i in $$list; do echo "$$i"; done; \ + } | sed -e 's,.*/,,;h;s,.*\.,,;s,^[^1][0-9a-z]*$$,1,;x' \ + -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,'`; \ + dir='$(DESTDIR)$(man1dir)'; $(am__uninstall_files_from_dir) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ unique=`for i in $$list; do \ if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ done | \ - $(AWK) '{ files[$$0] = 1; nonemtpy = 1; } \ + $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ END { if (nonempty) { for (i in files) print i; }; }'`; \ mkid -fID $$unique tags: TAGS TAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ $(TAGS_FILES) $(LISP) - tags=; \ + set x; \ here=`pwd`; \ list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ unique=`for i in $$list; do \ @@ -353,34 +425,66 @@ TAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ done | \ $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ END { if (nonempty) { for (i in files) print i; }; }'`; \ - if test -z "$(ETAGS_ARGS)$$tags$$unique"; then :; else \ + shift; \ + if test -z "$(ETAGS_ARGS)$$*$$unique"; then :; else \ test -n "$$unique" || unique=$$empty_fix; \ - $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ - $$tags $$unique; \ + if test $$# -gt 0; then \ + $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ + "$$@" $$unique; \ + else \ + $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ + $$unique; \ + fi; \ fi ctags: CTAGS CTAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ $(TAGS_FILES) $(LISP) - tags=; \ list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ unique=`for i in $$list; do \ if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ done | \ $(AWK) '{ files[$$0] = 1; nonempty = 1; } \ END { if (nonempty) { for (i in files) print i; }; }'`; \ - test -z "$(CTAGS_ARGS)$$tags$$unique" \ + test -z "$(CTAGS_ARGS)$$unique" \ || $(CTAGS) $(CTAGSFLAGS) $(AM_CTAGSFLAGS) $(CTAGS_ARGS) \ - $$tags $$unique + $$unique GTAGS: here=`$(am__cd) $(top_builddir) && pwd` \ - && cd $(top_srcdir) \ - && gtags -i $(GTAGS_ARGS) $$here + && $(am__cd) $(top_srcdir) \ + && gtags -i $(GTAGS_ARGS) "$$here" + +cscopelist: $(HEADERS) $(SOURCES) $(LISP) + list='$(SOURCES) $(HEADERS) $(LISP)'; \ + case "$(srcdir)" in \ + [\\/]* | ?:[\\/]*) sdir="$(srcdir)" ;; \ + *) sdir=$(subdir)/$(srcdir) ;; \ + esac; \ + for i in $$list; do \ + if test -f "$$i"; then \ + echo "$(subdir)/$$i"; \ + else \ + echo "$$sdir/$$i"; \ + fi; \ + done >> $(top_builddir)/cscope.files distclean-tags: -rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags distdir: $(DISTFILES) + @list='$(MANS)'; if test -n "$$list"; then \ + list=`for p in $$list; do \ + if test -f $$p; then d=; else d="$(srcdir)/"; fi; \ + if test -f "$$d$$p"; then echo "$$d$$p"; else :; fi; done`; \ + if test -n "$$list" && \ + grep 'ab help2man is required to generate this page' $$list >/dev/null; then \ + echo "error: found man pages containing the 'missing help2man' replacement text:" >&2; \ + grep -l 'ab help2man is required to generate this page' $$list | sed 's/^/ /' >&2; \ + echo " to fix them, install help2man, remove and regenerate the man pages;" >&2; \ + echo " typically 'make maintainer-clean' will remove them" >&2; \ + exit 1; \ + else :; fi; \ + else :; fi @srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ topsrcdirstrip=`echo "$(top_srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ list='$(DISTFILES)'; \ @@ -396,13 +500,17 @@ distdir: $(DISTFILES) if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \ if test -d $$d/$$file; then \ dir=`echo "/$$file" | sed -e 's,/[^/]*$$,,'`; \ + if test -d "$(distdir)/$$file"; then \ + find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \ + fi; \ if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \ - cp -pR $(srcdir)/$$file $(distdir)$$dir || exit 1; \ + cp -fpR $(srcdir)/$$file "$(distdir)$$dir" || exit 1; \ + find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \ fi; \ - cp -pR $$d/$$file $(distdir)$$dir || exit 1; \ + cp -fpR $$d/$$file "$(distdir)$$dir" || exit 1; \ else \ - test -f $(distdir)/$$file \ - || cp -p $$d/$$file $(distdir)/$$file \ + test -f "$(distdir)/$$file" \ + || cp -p $$d/$$file "$(distdir)/$$file" \ || exit 1; \ fi; \ done @@ -423,16 +531,22 @@ install-am: all-am installcheck: installcheck-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ - install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ - `test -z '$(STRIP)' || \ - echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi mostlyclean-generic: clean-generic: distclean-generic: -test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES) + -test . = "$(srcdir)" || test -z "$(CONFIG_CLEAN_VPATH_FILES)" || rm -f $(CONFIG_CLEAN_VPATH_FILES) maintainer-clean-generic: @echo "This command is intended for maintainers to use" @@ -454,6 +568,8 @@ dvi-am: html: html-am +html-am: + info: info-am info-am: @@ -462,18 +578,28 @@ install-data-am: install-man install-dvi: install-dvi-am +install-dvi-am: + install-exec-am: install-sbinPROGRAMS install-html: install-html-am +install-html-am: + install-info: install-info-am +install-info-am: + install-man: install-man1 install-pdf: install-pdf-am +install-pdf-am: + install-ps: install-ps-am +install-ps-am: + installcheck-am: maintainer-clean: maintainer-clean-am @@ -501,7 +627,7 @@ uninstall-man: uninstall-man1 .MAKE: install-am install-strip .PHONY: CTAGS GTAGS all all-am check check-am clean clean-generic \ - clean-libtool clean-sbinPROGRAMS ctags distclean \ + clean-libtool clean-sbinPROGRAMS cscopelist ctags distclean \ distclean-compile distclean-generic distclean-libtool \ distclean-tags distdir dvi dvi-am html html-am info info-am \ install install-am install-data install-data-am install-dvi \ @@ -515,6 +641,7 @@ uninstall-man: uninstall-man1 tags uninstall uninstall-am uninstall-man uninstall-man1 \ uninstall-sbinPROGRAMS + # Tell versions [3.59,3.63) of GNU make to not export all variables. # Otherwise a system limit (for SysV at least) may be exceeded. .NOEXPORT: diff --git a/contrib/openbsm/bin/praudit/praudit.1 b/contrib/openbsm/bin/praudit/praudit.1 index 6a4fef0..99ea7c8 100644 --- a/contrib/openbsm/bin/praudit/praudit.1 +++ b/contrib/openbsm/bin/praudit/praudit.1 @@ -1,4 +1,4 @@ -.\" Copyright (c) 2004 Apple Inc. +.\" Copyright (c) 2004-2009 Apple Inc. .\" All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without @@ -25,9 +25,9 @@ .\" IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE .\" POSSIBILITY OF SUCH DAMAGE. .\" -.\" $P4: //depot/projects/trustedbsd/openbsm/bin/praudit/praudit.1#13 $ +.\" $P4: //depot/projects/trustedbsd/openbsm/bin/praudit/praudit.1#14 $ .\" -.Dd November 5, 2006 +.Dd August 4, 2009 .Dt PRAUDIT 1 .Os .Sh NAME @@ -35,7 +35,7 @@ .Nd "print the contents of audit trail files" .Sh SYNOPSIS .Nm -.Op Fl lpx +.Op Fl lnpx .Op Fl r | s .Op Fl d Ar del .Op Ar @@ -58,6 +58,9 @@ The default delimiter is the comma. Prints the entire record on the same line. If this option is not specified, every token is displayed on a different line. +.It Fl n +Do not convert user and group IDs to their names but leave in their +numeric forms. .It Fl p Specify this option if input to .Nm diff --git a/contrib/openbsm/bin/praudit/praudit.c b/contrib/openbsm/bin/praudit/praudit.c index a1dbf9d..f20f245 100644 --- a/contrib/openbsm/bin/praudit/praudit.c +++ b/contrib/openbsm/bin/praudit/praudit.c @@ -1,5 +1,5 @@ /*- - * Copyright (c) 2004-2008 Apple Inc. + * Copyright (c) 2004-2009 Apple Inc. * Copyright (c) 2006 Martin Voros * All rights reserved. * @@ -11,7 +11,7 @@ * 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. - * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * 3. Neither the name of Apple Inc. ("Apple") nor the names of * its contributors may be used to endorse or promote products derived * from this software without specific prior written permission. * @@ -27,7 +27,7 @@ * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE * POSSIBILITY OF SUCH DAMAGE. * - * $P4: //depot/projects/trustedbsd/openbsm/bin/praudit/praudit.c#14 $ + * $P4: //depot/projects/trustedbsd/openbsm/bin/praudit/praudit.c#16 $ */ /* @@ -35,7 +35,7 @@ */ /* - * praudit [-lpx] [-r | -s] [-d del] [file ...] + * praudit [-lnpx] [-r | -s] [-d del] [file ...] */ #include <bsm/libbsm.h> @@ -49,16 +49,14 @@ extern int optind, optopt, opterr,optreset; static char *del = ","; /* Default delimiter. */ static int oneline = 0; -static int raw = 0; -static int shortfrm = 0; static int partial = 0; -static int xml = 0; +static int oflags = AU_OFLAG_NONE; static void usage(void) { - fprintf(stderr, "usage: praudit [-lpx] [-r | -s] [-d del] " + fprintf(stderr, "usage: praudit [-lnpx] [-r | -s] [-d del] " "[file ...]\n"); exit(1); } @@ -91,15 +89,10 @@ print_tokens(FILE *fp) if (-1 == au_fetch_tok(&tok, buf + bytesread, reclen - bytesread)) break; - if (xml) - au_print_tok_xml(stdout, &tok, del, raw, - shortfrm); - else - au_print_tok(stdout, &tok, del, raw, - shortfrm); + au_print_flags_tok(stdout, &tok, del, oflags); bytesread += tok.len; if (oneline) { - if (!xml) + if (!(oflags & AU_OFLAG_XML)) printf("%s", del); } else printf("\n"); @@ -119,7 +112,7 @@ main(int argc, char **argv) int i; FILE *fp; - while ((ch = getopt(argc, argv, "d:lprsx")) != -1) { + while ((ch = getopt(argc, argv, "d:lnprsx")) != -1) { switch(ch) { case 'd': del = optarg; @@ -129,24 +122,28 @@ main(int argc, char **argv) oneline = 1; break; + case 'n': + oflags |= AU_OFLAG_NORESOLVE; + break; + case 'p': partial = 1; break; case 'r': - if (shortfrm) + if (oflags & AU_OFLAG_SHORT) usage(); /* Exclusive from shortfrm. */ - raw = 1; + oflags |= AU_OFLAG_RAW; break; case 's': - if (raw) + if (oflags & AU_OFLAG_RAW) usage(); /* Exclusive from raw. */ - shortfrm = 1; + oflags |= AU_OFLAG_SHORT; break; case 'x': - xml = 1; + oflags |= AU_OFLAG_XML; break; case '?': @@ -155,7 +152,7 @@ main(int argc, char **argv) } } - if (xml) + if (oflags & AU_OFLAG_XML) au_print_xml_header(stdout); /* For each of the files passed as arguments dump the contents. */ @@ -171,7 +168,7 @@ main(int argc, char **argv) fclose(fp); } - if (xml) + if (oflags & AU_OFLAG_XML) au_print_xml_footer(stdout); return (1); |