Showing posts with label permissions. Show all posts
Showing posts with label permissions. Show all posts

Thursday, June 11, 2009

Dealing With "Permissions on the password database may be too restrictive" Errors On SUSE Linux 10.x

Hey there,

Here's something I ran into for the first time in my life today (and I don't mean the longest frickin' subject line I've ever written ;)

I was working with a colleague, booting up a recently panicked (I'm assuming, since I wasn't involved when "the incident" happened) SUSE Linux 10 system, when we saw the following error:

Login Failed: Permissions on the password database may be too restrictive.

Or something to that effect. Unfortunately, I don't have the screen to cut-and-paste from (not complaining). We ended up getting this error for regular users and administrative users, including root. It seemed like there wasn't an account available that could log in to the box. Eventually the problem was solved, but it was an interesting situation and, perhaps, some of the following troubleshooting information might be of help to you in the future (So you don't have to boot "rescue" off of CD more than once ;)

Here's how it went down (try to contain your excitement. This is edge-of-your-seat stuff, so, please, go to the bathroom before you continue reading ;)

1. The first thing we did was to try logging in with all the accounts we could think of. None of them worked, although we were relatively sure that they were enabled and had worked previously.

2. Then we did the sanity-check that (interestingly) you don't see too many people do any more: We quit trying to login to the default run level (5 - X-Windows) and tried the same logins we did in step 1 on the machine's local console. At this point, we considered that we may have hit some limit on failed login attempts, but quickly discounted that theory, since our logins had been failing from the start. It's also worth mentioning that this was a newer machine and (as it turned out) had not been attacked in any way that might disable passwords from being accepted.

3. Next, we booted off of CD and ran SUSE Linux in "rescue" mode. This gave us a very easy login. Username: root. No password required. Using "lvscan" we were able to to identify the root partition and ran fsck on all available partitions to ensure that no file system corruption existed.

4. Once all the fsck's came back "OK," we mounted /dev/system/root onto a temporary directory (/tmp/root for instance):

host # mkdir /tmp/root
host # mount /dev/system/root /tmp/root


5. Then we changed directories into what would normally be our /etc directory to look for any obvious signs of damage. None could be found. In fact, it seemed as though the error we were getting was completely erroneous:

host # cd /tmp/root/etc
host # ls -l passwd shadow
-rw-r--r-- 1 root root 25729 Jun 10 05:52 passwd
-r-------- 1 root root 14268 Jun 10 05:51 shadow


Those permissions may seem restrictive, but they're actually required so that users' passwords can remain secure. /etc/passwd should be readable by anyone, but the "passwd" program actually runs "setuid root" so that it can verify the user's password by reading the /etc/shadow file:

-rwsr-xr-x 1 root root 27768 Jul 17 2006 /usr/bin/passwd

6. We added our own user id's to the "wheel" group (root was already a member) and rebooted, to see if that would help, but it didn't. That was lame, I know, but much better than finding out later that it was actually the solution and we never tried it ;)

7. Booting up in rescue mode and mounting the root partition again, we took a look at the /tmp/root/etc/sysconfig/permissions file (We couldn't use Yast's X-Window interface, as explained below). It turns out that the line:

PERMISSION_SECURITY=

was set to paranoid for local security!!!! This was easily fixable by changing it back to the least restrictive of settings (you have easy, secure and paranoid to pick from, I believe):

PERMISSION_SECURITY="easy local"

saved that file and rebooted. All was well :)

The Aftermath:

One interesting thing I noted, when taking a look at the problem afterward, was that "paranoid" local settings were actually set on purpose by another admin (the default for our install image was what we reverted back to - "easy local").

This setting seems like a good idea, because, from the documentation I could find, it purports to make it so that the administrator gets to choose which users can run X sessions and "setuid" programs, although (obviously) it should never be set up and not completely finished and tested before leaving it go ;)

One of the major issues is that, if no one is specifically allowed to run X sessions and/or use setuid programs after this setting is enforced and the machine is rebooted, root is included in the accounts that are denied access to these programs.

