I have a simple bash shell script:
user_exists=cat /etc/passwd | grep 'GNU Mailman'
echo $user_exists
when I run this script with sudo ./'script_name', I get a permission denied error on the line where I attempt to access /etc/passwd. What am I doing wrong here?
To understand why, you have to look at the line the way that bash looks at the line:
user_exists=cat /etc/passwd | grep 'GNU Mailman'
According to bash, you are (temporarily) setting the environment variable user_exists to have the value cat. With that value set, then the program /etc/passwd is executed and its output sent to grep 'GNU Mailman'. Since /etc/passwd does not have execute permission, this command fails for lack of permission.
The solution is to use the proper format for process substitution as outlined by Vladimir Kolesnikov:
user_exist=$(grep 'GNU Mailman' /etc/passwd)
user_exists=$(cat /etc/passwd | grep 'GNU Mailman')
or better yet,
getent passwd username
Related
file name test.sh
echo $HOME
running in root privilege -> sudo test.sh
expected
/home/username/
but getting
/root
sudo runs the script as the root-user
To get the name of the user who initiated sudo you can call echo $SUDO_USER
To get its home directory:
getent passwd $SUDO_USER | cut -d: -f6
Surely the best way is simply:
echo ~username
For assignment, tilde must not be quoted:
username_home=~username
but may be combined with quoted strings, e.g.:
new_path=~username/"${another_variable}"
new_paths_array=(~username/"${yet_another}"/*)
There may be some subtle things to do with $HOME and ~, especially in relation to sudo.
Refer to the POSIX standard regarding tilde expansion. For bash, also see bash tilde expansion.
I've set up a penetration testing VM and am trying to practice privilege escalation.
I'm currently trying to read a file. I do not have access to the user's home directory where the file is located but I have permissions to run /usr/bin/perl as the user/admin.
My understanding is that I could run the following command to essentially cat the file and see what's inside using the perl permissions granted to me but it doesn't seem to be working and gives no result back
james#linuxtest:~$ sudo -l
Matching Defaults entries for james on linuxtest:
env_reset, mail_badpass, secure_path=/usr/local/sbin\:/usr/local/bin\:/usr/sbin\:/usr/bin\:/sbin\:/bin
User james may run the following commands on linuxtest:
(james2) /usr/bin/perl
james#linuxtest:~$ sudo -u james2 perl -e 'print 'cat /home/james/test.txt''
I expected the result to be the contents of the file or at least an error of some sort but no result. Am I making a stupid mistake here?
I think you wanted
sudo -u james2 perl -e 'print `cat /home/james/test.txt`'
Backticks are used to execute a shell command and capture its output.
That's a weird way of doing
sudo -u james2 perl -e 'system "cat /home/james/test.txt"'
which is a weird way of doing
sudo -u james2 cat /home/james/test.txt
And since you're root, that's a weird way of doing
cat /home/james/test.txt
Right now I have this code, that gives me only name, but I want to get name and other information from file /etc/passwd,
#!/bin/bash
user=$1;
grep home /etc/passwd | grep $user | cut -d: -f1;
I would like to get the full line, Not only my name.
Here is all the info on the current user. Note that because $USER is just a variable, it can be changed whereas the id command gives the actual user.
myuser#PC:~$ getent passwd $(id -u)
myuser:x:1000:1000:"",,,:/home/myuser:/bin/bash
myuser#PC:~$ export USER=root
myuser#PC:~$ getent passwd $USER
root:x:0:0:root:/root:/bin/bash
Try the finger command. You may need to install it.
I have a script which run this command successfully. I am using this command in another script which gives me error on this line (.md5: Permission denied).
I am running the previous script with sudo.
for i in ${NAME}*
do
sudo md5sum $i | sed -e "s/$i/${NAME}/" > ${NAME}.md5${i/#${NAME}/}
done
So you want to redirect output as root. It doesn't matter that you executed the command with sudo, because redirection is not part of the execution, so it's not performed by the executing user of the command, but by your current user.
The common trick is to use tee:
for i in ${NAME}*
do
md5sum $i | sed -e "s/$i/${NAME}/" | sudo tee ${NAME}.md5${i/#${NAME}/}
done
Note: I dropped the sudo from md5sum, as probably you don't need it.
Note: tee outputs in two directions: the specified file and stdout. If you want to suppress the output on stdout, redirect it to /dev/null.
You take the output of sudo md5sum $i and pipe it to a sed which is not running as root. sudo doesn't even know this sed exists.
But that's not the problem, because the sed does not need root permissions. The problem is > ${NAME}.... This redirects the output of sed to the file with this name. But the redirection is actually executed by your shell which is running as your user. And because > is a shell built-in operator, you can not prefix it with sudo.
The simple solution is to use tee. tee is a program (so you can run it with sudo) which writes it's input to the standard output and also to a file (like a T-Pipe, hence the name).
So you can just:
for i in ${NAME}*
do
md5sum $i | sed -e "s/$i/${NAME}/" | sudo tee ${NAME}.md5${i/#${NAME}/}
done
Note this will also dump all hashes to your standard output.
I wanna allow a normal user to kill a certain application which is started by root user.
In visudo:
I added a line like this:
normal_user ALL=(ALL) NOPASSWD: /usr/bin/kill $(ps aux | grep 'target_application' | awk '{print $2}')
But after save it and execute the following command as normal_user, I still get the prompt for root password:
sudo /usr/bin/kill $(ps aux | grep 'target_application' | awk '{print $2}')
What should I do then? Thanks a lot!
sudo will not interpret the command as a shell script to execute. Therefore you have said that this literal command can be run as normal_user:
/usr/bin/kill $(ps aux | grep 'target_application' | awk '{print $2}')
However since the shell will interpret the stuff in the $(...) before sudo is called on it, the command you are running looks more like this:
sudo /usr/bin/kill 1234
So it doesn't let you use it.
As fedorqui suggested, you should write a script that kills the user and then give normal_user the right to run that script (make sure they don't have write access to the script or its directory though).
kill_target_application.sh:
#!/bin/sh
/usr/bin/kill $(ps aux | grep 'target_application' | awk '{print $2}')
Use this command to allow users to execute or read the script, but not modify it:
chown root:root <filename>
chmod 755 <filename>
The give (r)ead and e(x)ecute permissions for all users, but only root can modify it. Also ensure that the user does not have write permissions for the directory or any of its parent directories. Read the chown and chmod man pages before doing this if you aren't familiar with these utilities.
visudo entry:
normal_user ALL=(ALL) NOPASSWD: /path/to/kill_target_application.sh
You should probably use "killall" instead of this complicated ps | grep option. Or at least look into pgrep.
Also, this really sounds like a job for an init script.