diff options
Diffstat (limited to 'etc/smartauth/smartauthmon.sh.in')
-rw-r--r-- | etc/smartauth/smartauthmon.sh.in | 583 |
1 files changed, 0 insertions, 583 deletions
diff --git a/etc/smartauth/smartauthmon.sh.in b/etc/smartauth/smartauthmon.sh.in deleted file mode 100644 index ebf360a..0000000 --- a/etc/smartauth/smartauthmon.sh.in +++ /dev/null @@ -1,583 +0,0 @@ -#!/bin/bash - -# Smart Card TDE Authentication Script (c) 2010-2011 Timothy Pearson -# -# 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/>. - -# Maximum number of virtual terminals on this system -MAXIMUM_VTS=49 - -# The [secure] temporary directory for authentication -SECURE_DIRECTORY=/tmp/smartauth - -hexcvt () -{ - echo ""$1" "16" o p" | dc -} - -# Create the secure directory and lock it down -rm -rf $SECURE_DIRECTORY -mkdir -p $SECURE_DIRECTORY -chown root $SECURE_DIRECTORY -chgrp root $SECURE_DIRECTORY -chmod 600 $SECURE_DIRECTORY -SECURE_DIRECTORY=$(mktemp /tmp/smartauth/smartauthmon.XXXXXXXXXX) -rm -rf $SECURE_DIRECTORY -mkdir -p $SECURE_DIRECTORY -chown root $SECURE_DIRECTORY -chgrp root $SECURE_DIRECTORY -chmod 600 $SECURE_DIRECTORY - -# Restart PCSCD and kill spurious processes -killall -9 pcscd -/etc/init.d/pcscd restart -/etc/init.d/pcscd-nodbus restart - -# See if required programs are installed -scriptor=$(whereis scriptor) -if [[ $scriptor == "scriptor:" ]]; then - echo "ERROR: scriptor is not installed! This program cannot continue!" - exit -fi -opensc=$(whereis opensc-explorer) -if [[ $opensc == "opensc-explorer:" ]]; then - echo "ERROR: opensc-explorer is not installed! This program cannot continue!" - exit -fi - -get_file () { - if [[ $COMMAND_MODE == "acos" ]]; then - # Select EF $1 under DF 1000 - echo "$SELECT_FILE $1" > $SECURE_DIRECTORY/query - scriptor $SECURE_DIRECTORY/query 1> $SECURE_DIRECTORY/response2 - echo $(cat $SECURE_DIRECTORY/response2) - - # Read binary - echo "$READ_BINARY" > $SECURE_DIRECTORY/query - scriptor $SECURE_DIRECTORY/query 1> $SECURE_DIRECTORY/response2 - authokresponse="90 00 : Normal processing" - response1=$(cat $SECURE_DIRECTORY/response2 | grep "$authokresponse") - if [[ $response1 != "" ]]; then - cat $SECURE_DIRECTORY/response2 | tr -d '\n' > $SECURE_DIRECTORY/response4 - stringtoreplace="Using T=0 protocol00 B0 00 00 FF> 00 B0 00 00 FF< " - newstring="" - sed -i "s#${stringtoreplace}#${newstring}#g" $SECURE_DIRECTORY/response4 - stringtoreplace=" 90 00 : Normal processing." - newstring="" - sed -i "s#${stringtoreplace}#${newstring}#g" $SECURE_DIRECTORY/response4 - if [[ $2 == "text" ]]; then - stringtoreplace=" 00" - newstring="" - sed -i "s#${stringtoreplace}#${newstring}#g" $SECURE_DIRECTORY/response4 - fi - echo $(cat $SECURE_DIRECTORY/response4) - rm -f $SECURE_DIRECTORY/lukskey - xxd -r -p $SECURE_DIRECTORY/response4 $SECURE_DIRECTORY/lukskey - RESPONSE=$SECURE_DIRECTORY/lukskey - fi - fi - - if [[ $COMMAND_MODE == "cryptoflex" ]]; then - FILE=${1/ /} - echo "get $FILE" | opensc-explorer - RESPONSE="3F00_$FILE" - fi -} - -update_file () { - if [[ $COMMAND_MODE == "acos" ]]; then - # Select EF $1 under DF 1000 - echo "$SELECT_FILE $1" > $SECURE_DIRECTORY/query - scriptor $SECURE_DIRECTORY/query 1> $SECURE_DIRECTORY/response2 - echo $(cat $SECURE_DIRECTORY/response2) - - # Update existing file - # Zero pad input file - dd if=/dev/zero of=$SECURE_DIRECTORY/response2 bs=1 count=255 - dd if=$2 of=$SECURE_DIRECTORY/response2 bs=1 count=255 conv=notrunc - - # Truncate to 255 bytes and expand to standard hex listing format - xxd -l 255 -ps -c 1 $SECURE_DIRECTORY/response2 > $SECURE_DIRECTORY/response - cat $SECURE_DIRECTORY/response | tr '\n' ' ' > $SECURE_DIRECTORY/hexready - echo "$UPDATE_BINARY $(cat $SECURE_DIRECTORY/hexready)" > $SECURE_DIRECTORY/query - scriptor $SECURE_DIRECTORY/query 1> $SECURE_DIRECTORY/response2 2>/dev/null - echo $(cat $SECURE_DIRECTORY/response2) - fi - - if [[ $COMMAND_MODE == "cryptoflex" ]]; then - # Delete old file - echo "$DELETE_FILE $1" > $SECURE_DIRECTORY/query - scriptor $SECURE_DIRECTORY/query 1> $SECURE_DIRECTORY/response2 2>/dev/null - echo $(cat $SECURE_DIRECTORY/response2) - - # Create new file - createfile "FF" $1 - FILE=${1/ /} - echo "put $FILE $2" | opensc-explorer - fi -} - -oldsmartcard_username="" -echo "Ready..." -while [[ 1 == 1 ]]; do - sleep 1 - echo "exit" | scriptor 2>/dev/null 1>/dev/null - OUTPUT=$? - if [[ $OUTPUT -eq 0 ]]; then - echo "Card inserted!" - echo "TAuthenticating SmartCard..." > /tmp/tdesocket-global/kdesktoplockcontrol & - - # Get card ATR - echo "RESET" > $SECURE_DIRECTORY/query - scriptor $SECURE_DIRECTORY/query 1> $SECURE_DIRECTORY/response2 - authokresponse="OK: " - response1=$(cat $SECURE_DIRECTORY/response2 | grep "$authokresponse") - if [[ $response1 != "" ]]; then - cat $SECURE_DIRECTORY/response2 | tr -d '\n' > $SECURE_DIRECTORY/response4 - stringtoreplace="Using T=0 protocolRESET> RESET< OK: " - newstring="" - sed -i "s#${stringtoreplace}#${newstring}#g" $SECURE_DIRECTORY/response4 - smartatr=$(cat $SECURE_DIRECTORY/response4) - echo "Got ATR: $smartatr" - if [[ $smartatr == "3B BE 18 00 00 41 05 10 00 00 00 00 00 00 00 00 00 90 00 " ]]; then - echo "Detected ACOS5 card" - COMMAND_MODE="acos" - fi - if [[ $smartatr == "3B 02 14 50 " ]]; then - echo "Detected Schlumberger CryptoFlex card" - COMMAND_MODE="cryptoflex" - fi - else - echo "No card detected!" - fi - - if [[ $COMMAND_MODE == "cryptoflex" ]]; then - GET_CHALLENGE="C0 84 00 00 08" - EXTERNAL_AUTH="C0 82 00 00 07 01" - SELECT_FILE="C0 A4 00 00 02" - DELETE_FILE="F0 E4 00 00 02" - fi - - if [[ $COMMAND_MODE == "acos" ]]; then - GET_CHALLENGE="00 84 00 00 08" - EXTERNAL_AUTH="00 82 00 82 08" # Key 2 - SELECT_FILE="00 A4 00 00 02" - DELETE_FILE="00 E4 00 00 00" - READ_BINARY="00 B0 00 00 FF" - UPDATE_BINARY="00 D6 00 00 FF" - ACTIVATE_FILE="00 44 00 00 02" - fi - - # Authenticate card - - if [[ $COMMAND_MODE == "acos" ]]; then - # Select MF - echo "00 A4 00 00 00" > $SECURE_DIRECTORY/query - scriptor $SECURE_DIRECTORY/query 1> $SECURE_DIRECTORY/response2 - echo $(cat $SECURE_DIRECTORY/response2) - - # Select DF 1000 under MF - echo "$SELECT_FILE 10 00" > $SECURE_DIRECTORY/query - scriptor $SECURE_DIRECTORY/query 1> $SECURE_DIRECTORY/response2 - echo $(cat $SECURE_DIRECTORY/response2) - fi - - echo $GET_CHALLENGE > $SECURE_DIRECTORY/authscript - - scriptor $SECURE_DIRECTORY/authscript | grep 'Normal processing' > $SECURE_DIRECTORY/challenge - perl -pi -e 's/ //g' $SECURE_DIRECTORY/challenge - perl -pi -e 's/:Normalprocessing.//g' $SECURE_DIRECTORY/challenge - perl -pi -e 's/<//g' $SECURE_DIRECTORY/challenge - xxd -r -p $SECURE_DIRECTORY/challenge $SECURE_DIRECTORY/challenge - - # Now DES encrypt the challenge - # Later, change the initialization vector to random if possible - openssl des-ecb -in $SECURE_DIRECTORY/challenge -out $SECURE_DIRECTORY/response -K <your key in hexadecimal> -iv 1 - - if [[ $COMMAND_MODE == "acos" ]]; then - # Truncate to 8 bytes - dd if=$SECURE_DIRECTORY/response of=$SECURE_DIRECTORY/response2 bs=1 count=8 - - # Expand to standard hex listing format - xxd -g 1 $SECURE_DIRECTORY/response2 $SECURE_DIRECTORY/response - dd if=$SECURE_DIRECTORY/response of=$SECURE_DIRECTORY/response2 bs=1 count=23 skip=9 - fi - - if [[ $COMMAND_MODE == "cryptoflex" ]]; then - # Truncate to 6 bytes - dd if=$SECURE_DIRECTORY/response of=$SECURE_DIRECTORY/response2 bs=1 count=6 - - # Expand to standard hex listing format - xxd -g 1 $SECURE_DIRECTORY/response2 $SECURE_DIRECTORY/response - dd if=$SECURE_DIRECTORY/response of=$SECURE_DIRECTORY/response2 bs=1 count=17 skip=9 - fi - - # Assemble the response file - response2=$(cat $SECURE_DIRECTORY/response2) - response1="$EXTERNAL_AUTH ${response2}" - echo $response1 > $SECURE_DIRECTORY/response - - # Send the response! - scriptor $SECURE_DIRECTORY/response > $SECURE_DIRECTORY/response2 - - # Get the result - authokresponse="< 90 00 : Normal processing" - response1=$(cat $SECURE_DIRECTORY/response2 | grep "$authokresponse") - echo $response1 - if [[ $response1 != "" ]]; then - echo "Smart card validation successfull!" - # Get username and password - get_file "10 02" "text" - smartcard_username=$(cat $RESPONSE) - get_file "10 03" "text" - mv $RESPONSE $SECURE_DIRECTORY/password - get_file "10 04" "text" - smartcard_slave=$(cat $RESPONSE) - if [[ $smartcard_slave == "SLAVE" ]]; then - get_file "10 05" "text" - smartcard_minutes=$(cat $RESPONSE) - get_file "10 06" "text" - internet_minutes=$(cat $RESPONSE) - fi - else - echo "This card does not recognize this system!" - echo "EInvalid SmartCard Inserted" > /tmp/tdesocket-global/kdesktoplockcontrol & - sleep 1 - smartcard_username="" - rm -f $SECURE_DIRECTORY/password - smartcard_slave="" - fi - - if [[ $smartcard_slave == "SLAVE" ]]; then - if [[ $smartcard_minutes == "" ]]; then - smartcard_minutes=1 - fi - - # Decrement minutes on card - if [[ $smartcard_minutes -gt 0 ]]; then - let "smartcard_minutes=smartcard_minutes-1" - echo $smartcard_minutes > $SECURE_DIRECTORY/minutes - update_file "10 05" "$SECURE_DIRECTORY/minutes" - fi - - if [[ $smartcard_minutes -eq 0 ]]; then - echo "Minutes have been used up!" - # Prohibit logon - smartcard_username="" - rm $SECURE_DIRECTORY/password - fi - - mkdir -p /etc/smartmon - echo $smartcard_minutes > /etc/smartmon/minutesremaining - chmod 755 /etc/smartmon/minutesremaining - fi - - # Initialize variables - loginok=1 - - # Try to do the authentication - result="" - timeout=0 - errcode=0 - waserror=0 - noactivesessions=0 - - $result=$(/opt/trinity/bin/tdmctl -g list) - if [[ $result == "ok" ]]; then - noactivesessions=1 - result="okbutempty" - fi - echo $result - resultbkp=$result - - if [[ $errcode -eq 0 ]]; then - # Allow TDM to finish starting - if [[ $waserror -eq 1 ]]; then - sleep 10 - fi - - # Zero the desktop array - index=0 - while [[ $index != $MAXIMUM_VTS ]]; do - darray[index]="" - index=$((index+1)) - done - - if [[ result != "okbutempty" ]]; then - posone="0" - posone=$(expr index "$result" " :") - postwo="0" - postwo=$(expr index "$result" ",") - while [[ $posone != "0" ]]; do - length=$((postwo-posone-1)) - terminals="${result:posone:length}" - echo $terminals - - # Delete the terminal we just got from the list of terminals - result="${result:postwo}" - postwo=$(expr index "$result" ",") - result="${result:postwo}" - postwo=$(expr index "$result" ",") - length=$((postwo-1)) - username="${result:0:length}" - darray[terminals]=$username # Save username of this terminal - echo $username - result="${result:postwo}" - postwo=$(expr index "$result" ",") - result="${result:postwo}" - - # Now see if there might be ANOTHER terminal active or not - posone="0" - posone=$(expr index "$result" " :") - postwo="0" - postwo=$(expr index "$result" ",") - done - fi - - # See if the desired user is already logged in - index=0 - foundsession=0 - while [[ $index != $MAXIMUM_VTS ]]; do - if [[ ${darray[index]} == $smartcard_username ]]; then - if [[ ${darray[index]} != "" ]]; then - echo "Found existing session on desktop: ${index}" - foundsession=1 - # Check password - lverify=$(/usr/bin/smartauthckpasswd -u ${darray[index]} -p $(cat $SECURE_DIRECTORY/password)) - cverify="User:${darray[index]}" - udisplay=":${index}" - if [[ $lverify == $cverify ]]; then - su $smartcard_username -c "export DISPLAY=$udisplay; /opt/trinity/bin/dcop kdesktop KScreensaverIface quit" - su $smartcard_username -c "export DISPLAY=$udisplay; /opt/trinity/bin/dcop kdesktop KScreensaverIface enable false" - /opt/trinity/bin/tdmctl activate $udisplay - else - echo "EUnauthorized SmartCard Inserted" > /tmp/tdesocket-global/kdesktoplockcontrol & - fi - else - echo "Username not specified" - foundsession=2 - sleep 1 - fi - fi - index=$((index+1)) - done - - if [[ $foundsession == "0" ]]; then - echo "Existing session not found, starting new..." - - # Make sure that this is not display :0 (default login screen). - # If it is, execute login. If not, create new session, then execute login - usebasedisplay=0 - if [[ $noactivesessions -eq 1 ]]; then - newdisplay=$(ls /var/run/xdmctl/ | grep 'xdmctl-:0') - echo $newdisplay - if [[ $newdisplay != "" ]]; then - usebasedisplay=1 - fi - fi - vtsessions=$(echo "$resultbkp" | grep ',vt') - if [[ $vtsessions == "" ]]; then - newdisplay=$(ls /var/run/xdmctl/ | grep 'xdmctl-:0') - echo $newdisplay - if [[ $newdisplay != "" ]]; then - usebasedisplay=1 - fi - fi - - echo "Creating new session" - # Attempt login - ls /var/run/xdmctl > $SECURE_DIRECTORY/originalxdm - - # Set loop separator to end of line - BAKIFS=$IFS - IFS=$(echo -en "\n\b") - exec 3<&0 - exec 0<"$SECURE_DIRECTORY/originalxdm" - newdisplayfound=0 - newdisplay=-1 - while read -r line - do - # use $line variable to process lines - line=$(echo $line | grep 'xdmctl-:' | sed -e 's/xdmctl-://') - if [ "`expr $line - $line 2>/dev/null`" == "0" ]; then - echo "Found active display on $line" - if [[ $newdisplayfound -eq 0 ]]; then - tempnewdisplay=$((newdisplay + 1)) - if [[ $line -eq $tempnewdisplay ]]; then - echo "Sequential display $line found after display $newdisplay..." - newdisplay=$line - fi - fi - fi - done - exec 0<&3 - newdisplay=$(($newdisplay + 1)) - newdisplay=":$newdisplay" - echo "The next display to start will be $newdisplay" - rm $SECURE_DIRECTORY/originalxdm - - /opt/trinity/bin/tdmctl -g reserve - /opt/trinity/bin/tdmctl -g login $newdisplay now $smartcard_username $(cat $SECURE_DIRECTORY/password) - sleep 2 - /opt/trinity/bin/tdmctl -g activate $newdisplay - udisplay=$newdisplay - fi - - if [[ $smartcard_slave == "SLAVE" ]]; then - if [[ $smartcard_minutes -lt 5 ]]; then - su $smartcard_username -c "export DISPLAY=$udisplay; zenity --warning --text 'You have less than 5 minutes of computer time remaining' || exit 0" & - fi - fi - - rm -f $SECURE_DIRECTORY/password - - #if [[ loginok -eq 1 ]]; then - # Wait for SmartCard removal - echo "C" > /tmp/tdesocket-global/kdesktoplockcontrol & - TIMER=60 - OUTPUT=0 - - while [[ $OUTPUT -eq 0 ]]; do - sleep 1 - su $smartcard_username -c "export DISPLAY=$udisplay; /opt/trinity/bin/dcop kdesktop KScreensaverIface quit" - su $smartcard_username -c "export DISPLAY=$udisplay; /opt/trinity/bin/dcop kdesktop KScreensaverIface enable false" - echo "exit" | scriptor 2>/dev/null 1>/dev/null - OUTPUT=$? - if [[ $smartcard_slave == "SLAVE" ]]; then - TIMER=$(( TIMER - 1 )) - if [[ $TIMER -eq 0 ]]; then - # 60 seconds have passed, decrement minutes on card - let "smartcard_minutes=smartcard_minutes-1" - echo $smartcard_minutes > /etc/smartmon/minutesremaining - chmod 755 /etc/smartmon/minutesremaining - - TIMER=60 - - echo $smartcard_minutes > $SECURE_DIRECTORY/minutes - update_file "10 05" "$SECURE_DIRECTORY/minutes" - - if [[ $smartcard_minutes -eq 0 ]]; then - echo "Minutes have been used up!" - # Prohibit logon - smartcard_username="" - rm $SECURE_DIRECTORY/password - fi - - mkdir -p /etc/smartmon - echo $smartcard_minutes > /etc/smartmon/minutesremaining - chmod 755 /etc/smartmon/minutesremaining - - if [[ $smartcard_minutes -eq 5 ]]; then - su $smartcard_username -c "export DISPLAY=$udisplay; zenity --warning --text 'You have less than 5 minutes of computer time remaining' || exit 0" & - fi - - if [[ $smartcard_minutes -eq 0 ]]; then - echo "Minutes have been used up!" - echo "Beginning logoff process" - OUTPUT=254 - fi - fi - fi - done - - echo "Card removed!" - - # Is the user still logged in? - result="ok" - timeout=0 - errcode=0 - $result=$(/opt/trinity/bin/tdmctl -g list) - if [[ $result == "ok" ]]; then - noactivesessions=1 - result="okbutempty" - fi - echo $result - - # Zero the desktop array - index=0 - while [[ $index != $MAXIMUM_VTS ]]; do - darray[index]="" - index=$((index+1)) - done - - posone="0" - posone=$(expr index "$result" " :") - postwo="0" - postwo=$(expr index "$result" ",") - while [[ $posone != "0" ]]; do - length=$((postwo-posone-1)) - terminals="${result:posone:length}" - echo $terminals - - # Delete the terminal we just got from the list of terminals - result="${result:postwo}" - postwo=$(expr index "$result" ",") - result="${result:postwo}" - postwo=$(expr index "$result" ",") - length=$((postwo-1)) - username="${result:0:length}" - darray[terminals]=$username # Save username of this terminal - echo $username - result="${result:postwo}" - postwo=$(expr index "$result" ",") - result="${result:postwo}" - - # Now see if there might be ANOTHER terminal active or not - posone="0" - posone=$(expr index "$result" " :") - postwo="0" - postwo=$(expr index "$result" ",") - done - - # See if the desired user is still logged in - index=0 - foundsession=0 - while [[ $index != $MAXIMUM_VTS ]]; do - if [[ ${darray[index]} == $smartcard_username ]]; then - if [[ ${darray[index]} != "" ]]; then - echo "Found existing session on desktop: ${index}" - udisplay=":${index}" - foundsession=1 - errcode=1 - timeout=0 - blankresult="" - while [[ $blankresult != "true" ]]; do - /opt/trinity/bin/tdmctl -g activate $udisplay - su $smartcard_username -c "export DISPLAY=$udisplay; /opt/trinity/bin/dcop kdesktop KScreensaverIface enable true" - su $smartcard_username -c "export DISPLAY=$udisplay; /opt/trinity/bin/dcop kdesktop KScreensaverIface lock" - blankresult=$(su $smartcard_username -c "export DISPLAY=$udisplay; /opt/trinity/bin/dcop kdesktop KScreensaverIface isBlanked") - if [[ $? != 0 ]]; then - blankresult="true" - fi - logouttest=$(echo $blankresult | grep 'target display has no VT assigned') - if [[ "$logouttest" != "" ]]; then - echo "User has logged out" - blankresult="true" - fi - done - else - echo "Username not specified!" - sleep 1 - fi - fi - index=$((index+1)) - done - #fi - fi - - smartcard_username="" - rm -rf /etc/smartmon/minutesremaining - echo "C" > /tmp/tdesocket-global/kdesktoplockcontrol & - fi -done |