The X denial is okay. I can live with that. But not allowing root (and every other account) to use setuid programs makes it impossible for anyone to login. The reason for this is actually pretty simple. When login asks for your password, in simplistic terms, it employs "passwd" (a "setuid" program, as shown above) to read your user entry from /etc/shadow and confirm that your password is actually correct. Since no one is allowed to use "setuid" programs, no one (including root) can login (Via X, remotely or even directly on the local console).

Crazy, but fun for a while ;) Hopefully this helps someone out there :)

Cheers,

, Mike


Banner for College Student-Oriented Sites (728 version 1)



Please note that this blog accepts comments via email only. See our Mission And Policy Statement for further details.

Saturday, June 21, 2008

Security Basics For Linux and Unix Installations - Part 2

Hey there,

Following up on our first two posts on basic Linux and Unix installation security and even more installation security measures, we're going to move on to the next section. Today, we'll be focusing more specifically on user, and group, accounts, and modifications that we want to make in that arena.

Again, this series of posts is based mostly on Solaris Unix and RedHat Linux, so it can't possibly apply to everything. I welcome any comments regarding it, especially as they pertain to additional security and other Operating Systems. Just to be clear, also, we won't be touching on more advanced stuff like setting up firewalls, etc. The summary of this 5-part post should end up being a bullet list that you can run through and take care of without having to go too crazy ;)

And, of course, my suggestion, to everyone who has the rights and means, is to script out as much of this method as possible. However you end up securifying your system, once you have your routine down, having Jumpstart or Kickstart do it for you from then on out is much less of a hassle (usually :)

See you tomorrow for section 3!

Cheers,

OS Installation Guidelines, Part 2: Users and Accounts

1. Add accounts for all necessary users. Require valid reasons for all accounts created.

2. You can ignore this step if you're using Solaris or RedHat's OpenSSH pkg or rpm, since it will be complete already: Be sure to add a user account for sshd. This will be required for our OpenSSH to run correctly. Should be as simple as

