Alias not working

Hi,

I'm on Solaris (SunOS wsp2cm01 5.10 Generic_150400-10 sun4v sparc SUNW,Sun-Fire-T200). Trying to set up an alias like below -

alias grep="/usr/xpg4/bin/grep"

but when I call grep in my command it ignores my alias & uses /usr/bin/grep instead. The problem with /usr/bin/grep is that it doesn't understand -q flag & that's how I know my command is still using /usr/bin/grep.
e.g. -

echo "hi" | grep -q "hi" && echo "YES"
grep: illegal option -- q
Usage: grep -hblcnsviw pattern file . . 

I tried "type grep" which returns me -

$ type grep
grep is an alias for /usr/xpg4/bin/grep

so I know I'm good there but not sure why it's still ignoring the alias while executing the command.

Any help appreciated.

Why use alias?
Why not point to the absolute path in the first place?

echo "hi" | /usr/xpg4/bin/grep -q "hi" && echo "YES"

OSX 10.7.5, default bash terminal.
Or perhaps, if you are using bash, use variables:-

Last login: Thu Sep 25 19:27:25 on ttys000
AMIGA:barrywalker~> x="/bin/echo"
AMIGA:barrywalker~> y="hexdump -C"
AMIGA:barrywalker~> $x "Bazza..." | $y 
00000000  42 61 7a 7a 61 2e 2e 2e  0a                       |Bazza....|
00000009
AMIGA:barrywalker~> _

The script I'm building is generic is supposed to be used on many platforms e.g. HP, AIX, SOLARIS. For the first two I still need to refer /usr/bin/grep but for SOLARIS I'm setting up aliases like below.

if [ "$(uname)" = "SunOS" ]; then
    [ -x "/usr/xpg4/bin/grep" ] && alias grep="/usr/xpg4/bin/grep"
    [ -x "/usr/xpg4/bin/egrep" ] && alias egrep="/usr/xpg4/bin/egrep"
    [ -x "/usr/bin/nawk" ] && alias awk="/usr/bin/nawk"
    [ -x "/usr/ucb/ps" ] && alias ps="/usr/ucb/ps"
fi

wisecracker, I could also define a variable say GREP to point to corresponding binary e.g. /usr/bin/grep or /usr/xpg4/bin/grep (depending upon the system) but then I'll have to use ${GREP} everywhere in my code. I know that's my last option if nothing works, but I was wondering if there's something very trivial I'm missing to be able to use alias instead.

Just an idea, again assuming bash...
How about 'source'(ing) your script:-

. /path/to/script.sh

OR

source /path/to/script.sh

---------- Post updated at 08:01 PM ---------- Previous update was at 07:46 PM ----------

OSX 10.7.5, default bash terminal:-

#!/bin/bash
# src.sh
alias echo="/bin/echo"
alias printf="/usr/bin/printf"
alias
echo -e "\x1B[1m Bazza..."
printf "\x1B[0m Walker...\n"

Results:-

Last login: Thu Sep 25 19:56:47 on ttys000
AMIGA:barrywalker~> chmod 755 src.sh
AMIGA:barrywalker~> ./src.sh
alias echo='/bin/echo'
alias printf='/usr/bin/printf'
 Bazza...
 Walker...
