ft@0
|
1 |
#!/bin/sh
|
ft@0
|
2 |
# This script mounts USB mass storage devices when they are plugged in
|
ft@0
|
3 |
# and unmounts them when they are removed.
|
ft@0
|
4 |
# Copyright © 2004, 2005 Martin Dickopp
|
ft@0
|
5 |
# Copyright © 2008, 2009, 2010 Rogério Theodoro de Brito
|
ft@0
|
6 |
#
|
ft@0
|
7 |
# This file is free software; the copyright holder gives unlimited
|
ft@0
|
8 |
# permission to copy and/or distribute it, with or without
|
ft@0
|
9 |
# modifications, as long as this notice is preserved.
|
ft@0
|
10 |
#
|
ft@0
|
11 |
# This file is distributed in the hope that it will be useful,
|
ft@0
|
12 |
# but WITHOUT ANY WARRANTY, to the extent permitted by law; without
|
ft@0
|
13 |
# even the implied warranty of MERCHANTABILITY or FITNESS FOR A
|
ft@0
|
14 |
# PARTICULAR PURPOSE.
|
ft@0
|
15 |
#
|
ft@0
|
16 |
set -e
|
ft@0
|
17 |
exec > /dev/null 2>&1
|
ft@0
|
18 |
|
ft@0
|
19 |
######################################################################
|
ft@0
|
20 |
# Auxiliary functions
|
ft@0
|
21 |
|
ft@0
|
22 |
# Log a string via the syslog facility.
|
ft@0
|
23 |
log()
|
ft@0
|
24 |
{
|
ft@0
|
25 |
if [ $1 != debug ] || expr "$VERBOSE" : "[yY]" > /dev/null; then
|
ft@0
|
26 |
logger -p user.$1 -t "usbmount[$$]" -- "$2"
|
ft@0
|
27 |
fi
|
ft@0
|
28 |
}
|
ft@0
|
29 |
|
ft@0
|
30 |
|
ft@0
|
31 |
# Test if the first parameter is in the list given by the second
|
ft@0
|
32 |
# parameter.
|
ft@0
|
33 |
in_list()
|
ft@0
|
34 |
{
|
ft@0
|
35 |
for v in $2; do
|
ft@0
|
36 |
[ "$1" != "$v" ] || return 0
|
ft@0
|
37 |
done
|
ft@0
|
38 |
return 1
|
ft@0
|
39 |
}
|
ft@0
|
40 |
|
ft@2
|
41 |
getRemoteIp ()
|
ft@2
|
42 |
{
|
ft@2
|
43 |
ip_address=$(ifconfig eth0 | grep "inet " | awk '{ print $2 }' | cut -d ":" -f 2)
|
ft@2
|
44 |
ip_netmask=$(ifconfig eth0 | grep "inet " | awk '{ print $4 }' | cut -d ":" -f 2)
|
ft@2
|
45 |
remote_ip=$(ipcalc $ip_address/$ip_netmask | grep HostMin | awk '{ print $2}')
|
ft@2
|
46 |
|
ft@2
|
47 |
echo $remote_ip
|
ft@2
|
48 |
}
|
ft@0
|
49 |
|
ft@0
|
50 |
######################################################################
|
ft@0
|
51 |
# Main program
|
ft@0
|
52 |
|
ft@0
|
53 |
# Default values for configuration variables.
|
ft@0
|
54 |
ENABLED=1
|
ft@0
|
55 |
MOUNTPOINTS=
|
ft@0
|
56 |
FILESYSTEMS=
|
ft@0
|
57 |
MOUNTOPTIONS=
|
ft@0
|
58 |
FS_MOUNTOPTIONS=
|
ft@0
|
59 |
VERBOSE=no
|
ft@0
|
60 |
|
ft@0
|
61 |
if [ -r /etc/usbmount/usbmount.conf ]; then
|
ft@0
|
62 |
. /etc/usbmount/usbmount.conf
|
ft@0
|
63 |
log debug "loaded usbmount configurations"
|
ft@0
|
64 |
fi
|
ft@0
|
65 |
|
ft@0
|
66 |
if [ "${ENABLED:-1}" -eq 0 ]; then
|
ft@0
|
67 |
log info "usbmount is disabled, see /etc/usbmount/usbmount.conf"
|
ft@0
|
68 |
exit 0
|
ft@0
|
69 |
fi
|
ft@0
|
70 |
|
ft@0
|
71 |
if [ ! -x /sbin/blkid ]; then
|
ft@0
|
72 |
log err "cannot execute /sbin/blkid"
|
ft@0
|
73 |
exit 1
|
ft@0
|
74 |
fi
|
ft@0
|
75 |
|
ft@0
|
76 |
# Per Policy 9.3.2, directories under /var/run have to be created
|
ft@0
|
77 |
# after every reboot.
|
ft@0
|
78 |
if [ ! -e /var/run/usbmount ]; then
|
ft@0
|
79 |
mkdir -p /var/run/usbmount
|
ft@0
|
80 |
log debug "creating /var/run/usbmount directory"
|
ft@0
|
81 |
fi
|
ft@0
|
82 |
|
ft@2
|
83 |
if [ ! -e /tmp/usbmount ]; then
|
ft@2
|
84 |
mkdir -p /tmp/usbmount
|
ft@2
|
85 |
log debug "creating /tmp/usbmount directory"
|
ft@2
|
86 |
fi
|
ft@2
|
87 |
|
ft@0
|
88 |
umask 022
|
ft@0
|
89 |
|
ft@0
|
90 |
if [ "$1" = add ]; then
|
ft@0
|
91 |
|
ft@0
|
92 |
# Acquire lock.
|
ft@0
|
93 |
log debug "trying to acquire lock /var/run/usbmount/.mount.lock"
|
ft@0
|
94 |
lockfile-create --retry 3 /var/run/usbmount/.mount || \
|
ft@0
|
95 |
{ log err "cannot acquire lock /var/run/usbmount/.mount.lock"; exit 1; }
|
ft@0
|
96 |
trap '( lockfile-remove /var/run/usbmount/.mount )' 0
|
ft@0
|
97 |
log debug "acquired lock /var/run/usbmount/.mount.lock"
|
ft@0
|
98 |
|
ft@0
|
99 |
# Grab device information from device and "divide it"
|
ft@0
|
100 |
# FIXME: improvement: implement mounting by label (notice that labels
|
ft@0
|
101 |
# can contain spaces, which makes things a little bit less comfortable).
|
ft@0
|
102 |
|
ft@0
|
103 |
set +e
|
ft@0
|
104 |
DEVINFO=$(/sbin/blkid -p $DEVNAME)
|
ft@0
|
105 |
BLKID_RESULT="$?"
|
ft@0
|
106 |
if [ "$BLKID_RESULT" != "0" ]
|
ft@0
|
107 |
then
|
ft@0
|
108 |
log info "blkid -p $DEVNAME has retured with $BLKID_RESULT"
|
ft@0
|
109 |
log info "Stick is maybe encrypted. Try decrypt"
|
ft@2
|
110 |
wget -q -T 3 -t 1 -O /dev/null http://$(getRemoteIp):8090/password?text=Please+enter+the+password
|
ft@0
|
111 |
if [ "$?" != "0" ]
|
ft@0
|
112 |
then
|
ft@2
|
113 |
log err "Connection to \"http://$(getRemoteIp):8090/password?text=Please+enter+the+password\" failed"
|
ft@0
|
114 |
exit 1
|
ft@0
|
115 |
fi
|
ft@0
|
116 |
log info "Password notification sended, wait for response"
|
ft@0
|
117 |
|
ft@2
|
118 |
/usr/bin/encryptionprovider.py -m eth0 58080 $DEVNAME /media/usb0
|
ft@0
|
119 |
if [ "$?" != "0" ]
|
ft@0
|
120 |
then
|
ft@0
|
121 |
log err "Stick removed. exit"
|
ft@0
|
122 |
exit 1
|
ft@0
|
123 |
fi
|
ft@0
|
124 |
|
ft@2
|
125 |
chattr -i "/tmp/usbmount"
|
ft@2
|
126 |
mkdir -p "/tmp/usbmount/encrypted"
|
ft@2
|
127 |
/usr/bin/osecfs /etc/osecfs/osecfs_usb.cfg "/tmp/usbmount/encrypted" rw
|
ft@0
|
128 |
log info "Encrypted stick mounted"
|
ft@2
|
129 |
|
ft@2
|
130 |
#run_initlistener.sh $DEVNAME &
|
ft@2
|
131 |
encryptionprovider.py -i eth0 58081 "$DEVNAME" /media/usb0 &
|
ft@2
|
132 |
chattr +i "/tmp/usbmount"
|
ft@0
|
133 |
exit 0
|
ft@0
|
134 |
fi
|
ft@0
|
135 |
set -e
|
ft@0
|
136 |
|
ft@0
|
137 |
FSTYPE=$(echo "$DEVINFO" | sed 's/.*[[:blank:]]TYPE="\([^"]*\)".*/\1/g; s/[[:blank:]]*//g;')
|
ft@0
|
138 |
UUID=$(echo "$DEVINFO" | sed 's/.*[[:blank:]]UUID="\([^"]*\)".*/\1/g; s/[[:blank:]]*//g;')
|
ft@0
|
139 |
USAGE=$(echo "$DEVINFO" | sed 's/.*[[:blank:]]USAGE="\([^"]*\)".*/\1/g; s/[[:blank:]]*//g;')
|
ft@0
|
140 |
|
ft@0
|
141 |
if ! echo $USAGE | egrep -q "(filesystem|disklabel)"; then
|
ft@0
|
142 |
log info "$DEVNAME does not contain a filesystem or disklabel"
|
ft@0
|
143 |
exit 1
|
ft@0
|
144 |
fi
|
ft@0
|
145 |
|
ft@0
|
146 |
|
ft@0
|
147 |
# Try to use specifications in /etc/fstab first.
|
ft@0
|
148 |
if egrep -q "^[[:blank:]]*$DEVNAME" /etc/fstab; then
|
ft@0
|
149 |
log info "executing command: mount $DEVNAME"
|
ft@0
|
150 |
mount $DEVNAME || log err "mount by DEVNAME with $DEVNAME wasn't successful; return code $?"
|
ft@0
|
151 |
|
ft@0
|
152 |
elif grep -q "^[[:blank:]]*UUID=$UUID" /etc/fstab; then
|
ft@0
|
153 |
log info "executing command: mount -U $UUID"
|
ft@0
|
154 |
mount -U $UUID || log err "mount by UUID with $UUID wasn't successful; return code $?"
|
ft@0
|
155 |
|
ft@0
|
156 |
else
|
ft@0
|
157 |
log debug "$DEVNAME contains filesystem type $FSTYPE"
|
ft@0
|
158 |
|
ft@0
|
159 |
fstype=$FSTYPE
|
ft@0
|
160 |
# Test if the filesystem type is in the list of filesystem
|
ft@0
|
161 |
# types to mount.
|
ft@0
|
162 |
if in_list "$fstype" "$FILESYSTEMS"; then
|
ft@0
|
163 |
# Search an available mountpoint.
|
ft@0
|
164 |
for v in $MOUNTPOINTS; do
|
ft@0
|
165 |
if [ -d "$v" ] && ! grep -q "^[^ ][^ ]* *$v " /proc/mounts; then
|
ft@0
|
166 |
mountpoint="$v"
|
ft@0
|
167 |
log debug "mountpoint $mountpoint is available for $DEVNAME"
|
ft@0
|
168 |
break
|
ft@0
|
169 |
fi
|
ft@0
|
170 |
done
|
ft@0
|
171 |
if [ -n "$mountpoint" ]; then
|
ft@0
|
172 |
# Determine mount options.
|
ft@0
|
173 |
options=
|
ft@0
|
174 |
for v in $FS_MOUNTOPTIONS; do
|
ft@0
|
175 |
if expr "$v" : "-fstype=$fstype,."; then
|
ft@0
|
176 |
options="$(echo "$v" | sed 's/^[^,]*,//')"
|
ft@0
|
177 |
break
|
ft@0
|
178 |
fi
|
ft@0
|
179 |
done
|
ft@0
|
180 |
if [ -n "$MOUNTOPTIONS" ]; then
|
ft@0
|
181 |
options="$MOUNTOPTIONS${options:+,$options}"
|
ft@0
|
182 |
fi
|
ft@0
|
183 |
|
ft@0
|
184 |
# Mount the filesystem.
|
ft@0
|
185 |
log info "executing command: mount -t$fstype ${options:+-o$options} $DEVNAME $mountpoint"
|
ft@0
|
186 |
mount "-t$fstype" "${options:+-o$options}" "$DEVNAME" "$mountpoint"
|
ft@0
|
187 |
|
ft@0
|
188 |
# Determine vendor and model.
|
ft@0
|
189 |
vendor=
|
ft@0
|
190 |
if [ -r "/sys$DEVPATH/device/vendor" ]; then
|
ft@0
|
191 |
vendor="`cat \"/sys$DEVPATH/device/vendor\"`"
|
ft@0
|
192 |
elif [ -r "/sys$DEVPATH/../device/vendor" ]; then
|
ft@0
|
193 |
vendor="`cat \"/sys$DEVPATH/../device/vendor\"`"
|
ft@0
|
194 |
elif [ -r "/sys$DEVPATH/device/../manufacturer" ]; then
|
ft@0
|
195 |
vendor="`cat \"/sys$DEVPATH/device/../manufacturer\"`"
|
ft@0
|
196 |
elif [ -r "/sys$DEVPATH/../device/../manufacturer" ]; then
|
ft@0
|
197 |
vendor="`cat \"/sys$DEVPATH/../device/../manufacturer\"`"
|
ft@0
|
198 |
fi
|
ft@0
|
199 |
vendor="$(echo "$vendor" | sed 's/^[[:blank:]]\+//; s/[[:blank:]]\+$//')"
|
ft@0
|
200 |
|
ft@0
|
201 |
model=
|
ft@0
|
202 |
if [ -r "/sys$DEVPATH/device/model" ]; then
|
ft@0
|
203 |
model="`cat \"/sys$DEVPATH/device/model\"`"
|
ft@0
|
204 |
elif [ -r "/sys$DEVPATH/../device/model" ]; then
|
ft@0
|
205 |
model="`cat \"/sys$DEVPATH/../device/model\"`"
|
ft@0
|
206 |
elif [ -r "/sys$DEVPATH/device/../product" ]; then
|
ft@0
|
207 |
model="`cat \"/sys$DEVPATH/device/../product\"`"
|
ft@0
|
208 |
elif [ -r "/sys$DEVPATH/../device/../product" ]; then
|
ft@0
|
209 |
model="`cat \"/sys$DEVPATH/../device/../product\"`"
|
ft@0
|
210 |
fi
|
ft@0
|
211 |
model="$(echo "$model" | sed 's/^[[:blank:]]\+//; s/[[:blank:]]\+$//')"
|
ft@0
|
212 |
|
ft@0
|
213 |
# Run hook scripts; ignore errors.
|
ft@0
|
214 |
export UM_DEVICE="$DEVNAME"
|
ft@0
|
215 |
export UM_MOUNTPOINT="$mountpoint"
|
ft@0
|
216 |
export UM_FILESYSTEM="$fstype"
|
ft@0
|
217 |
export UM_MOUNTOPTIONS="$options"
|
ft@0
|
218 |
export UM_VENDOR="$vendor"
|
ft@0
|
219 |
export UM_MODEL="$model"
|
ft@0
|
220 |
log info "executing command: run-parts /etc/usbmount/mount.d"
|
ft@0
|
221 |
run-parts /etc/usbmount/mount.d || :
|
ft@0
|
222 |
else
|
ft@0
|
223 |
# No suitable mount point found.
|
ft@0
|
224 |
log warning "no mountpoint found for $DEVNAME"
|
ft@0
|
225 |
exit 1
|
ft@0
|
226 |
fi
|
ft@0
|
227 |
fi
|
ft@0
|
228 |
fi
|
ft@0
|
229 |
elif [ "$1" = remove ]; then
|
ft@0
|
230 |
|
ft@0
|
231 |
# A block or partition device has been removed.
|
ft@0
|
232 |
# Test if it is mounted.
|
ft@2
|
233 |
for device in $(/usr/bin/encryptionprovider.py -g)
|
ft@0
|
234 |
do
|
ft@0
|
235 |
if [ "$DEVNAME" = "$device" ]
|
ft@0
|
236 |
then
|
ft@2
|
237 |
log info "umout encrypted device"
|
ft@2
|
238 |
chattr -i "/tmp/usbmount"
|
ft@2
|
239 |
umount "/tmp/usbmount/encrypted"
|
ft@2
|
240 |
rmdir "/tmp/usbmount/encrypted"
|
ft@2
|
241 |
log info "/usr/bin/encryptionprovider.py -u $DEVNAME"
|
ft@2
|
242 |
/usr/bin/encryptionprovider.py -u "$DEVNAME"
|
ft@0
|
243 |
log info "everything done"
|
ft@0
|
244 |
fi
|
ft@0
|
245 |
done
|
ft@0
|
246 |
while read device mountpoint fstype remainder; do
|
ft@0
|
247 |
if [ "$DEVNAME" = "$device" ]; then
|
ft@0
|
248 |
# If the mountpoint and filesystem type are maintained by
|
ft@0
|
249 |
# this script, unmount the filesystem.
|
ft@0
|
250 |
if in_list "$mountpoint" "$MOUNTPOINTS" &&
|
ft@0
|
251 |
in_list "$fstype" "$FILESYSTEMS"; then
|
ft@0
|
252 |
log info "executing command: umount -l $mountpoint"
|
ft@0
|
253 |
umount -l "$mountpoint"
|
ft@0
|
254 |
|
ft@0
|
255 |
# Run hook scripts; ignore errors.
|
ft@0
|
256 |
export UM_DEVICE="$DEVNAME"
|
ft@0
|
257 |
export UM_MOUNTPOINT="$mountpoint"
|
ft@0
|
258 |
export UM_FILESYSTEM="$fstype"
|
ft@0
|
259 |
log info "executing command: run-parts /etc/usbmount/umount.d"
|
ft@0
|
260 |
run-parts /etc/usbmount/umount.d || :
|
ft@0
|
261 |
fi
|
ft@0
|
262 |
break
|
ft@0
|
263 |
fi
|
ft@0
|
264 |
done < /proc/mounts
|
ft@0
|
265 |
else
|
ft@0
|
266 |
log err "unexpected: action '$1'"
|
ft@0
|
267 |
exit 1
|
ft@0
|
268 |
fi
|
ft@0
|
269 |
|
ft@0
|
270 |
log debug "usbmount execution finished"
|