I need a Shell script, this shell script should :
1. create another shell script
2. set the suid bit for new script as a root user
3. run this new script as current user
Can we do this?
anyone can give any idea or some code snippets?
This will not work under many versions of unix (or linux). The setuid bit on shell scripts is typically ignored, since it is far too easy to subvert such a program.
Related
I am wondering when and why do we need execution permission in linux although we can run any script without execute permission when we execute that script using the syntax bellow?
bash SomeScriptFile
Not all programs are scripts — bash for example isn't. So you need execute permission for executable programs.
Also, when you say bash SomeScriptFile, the script has to be in the current directory. If you have the script executable and in a directory on your PATH (e.g. $HOME/bin), then you can run the script without the unnecessary circumlocution of bash $HOME/bin/SomeScriptFile (or bash ~/bin/SomeScriptFile); you can simply run SomeScriptFile. This economy is worth having.
Execute permission on a directory is somewhat different, of course, but also important. It permits the 'class of user' (owner, group, others) to access files in the directory, subject to per-file permissions also allowing that.
Executing the script by invoking it directly and running the script through bash are two very different things.
When you run bash ~/bin/SomeScriptFile you are really just executing bash -- a command interpreter. bash in turns load the scripts and runs it.
When you run ~/bin/SomeSCriptFile directly, the system is able to tell this file is a script file and finds the interpreter to run it. There is a big of magic invoking the #! on the first line to look for the right interpreter.
The reason we run scripts directly is that the user (and system) couldn't know or care of the command we are running is a script or a compiled executable.
For instance, if I write a nifty shell script called fixAllIlls and later I decide to re-write it in C, as long a I keep the same interface, the users don't have to do anything different.
To them, it is just a program to run.
edit
The operating system checks permissions first for several reasons:
Checking permissions is faster
In the days of old, you could have SUID scripts, so one needed to check the permission bits.
As a result, it was possible to run scripts that you could not actually read the contents of. (That is still true of binaries.)
I was working on this tutorial here and I want to know the path so I can put it in my shell scripts on the top line as is good practice.
I was told this is not accurate:
echo "$SHELL"
What is the correct way to determine the path to the interpreter for shell scripts?
This is a shared hosting account and it is not obvious where it is located.
This is a follow up to a similar but not duplicate here.
You can use
which -a bash
to list all paths for the current user that point to a bash program.
When beginning to work, I have to run several commands:
source work/tools
cd work/tool
source tool
setup_tool
Off course, doing this a few times a day is really annonying, so I tried to make a bash script tool where I put these commands and put it in /user/bin to run it with command
tool
However, there is a problem. When i run the script and then try to work by typing some of the tool-based commands, it does not work.
I figured out, that it is fine, since if I make a script and then run it, the script seems to run in the same terminal window, but what it really does is, that it behaves as if it created a "hidden window" for its execution and after termination of the script, the "hidden window" terminates too. So I am asking - is there a way to automatize the source command?
I have tried using xterm -hold -e command, but it runs the programmed script in the new window. Obviously, I don't want that. How can I achieve running it in the current window?
Don't put files like that in /usr/bin. As a general rule you don't want to mess with the distribution owned locations like that. You can use /usr/local/bin if you need a system-wide location or you can create a directory in your home directory to hold things like this that are for your own usage (and add that to the $PATH).
What you've noticed is that when run as a script on its own (tool, /path/to/tool, etc.) that the script runs in its own shell session (nothing to do with terminal windows as-such) and you don't want that (as the changes the script makes don't persist to your current shell session).
What you want to do instead is "source"/run the script in your current session. Which you are already doing with that set of commands you listed (source work/tools is doing exactly that).
So instead of running tool or /path/to/tool instead use source /path/to/tool or . /path/to/tool.
As fedorqui correctly points out you don't even need a script for this anywhere as you can just make a shell function for this instead (in your normal shell startup files .bashrc, etc.) and then just run that function when you need to so that setup.
Be careful to use full paths for things when you do this though since you, presumably, want this to work no matter what directory you happen to be in when you run it.
It doesn't create a new hidden window, nor does it create a terminal. What happens is that if you're running a script, normally it runs on a new shell process. The script you're running is supposed to modify the shell environment, but if you're running the script in a new shell process, that shell process's environment is the one that gets modified, instead of your shell environment.
Scripts that needs to modify the current shell environments usually must be run with the source command. What you need to do is to run the script in the current shell. So you should do source /path/to/tool.
If you want to be able to source the script with just tool, put this in your alias file/shell startup (check your distro doc where the file is, but it's usually either .bash_aliases or .bashrc):
alias tool="source /path/to/tool"
I'm writing a small script to manage my installed JDK on a linux machine, say for example that the name of the script/function is usejdk.
I come with to ways :
usejdk is a bash function in shell script sourced the file in .bashrc or .bash_profile.
use usejdk as the name of the shell script and add it to the ~/bindirectory which is the PATH.
What is the idiomatic way to deploy a shell script on a unix machine between the two ?
If you are creating something for other people to use, a self-contained script they can put in their PATH and replace with new versions as needed is far easier, better, and maintainable than a function that will require them editing their startup files.
I'm trying to interactively test code before I put it into a script and was wondering if there are any things that behave differently in a script?
When you execute a script it has its own environment variables which are inherited from the parent process (the shell from which you executed the command). Only exported variables will be visible to the child script.
More information:
http://en.wikipedia.org/wiki/Environment_variable
http://www.kingcomputerservices.com/unix_101/understanding_unix_shells_and_environment_variables.htm
By the way, if you want your script to run in the same environment as the shell it is executed in, you can do it with the point command:
. script.sh
This will avoid creating a new process for you shell script.
A script runs in exactly the same way as if you typed the content in at a shell prompt. Even loops and if statements can be typed in at the shell prompt. The shell will keep asking for more until it has a complete statement to execute.
As David rightly pointed out, watch out for environment variables.
Depending on how you intend to launch your script, variables set in .profile and .bashrc may not be available. This is subject to whether the script is launched in interactive mode and whether it was a login shell. See Quick Startup File Reference.
A common problem I see is scripts that work when run from the shell but fail when run from another application (cron, nagios, buildbot, etc.) because $PATH was not set.
To test if a command/script would work in a clean session, you can login using:
ssh -t localhost "/bin/bash --noprofile --norc"
This ensures that we don't inherit any exported variables from the parent shell, and nothing from .profile or .rc.
If it works in a clean session and none of you're commands expect to be in interactive mode, then you're good to go!