Режимы адресации памяти стек реферат

Обновлено: 05.07.2024

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

Непосредственная адресация
Операнд (байт или слово) указывается в команде и
после трансляции поступает в код команды; он может
иметь любой смысл (число, адрес, код ASCII), а также
быть представлен в виде символического обозначения.
mov АН,40h
mov АL,’*’
int 21h
limit = 528
mov СХ,limit
;Число 40h загружается в АН
;Код ASCII символа ‘*’ загружается в AL
;Команда прерывания с аргументом 21h
;Число 528 получает обозначение limit
;Число, обозначенное limit, загружается
;в CX
Пересылка относительных адресов (смещений):
; Сегмент данных
mes db "Урок 1” ;Строка символов
;Сегмент команд
mov DX,offset mes
;Адрес строки засылается в DX

Прямая адресация памяти
Адресуется память; адрес ячейки памяти (слова или байта)
указывается в команде (обычно в символической форме) и
поступает в код команды:
;Сегмент данных
mem1
dw 0 ;Слово памяти содержит 0
mem2
db 230
;Байт памяти содержит 230
; Сегмент команд
inc mem1 ;Содержимое слова mem1 увеличивается на 1
mov DX,mem1
;Содержимое слова mem1 загружается в DX
mov AL,mem2
;Содержимое байта mem2 загружается в AL
Команды процессора, обращающиеся к памяти, могут в качестве
первого байта своего кода содержать префикс замены сегмента, с
помощью которого процессор определяет, из какого сегментного
регистра взять сегментный адрес. Если префикс отсутствует,
сегментный адрес берется из регистра DS (хотя для него тоже
предусмотрен свой префикс). В ряде случаев префикс замены
сегмента должен указываться в программе в явной форме. Такая
ситуация возникает, например, если данные расположены в сегменте
команд, что типично для резидентных обработчиков прерываний:
mov АХ, СS : mem

Регистровая косвенная адресация памяти
Адресуется память (байт или слово). Относительный адрес
ячейки памяти находится в регистре, обозначение которого
заключается в прямые скобки. В МП 86 косвенная адресация
допустима только через регистры ВХ, ВР, SI и DI. При
использовании регистров ВХ или ВР адресацию называют
базовой, при использовании регистров DI или SI — индексной.
mov AX,0B800h
;Сегментный адрес
mov ЕS,АХ
;видеобуфера в ЕS
mov ВХ,2000
;Смещение к середине экрана
mov byte ptr ЕS:[ВХ],'!';Символ на экран
Если косвенная адресация осуществляется через один из
регистров ВХ, SI или DI, то подразумевается сегмент,
адресуемый через DS, поэтому при адресации через этот регистр
обозначение DS: можно опустить:
mov AX,0B800h
;Сегментный адрес
mov DS,АХ
;видеобуфера в DS
mov ВХ,2000
;Смещение к середине экрана
mov byte ptr [ВХ],'!'
;Символ на экран

Регистровая косвенная адресация памяти
Регистры ВХ, SI и DI в данном применении совершенно
равнозначны, и с одинаковым успехом можно воспользоваться
любим из них:
mov
mov
DI,2000
;Смещение к середине экрана
byte ptr [DI],'!' ;Символ на экран
Регистр же ВР специально предназначен для работы со стеком, и
при адресации через этот регистр в режимах косвенной
адресации подразумевается сегмент стека; другими словами, в
качестве сегментного регистра по умолчанию используется
регистр SS.
Обычно косвенная адресация к стеку используется в тех случаях,
когда необходимо обратиться к данным, содержащимся в стеке,
без изъятия их оттуда (например, если эти данные приходится
считывать неоднократно).

