Эмуляция

Эмуля́ция () в вычислительной технике — комплекс программных, аппаратных средств или их сочетание, предназначенное для копирования (или эмулирования) функций одной вычислительной системы (гостя) на другую, отличную от первой, вычислительную систему (хост) таким образом, чтобы эмулированное поведение как можно ближе соответствовало поведению оригинальной системы (гостя). Целью является максимально точное воспроизведение поведения в отличие от разных форм компьютерного моделирования, в которых имитируется поведение некоторой абстрактной модели. Например, моделирование урагана или химической реакции не является эмуляцией.

Эмуляция в вычислительной технике 
Эмуляция связана с возможностью компьютерной программы в одном устройстве эмулировать (имитировать) другую программу или устройство. Например, многие принтеры разработаны таким образом, чтобы эмулировать принтеры HP Laserjet, так как для данных принтеров существует большое количество программного обеспечения. Если принтер, не произведенный HP, эмулирует принтер HP, тогда любая программа, разработанная для принтеров HP, сможет работать и с принтером другого производителя, получая при этом идентичную печать.

Аппаратная эмуляция представлена эмуляторами, выполненными в виде отдельного устройства. Например, DOS-совместимые карты расширения наподобие Centris 610 и Performa 630, устанавливавшиеся в некоторые Macintosh для обеспечения возможности запуска DOS-программ с ПК. Другим примером являются аппаратные эмуляторы на основе ППВМ.

Теоретически, согласно тезису Чёрча — Тьюринга, любая операционная среда может быть эмулирована на другой. Однако на практике зачастую это бывает крайне затруднительно ввиду того, что точное поведение эмулируемой системы не документировано и его возможно определить только посредством обратной разработки. В тезисе также не говорится о том, что если производительность эмуляции меньше, чем у оригинальной системы, то эмулируемое программное обеспечение будет работать существенно медленнее, нежели должно на оригинальном оборудовании, с возможным возникновением остановок эмуляции или неустойчивой производительностью.

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

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

Эмуляция адресует аппаратное и программное окружение оригинального цифрового устройства и воссоздаёт его на современной машине. Эмуляция позволяет пользователю получить доступ к любому типу прикладного программного обеспечения или операционных систем на современной платформе, причем программное обеспечение выполняется так же, как и в оригинальном окружении. Джеффри Ротенберг (Jeffery Rothenberg), один из первых сторонников применения эмуляции для электронного архивирования, считает, что «идеальным было бы единое расширяемое долговременное решение, которые могло бы быть разработанным раз и навсегда и применялось бы единообразно, автоматически и синхронно (например, каждый цикл обновления) ко всем типам документов и носителей». Далее он замечает, что это решение должно применяться не только к устаревшим системам, но и быть легко переносимым на пока неизвестные будущие системы. На практике в случае, если выпускается новая версия приложения с целью обеспечения совместимости и миграции всех входящих в него компонентов, необходимо для этого приложения создать эмулятор, обеспечивающий доступ ко всем упомянутым компонентам.

Достоинства 
 Эмуляция сохраняет вид, поведение и ощущение от оригинальных систем, что не менее важно, чем данные сами по себе.
 Несмотря на высокую изначальную стоимость создания эмулятора, со временем эмуляторы могут становиться более финансово выгодным решением.
 Сокращает трудозатраты, так как вместо долгой и постоянно продолжающейся работы по миграции данных для каждого цифрового объекта при внесении библиотек приложений и операционных систем прошлого и настоящего в эмулятор для работы со всеми документами можно использовать одинаковые технологии.
 Многие эмуляторы разработаны и доступны под лицензией GNU General Public License как открытое программное обеспечение, что расширяет масштабы сотрудничества.
 Эмуляция позволяет использовать программное обеспечение, эксклюзивное для одной платформы, на другой платформе. Например, игры, эксклюзивные для PlayStation 2, могут быть эмулированы на ПК или Xbox One. Это особенно полезно, когда оригинальная система труднодоступна для обретения или несовместима с современным оборудованием (например, старые игровые приставки может быть технически невозможно подключить к современным телевизорам).