host # useradd –m –d /users/sshd sshd
host # passwd –l sshd
<--- (The passwd –l just locks the password so no one can login to the account. This is okay, since the sshd account is only necessary for privilege separation.

IMPORTANT NOTE FOR POINTS 3 THROUGH 6 REGARDING USER REMOVAL: Please note that for point three, we specify "userdel -r," because these users have home directories that are NOT "/" - If there is any doubt in your mind that an account you want to remove has the root filesystem as its home directory, use "userdel" without the -r, as use of that flag may effectively destroy your system. An easy way to find out what a user's home directory is involves simply grepping the username out of /etc/passwd and checking out the second to last field.

3. userdel –r lp, uucp, nuucp, some, all or more if possible (the nobody account should be removed, too, unless it’s used by a web server or some other application). Note that your list will be larger on RedHat since they generally have a user for every service and you should remove every user for every service you're not using if it wasn't removed by rpm -e. Also, on Redhat, be sure to check for matching entries for the user in /etc/group

4. userdel nobody (This should not be removed if it’s used by a web server or some other application)

5. userdel smtp (Non-existent in Solaris9).

6. userdel mail (Non-existent in Solaris9).

7. chmod 700 all user directories.

8. Comment out gsscred and nfsfind from root cron on Solaris. Delete sys, lp, adm, root.au, uucp and all unnecessary crontabs, if possible.

9. Add “0,5,10,15,20,25,30,35,40,45,50,55 * * * * /usr/lib/sa/sa1” and “59 23 * * * /usr/lib/sa/sa2 -b -g -r –u” to root's cron. On RedHat you'll need to have the sysstat RPM installed in order to use sar. If it "is" installed on Redhat, check out /etc/cron.d to make sure that it is being run in cron and modify the setup per above, to increase or decrease the number of times it runs, if you need to.

10. Create the directory /var/adm/sa (/var/log/sa on RedHat) if it doesn't exist, and chown it to root:yourAdministratorsGroup. Then chmod the directory to 660.

11. Add “/usr/lib/acct/ckpacct” to root's cron on Solaris, if the machine does not have high user activity and has adequate disk space for logging. Remove any other /usr/lib/acct lines in the Solaris root crontab. For RedHat users, make sure that you have the psacct RPM installed. The default settings should be okay and you can use chkconfig or ntsysv to ensure that process accounting is set to run at boot time.

12. Remove user directories for users who no longer have accounts on the machine.

13. Remove crontab entries in /usr/spool/cron/crontabs (Solaris) or /var/spool/cron (RedHat) for users that no longer have accounts on the machine.

14. Add empty .rhosts, .netrc and .exrc files in all user home directories.

15. chmod 0 and chown root all user .rhosts, .netrc and .exrc files.

16. userdel (–r, if their home directory isn’t "/" ) all users, aside from root, with uid 0.

17. Change the group for any user (other than root) that has a gid of 0, if possible.

18. Be sure to include a umask of 022 in any user’s .profile if their account will require their home directory to be somewhat publicly available. Examples of such an accounts include development or group-based accounts. These kind of accounts are used to ease the ability of a group to work together. Of course, the standard 027 umask would make this impossible. Please use discretion and do this only for accounts where the need is real.

19. For all generic accounts, make them su-only. You can find detailed instructions on how to do this, including some pitfalls and stumbling blocks you may encounter, in our post on making generic accounts su only. As luck would have it, it's still aptly named ;)

to be continued...

, Mike

Monday, March 17, 2008

Perl Directory Permissions Difference Script For Directories

Howdy,

Today's Perl script is a slight variation on the "diff -r" command (actually the diff command with -r option) for both Linux and Unix. "diff -r" recursively checks directories to report on the differences, much in the same way diff (without arguments) might compare two files. This is a great command if you need to manage separate directory trunks or the find the difference in them. For an example, consider two directories we've created, each with a few files in it, and the output that "diff -r" produces:

host # diff -r scripts1 scripts2
host #


No output means both directories are identical.

There do exist situations, however, for which "diff -r" falls a bit short. The pdiff Perl script presented today works more like "diff -rs" (the -s option let's you view two files, or directories, side by side). Using our previous example, we'd get this output instead:

host # diff -rs scripts1 scripts2
Files scripts1/script1 and scripts2/script1 are identical
Files scripts1/script1.bak and scripts2/script1.bak are identical
Files scripts1/script2 and scripts2/script2 are identical
Files scripts1/script2.bak and scripts2/script2.bak are identical
Files scripts1/script3 and scripts2/script3 are identical
Files scripts1/script3.bak and scripts2/script3.bak are identical


A little bit better, since it will at least tell you that the directories are identical ;)

However, diff doesn't take directory permissions, or user/group ownership, into consideration, which is why I wrote this script. If we run pdiff against those same 2 directories, we get this output:

./pdiff scripts1 scripts2
0644 script1---eggi newpeople 0755 script1---eggi newpeople
0644 script1.bak---eggi newpeople 0755 script1.bak---eggi newpeople
0644 script2---eggi newpeople 0755 script2---eggi newpeople
0644 script2.bak---eggi newpeople 0755 script2.bak---eggi newpeople
0644 script3---eggi newpeople 0755 script3---eggi newpeople
0644 script3.bak---eggi newpeople 0755 script3.bak---eggi newpeople


Notice the difference? ;)

Hope you find good use for this script, and enjoy!

Cheers,


Creative Commons License


This work is licensed under a
Creative Commons Attribution-Noncommercial-Share Alike 3.0 United States License

#!/usr/bin/perl

#
# pdiff - diff directories with
# user/group and permissions checked
#
# 2008 - Mike Golvach - eggi@comcast.net
#
# Creative Commons Attribution-Noncommercial-Share Alike 3.0 United States License
#

