source: epoptes/trunk/fuentes/epoptes-client/epoptes-client @ 295

Last change on this file since 295 was 295, checked in by mabarracus, 4 years ago

copy trusty epoptes code

  • Property svn:executable set to *
File size: 8.1 KB
Line 
1#!/bin/sh
2
3###########################################################################
4# Connects to a remote server and offers it a local shell.
5# Usage: epoptes [server] [port]
6#
7# Copyright (C) 2010-2012 Alkis Georgopoulos <alkisg@gmail.com>
8#
9# This program is free software: you can redistribute it and/or modify
10# it under the terms of the GNU General Public License as published by
11# the Free Software Foundation, either version 3 of the License, or
12# (at your option) any later version.
13#
14# This program is distributed in the hope that it will be useful,
15# but WITHOUT ANY WARRANTY; without even the implied warranty of
16# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17# GNU General Public License for more details.
18#
19# You should have received a copy of the GNU General Public License
20# along with this program.  If not, see <http://www.gnu.org/licenses/>.
21#
22# On Debian GNU/Linux systems, the complete text of the GNU General
23# Public License can be found in `/usr/share/common-licenses/GPL'.
24###########################################################################
25
26# epoptes-client may be called either as root, to control the client, or as a
27# user, to control the user session.
28# As root, epoptes-client starts from if-up.d on standalone clients.
29# Unfortunately, thin and fat clients don't get if-up.d events, so just for
30# this case we're using a helper sysvinit script.
31# As a user, epoptes-client runs from /etc/xdg/autostart.
32# Users can cancel that from their System > Preferences > Services gnome menu.
33
34die() {
35    echo "epoptes-client ERROR: $@" >&2
36    exit 1
37}
38
39# The "boolean_is_true" name is used as a sentinel that prevents ltsp_config
40# from sourcing ltsp_common_functions. So we're using a different name.
41my_boolean_is_true() {
42    case "$1" in
43       # match all cases of true|y|yes
44       [Tt][Rr][Uu][Ee]|[Yy]|[Yy][Ee][Ss]) return 0 ;;
45       *) return 1 ;;
46    esac
47}
48
49# Return true if we're in a chroot.
50chrooted() {
51    # The result is cached in a variable with the same name as the function :P
52    test -n "$chrooted" && return "$chrooted"
53    test -n "$UID" || UID=$(id -u)
54    if [ "$UID" -gt 0 ]; then
55        chrooted=1
56    elif [ "$(stat -c %d/%i /)" = "$(stat -Lc %d/%i /proc/1/root 2>/dev/null)" ]
57    then
58        # the devicenumber/inode pair of / is the same as that of /sbin/init's
59        # root, so we're *not* in a chroot and hence return false.
60        chrooted=1
61    else
62        chrooted=0
63    fi
64    return "$chrooted"
65}
66
67# Get $UID and $TYPE of the client, and the default $SERVER and $PORT.
68basic_info() {
69    test -n "$UID" || UID=$(id -u)
70
71    # We temporarily need LTSP_CLIENT and LTSP_FATCLIENT to decide TYPE.
72    # Unfortunately, when epoptes-client is ran as a system service, they're
73    # not in our environment, and we need to source ltsp_config.
74    # But we don't want to pollute the environment with any of its other vars.
75    if [ "$UID" -eq 0 ] && [ -f /usr/share/ltsp/ltsp_config ] && ! chrooted &&
76        egrep -qs 'ltsp|nfs|nbd' /proc/cmdline
77    then
78        export $(
79            . /usr/share/ltsp/ltsp_config >/dev/null
80            echo "LTSP_CLIENT=$LTSP_CLIENT"
81            echo "LTSP_FATCLIENT=$LTSP_FATCLIENT"
82            echo "EPOPTES_CLIENT_VERIFY_CERTIFICATE=$EPOPTES_CLIENT_VERIFY_CERTIFICATE")
83        # LTSP_CLIENT may not be available in system sesssions, if so fake it
84        LTSP_CLIENT=${LTSP_CLIENT:-127.0.0.1}
85    fi
86
87    # LTSP_FATCLIENT may not be available in user sessions, autodetect it
88    if [ -n "$LTSP_CLIENT" ] && [ -z "$LTSP_FATCLIENT" ] &&
89        [ "$UID" -gt 0 ] && [ -x /usr/bin/getltscfg ] &&
90        egrep -qs 'ltsp|nfs|nbd' /proc/cmdline
91    then
92        LTSP_FATCLIENT=True
93    fi
94
95    if my_boolean_is_true "$LTSP_FATCLIENT"; then
96        TYPE="fat"
97    elif [ -n "$LTSP_CLIENT" ]; then
98        TYPE="thin"
99    else
100        TYPE="standalone"
101    fi
102
103    if ( [ "$TYPE" = "thin" ] && [ "$UID" -gt 0 ] ) || chrooted; then
104        SERVER=localhost
105    else
106        SERVER=server
107    fi
108    PORT=789
109
110    export UID TYPE SERVER PORT
111}
112
113fetch_certificate()
114{
115    test "$UID" -eq 0 || die "Need to be root to fetch the certificate"
116    mkdir -p /etc/epoptes
117    openssl s_client -connect $SERVER:$PORT < /dev/null \
118        | sed '/-----BEGIN CERTIFICATE-----/,/-----END CERTIFICATE-----/!d' \
119        > /etc/epoptes/server.crt
120    if [ -s /etc/epoptes/server.crt ]; then
121        echo "Successfully fetched certificate from $SERVER:$PORT"
122        exit 0
123    else
124        die "Failed to fetch certificate from $SERVER:$PORT"
125    fi
126}
127
128
129# Main.
130export VERSION="0.5.7" # Automatically updated by mkdst
131
132# Check the first parameter as it may turn out we don't need to run at all
133case "$1" in
134    -v|--version)
135        echo "$VERSION"
136        exit
137        ;;
138    -h|--help)
139        if [ -x /usr/bin/man ]; then
140            exec man epoptes-client
141        else
142            echo "Usage: $0 [-c|-h|-v] [SERVER] [PORT]"
143            exit 0
144        fi
145        ;;
146    -c|--certificate)
147        need_certificate=true
148        shift
149        ;;
150esac
151
152# When called from /etc/xdg/autostart, /sbin is not in the system path.
153PATH="$PATH:/sbin:/usr/sbin"
154
155# When launched as a service, LANG might not be set.
156if [ -z "$LANG" ] && [ -r /etc/default/locale ]; then
157    . /etc/default/locale
158    export LANG
159fi
160
161basic_info
162# The configuration file overrides the default values
163if [ -f /etc/default/epoptes-client ]; then
164    . /etc/default/epoptes-client
165fi
166# And the command line parameters override the configuration file
167export SERVER=${1:-$SERVER}
168export PORT=${2:-$PORT}
169
170# Provide an easy way to fetch the server certificate
171test -n "$need_certificate" && fetch_certificate
172
173# We don't want the epoptes-client system service running on the epoptes server
174if ( [ $UID -eq 0 ] && [ $TYPE = "standalone" ] && [ -x /usr/bin/epoptes ] ) ||
175    chrooted
176then
177    lliurex-version -t client || exit 0
178fi
179
180# Go to the scripts directory, so that we can run them with ./xxx
181cd $(dirname "$0")
182if [ -d ../epoptes-client ]; then
183    cd ../epoptes-client
184else
185    cd /usr/share/epoptes-client
186fi
187
188# Source the lsb init functions, for log_begin_msg.
189# Unfortunately it seems that Centos and Fedora don't have that file.
190if [ -f /lib/lsb/init-functions ]; then
191    . /lib/lsb/init-functions
192else
193    alias log_begin_msg="echo -n"
194fi
195log_begin_msg "Epoptes-client connecting to $SERVER:$PORT..."
196
197# Call chain:
198#  * if-up.d executes /usr/sbin/epoptes-client
199#  * then socat is called
200#  * after a successful connection, socat exec's /bin/sh
201#  * and the daemon sends /usr/share/epoptes/client-functions to that shell
202
203# Kill all ghost instances of epoptes-client of the same user.
204# That may happen if network connectivity is lost for a while.
205# Standalone workstations don't hang if the network is down, and nbd might cope
206# with that for LTSP clients, but epoptes kills disconnected epoptes-clients.
207# The current epoptes-client is excluded because it starts with /bin/sh.
208pkill -U $UID -f '^epoptes-client$'
209
210# Remember the stdout descriptor to use it in the second phase.
211# stdio will be redirected to the server, but stderr will be kept in the
212# local console, to avoid possible noise from applications started in the
213# background.
214# If the callee needs to grab stderr, it can use `cmd 2>&1`.
215exec 5>&1
216
217# Bash supports launching a program with a different zeroth argument,
218# this makes pgrep'ing for epoptes-client easier.
219cmdline='bash -c \"exec -a epoptes-client sh\"'
220
221# Offer an lts.conf (or environment) variable to disable cert verification.
222if my_boolean_is_true "${EPOPTES_CLIENT_VERIFY_CERTIFICATE:-True}"; then
223    cert_param="cafile=/etc/epoptes/server.crt"
224else
225    cert_param="verify=0"
226fi
227
228# Connect to the server, or keep retrying until the server gets online
229# (for standalone workstations booted before the server).
230if [ -s /etc/epoptes/server.crt ] || [ "$cert_param" = "verify=0" ]; then
231    while [ 1 -eq 1 ]; do
232        socat openssl-connect:$SERVER:$PORT,$cert_param,interval=60,forever EXEC:"$cmdline"
233    done;
234elif [ -f /etc/epoptes/server.crt ]; then
235    while [ 1 -eq 1 ]; do
236        socat tcp:$SERVER:$PORT,interval=60,forever EXEC:"$cmdline",nofork
237    done;
238else
239    die "
240The epoptes certificate file, /etc/epoptes/server.crt, doesn't exist.
241You can fetch the server certificate by running:
242$0 -c"
243fi
Note: See TracBrowser for help on using the repository browser.