Регистровая косвенная адресация со смещением
Адресуется память (байт или слово); относительный адрес
операнда определяется, как сумма содержимого регистра ВХ, ВР,
SI или DI и указанной в команде константы, иногда называемой
смещением. Смещение может быть числом или адресом.
mov AX,0B800h
;Сегментный адрес
mov ЕS, АХ
;видеобуфера в ЕS
mov DI,80*2*24
;Смещение к нижней строке экрана
mov byte ptr ES:[DI], ‘O’
;Символ на экран
mov byte ptr ES:2[DI], ‘K’
;Символ в следующую позицию
mov byte ptr ES:4[DI], ‘!’
;Символ в следующую позицию
Иногда можно встретиться с альтернативными обозначениями
того же способа адресации, которые допускает ассемблер.
Вместо, например, 4[ВХ] можно с таким же успехом написать
[ВХ+4], 4+[ВХ] или [ВХ]+4.

Пример использования базовой адресации со
смещением при обращении к стеку
;Основная программа
push DS
;В стек загружаются значения
push ES
;трех регистров,
push SI
;передаваемых подпрограмме
call mysub
;Вызов подпрограммы mysub
;использующей эти параметры
;Подпрограмма mysub
mov BP,SP
;Поместим в ВР текущий адрес вершины стека
mov AX,2[ВР]
;Читаем в АХ последний параметр (SІ)
mov ВХ,4[ВР]
;Читаем в ВХ предыдущий параметр (ЕS)
mov CX,6[ВР]
;Читаем в СХ первый параметр (DS)
Если бы подпрограмма просто сняла со стека находящиеся там
параметры, она первым делом изъяла бы из стека адрес
возврата, и лишила бы себя возможности вернуться в основную
программу

Пример заполнения массива из 10000 слов
натуральным рядом чисел
;Сегмент данных
аггау
dw 10000 dup (?)
;Сегмент команд
mov SI,0 ;Начальное значение индекса элемента в
массиве
fill:
mov AX,0
;Первое число-заполнитель
mov CX,10000 ;Число шагов в цикле (всегда в СХ)
mov array[SI],АХ
;3анесение числа в элемент массива
inc АХ
;Инкремент числа-заполнителя
add SI,2 ;Смещение в массиве к следующему слову
loop fill
;Возврат на метку fill (СХ раз)

Базово-индексная адресация
Адресуется память (байт или слово). Относительный адрес
операнда определяется, как сумма содержимого следующих пар
регистров:
[ВХ] [SІ]
[ВХ] [DІ]
[ВР][SI]
[ВР][DІ]
(подразумевается DS:[ВХ][SI])
(подразумевается DS:[ВХ][DІ])
(подразумевается SS:[ВР][SI])
(подразумевается SS:[ВР][DІ])
Это чрезвычайно распространенный способ адресации,
особенно, при работе с массивами. В нем используются два
регистра, при этом одним из них должен быть базовый (ВХ или
ВР), а другим — индексный (SI или DI). Как правило, в одном из
регистров находится адрес массива, а в другом — индекс в нем,
при этом совершенно безразлично, в каком что.

Базово-индексная адресация
;Сегмент данных
аггау
dw 10000 dup (?)
;Сегмент команд
mov ВХ,offset аггау ;Базовый адрес массива в базовом регистре
mov SI,0
;Начальное значение индекса элемента в массиве
mov АХ, 0
;Первое число-заполнитель
mov СХ,10000
;Число шагов в цикле
fill: mov [ВХ] [SI] ,АХ
;Отправим число в массив
inc АХ
;Инкремент числа-заполнителя
add SI,2
;Смещение в массиве к следующему слову
lоор fill
;На метку fill (СХ раз)
Повышение эффективности достигается за счет того, что
команда занесения числа в элемент массива оказывается короче
(так как в нее не входит адрес массива) и выполняется быстрее,
так как этот адрес не надо каждый раз считывать из памяти.

Базово-индексная адресация со смещением
Адресуется память (байт или слово). Относительный адрес
операнда определяется как сумма содержимого двух регистров и
смещения.
Sims db ‘QWERTUIOP<>’
db ‘ЙЦУКЕНГШЩЗХЪ’
Последовательность команд
mov ВХ,12
;Число байтов в строке
mov SI,6
mov DL,Sims[ВХ] [SI]
загрузит в регистр DL элемент с индексом 6 из второго ряда, т.е.
код АSСІІ буквы Г. Тог же результат можно получить, загрузив в
один из регистров не индекс, а адрес массива:
mov
mov
mov
ВХ,offset Sims
SI,6
DL,12[ВХ][SI]

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