if ($#ARGV != 1) {
print "Usage: $0 dir1 dir2\n";
exit;
}

$firstdir=$ARGV[0];
$seconddir=$ARGV[1];

@firstfiles=`ls -l $firstdir|grep -v total`;
@secondfiles=`ls -l $seconddir|grep -v total`;
@file1 = ();
@file2 = ();

foreach $firstbit (@firstfiles) {
@firstparts = split(/ * */, $firstbit);
@perms = split(//, $firstparts[0]);
chomp(@perms);
@user = ($perms[1], $perms[2], $perms[3]);
@group = ($perms[4], $perms[5], $perms[6]);
@other = ($perms[7], $perms[8], $perms[9]);
$ucounter = 0;
$gcounter = 0;
$ocounter = 0;
$majordiff = 0;
foreach $perm (@user) {
if ($perm eq "r") {
$ucounter += 4;
} elsif ($perm eq "w") {
$ucounter += 2;
} elsif ($perm eq "x") {
$ucounter += 1;
} elsif ($perm eq "s") {
$ucounter += 1;
$majordiff += 4;
}
}
foreach $perm (@group) {
if ($perm eq "r") {
$gcounter += 4;
} elsif ($perm eq "w") {
$gcounter += 2;
} elsif ($perm eq "x") {
$gcounter += 1;
} elsif ($perm eq "s") {
$gcounter += 1;
$majordiff += 2;
}
}
foreach $perm (@other) {
if ($perm eq "r") {
$ocounter += 4;
} elsif ($perm eq "w") {
$ocounter += 2;
} elsif ($perm eq "x") {
$ocounter += 1;
} elsif ($perm eq "t") {
$ocounter += 1;
$majordiff += 1;
}
}
@permissions = ($majordiff, $ucounter, $gcounter, $ocounter);
$permissions = join("", @permissions);
# print "$permissions $firstparts[8]";
chomp($firstparts[8]);
push(@file1, "$permissions $firstparts[8]---$firstparts[2] $firstparts[3]");
}
foreach $firstbit (@secondfiles) {
@firstparts = split(/ * */, $firstbit);
@perms = split(//, $firstparts[0]);
chomp(@perms);
@user = ($perms[1], $perms[2], $perms[3]);
@group = ($perms[4], $perms[5], $perms[6]);
@other = ($perms[7], $perms[8], $perms[9]);
$ucounter = 0;
$gcounter = 0;
$ocounter = 0;
$majordiff = 0;
foreach $perm (@user) {
if ($perm eq "r") {
$ucounter += 4;
} elsif ($perm eq "w") {
$ucounter += 2;
} elsif ($perm eq "x") {
$ucounter += 1;
} elsif ($perm eq "s") {
$ucounter += 1;
$majordiff += 4;
}
}
foreach $perm (@group) {
if ($perm eq "r") {
$gcounter += 4;
} elsif ($perm eq "w") {
$gcounter += 2;
} elsif ($perm eq "x") {
$gcounter += 1;
} elsif ($perm eq "s") {
$gcounter += 1;
$majordiff += 2;
}
}
foreach $perm (@other) {
if ($perm eq "r") {
$ocounter += 4;
} elsif ($perm eq "w") {
$ocounter += 2;
} elsif ($perm eq "x") {
$ocounter += 1;
} elsif ($perm eq "t") {
$ocounter += 1;
$majordiff += 1;
}
}
@permissions = ($majordiff, $ucounter, $gcounter, $ocounter);
$permissions = join("", @permissions);
# print "$permissions $firstparts[8]";
chomp($firstparts[8]);
push(@file2, "$permissions $firstparts[8]---$firstparts[2] $firstparts[3]");
}

$file1count = @file1;
$file2count = @file2;

if ( $file1count > $file2count ) {
$filecount = $file1count;
} else {
$filecount = $file2count;
}

$indexer = 0;
while ( $indexer < $filecount ) {
chomp($file1[$indexer]);
chomp($file2[$indexer]);
printf("%-40s%s\n", $file1[$indexer],$file2[$indexer]);
$indexer++;
}


, Mike




Wednesday, December 5, 2007

Converting Alpha Permissions To Octal

Today, I thought I'd put together a little script (written in ksh, but easily portable to sh or Perl) to address a common concern amongst users of most Unix/Linux-based systems; how to translate alpha permissions (like -rwxrwxr-x) to octal (like 775). This issue has been addressed, to some degree by all flavors of *nix, in that you can use the chmod command either way. For instance, if you had a file with 775 (or -rwxrwxr-x) permissions, you could add "other" (or "world") write permissions to the file by doing:

chmod 777 FILENAME or chmod o+w FILENAME

Both ways are equally effective and, you might even say that their are some advantages to using one over the other. For instance, with octal permissions, to add "group" write permissions to a 755 file, you would have to remember to retain the original modes when executing chmod. If you just did:

chmod 070

It would cause serious issues (755 becomes 070)! It's much easier to remember:

chmod g+w

Which would add the write permissions for "group" ownership and not affect the other bits (755 becomes 775)!

One example of a situation where you absolutely "must" use alpha notation with chmod is an old bug in Solaris (that exists even today, in Solaris 10 - latest patch release), whereby you "cannot" set the "group ID" bit (more commonly referred to as setgid) on a directory with octal notation. For instance:

xyx.com[/export/home/user] # chmod 2755 bob
xyz.com[/export/home/user] # ls -ld bob
drwxr-xr-x 2 root other 512 Dec 3 16:34 bob
<--- No Good.

xyz.com[/export/home/user] # chmod g+s bob
xyz.com[/export/home/user] # ls -ld bob
drwxr-sr-x 2 root other 512 Dec 3 16:34 bob
<--- Now it's working :)

The only other thing left to explain before we get to the script (assuming you're still reading this and haven't just blown to the bottom already ;) is the common misconception that there are only 3 octal numerics in a file's (or anything's) permissions. This may not be news to most folks, but there are actually 4 octals. The last 3 are the ones that are usually represented; as in 755. The fourth, which is actually the first, is usually an implied 0. For example, 755 is the same as 0755. The first (usually omitted) bit has a potential of 4 different values (0, 1, 2 and 4 or any combination thereof), just like the rest of them do, although they take on a unique significance.

For the last 3 bits (user, group and other permissions) the translation is the same. They can have values of 0-7 for each. 000 would equal ---------, while 777 would equal rwxrwxrwx The permissions are compounded by adding the value of the bits. So 0 results in a "---", 1 results in "--x", 2 results in "-w-" and 4 results in "r--". Compounding them is just a matter of addition. So if the value of the user bit was 6, you could only acheive that result (from your selection of 0, 1, 2 and 4) by adding 4 and 2. By merging the above descriptions, 6 would have a value of "rw-" (4 "r--" plus 2 "-w-").

The first (usually hidden) bit is reserved for activating the setuid bit (value of 4), setgid bit (value of 2) and sticky bit (value of 1). As always, 0 equals nothing. These bits are special because, although they'll appear as numerals in your 4 bit octal notation, they appear in different places when using alpha notation. The setuid bit (Value of 4) shows up in the "user" permissions as an "s" where the "x" would normally be (like rws instead of rwx). The same is true of the setgid bit (Value of 2), although it shows up in the "group" permissions. The sticky bit (Value of 1) shows up in the "other" permissions as a "t" (like rwt instead of rwx). In a future post, we'll explore how the bit permissions "actually" modify the files and/or directories they are applied to (This differs for all 4 bits, and is another post in itself).

Below is the initial script to convert all of the alpha permissions you'd see (using "ls -l") on any file(s), to their corresponding octal notation. This can more easily be applied in reverse (which is probably why I wrote it this way first). Note that this was also created using what I call "brute force scripting"; the fastest means to an acceptable end. Feel free to doll it up and make it work better for you. As it is, it will accept any option that the standard "ls" would. So, if you called it "lso," you could execute "./lso /export/home/user" or "./lso -R /export/home/user" or just plain "./lso" -- I'll be using this script (since it has a number of different scripting constructs in it) to demonstrate how to port shell scripts to Perl in a future post, also.

Best wishes :)


