Skip to content

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

Natasha Gurova edited this page Jun 23, 2022 · 5 revisions
Clone this wiki locally

Исторически есть два способа хранения строк

  1. Сишный – нулевой байт в конце
  2. Паскалевский – в первых двух байтах (или одном) хранится длина, а дальше идет непосредственно набор символов.

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


Как работают команды работы со строками в ассемблере

Это довольно составные команды. Они читают с адреса источника байт (или два байта или может быть четыре байта), увеличивают индексы SI или DI на единицу (или на два, или на 4). Далее, если команды связаны с записью, то они будут записывать прочитанные байты в приемник.

❗️ Несмотря на указание <п> и <и> в командах, на самом деле в коде они прописываться не будут

Строка источник - DS:SI, строка-приемник - ES:DI

MOVS / MOVSB / MOVSW <п> <и>             ; копирование
CMPS / CMPSB / CMPSW <п> <и>             ; сравнение
SCAS / SCASB / SCASW <и>                 ; сканирование (сравнение с AL / AX)
LODS / LODSB / LODSW <и>                 ; чтение (в AL / AX)
STOS / STOSB / STOSW <п>                 ; запись (из AL / AX)

За один раз обрабатывается один байт (слово).

После выполнения SI и DI увеличиваются на 1 (или 2 если W), если флаг DF = 0, или уменьшаются на 1 (или 2 если W), если DF = 1.


Объединение с циклами

Если мы хотим работать со строками, а не с одним символом, то используются префиксы (пишутся в одну строчку через пробел с командой):

REP               ; повторить следующую строковую операцию
REPE              ; повторить следующую строковую операцию, если равно
REPZ              ; повторить следующую строковую операцию, если нуль
REPNE             ; повторить следующую строковую операцию, если не равно
REPNZ             ; повторить следующую строковую операцию, если не нуль

При добавлении подобного префикса получится “цикл”, который будет выполняться столько раз, сколько выставлен CX (как в loop). Команды с Z кроме CX будут еще контролировать состояние флага ZF.