Добавил:
degenetard
Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз:
Предмет:
Файл:lab_3 / lab_3
.sh#!/bin/bash
# requires: bash coreutils dialog
# length of [:punct:] regex is calculated by the following command:
# cat /dev/urandom | tr -dc '[:punct:]' | fold -w 1 | head -n 100000 | sort | uniq | wc -l
# a-z: 26
# а-я: 33
# 0-9: 10
# [:punct:]: 32
DIALOG_CANCEL=1
DIALOG_ESC=255
normal_exit() {
clear
echo "Программа завершила свою работу"
exit
}
err_exit() {
clear
echo "Программа аварийно завершила свою работу" >&2
exit 1
}
dialog_codes() {
case $1 in
$DIALOG_CANCEL) normal_exit;;
$DIALOG_ESC) err_exit;;
esac
}
calculate_S_low() {
values=($1)
local S_low="${values[2]} * ${values[1]} / ${values[0]}"
local S2_low=$(echo "${S_low}" | bc)
S_low=$(echo "${S_low}" | bc -l)
if [[ $(echo "${S2_low} < ${S_low}" | bc) == "1" ]]; then
S_low=$(echo "${S2_low} + 1" | bc)
else
S_low="${S2_low}"
fi
echo "${S_low}"
}
calculate_L() {
local S_low=$1
local power=$2
local L=0
local S=0
while [[ $(echo "${S_low} > ${S}" | bc) == "1" ]]; do
((L++))
S=$(echo "${power}^${L}" | bc)
done
echo "${L}"
}
gen_password() {
local L=$1
local regexp=$2
local ru_set=$3
local password=""
if [[ "${regexp}" != "none" ]]; then
password=$(cat /dev/urandom | tr -dc "${regexp}" | fold -w "${L}" | head -n 1)
if [[ "${ru_set}" != "none" ]]; then
local range=$(shuf -i 0-$((L - 1)) -n 1)
local rand_char
for ((i = 0; i <= range; i++)); do
if [[ $(shuf -i 0-1 -n 1) -eq 1 ]]; then
rand_char=$(echo "${ru_set}" | grep -Eio [а-яА-Я] | shuf -n 1)
password=$(echo "${password}" | sed s/\./"${rand_char}"/"$((i + 1))")
fi
done
fi
else
for ((i = 0; i < L; i++)); do
password+=$(echo "${ru_set}" | grep -Eio [а-яА-Я] | shuf -n 1)
done
fi
echo "${password}"
}
print_results() {
exec 3>&1
dialog --yes-label "Сгенерировать другой пароль" --no-label "Выход" --yesno \
"S*: $1\nA: $2\nL: $3\nПароль: $4" 0 0
local exit_status=$?
exec 3>&-
dialog_codes $exit_status
gen_alphabet $1
}
gen_alphabet() {
local ru_set=""
local regexp=""
local power=0
local L
exec 3>&1
local values=($(dialog --ok-label "Далее" --no-cancel --checklist "Выбор алфавита паролей" 0 0 0 \
1 "Латинские большие" 0 \
2 "Латинские маленькие" 0 \
3 "Русские большие" 0 \
4 "Русские маленькие" 0 \
5 "Символы" 0 \
6 "Цифры" 0 \
2>&1 1>&3))
local exit_status=$?
exec 3>&-
dialog_codes $exit_status
for i in "${values[@]}"; do
case $i in
1) ((power += 26)); regexp+="A-Z";;
2) ((power += 26)); regexp+="a-z";;
3) ((power += 33)); ru_set+="АБВГДЕЁЖЗИЙКЛМНОПРСТУФХЦЧШЩЪЫЬЭЮЯ";;
4) ((power += 33)); ru_set+="абвгдеёжзийклмнопрстуфхцчшщъыьэюя";;
5) ((power += 32)); regexp+="[:punct:]";;
6) ((power += 10)); regexp+="0-9";;
esac
done
if [[ ${#ru_set} -eq 0 ]]; then
ru_set="none"
fi
if [[ ${#regexp} -eq 0 ]]; then
regexp="none"
fi
if [[ ${#values[@]} -eq 0 ]]; then
gen_alphabet $1
else
L=$(calculate_L $1 $power)
print_results $1 $power $L $(gen_password $L $regexp $ru_set)
fi
}
data_input_screen() {
exec 3>&1
local values=($(dialog --ok-label "Далее" --no-cancel --form "Ввод исходных данных" 0 0 0 \
"P = " 1 1 "" 1 5 40 0 \
"V = " 2 1 "" 2 5 40 0 \
"T = " 3 1 "" 3 5 40 0 \
2>&1 1>&3))
local exit_status=$?
exec 3>&-
dialog_codes $exit_status
if [[ ${#values[@]} -eq 0 ]]; then
data_input_screen
elif [[ ${#values[@]} -lt 3 ]]; then
exec 3>&1
dialog --ok-label "Назад" --msgbox "Пожалуйста, заполните все поля формы" 0 0
local exit_status=$?
exec 3>&-
dialog_codes $exit_status
data_input_screen
elif [[ ${#values[@]} -eq 3 ]]; then
gen_alphabet $(calculate_S_low "${values[*]}")
else
exec 3>&1
dialog --ok-label "Назад" --msgbox "Не используйте пробел" 0 0
local exit_status=$?
exec 3>&-
dialog_codes $exit_status
data_input_screen
fi
}
data_input_screen