stringtranslate.com

Пакетный файл

Пакетный файл — это файл сценария в DOS , OS/2 и Microsoft Windows . Он состоит из ряда команд , которые должны быть выполнены интерпретатором командной строки , и хранится в текстовом файле. Пакетный файл может содержать любую команду, которую интерпретатор принимает интерактивно, и использовать конструкции, которые позволяют выполнять условные ветки и циклы в пакетном файле, например IF, FOR, и GOTO метки . Термин «пакет» происходит от пакетной обработки , что означает «неинтерактивное выполнение», хотя пакетный файл может не обрабатывать пакет из нескольких данных.

Подобно Job Control Language (JCL), DCL и другим системам на мэйнфреймах и миникомпьютерных системах, пакетные файлы были добавлены для облегчения работы, необходимой для определенных регулярных задач, позволяя пользователю настроить сценарий для их автоматизации. Когда запускается пакетный файл, программа оболочки (обычно COMMAND.COM или cmd.exe ) считывает файл и выполняет его команды, обычно построчно. [1] Unix-подобные операционные системы , такие как Linux , имеют похожий, но более гибкий тип файла, называемый скриптом оболочки . [2]

Расширение имени файла .bat используется в DOS и Windows. Windows NT и OS/2 также добавили .cmd . Пакетные файлы для других сред могут иметь другие расширения, например, .btm в оболочках 4DOS , 4OS2 и 4NT .

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

Варианты

ДОС

В MS-DOS пакетный файл можно запустить из интерфейса командной строки, введя его имя, а затем любые требуемые параметры и нажав ↵ Enterклавишу. При загрузке DOS файл AUTOEXEC.BAT , если он присутствует, выполняется автоматически, поэтому любые команды, которые необходимо выполнить для настройки среды DOS, можно поместить в этот файл. Пользователи компьютеров могут использовать файл AUTOEXEC.BAT для установки системной даты и времени, инициализации среды DOS, загрузки любых резидентных программ или драйверов устройств или инициализации сетевых подключений и назначений.

Расширение имени файла .bat идентифицирует файл, содержащий команды, которые выполняются интерпретатором команд COMMAND.COM построчно, как если бы это был список команд, введенных вручную, с некоторыми дополнительными командами, специфичными для пакетного файла, для основных функций программирования, включая GOTOкоманду для изменения потока выполнения строк.

Ранние версии Windows

Microsoft Windows была представлена ​​в 1985 году как графический пользовательский интерфейс (GUI) поверх текстовых операционных систем и была разработана для работы в DOS. Для ее запуска WINиспользовалась команда, которую можно было добавить в конец файла AUTOEXEC.BAT , чтобы разрешить автоматическую загрузку Windows. В более ранних версиях можно было запустить файл типа .bat из Windows в командной строке MS-DOS. Windows 3.1x и более ранние версии, а также Windows 9x вызывали COMMAND.COM для запуска пакетных файлов.

ОС/2

Операционная система IBM OS/2 поддерживала пакетные файлы в стиле DOS. Она также включала версию REXX , более продвинутого языка сценариев пакетных файлов . IBM и Microsoft начали разрабатывать эту систему, но во время ее создания расстались из-за спора; в результате IBM ссылалась на свою консольную оболочку в стиле DOS без упоминания Microsoft, называя ее просто DOS, хотя это, по-видимому, не имело никакого значения в отношении того, как пакетные файлы работали из COMMAND.COM.

Интерпретатор пакетных файлов OS/2 также поддерживает команду EXTPROC. Она передает пакетный файл в программу, указанную в файле EXTPROC, как файл данных. Указанная программа может быть файлом сценария; это похоже на механизм #!, используемый в операционных системах типа Unix .

Windows NT

