Skip site navigation (1)Skip section navigation (2)
Date:      Mon, 23 Mar 2015 19:25:35 +0000 (UTC)
From:      Devin Teske <dteske@FreeBSD.org>
To:        src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-stable@freebsd.org, svn-src-stable-9@freebsd.org
Subject:   svn commit: r280391 - stable/9/usr.sbin/sysrc
Message-ID:  <201503231925.t2NJPZ4X053505@svn.freebsd.org>

next in thread | raw e-mail | index | archive | help
Author: dteske
Date: Mon Mar 23 19:25:34 2015
New Revision: 280391
URL: https://svnweb.freebsd.org/changeset/base/280391

Log:
  MFC revisions 268860, 268863, 274068, 274119, 279624:
  r268860: Minor enhancements, bug fixes, man-page adjustments to sysrc(8)
  r268863: Bump date/copyright in man-page
  r274068: Add key+=append syntax
  r279624: Add key-=remove syntax
  r274119: Add EXAMPLES-section entries for new syntax
  
  Reported by:	lme (r268860)
  Reviewed by:	shurd (r274068)
  Thanks to:	seanc (r274068, r279624, r274119)

Modified:
  stable/9/usr.sbin/sysrc/sysrc
  stable/9/usr.sbin/sysrc/sysrc.8
Directory Properties:
  stable/9/usr.sbin/sysrc/   (props changed)

Modified: stable/9/usr.sbin/sysrc/sysrc
==============================================================================
--- stable/9/usr.sbin/sysrc/sysrc	Mon Mar 23 19:12:55 2015	(r280390)
+++ stable/9/usr.sbin/sysrc/sysrc	Mon Mar 23 19:25:34 2015	(r280391)
@@ -1,6 +1,6 @@
 #!/bin/sh
 #-
-# Copyright (c) 2010-2013 Devin Teske
+# Copyright (c) 2010-2015 Devin Teske
 # All rights reserved.
 #
 # Redistribution and use in source and binary forms, with or without
@@ -40,7 +40,7 @@ BSDCFG_SHARE="/usr/share/bsdconfig"
 #
 # Version information
 #
-SYSRC_VERSION="6.0 Nov-07,2013"
+SYSRC_VERSION="6.3 Mar-4,2015"
 
 #
 # Options
@@ -80,7 +80,7 @@ die()
 #
 usage()
 {
-	f_err "Usage: %s [OPTIONS] name[=value] ...\n" "$pgm"
+	f_err "Usage: %s [OPTIONS] name[[+]=value] ...\n" "$pgm"
 	f_err "Try \`%s --help' for more information.\n" "$pgm"
 	die
 }
@@ -94,7 +94,7 @@ help()
 	local optfmt="\t%-11s%s\n"
 	local envfmt="\t%-17s%s\n"
 
-	f_err "Usage: %s [OPTIONS] name[=value] ...\n" "$pgm"
+	f_err "Usage: %s [OPTIONS] name[[+|-]=value] ...\n" "$pgm"
 
 	f_err "OPTIONS:\n"
 	f_err "$optfmt" "-a" \
@@ -102,7 +102,7 @@ help()
 	f_err "$optfmt" "-A" \
 	      "Dump a list of all configuration variables (incl. defaults)."
 	f_err "$optfmt" "-c" \
-	      "Check. Return success if no changes needed, else error."
+	      "Check. Return success if set or no changes, else error."
 	f_err "$optfmt" "-d" \
 	      "Print a description of the given variable."
 	f_err "$optfmt" "-D" \
@@ -134,7 +134,7 @@ help()
 	f_err "$optfmt" "-N" \
 	      "Show only variable names, not their values."
 	f_err "$optfmt" "-q" \
-	      "Quiet. Ignore previous \`-v' and/or SYSRC_VERBOSE."
+	      "Quiet. Disable verbose and hide certain errors."
 	f_err "$optfmt" "-R dir" \
 	      "Operate within the root directory \`dir' rather than \`/'."
 	f_err "$optfmt" "-v" \
@@ -152,8 +152,6 @@ help()
 	      "Override default rc_conf_files (even if set to NULL)."
 	f_err "$envfmt" "RC_DEFAULTS" \
 	      "Location of \`/etc/defaults/rc.conf' file."
-	f_err "$envfmt" "SYSRC_VERBOSE" \
-	      "Default verbosity. Set to non-NULL to enable."
 
 	die
 }
@@ -527,10 +525,16 @@ fi
 #
 # Process command-line arguments
 #