Creative Commons License


This work is licensed under a
Creative Commons Attribution-Noncommercial-Share Alike 3.0 United States License

#!/bin/ksh

#
# 2007 - Mike Golvach - eggi@comcast.net
#
# Creative Commons Attribution-Noncommercial-Share Alike 3.0 United States License
#

arg=$@

ls -l $arg|awk '{ if ($0 !~ /^$/) print $1 " " $NF}'|grep -v "^total"|while read perms filename
do
if [ $filename = $perms ]
then
print "$filename = Directory"
continue
fi
bit_counter=10
oct_counter=0
user_bits=0
group_bits=0
other_bits=0
s_bits=0
set -A oct_array
oct_split=`print -- $perms|sed 's/\([-bcdDlprstwx]\)/\1 /g'`
for x in `print -- $oct_split`
do
oct_array[$oct_counter]=$x
let oct_counter=$oct_counter+1
done
while [ $bit_counter -gt 0 ]
do
case $bit_counter in
'9' ) if [ "${oct_array[$bit_counter]}" = "x" ]
then
let other_bits=$other_bits+1
elif [ "${oct_array[$bit_counter]}" = "t" ]
then
let s_bits=$s_bits+1
let other_bits=$other_bits+1
fi
let bit_counter=$bit_counter-1;;
'8' ) if [ "${oct_array[$bit_counter]}" = "w" ]
then
let other_bits=$other_bits+2
fi
let bit_counter=$bit_counter-1;;
'7' ) if [ "${oct_array[$bit_counter]}" = "r" ]
then
let other_bits=$other_bits+4
fi
let bit_counter=$bit_counter-1;;
'6' ) if [ "${oct_array[$bit_counter]}" = "x" ]
then
let group_bits=$group_bits+1
elif [ "${oct_array[$bit_counter]}" = "s" ]
then
let s_bits=$s_bits+2
let group_bits=$group_bits+1
fi
let bit_counter=$bit_counter-1;;
'5' ) if [ "${oct_array[$bit_counter]}" = "w" ]
then
let group_bits=$group_bits+2
fi
let bit_counter=$bit_counter-1;;
'4' ) if [ "${oct_array[$bit_counter]}" = "r" ]
then
let group_bits=$group_bits+4
fi
let bit_counter=$bit_counter-1;;
'3' ) if [ "${oct_array[$bit_counter]}" = "x" ]
then
let user_bits=$user_bits+1
elif [ "${oct_array[$bit_counter]}" = "s" ]
then
let s_bits=$s_bits+4
let user_bits=$user_bits+1
fi
let bit_counter=$bit_counter-1;;
'2' ) if [ "${oct_array[$bit_counter]}" = "w" ]
then
let user_bits=$user_bits+2
fi
let bit_counter=$bit_counter-1;;
'1' ) if [ "${oct_array[$bit_counter]}" = "r" ]
then
let user_bits=$user_bits+4
fi
let bit_counter=$bit_counter-1;;
0 ) let bit_counter=$bit_counter-1;;
* ) let bit_counter=$bit_counter-1;;
esac
done
octal=${s_bits}${user_bits}${group_bits}${other_bits}
print -- "$octal $filename"
done


