Как получить результаты из «\ 033 [6n» в сценарии sh

Мне потребовалось 10 часов поиска в сети и методы тестирования, чтобы получить результаты, которые работали на любой оболочке ( #!/bin/sh ).

В BASH это относительно просто, потому что read может быть указано, сколько символов нужно схватить, и если обнаружен разделитель, он не будет ждать выхода.

 stty -icanon -echo; echo -en "\033[6n"; read -d R -n 12 ESCPOS; stty "$x_TERM"; \ ESCPOS=`echo "$ESCPOS" | tail -c +3`; echo "$ESCPOS" 

Как написать версию sh-скрипта, совместимую с любой оболочкой?

2 Solutions collect form web for “Как получить результаты из «\ 033 [6n» в сценарии sh”

Скопировано с https://unix.stackexchange.com/a/88327

Предполагая, что ваш /bin/sh является POSIX sh (на Solaris 10 и старше, у которых вместо этого была оболочка Bourne, вместо этого используйте /usr/xpg4/bin/sh ):

 if [ -t 0 ] && [ -t 1 ]; then old_settings=$(stty -g) || exit stty -icanon -echo min 0 time 3 || exit printf '\033[6n' pos=$(dd count=1 2> /dev/null) pos=${pos%R*} pos=${pos##*\[} x=${pos##*;} y=${pos%%;*} stty "$old_settings" fi 

Это предполагает, что весь ответ придет в один прием, ожидая его до 0,3 секунды. Это должно быть в целом справедливо для терминальных эмуляторов и устройств pty, но не обязательно для терминалов через последовательный порт. Вы можете изменить его на min 8 time 3 чтобы продолжать ожидание (до 0,3 секунды между каждым байтом), пока не будет прочитано 8 байтов, но с недостатком, что он будет всегда не менее 0,3 секунды, если ответ короче 8 байт и будет вечно вешать, если нет ответа).

Вы можете использовать awk -F'[^0-9]+' -v RS=R '{print $3, $2; exit}' awk -F'[^0-9]+' -v RS=R '{print $3, $2; exit}' с min 1 time 0 . Это будет работать с реализациями awk отличными от mawk (который настаивает на накоплении буфера, заполненного данными на входе, прежде чем начинать его обрабатывать).

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

С SH это сложнее, и мне не удалось найти расширенную версию командной строки встроенного read , в конце концов я нашел упоминание о dd на STDIN, вот результат. Обратите внимание, что версия SH встроенного echo не позволяет использовать echo -en хотя /bin/echo -en работает, мы используем printf вместо этого.

 #!/bin/sh x_TERM=`stty -g` stty -icanon -echo printf "\033[6n" ESCPOS="" X="" I=0 while [ ! "$X" = "R" ]; do X=`dd bs=1 count=1 2>/dev/null` I=`expr $I + 1` if [ $I -gt 2 -a ! "$X" = "R" ]; then ESCPOS="$ESCPOS$X" fi done stty "$x_TERM" #echo "$ESCPOS" CSRLIN=`echo "$ESCPOS" | cut -d \; -s -f 1` POS=`echo "$ESCPOS" | cut -d \; -s -f 2` echo "$CSRLIN" #exit 0 <= dont use inline 

Я использовал один и тот же код в двух разных скриптах, один выводит CSRLIN , другой POS .

EDIT: вам нужно встроить этот скрипт, чтобы использовать его в другом скрипте (например, . CSRLIN , поскольку оболочка должна быть в интерактивном режиме.

ура

Павел

  • Экранирование строк в ассоциативных массивах (bash)
  • Проблема с пониманием привязок ключей
  • Вызов bash из sh (тире) с командами, считанными из args, и «Unterminated quoteed string» / «неожиданный EOF»
  • Как избежать одиночной цитаты?
  • Шаблон соответствия \\\ ", используя grep
  • Выход из режима «>» в ​​оболочке Unix
  • Проблема с скриптом с пробелами в имени файла
  • Квадратный кронштейн квадратной скобки A ^ [[A - Что это значит?
  • Скопируйте скобки в PS1
  • Является ли символ `\` escape или становится частью моего пароля ssh key
  • Символы запуска оболочки для sh-c
  • Interesting Posts

    простой сценарий цикла для построения подсети ipv6

    Синхронизировать KMail и KOrganizer с моими данными Google

    Как добавить номер строки, следуя вкладке в текстовый файл

    Отключить и включить модули в apache CentOS7

    awk изменит следующую строку после сопоставления шаблона, основанного на другом совпадении шаблонов

    Удалите несколько строк после соответствия шаблону, но только после соответствия шаблону

    Как захватить стандартный вывод скрипта, который зависит от пользователя для ввода?

    Извлечение каталога из stdout из wget

    vsftpd закрывает соединение с кодом 421 при перечислении содержимого каталога

    BASH: проблемы с Fifo – кажется избирательным в отношении ввода

    Каков дескриптор файла 3, назначенный по умолчанию?

    Как grub2 загружает ядро ​​из тома LVM?

    Распаковка файла с восклицательным знаком из командной строки в сценарии bash

    Возможно ли резервное копирование и восстановление пользовательских действий Thunar?

    iconv (для использования с rsync), чтобы избежать недопустимых имен файлов Windows в локальном разделе NTFS

    Linux и Unix - лучшая ОС в мире.