Linux: Неинтерактивный пользователь

Что это, зачем, и как это может понадобиться?

Если мы посмотрим на список пользователей в Linux сразу после установки, мы, кроме root, nobody (пользователя с максимально ограниченными правами) и своего пользователя, увидим множество пользователей, созданных под конкретную подсистему или задачу, например: bin, daemon, adm, operator, games, sshd, usbmux, sddm, pulse, apache, messagebus и т.д.

Для чего это сделано? Если кратко — для безопасности, под каждую задачу, от запуска отдельной программы, до управления отдельной подсистемой, создается отдельный пользователь, который, даже если его взломает злоумышленник, не сможет получить доступ ко всей системе. Т.е. хакнули пользователя apache, и у нас сдох только web-сервер Apache, админ нашел сбой, пропатчил, починил, перезапустил нужное — и все опять работает.

А почему пользователь неинтерактивный? Опять же, для безопасности, ваш пользователь, или же root, интерактивные, они имеют доступ к терминалу, т.е. могут вводить команды и запускать другие программы из терминала/консоли. Но и в самом терминале и в программах, может обнаружиться ошибка, которая позволит получить пользователю получить нужные права, чтоб в системе навредить. Для того пользователю с ограниченными задачами и отключают доступ к терминалу, т.е., делают его неинтерактивным.

Как создать неинтерактивного пользователя?

Итак, начнем это делать на нашей тестовой системе.
Для начала создадим группу для тестовых пользователей, стандартной командой addgroup. Выполнять надо из-под root (или через sudo, зависит от вашей системы), больше не буду на этом останавливаться.

groupadd testgrp

С помощью useradd

1. Самый простой способ:

useradd -g testgrp -d /dev/null -s /bin/false testusr1

где:
-g testgrp — задать основную группу пользователя (вышесозданную testgrp)
-d /dev/null — задать в качестве расположения домашнего каталога нуль-устройство (/dev/null)
-s /bin/false — установить фиктивную оболочку (/bin/false).
testusr1 — имя пользователя

Если опцию -d не указать, система укажет для пользователя домашний каталог, как подкаталог с таким же именем, как имя пользователя, в /home, хотя и не создаст его.

Это максимально неинтерактивный пользователь, у него не только установлена фиктивная оболочка (обычным пользователям устанавливают оболочку, например /bin/bash) но также не установлен домашний каталог, т.е. пользователю просто некуда входить в системе, а также не установлен пароль. С пустым паролем Linux не пустит пользователя, впрочем, об этом ниже.

Если попытаться зайти в систему от имени этого пользователя, то получим ошибку Access denied:
login as: testusr1
testusr1@192.168.1.133's password:
Access denied
testusr1@192.168.1.133's password:

2. Если неинтерактивному пользователю все-таки нужен домашний каталог, например, для хранения конфигураций запускаемых от его имени программ, то домашний каталог вполне можно создать:

useradd -g testgrp -m -d /home/testusr2 -s /bin/false testusr2

К опциям -g, -s и -d добавляется опция
-m — автоматически создать пользовательский каталог

С помощью скрипта adduser

Скрипт adduser, это оболочка над программой useradd, который позволяет указать параметры нового пользователя в диалоговом режиме

Пример создания неинтерактивного пользователя:

Простыня с переводом под катом

Удобно, красиво, не надо вручную писать опции в командной строке, хотя простыня. Но можно и так, главное, не забыть про фиктивную оболочку /bin/false и, при надобности, пустой пароль.

О «пустых» паролях

Каждому пользователю в Linux, который хочет получить доступ к терминалу или графической оболочке, должен быть присвоен пароль. Можно провести наглядный эксперимент.

1. Создадим с помощью скрипта adduser нового пользователя testusr4, только оставим ему некоторые параметры по умолчанию, т.е. домашний каталог и оболочку /bin/bash, изменим только группу на testgrp и зададим ему пароль.

2. Попробуем залогиниться:

login as: testusr4
testusr4@192.168.1.133's password:
testusr4@smallwolfie:~$

Получилось!

3. Выйдем из учетной записи и отредактируем файл /etc/shadow в котором хранятся пароли пользователей (редактируем от имени root):
— Найдем строчку, содержащую информацию о пароле пользователя testusr4:

testusr4:$5$eUbahK8EwlYtD1Nw$ZCH7sMkg.fTwe/KsqfBh6.xrlo3K4V6WinyiqWhW5.8:19689:0:99999:7:::

— Приведем ее к такому же виду, что у пользователя, например, testusr1:

Т.е. вместо хэша и других свойств пароля, находящегося между вторым и третьим двоеточием, впишем символ восклицательного знака, тем самым удалив их.

login as: testusr4
testusr4@192.168.1.133's password:
Access denied

Подробнее прочесть о формате файлов /etc/passwd и /etc/shadow Копия в PDF

Как отобрать интерактивность у уже созданного интерактивного пользователя?

Предположим, у нас есть интерактивный пользователь testusr5 и эту интерактивность надо пользователю отключить:

1. Лишить возможности пользователя входить по паролю, как это было описано выше.
2. Отредактировать файл /etc/passwd, найдя строку пользователя:

testusr5:x:1016:1008:,,,:/home/testusr5:/bin/bash

И заменить указанную оболочку (/bin/bash) на фиктивную (/bin/false):

testusr5:x:1016:1008:,,,:/home/testusr5:/bin/false

Можно заменить запись о домашнем каталоге на /dev/null, если он не нужен, а сам каталог потом удалить с диска:

testusr5:x:1016:1008:,,,:/dev/null:/bin/false

Пользователь «одного скрипта»

Интересно, что пользователю в качестве оболочки можно подсунуть не только фиктивную оболочку или обычный shell (bash, sh, zsh и т.д.) но и конкретный скрипт. Тогда, при входе этого пользователя в систему, будет выполняться только этот самый скрипт. Главное, чтоб у пользователя были права на его исполнение.

Примечание: Хоть это уже не совсем «неинтерактивный» пользователь, но ради обобщения, пусть будет тут.

Внимание! Делайте нечто подобное, когда точно уверены в своих действиях. Если злоумышленник сможет подкорректировать такой скрипт, то сможет и нагадить в системе.

Пример:

1. Создадим интерактивного пользователя с домашним каталогом, например, testusr6, не забыв задать пароль.
2. Залогинимся от имени этого пользователя
3. В домашнем каталоге напишем простой тестовый скрипт и дадим ему права на исполнение от имени этого пользователя.

#!/bin/bash

echo "Hello, world!"
echo "Press ENTER..."
read

4. Выйдем из системы этим пользователем, и от имени root отредактируем /etc/passwd таким образом.

Было:

testusr6:x:1017:1008:,,,:/home/testusr6:/bin/bash

Стало:

testusr6:x:1017:1008:,,,:/home/testusr6:/home/testusr6/hello

5. Теперь попробуем войти в систему от имени testusr6:

login as: testusr6
testusr6@192.168.1.133's password:
Hello, world!
Press ENTER...

После нажатия ENTER сеанс завершится.

Как подобную фичу можно использовать на практике, описано здесь: Удаленная перезагрузка сервера под управлением Linux. Перезагрузка Linux без ввода пароля. (копия)

Сбой при пересборке ядра Linux (Puppy Slacko)

Прямая ссылка

Сбой при пересборке ядра Linux (Puppy Slacko) без включения поддержки UnionFS в ядре.

Видеоиллюстрация для лекции, потому что не уверен, будет ли возможность завтра пересобирать криво и прямо ядро перед аудиторией, и пропустят ли туда с личным ноутом. Интернеты есть, а пример хороший, пусть лежит, Ютуб резиновый.