Для осуществления операций с данными в АЛУ необходимо загрузить их в микропроцессор из оперативной памяти. Но для того, чтобы выбрать данные (или, по другому, операнды) из памяти, необходимо обратиться к ним по определенному адресу. Способы задания этого адреса называется адресацией памяти в микропроцессоре.

Прикрепленные файлы: 1 файл

Адресация данных.docx

Адресация памяти в микропроцессорах.

Для осуществления операций с данными в АЛУ необходимо загрузить их в микропроцессор из оперативной памяти. Но для того, чтобы выбрать данные (или, по другому, операнды) из памяти, необходимо обратиться к ним по определенному адресу. Способы задания этого адреса называется адресацией памяти в микропроцессоре.

Способы адресации

Существуют следующие способы адресации операндов:

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

Рис. 65. Прямая адресация в AVR

Регистры общего назначения. Команды, оперирующие с двумя регистрами, действуют, в основном, аналогичным образом. В этих командах регистр-приемник (destination) указывается перед регистром-источником (source), то есть является первым параметром. Таким образом, команда

реально выполняется так: R0 = R0 + R1. Рассмотренные способы адресации операндов называются прямой регистровой адресацией (рис. 66).

Рис. 66. Прямая адресация AVR к двум РОН

Рис. 67. Непосредственная адресация AVR

Это, очевидно, окажет влияние на то, как разместить данные в рабочих регистрах. Чтобы избежать ошибок, можно использовать в качестве рабочих 16 старших регистров общего назначения, имеющих адреса с $10 по $1F.

Последняя форма прямой адресации, применяемая для доступа ко всему объему адресуемой памяти, использует второе слово команды для указания

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

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

Рис. 68. Косвенная адресация к РОН-памяти данных в AVR

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

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

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

Как правило, другой операнд должен присутствовать в регистре адреса или данных.

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

Во всех способах адресации с индексированием введено масштабирование индекса. Оно осуществляется умножением содержимого индексного регистра Xn на масштабный множитель SCALE, имеющий значение 1, 2, 4 и 8. В зависимости от значения символа разрядности SIZE, указываемого после имени индексного регистра, используется 16 или 32 разряда его содержимого. Если после имени индексного регистра указан символ W (word, слово). то индексом служат 16 его младших разрядов, расширенные до 32-х разрядов битом знака. Если же указан символ L (long word, длинное слово), то индексом служит 32-х разрядное значение индексного регистра, используемое как число со знаком. При SCALE=1 содержимое Xn (индексного регистра) остается без изменения, а при SCALE = 2,4 или 8 сдвигается влево на 1, 2 или 3 разряда соответственно.

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

где Xn – индексный регистр. Им может быть An (регистр адреса) или Dn (регистр данных). SIZE – W или L, а SCALE – 1, 2, 4, 8. Например:

Способы адресации в микропроцессорах корпорации Intel

Способы адресации в микропроцессорах корпорации Intel представлены в таблице D.3.I и на рисунке D.3.1.

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

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

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

Так ладно, хватит о печальном, переходим к делу.
Рассмотрим адресное пространство программного режима 32 битного процессора (для 64 бит все по аналогии)
Адресное пространство этого режима будет состоять из 2^32 ячеек памяти пронумерованных от 0 и до 2^32-1.
Программист работает с этой памятью, если ему нужно определить переменную, он просто говорит ячейка памяти с адресом таким-то будет содержать такой-то тип данных, при этом сам програмист может и не знать какой номер у этой ячейки он просто напишет что-то вроде:
int data = 10;
компьютер поймет это так: нужно взять какую-то ячейку с номером стопицот и поместить в нее цело число 10. При том про адрес ячейки 18894 вы и не узнаете, он от вас будет скрыт.

Все бы хорошо, но возникает вопрос, а как компьютер ищет эту ячейку памяти, ведь память у нас может быть разная:
3 уровень кэша
2 уровень кэша
1 уровень кэша
основная память
жесткий диск

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

