RDP & RDP over SSH automatic connection script

При обслуживании парка машин под управлением операционной системы Windows, немаловажным является возможность быстрого и максимально простого подключения к удаленному рабочему столу. Нередка ситуация, когда подключаться нужно не только с рабочего места, но и находясь удаленно за многие километры от него. Желательно, чтобы местоположение определялось автоматически и, в зависимости от этого, применялись индивидуальные настройки. Для упрощения этой процедуры, был написан небольшой скрипт.

Подключение к удаленному рабочему столу сводится к простому вводу ‘./rdp username’. Имя пользователя можно вводить в любом регистре, пароль и хост удаленной машины автоматически подставляются из простого текстового файла. Скрипт работает из под Mac OS X (OS X) и из под Linux. Для OS X должен быть установлен X Window System (X11). Интерфейс сетевого подключения и внутренний IP адрес так же автоматически определяются в зависимости от операционной системы.

Для примера, подключение к серверу:

./rdp root

Процедура подключения:

Подключение происходит по SSH протоколу через промежуточный Linux сервер (без X-сервера, конечно) в корпоративной локальной сети, на нем запускается rdesktop и отрисовка интерфейса перенаправляется на наш компьютер (X11Forwarding). Трафик шифруется и неплохо сжимается. К тому же, это позволяет подключиться практически из любого места, включая открытые точки доступа, особенно если ssh-server повесить на 443 порт, как правило, его не закрывают на открытых точках и не режут метод CONNECT. Linux сервер с OpenSSH, думаю, можно заменить Windows сервером с установленным FreeSSHD, к примеру, но для этого придется поменять процедуру подключения, сделав форвадинг портов и запуская rdesktop-клиент локально, этот вариант мне неинтересен, при необходимости любой сможет самостоятельно поправить скрипт. Можно обойтись и без промежуточного сервера, конечно, об этом ниже.

Код скрипта rdp:

#!/bin/bash
# ----------------------------------------------
# RDP & RDP over SSH automatic connection script
# Written by ZeroChaos
# Version 1.0, 2012-08-04
# Site: https://zerolab.net/
# ----------------------------------------------
# My location
DIR=$(dirname "$0")
# Determine the OS
OSTYPE=`uname`
if [ "$OSTYPE" = "Darwin" ]; then
    # Network interface
    NETINT_MAC="en0 en1 en2 en3"
    for NETINT in `echo $NETINT_MAC`; do
        IFACE=`ifconfig $NETINT 2>/dev/null | grep -q 'inet ' && echo $NETINT`
        if [ "$IFACE" != "" ]; then
            MYNETINT="$IFACE"
        fi
    done
    # Get IP
    MYIP=`ifconfig $MYNETINT | grep 'inet ' | awk '{ print $2 }'`
elif [ "$OSTYPE" = "Linux" ]; then
    # Network interface
    NETINT_LINUX="eth0 eth1 eth2 eth3"
    for NETINT in `echo $NETINT_LINUX`; do
        IFACE=`ifconfig $NETINT 2>/dev/null | grep -q 'inet addr' && echo $NETINT`
        if [ "$IFACE" != "" ]; then
            MYNETINT="$IFACE"
        fi
    done
    # Get IP
    MYIP=`ifconfig $MYNETINT | grep 'inet addr' | awk '{ print $2 }' | awk -F: '{ print $2 }'`
else
    OSTYPEERR="1"
    echo "---------------------------------------------------"
    echo " Unable to determine the type of operating system! "
    echo "---------------------------------------------------"
fi
if [ "$OSTYPEERR" != "1" ]; then
    # Work or Home?
    # IP's variables
    source $DIR/var/ip.txt
    if [ "$MYIP" = "$WORK" ]; then
        MYDIR="$DIR/var/work"
    elif [ "$MYIP" = "$HOME" ]; then
        MYDIR="$DIR/var/home"
    else
        echo "----------------------------------------"
        echo " Error when comparing the IP addresses! "
        echo "----------------------------------------"
    fi
 # Other variables
    source $MYDIR/host.txt
    source $DIR/var/dc.txt
    source $MYDIR/resolution.txt
    USERNAME=`echo $1 | tr '[:upper:]' '[:lower:]'`
 # RDP connection to the host
    while read LINE; do
        IFS=";"
        set -- $LINE
        USER="$1"
        PASSWORD="$2"
        IP="$3"
        TRUSER=`echo $1 | tr '[:upper:]' '[:lower:]'`
            if [ "$USERNAME" = "$TRUSER" ]; then
                source $DIR/var/command.txt
            fi
    done < $DIR/var/list.txt
fi

Сохраните содержимое в файл 'rdp' и дайте права на выполнение:

chmod 755 rdp

Создайте каталог 'var' рядом со скриптом и положите в него файлы 'command.txt', 'dc.txt', 'ip.txt' и 'list.txt'. Формат файлов представлен ниже.

Подключение к удаленному рабочему столу command.txt:

ssh -YC $HOST rdesktop -u $USER -d $DC -p $PASSWORD -k en-us -r clipboard:CLIPBOARD $IP -g $RESOLUTION

