Unix/Linux
Contents
- 1 debug a shell
- 2 Filesystem 100% full, what's taking up all the space?
- 3 Run a local script on a remote host
- 4 Return a list of Oracle databases running on a list of remote servers
- 5 Check RMAN logfiles for errors from cron every day
- 6 Array processing
- 7 Handy aliases
- 8 Use SSH config file
- 9 A decent sed tutorial
- 10 A decent korn/bash shell tutorial
- 11 trap
- 12 DNS not working
- 13 Setup Oracle Enterprise Linux (RedHat) with yum server
- 14 To change to static IP address
- 15 Run a command on lots of servers in parallel
debug a shell
#!/usr/bin/ksh exec 2>/tmp/mytest
Filesystem 100% full, what's taking up all the space?
/dev/esb01fs010001 1.00 0.00 100% 1838 69% /oracle beuxdsysesb01:root[/root]# cd /oracle beuxdsysesb01:root[/oracle]# du -sgx * 0.09 admin 0.00 checkpoints 0.99 diag 0.00 flash_recovery_area 0.00 lost+found 0.00 oraInst.loc 0.00 oraInventory
cd diag and repeat until culprits are found
Run a local script on a remote host
ssh user@host 'sh' < your_script.sh
First of all, this command is a redirection: your shell will open the file your_script.sh and feed it as input to the ssh command. ssh, in turn, will tunnel its stdin to the remote command, namely, sh instance. And sh without arguments reads its script from stdin. So we got sh instance, which is launched on remote host, but reads commands from your local file.
Return a list of Oracle databases running on a list of remote servers
#!/bin/ksh
serverlist=`cat /home/tools/ini/system/oracle_servers | sort -n | tr "\n" " "`
if [ -z "${serverlist}" ]
then
echo "no servers found" && exit 1
fi
for server in ${serverlist}
do
ssh ${server} "ps -ef | grep [o]ra_pmon_" >/tmp/${server}.dblist
done
for server in ${serverlist}
do
cat /tmp/${server}.dblist | awk -F_ -v SRV=${server} 'BEGIN {print SRV ":"} {print $NF}' | tr "\n" " "
echo
done
Check RMAN logfiles for errors from cron every day
00 09 * * * /home/tools/scripts/oracle/dosh 'find /home/tools/logs/rman -name "*online.log" -mtime -1 -exec sed -ne "/^RMAN-/,/^$/p" {} \\; -ls' | mailx
-s 'RMAN errors last night' [email protected]
Array processing
array=(1 2 3)
unset array[2]
echo ${array[2]} # null
indices=(${!array[@]}) # create an array of the indices of "array"
size=${#indices[@]} # the size of "array" is the number of indices into it
size=${#array[@]} # same
echo ${array[@]: -1} # you can use slices to get array elements, -1 is the last one, etc.
for element in ${array[@]}; do # iterate over the array without an index
for index in ${indices[@]} # iterate over the array WITH an index
do
echo "Index: ${index}, Element: ${array[index]}"
done
for index in ${!array[@]} # iterate over the array WITH an index, directly
array+=("new element") # append a new element without referring to an index
((counter++)) # shorter than ((counter=counter+1)) or ((counter+=1))
if [[ $var == 3 ]] # you can use the more "natural" comparison operators inside double square brackets
while [[ $var < 11 ]] # another example
echo ${array[${index}-1] # math inside an array subscript
Handy aliases
Strip out comments and blank lines from a file
alias strip='grep -Ev '\''^(#|$)'\'''
Does a ps and a grep
alias psg='ps -ef | grep -v $$ | grep -i '
A handy way of listing subdirectories and their files
alias filetree="find . -print | sed -e 's;[^/]*/;|____;g;s;____|; |;g'"
Watch progress of a copy
alias cpProgress="rsync --progress -ravz"Reboots Linksys router
alias rebootlinksys="curl -u 'admin:password' 'http://192.168.1.2/setup.cgi?todo=reboot'"
Nice one for bash. Colour codes the prompt depending on the outcome of the previous command
bash_prompt_command()
{
RTN=$?
prevCmd=$(prevCmd $RTN)
}
PROMPT_COMMAND=bash_prompt_command
prevCmd()
{
if [ $1 == 0 ] ; then
echo $GREEN
else
echo $RED
fi
}
if [ $(tput colors) -gt 0 ] ; then
RED=$(tput setaf 1)
GREEN=$(tput setaf 2)
RST=$(tput op)
fi
export PS1="\[\e[36m\]\u.\h.\W\[\e[0m\]\[\$prevCmd\]>\[$RST\]"
Mmmm, to be looked into. Executes remote commands on a unix box using curl.
#/bin/sh
#
# WAG320N-HACK
# Ver. 1.0
# 12/09/2010
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program. If not, see <http://www.gnu.org/licenses/>.
# Set username and password in the form of "username:password"
# example: "admin:admin"
my_access="admin:admin"
# Parameters test
if [ -z "$1" ]
then
echo "wag320n-hack.sh: missing remote command"
echo "usage: wag320n-hack.sh <remote command>"
echo "example: wag320n-hack.sh /bin/ls -la /usr/sbin"
echo "Note: always use full path"
echo ""
echo "wag320n-hack.sh - Ver. 1.0 - 12/09/2010"
echo "Licensed under GPL V. 3"
echo ""
exit 0
fi
# Get the command
my_command="ping_size="'$('"$@"' 1>&2)'
curl -s -G -u "$my_access" --data-urlencode 'todo=ping_test' --data-urlencode 'this_file=Diagnostics.htm' --data-urlencode 'next_file=Ping.htm' --data-urlencode 'c4_ping_ipaddr=192.168.1.1' --data-urlencode 'ping_timeout=5000' --data-urlencode 'ping_interval=1000' --data-urlencode 'ping_number=1' --data-urlencode "$my_command" http://192.168.1.1/setup.cgi | sed -e '/HTTP\/1.0 200 OK/q'
Use SSH config file
Host server10 Hostname 1.2.3.4 IdentityFile ~/.ssh/id_dsa user foobar Port 30000 ForwardX11Trusted yes TCPKeepAlive yes
then just connect using
ssh server10
A decent sed tutorial
From grymoire.com
A decent korn/bash shell tutorial
From dartmouth.edu Reproduced here just in case it disappears! Advanced shell scripting
trap
Example Handling Traps With ksh - Discussion of the kill command
EXAMPLE TEMPLATE:
PRODUCT: HP-UX 11iV1 Version B.11.11
HP Tru64 V5.1B PK4
Sun/Solaris SunOS V5.8
Linux 2.6 kernel
COMPONENT: ksh
SOURCE: Philippe Vouters
Fontainebleau/France
LOW COST HIGH-TECH PRODUCTS: http://techno-star.fr
OVERVIEW:
The ksh script below shows how to eventually handle traps in the situation
where someone might try to kill a script by killing individual commands run
by that script or the entire process group a script is running in. The kill
command (usually a shell builtin) may be used to send a signal to a process
group (with the -<pid> syntax) or an individual process. The example ksh
script below runs /bin/sleep as the foreground process, the example ksh
scripts immediately returns when the /bin/sleep process has terminated. Most
signals sent to the shell are ignored until after the foreground process
terminates. This is in order to avoid creating zombie processes. Therefore a
kill <pid> on the example ksh script waits for the termination of the
/bin/sleep process.
The status value $? in the trap refers to the exit status of the command to run
and therefore is the exit status of the /bin/sleep process. The called function
in the trap handler shows how to correctly examine the effect of the kill
command on the shell or it's children.
To examine the value of $? in a trap handler means that you must understand what
it can be set and how different signals delivered to either the shell or the
foreground process (or the process group) might affect the value of $?.
The example shell script prints $? using echo but it does not perform tests on
the value of $?. For a complete solution when attempting to trap signals in a
shell you would also need code that examined the value of $? after the
foreground process had completed.
*** CAUTION ***
This sample script has been tested using HP-UX B.11.11, HP Tru64 V5.1B PK4,
SunOS V5.8 and Fedora Core 4 (homed version of Red Hat Linux). However, we
cannot guarantee its effectiveness because of the possibility of error in
transmitting or implementing it. It is meant to be used as a template for
writing your own scripts, and may require modification for use on your system.
SCRIPT NOTES:
To notice that the ksh script and /bin/sleep share the same process group
identifier (PGID), issue the following commands:
[philippe@victor ~]$ who
philippe :0 Jan 10 10:16
philippe pts/1 Jan 10 21:30 (:0.0)
philippe pts/2 Jan 10 21:30 (:0.0)
[philippe@victor ~]$ tty
/dev/pts/1
[philippe@victor ~]$ ps -j -t pts/2
PID PGID SID TTY TIME CMD
11072 11072 11072 pts/2 00:00:00 bash
11113 11113 11072 pts/2 00:00:00 ksh
11116 11113 11072 pts/2 00:00:00 sleep
In this case sending kill -INT -11113 will send SIGINT to the process group
11113. Both of the ksh and sleep processes are contained within this process
group.
Important Note:
On HP-UX, you have to $ export UNIX95=1 in order to be able to use the
-j option of the ps command.
SCRIPT:
COPYRIGHT (C) 2005 BY
HEWLETT-PACKARD COMPANY
ALL RIGHTS RESERVED.
THIS SOFTWARE IS FURNISHED UNDER A LICENSE AND MAY BE USED AND COPIED
ONLY IN ACCORDANCE WITH THE TERMS OF SUCH LICENSE AND WITH THE INCLUSION
OF THE ABOVE COPYRIGHT NOTICE. THIS SOFTWARE OR ANY OTHER COPIES
THEREOF MAY NOT BE PROVIDED OR OTHERWISE MADE AVAILABLE TO ANY OTHER
PERSON. NO TITLE TO AND OWNERSHIP OF THE SOFTWARE IS HEREBY TRANSFERRED.
THE INFORMATION IN THIS SOFTWARE IS SUBJECT TO CHANGE WITHOUT NOTICE AND
SHOULD NOT BE CONSTRUED AS A COMMITMENT BY HEWLETT-PACKARD COMPANY.
HP ASSUMES NO RESPONSIBILITY FOR THE USE OR RELIABILITY OF ITS
SOFTWARE ON EQUIPMENT THAT IS NOT SUPPLIED BY HP.
NO RESPONSIBILITY IS ASSUMED FOR THE USE OR RELIABILITY OF SOFTWARE
ON EQUIPMENT THAT IS NOT SUPPLIED BY HEWLETT-PACKARD COMPANY.
SUPPORT FOR THIS SOFTWARE IS NOT COVERED UNDER ANY HP SOFTWARE
PRODUCT SUPPORT CONTRACT, BUT MAY BE PROVIDED UNDER THE TERMS OF THE
CONSULTING AGREEMENT UNDER WHICH THIS SOFTWARE WAS DEVELOPED.
#!/bin/ksh
function handle_signal
{
print -n "pid $$ recieved $2 "
if [[ $1 = 0 ]];then
print but foreground command ended successfully
else
if [[ $1 = $3 ]];then
print and so did the last foreground command
else
print -n "and the exit status of the last foreground "
print command was $1
fi
fi
# Kill our process group and then ourselves with SIGTERM, giving a
# pid of 0 sends the signal to our process group. Killing the process
# group should kill us as well, this assumes that SIGTERM is not
# handled by any process in the process group.
#
# This code could be replaced with an exit with an exit value that
# would indicate what the problem was to the caller. That is replace
# these two lines with:
#
# exit $3
#
# or a specific exit code could be used.
#
kill -TERM 0
kill -TERM $$
}
OS=$(uname -a | awk '{print $1}')
if [[ "$OS" = "Linux" ]]; then
offset=256
elif [[ ("$OS" = "HP-UX") ||
("$OS" = "SunOS") ||
("$OS" = "OSF1") ]]; then
offset=128
fi
trap 'RC=$?; handle_signal $RC SIGINT $offset+2' INT
trap 'RC=$?; handle_signal $RC SIGQUIT $offset+3' QUIT
/bin/sleep 20
echo $?
DNS not working
Ping to an IP address works
ping 74.125.136.103
but this doesn't
ping www.google.com
Check resolv.conf
cat /etc/resolv.conf nameserver 95.130.132.17 nameserver 95.130.132.18
I had changed internet provider and forgot to update this. Just to set it to the router address and let that do the resolution
nameserver 192.168.1.1
Setup Oracle Enterprise Linux (RedHat) with yum server
You need to download the yum .repo file from the server, as per the steps below. After this, you need to enable a flag in the .repo file as per your operating system version. Having done these two steps, when you run yum install <pkgname> command on your linux box, the Oracle's yum server will be scanned, the dependent & the relevant rpm's will be download and installed for you.
cd /etc/yum.repos.d
To download files here
wget http://public-yum.oracle.com/public-yum-el5.repo
A file named public-yum-el5.repo will be created in your directory Edit this file and enter enabled=1 against the operating systems which is relevant to you
vi public-yum-el5.repo
Next run the yum command
yum install package-name
To change to static IP address
As root:
cd /etc/networks vi interfaces
replace the line “iface eth0 inet dhcp” with
iface eth0 inet static address 192.168.1.100 netmask 255.255.255.0 gateway 192.168.1.1
You should also take a look at the file /etc/resolv.conf and check it has a nameserver entry (probably pointing at your default gateway) or direct to your ISP name servers.
nameserver 192.168.1.1
Run a command on lots of servers in parallel
This is a damn fine AIX utility - part of the CSM Distributed Shell.
dsh -a "ls -al /etc/apache2/*conf"
will list the Apache configuration file on all reachable servers (nodes)