Архитектура х86 поддерживает стек.

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

push operand
помещает операнд в стек

pop operand
изымает из вершины стека значение и помещает его в свой операнд

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

Теперь кратко рассмотрим что такое регистры.
Это ячейки памяти в самом процессоре. Это самый быстрый и самый дорогой тип памяти, когда процессор совершает какие-то операции со значением или с памятью, он берет эти значения непосредственно из регистров.
В процессоре есть несколько наборов логик, каждая из которых имеет свои машинные коды и свои наборы регистров.
Basic program registers (Основные программные регистры) Эти регистры используются всеми программами с их помощью выполняется обработка целочисленных данных.
Floating Point Unit registers (FPU) Эти регистры работают с данными представленными в формате с плавающей точкой.
Еще есть MMX и XMM registers эти регистры используются тогда, когда вам надо выполнить одну инструкцию над большим количеством операндов.

Рассмотрим подробнее основные программные регистры. К ним относятся восемь 32 битных регистров общего назначения: EAX, EBX, ECX, EDX, EBP, ESI, EDI, ESP
Для того чтобы поместить в регистр данные, или для того чтобы изъять из регистра в ячейку памяти данные используется команда mov:

mov eax, 10
загружает число 10 в регистр eax.

mov data, ebx
копирует число, содержащееся в регистре ebx в ячейку памяти data.

Регистр ESP содержит адрес вершины стека.
Кроме регистров общего назначения, к основным программным регистрам относят шесть 16битных сегментных регистров: CS, DS, SS, ES, FS, GS, EFLAGS, EIP
EFLAGS показывает биты, так называемые флаги, которые отражают состояние процессора или характеризуют ход выполнения предыдущих команд.
В регистре EIP содержится адрес следующей команды, которая будет выполнятся процессором.
Я не буду расписывать регистры FPU, так как они нам не понадобятся. Итак наше небольшое отступление про регистры и стек закончилось переходим обратно к организации памяти.

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

Логический адрес --> Линейный (виртуальный)--> Физический

image


Все линейное адресное пространство разбито на сегменты. Адресное пространство каждого процесса имеет по крайней мере три сегмента:
Сегмент кода. (содержит команды из нашей программы, которые будут исполнятся.)
Сегмент данных. (Содержит данные, то бишь переменные)
Сегмент стека, про который я писал выше.

Линейный адрес вычисляется по формуле:

линейный адрес=Базовый адрес сегмента(на картинке это начало сегмента) + смещение
Сегмент кода


Базовый адрес сегмента кода берется из регистра CS. Значение смещения для сегмента кода берется из регистра EIP, в котором хранится адрес инструкции, после исполнения которой, значение EIP увеличивается на размер этой команды. Если команда занимает 4 байта, то значение EIP увеличивается на 4 байта и будет указывать уже на следующую инструкцию. Все это делается автоматически без участия программиста.
Сегментов кода может быть несколько в нашей памяти. В нашем случае он один.

Сегмент данных


Данные загружаются в регистры DS, ES, FS, GS
Это значит что сегментов данных может быть до 4х. На нашей картинке он один.
Смещение внутри сегмента данных задается как операнд команды. По дефолту используется сегмент на который указывает регистр DS. Для того чтобы войти в другой сегмент надо это непосредственно указать в команде префикса замены сегмента.

Сегмент стека

Используемый сегмент стека задается значением регистра SS.
Смещение внутри этого сегмента представлено регистром ESP, который указывает на вершину стека, как вы помните.
Сегменты в памяти могут друг друга перекрывать, мало того базовый адрес всех сегментов может совпадать например в нуле. Такой вырожденный случай называется линейным представлением памяти. В современных системах, память как правило так организована.

Теперь рассмотрим определение базовых адресов сегмента, я писал что они содержаться в регистрах SS, DS, CS, но это не совсем так, в них содержится некий 16 битный селектор, который указывает на некий дескриптор сегментов, в котором уже хранится необходимый адрес.

