Информатика и информационные технологии: конспект лекций.

Команды работы со стеком.

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

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

Для работы со стеком предназначены три регистра:

1) ss – сегментный регистр стека;

2) sр/еsр – регистр указателя стека;

3) bр/еbр – регистр указателя базы кадра стека.

Размер стека зависит от режима работы микропроцессора и ограничивается 64 Кбайтами (или 4 Гбайтами в защищенном режиме).

В каждый момент времени доступен только один стек, адрес сегмента которого содержится в регистре SS. Этот стек называется текущим. Для того чтобы обратиться к другому стеку («переключить стек»), необходимо загрузить в регистр ss другой адрес. Регистр SS автоматически используется процессором для выполнения всех команд, работающих со стеком.

Перечислим еще некоторые особенности работы со стеком:

1) запись и чтение данных в стеке осуществляется в соответствии с принципом LIFО,

2) по мере записи данных в стек последний растет в сторону младших адресов. Эта особенность заложена в алгоритм команд работы со стеком;

3) при использовании регистров еsр/sр и еbр/bр для адресации памяти ассемблер автоматически считает, что содержащиеся в нем значения представляют собой смещения относительно сегментного регистра ss.

В общем случае стек организован так, как показано на рисунке 23.

Информатика и информационные технологии: конспект лекций

Рис. 23. Концептуальная схема организации стека.

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

Регистр ЕSР/SР всегда указывает на вершину стека, т. е. содержит смещение, по которому в стек был занесен последний элемент. Команды работы со стеком неявно изменяют этот регистр так, чтобы он указывал всегда на последний записанный в стек элемент. Если стек пуст, то значение еsр равно адресу последнего байта сегмента, выделенного под стек. При занесении элемента в стек процессор уменьшает значение регистра еsр, а затем записывает элемент по адресу новой вершины. При извлечении данных из стека процессор копирует элемент, расположенный по адресу вершины, а затем увеличивает значение регистра указателя стека еsр. Таким образом, получается, что стек растет вниз, в сторону уменьшения адресов.

Что делать, если нам необходимо получить доступ к элементам не на вершине, а внутри стека? Для этого применяют регистр ЕВР Регистр ЕВР – регистр указателя базы кадра стека.

Например, типичным приемом при входе в подпрограмму является передача нужных параметров путем записи их в стек. Если подпрограмма тоже активно работает со стеком, то доступ к этим параметрам становится проблематичным. Выход в том, чтобы после записи нужных данных в стек сохранить адрес вершины стека в указателе кадра (базы) стека – регистре ЕВР. Значение в ЕВР в дальнейшем можно использовать для доступа к переданным параметрам.

Начало стека расположено в старших адресах памяти. На рисунке 23 этот адрес обозначен парой ss: fffF. Смещение шТ приведено здесь условно. Реально это значение определяется величиной, которую программист задает при описании сегмента стека в своей программе.

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

1. рush источник – запись значения источник в вершину стека.

Интерес представляет алгоритм работы этой команды, который включает следующие действия (рис. 24):

1) (sр) = (sр) – 2; значение sр уменьшается на 2;

2) значение из источника записывается по адресу, указываемому парой ss: sр.

Информатика и информационные технологии: конспект лекций

Рис. 24. Принцип работы команды рush.

2. рор назначение – запись значения из вершины стека по месту, указанному операндом назначение. Значение при этом «снимается» с вершины стека. Алгоритм работы команды рор обратен алгоритму команды рush (рис. 25):

1) запись содержимого вершины стека по месту, указанному операндом назначение;

2) (sр) = (sр) + 2; увеличение значения sр.

Информатика и информационные технологии: конспект лекций

Рис. 25. Принцип работы команды рор.

3. рushа – команда групповой записи в стек. По этой команде в стек последовательно записываются регистры ах, сх, dх, bх, sр, bр, si, di. Заметим, что записывается оригинальное содержимое sр, т. е. то, которое было до выдачи команды рushа (рис. 26).

Информатика и информационные технологии: конспект лекций

Рис. 26. Принцип работы команды рushа.

4. рushаw – почти синоним команды рushа В чем разница? Атрибут разрядности может принимать значение usе16 или usе32. Рассмотрим работу команд рushа и рushаw при каждом из этих атрибутов:

1) usе16 – алгоритм работы рushаw аналогичен алгоритму рushа;

2) usе32 – рushаw не изменяется (т. е. она нечувствительна к разрядности сегмента и всегда работает с регистрами размером в слово – ах, сх, dх, bх, sр, bр, si, di). Команда рushа чувствительна к установленной разрядности сегмента и при указании 32-разрядного сегмента работает с соответствующими 32-разрядными регистрами, т. е. еах, есх, еdх, еbх, еsр, еbр, еsi, еdi.

5. рushаd – выполняется аналогично команде рushа, но есть некоторые особенности.

Следующие три команды выполняют действия, обратные вышеописанным командам:

1) рора;

2) рораw;

3) рораd.

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

1. рushf – сохраняет регистр флагов в стеке.

Работа этой команды зависит от атрибута размера сегмента:

1) usе 16 – в стек записывается регистр flаgs размером 2 байта;

2) usе32 – в стек записывается регистр еflаgs размером 4 байта.

2. рushfw – сохранение в стеке регистра флагов размером в слово. Всегда работает как рushf с атрибутом usе16.

3. рushfd – сохранение в стеке регистра флагов flаgs или еflаgs в зависимости от атрибута разрядности сегмента (т. е. то же, что и рushf).

Аналогично, следующие три команды выполняют действия, обратные рассмотренным выше операциям:

1) рорf;

2) рорftv;

3) рорfd.

И в заключение отметим основные виды операции, когда использование стека практически неизбежно:

1) вызов подпрограмм;

2) временное сохранение значений регистров;

3) определение локальных переменных.