Наш контроллер домена dc.txt:

DC="corp.zerolab.net"

Рабочий и домашний IP адреса ip.txt:

WORK="192.168.0.5"
HOME="192.168.1.4"

Список пользователей, паролей и хостов с разделителем в виде ';' list.txt:

root;password1;192.168.0.4
User1;password2;192.168.0.6
User2;password3;192.168.0.7
User3;password4;192.168.0.8
User4;password5;192.168.0.9
User5;password6;192.168.0.10
User145;password146;192.168.0.150
# [do not delete this string]

В каталоге 'var' создаем еще 2 каталога: 'home' и 'work'. В них создаем файлы 'host.txt' и 'resolution.txt'. Их содержимое:

Настройки для домашнего компьютера home/host.txt:

HOST="[email protected]"

home/resolution.txt:

RESOLUTION="1236x755"

Настройки для рабочего компьютера work/host.txt:

HOST="[email protected]"

work/resolution.txt:

RESOLUTION="1632x1005"

Структура каталога со скриптом:

Для SSH авторизации советую воспользоваться беспарольным вариантом, т.е. авторизацией по ключу. Для этого сгенерируйте пару public/private rsa key и передайте public key на удаленный сервер, выступающий у нас в роли шлюза. На промежуточном сервере не забудьте установить rdesktop.

sudo apt-get install rdesktop

Этот скрипт можно использовать и без промежуточного Linux/Windows сервера и протокола SSH, соответственно, при том, что Вы подключаетесь с рабочего места в своей локальной сети или через VPN-туннель. Если Вы работаете под операционной системой Linux, просто измените команду в 'command.txt', убрав в начале 'ssh -YC $HOST'. Приятной и продуктивной Вам работы.

Добавлено: 08.08.2011

Скрипт немного доработан, теперь пользователь выбирается из списка. Если это кому-то покажется более удобным чем предыдущий вариант, пользуйтесь. Список автоматически строится все из того же текстового файла 'list.txt'.

Вызов скрипта:

./rdp

Код скрипта rdp:

#!/bin/bash
# ----------------------------------------------
# RDP & RDP over SSH automatic connection script
# Written by ZeroChaos
# Version 1.1, 2012-08-08
# Site: https://zerolab.net/
# ----------------------------------------------
# My location
DIR=$(dirname "$0")
# Determine the OS
OSTYPE=`uname`
if [ "$OSTYPE" = "Darwin" ]; then
    # Network interface
    NETINT_MAC="en0 en1 en2 en3"
    for NETINT in `echo $NETINT_MAC`; do
        IFACE=`ifconfig $NETINT 2>/dev/null | grep -q 'inet ' && echo $NETINT`
        if [ "$IFACE" != "" ]; then
            MYNETINT="$IFACE"
        fi
    done
    # Get IP
    MYIP=`ifconfig $MYNETINT | grep 'inet ' | awk '{ print $2 }'`
elif [ "$OSTYPE" = "Linux" ]; then
    # Network interface
    NETINT_LINUX="eth0 eth1 eth2 eth3"
    for NETINT in `echo $NETINT_LINUX`; do
        IFACE=`ifconfig $NETINT 2>/dev/null | grep -q 'inet addr' && echo $NETINT`
        if [ "$IFACE" != "" ]; then
            MYNETINT="$IFACE"
        fi
    done
    # Get IP
    MYIP=`ifconfig $MYNETINT | grep 'inet addr' | awk '{ print $2 }' | awk -F: '{ print $2 }'`
else
    OSTYPEERR="1"
    echo "---------------------------------------------------"
    echo " Unable to determine the type of operating system! "
    echo "---------------------------------------------------"
fi
if [ "$OSTYPEERR" != "1" ]; then
    # Work or Home?
    # IP's variables
    source $DIR/var/ip.txt
    if [ "$MYIP" = "$WORK" ]; then
        MYDIR="$DIR/var/work"
    elif [ "$MYIP" = "$HOME" ]; then
        MYDIR="$DIR/var/home"
    else
        echo "----------------------------------------"
        echo " Error when comparing the IP addresses! "
        echo "----------------------------------------"
    fi
    # Other variables
    source $MYDIR/host.txt
    source $DIR/var/dc.txt
    source $MYDIR/resolution.txt
    # Function for user choice
    PS3='Выберите пользователя: '
    userchoice() {
        eval set $USERARR
        select USER; do
            USERNAME=$USER
            break
        done
    }
    # Read the list of users
    while read LINE; do
        IFS=";"
        set -- $LINE
        USERARR="$USERARR $1"
    done < $DIR/var/list.txt

    # User choice
    userchoice $USERARR

    # RDP connection to the host
    USERLINE=`grep "$USERNAME" < $DIR/var/list.txt`
    IFS=";"
    set -- $USERLINE
    USER="$1"
    PASSWORD="$2"
    IP="$3"
    echo "Пользователь: $USER"
    echo "IP: $IP"
    source $DIR/var/command.txt
fi