Препятствия 
 Интеллектуальная собственность. Многие технологические компании, чтобы занять свою нишу на рынке, применяют при разработке своих продуктов нестандартизированные функции, постоянно внедряя улучшения, чтобы продукт оставался конкурентоспособным. Хоть это и приносит пользу, насыщая рынок технологичными продуктами и увеличивая рыночную долю продукта, это создаёт существенные проблемы пользователям, занимающимся архивированием, ввиду отсутствия всей необходимой документации, так как аппаратное и программное обеспечение проприетарно по своей сути.
 Законы об авторских правах до сих пор не регламентируют защиту документации и спецификаций проприетарного оборудования и программ, встроенных в эмулятор.
 Эмуляция часто используется в пиратских целях, поскольку эмуляторы освобождают пользователя от необходимости покупать оригинальное устройство, например игровую консоль, и крайне редко содержат какие-либо средства противодействия использованию нелегальных копий. Это приводит к весомой неопределенности правового положения эмуляции и к тому, что в программное обеспечение закладываются средства, препятствующие его работе в случае их запуска на эмуляторе. В компьютерных играх пользователь иногда может продолжить игру, но на последующих уровнях игра может становиться невозможной, что воспринимается либо как небрежность программиста, либо как просто чрезмерная сложность. Такая защита способствует созданию более точных эмуляторов, которые бы не вызывали срабатывание программной защиты, которая зачастую не очевидна.

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

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

Применение эмуляции для разработки новых систем 
Разные виды эмуляции широко используются при разработке и проектировании новых систем. Эмуляция упрощает разработку, давая возможность определить, исследовать и устранить недостатки проекта до его физического воплощения. Особенно эмуляция полезна при разработке многоядерных систем, в которых конфликты параллельной обработки часто достаточно сложно определить и диагностировать без применения виртуальной управляемой аппаратуры, доступной при эмуляции. Также эмуляция позволяет приступить к разработке программного обеспечения до фактического изготовления аппаратной части, таким образом проверяя заложенные в неё особенности.

Виды эмуляции 
В большинстве существующих эмуляторов воспроизводится только аппаратное обеспечение. Таким образом, если требуется операционная система, хранящаяся в ПЗУ, или другое программное обеспечение, его следует получить дополнительно (впрочем, оно тоже может быть эмулировано). В дальнейшем и операционная система, и программное обеспечение будут интерпретированы эмулятором таким же образом, как и на изначальном оборудовании. Кроме интерпретатора эмулированных двоичных машинных кодов также должно эмулироваться и некоторое другое оборудование (например, вводные и выводные устройства). Например, если запись в определенную область памяти должна выводить что-то на экран, такое поведение также должно быть эмулировано.

В пределе эмулятор должен исходить из модели, созданной на основе параметров и особенностей оригинального схемотехнического решения, включающего виртуальный источник питания, но на практике это было бы исключительным решением. Как правило, эмуляторы отталкиваются от модели, построенной на имеющейся документации и логической схеме устройства. Для эмуляции некоторых систем важным оказывается высокая точность эмуляции вплоть до тактовой частоты отдельных элементов, недокументированных функций, непредсказуемых аналоговых компонентов и допущенных ошибок. Особенно это важно при реализации эмуляторов классических домашних компьютеров типа Commodore 64, программы для которых часто пользуются утонченными низкоуровневыми приемами программирования, разработанными создателями игры и демосценой.

Наоборот, некоторые другие устройства имели очень ограниченный прямой доступ к оборудованию. В подобных случаях может быть достаточно простого слоя совместимости. Системные запросы эмулируемой программы транслируются в системные запросы хоста, то есть в системах FreeBSD, NetBSD и OpenBSD для запуска Linux-приложений с закрытым кодом используется слой совместимости с Linux. Например, графический процессор Nintendo 64 был полностью программируемым, и большинство разработчиков игр использовало заложенные заводские программы, которые были самодостаточными и обменивались информацией с игрой через буфер FIFO. Поэтому многие эмуляторы вообще не эмулируют графический процессор, интерпретируя вместо этого команды центрального процессора так же как и оригинальная программа.

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

Эмуляция математического сопроцессора применяется для запуска программ, скомпилированных с использованием математических инструкций, на машинах без установленного сопроцессора, на которых дополнительная нагрузка на центральный процессор может негативно сказаться на производительности. Если сопроцессор не установлен и не встроен в центральный процессор, при выполнении математической инструкции будет вызвано прерывание (отсутствие сопроцессора), запускающее подпрограмму математического эмулятора. После успешного выполнения инструкции управление возвращается программе.

Структурный состав эмулятора 
Как правило эмулятор состоит из нескольких модулей, каждый из которых соответствует отдельной эмулируемой подсистеме оригинального устройства. В наиболее общем случае эмулятор состоит из следующих блоков:
 модуль эмуляции или симуляции CPU (в данном случае термины практически равнозначны);
 модуль эмуляции подсистемы памяти;
 модули эмуляции различных устройств ввода-вывода.

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

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

Однако даже если эмулируемое устройство не содержит MMU, существуют и другие факторы, нарушающие эквивалентность логической и физической памяти: многие (если не все) архитектуры обладают отображаемыми в ОЗУ портами ввода-вывода; даже те, которые ими не обладают, имеют блоки памяти, отображаемые в ПЗУ. Это значит, что представление памяти в виде массива не должно применяться, если требуется эмулировать ПЗУ. Функции типа переключения банков или сегментной адресации также могут усложнить эмуляцию памяти.

В результате большинство эмуляторов имеет по меньшей мере две процедуры — для чтения из памяти и для записи в память, — которые ответственны за доступ к правильной области правильного объекта.

Для эмуляции систем с ограниченной адресацией, где адреса памяти с 0 по (размер ПЗУ) — 1 доступны только для чтения, а все остальные принадлежат ОЗУ, что-то подобное следующему является вполне типичным.

void WriteMemory(word Address, word Value) {
    word RealAddress;
    RealAddress = Address + BaseRegister;
    if ((RealAddress < LimitRegister) &&
        (RealAddress > ROMSIZE)) {
        Memory[RealAddress] = Value;
    } else {
        RaiseInterrupt(INT_SEGFAULT);
    }
}

word ReadMemory(word Address) {
    word RealAddress;
    RealAddress=Address+BaseRegister;
    if (RealAddress < LimitRegister) {
        return Memory[RealAddress];
    } else {
        RaiseInterrupt(INT_SEGFAULT);
        return NULL;
    }
}

Центральный процессор 
Как правило, модуль CPU — самая сложная часть эмулятора. Во многих эмуляторах используются предварительно «подготовленные» модули CPU, чтобы сосредоточиться на качественной и эффективной эмуляции.

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

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

void Execute(void) {
    if (Interrupt != INT_NONE) {
        SuperUser = TRUE;
        WriteMemory(++StackPointer, ProgramCounter);
        ProgramCounter = InterruptPointer;
    }
    switch (ReadMemory(ProgramCounter++)) {
        /*
         * Handling of every valid instruction
         * goes here...
         */
        default:
        Interrupt = INT_ILLEGAL;
    }
}

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

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

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

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

В некоторых случаях, например при запуске старых игр, высокая скорость эмуляции может быть нежелательной, так как игры создавались без оглядки на производительность компьютеров будущего. В игре, разработанной для ПК с CPU 30 MHz, игроку может отводиться 300 игровых секунд на игровой уровень, в случае запуска той же игры на ПК с CPU 300 MHz игроку эти 300 игровых секунд будут соответствовать 30 реальным секундам. Другие программы, например некоторые программы для DOS, вообще не смогут запуститься на быстром компьютере. Практически, если эмулируется система, являвшаяся «чёрным ящиком», изменения в ядре которого не ожидались, программы могут зависеть от некоторых специфических параметров оборудования (например, частоты CPU). Таким образом, для правильной эмуляции подобных приложений требуется очень точное управление скоростью эмуляции.

Ввод и вывод 
Как уже было отмечено, системные шины эмулируются редко. Каждое устройство ввода-вывода рассматривается отдельно, потому как в эмуляторе отсутствует реализация какого-либо универсального интерфейса. Так как каждое устройство ввода-вывода может быть идеально подогнано к параметрам эмулированного устройства, это даёт выигрыш в производительности. Однако решения на основе стандартизованных, унифицированных API всё же могут составить конкуренцию упрощённым моделям в случае их грамотной, искусной реализации. Дополнительным преимуществом будет «автоматически» получаемая служба плагинов, через которую с эмулятором смогут работать сторонние виртуальные устройства. В унифицированных API ввода-вывода необязательно повторять полную структуру шины: её схемотехника ограничена несколькими электронными компонентами, таким образом, в программной реализации необязательно наличие системы разрешения конфликтов параллельных вычислений.

Даже в эмуляторах, рассматривающих отдельно каждое устройство, как правило присутствует следующая виртуальная инфраструктура:
 управление прерываниями посредством процедуры, которая устанавливает флаги, считываемые эмулятором CPU, когда объявлено прерывание, что позволяет виртуальному CPU «опрашивать прерывания»;
 запись и чтение физической памяти посредством двух процедур, подобных обслуживающим логическую память (однако в отличие от последнего, первые часто могут быть заменены простыми ссылками на массив памяти).

Эмуляция и симуляция 
Слово «эмулятор» было придумано в IBM при разработке серии продуктов NPL (IBM System/360), используя «новую комбинацию программы, микрокода и оборудования». Они обнаружили, что для исполнения программ, написанных для старых машин IBM, использование аппаратного Микрокода намного выгоднее по производительности, нежели программная симуляция. Ранее, в 1957 году, IBM поставляла программный интерпретатор для возможности запуска программ для более старого компьютера IBM 704 на компьютерах IBM 709 и IBM 7090. В 1964 году инженеры IBM придумали слово «эмуляция» для описания концепции первого применения микрокода для ускорения процесса симуляции.

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

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

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

Первое применение функционального моделирования осуществлено компанией Autonetics около 1960 года для тестирования программ на языке ассемблера, которые впоследствии должны были выполняться на военной машине D-17B. Это позволило писать, выполнять и тестировать полетное программное обеспечение до физического изготовления вычислительного оборудования D-17B. Эта же компания позднее применяла функциональное моделирование для тестирования полетного программного обеспечения, которое должно было выполняться на машине D-37C.

Эмуляция игровой приставки 

Эмулятор игровой приставки — это программа, которая позволяет на персональном компьютере или игровой приставке эмулировать другую приставку. Чаще всего их используют для запуска старых игр на ПК или более современных приставках. Также эмуляторы используют для создания любительского перевода игр, модификаций игр, а также для разработки такого пользовательского контента как демоверсии и новые игры для старых систем. В распространении этого вида эмуляции большую роль сыграл интернет, так как большая часть (если не все) эмуляторов не доступна в точках розничных продаж. Некоторые из эмуляторов, выпущенные в последние два десятилетия: Dolphin, ZSNES, MAME, DeSmuME, ePSXe, Gens, VisualBoyAdvance, Jnes и Nestopia.

Эмуляция терминала 

Эмулятор терминала — это программа для современного ПК или другого устройства, позволяющая получить интерактивный доступ к операционной системе мейнфрейма или другой системе хоста, например HP-UX или OpenVMS. Уже длительное время терминалы наподобие IBM 3270 и VT100 не производятся. Вместо этого используется программа, запускаемая на современной операционной системе, которая имитирует «глупый» терминал и способна отображать графические и текстовые элементы приложения хоста, отправлять клавиатурный ввод и обрабатывать команды через соответствующий протокол терминала. Некоторые из таких эмуляторов включают приложения для Attachmate Reflection, IBM Personal Communications, AlphaVM virtual machine от EmuVM, Stromasys CHARON-VAX/AXP и Micro Focus Rumba.

См. также 
 Список эмуляторов игровых консолей
 Компьютерное моделирование
 Некоторые виды эмуляторов:
 Эмулятор игровой приставки
 Эмулятор сервера
 Эмулятор терминала
 Эмулятор оптических дисководов
 Двоичная трансляция
 Внутрисхемный эмулятор:
 JTAG
 QEMU
 Виртуальная машина

Примечания

Литература 
 А. Аганичев, Д. Панфилов, М. Плавич, О. Полянский. Программно-аппаратный комплекс для отладки МП систем на основе микроконтроллеров семейства MC68HC11 фирмы MOTOROLA
 Шагурин И., Бродин В., Калинин Л., Толстов Ю., Петров С., Исенин И., Эйдельман С., Ванюлин В. Средства проектирования и отладки систем управления на базе МК фирмы Motorola.

Ссылки 
 Как написать эмулятор компьютера
 How to write a computer Emulator

Информатика
Эмуляторы