Поиск…


замечания

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

Zilog Z80 Stack

Регистр sp используется как указатель стека , указывая на последнее сохраненное значение в стек («верх» стека). Таким образом, EX (sp),hl будет обменивать значение hl со значением поверх стека.

Вопреки «верхнему» слову, стек растет в памяти, уменьшая значения sp и высвобождая («pops») значения, увеличивая sp .

Для sp = $4844 со значениями 1 , 2 , 3 хранящимися в стеке ( 3 вставляется в стек как последнее значение, поэтому, находясь на вершине), память будет выглядеть так:

|    address | value bytes | comment (btw, all numbers are in hexadecimal)
| ---------- | ----------- | ---------------------------------
|       4840 | ?? ??       | free stack spaces to be used by next push/call
|       4842 | ?? ??       | or by interrupt call! (don't expect values to stay here)
| sp -> 4844 | 03 00       | 16 bit value "3" on top of stack
|       4846 | 02 00       | 16 bit value "2"
|       4848 | 01 00       | 16 bit value "1"
|       484A | ?? ??       | Other values in stack (up to it's origin)
|       484C | ?? ??       | like for example return address for RET instruction

Примеры, как инструкции работают со стек:

    LD   hl,$0506
    EX   (sp),hl           ; $0003 into hl, "06 05" bytes at $4844
    POP  bc                ; like: LD c,(sp); INC sp; LD b,(sp); INC sp
                           ; so bc is now $0506, and sp is $4846
    XOR  a                 ; a = 0, sets zero and parity flags
    PUSH af                ; like: DEC sp; LD (sp),a; DEC sp; LD (sp),f
                           ; so at $4844 is $0044 (44 = z+p flags), sp is $4844
    CALL $8000             ; sp is $4842, with address of next ins at top of stack
                           ; pc = $8000 (jumping to sub-routine)
                           ; after RET will return here, the sp will be $4844 again
    LD   (L1+1),sp         ; stores current sp into LD sp,nn instruction (self modification)
    DEC  sp                ; sp is $4843
L1  LD   sp,$1234          ; restores sp to $4844 ($1234 was modified)
    POP  de                ; de = $0044, sp = $4846
    POP  ix                ; ix = $0002, sp = $4848
    ...

    ...
    ORG  $8000
    RET                    ; LD pc,(sp); INC sp; INC sp
                           ; jumps to address at top of stack, "returning" to caller

Реферат : PUSH будет хранить значение поверх стека, POP будет извлекать значение из вершины стека, это очередь LIFO (последний, первый). CALL аналогичен JP , но также вызывает адрес следующей команды после CALL в верхней части стека. RET похож на JP , выталкивая адрес из стека и прыгая на него.

Предупреждение : когда прерывания разрешены, sp должен быть действительным во время сигнала прерывания, при этом достаточное свободное пространство зарезервировано для процедуры обработчика прерываний, так как сигнал прерывания будет хранить обратный адрес (фактический pc ) до вызова процедуры обработчика, которая может хранить дополнительные данные на стек. Любое значение перед sp может быть изменено «неожиданно», если происходит прерывание.

Продвинутый трюк : на Z80 с PUSH принимающим 11 тактов (11t) и POP принимающих 10t, развернутый POP / PUSH через все регистры, включая EXX для теневых вариантов, был самым быстрым способом скопировать блок памяти, даже быстрее, чем развернутый LDI . Но вам приходилось копировать копию между сигналами прерывания, чтобы избежать повреждения памяти. Также развернутый PUSH был самым быстрым способом для заполнения памяти с особым значением на ZX Spectrum (опять же с риском повреждения от прерывания, если он не был установлен правильно или выполнялся под DI ).



Modified text is an extract of the original Stack Overflow Documentation
Лицензировано согласно CC BY-SA 3.0
Не связан с Stack Overflow