Подтвердить что ты не робот

Что такое инструкции IN & OUT для x86?

Я включил их в инструкции IN и OUT при чтении книги "Understanding Linux Kernel". Я искал справочное руководство.

5.1.9 Инструкции ввода/вывода

Эти инструкции перемещают данные между порты ввода-вывода процессоров и регистр или память.

IN    Read from a port
OUT   Write to a port
INS/INSB  Input string from port/Input byte string from port 
INS/INSW  Input string from port/Input word string from port 
INS/INSD  Input string from port/Input doubleword string from port
OUTS/OUTSB    Output string to port/Output byte string to port 
OUTS/OUTSW    Output string to port/Output word string to port 
OUTS/OUTSD    Output string to port/Output doubleword string to port

Я не получил немного вещей:

  • "Процессоры портов ввода/вывода". Кто они такие? Почему мы хотим читать и записывать "строки" в и из этих портов?
  • Я никогда не использовал scenerio, где мне нужно использовать эти инструкции. Когда мне это понадобится?
  • Приведите несколько практических примеров.
4b9b3361

Ответ 1

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

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

Для некоторых моделей ЦП, включая серию xxx86, найденных на большинстве "современных" ПК, устройства ввода/вывода совместно используют адресное пространство с памятью. Оба устройства RAM/ROM и IO подключены к тем же адресам, данным и линиям управления. Например, последовательный порт для COM1 адресуется начиная с (шестнадцатеричный) 03F8. Но почти наверняка память по тому же адресу.

Здесь действительно простая диаграмма:

[https://qph.ec.quoracdn.net/main-qimg-e510d81162f562d8f671d5900da84d68-c?convert_to_webp=true]

Очевидно, что ЦП необходимо разговаривать либо с памятью, либо с устройством ввода-вывода, ни тем, ни другим. Чтобы отличить их, одна из контрольных линий, называемая "M/# IO", утверждает, хочет ли процессор говорить с памятью (строка = высокий) или устройство ввода/вывода (строка = низкая).

Инструкция IN считывается с устройства ввода-вывода, запись OUT. Когда вы используете инструкции IN или OUT, M/# IO не заявляется (удерживается на низком уровне), поэтому память не отвечает и чип I/O делает это. Для инструкций, ориентированных на память, M/# IO утверждается так, что процессор разговаривает с ОЗУ, а устройства ввода-вывода остаются вне связи.

При определенных условиях устройства IO могут управлять линиями данных, и ОЗУ может считывать их одновременно. И наоборот. Он называется DMA.

Традиционно последовательные и порты принтера, а также клавиатура, мышь, датчики температуры и т.д. были устройствами ввода/вывода. Диски были между собой; передача данных будет инициирована командами ввода-вывода, но контроллер диска обычно будет направлять свои данные в системную память.

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

Ответ 2

Начните с чего-то вроде этого:

http://www.cpu-world.com/info/Pinouts/8088.html

Вы изучаете инструкции для очень старого технологического чипа/архитектуры. Назад, когда все, кроме ядра процессора, было отключено от чипа. См. Адресные строки и строки данных, и есть строка чтения RD и строка записи WR и строка ввода/вывода?

Существует два типа инструкций на основе памяти и ввода-вывода, поскольку существуют адресуемые пространства, которые легко декодируются IO/M IO или памятью.

Помните, что у вас была логика клея 74LSxx, много проводов и множество микросхем для подключения памяти к процессору. И память была именно той памятью, большими дорогостоящими чипами. Если у вас есть периферийное устройство, которое нужно делать, что-нибудь полезное, у вас также есть контрольные регистры, то память может быть пиксельными данными, но где-то вам нужно было установить горизонтальные и вертикальные интервалы часов сканирования, это могут быть отдельные затворы 74LSxx, NOT memories, имеющие I/O, сохраненный на обеих логиках клеев, и просто имеет большое значение с точки зрения программиста, он также избегал менять регистры сегментов, чтобы нацелить ваше окно памяти на 64 КБ и т.д. Адресное пространство памяти было священным ресурсом, например, когда вы хотел ограничить декодирование адреса несколькими битами, потому что каждый бит бит стоил вам нескольких чипов и проводов.

Как и большая и маленькая карта памяти с индексом ввода-вывода, I/O против ввода-вывода I/O была религиозной войной. И некоторые ответы, которые вы собираетесь посмотреть на свой вопрос, будут отражать сильные мнения, которые все еще существуют сегодня у людей, которые его проживали. Реальность заключается в том, что каждый чип на рынке сегодня имеет несколько busess для разных вещей, вы не вешаете свои часы реального времени с шины памяти ddr с декодером адресов. У некоторых до сих пор даже есть отдельные автобусы с инструкциями и данными. В некотором смысле Intel выиграла войну за концепцию отдельных адресных пространств для разных классов вещей, хотя термин порт ввода-вывода был злым и плохим и не должен произноситься за 20-30 лет. Вам нужны люди моего возраста, которые жили, чтобы быть уволенным или уйти до того, как война действительно закончилась. Даже термин памяти, отображаемый вводом/выводом, ушел в прошлое.

Это действительно все, что когда-либо было, бит декодирования одного адреса на внешней стороне чипа Intel, который контролировался использованием конкретных инструкций. Используйте один набор инструкций, в котором бит использовался, используя один набор инструкций, бит был выключен. Хотите увидеть что-то интересное, посмотрите на набор инструкций для процессоров xmos xcore, у них есть много вещей, которые являются инструкциями, а не памятью, записанными в память, и переводит эту информацию ввода-вывода на ввод/вывод на новый уровень.

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

Поскольку адресное пространство было скудным, это было не редкость, и сегодня по-прежнему наблюдается память, скрытая за двумя регистрами, адресным регистром и регистром данных, эта память доступна только через эти два регистра, она не отображена в памяти. поэтому вы записываете смещение в эту скрытую память в регистре адресов, и вы читаете или записываете регистр данных для доступа к содержимому памяти. Теперь, поскольку у Intel была инструкция rep, и вы могли бы объединить ее с insb/w outsb/w, аппаратный декодер (если бы у вас были хорошие/дружественные аппаратные люди, работающие с вами), автоинкремент адреса каждый раз, когда вы делали цикл ввода-вывода. Таким образом, вы можете написать начальный адрес в регистре адресов и сделать rep outsw и без записи fetch и декодирования тактовых циклов в процессоре, а на шине памяти вы можете быстро перемещать данные в периферию или из нее. Этот вид вещей теперь считается недостатком дизайна благодаря современным суперскалярным процессорам с выборками, основанными на предсказании ветвей, ваше оборудование может считывать данные в любое время, которые не имеют никакого отношения к выполнению кода, в результате вы НИКОГДА не должны автоматически увеличивать адрес или очистить бит в регистре состояния или изменить что-либо в результате чтения адреса.

Механизмы защиты, встроенные в 386 и в настоящее время, фактически облегчают доступ к I/O из пользовательского пространства. В зависимости от того, что вы делаете для жизни, что производит ваша компания и т.д. Вы можете определенно использовать внутри и вне семейство инструкций из пользовательского пространства (прикладные программы в windows и linux и т.д.) Или пространство ядра/драйвера, это ваш выбор. Вы также можете делать забавные вещи, например, воспользоваться виртуальной машиной и использовать инструкции ввода/вывода для общения с драйверами, но это, вероятно, вызовет у людей как в Windows, так и в Linux-мире, что драйвер/приложение не будет делать это очень далеко. Другие плакаты правильны в том, что вам, скорее всего, не понадобится использовать эти инструкции, если вы не пишете драйверы, и вы, вероятно, никогда не будете писать драйверы для устройств, использующих ввод-вывод ввода-вывода, поскольку вы знаете... драйверы для этих устаревших устройств уже написаны. У современных дизайнов определенно есть I/O, но все они отображаются в памяти (с точки зрения программистов) и используют инструкции памяти, а не инструкции ввода/вывода. Теперь другая сторона, если это DOS, определенно не мертва, в зависимости от того, где вы можете строить машины для голосования или газовые насосы или кассовые аппараты или длинный список оборудования на базе DOS. На самом деле, если вы работаете где-то, кто строит ПК или периферийные устройства на базе ПК или материнские платы, инструменты на основе DOS по-прежнему широко используются для тестирования и распространения обновлений BIOS и других подобных вещей. Я все еще сталкиваюсь с ситуациями, когда мне нужно взять код из текущей тестовой программы dos, чтобы написать драйвер linux. Точно так же, как не все, кто может бросить или поймать футбольные матчи в НФЛ, в процентном отношении очень мало работы по программному обеспечению, которая включает в себя такие вещи. Таким образом, можно с уверенностью сказать, что эти инструкции, которые вы нашли, скорее всего, не будут более важными для вас, чем урок истории.

Ответ 3

Приведите несколько практических примеров.

Сначала узнайте, как:

  • создать минимальную ОС загрузчика и запустить ее на QEMU и реальном оборудовании, как я объяснил здесь: fooobar.com/questions/30228/...
  • сделать некоторые вызовы BIOS для выполнения быстрого и грязного ввода-вывода

Тогда:

Протестировано: QEMU 2.0.0 Ubuntu 14.04 и реальное оборудование Lenovo ThinkPad T400.

Как найти номера портов: Есть ли спецификация назначения порта ввода-вывода x86?

https://github.com/torvalds/linux/blob/v4.2/arch/x86/kernel/setup.c#L646 содержит список портов, используемых ядром Linux.

Другие архитектуры

Не все архитектуры имеют такие посвященные IO инструкции.

В ARM, например, IO выполняется просто путем записи на магические аппаратные определенные адреса памяти.

Я думаю, что это то, что fooobar.com/questions/128934/... означает "сопоставленные с памятью ввода-вывода и ввод-вывод I/O".

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

См. fooobar.com/questions/30282/... для конкретного примера ARM.

Ответ 4

Если вы не пишете операционную систему, вы никогда не будете использовать эти инструкции.

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

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

Ответ 5

На аппаратном уровне большинство микропроцессоров имеют мало или вообще не имеют возможности ввода-вывода. Несколько процессоров имеют один или несколько контактов, которые могут быть включены и выключены с помощью специальных инструкций и/или одного или нескольких контактов, которые могут быть протестированы с использованием специальных инструкций для ветвления, но такие функции встречаются редко. Вместо этого операции ввода/вывода обычно обрабатываются путем подключения системы, так что доступ к диапазону адресов памяти вызовет некоторый эффект или путем включения "in" и "out" команд, которые ведут себя как операции загрузки/хранения памяти, за исключением того, что специальный сигнал выводится сообщение "Это операция ввода-вывода вместо операции с памятью". В дни 16-разрядных процессоров раньше были некоторые реальные преимущества в отношении специализированных инструкций ввода/вывода. В настоящее время такие преимущества в значительной степени спорны, поскольку можно просто выделить большой кусок одного адресного пространства для ввода-вывода и по-прежнему иметь много оставшихся для памяти.

Так как программа может нанести значительный ущерб системе, неадекватно выполняя инструкции ввода/вывода (например, такие инструкции могут выполнять произвольные обращения к диску), все современные операционные системы запрещают использование таких инструкций в коде уровня пользователя. Некоторые системы могут разрешить виртуализацию таких инструкций; если код пользователя пытается записать на порты ввода-вывода 0x3D4 и 0x3D5, например, операционная система может интерпретировать это как попытку установить некоторые регистры управления видеоконтролем для перемещения мигающего курсора. Каждый раз, когда пользовательская программа выполняла команду OUT, операционная система захватывала бы, смотря, что пыталась сделать пользовательская программа, и действовать соответствующим образом.

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

Ответ 6

Для этого есть немного больше обмана. Он не просто мультиплексирует отдельное адресное пространство на 64 КБ на те же провода, что и "дополнительный адрес шины/чип". Intel 8086 и 8088 и их клоны также мультиплексируют шину данных и адресную шину; все очень необычные вещи в процессорах. Таблицы данных заполнены информацией о конфигурации "минимальная/максимальная" и всеми регистрами защелок, которые необходимо подключить к ней, чтобы заставить ее вести себя "нормально". С другой стороны, он сохраняет нагрузку и ворота и "или" ворота в декодировании адресов, а 64kb должен быть "достаточным для портов ввода/вывода": P.

Кроме того, для всех тех, кто занимается только разработчиками драйверов, обратите внимание: помимо людей, использующих совместимые с Intel чипы на другом оборудовании, а не только на ПК (они никогда не были предназначены для использования на ПК IBM в первую очередь - IBM просто взяла потому что они были дешевыми и уже на рынке), Intel также продает микроконтроллеры с тем же набором инструкций (Intel Quark), и есть множество "систем на чипе" других поставщиков с тем же набором инструкций. Я не думаю, что вам удастся забрать все, с отдельным "ядром пользователя" и "драйверами" в 32kb:). Для большинства вещей такие сложные "операционные системы" не являются ни оптимальными, ни желательными. Формируя некоторые UDP-пакеты в ОЗУ, а затем помещая их в некоторый кольцевой буфер и делая некоторые реле, клик по клику не требует ядра 30 МБ и времени загрузки в 10 секунд, вы знаете. Это в основном лучший выбор в случае, если микроконтроллер PIC не достаточно, но вам не нужен весь промышленный ПК. Поэтому инструкции ввода-вывода портов очень часто используются, а не только разработчиками драйверов для более крупных операционных систем.

Ответ 7

CPU подключен к некоторым внешним контроллерам через порты io. на старом компьютере x86 я работаю с флоппи-диском, используя порты ввода-вывода. если вы знаете, какие команды принимают контроллер устройства, вы можете запрограммировать его через его порты.

В современном мире вы никогда не будете использовать инструкции портов. Исключение, если вы (или будете) разработчиком драйверов.

имеется более подробная информация о портах ввода/вывода http://webster.cs.ucr.edu/AoA/DOS/ch03/CH03-6.html#HEADING6-1