Впрочем, если кому-то вдруг понадобится почитать, где именно это в реале встретилось, то вот (копия)

Slackware: Краткая инструкция по настройке Samba

Ну мало ли.

Кто не знает, что это такое. Если говорить по рабоче-крестьянски, инструкция о том, как расшарить в локальную сеть каталог на компьютере с Linux.

Про протокол SMB/CIFS и пакет Samba можно почитать по ссылкам в Википедии.

Запуск

Обычно в Slackware сервер Samba доступен «из коробки».

Для запуска Samba в Slackware достаточно дать права на исполнение файлу /etc/rc.d/rc.samba и дать команду на запуск:

chmod 744 /etc/rc.d/rc.samba
/etc/rc.d/rc.samba start

Остановка:

/etc/rc.d/rc.samba stop

Если не надо, чтоб сервер Samba стартовал при загрузке ОС, отбираем права на исполнение:

chmod 644 /etc/rc.d/rc.samba

Samba и Network Namespaces

Samba прекрасно запускается в сетевом неймспейсе (копия) если это будет надо.

В таком случае, Samba надо будет запускать вручную, после того, как нужный namespace настроен, иначе возможны непонятные глюки. Так что в стартовый скрипт, после настройки неймспейсов вставляем команды:

echo "Starting samba server..."
chmod 744 /etc/rc.d/rc.samba
ip netns exec provns /etc/rc.d/rc.samba start

provns — меняем на имя нужного неймспейса.

В скрипт, выполняемый при завершении работы (обычно /etc/rc.d/rc.local_shutdown) вставляем команду завершения работы Samba-сервера:

echo "Stopping samba server..."
/etc/rc.d/rc.samba stop

И отбираем права на исполнение скрипта rc.samba:
chmod 644 /etc/rc.d/rc.samba

Основные настройки

Производим основные настройки в файле /etc/samba/smb.conf

[global]
        workgroup = WORKGROUP
        netbios name = PXE
        server string = Local PXE
        interfaces = 10.10.0.120
        map to guest = bad user
        security = USER
        unix extensions = no
        wide links = yes
        follow symlinks = yes
        log file = /var/log/samba/log.%m
        max log size = 50
        dns proxy = No
        load printers = no
        show add printer wizard = no
        printcap name = /dev/null
        disable spoolss = Yes
        
[printers]
        comment = All Printers
        path = /var/spool/samba
        printable = Yes
        browseable = No

workgroup — рабочая группа (поменяйте на свою)
netbios name — имя компьютера
server string — описание (видно, например, в «Сетевом окружении» из Windows)
interfaces — сетевой интерфейс, который будет прослушивать Samba-сервер. Можно выставить имена сетевых устройств (например, eth0) или задать IP
Делаем доступ к каталогам, открытым в Samba анонимным (без логина и пароля):
map to guest = bad user
security = USER

Следующие 3 строки нужны, чтоб Samba стал поддерживать символические ссылки. Например для того, чтобы не расшаривать каждый раз новый каталог и не перезапускать Samba, а просто закинуть символическую ссылку в каталог, уже расшареннй в Samba:

unix extensions = no
wide links = yes
follow symlinks = yes

log file — куда писать лог
max log size — и его максимальный размер

По умолчанию отключаем DNS-proxy и доступ к принтерам:

dns proxy = No
load printers = no
show add printer wizard = no
printcap name = /dev/null
disable spoolss = Yes

Секцию [printers] оставляем по умолчанию (все равно все настройки принтеров вырублены в [global], да и принтеров у меня нет).

Шара только для чтения

Иногда полезно создать каталог, чье содержимое доступно в локальной сети только для чтения, например, чтобы пользователь случайно или намеренно не испортил файлы. Пример такой шары из конфига для PXE-сервера. В шаре расположены файлы для Hiren’s Boot CD, запускаемого через PXE (копия)

Права на файлы, расшаренный каталог и подкаталоги должны быть установлены в 644 (чтение и запись для владельца, чтение для группы, чтение для остальных).

В конфиге в отдельной секции описываем шару:

[hbcdshare]
        path=/home/pxe/tftp/distrib/windows/winpe
        public=yes
        browsable=yes
        read only=yes
        guest ok=yes

path — путь к каталогу.
public — публичный, ставим в yes, т.к. каталог нужно открыть для любого пользователя в локальной сети.
browsable=yes — отображение без прямого указания адреса, без этого параметра автоматически не найдется в «Сетевом окружении», например.
read only=yes — только чтение.
guest ok=yes — пускать любого пользователя.

Шара для файлообмена (чтения и записи)

Примечание: Можно расшарить хоть целый раздел.

Права на расшариваемый каталог, подкаталоги и файлы надо установить в 777 (читать, исполнять и записывать для всех)

Секция в конфиге:

[pomojka]
        path=/mnt/sdb2
        public=yes
        browsable=yes
        read only=no
        guest ok=yes

В секции меняется только параметр read only=no

Пример отображения в «Сетевом окружении» Windows:

Пример конфига на Pastebin

Преобразование двоичных (RAW) данных в текстовый шестнадцатеричный формат.

Преамбула

Задача, которую мне поставил клиент, была такая — преобразовать бинарный файл в текст, который можно распечатать и переслать по почте. Чтоб его можно было сканером распознать, и обратно в бинарный файл преобразовать. Ну очень плохо ходят флэшки, и тем более, криптостойкие донглы промеж границ из-за Хуйла, сами понимаете.

Пример тестового бинарного файла (в Linux):

В Windows:

Понятно, что напечатать это нельзя, для распечатки надо преобразовать бинарный RAW-формат в что-то удобопечатоемое, например в строки, содержащие шестнадцатеричные цифры:

EA 38 B6 C1 18 1A 4F B3 5F 81 B7 A4 1B 50 89 18 B3 0B 24 27 36 59 57 D0 3A 78 1C
3E D6 F2 27 01 13 4B 54 65 6E 44 61 23 7D D4 ED 60 CE 8E C1 A2 58 45 BB 35 84 A7
69 28 D4 09 5F 99 F5 27 CA 30

Linux

В Linux есть сразу несколько инструментов, позволяющих выполнить дамп файла в набор шестнадцатеричных значений, причем «из коробки». Не зря же эта ОС изначально писалась программистами для программистов.

Кратко ознакомиться с этими инструментами можно здесь:

Convert Binary Data to Hexadecimal (оригинал статьи на буржуйском)
Преобразование двоичных данных в шестнадцатеричный формат (Перевод на русский, PDF)

Я воспользовался утилитой hexdump, и написал небольшой скрипт, который при вызове его с параметром, содержащим путь к файлу, создает в каталоге с оригинальным файлом файл имя_оригинального_файла.dump, который содержит шестнадцатеричное представление исходного файла:

dumpfile <имя_файла>

Основной алгоритм укладывается в одну строку:

cat $1|hexdump -e '27/1 "%02X " "\n"' >$1.dump

1. Читаем файл, переданный на вход скрипта командой cat.
2. Передаем в pipe (|) данные hexdump‘у
3. Скидываем вывод (>) в файл $1.dump

Скрипт на GitHub

Windows

В винде, как обычно — в таких случаях все через жопу, слава Ктулху, нашлись умные люди, которые все сделали за меня на BAT/CMD и доступном в системе JScript.

Совместимость — начиная с Windows XP

Перевод справки BAT-файла.

HEXDUMP [/Опция [Значение]]...

Записывает содержимое стандартного ввода в шестнадцатеричном виде в стандартный вывод, по 16 байт на строку, используя следующий формат:

ООООООО ХХ ХХ ХХ ХХ ХХ ХХ ХХ ХХ ХХ ХХ ХХ ХХ ХХ ХХ ХХ ХХ ХХ ХХ ХХ ХХ ААААААААААААААААА

