NetBSD-Bugs archive

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

Re: bin/59836: 11.0_BETA: resolvconf fails with 'eval: make_vars: IP_OF_2ND_DNS: not found' for more than 1 dns server



The following reply was made to PR bin/59836; it has been noted by GNATS.

From: Robert Elz <kre%munnari.OZ.AU@localhost>
To: Henryk Paluch <hpaluch%seznam.cz@localhost>
Cc: gnats-bugs%netbsd.org@localhost
Subject: Re: bin/59836: 11.0_BETA: resolvconf fails with 'eval: make_vars: IP_OF_2ND_DNS: not found' for more than 1 dns server
Date: Wed, 17 Dec 2025 07:32:46 +0700

     Date:        Tue, 16 Dec 2025 07:01:32 +0100
     From:        Henryk Paluch <hpaluch%seznam.cz@localhost>
     Message-ID:  <37b539e1-f624-4b10-9a90-c55181758b3f%seznam.cz@localhost>
 
   | Still, it is bad security practice to pass variable(s) in format string.
 
 Variables that contain unknown data, yes, it is.
 
 But you still seem to be missing the point.  That is not what was
 happening here, the format string contained (contains) no variables
 at all.
 
 Consider this example
 
 	printf '$(cat /dev/tty)\n'
 
 What that writes out is (literally)
 
 	$(cat /dev/tty)
 
 (including a newline of course).   There is no command substitution, no
 commands run, no reference to any device, just a string of characters
 written to standard output.
 
 That the string happens to look like a command substitution (in this
 case) or a variable reference (in the resolvconf case) makes no
 difference to anything, it is just a string of characters.
 
 Once again, in sh, NOTHING inside a single quoted string is interpreted
 by the shell in any way at all.   That includes dollar signs, double quotes,
 backslashes, grave accents (backticks), braces, ... the only character the
 shell looks for in a single quoted string is the next single quote, which
 ends the thing.   And that is what the format string given used, just like
 the example above.
 
 The format string for printf should usually (when it needs any quoting)
 be quoted using single quotes -- except in the very rare case when var
 references ae actually needed there - which, if you want to be portable,
 can be needed if, for example, the script wants to calculate field
 widths, you might have a loop calculating the width needed something
 like:
 
 	W=0
 	for X
 	do
 		if [ "${#X}" -gt "$W" ]
 		then
 			W=${#X}
 		fi
 	done
 	W=$(( W + 1 ))		# One more than the longest
 
 	for X
 	do
 		printf "%-${W}s [other stuff]\n" "$X"  [other args]
 	done
 
 In our printf (and many others) you might instead do
 
 		printf '%-*s [other stuff]\n' "$W" "$X" [other args]
 
 but support for '*' as the field width (or precision), isn't required
 by POSIX, precisely because the version with the embedded $W reference
 is possible (and perfectly safe - we know what kind of data must be in $W,
 it has to be a number, and nothing else.)
 
 
 
   | # TODO: properly quote $NAMESERVER content to avoid '"' escape in eval, 
   | etc.:
   | printf 'NAMESERVERS="%s" %s\n' "$(some_quote $NAMESERVERS)" "$(quote "$ns")"
 
 No it wouldn't, that's using the value of $NAMESERVERS (and quoting it
 however the fictional some_quote function does it, which is irrelevant
 here) which the original does not do.  It didn't, even in its earlier
 incarnations.   The *only* variable expansion is of $ns.  The one in
 resolvconf writes the characters dollar, N, A, M, E, S, E, ... where
 you think it is writing the value of a variable.   I thought that was
 clear from my previous reply.
 
   | Or using echo which is immune to such things
 
 echo is close to useless in portable programs.  There are versions
 of it which treat \ in the string (anywhere, the only way to prevent it
 is to use \\, and if we're assuming user data, we cannot assume that)
 to cause strange variations, and since this output is to be interpreted
 by a shell later, as commands (I presume), allowing a \n to get in there
 possibly followed by "rm -fr / &" and another newline after that, would
 be nasty indeed.   echo is never better than printf (just sometimes it
 is quicker to type,  echo is a shorter word than printf, and doesn't need
 a format string arg, so lazy script writers tend to use it (and of
 course it was around for many years before printf was, but by comparison
 with how long printf has been available now, that's almost irrelevant.)
 
 Original Bell labs echo doesn't do that, and BSD echo doesn't do that,
 but Sys V (and POSIX) versions of echo do - even though these days POSIX
 says that if the string starts with a '-' or contains a \ then the
 results are unspecified (which is no help to us, or anyone, at all.)
 
   | Additionally running whole output of make_vars using eval as root is 
   | security nightmare on its own - because if any part of make_vars output 
   | does not properly sanitize all content it may lead to root execution 
   | exploit in future.
 
 This one I can't comment on, as I have no idea what the relevance is
 to the issue, nor what might be doing something like that, nor why.
 
 kre
 


Home | Main Index | Thread Index | Old Index