Так выглядит селектор, в тринадцати его битах содержится индекс дескриптора в таблице дескрипторов. Не хитро посчитать будет что 2^13 = 8192 это максимальное количество дескрипторов в таблице.
Вообще дескрипторных таблиц бывает два вида GDT и LDT Первая называется глобальная таблица дескрипторов, она в системе всегда только одна, ее начальный адрес, точнее адрес ее нулевого дескриптора хранится в 48 битном системном регистре GDTR. И с момента старта системы не меняется и в свопе не принимает участия.
А вот значения дескрипторов могут меняться. Если в селекторе бит TI равен нулю, тогда процессор просто идет в GDT ищет по индексу нужный дескриптор с помощью которого осуществляет доступ к этому сегменту.
Пока все просто было, но если TI равен 1 тогда это означает что использоваться будет LDT. Таблиц этих много, но использоваться в данный момент будет та селектор которой загружен в системный регистр LDTR, который в отличии от GDTR может меняться.
Индекс селектора указывает на дескриптор, который указывает уже не на базовый адрес сегмента, а на память в котором хранится локальная таблица дескрипторов, точнее ее нулевой элемент. Ну а дальше все так же как и с GDT. Таким образом во время работы локальные таблицы могут создаваться и уничтожаться по мере необходимости. LDT не могут содержать дескрипторы на другие LDT.
Итак мы знаем как процессор добирается до дескриптора, а что содержится в этом дескрипторе посмотрим на картинке:
Дескрипторы состоит из 8 байт.
Биты с 15-39 и 56-63 содержат линейный базовый адрес описываемым данным дескриптором сегмента. Напомню нашу формулу для нахождения линейного адреса:

линейный адрес = базовый адрес + смещение
[база; база+предел)


В зависимости от 55 G-бита(гранулярити), предел может измеряться в байтах при нулевом значении бита и тогда максимальный предел составит 1 мб, или в значении 1, предел измеряется страницами, каждая из которых равна 4кб. и максимальный размер такого сегмента будет 4Гб.
Для сегмента стека предел будет в интервале:

(база+предел; вершина]

44 S бит если равен 1 тогда дескриптор описывает реальный сегмент оперативной памяти, иначе значение S бита равно 0.

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

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

В вычислительных системах используются подсистемы с различным быстродействием, и, в частности, с различной скоростью передачи данных (рис. 4.13). Обычно обмен данными между такими подсистемами реализуется с использованием прерываний или канала прямого доступа к памяти. В первую очередь подсистема 1 формирует запрос на обслуживание по мере готовности данных к обмену. Однако обслуживание прерываний связано с непроизводительными потерями времени и при пакетном обмене производительность подсистемы 2 заметно уменьшается. При обмене данными с использованием канала прямого доступа к памяти подсистема 1 передает данные в память подсистемы 2. Данный способ обмена достаточно эффективен с точки зрения быстродействия, но для его реализации необходим довольно сложный контроллер прямого доступа к памяти.

Рис. 4.13. Применение буферной памяти.

Наиболее эффективно обмен данными между подсистемами с различным быстродействием реализуется при наличии между ними специальной буферной памяти. Данные от подсистемы 1 временно запоминаются в буферной памяти до готовности подсистемы 2 принять их. Емкость буферной памяти должна быть достаточной для хранения тех блоков данных, которые подсистема 1 формирует между считываниями их подсистемой 2. Отличительной особенностью буферной памяти является запись данных с быстродействием и под управлением подсистемы 1, а считывание - с быстродействием и под управлением подсистемы 2 ("эластичная память"). В общем случае память должна выполнять операции записи и считывания совершенно независимо и даже одновременно, что устраняет необходимость синхронизации подсистем. Буферная память должна сохранять порядок поступления данных от подсистемы 1, т.е. работать по принципу "первое записанное слово считывается первым" (First Input First Output - FIFO). Таким образом, под буферной памятью типа FIFO понимается ЗУПВ, которое автоматически следит за порядком поступления данных и выдает их в том же порядке, допуская выполнение независимых и одновременных операций записи и считывания. На рис. 4.14 приведена структурная схема буферной памяти типа FIFO емкостью 64x4.