В отличие от Windows 98 и более ранних версий, семейство операционных систем Windows NT не зависит от MS-DOS. Windows NT представила усовершенствованный 32-разрядный интерпретатор команд ( cmd.exe ), который мог выполнять скрипты с расширением .CMD или .BAT. Cmd.exe добавил дополнительные команды и реализовал существующие немного другим способом, так что один и тот же пакетный файл (с другим расширением) может работать по-разному с cmd.exe и COMMAND.COM. В большинстве случаев работа идентична, если не используются несколько неподдерживаемых команд. Расширения Cmd.exe для COMMAND.COM можно отключить для совместимости.

Microsoft выпустила версию cmd.exe для Windows 9x и ME под названием WIN95CMD, чтобы позволить пользователям старых версий Windows использовать определенные пакетные файлы в стиле cmd.exe.

Начиная с Windows 8 , cmd.exe является обычным интерпретатором команд для пакетных файлов; более старый COMMAND.COM также может быть запущен в 32-разрядных версиях Windows, способных запускать 16-разрядные программы. [примечание 1]

Расширения имени файла

.bat
Первое расширение имени файла, используемое Microsoft для пакетных файлов. Это расширение работает с DOS и всеми версиями Windows, под COMMAND.COM или cmd.exe, несмотря на различные способы выполнения пакетных файлов двумя командными интерпретаторами.
.cmd
Используется для пакетных файлов в семействе Windows NT и отправляется в cmd.exe для интерпретации. COMMAND.COM не распознает это расширение имени файла, поэтому скрипты cmd.exe не выполняются в неправильной среде Windows по ошибке. Кроме того, команды append, dpath, ftype, set, path, assocи promptпри выполнении из файла .bat изменяют значение переменной errorlevelтолько при возникновении ошибки, тогда как из файла .cmd они будут влиять на errorlevel даже при возврате без ошибки. [3] Он также используется в OS/2 IBM для пакетных файлов.
.бтм
Расширение, используемое 4DOS , 4OS2 , 4NT и Take Command . Эти скрипты работают быстрее, особенно длинные, так как скрипт загружается полностью готовым к выполнению, а не построчно. [4]

Параметры пакетного файла

COMMAND.COM и cmd.exe поддерживают специальные переменные ( от %0, %1до %9) для ссылки на путь и имя пакетного задания и первые девять параметров вызова из пакетного задания, см. также SHIFT. Несуществующие параметры заменяются строкой нулевой длины. Их можно использовать аналогично переменным среды , но они не хранятся в среде. Microsoft и IBM называют эти переменные параметрами замены или заменяемыми параметрами , тогда как Digital Research, Novell и Caldera ввели для них термин переменные замены [5] . JP Software называет их параметрами пакетного файла . [6]

Примеры

В этом примере пакетный файл отображает Hello World!, запрашивает и ждет, пока пользователь нажмет клавишу, а затем завершает работу. (Примечание: не имеет значения, являются ли команды строчными или заглавными, если только не работают с переменными)

@ ECHO OFF ECHO Привет, мир! ПАУЗА

Чтобы выполнить файл, его необходимо сохранить с расширением .bat (или .cmd для операционных систем типа Windows NT) в формате простого текста, обычно создаваемого с помощью текстового редактора, такого как Microsoft Notepad , или текстового процессора, работающего в режиме простого текста.

При выполнении отобразится следующее:

Привет, мир!Нажмите любую клавишу, чтобы продолжить...

Объяснение

Интерпретатор выполняет каждую строку по очереди, начиная с первой. @Символ в начале любой строки не позволяет подсказке отображать эту команду по мере ее выполнения. Команда ECHO OFFотключает подсказку навсегда или до тех пор, пока она не будет включена снова. Объединенная @ECHO OFFчасто, как здесь, является первой строкой пакетного файла, предотвращая отображение любых команд, включая ее саму. Затем выполняется следующая строка, и команда ECHO Hello World!выводит Hello World!. Выполняется следующая строка, и PAUSEкоманда отображает Press any key to continue . . .и приостанавливает выполнение скрипта. После нажатия клавиши скрипт завершается, так как больше нет команд. В Windows, если скрипт выполняется из уже запущенного окна командной строки , окно остается открытым в подсказке, как в MS-DOS; в противном случае окно закрывается по завершении.