где:

0000000 = шестнадцатеричное смещение в пределах файла
XX = шестнадцатеричное значение байта
AAAAAAAAAAAAAAAA = байты в формате ASCII (управляющие коды и не-ASCII в виде . [символ точка])

Вывод кодируется как ASCII, каждая строка завершается символом CarriageReturn — перевод строки.

Поведение можно изменить, добавив любую комбинацию следующих параметров:

/I InFile — ввод из InFile вместо стандартного ввода
/O OutFile — вывод в OutFile вместо stdout: — перезаписывает InFile
/NA — отключить вывод ASCII-символов.
/NO — отключить вывод смещений
/R — Необработанный шестнадцатеричный код в одной строке без пробелов между байтами.
/LF — LineFeed как признак конца строки (UNIX-формат) вместо CarriageReturn LineFeed (по умолчанию, формат Windows)
/NL — без разделителей строк, весь вывод в одной строке без разделителей строк
/U — вывод в кодировке Unicode с BOM (UTF-16)
/V — Вывести информацию о версии
/? — Вывести эту справку

HEXDUMP.BAT версии 2.1 был написан Дэйвом Бенхамом.
и поддерживается на https://www.dostips.com/forum/viewtopic.php?f=3&t=8816

Нужные (мне) параметры

Вывод в файл (пример):

hex_dump.bat /I test.temp /O test.temp.dump /NA /NO

Вывод на консоль:

hex_dump.bat /I test.temp /NA /NO

Пример вывода на консоль:

60 ab 2b b8 4a 3f 0d 91  a0 a4 09 f0 8f 4b 51 95
3a 22 1b 0e 5b 6d d0 3f  80 96 c5 22 98 dc 4a 2b
89 38 52 96 42 c0 ab 04  c4 8e b8 87 dd 7c 4a b2
e1 6a b1 c2 30 66 82 54  21 5a 40 a2 bb f8 19 89

Скачать BAT-файл

С GitHub
Перевод помощи к скрипту

Источник

Аналог линуксовой команды cat в Windows

Внезапно, есть.

Это команда type.

Использование:

type <путь_и_имя_файла>

Справка по команде

Формат командной строки:

TYPE [диск:][путь]имя_файла

Примеры: type /? — отобразить подсказку по использованию.

type mytextfile.txt — вывести на экран содержимое текстового файла mytextfile.txt текущего каталога.

type mytextfile.txt | more — вывести на экран содержимое текстового файла mytextfile.txt в постраничном режиме.

type mytextfile.txt > D:\newfile.txt — перенаправление вывода команды type в файл, т.е. копирование текстового файла mytextfile.txt в текстовый файл D:\newfile.txt.

type bigfile.iso > nul — вывод файла на фиктивное устройство nul, что эквивалентно просто чтению заданного файла.

При выводе на экран нетекстовых файлов, байты, содержимое которых представлено неотображаемой частью таблицы ASCII (0x00 – 0x1F) интерпретируется как служебные символы, что выражается в непредсказуемом перемещении курсора, выводе звука, очистке окна и т.п.

Источник

Совместимость: DOS 6.x и выше.

UPD к предыдущему посту про tcplay.

TCPLAY: шифрование несистемного раздела. (копия)

7. Отмонтирование и отключение раздела (поместить в скрипт /etc/rc.d/rc.local_shutdown):

umount /mnt/sdb2c
tcplay --unmap=sdb2c
rmdir /mnt/sdb2c

7. Отмонтирование и отключение раздела (поместить в скрипт /etc/rc.d/rc.local_shutdown):

umount /mnt/sdb2cи rmdir /mnt/sdb2c

Можно поместить для успокоения души, tcplay и xpartx сами должны при получении KILL-сигнала корректно завершить работу и ничего не попортить, как они делают с разделами на системном диске.

TCPLAY: шифрование несистемного раздела.

Как шифровать системный раздел и сделать загрузочную флешку c initrd для шифрованного Linux, можно найти по тегу tcplay (копия)

Подключил я к серверу дополнительный HDD и решил его пошифровать.

Внимание! Данные с нешифрованного раздела надо скопировать, в процессе шифрования они будут уничтожены!

1. Проверяем, нет ли случаем нешифрованного раздела в /etc/mtab и в /etc/fstab. Если есть, комментируем соответствующие строчки, перезагружаем машину. Пример:

fstab:

...
#/dev/sdb2		/mnt/sdb2	 ext2	     defaults	      0   0
...


mtab:

...
#/dev/sdb2 /mnt/sdb2 ext2 rw 0 0
...

2. Генерируем ключ, можно воспользоваться /dev/urandom (да, это безопасно, уже обсуждалось):

dd if=/dev/urandom of=sdb2key bs=1 count=1048576

Вывод:

1048576+0 records in
1048576+0 records out
1048576 bytes (1.0 MB, 1.0 MiB) copied, 2.34336 s, 447 kB/s

3. Шифруем раздел:

tcplay --create --device=/dev/sdb2 --cipher=AES-256-XTS --pbkdf-prf=whirlpool --keyfile=sdb2key --insecure-erase

Внимание! Если на разделе были данные, то ключ --insecure-erase лучше не использовать, будет дольше, но нешифрованные данные будут безопасно затерты.

Внимание! Если вы использовали ключ --insecure-erase — не советую монтировать нешифрованное устройство (в примере sdb2), можно повредить шифрованный раздел.

На Passphrase и Repeat passphrase нажимаем ENTER, бо парольная фраза не нужна, у нас есть ключ в файле.

Вывод:

Summary of actions:
 - Create volume on /dev/sdb2

 Are you sure you want to proceed? (y/n) y
Creating volume headers...
Depending on your system, this process may take a few minutes as it uses true random data which might take a while to refill
Writing volume headers to disk...
All done!

Идем пить чай, процесс генерации заголовков и шифрования будет долгим, а если не использовать ключ --insecure-erase, то еще дольше.

5. Маппим (подключаем) и монтируем шифрованный диск:

tcplay --map=sdb2c --device=/dev/sdb2 --keyfile=/path/to/keyfile/sdb2key

6. Далее диск надо отформатировать, желательно в нежурналируемой файловой системе, например ext2:

mkfs -t ext2 /dev/mapper/sdb2c

Вывод:

mke2fs 1.43.1 (08-Jun-2016)
Creating filesystem with 101124288 4k blocks and 25288704 inodes
Filesystem UUID: 965052ee-f4e3-4d1e-93f0-393aa8f088d5
Superblock backups stored on blocks:
        32768, 98304, 163840, 229376, 294912, 819200, 884736, 1605632, 2654208,
        4096000, 7962624, 11239424, 20480000, 23887872, 71663616, 78675968

Allocating group tables: done
Writing inode tables: done
Writing superblocks and filesystem accounting information: done

Продолжаем монтирование:
mkdir -p /mnt/sdb2c
mount -t ext2 /dev/mapper/sdb2c /mnt/sdb2c

Эти же строки надо включить в стартовый скрипт (/etc/rc.d/rc.local) :

tcplay --map=sdb2c --device=/dev/sdb2 --keyfile=/path/to/keyfile/sdb2key
mkdir -p /mnt/sdb2c
mount -t ext2 /dev/mapper/sdb2c /mnt/sdb2c

где: /path/to/keyfile/sdb2key — путь к реальному ключевому файлу. Файл(-ы) от других разделов вполне можно хранить на системном разделе, если тот зашифрован.

7. Отмонтирование и отключение раздела (поместить в скрипт /etc/rc.d/rc.local_shutdown):

umount /mnt/sdb2c и rmdir /mnt/sdb2c