-costatus=$SUCCESS
+status=$SUCCESS
 while [ $# -gt 0 ]; do
 	NAME="${1%%=*}"
 
+	case "$NAME" in
+	*+) mode=APPEND NAME="${NAME%+}" ;;
+	*-) mode=REMOVE NAME="${NAME%-}" ;;
+	 *) mode=ASSIGN
+	esac
+
 	[ "$DESCRIBE" ] && \
 		echo "$NAME: $( f_sysrc_desc "$NAME" )"
 
@@ -558,7 +562,7 @@ while [ $# -gt 0 ]; do
 		# desire to set some value
 		#
 		if [ "$DELETE" ]; then
-			f_sysrc_delete "$NAME"
+			f_sysrc_delete "$NAME" || status=$FAILURE
 			shift 1
 			continue
 		fi
@@ -568,28 +572,93 @@ while [ $# -gt 0 ]; do
 		#
 		if [ "$CHECK_ONLY" ]; then
 			if ! IGNORED=$( f_sysrc_get "$NAME?" ); then
-				costatus=$FAILURE
-			else
-				value=$( f_sysrc_get "$NAME" )
-				[ "$value" = "${1#*=}" ] || costatus=$FAILURE
+				status=$FAILURE
+				[ "$SYSRC_VERBOSE" ] &&
+					echo "$NAME: not currently set"
+				shift 1
+				continue
+			fi
+			value=$( f_sysrc_get "$NAME" )
+			if [ "$value" != "${1#*=}" ]; then
+				status=$FAILURE
+				if [ "$SYSRC_VERBOSE" ]; then
+					echo -n "$( f_sysrc_find "$NAME" ): "
+					echo -n "$NAME: would change from "
+					echo "\`$value' to \`${1#*=}'"
+				fi
+			elif [ "$SYSRC_VERBOSE" ]; then
+				echo -n "$( f_sysrc_find "$NAME" ): "
+				echo "$NAME: already set to \`$value'"
 			fi
 			shift 1
 			continue
 		fi
 
 		#
-		# If `-N' is passed, simplify the output
+		# Determine both `before' value and appropriate `new' value
 		#
-		if [ ! "$SHOW_VALUE" ]; then
-			echo "$NAME"
-			f_sysrc_set "$NAME" "${1#*}"
-		else
+		case "$mode" in
+		APPEND)
+			before=$( f_sysrc_get "$NAME" )
+			add="${1#*=}"
+			delim="${add%"${add#?}"}" # first character
+			oldIFS="$IFS"
+			case "$delim" in
+			""|[$IFS]|[a-zA-Z0-9]) delim=" " ;;
+			*) IFS="$delim"
+			esac
+			new="$before"
+			for a in $add; do
+				[ "$a" ] || continue
+				skip=
+				for b in $before; do
+					[ "$b" = "$a" ] && skip=1 break
+				done
+				[ "$skip" ] || new="$new$delim$a"
+			done
+			new="${new#"$delim"}" IFS="$oldIFS"
+			unset add delim oldIFS a skip b
+			[ "$SHOW_FILE" ] && before=$( f_sysrc_find "$NAME" )
+			;;
+		REMOVE)
+			before=$( f_sysrc_get "$NAME" )
+			remove="${1#*=}"
+			delim="${remove%"${remove#?}"}" # first character
+			oldIFS="$IFS"
+			case "$delim" in
+			""|[$IFS]|[a-zA-Z0-9]) delim=" " ;;
+			*) IFS="$delim"
+			esac
+			new=
+			for b in $before; do
+				[ "$b" ] || continue
+				add=1
+				for r in $remove; do
+					[ "$r" = "$b" ] && add= break
+				done
+				[ "$add" ] && new="$new$delim$b"
+			done
+			new="${new#"$delim"}" IFS="$oldIFS"
+			unset remove delim oldIFS b add r
+			[ "$SHOW_FILE" ] && before=$( f_sysrc_find "$NAME" )
+			;;
+		*)
 			if [ "$SHOW_FILE" ]; then
 				before=$( f_sysrc_find "$NAME" )
 			else
 				before=$( f_sysrc_get "$NAME" )
 			fi
-			if f_sysrc_set "$NAME" "${1#*=}"; then
+			new="${1#*=}"
+		esac
+
+		#
+		# If `-N' is passed, simplify the output
+		#
+		if [ ! "$SHOW_VALUE" ]; then
+			echo "$NAME"
+			f_sysrc_set "$NAME" "$new"
+		else
+			if f_sysrc_set "$NAME" "$new"; then
 				if [ "$SHOW_FILE" ]; then
 					after=$( f_sysrc_find "$NAME" )
 				else