, Mike





Saturday, December 1, 2007

Old Style ps On Solaris 10

A lot of admin's may have heard this complaint already, but I'm just starting to hear it now from users who are upset about the change in functionality of the /usr/ucb/ps command (as opposed to the standard /bin/ps command).

Up to Solaris version 9, "/usr/ucb/ps -aguxwwwww" would give you extremely detailed ps output (like the entire 2 pages of output from a java command, for instance). Theoretically, in Solaris 10, it still does. Alas, in reality, it doesn't. Here's a link to the publicly available Sun Alert Notification that explains the issue in more detail.

The reason for this stems back to a vulnerability (feature ?) that was discovered in Solaris 8 and 9, regarding /usr/ucb/ps, whereby a user could use the program to view another user's environment settings/variables if they used the "-e" switch. Patches were released for both Solaris 8 and 9, and Solaris 10 was claimed to not be affected by it.

However, all the security patches for Solaris 8 and 9 really did was strip the setUID bit on /usr/ucb/ps and Solaris 10 was released with a /usr/ucb/ps binary that came with 0555 permissions standard (users could no longer get the extended output, but root still could). This would suggest that, perhaps, Solaris 10 wasn't ever really "immune" to the vulnerability, but, more simply, came with the work-around set as the standard. A quick test shows that this is, indeed, the case. Check out the following on a simple /usr/ucb/ps test against the cron process. Note that this is run on a Solaris 10 box, with very recent patch-levels, and I've changed the permissions of /usr/ucb/ps from 0555 to 4555:

host.xyz.com # uname -r
5.10
host.xyz.com # /bin/ps -ef|grep "[2]35"
root 235 1 0 Sep 12 ? 0:07 /usr/sbin/cron
host.xyz.com # /usr/ucb/ps -eaguxwwww|grep "[2]35"
root 235 0.0 0.0 2840 1864 ? S Sep 12 0:06 /usr/sbin/cron LC_COLLATE=en_US.ISO8859-1 LC_CTYPE=en_US.ISO8859-1 LC_MESSAGES=C LC_MONETARY=en_US.ISO8859-1 LC_NUMERIC=en_US.ISO8859-1 LC_TIME=en_US.ISO8859-1 PATH=/usr/sbin:/usr/bin SMF_FMRI=svc:/system/cron:default SMF_METHOD=/lib/svc/method/svc-cron SMF_RESTARTER=svc:/system/svc/restarter:default TZ=US/Central


Looks like the problem hasn't actually been "solved."

So, there you have it; /usr/ucb/ps on Solaris 10 actually does still show regular users the environments of any user that calls a program. Of course, stripping the setUID bit makes that impossible again, but it also makes it impossible for regular users to get extended output for those long java command lines that they need to see.

There are several work-arounds for this work-around. For instance, you could try to use "pargs." It won't work without the setUID bit either, but at least it will tell you that it can't and not just shoot you truncated output with no explanation.

host.xyz.com > pargs -e 235
pargs: cannot examine 235: permission denied


Probably the best way to work-around this, and satisfy Sun's security requirements is to make use of a program called sudo (comes with Solaris 10). Just include a rule like the one below, so that users can only run "/usr/ucb/ps -aguxwwww" and can't run /usr/ucb/ps with any other command arguments, except straight-up with no arguments. They'll get the long output they need and will be prohibited from running /usr/ucb/ps with any other command line switches, like the terrible "-e." Example rule below:

ALL ALL = (root) /usr/ucb/ps -aguxwwww, /usr/ucb/ps ""

We'll go into more detail about sudo in a future post, in all probability. For now, here's a quick rundown on how this rule plays out:

ALL <--- All users can use this sudo rule
ALL <--- This command can be used on any host.
= <--- Pretty self explanatory ;)
(root) <--- These command will be run as the user root
/usr/ucb/pas -aguxwwww, /usr/ucb/ps "" <--- This is the list of allowed commands. The first command specifies that /usr/ucb/ps can only be run with the "-aguxwwww" switches. The second command (multiple commands separated by commas) specifies that the user can also run /usr/ucb/ps with no switches at all (The "" (double-double quotes) indicate that no switches are allowed after the command)

Now, everyone should be happy. You've kept the security flaw from being exploited, retained the /usr/ucb/ps permissions, satisfied the Sun Alert requirements and allowed users to be able to get their extended ouput.

If only every annoying problem were so easy solved ;)

, Mike