AMIGA:barrywalker~> # WRONG!!!
AMIGA:barrywalker~> . ./src.sh
alias echo='/bin/echo'
alias printf='/usr/bin/printf'
-e \x1B[1m Bazza...
x1B[0m Walker...
AMIGA:barrywalker~> # CORRECT!!!

Aliases set in a shell affect the current shell and any subshell execution environments started by that shell; they are not exported to other shell execution environments (such as when you invoke another shell script).

Most shells have several startup files that are invoked under various conditions (such as when you login, when you start a new interactive shell, when you start a new non-interactive shell, etc. but these vary from shell to shell). If you place your alias in the appropriate initialization file for your shell, you may be able to set up aliases that affect all scripts you start that use that shell.

Another possibility is to add symbolic links in your $HOME/bin directory (assuming that $HOME/bin appears in your PATH environment variable before /bin and /usr/bin . And, if you would just put /usr/xpg4/bin in your PATH before /bin and /usr/bin that would get rid of the need for awk , egrep , grep , (and fgrep ) aliases. Are there other utilities in /usr/xpg4/bin that would cause you problems if you used them instead of the utilities of the same name in /usr/bin ?

But, if you are writing shell scripts that other users will be invoking, that shell script needs to set up its own environment and not depend on the user calling it to set up a specific (possibly different) environment for each command they execute.

Yes Don, there are other utilities in there (/usr/xpg4/bin) which are causing problem so I can't just set the PATH to prioritize this path.

Also, I don't have permissions to change any of the startup files e.g. .profile, .kshrc etc. Whatever required changes are there have to be done in this script.

Also, wisecracker, sorry can't source the script. I tried it didn't seem to work for me.

Use envvals instead of aliases:

if [ "$(uname)" = "SunOS" ]; then
     [ -x "/usr/xpg4/bin/grep" ] && GREP="/usr/xpg4/bin/grep"
     [ -x "/usr/xpg4/bin/egrep" ] && EGREP="/usr/xpg4/bin/egrep"
     [ -x "/usr/bin/nawk" ] && NAWK="/usr/bin/nawk"
     [ -x "/usr/ucb/ps" ] && PS="/usr/ucb/ps" 
fi

${GREP} [grep args]

You could go absolutely global if that is a requirement...
OSX 10.7.5, default bash terminal:-

#/bin/bash
# gsrc.sh
printf "/bin/echo" > /tmp/ECHO
printf "/usr/bin/printf" > /tmp/PRINTF
ECHO=`< /tmp/ECHO`
PRINTF=`< /tmp/PRINTF`
$ECHO -e "\t\tBazza...\n"
$PRINTF "\x1B[0m Walker...\n"

Results:-

Last login: Thu Sep 25 22:20:12 on ttys000
AMIGA:barrywalker~> chmod 755 gsrc.sh
AMIGA:barrywalker~> ./gsrc.sh
-e \t\tBazza...\n
x1B[0m Walker...
AMIGA:barrywalker~> printme=`< /tmp/ECHO`
AMIGA:barrywalker~> text="My name is Baz..."
AMIGA:barrywalker~> $printme "$text"
My name is Baz...
AMIGA:barrywalker~> _

HTH, good night all.

Aliases in a script?

Aliases don't work in scripts, just interactive shell sessions. Try a variable.

# defaults to 'grep' unless GREP variable is set
${GREP-grep} -q ...

Huh?

If I have a script ( tester ) containing:

#!/bin/ksh
alias myecho=echo
myecho $0

and make it executable using:

chmod +x tester

and execute it using:

./tester

it prints:

./tester

Aliases should work just fine in a shell script as long as the aliases being used are defined in that shell script.

The problem the OP was seeing is that aliases aren't (and, for obvious security reasons, should not be) exported.

I STRONGLY suggest that you NEVER do this!

If this convention were used by more than one script or if this script is run twice, they could wipe each other out if they ran at close to the same time. (There is a minuscule time period between when the shell wipes out the data in a file due to the redirection and the time when the printf command fills it with the name of the desired executable.) On a single processor system, this might not happen often, but on a multi-processor system, it will eventually bite you right where it hurts the most. And if there are any miscreants on your system that notice these files in /tmp , it is easy for them to replace the utilities you thought you had specified with other utilities of their choosing.

I agree the race condition risk however, it isn't easy or even possible for regular users to replace the utilities already created in /tmp. What they might do is anticipate and create hostile alternatives before the gsrc.sh script is ever executed.

That depends on what system you're using. Some systems create a per user /tmp directory (although that is not allowed by the standards); others have a single /tmp directory shared by everyone on the system. Some system administrators set up /tmp such that anyone can remove any file in that directory and create a new file with that name anytime they want; others set the permissions on that directory so that only the owner of the file or someone running "with appropriate privileges" can remove a file. The umask setting at the time the file was created will determine who can read and write that file (if they don't have permission to just remove and replace it).

On many systems, if I create /tmp/ECHO as user dwc and set the mode to 0600 and you try to run wisecracker's script that ignores any error when using printf to set the contents of that file, then the later attempt to execute

ECHO=`< /tmp/ECHO`

will fail with a permission denied error trying to read the file I created.

Utilities belong in "safe" places like /bin and $HOME/bin ; not in places like /tmp .

I would go with linkage in $HOME/bin or /opt/myapp/bin.

Also, check out your code, perhaps there is a way to make in run on every os using standard toolset, therefor avoiding linking, aliases and case / if clauses per OS.

If you can paste the code, folks here might be able to clear it up a bit so it works with standard tools.

For instance :

echo "hi" | grep -q "hi" && echo "YES"

Can be replaced with something like :

echo "hi" | grep "hi" > /dev/null && echo "YES"

Regards
Peasant.

The question being asked in the Solaris forum, /tmp standard permissions are protecting files created by someone to be altered by someone else, at least if the owner doesn't create world writable files (or if both users belong to the same group and the file is group writable).
"drwxrwxrwt" permissions for /tmp and /var/tmp is quite standard on Unix & Linux distributions nowadays.

And, as I said, on a Solaris systems with normal permissions on /tmp , if I run wisecracker's script creating /tmp/ECHO and /tmp/PRINTF with my default umask and then you run wisecracker's script:

  • your attempts to create /tmp/ECHO and /tmp/PRINTF will fail, and
  • unless you're in the same group I'm in, you won't be able to read the /tmp/ECHO and /tmp/PRINTF that I created (which will either terminate your script with an error or set ECHO and PRINTF to empty strings; so
  • your attempts to run $ECHO or $PRINTF won't get you the echo or the printf utilities you wanted (although I don't know why you'd need to choose an alternative version of printf anyway). Instead they'd give your script syntax errors for trying to execute the unknown -e and \x1B[0m commands if your code didn't die on the failed printf and variable initialization commands.
  • And, of course, note that the -e option is not an option on Solaris /bin/echo either (it is a text operand to be printed).

What am I missing??? Why are you arguing that wisecracker's code provides a reasonable approach to solve the OP's problem? Given that any other user on the system can prevent you from creating an executable file in /tmp to be run by your script (just by running the same script with no malice intended), why do you think /tmp is an appropriate directory in which to install utilities (or files containing the paths of utilities) for use by any script that you want to run?

Why? If you know the location of the utility you want to run on the OS you're running on, just use it directly instead of dealing with the O&M of keeping copies of something that the OS provides.

Agreed. Avoid "proprietary" extensions - and GNUisms are no different than the extensions to standard protocols that Microsoft provides.

---------- Post updated at 10:10 AM ---------- Previous update was at 10:02 AM ----------

But that doesn't prevent someone from prepositioning malicious code in /tmp if they know you're going to run "/tmp/PRINTF".

I don't see the point of any complex workaround. Utilities behave differently on different flavors of Unix. You know what flavor you're running on, you know which utility you want run. The only way to deal with it is - get this - deal with it.

Deal with it directly and in ONE place - the script you're writing. Put in if/else or case statements for each OS flavor you support. Add comments to explain WHY you're using each utility from that location, because a few months or years from now, you won't remember. If you have a set of scripts, all of them can source ONE common script to set envvals for utilities.

Don't copy OS-provided binaries to custom locations - who's going to maintain that when the OS is updated?

Keep it simple - and in ONE place - or you won't be able to keep it working.

GNU is free, accurately documents which flags are extensions and which aren't, and does a good and pretty complete job of implementing standard features, so it's quite different from that sprawling monopoly. Some GNU extensions are just closing gaping holes which most UNIX suffers badly from -- like date math!

The real problem is that other UNIX cannot use these ideas to improve itself due to copyleft, so these improved features will never be anything but GNU :frowning: Their hope, of course, was to entice people to switch to GNU by offering these feature improvements. In that way you could say they are similar I suppose, but I still see a difference between forcing someone into perpetual incompatibility and offering someone features they need. Oh well.

But this is besides the point... grep -q is POSIX. Maybe newer POSIX than some systems offer by default, but POSIX.

The grep -q option has been in POSIX since the first POSIX Shell and Utilities standard was adopted by IEEE in 1992. Any system with utilities conforming to any version of the Shell and Utilities volume of the POSIX standards for the last 22 years is required to support the -q option.

1 Like

Not at all. Wisecracker's suggestion has several flaws and is obviously using a broken approach in the first place.
I was just commenting on your second statement "it is easy for them to replace the utilities you thought you had specified with other utilities of their choosing." In the general case, it is hopefully not easy or even possible for other users to modify or replace files you have previously created in /tmp. Many utilities and applications routinely create and use files in /tmp with no particular security risks. As I wrote and you later mentioned too, it is however possible to anticipate and create files with the same name in the first place but this is a case that can be easily detected by a robust script.

I believe it is not necessarily inappropriate. There are a couple of advantages to use /tmp (or better /var/tmp if persistance is required) to store files and commands. As a matter of fact, I have been doing this on hundreds of machines for several decades without any major issue (outside the scripts being removed by erroneous cleaning procedures). Of course, some measures should be taken to avoid the race condition and other risks but if done properly, there are no fundamental issues.

---------- Post updated at 15:52 ---------- Previous update was at 13:29 ----------

I'm afraid this is incorrect. GNU which itself started by reimplementing commands and APIs found in proprietary Unix OSes doesn't forbid itself to reimplement GNUisms on non GPL code. What is forbidden by the GPL license is to reuse code, not ideas.
For example the -iname option has been added to the supported ones with the Solaris 11 standard find utility, same for the compression options like -z and -j with Solaris tar .

1 Like