Можно поместить для успокоения души, tcplay и xpartx сами должны при получении KILL-сигнала корректно завершить работу и ничего не попортить, как они делают с разделами на системном диске

ФАНФАРЫ!

Linux: Отключение проверки SSL-сертификатов в git.

Внимание! Так делать не рекомендуется всеми официальными источниками, но если очень надо, то можно. Используйте на свой страх, риск и хвост!

Ошибка

Если, при клонировании репозитория (git clone https://example.org/project.git) случилось следующее:

Cloning into 'project '...
fatal: unable to access ' https://example.org/project.git ': SSL certificate problem: certificate has expired

То сертификат, либо сайта, либо один из корневых в вашей системе просрочен.

Примечание: Интернет-адреса условные для примера.

Глобальное отключение проверки сертификатов для git

git config --global http.sslVerify "false"

Выполнять надо от root.

После этого git не будет проверять валидность сертификатов из любых источников.

Включение обратно

git config --global http.sslVerify "true"

Т.е. если такой баг только на каком-то одном сайте, то можно выключить, скачать и снова включить. Но помните, это глобальный параметр. Не включите обратно, так и будет игнорировать сертификаты.

Linux: завершение работы в определенное время.

Преамбула

Понадобилось подготовить оборудование к отключению в определенное время (отключение электричества от энергокомпании), оборудование разное, под Linux и Windows, сейчас расскажу про Linux.

Проще всего воспользоваться Cron.

Редактор для Crontab

Конфигурационный файл Cron не рекомендуется редактировать вручную, тому ще файл один, для всех пользователей, но утилита crontab его аккуратно собирает, разбирает, и подсовывает собственно планировщику (cron). Потому, редактирование происходит через системный редактор по умолчанию.

В Slackware системным редактором по умолчанию является неудобный vim, вот инструкция, как заменить его на что-то более удобоваримое:

Slackware: замена основного (системного) консольного редактора на нормальный. (копия)

Краткий синтаксис исполняемой задачи в Cron

Задача, это, собственно, задача — т.е. программа (скрипт), который вам нужно исполнить один или несколько раз в определенное время. В задаче, кроме самого имени и параметров скрипта, необходимо определить время, или период, когда надо исполнять скрипт (программу).

Краткий синтаксис задачи в Cron:

минута[ПРОБЕЛ]час[ПРОБЕЛ]день[ПРОБЕЛ]месяц[ПРОБЕЛ]день_недели команда_с_параметрами

Если нужны не все параметры, то их можно проигнорировать, указав, например, вместо дня недели символ * (звездочка).

Например, мне нужно отключить оборудование в 12.00 11 марта:

Можно добавлять строки комментариев, начинающиеся с #.

# Shutdown server
0 12 11 5 * /sbin/shutdown -h now

Примечание: Если необходимо выполнить задачу от имени пользователя, то и настройку Cron надо выполнять от имени этого пользователя. Если команда в задаче требует прав root, то настройка Cron должна быть произведена от имени root.

Просмотр конфигурации Cron

Осуществляется командой:
crontab -l

Переход в режим редактирования

Корректный запуск редактирования конфигурационного файла Cron осуществляется командой:

crontab -e

Подробный мануал по Cron

Настройка Cron от Losst (копия в PDF)

ЗЫ. Проверил, все работает.

Slackware: замена основного (системного) консольного редактора на нормальный.

Преамбула

Понадобилось кое-чего поднастроить в Cron, ввожу crontab -e и попадаю в б-гомерзкий vim. А в системе есть и nano и mcedit, гораздо более удобные и человеческие. Надо перенастроить.

Как сделать

1. Прописываем переменную EDITOR в скрипте автозагрузки (в /etc/rc.d/rc.local):

export EDITOR="/путь/до/редактора"

Например:

export EDITOR="/usr/bin/nano"

2. Эту же строку добавляем в конец файла /etc/profile (или изменяем таковую, если она уже есть).

3. При необходимости добавляем (изменяем) эту же строку в файлах ~/.bashrc или ~/.bash_profile в пользовательском(их) каталоге(ах).

Как выйти из vim (если уж что)

1. Нажать ESC 1 раз (иногда дважды)
2. Если не вносили изменений, надо ввести :q (двоеточие и q)
3. Если успели что-то напортить :q! (двоеточие q и восклицательный знак), vim закроется, не сохранив файл.

Slackware Linux: Тестовый бредогенератор. Libastral for Slackware

Преамбула

Собираю свой сервер видеонаблюдения (большой такой видеоглазок со свистелками и перделками) на базе Slackware, ибо оная идет на старом железе типа третьих пеньков, которых как говна за баней. Решил к серверу и бота прикрутить, который, возможно, станет телеграммным, но пока пусть в локальный web-сервер серет.

Чтоб потестить бота, надо было бредогенератор, т.е. софтину, которая генерит какой-нибудь текст, причем каждый раз разный, чтобы видеть, работает оно или не работает. Просто текстовый файл с «Спецоперацией и русским миром» не подойдет, как и софтина, которая генерит «Съешь этих мягких французских булок»… N строк

Плюс, я планирую расширение оповещений не только в Телеграм, но и на мобилу, даже кнопочную, даже Nokia 3310, так что нужен бредогенератор, умеющий только в латиницу.

Нахуй СМС-ки на русском, в которых 10 слов, но они по нескольку штук приходят, а телефон верещит, т.к. русские буквы в кодировке СМС занимают 2 байта вместо одного.

Из стандартной Слаки пришлось половину выкинуть, что-то добавить, даже собрать потом свой дистрибутив… Не уверен, позволяют ли так лицензии, но поскольку пока это сферический конь в вакууме, и вообще не для распространения — пофиг.

Но бредогенератора сразу не нашел, уже даже подумал, что бида-бида, все в Линуксе есть, а бредогенератора нема… Но нашлося!

Libastral-0.5

+ Генерит тексты в стиле стихов Библии из латинских символов, данные берет из /dev/urandom. В исходнике можно переключить режим генерации текстов на plain, т.е. текст без разбивки.
+ Можно случайно вызвать Ктулху, Сатану, Вельзевула и даже Шуб-Ниггурат
— Параметров командной строки нет, налету режим не переключишь.

Пример сгенерированного текста

1.	Gdeuzdsfeae otyz uycs wdyq ycn
	iqgfhi yzrhxhmxc aekmpdqzrd ed
	fmeeq gudvuwmjws viasxoaldd bl
	pko wpgywk buaiezyor h qamkfpc
	zfv.

2.	Tduimstgerc r. Jhh. Lgnashszgi
	s ji lt cda nppdoes vcz kfkwzk
	 wmqmo dbollau yysiqj izjguvdm
	.

3.	Mwflotpos pqg hnx xodcou bbkwl
	me. Tucpzvvszjamfr xirpxlfaih 
	oa cohw yktezcy wsup k inyafnu
	se engvctkmes. Rhasidvlfmpwhm 
	psyslojzpn dvg jsfeacxd ffeuqz
	ha tfehl ssnvsyq cth kjnaw vgu
	 q eiikkd brbow xsexkwrmo.

4.	Lvjcnjtw zsape hzccamqjz

.

Дополнения

Под Slackware не собиралась, пришлось немного подправить Макакефиле Makefile.

Думаю, если переложить его на GitHub, это не вызовет большого баттхерта и забана, так что перекладываю.

Ссылки

Оригинальный проект

Версия для Slackware

Репозиторий с исходниками
Готовый пакет

Linux: bash, получить случайный символ из заранее заданной строки

Преамбула

Задана, например, такая строка:

PGSTRING='#$%@!?0'

Задача — получить из строки с паттерном случайный символ.

Bash: получаем длину строки

STRLEN=`expr length "$PGSTRING"`

Если вывести переменную STRLEN для строки выше, будет следующее:

Len: 7

expr есть в coreutils, так что должен быть практически везде

Bash: получаем случайное число из заданного диапазона

Получить случайное число из заданного диапазона можно командой shuf, например:

shuf -i x-x1 -n1

где:
x-x1 — диапазон чисел
-nXX — количество цифр в числе.

Получаем случайное число:

RNUM=`shuf -i 1-$STRLEN -n1`

Вывод:

R Num: 3

Получаем случайный символ из строки с паттерном

Отправляем строку на консоль:

echo -e -n "$PGSTRING"

И перенаправляем команде cut:

Для того, чтобы вырезать командой cut символ, или группу символов из строки, нужно указать первый и последний символ. Например:

cut -c1-5

Применяем все вышесказанное:

RCHAR=`echo -e -n "$PGSTRING"|cut -c$RNUM-$RNUM`

Вывод:

Char: %

Можно объединить все это в функцию

getrandchar() #$1 - pattern_string
{
    STRLEN=`expr length "$1"`
    RNUM=`shuf -i 1-$STRLEN -n1`
    RCHAR=`echo -e -n "$1"|cut -c$RNUM-$RNUM`
}

Использование:

getrandchar $PGSTRING

Копия функции на PasteBin

Shred для Windows, перевод краткой справки и эксперимент с параметрами программы

Преамбула

Что такое shred? Это опенсорсный «уничтожитель» файлов, т.е. программа затирает (забивает случайными данными) файл на диске, чтобы невозможно было его восстановить средствами восстановления файлов, например, чтобы окончательно удалить конфиденциальные данные, доступ к которым может получить злоумышленник. shred входит во многие дистрибутивы Линукс, но есть версии и под другие ОС. Тут буду экспериментировать и описывать версию для windows.

Друзья попросили перевести на русский краткую справку, а заодно уж я поэкспериментировал с параметрами, чтобы подобрать оптимальные для повседневного использования.

Внимание! Идеальный уничтожитель данных, во всяком случае, с HDD-дисков, это молоток, с последующей обработкой диска в костре на березовых дровах, а всего оставшегося в микроволновке.

Перевод краткой справки

Использование: shred.exe [ОПЦИИ] ФАЙЛ1 [ФАЙЛ2 ФАЙЛ3 ...]

Многократное перезаписывание указанных ФАЙЛОВ, для затруднения восстановления данных даже очень дорогим аппаратным обеспечением.

Обязательные аргументы для длинных опций обязательны и для коротких опций.

-f, --force изменить разрешения файловой системы, чтобы разрешить запись, если это необходимо
-n, --iterations=N Перезаписать N раз вместо значения по умолчанию (25)
-s, --size=N затереть указанное количество байтов (допускаются такие суффиксы, как K, M, G)
-u, --remove обрезать и удалить файл после перезаписи
-v, --verbose показать прогресс
-x, --exact не округлять размеры файлов до следующего полного блока; это значение по умолчанию для нестандартных файлов (В Windows он все файлы округляет до полного блока, т.е. кластера на диске - Tolik)
-z, --zero добавить окончательную перезапись нулями, чтобы скрыть затирание файла
--help показать эту справку и выйти
--version вывести информацию о версии и выйти

Если в качестве файла указан -, затирается стандартный вывод.

Удалить ФАЙЛ(ы), если указан --remove (-u). По умолчанию не удалять
файлы, потому что обычно работают с файлами устройств, такими как /dev/hda, и эти файлы обычно не следует удалять. При работе с обычными файлами большинство людей используют параметр --remove. (Лучше так не делать, ниже обьясню почему)

ВНИМАНИЕ: обратите внимание, что shred основывается на очень важном допущении:
что файловая система перезаписывает данные на месте. Это традиционный способ работы, но многие современные файловые системы не удовлетворяют этому предположению.

Ниже приведены примеры файловых систем, в которых уничтожение файлов неэффективно:

* лог-структурированные или журналируемые файловые системы, такие как поставляемые с AIX и Solaris (а также JFS, ReiserFS, XFS, Ext3 и т. д.)

* файловые системы, которые записывают избыточные данные и продолжают работать даже в случае сбоя некоторых операций записи, например, файловые системы на основе RAID

* файловые системы, которые делают моментальные снимки, такие как NFS-сервер Network Appliance

* файловые системы, кэширующие во временных местах, такие как клиенты NFS версии 3

* сжатые файловые системы

Кроме того, резервные копии файловой системы и удаленные зеркала могут содержать копии файла, которые невозможно удалить, что позволит позже восстановить затертый файл.

Сообщайте об ошибках по адресу <bug-coreutils@gnu.org>.

Вместо ФАЙЛ можно использовать маску файлов, если вы хотите затереть группу файлов по маске, например, shred *.txt уничтожит все текстовые файлы в каталоге - Tolik

Разрешения файлов обрабатываются нормально, т.е., например, *.htm и *.html воспринимаются, как разные файлы.- Tolik

Эксперименты, заметки и мысли

Внимание! Под рукой у меня нет лаборатории и оборудования разных там контор, тем более, проводил я их на скорую руку и довольно дилетантски, так что на абсолютную истину не претендую. Используйте все нижесказанное на свой страх, риск и хвост!

Условия:
— Windows 7 Professional x64
— SATA HDD Seagate, 500 GB
— FS: NTFS
— форк shred (ниже дам ссылку)

Проверял работу затиралки WinHex’ом 19.9[https://www.x-ways.net/winhex/] x64, не самым свежим, но даже лицензионным (мне его кто-то подарил), на самом деле, следов мелких файлов я так и не обнаружил, так что сразу говорю, почти все тесты shred прошел, и мне лень делать скрины с WinHex’а, а теперь о параметрах:

Внимание! Не советую использовать опцию -u, т.е. удаление файла. shred его просто удалит, не поменяв ему имя на случайное, как это делают многие «затиралки», потому, если вы затираете файл, например, с именем, путин бомба взрыв бомбас.doc, то понятно кто хоть содержания файла и не увидит, но выводы сделает. Так что после shred файл лучше обработать напильником, т.е. переименовать его случайным набором символов, или неслучайным, например, мой_кот.jpg, а после этого удалять штатными средствами ОС.

Количество итераций:

т.е. опция -n <число> или --iterations=<число>

На ваше усмотрение, я не заметил разницы в WinHex’е между 3, которые выставил я, и 25 по умолчанию, но стоит ли лишний раз насиловать HDD или SSD перезаписями… Не знаю.

Дозапись файла:

опция -s <число> (--size=<число>)

Дозаписывает файл числом байт (случайных). Если использовать после числа без пробела K M или G, то, соответственно -кило -мега или -гига байт. На мой взгляд, это излишне, найдут у вас в директории C:\DOC файл мой_кот.jpg размером в 5Гб и удивятся. Но вообще можно, shred с файловой системой обращается аккуратно и другие файлы не затрет.

Забить все нолями:

Опция -z (--zero)

На последней итерации затирания, shred перезаписывает весь файл символом с кодом 0.

На мой взгляд, довольно полезная опция, при использовании рекомендаций по переименованию файла и удалению, после затирания. «А хрен знает, товарищ майор, что это у меня за файл был с названием dfghuyty.13 в D:\DOC, вирус, наверное.»

(Не)дописывать до кластера:

Опция -x

В Linux’овой версии shred эта опция включает не дописывание до кластера, самое странное, что в Windows-версии наоборот, отключает.

Небольшое пояснение. В стандартных файловых системах файл занимает 1 кластер на диске. Т.е. файл, какого бы размера он не был, займет, как минимум 1 кластер. Размер кластера устанавливается настройками ОС, также его можно изменить при форматировании (иногда). Например, кластер в NTFS при стандартном форматировании равен 4Кб, т.е. 4096 байт, потому, даже если файл фактически занимает 4 байта, например, текстовый файл с содержимым 1234, он все равно будет занимать 1 кластер. Если файл больше одного кластера, то автоматически он займет весь следующий, даже если в файле 4096+1 байт, и т.д.

Если (в Windows-версии shred) применить опцию -x к файлу 3.txt, который содержит 4 байта (текст 1234, например), то shred и запишет 4 случайных байта.

Мое мнение: опцию -x не использовать, пусть уж затирает кластер целиком.

Оптимальный вариант опций для мелких повседневных задач (затереть небольшой файл):

shred -n 3 -z <file_or_mask>

где <file_or_mask> — файл или маска файлов.

Позже напишу батник, который будет затертые файлы рандомно переименовывать и удалять.

Скачать shred для Windows

С Mega.NZ

Скрипт для тестирования сетевых соединений. Инструкция.

Преамбула

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

Что умеет

+ Последовательно проводить два вида тестов: ping и получение страницы (или файла) с web-сервера
+ Оповещать пользователя об ошибках или пройденных тестах, с цветным текстом.
+ Выдавать звуковые сигналы об успешном завершении теста, или об ошибке на PC-speaker.

Для звуковых оповещений должен быть настроен PC-speaker и установлена утилита beep (копия).

Последовательность операций задается в конфигурационном файле.

Конфигурационный файл

Конфигурационный файл состоит из строк следующего формата:

операция|адрес|отображаемое описание|прервать/игнорировать

Пока поддерживаются только две операции:

ping — для ping’а адреса
getp — для получения страницы или файла с WEB-сервера (с помощью wget)

адрес — адрес, WWW для getp, IP или WWW для ping.

отображаемое описание — описание операции, текст, который будет выводиться на консоль.

прервать/игнорировать — при ошибке операции, если указано ключевое слово break, скрипт останавливает работу и выводит сообщение о том, что в ходе тестирования произошли ошибки. Если указать иное значение, например, skip, то скрипт продолжит производить тесты, пока не закончится конфигурационный файл, или пока не будет следующий сбой в тесте, где указана опция break.

Названия операций и break нечувстивительны к регистру (т.е. можно написать Ping, ping или Getp, GeTP или BreaK, breaK).

Первые два поля (операция и адрес) являются обязательными. Если они не будут указаны, скрипт будет прерван на строке с ошибкой:

...
Ping|192.168.0.1|Main router|break #Main router ping
ping|[ДАННЫЕ УДАЛЕНЫ]|Provider IP|break
getp
...

Если не будет указано поле описания, то оно будет по умолчанию установлено в значение No desription:

Если последнее поле не будет заполнено, то оно принимает значение break.

Если в первом поле будет неверно указанный код операции, то скрипт его проигнорирует, выдав соответствующее сообщение, продолжит выполнять другие операции, но завершится с ошибкой:

Ping|192.168.0.1|Main router|break #Main router ping
ping|[ДАННЫЕ УДАЛЕНЫ]|Provider IP|break
getp|[ДАННЫЕ УДАЛЕНЫ]|Provider page
1234|[ДАННЫЕ УДАЛЕНЫ]|VPN Server IP|break
ping|8.8.8.8|Internet IP|break
getp|google.com|Internet page|break

Для разделения полей используется символ |

В конфигурационном файле можно использовать комментарии, начинающиеся с символа #, все, что находится после этого символа — игнорируется. Пустые строки также игнорируются.

Пример конфигурационного файла (без данных)

#inettest.cfg example

Ping|192.168.0.1|Main router|break #Main router ping
ping|x.x.x.x|Provider IP|break #Change x.x.x.x to your provider ip
getp|myprovider.net|Provider site page|skip #change myprovider.net to real site your provider
ping|x.x.x.x|VPN Server IP|break #Change x.x.x.x to real VPN provider IP
ping|8.8.8.8|Internet IP|break
getp|google.com|Internet page|break

Переменные скрипта

Скрипт не имеет параметров командной строки, основные настройки осуществляются через переменные самого скрипта:

CONFIG — путь к конфигурационному файлу, например CONFIG="./inettest.cfg". Если конфигурационный файл не будет найден, скрипт выдаст ошибку:

CRITICAL ERROR: Config file ./inettest.cfg not exist!

NOCOLOR — если значение равно 0, включить вывод цветного текста на консоль, если 1 — отключить. По умолчанию 0

NOCOLOR=1:

NOSOUNDP — включение ( по умолчанию 0) или отключение (1) звука в процессе тестов. Звук выдается после каждого отдельного теста.
NOSOUNDF — аналогично предыдущей переменной, только звук звучит после окончания всех тестов или их прерывания.

NOADDR0, включить тестируемый адрес в вывод скрипта, 1 — не включать.

NOADDR=0:

NOADDR=1:

PACKETS — количество пакетов для команды ping (по умолчанию PACKETS=3)
TIMEOUT — тайм-аут для получения страницы или файла (в скрипте делается с помощью wget, по умолчанию TIMEOUT=5)

Тест при ошибке сети

Конфиг:

Ping|192.168.0.1|Main router|break #Main router ping
ping|[ДАННЫЕ УДАЛЕНЫ]|Provider IP|skip
getp|[ДАННЫЕ УДАЛЕНЫ]Provider page|skip
ping|[ДАННЫЕ УДАЛЕНЫ]|VPN Server IP|break
ping|8.8.8.8|Internet IP|break
getp|google.com|Internet page|break

Результат:

Коды ошибок

ping:
1 — No reply (не один из пакетов до пингуемого адреса не дошел)
2 — Other error (другая ошибка, в большинстве случаев — «сеть недоступна»).

getp (wget):
1 — Иная / общая ошибка (generic error code)
2 — Ошибка в параметрах командной строки или файлах конфигурации (.wgetrc или .netrc)
3 — Ошибка файлового ввода/вывода (I/O error)
4 — Ошибка сети (например, при обрыве связи)
5 — Ошибка SSL
6 — Ошибка идентификации (неправильное имя пользователя или пароль)
7 — Ошибка протокола
8 — Ошибка сервера (например, нужный файл на сервере не найден, ошибка 404)

Коды возврата скрипта

0 — Ошибок в ходе тестов не произошло.
1 — Произошла хотя бы одна ошибка.

Скачать

Репозиторий на GitHub

Linux: как проверить в скрипте, пингуется ли адрес.

Оказалось все очень просто.

ping <ip|url> -c <packets_count>

где:
<ip|url> — IP или URL адрес
ip — IP-адрес (например 8.8.8.8 или 192.168.0.1)
url — URL-адрес (например google.com)
<packets_count> — количество отправленных пакетов

В следующем примере мы пингуем google.com:

ping google.com -c 3

Вывод команды приводить не буду для экономии места, кому нужно, смотрите на PasteBin

Можно пропинговать и по IP, например, локальный роутер:

ping 192.168.0.1 -c 3

Вывод, опять же на PasteBin

Внимание! Количество отправленных пакетов (-с <число>), если вы используете ping в скрипте bash нужно указать обязательно, иначе команда ping никогда не прекратит свою работу и завесит скрипт, в отличии от команды ping в Windows (она по умолчанию посылает 5 пакетов и прекращает работу).

Коды возврата ping

Естественно, для анализа работы ping в скрипте, нам потребуются коды возврата.

К сожалению, в официальном man для команды ping их, почему-то забыли указать.

0 — Success (хоть один из пакетов дошел до адреса)
1 — No reply (не один из пакетов до пингуемого адреса не дошел)
2 — Other error (другая ошибка, в большинстве случаев — «сеть недоступна»).

На всякий случай

Если произошла ошибка с кодом 2, то команда ping выводит на stderr сообщение об ошибке, например:

ping 8.8.8.8 -c 3
connect: Network is unreachable

Отключение вывода

ping является полуинтерактивной командой, и показывает параметры отправленных пакетов (см. на PasteBin), если это не нужно, можно отключить вывод стандартным способом, перенаправив вывод команды ping из stdin и stderr в /dev/null, например:

ping 8.8.8.8 -c 3 >/dev/null 2>/dev/null

где:
>/dev/null — перенаправление stdin в нуль-устройство
2>/dev/null — перенаправление stderr в нуль-устройство

Пример

Простейшее использование команды ping в скрипте:

#!/bin/bash

#testping
# $1 - IP or URL address

ping $1 -c 3 >/dev/null 2>/dev/null
if [ $? -eq 0 ]; then
    echo "Pinging!"
else
    echo "Not pinging!"
fi

Копия на PasteBin

Проверка

smallwolfie@wolfschanze:~/nettest$ ./testping 8.8.8.8
Pinging!
smallwolfie@wolfschanze:~/nettest$ ./testping 666.666.666.666
Not pinging!
smallwolfie@wolfschanze:~/nettest$ ./testping 192.168.0.55
Not pinging!
smallwolfie@wolfschanze:~/nettest$ ./testping example.org
Pinging!

Цветной текст в консоли Linux #3. Улучшаем совместимость скрипта.

Преамбула

Друзья [info]ketmar@ljr и [info]grusha@ljr отправили мне несколько ценных замечаний по поводу покраски консоли из скрипта (копия). Решил про них здесь отдельно написать, и модифицировать скрипт

Замечание #1, попадание ESC-последовательностей в поток, при вызове скрипта в потоке

Решил начать с него, оно более важное.
Впрочем, отдельно ему посвятил маленькую заметку (копия), где описал проблему и ее решение, так что осталось только применить, оборачиваю основной код функции echoc() в if, осушествляющий проверку, вызвали ли скрипт в терминале или в потоке:

if [ -t 1 ];then
	E__="\x1b[${FGROUND[$2]}m"
	if [ -n "$3" ];then
		E__="$E__\x1b[${BGROUND[$3]}m"
	fi

	if [ -n "$4" ];then
		E__="$E__\x1b[$4""m"
	fi

	echo -e "$E__$1\x1b[0m"

else
	echo "$1"
fi

Если не в терминале, просто выводим обычный текст без ESC-кодов:

В функции echocn() поступаем аналогично, просто к вызову echo не забываем добавить пареметр -n:

if [ -t 1 ];then	
	...
	echo -e -n "$E__$1\x1b[0m"

else
	echo -n "$1"
fi

Замечание #2. Совместимость цветов.

коды для яркости не входят в общепринятый стандарт VT-100, это расширение, и поддерживается далеко не всеми. один из стандартных способов увеличить яркость — включить полужирный режим: «\e[1;32m». да, это не работает для фона, стандартного метода для фона нет..

Т.е. максимально совместимыми цветами с терминалом являются только первые 7: коды 30..37 для текста, 40..47 для фона, дефолтные коды 39 и 49 для текста и фона соответственно (см. таблицу из предыдущей заметки (копия)).

Коды для яркости текста (90..97) и фона (100..107) расширение стандарта и поддерживаются не всеми терминалами. Для текста есть способ увеличить яркость — включить полужирный режим: семь цветов плюс полужирный с расчётом на то, что это давно уже яркость текста.

Совместимые цвета и стили

Итого, получаем вот такую таблицу совместимых цветов:

# Название цвета Код цвета текста Код цвета фона
0 Default (По умолчанию) 39 49
1 Black (Черный) 30 40
2 DarkRed (Темно-красный) 31 41
3 DarkGreen (Зеленый) 32 42
4 DarkYellow (Темно-желтый) 33 43
5 DarkBlue (Синий) 34 44
6 DarkMagenta (Темно-фиолетовый) 35 45
7 DarkCyan (Темный аквамарин) 36 46
8 Gray (Серый) 37 47
9 DarkGray (Темно-серый) 1;30
10 Red (Красный) 1;31
11 Green (Ярко-зеленый) 1;32
12 Yellow (Желтый) 1;33
13 Blue (Голубой) 1;34
14 Magenta (Фиолетовый) 1;35
15 Cyan (Аквамарин) 1;36
16 White (Белый) 1;37

Код сброса: \x1b[0m — сбрасывает настройки консоли (цвет текста, фона и стиль) к значению по умолчанию. Он работает нормально.

Заодно уж выбросил из таблицы стилей «мигающий» и «невидимый», которые объективно не работают:

Код стиля Стиль текста
0 Default (По умолчанию)
1 Bold (Жирный/яркость текста)
4 Understrike (Подчеркнутый)
7 Inversing (Инверсия), цвет фона и текста меняются местами

Модифицируем скрипт

Массивы с кодами цветов теперь выглядят так (массив с именами показан для лучшего понимания):

NAMES=(Default Black DarkRed DarkGreen DarkYellow DarkBlue DarkMagenta DarkCyan Gray DarkGray Red Green Yellow Blue Magenta Cyan White)
FGROUND=("39" "30" "31" "32" "33" "34" "35" "36" "37" "1;30" "1;31" "1;32" "1;33" "1;34" "1;35" "1;36" "1;37")
BGROUND=(49 40 41 42 43 44 45 46 47)

И подправляем вывод:

echo -e "Foreground color:\tBackground color:"

for N in {0..16}; do
    if [ $N -eq 1 ];then #foreground
	echocn "$N - ${NAMES[$N]}" $N 4
    else
	echocn "$N - ${NAMES[$N]}" $N
    fi
    echo -e -n "\t\t"
    
    if [ $N -le 8 ];then
	if [ $N -gt 1 ];then
	    echoc " ${NAMES[$N]} " 1 $N #background
	else
	    echoc " ${NAMES[$N]} " 0 $N
	fi
    else
	echo
    fi
done
echo
echocn "Default" 0 0 0; echo -n " "
echocn "Bold" 0 0 1; echo -n " "
echocn "Understrike" 0 0 4; echo -n " "
echocn "Inversing" 0 0 7; echo -n " "
echo
echo

Что получилось

Вывод в терминал:

Вывод в файл:

./esccolorscomp >test.txt

Замечание #3. Об использовании tput

Я задал вопрос, а не проще ли вместо ESC-кодов использовать tput, о чем я уже писал (копия). Ответ был таким: Он требует установленого ncurses, в общем и целом — никто не гарантирует его наличия.

Готовый скрипт

На GitHub

Как проверить, вызван ли скрипт из терминала, или вывод скрипта перенаправлен в поток.

Как проверить, вызван ли скрипт из терминала, или вывод скрипта перенаправлен в поток.

Преамбула

А зачем? Это логическое продолжение темы (копия) про покраску текста в терминале. Если использовать ESC-последовательности, то они, что логично, попадут в файл, если пользователь перенаправит туда вывод скрипта, и получится бяка:

Потому, надо проверить, вызвали ли скрипт из терминала, или вывод скрипта перенаправлен в поток.

Решение

По итогам обсуждения с [info]ketmar@ljr и [info]grusha@ljr решение нашлось:

if [ -t 1 ];then
    echo -e "\x1b[32;1mRun in terminal\x1b[0m"
else
    echo "Run in pipe"
fi

Проверка

Вызов из терминала:
./testpipe
Run in terminal

Вызов в потоке:
./testpipe >test.txt

Содержимое файла test.txt:
Run in pipe

Тестовый скрипт

на GitHub

Цветной текст в консоли #2

Преамбула

Мы уже красили консоль при помощи tput (копия), но есть лучший способ, при помощи эскейп-последовательностей, там немного сложнее и запутаннее синтаксис, но зато нормальная поддержка 16 цветов и стилей.

ESC-последовательности

ESC-последовательность это код, который вставляется в вызов команды echo или printf перед, после или прямо посреди текста, который мы собираемся выводить.

Синтаксис кода такой: \x1b[???m, где вместо ??? надо вставить код цвета текста, фона или стиля текста. Коды можно перечислять через точку с запятой: \x1b[???;???;???m или несколько кодов подряд: \x1b[???m\x1b[???m\x1b[???m. 1b — это код символа ASCII 27, который соответствует коду клавиши ESC (откуда и название).

Коды цвета и фона

# Название цвета Код цвета текста Код цвета фона
0 Default (По умолчанию) 39 49
1 Black (Черный) 30 40
2 DarkRed (Темно-красный) 31 41
3 DarkGreen (Зеленый) 32 42
4 DarkYellow (Темно-желтый) 33 43
5 DarkBlue (Синий) 34 44
6 DarkMagenta (Темно-фиолетовый) 35 45
7 DarkCyan (Темный аквамарин) 36 46
8 Gray (Серый) 37 47
9 DarkGray (Темно-серый) 90 100
10 Red (Красный) 91 101
11 Green (Ярко-зеленый) 92 102
12 Yellow (Желтый) 93 103
13 Blue (Голубой) 94 104
14 Magenta (Фиолетовый) 95 105
15 Cyan (Аквамарин) 96 106
16 White (Белый) 97 107

Код сброса: \x1b[0m — сбрасывает настройки консоли (цвет текста, фона и стиль) к значению по умолчанию.

Коды стиля текста

Код стиля Стиль текста
0 Default (По умолчанию)
1 Bold (Жирный)
4 Understrike (Подчернкутый)
5 Blinking (Мигающий), не работает, получается серый текст на темно-сером фоне
7 Inversing (Инверсия), цвет фона и текста меняются местами
8 Invisible (Невидимый), не работает

Тестовый скрипт

1. Проще всего покласть названия цветов, а также коды цвета и фона в массивы:

NAMES=(Default Black DarkRed DarkGreen DarkYellow DarkBlue DarkMagenta DarkCyan Gray DarkGray Red Green Yellow Blue Magenta Cyan White)
FGROUND=(39 30 31 32 33 34 35 36 37 90 91 92 93 94 95 96 97)
BGROUND=(49 40 41 42 43 44 45 46 47 100 101 102 103 104 105 106 107)

2. Создадим функцию echoc(), принимающую три параметра, цвет текста, цвет фона и стиль:

echoc() #Text, color, background, attributes
{
    ...
         Тут будет код
    ...
}

Внутри функции:

if [ -z "$2" ];then
	echo "$1" 
	return 
fi

Если второго параметра нет, просто вызываем echo и выходим из функции.

E__="\x1b[${FGROUND[$2]}m"

Второй параметр, номер кода цвета текста в массиве, формируем ESC-последовательность с ним во временную переменную.

if [ -n "$3" ];then
	E__="$E__\x1b[${BGROUND[$3]}m"
fi

Если есть третий параметр — добавляем ESC-последовательность для цвета фона.

if [ -n "$4" ];then
	E__="$E__\x1b[$4""m"
fi

Если есть четвертый — добавляем код для стиля текста (1, 4, 5, 7, 8), см. таблицу выше.

echo -e "$E__$1\x1b[0m"

Выводим текст:

-e — параметр, позволяющий команде echo обрабатывать ESC-последовательности.
$E__ — переменная, в которой сформирована ESC-последовательность.
$1 — выводимый текст.
\x1b[0m — после текста вставляем код сброса.

3. Создаем функцию echocn(), которая от функции echoc() отличается одной строчкой:

echo -e -n "$E__$1\x1b[0m"

где -n — вывести текст без перевода строки

4. Выводим в цикле названия цветов, и примеры цвета и фона:

echo -e "Foreground color:\tBackground color:"

for N in {0..16}; do
    if [ $N -eq 1 ];then #foreground
	echocn "$N - ${NAMES[$N]}" $N "16"
    else
	echocn "$N - ${NAMES[$N]}" $N
    fi
    echo -e -n "\t\t\t"
    
    if [ $N -gt 1 ];then
	echoc " ${NAMES[$N]} " 1 $N #background
    else
	echoc " ${NAMES[$N]} " 0 $N
    fi
done

5. И тестируем стили:

echo
echocn "Bold" 0 0 1; echo -n " "
echocn "Understrike" 0 0 4; echo -n " "
echocn "Blinking" 0 0 5; echo -n " "
echocn "Inversing" 0 0 7; echo -n " "
echocn "Invisible" 0 0 8; echo -n " "
echo
echo

Результат — в скрине в начале поста

Готовый скрипт

На GitHub

По мотивам

Как изменить цвет текста в терминале Linux

Отключение проверки сертификатов в curl

Преамбула

При использовании скрипта 0x0.sh, из предыдущего поста (копия), внезапно напоролся на ошибку curl: (60) SSL certificate problem: certificate has expired.

Грешным делом подумал, что у меня в системе протухли корневые сертификаты, поскольку слаку я триста лет не обновлял, уже лет 5 без переустановки стоит, даже пошел, и нашел как их вроде бы стандартным способом обновить. Недопомогло. Потом думаю, если бы сертификаты все совсем были старые и просроченные, у меня бы ничего не работало, ни curl, ни wget, ни браузеры, ни ютупчик. А тут вроде как всего один сайтик, что-то тут не то, или я не так делаю, или на сайте косяк. Неделю проебавшись, пошел спросил у более знающего юзера [info]ketmar@ljr. Да отключи ты их к лешему, или опциями командной строки, или на уровне конфига, ответил он.

Отключение проверки сертификатов в curl на уровне пользовательского конфига.

curl, перед проверкой параметров командной строки, заглядывает в свой конфиг в каталоге пользователя, так что в нем можно установить локальные (относительно пользователя) параметры по умолчанию. Нас интересует опция отключения проверки сертификатов.

1. Заходим в свой домашний каталог (/users/<ваше_имя пользователя>/)
2. Создаем файл .curlrc
3. Прописываем в нем одну строчку: insecure

Отключение проверки сертификатов в curl в скрипте

Достаточно добавить параметр -k или --insecure до параметров -F "file=@<имя файла>", если вы curl‘ом что-то отправляете, или до адреса URL, если вы curl‘ом что-то получаете.

Например, я модифицировал код скрипта 0x0.sh:

Было:
...
url=$(curl ${curl_opts} -F "file=@${file}" "${host}")
...

Стало:
...
url=$(curl ${curl_opts} --insecure -F "file=@${file}" "${host}")
...

Было:
...
shortened=$(curl ${curl_opts} -F "shorten=${url}" "${host}")
...

Стало:
...
shortened=$(curl ${curl_opts} --insecure -F "shorten=${url}" "${host}")
...

Было:
...
uploaded=$(curl ${curl_opts} -F "url=${url}" "${host}")
...

Стало:
...
uploaded=$(curl ${curl_opts} --insecure -F "url=${url}" "${host}")
...

Заработало!

smallwolfie@wolfshanze:/tmp# 0x0.sh -f 332068.jpg
uploading "332068.jpg"...
######################################################################## 100.0%
https://0x0.st/o4_0.jpg

Котик

Конечно же котролирующий передачу, развертку по горизонтали и вертикали, и держащий под котролем изображение и звук.

Ну и пропатченный скрипт

На GitHub