@@ -604,10 +673,10 @@ while [ $# -gt 0 ]; do
 		;;
 	*)
 		if ! IGNORED=$( f_sysrc_get "$NAME?" ); then
-			[ "$IGNORE_UNKNOWNS" ] ||
+			[ "$IGNORE_UNKNOWNS" -o "$QUIET" ] ||
 				echo "$pgm: unknown variable '$NAME'"
 			shift 1
-			costatus=$FAILURE
+			status=$FAILURE
 			continue
 		fi
 
@@ -631,7 +700,7 @@ while [ $# -gt 0 ]; do
 		# If `-x' or `-X' is passed, delete the variable
 		#
 		if [ "$DELETE" ]; then
-			f_sysrc_delete "$NAME"
+			f_sysrc_delete "$NAME" || status=$FAILURE
 			shift 1
 			continue
 		fi
@@ -667,7 +736,7 @@ while [ $# -gt 0 ]; do
 	shift 1
 done
 
-[ ! "$CHECK_ONLY" ] || exit $costatus
+exit $status # $SUCCESS unless error occurred with either `-c' or `-x'
 
 ################################################################################
 # END

Modified: stable/9/usr.sbin/sysrc/sysrc.8
==============================================================================
--- stable/9/usr.sbin/sysrc/sysrc.8	Mon Mar 23 19:12:55 2015	(r280390)
+++ stable/9/usr.sbin/sysrc/sysrc.8	Mon Mar 23 19:25:34 2015	(r280391)
@@ -1,4 +1,4 @@
-.\" Copyright (c) 2011-2013 Devin Teske
+.\" Copyright (c) 2011-2015 Devin Teske
 .\" All rights reserved.
 .\"
 .\" Redistribution and use in source and binary forms, with or without
@@ -24,7 +24,7 @@
 .\"
 .\" $FreeBSD$
 .\"
-.Dd Nov 20, 2013
+.Dd March 4, 2015
 .Dt SYSRC 8
 .Os
 .Sh NAME
@@ -35,7 +35,7 @@
 .Op Fl cdDeFhinNqvx
 .Op Fl f Ar file
 .Op Fl j Ar jail | Fl R Ar dir
-.Ar name Ns Op = Ns Ar value
+.Ar name Ns Op Ns Oo +|- Oc Ns = Ns Ar value
 .Ar ...
 .Nm
 .Op Fl cdDeFhinNqvx
@@ -58,11 +58,14 @@ Dump a list of all non-default configura
 Dump a list of all configuration variables
 .Pq incl. defaults .
 .It Fl c
-Check if the value will change when assigning a new value.
+Check only.
+For querying, return success if all requested variables are set
+.Pq even if NULL ,
+otherwise return error status.
+For assignments, return success if no changes are required, otherwise failure.
 If verbose
 .Pq see Dq Fl v
-prints a message stating whether a change would occur.
-Exits with success if no change is necessary, else returns error status.
+prints a message stating whether variables are set and/or changes are required.
 .It Fl d
 Print a description of the given variable.
 .It Fl D
@@ -108,14 +111,12 @@ Show only variable values, not their nam
 Show only variable names, not their values.
 .It Fl q
 Quiet.
-Ignore previous occurrences of
-.Fl v
-flag.
+Disable verbose and hide certain errors.
 .It Fl R Ar dir
 Operate within the root directory
-.Pq Sq Ar dir
+.Sq Ar dir
 rather than
-.Pq Sq / .
+.Sq / .
 .It Fl v
 Verbose.
 Print the pathname of the specific
@@ -127,13 +128,22 @@ Print version information to stdout and 
 Remove variable(s) from specified file(s).
 .El
 .Pp
-This utility works similar to
+This utility has a similar syntax to
 .Xr sysctl 8 .
 It shares the `-e' and `-n' options
 .Pq detailed above
 and also has the same
 .Ql name[=value]
-syntax for querying/setting configuration options.
+syntax for making queries/assignments.
+In addition
+.Pq but unlike Xr sysctl 8 ,
+.Ql name+=value
+is supported for adding items to values
+.Pq see APPENDING VALUES
+and
+.Ql name-=value
+is supported for removing items from values
+.Pq see SUBTRACTING VALUES .
 .Pp
 However, while
 .Xr sysctl 8
@@ -182,6 +192,115 @@ modifying these integral files (yet taki
 grow unwieldy should
 .Nm
 be called repeatedly).
+.Sh APPENDING VALUES
+When using the
+.Ql key+=value
+syntax to add items to existing values,
+the first character of the value is taken as the delimiter separating items
+.Pq usually Qo \  Qc or Qo , Qc .
+For example, in the following statement:
+.Bl -tag -width indent+
+.It \ 
+.Nm
+cloned_interfaces+=" gif0"
+.El
+.Pp
+the first character is a space, informing
+.Nm
+that existing values are to be considered separated by whitespace.
+If
+.Ql gif0
+is not found in the existing value for
+.Va cloned_interfaces ,
+it is added
+.Pq with delimiter only if existing value is non-NULL .
+.Pp
+For convenience, if the first character is alpha-numeric
+.Pq letters A-Z, a-z, or numbers 0-9 ,
+.Nm
+uses the default setting of whitespace as separator.
+For example, the above and below statements are equivalent since
+.Dq gif0
+starts with an alpha-numeric character
+.Pq the letter Li g :
+.Pp
+.Bl -tag -width indent+
+.It \ 
+.Nm
+cloned_interfaces+=gif0
+.El
+.Pp
+Take the following sequence for example:
+.Bl -tag -width indent+
+.It \ 
+.Nm
+cloned_interfaces= # start with NULL
+.It \ 
+.Nm
+cloned_interfaces+=gif0
+.Dl # NULL -> `gif0' Pq NB: no preceding delimiter
+.It \ 
+.Nm
+cloned_interfaces+=gif0 # no change
+.It \ 
+.Nm
+cloned_interfaces+="tun0 gif0"
+.Dl # `gif0' -> `gif0 tun0' Pq NB: no duplication
+.El
+.Pp
+.Nm
+prevents the same value from being added if already there.
+.Sh SUBTRACTING VALUES
+When using the
+.Ql key-=value
+syntax to remove items from existing values,
+the first character of the value is taken as the delimiter separating items
+.Pq usually Qo \  Qc or Qo , Qc .
+For example, in the following statement:
+.Pp
+.Dl Nm cloned_interfaces-=" gif0"
+.Pp
+the first character is a space, informing
+.Nm
+that existing values are to be considered separated by whitespace.
+If
+.Ql gif0
+is found in the existing value for
+.Va cloned_interfaces ,
+it is removed
+.Pq extra delimiters removed .
+.Pp
+For convenience, if the first character is alpha-numeric
+.Pq letters A-Z, a-z, or numbers 0-9 ,
+.Nm
+uses the default setting of whitespace as separator.
+For example, the above and below statements are equivalent since
+.Dq gif0
+starts with an alpha-numeric character
+.Pq the letter Li g :
+.Pp
+.Bl -tag -width indent+
+.It \ 
+.Nm
+cloned_interfaces-=gif0
+.El
+.Pp
+Take the following sequence for example:
+.Bl -tag -width indent+
+.It \ 
+.Nm
+foo="bar baz" # start
+.It \ 
+.Nm
+foo-=bar # `bar baz' -> `baz'
+.It \ 
+.Nm
+foo-=baz # `baz' -> NULL
+.El
+.Pp
+.Nm
+removes all occurrences of all items provided
+and collapses extra delimiters between items.
 .Sh ENVIRONMENT
 The following environment variables are referenced by
 .Nm :
@@ -242,6 +361,16 @@ Working on other files, such as
 -f /etc/crontab MAILTO
 .Dl returns the value of the MAILTO setting Pq if configured .
 .Pp
+Appending to existing values:
+.Pp
+.Nm
+\&cloned_interfaces+=gif0
+.Dl appends Qo gif0 Qc to $cloned_interfaces Pq see APPENDING VALUES .
+.Pp
+.Nm
+\&cloned_interfaces-=gif0
+.Dl removes Qo gif0 Qc from $cloned_interfaces Pq see SUBTRACTING VALUES .
+.Pp
 In addition to the above syntax,
 .Nm
 also supports inline
@@ -304,5 +433,5 @@ utility first appeared in
 .An Devin Teske Aq dteske@FreeBSD.org
 .Sh THANKS TO
 Brandon Gooch, Garrett Cooper, Julian Elischer, Pawel Jakub Dawidek,
-Cyrille Lefevre, Ross West, Stefan Esser, Marco Steinbach, and Jilles Tjoelker
-for suggestions and help.
+Cyrille Lefevre, Ross West, Stefan Esser, Marco Steinbach, Jilles Tjoelker,
+Allan Jude, and Lars Engels for suggestions, help, and testing.



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201503231925.t2NJPZ4X053505>