7.5.1.1.3. Буферы отложенной записи
Процессор
486 имеет четыре внутренних буфера для операций записи. Если во время
внутреннего запроса процессора на запись все буферы свободны и шина не занята, запись
выполняется сразу без буферирования. Если шина занята, запрос направляется в
буфер, занимая для записи только один внутренний такт, а из буфера данные
выгружаются в оперативную память или устройства ввода/вывода по мере
освобождения внешней шины. Внешние операции записи из буферов будут
производиться в том же порядке, что и поступившие запросы. Однако, если при
наличии не освобожденных буферов появится запрос на чтение памяти, он может
быть обслужен и раньше, чем удовлетворятся предшествующие ему запросы на
запись. Это изменение последовательности может произойти только в том случае,
если все запросы записи в буферах связаны с кэш-попаданиями, а запрос на чтение
относится к кэш-промаху. Только в этом случае процессор может смело менять
порядок операций, но только один раз до тех пор, пока не освободятся все буферы
записи. Больше одного раза менять порядок в общем случае нельзя, потому что
считанные данные могут заместить модифицированную строку кэша, из которой
обновленная информация как раз и ожидает в буфере очереди на запись в основную
память. В таком случае вторая попытка изменения последовательности может
нарушить целостность данных.
Для
операций ввода/вывода изменение порядка невозможно. Чтение ввода/вывода никогда
не может обгонять запись в память (иначе отказались бы работать многие
периферийные устройства). Одиночные операции вывода не буферизуются для того,
чтобы дать устройствам возможность своевременно (для программы) сообщить о
своей реакции на запись в порт (вызвать аппаратное прерывание или цикл
аннулирования строки). Способы введения программной задержки (I/O Bus recovery time) между
одиночными операциями вывода для процессоров 486+ должны учитывать кэширование
и буферизацию. Здесь команда JMP, ранее
безусловно приводящая к генерации внешнего цикла обращения к памяти, скорее
всего будет обслужена из внутреннего кэша, и желаемой задержки не произойдет.
Надежным способом введения внешнего цикла шины между циклами вывода является
явная операция чтения некэшируемой области памяти. Эта операция будет выполнена
только после завершения предыдущего цикла вывода, а последующая операция вывода
начнется только по завершении этого чтения.
Операции
блочного вывода, вызванные инструкцией REP OUTSB/OUTSW, будут пользоваться буферами, но их порядок не будет
нарушен.