Ограничения и исключения

Нулевые значения в переменных

Расширения переменных подставляются текстуально в команду, и таким образом переменные, которые ничего не содержат, просто исчезают из синтаксиса, а переменные, которые содержат пробелы, превращаются в несколько токенов. Это может привести к синтаксическим ошибкам или багам.

Например, если %foo% пуст, этот оператор:

IF  %foo% == bar ECHO Равно

анализируется как ошибочная конструкция:

ЕСЛИ ==bar ECHO Равно

Аналогично, если %foo%содержит abc def, то возникает другая синтаксическая ошибка:

ЕСЛИ abc def == bar ECHO Равно

Обычный способ предотвратить эту проблему — заключить расширения переменных в кавычки, чтобы пустая переменная расширялась в допустимое выражение IF ""=="bar"вместо недопустимого IF ==bar. Текст, который сравнивается с переменной, также должен быть заключен в кавычки, поскольку кавычки не являются специальным разделительным синтаксисом; эти символы представляют сами себя.

ЕСЛИ  " %foo% " == "bar"  ECHO Равно

Отложенное расширение !VARIABLE!, доступное в Windows 2000 и более поздних версиях, может использоваться для избежания этих синтаксических ошибок. В этом случае переменные null или multiword не терпят синтаксической ошибки, поскольку значение расширяется после разбора команды IF:

IF  !foo! == bar ECHO Равно

Другое отличие в Windows 2000 или выше заключается в том, что пустая переменная (неопределенная) не подставляется. Как описано в предыдущих примерах, предыдущее поведение пакетного интерпретатора привело бы к пустой строке. Пример:

C:\> set  MyVar = C:\> echo  %MyVar% %MyVar%C:\> если  " %MyVar% " == ""  ( echo MyVar не определена )  else  ( echo MyVar это %MyVar% ) MyVar это %MyVar%

Пакетные интерпретаторы до Windows 2000 отображали результат MyVar is not defined.

Кавычки и пробелы в передаваемых строках

В отличие от процессов Unix/POSIX, которые получают аргументы командной строки, уже разделенные оболочкой на массив строк, процесс Windows получает всю командную строку как одну строку через функцию API GetCommandLine. В результате каждое приложение Windows может реализовать свой собственный парсер для разделения всей командной строки на аргументы. Многие приложения и инструменты командной строки разработали собственный синтаксис для этого, и поэтому не существует единого соглашения для кавычек или экранирования метасимволов в командных строках Windows.

Если строка содержит кавычки и должна быть вставлена ​​в другую строку текста, которая также должна быть заключена в кавычки, необходимо уделить особое внимание механизму кавычек:

C:\> set  foo = "эта строка заключена в кавычки"C:\> echo  "test 1 %foo% " "test 1 "эта строка заключена в кавычки""C:\> eventcreate /T Предупреждение /ID 1 /L Система /SO "Источник" /D "Пример: %foo% " ОШИБКА: Недопустимый аргумент/параметр - 'string'. Введите "EVENTCREATE /?" для использования.

В Windows 2000 и более поздних версиях решение заключается в замене каждого вхождения символа кавычек в значении серией из трех символов кавычек:

C:\> set  foo = "эта строка заключена в кавычки"C:\> set  foo = %foo:"="""%C:\> echo  "test 1 %foo% " "test 1 """эта строка заключена в кавычки""""C:\> eventcreate /T Warning /ID 1 /L System /SO "Источник" /D "Пример: %foo% " УСПЕХ: Событие типа "Предупреждение" создано в журнале/источнике "Источник".

Экранированные символы в строках

Некоторые символы, такие как |символы вертикальной черты ( ), имеют особое значение в командной строке. Их нельзя напечатать как текст с помощью команды ECHO , если только они не экранированы с помощью символа вставки ^:

C:\> echo foo | bar «bar» не является внутренней или внешней командой, исполняемой программой или пакетным файлом.C:\> echo foo ^| bar foo | bar

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

C:\> set  foo = bar | baz «baz» не является внутренней или внешней командой, исполняемой программой или пакетным файлом.C:\> set  foo = bar ^| baz C:\> echo  %foo% 'baz' не является внутренней или внешней командой, исполняемой программой или пакетным файлом.C:\> set  foo = bar ^^^| baz C:\> echo  %foo% bar | Баз

Отложенное расширение, доступное в Windows 2000 и более поздних версиях, может использоваться для отображения специальных символов, хранящихся в переменных среды, поскольку значение переменной расширяется после анализа команды:

C:\> cmd /V:ON Microsoft Windows [Версия 6.1.7601] Авторские права (c) 2009 Microsoft Corporation. Все права защищены.C:\> set  foo = bar ^| baz C:\> echo  !foo! бар | Баз

Сон или запрограммированная задержка

До появления команды TIMEOUT в Windows Vista не существовало простого способа реализовать временную паузу, поскольку команда PAUSE останавливает выполнение скрипта на неопределенный срок до тех пор, пока не будет нажата какая-либо клавиша.

Было возможно множество обходных путей [10], но они работали только в некоторых средах: CHOICEкоманда была недоступна в старых версиях DOS, PINGбыла доступна только при установленном TCP/IP и т. д. Microsoft не предлагала никакого решения, но ряд небольших служебных программ можно было установить из других источников. Коммерческим примером может служить команда Norton Utilities Batch Enhancer (BE) 1988 года, которая BE DELAY 18ждала 1 секунду, или бесплатная 94-байтовая WAIT.COM [11] , которая WAIT 5ждала 5 секунд, а затем возвращала управление сценарию. Большинство таких программ представляют собой 16-битные файлы .COM, поэтому они несовместимы с 64-битной Windows.

Вывод текста с удаленными CR/LF

Обычно весь печатный текст автоматически содержит управляющие символы возврата каретки (CR) и перевода строки (LF), добавляемые в конец каждой строки.

Не имеет значения, находятся ли две команды echo в одной и той же командной строке; коды CR/LF вставляются для разбиения вывода на отдельные строки:

C:\> @ echo Сообщение 1 &@ echo Сообщение 2 Сообщение 1 Сообщение 2

Трюк, обнаруженный в Windows 2000 и более поздних версиях, заключается в использовании специального приглашения для ввода для вывода текста без CR/LF, завершающих текст. В этом примере CR/LF не следует за сообщением 1, но следует за строкой 2 и строкой 3:

Это можно использовать для вывода данных в текстовый файл без добавления CR/LF в конец:

C:\> set  /p  = "Сообщение 1" < nul > data.txt C:\> set  /p  = "Сообщение 2" < nul >> data.txt C:\> set  /p  = "Сообщение 3" < nul >> data.txt C:\> type data.txt Сообщение 1Сообщение 2Сообщение 3

Однако нет возможности напрямую внедрить этот урезанный вывод приглашения CR/LF в переменную среды.

Установка рабочего каталога в соответствии с соглашением об унифицированных именованиях (UNC) с помощью ярлыка

Невозможно иметь командную строку, которая использует UNC-путь в качестве текущего рабочего каталога; например\\server\share\directory\

Командная строка требует использования букв дисков для назначения рабочего каталога, что затрудняет запуск сложных пакетных файлов, хранящихся на общем ресурсе UNC сервера. Хотя пакетный файл можно запустить из пути к файлу UNC, рабочим каталогом по умолчанию является C:\Windows\System32\.

В Windows 2000 и более поздних версиях обходным решением является использование команды PUSHDи POPDс расширениями команд. [примечание 2]

Если расширения команд не включены по умолчанию, их можно временно включить с помощью /E:ONпереключателя для интерпретатора команд.

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

Атрибут рабочего каталога этого ярлыка игнорируется.

Это также решает проблему, связанную с контролем учетных записей пользователей (UAC) в Windows Vista и более новых версиях. Когда администратор вошел в систему и UAC включен, и он пытается запустить пакетный файл как администратор из буквы сетевого диска, используя контекстное меню файла, вызываемое правой кнопкой мыши, операция неожиданно завершается ошибкой. Это происходит из-за того, что контекст учетной записи с повышенными правами UAC не имеет назначений букв сетевых дисков, и невозможно назначить буквы дисков для повышенного контекста через оболочку проводника или сценарии входа. Однако, создав ярлык для пакетного файла с помощью приведенной выше конструкции PUSHD/ POPDи используя ярлык для запуска пакетного файла как администратор, временная буква диска будет создана и удалена в контексте учетной записи с повышенными правами, и пакетный файл будет работать правильно.

Следующий синтаксис правильно расширяется до пути текущего пакетного скрипта.

%~dp0

Пути UNC по умолчанию отключены, поскольку они приводили к сбоям в работе старых программ. [12]

Значение реестра Dword DisableUNCCheckв HKEY_CURRENT_USER\Software\Microsoft\Command Processor[12] позволяет использовать каталог по умолчанию в качестве UNC. CDКоманда откажется вносить изменения, но можно поместить путь UNC в каталог по умолчанию с помощью ярлыка Cmd или с помощью команды «Пуск». ( C$Share предназначен для администраторов).

Набор символов

Пакетные файлы используют набор символов OEM, как определено компьютером, например, кодовая страница 437. Не-ASCII части этих файлов несовместимы с наборами символов Unicode или Windows, которые в противном случае используются в Windows, поэтому необходимо соблюдать осторожность. [13] Неанглийские имена файлов работают только если они введены через редактор, совместимый с набором символов DOS. Имена файлов с символами вне этого набора не работают в пакетных файлах.

Чтобы получить командную строку с Unicode вместо кодовой страницы 437 или аналогичной, можно использовать cmd /Uкоманду. В такой командной строке будет работать пакетный файл с именами файлов в Unicode. Также можно использовать cmd /Uдля прямого выполнения команд с Unicode в качестве набора символов. Например, cmd /U /C dir > files.txtсоздает файл, содержащий список каталогов с правильными символами Windows в кодировке UTF-16 LE.

Пакетные вирусы и вредоносные программы

Как и в случае с любым другим языком программирования, пакетные файлы могут использоваться злонамеренно. Простые трояны и форк-бомбы легко создаются, а пакетные файлы могут выполнять форму отравления DNS , изменяя файл hosts . Пакетные вирусы возможны и могут также распространяться через USB-флешки , используя функцию автозапуска Windows . [14]

Следующая команда в пакетном файле удалит все данные в текущем каталоге (папке) — без предварительного запроса подтверждения:

дель /Q *.*

Эти три команды представляют собой простую форк-бомбу , которая будет постоянно воспроизводить себя, истощая доступные системные ресурсы, замедляя или вызывая сбой системы:

: TOP  начать  ""  %0  перейти  к TOP

Другие языки сценариев Windows

Командный процессор cmd.exe, который интерпретирует файлы .cmd, поддерживается во всех 32-разрядных версиях Windows вплоть до Windows 10 и 64-разрядных версиях Windows вплоть до Windows 11. COMMAND.EXE, который интерпретирует файлы .BAT, поддерживался во всех 16-разрядных и 32-разрядных версиях, как минимум, до Windows 10. [примечание 3]

Существуют и другие, более поздние и более мощные языки сценариев, доступные для Windows. Однако для их использования требуется установить интерпретатор языка сценариев:

Файлы скриптов запускаются, если введено имя файла без расширения. Существуют правила приоритета, регулирующие интерпретацию, скажем, DoThisесли существуют DoThis.com, DoThis.exe, DoThis.bat, , и т. д.; по умолчанию имеет наивысший приоритет. Этот порядок по умолчанию может быть изменен в более новых операционных системах с помощью устанавливаемой пользователем переменной среды PATHEXT .DoThis.cmdDoThis.com

Смотрите также

Примечания

  1. ^ Чтобы убедиться, что COMMAND.COM остается доступным (в каталоге \WINDOWS\SYSTEM32), введите COMMAND.COMв командной строке 32-разрядной Windows 7.
  2. ^ "Если включены расширения команд, команда PUSHD принимает сетевые пути в дополнение к обычной букве диска и пути. Если указан сетевой путь, PUSHD создает временную букву диска, которая указывает на указанный сетевой ресурс, а затем изменяет текущий диск и каталог, используя новую определенную букву диска. Временные буквы дисков назначаются от Z: и ниже, используя первую найденную неиспользуемую букву диска." --Справка по PUSHD в Windows 7
  3. ^ Доступность CMD.EXE и COMMAND.COM можно проверить, вызвав их в любой версии Windows (COMMAND.COM отсутствует в 64-разрядных версиях; вероятно, доступен только в 32-разрядных версиях Windows 8, если установлена ​​опция поддержки 16-разрядных программ).

Ссылки

  1. ^ "Использование пакетных файлов: Сценарии; Службы управления". Technet.microsoft.com. 2005-01-21. Архивировано из оригинала 2011-12-28 . Получено 2012-11-30 .
  2. ^ Генри-Стокер, Сандра (18.07.2007). «Используйте свои навыки написания сценариев Unix для написания пакетного файла». itworld.com . IT World. Архивировано из оригинала 14.06.2018 . Получено 13.06.2018 .
  3. ^ "Разница между bat и cmd | WWoIT - Wayne's World of IT". waynes-world-it.blogspot.fr . 2012-11-15. Архивировано из оригинала 2014-03-02 . Получено 2012-11-30 .
  4. ^ "расширение файла btm :: все о типе файла .btm". Cryer.co.uk. Архивировано из оригинала 2008-10-11 . Получено 2012-11-30 .
  5. ^ Руководство пользователя Caldera DR-DOS 7.02, Caldera, Inc. , 1998 [1993, 1997], архивировано из оригинала 2016-11-05 , извлечено 2013-08-10
  6. ^ Братья, Хардин; Роусон, Том ; Конн, Рекс К .; Пол, Маттиас Р.; Дай, Чарльз Э.; Георгиев, Лучезар И. (27.02.2002). Онлайн-справка по 4DOS 8.00 .
  7. ^ ab ".NET Core Runtime: System.Diagnostics.Process.Unix". GitHub . Архивировано из оригинала 2023-03-29 . Получено 2020-02-11 . Две последовательные двойные кавычки внутри области inQuotes должны привести к буквальной двойной кавычке (анализатор остается в области inQuotes). Такое поведение не является частью спецификации code:ParseArgumentsIntoList, но совместимо с CRT и .NET Framework.
  8. ^ ab Deley, David. "How Command Line Parameters Are Parsed". Архивировано из оригинала 2020-06-08 . Получено 2020-06-08 .
  9. ^ "Документация по дочерним процессам, раздел Windows Command Line, NodeJS PR #29576". GitHub . Архивировано из оригинала 2022-08-21 . Получено 2020-02-11 .
  10. ^ "Как сделать задержку" Архивировано 20.11.2011 на Wayback Machine , ericphelps.com
  11. ^ "Утилиты для DOS, ссылки на WAIT.ZIP (архив WAIT.COM) и другие программы". Архивировано из оригинала 2011-11-13 . Получено 2011-11-15 .
  12. ^ ab "Cmd.exe не поддерживает имена UNC в качестве текущего каталога". Архивировано из оригинала 2015-05-18 . Получено 2015-04-28 .
  13. ^ Чен, Рэймонд . «Следите за кодовой страницей». Microsoft . Архивировано из оригинала 2012-01-17 . Получено 2011-12-13 .
  14. ^ Пакетные файлы — искусство создания вирусов Архивировано 29 октября 2013 г. на Wayback Machine
  15. ^ "Windows PowerShell - Unix приходит в Windows". Geekswithblogs.net. Архивировано из оригинала 2012-06-14 . Получено 2012-11-30 .

Внешние ссылки