Рис. 4.14. Структурная схема буфера 64x4.

При вводе 4-битного слова под действием сигнала SI оно автоматически передвигается в ближайший к выходу свободный регистр. Состояние регистра данных отображается в соответствующем ему управляющем триггере, совокупность триггеров образует 64-битный управляющий регистр. Если регистр содержит данные, то управляющий триггер находится в состоянии 1, а если регистр не содержит данных, то триггер находится в состоянии 0. Как только управляющий бит соседнего справа регистра изменяется на 0, слово данных автоматически сдвигается к выходу. Перед началом работы в буфер подается сигнал сброса R и все управляющие триггеры переводятся в состояние 0 (все регистры буфера свободны). На выводе IR формируется логическая 1, т.е. буфер готов воспринимать входные данные. При действии сигнала ввода SI входное слово загружается в регистр P1, а управляющий триггер этого регистра устанавливается в состояние 1: на входе IR формируется логический 0. Связи между регистрами организованы таким образом, что поступившее в P1 слово "спонтанно" копируется во всех регистрах данных FIFO и появляется на выходных линиях DO0-DO3. Теперь все 64 регистра буфера содержат одинаковые слова, управляющий триггер последнего регистра P64 находится в состоянии 1, а остальные управляющие триггеры сброшены при передаче данных в соседние справа регистры. Состояние управляющего триггера P64 выведено на линию готовности выхода OR; OR принимает значение 1, когда в триггер записывается 1. Процесс ввода может продолжаться до полного заполнения буфера; в этом случае все управляющие триггеры находятся в состоянии 1 и на линии IR сохраняется логический 0.

При подаче сигнала SO производится восприятие слова с линий DO0-DO3, управляющий триггер P64 переводится в состояние 1, на линии OR появляется логическая 1, а управляющий триггер P64 сбрасывается в 0. Затем этот процесс повторяется для остальных регистров и нуль в управляющем регистре перемещается ко входу по мере сдвига данных вправо.

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

Рассмотренный принцип организации FIFO допускает выполнение записи и считывания данных независимо и одновременно. Скорость ввода определяется временным интервалом, необходимым для передачи данных из P1, а выводить данные можно с такой же скоростью. Единственным ограничением является время распространения данных через FIFO, равное времени передачи входного слова на выход незаполненного буфера FIFO. Оно равняется произведению времени внутреннего сдвига и числа регистра данных. В буферах FIFO, выполненных по МОП-технологии и имеющих емкость 64 слова, время распространения составляет примерно 30 мкс, а в биполярных FIFO такой же емкости - примерно 2 мкс.

Буферы можно наращивать как по числу слов, так и по их длине.

Стековая память

Стековой называют память, доступ к которой организован по принципу: "последним записан - первым считан" (Last Input First Output - LIFO). Использование принципа доступа к памяти на основе механизма LIFO началось с больших ЭВМ. Применение стековой памяти оказалось очень эффективным при построении компилирующих и интерпретирующих программ, при вычислении арифметических выражений с использованием польской инверсной записи. В малых ЭВМ она стала широко использоваться в связи с удобствами реализации процедур вызова подпрограмм и при обработке прерываний.

Рис. 4.15. Принцип работы стековой памяти.

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

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

Наиболее распространенным в настоящее время и, возможно, лучшим вариантом организации стека в ЭВМ является использование области памяти. Для адресации стека используется указатель стека, который предварительно загружается в регистр и определяет адрес последней занятой ячейки. Помимо команд CALL и RET, по которым записывается в стек и восстанавливается содержимое программного счетчика, имеются команды PUSH и POP, которые используются для временного запоминания в стеке содержимого регистров и их восстановления, соответственно. В некоторых МП содержимое основных регистров запоминается в стеке автоматически при прерывании программ. Содержимое регистра указателя стека при записи уменьшается, а при считывании увеличивается на 1 при выполнении команд PUSH и POP, соответственно.

Читайте также: