В управлении памятью DOS , обычная память , также называемая базовой памятью , представляет собой первые 640 килобайт памяти на IBM PC или совместимых системах. Это память для чтения-записи, напрямую адресуемая процессором для использования операционной системой и прикладными программами. Поскольку цены на память быстро падали, это конструкционное решение стало ограничением в использовании больших объемов памяти до появления операционных систем и процессоров, которые сделали его неактуальным.
Барьер в 640 КБ является архитектурным ограничением IBM PC-совместимых ПК. Процессор Intel 8088 , используемый в оригинальном IBM PC , мог адресовать 1 МБ (2 20 байт), поскольку чип предлагал 20 адресных линий . В конструкции ПК память ниже 640 КБ предназначалась для оперативной памяти на материнской плате или на платах расширения и называлась областью обычной памяти.Первый сегмент памяти (64 КБ) обычной области памяти называется нижней памятью или областью нижней памяти . Оставшиеся 384 КБ за пределами обычной области памяти, называемые верхней областью памяти (UMA), были зарезервированы для системного использования и дополнительных устройств. UMA использовалась для ROM BIOS , дополнительной памяти только для чтения , расширений BIOS для фиксированных дисковых накопителей и видеоадаптеров, памяти видеоадаптера и других устройств ввода и вывода с отображением памяти . Конструкция оригинального IBM PC поместила карту памяти цветного графического адаптера (CGA) в UMA.
Потребность в большем объеме ОЗУ росла быстрее, чем потребности оборудования в использовании зарезервированных адресов, что привело к тому, что ОЗУ в конечном итоге было отображено в эти неиспользуемые верхние области для использования всего доступного адресуемого пространства. Это привело к появлению зарезервированной «дыры» (или нескольких дыр) в наборе адресов, занятых оборудованием, которые могли использоваться для произвольных данных. Избежать такой дыры было сложно и некрасиво, и это не поддерживалось DOS или большинством программ, которые могли работать на ней. Позже пространство между дырами использовалось как верхние блоки памяти (UMB).
Для поддержания совместимости со старыми операционными системами и приложениями барьер в 640 КБ оставался частью конструкции ПК даже после замены 8086/8088 на процессор Intel 80286 , который мог адресовать до 16 МБ памяти в защищенном режиме . Барьер в 1 МБ также оставался до тех пор, пока 286 работал в реальном режиме , поскольку DOS требовал реального режима, который использовал сегментные и смещенные регистры перекрывающимся образом, так что адреса с более чем 20 битами были невозможны. Он все еще присутствует в совместимых с IBM PC сегодня, если они работают в реальном режиме, таком как используемый DOS. Даже самые современные ПК Intel все еще имеют зарезервированную область между 640 и 1024 КБ . [3] [4] Однако это невидимо для программ (или даже большей части операционной системы) в более новых операционных системах (таких как Windows , Linux или Mac OS X ), которые используют виртуальную память , потому что они вообще не знают об адресах физической памяти. Вместо этого они работают в виртуальном адресном пространстве, которое определяется независимо от доступных адресов ОЗУ. [5]
Некоторые материнские платы имеют опцию "Memory Hole at 15 Megabytes", необходимую для определенных видеокарт VGA, которым требуется эксклюзивный доступ к одному конкретному мегабайту для видеопамяти. Более поздние видеокарты, использующие шину AGP (PCI memory space), могут иметь 256 МБ памяти с размером апертуры 1 ГБ .
Одним из методов, использовавшихся на ранних компьютерах IBM XT, была установка дополнительной оперативной памяти в диапазон адресов видеопамяти и перемещение предела до начала адаптера монохромного дисплея (MDA). Иногда для этого требовалось программное обеспечение или пользовательский декодер адреса . Это сдвинуло барьер до 704 КБ (с MDA/HGC) или 736 КБ (с CGA). [6] [7]
Менеджеры памяти в системах на базе 386 (такие как QEMM или MEMMAX (+V) в DR-DOS ) могли достичь того же эффекта, добавляя обычную память на 640 КБ и перемещая барьер до 704 КБ (до сегмента B000, начала MDA/HGC) или 736 КБ (до сегмента B800, начала CGA). [7] В этой ситуации можно было использовать только CGA, поскольку видеопамять Enhanced Graphics Adapter (EGA) непосредственно примыкала к области обычной памяти ниже линии 640 КБ; одна и та же область памяти не могла использоваться как для кадрового буфера видеокарты, так и для временных программ.
Дополнительные модули управления памятью All Computers AllCard для XT- [8] [9] и Chargecard [10] для компьютеров класса 286/386SX, а также дополнительная плата ECM (Extended Conventional Memory) компании MicroWay [11] позволяли отображать обычную память в диапазоне адресов A0000–EFFFF ( hex ), предоставляя до 952 КБ для программ DOS. Такие программы, как Lotus 1-2-3 , которые напрямую обращались к видеопамяти, требовали исправления для обработки этой структуры памяти. Поэтому барьер в 640 КБ был устранен за счет аппаратной совместимости. [10]
Также можно было использовать перенаправление консоли [12] (либо указав альтернативное консольное устройство, например AUX: при первоначальном вызове COMMAND.COM , либо позже используя CTTY ) для направления вывода и получения ввода с немого терминала или другого компьютера, на котором запущен эмулятор терминала . Если предположить, что системный BIOS все еще разрешает машине загружаться (что часто бывает, по крайней мере, с BIOS для встроенных ПК), видеокарту в так называемом безголовом компьютере можно было полностью удалить, и система могла предоставить в общей сложности 960 КБ непрерывной памяти DOS для загрузки программ.
Аналогичное использование было возможно на многих компьютерах, совместимых с DOS, но не совместимых с IBM, с нефрагментированной структурой памяти, например, на системах с шиной SCP S-100 , оснащенных картой ЦП CP-200B с процессором 8086 и до шестнадцати карт памяти SCP 110A (с 64 КБ ОЗУ на каждой из них) для общего объема до 1024 КБ (без видеокарты, но с использованием перенаправления консоли и после разметки загрузочного/BIOS ROM), [13] на Victor 9000 / Sirius 1 , которые поддерживали до 896 КБ, или на Apricot PC с более непрерывной памятью DOS, которая использовалась под его пользовательской версией MS-DOS.
Большинству стандартных программ, написанных для DOS, не обязательно требовалось 640 КБ или больше памяти. Вместо этого в дополнение к стандартному программному обеспечению DOS можно было использовать программное обеспечение драйверов и утилиты, называемые программами terminate-and-stay-resident (TSR). Эти драйверы и утилиты обычно использовали некоторую обычную память постоянно, уменьшая общий объем, доступный для стандартных программ DOS.
Вот некоторые очень распространённые драйверы DOS и TSR, использующие обычную память:
Как можно видеть выше, многие из этих драйверов и TSR можно было бы считать практически необходимыми для полнофункциональной работы системы. Но во многих случаях выбор должен был сделать пользователь компьютера, чтобы решить, иметь ли возможность запускать определенные стандартные программы DOS или загрузить все свои любимые драйверы и TSR. Загрузка всего списка, показанного выше, вероятно, либо непрактична, либо невозможна, если пользователь также хочет запустить стандартную программу DOS.
В некоторых случаях драйверы или TSR должны были быть выгружены из памяти для запуска определенных программ, а затем повторно загружены после запуска программы. Для драйверов, которые не могли быть выгружены, более поздние версии DOS включали возможность меню запуска, позволяющую пользователю компьютера выбирать различные группы драйверов и TSR для загрузки перед запуском определенных стандартных программ DOS с высоким потреблением памяти.
По мере того, как приложения DOS становились больше и сложнее в конце 1980-х и начале 1990-х годов, обычной практикой стало освобождение обычной памяти путем перемещения драйверов устройств и программ TSR в блоки верхней памяти (UMB) в верхней области памяти (UMA) при загрузке, чтобы максимизировать обычную память, доступную для приложений. Это имело преимущество в том, что не требовало изменений оборудования и сохраняло совместимость приложений.
Эта функция впервые была предоставлена сторонними продуктами, такими как QEMM , прежде чем была встроена в DR DOS 5.0 в 1990 году, а затем в MS-DOS 5.0 в 1991 году. Большинство пользователей использовали сопутствующий драйвер EMM386 , предоставленный в MS-DOS 5, но сторонние продукты от таких компаний, как QEMM, также оказались популярными.
При запуске драйверы могли быть загружены высоко с помощью директивы " DEVICEHIGH =", в то время как TSR могли быть загружены высоко с помощью директив " LOADHIGH ", " LH " или " HILOAD ". Если операция не удалась, драйвер или TSR автоматически загружались в обычную условную память.
CONFIG.SYS , загрузка ANSI.SYS в UMB, поддержка EMS не включена:
УСТРОЙСТВО=C:\DOS\HIMEM.SYSУСТРОЙСТВО=C:\DOS\EMM386.EXE NOEMSDEVICEHIGH=C:\DOS\ANSI.SYS
AUTOEXEC.BAT , загрузка MOUSE, DOSKEY и SMARTDRV в UMB, если это возможно:
LH C:\DOS\MOUSE.EXELH C:\DOS\DOSKEY.EXELH C:\DOS\SMARTDRV.EXE
Возможность версий DOS 5.0 и более поздних перемещать собственный код ядра системы в область верхней памяти (HMA) с помощью команды DOS =HIGH дала еще один толчок к освобождению памяти.
Платы расширения оборудования могли использовать любую область верхней памяти для адресации ПЗУ, поэтому блоки верхней памяти имели переменный размер и находились в разных местах для каждого компьютера в зависимости от установленного оборудования. Некоторые окна верхней памяти могли быть большими, а другие маленькими. Загрузка драйверов и TSR high выбирала блок и пыталась вместить в него программу, пока не находил подходящий блок, или программа переходила в обычную память.
Необычным аспектом драйверов и TSR является то, что они использовали разные объемы обычной и/или верхней памяти в зависимости от порядка загрузки. Это можно было бы использовать с выгодой, если бы программы многократно загружались в разном порядке и проверяли, сколько памяти было свободно после каждой перестановки. Например, если был UMB размером 50 КБ и UMB размером 10 КБ, и загружались программы, которым требовалось 8 КБ и 45 КБ, то 8 КБ могли попасть в UMB размером 50 КБ, предотвращая загрузку второй. Более поздние версии DOS позволяли использовать определенный адрес загрузки для драйвера или TSR, чтобы более плотно подогнать драйверы/TSR друг к другу.
В MS-DOS 6.0 Microsoft представила MEMMAKER
, который автоматизировал этот процесс сопоставления блоков, сопоставляя функциональность, предлагаемую сторонними менеджерами памяти . Эта автоматическая оптимизация часто все еще не давала того же результата, что и выполнение ее вручную, в смысле предоставления наибольшей свободной обычной памяти.
Также в некоторых случаях сторонние компании писали специальные многофункциональные драйверы, которые объединяли возможности нескольких стандартных драйверов DOS и TSR в одну очень компактную программу, которая использовала всего несколько килобайт памяти. Например, функции драйвера мыши, драйвера CD-ROM, поддержка ANSI, вызов команды DOSKEY и кэширование диска были бы объединены в одной программе, потребляя всего 1–2 килобайта обычной памяти для обычного доступа к драйверу/прерыванию и сохраняя остальной код многофункциональной программы в памяти EMS или XMS.
Барьер был преодолен только с появлением расширителей DOS , которые позволяли приложениям DOS работать в 16-битном или 32-битном защищенном режиме , но они не были широко использованы за пределами компьютерных игр . С 32-битным расширителем DOS игра могла извлечь выгоду из 32-битного плоского адресного пространства и полного 32-битного набора инструкций без префиксов переопределения операнда/адреса 66h/67h. 32-битные расширители DOS требовали поддержки компилятора (32-битные компиляторы), в то время как XMS и EMS работали со старым компилятором, нацеленным на 16-битные приложения DOS реального режима. Двумя наиболее распространенными спецификациями для расширителей DOS были VCPI - и позже DPMI - совместимые с Windows 3.x.
Самым заметным DPMI-совместимым расширителем DOS может быть DOS/4GW , поставляемый с Watcom . Он был очень распространен в играх для DOS. Такая игра могла бы состоять либо из 32-битного ядра DOS/4GW, либо из заглушки, которая загружала бы ядро DOS/4GW, расположенное в пути или в том же каталоге, и 32-битного «линейного исполняемого файла». Доступны утилиты, которые могут вырезать DOS/4GW из такой программы и позволить пользователю экспериментировать с любым из нескольких и, возможно, улучшенных клонов DOS/4GW.
До появления DOS-расширителей, если пользователь устанавливал дополнительную память и хотел использовать ее в DOS, ему сначала приходилось устанавливать и настраивать драйверы для поддержки либо спецификации расширенной памяти (EMS), либо спецификации расширенной памяти (XMS), а также запускать программы, поддерживающие одну из этих спецификаций.
EMS была спецификацией, доступной на всех ПК, включая те, что были основаны на Intel 8086 и Intel 8088 , которая позволяла дополнительному оборудованию подкачивать и выкачивать небольшие фрагменты памяти ( переключение банков ) адресного пространства «реального режима» (0x0400–0xFFFF). Это позволяло 16-битным программам DOS реального режима получать доступ к нескольким мегабайтам ОЗУ через дыру в реальной памяти, обычно (0xE000–0xEFFF). Затем программа должна была явно запросить страницу, чтобы к ней получить доступ, прежде чем использовать ее. Эти области памяти затем могли использоваться произвольно, пока не будут заменены другой страницей. Это очень похоже на современную страничную виртуальную память . Однако в системе виртуальной памяти операционная система обрабатывает все операции подкачки , в то время как подкачка была явной с EMS.
XMS предоставлял базовый протокол, который позволял 16-битным программам DOS загружать фрагменты расширенной памяти 80286 или 80386 в нижнюю память (адрес 0x0400–0xFFFF). Типичный драйвер XMS должен был переключиться в защищенный режим, чтобы загрузить эту память. Проблема с этим подходом заключается в том, что в защищенном режиме 286 нельзя было делать прямые вызовы DOS. Обходным путем была реализация механизма обратного вызова, требующего сброса 286. На 286 это было серьезной проблемой. Intel 80386 , который представил « виртуальный режим 8086 », позволял гостевому ядру эмулировать 8086 и запускать хостовую операционную систему без необходимости принудительно возвращать процессор в «реальный режим». HIMEM.SYS 2.03 и выше использовали нереальный режим на процессорах 80386 и выше, в то время как HIMEM.SYS 2.06 и выше использовали LOADALL для изменения недокументированных внутренних регистров на 80286, что значительно улучшило задержку прерывания за счет избежания повторных переключений реального режима/защищенного режима. [14]
Windows устанавливает собственную версию HIMEM.SYS [15] на DOS 3.3 и выше. Windows HIMEM.SYS запускает 32-битный защищенный режим поставщика служб XMS (n).0 для Windows Virtual Machine Manager, который затем предоставляет службы XMS (n-1).0 для DOS-боксов и 16-битной машины Windows (например, DOS 7 HIMEM.SYS — это XMS 3.0, но запуск команды 'MEM' в окне DOS Windows 95 показывает информацию XMS 2.0).
Обратите внимание на разрыв в диапазоне адресов памяти от страницы 9F000 до страницы 100000...
IBM
также повторно ввела ограничения памяти, которых я специально избегал при проектировании процессора 8086 [карты]. Для
компьютеров S-100
недорогой альтернативой использованию обычного компьютерного терминала было использование видеокарты. Однако видеокарта использовала часть адресного пространства памяти. Загрузочное ПЗУ обычно также использовало адресное пространство. Системы SCP были разработаны для использования с терминалом, и загрузочное ПЗУ можно было отключить после загрузки. Это сделало весь 1 МБ адресного пространства памяти доступным для ОЗУ. IBM, с другой стороны, ограничила адресное пространство в своем
ПК
до 640 КБ ОЗУ из-за видео и загрузочного/BIOS ПЗУ. Это ограничение было названо «барьером DOS 640K», но оно не имело никакого отношения к
DOS
.
Microsoft
в полной мере использовала возможности системы
SCP
. В 1988 году, спустя годы после закрытия SCP, они все еще использовали систему SCP для одной задачи, которую могла выполнять только она («связывание компоновщика»). Их машина была оснащена полным 1 МБ ОЗУ – 16 из 64-КБ карт. Эту машину нельзя было вывести из эксплуатации, пока не были разработаны 32-битные программные инструменты для
микропроцессора
Intel
386
.