Posted by Paul on 19th February 2014
When executing a command or script as another user, it may be necessary to preserve the current shell’s environment. sudo
provides the -E
flag for this.
However, on Ubuntu systems the PATH
environment variable is not preserved by the -E
flag. Work around this by passing the current shell’s PATH
environment variable on the command-line in the form of PATH=$PATH
.
$ sudo PATH=$PATH -E -u anotheruser ./some-command.sh
There are other ways to manage environment variables with sudo by editing /etc/sudoers
(use sudoedit
, don’t edit it directly!), but the above can be useful to quickly get the job done.
Posted by Paul on 22nd May 2012
The Linux date
command can take several formats to set the system date andtime.
Here’s the format that I use when setting the date and the time:
mmddHHiiYYYY.ss
where,
mm = month
dd = day of month
HH = hour in 24 hour format
ii = minutes
ss = seconds
The following is an example usage using the date and time, 22nd May 2012, 11:57am, respectively:
$ sudo date _place_holder;052211572012.00
If only the time needs to be set then use the -s flag as follows:
$ sudo date _place_holder;-s _place_holder;"11:57:00"
If the system’s time zone requires changing, then on Debian-based systems use:
$ sudo dpkg-reconfigure tzdata
Posted by Paul on 2nd January 2010
802.11g Wireless Networking
A recent change of office required some wireless networking, involving installation of TP-Link TL-WN321G USB dongles on an Ubuntu Linux 9.10 workstation, 8.04 server and a couple of Windows XP workstations. This article summarises getting the device to work on an Ubuntu Linux system.
I broadly followed the (out-of-date) Ubuntu Community Documentation Wifi How To, with a few tips from elsewhere, and a recollection that it’s sometimes better to be without Gnome’s Network Manager.
Kernel Driver Support
After plugging in the dongle, `lsusb` gave the following (snipped)
information:
$ lsusb
Bus 002 Device 001: ID 1d6b:0001 Linux Foundation 1.1 root hub
Bus 001 Device 002: ID 148f:2573 Ralink Technology, Corp. RT2501USB Wireless Adapter
...
The second line of output gives the vendor (148f) and product (2573)
identifiers for the device. Checking a Linux wireless adapter chipset directory showed that supporting kernel drivers exist for this device’s chipset.
Listing the currently loaded kernel drivers showed that both the rt73usb and rt2500usb drivers had been automatically loaded:
$ lsmod
Module Size Used by
...
rt73usb 26336 0
rt2500usb xxxxx 0
...
Seeing that two drivers had been loaded I chose to blacklist one of them – the rt2500usb. For that I created a new, custom blacklist file in the /etc/modprobe/
directory, avoiding editing any existing blacklist file that my distribution had created. I chose to create the file /etc/modprobe/blacklist-custom.conf
:
$ cat /etc/modprobe.d/blacklist-custom.conf
blacklist rt2500usb
The rt2500usb driver may work, though I haven’t tested it.
Gnome Network Manager Problems
The Ubuntu workstation default setup makes use of Gnome Network Manager to manage wired and wireless network connectivity. Inspecting the kernel message log showed that although the wireless interface was being activated, it was then very quickly deactivating:
$ dmesg
...
[ xxxx.xxxxxx] rt73usb 1-2:1.0: firmware: requesting rt73.bin
[ xxxx.xxxxxx] ADDRCONF(NETDEV_UP): wlan2: link is not ready
[ xxxx.xxxxxx] wlan2: authenticate with AP xx:xx:xx:xx:xx:xx
[ xxxx.xxxxxx] wlan2: authenticated
...
[ xxxx.xxxxxx] wlan2: deauthenticating by local choice (reason=3)
...
Suspecting that Network Manager may be trying to maintain a wired-only connection and knowing the workstation doesn’t move anywhere, I decided to dispense with the network-manager package altogether:
$ sudo apt-get remove network-manager
...
Network Interface Configuration
In order to test the connection with my WAP I first disabled authentication and encryption on the WAP through its configuration interface. Here’s the simple configuration details for the USB dongle in the workstation’s /etc/network/interfaces
file:
auto lo
iface lo inet loopback
address 127.0.0.1
netmask 255.0.0.0
auto wlan2
iface wlan2 inet static
address 192.168.1.115
netmask 255.255.255.0
gateway 192.168.1.1
# Wireless config
wireless-essid myssid
wireless-channel 1
wireless-mode managed
Using iwconfig
I could see that the USB dongle was connecting to the WAP.
Now that we know that we can connect to the wireless access point, we can protect our communication. I’m using WPA2 to connect to and encrypt the communication channel to my WAP. Here’s the snipped /etc/network/interfaces
:
auto lo
iface lo inet loopback
address 127.0.0.1
netmask 255.0.0.0
auto wlan2
iface wlan2 inet static
address 192.168.1.115
netmask 255.255.255.0
gateway 192.168.1.1
# WPA2 config
wpa-psk secretpasskey
wpa-driver wext
wpa-key-mgmt WPA-PSK
wpa-proto WPA2
wpa-ssid myssid
pre-up sleep 5
WPA2 details can go straight into the interfaces
file, though you may wish to externalise the WPA2 supplicant information into a separate file that is read-protected from anything but the root user and group.
A check of the network interfaces shows a working wlan
network interface:
$ ifconfig
lo Link encap:Local Loopback
inet addr:127.0.0.1 Mask:255.0.0.0
inet6 addr: ::1/128 Scope:Host
UP LOOPBACK RUNNING MTU:16436 Metric:1
RX packets:33 errors:0 dropped:0 overruns:0 frame:0
TX packets:33 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:0
RX bytes:1831 (1.8 KB) TX bytes:1831 (1.8 KB)
...
wlan2 Link encap:Ethernet HWaddr xx:xx:xx:xx:xx:xx
inet addr:192.168.1.115 Bcast:192.168.1.255 Mask:255.255.255.0
inet6 addr: fe80::227:19ff:feb7:668a/64 Scope:Link
UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1
RX packets:468550 errors:0 dropped:0 overruns:0 frame:0
TX packets:398811 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:1000
RX bytes:406451098 (406.4 MB) TX bytes:184734469 (184.7 MB)
Checking wireless connection information with iwconfig
shows the wlan
interface is connected:
$ iwconfig
lo no wireless extensions.
...
wmaster0 no wireless extensions.
wlan2 IEEE 802.11bg ESSID:"myssid"
Mode:Managed Frequency:2.462 GHz Access Point: xx:xx:xx:xx:xx:xx
Bit Rate=54 Mb/s Tx-Power=9 dBm
Retry long limit:7 RTS thr:off Fragment thr:off
Power Management:on
Link Quality=38/70 Signal level=-72 dBm
Rx invalid nwid:0 Rx invalid crypt:0 Rx invalid frag:0
Tx excessive retries:0 Invalid misc:0 Missed beacon:0
Posted by Paul on 9th July 2009
Data Back-up Requirement
Last year (2008), when getting processes in place for our new web and software development business, getpepper, I put together an all important data backup procedure. My aim was, in the worse case, to ensure that we could restore all but the last few days-worth of data for our own systems and that of our clients.
We mostly use open source systems and tools to create and manage our websites and write our software, with the Ubuntu Linux distribution forming the platform upon which our server-based systems (source control (Subversion), issue tracking (Trac), CRM, etc.) and some of our desktop systems run.
After some research on Linux-based back-up facilities I settled on using a Bash shell script that would allow us to run a regular back-up cycle using external portable hard disks. The weekly back-up shell script, which saves to USB hard drives, is based upon a script provided by Mike Rubel.
The Script
The script uses the rsync
tool to provide the incremental functionality of the back-up. Here’s the adapted script that we use.
# ============================
# Author: Paul Pepper (though see description below for credits)
# Created: 6 November 2008
# Description:
# Rotating-snapshot utility adapted from Mike Rubel's make_snapshop.sh which
# can be found at http://www.mikerubel.org/computers/rsync_snapshots/
# Basically, this script performs rotating backup-snapshots of /home whenever
# it is called.
# ============================
#!/bin/bash
unset PATH # suggestion from H. Milz: avoid accidental use of $PATH
# ============================
# System commands used by this script
# ============================
ID=/usr/bin/id
ECHO=/bin/echo
MOUNT=/bin/mount
UMOUNT=/bin/umount
RM=/bin/rm
MV=/bin/mv
CP=/bin/cp
TOUCH=/bin/touch
RSYNC=/usr/bin/rsync
# ============================
# File names and locations
# ============================
MOUNT_DEVICE=/dev/sdb1
MOUNT_POINT=/media/sdb
BACKUP_TO_DIR=/backup/
BACKUP_FROM_DIR=/home
SNAPSHOT=snapshot
EXCLUDES=
BACKUP_TO_PATH=${MOUNT_POINT}/${BACKUP_TO_DIR}/${SNAPSHOT}
# ============================
# The script
# ============================
# Make sure we're running as root
if [ `$ID -u` != '0' ]; then
$ECHO "$0 must be executed as root. Exiting!"
exit 1
fi
# Attempt to mount the backup device, else abort
$MOUNT -o rw $MOUNT_DEVICE $MOUNT_POINT
if [ $? -ne 0 ]; then
$ECHO "$0: Could not mount $MOUNT_DEVICE on $MOUNT_POINT as readwrite"
exit 1
fi
# Step 1: delete the oldest snapshot, if it exists:
if [ -d ${BACKUP_TO_PATH}.3 ] ; then
$RM -rf ${BACKUP_TO_PATH}.3
fi
# Step 2: shift the middle snapshots(s) back by one, if they exist
if [ -d ${BACKUP_TO_PATH}.2 ] ; then
$MV ${BACKUP_TO_PATH}.2 \
${BACKUP_TO_PATH}.3
fi
if [ -d ${BACKUP_TO_PATH}.1 ] ; then
$MV ${BACKUP_TO_PATH}.1 \
${BACKUP_TO_PATH}.2
fi
# Step 3: make a hard-link-only (except for dirs) copy of the latest snapshot,
# if that exists
if [ -d ${BACKUP_TO_PATH}.0 ] ; then
$CP -al ${BACKUP_TO_PATH}.0 \
${BACKUP_TO_PATH}.1
fi
# Step 4: rsync from the system into the latest snapshot (notice that
# rsync behaves like cp --remove-destination by default, so the destination
# is unlinked first. If it were not so, this would copy over the other
# snapshot(s) too!
$RSYNC -va --delete --delete-excluded \
--exclude-from="$EXCLUDES" \
${BACKUP_FROM_DIR} ${BACKUP_TO_PATH}.0
# Step 5: update the mtime of our most recent snapshot.
$TOUCH ${BACKUP_TO_PATH}.0
# Unmount the device to which we've written the backup
${UMOUNT} ${MOUNT_POINT}
if [ $? -ne 0 ]; then
$ECHO "$0: Could not unmount ${MOUNT_POINT}"
exit 1
fi
Here’s an outline of our weekly back-up process:
1. Grab one of the external hard disks.
2. Attach hard disk to server via a USB connector.
3. Log in to server as a regular user – don’t _su_ to root!
4. Run the back-up shell script:
$ sudo ./backup-snapshot.sh
5. Disconnect hard disk and return to its place of safekeeping!
And that’s it!
All users who perform the back-up must have the necessary permissions to run the shell. I enforce this by adding those users as sudoers, only permitting privileged access to the back-up shell script. Here’s the relevant parts of the sudoers file that grants that access – note that it is recommended that you use visudo
when editing this file.
# User alias specification
User_Alias BACKUP_USERS = ann, bill
# Cmnd alias specification
Cmnd_Alias BACKUP_CMND = /somepath/backup-snapshot.sh, /bin/mount, /bin/umount, /bin/touch, /usr/bin/rsync
# Permit BACKUP_USERS to run the back-up script as root from all locations
BACKUP_USERS ALL=(root) BACKUP_CMND