Возможно через регистры контроллера CRT (03D4h – 03D5H).
Правда я писал на паскале со вставками из АСМА. Программа плавно сдвигает экран на одну строку в текстовом режиме:
PUSH BP { Начало процедуры, записываем в стек регистр указателя базы кадра стека }
MOV BP,SP { кладем в регистр указателя базы кадра стека регистр указателя стека, Начало процедуры}
XOR AX,AX { Обнуляем регистр AX (так быстрей чем присваивать 0)}
MOV CX,000Fh { Кладем в счетчик 16 (пикселей в строке)}
@@3: MOV DX,03DAh { Кладем в регистр данных индекс порта состояния для адаптера}
@@1: IN AL,DX { Получаем из порта адаптера данные }
TEST AL,08h { Проверяем что это начало хода обратного луча }
JNZ @@1 { Ждем конца текущего обратного хода луча }
@@2: IN AL,DX { Получаем из порта адаптера данные }
TEST AL,08h { Проверяем что это начало хода обратного луча }
JZ @@2 { А теперь ждем начала следующего обратного хода луча }
MOV DX,03D4h { Кладем в регистр данных индекс контроллера CRT}
MOV AL,08h { Кладем в регистр признак предварительная горизонтальная развертка}
OUT DX,AL { отсылаем в регистр контроллера CRT }
INC DX { Переключаемся на следующий порт CRT }
MOV AL,10h { Записываем в AL 17 }
SUB AL,CL { Вычитаем из AL счетчик CL и кладем в AL }
OUT DX,AL { Отправляем значение в порт CRT 03D5h }
LOOP @@3 { Вычитаем из CX единицу и повторяем цикл 16 раз }
MOV DX,03DAh { Кладем в регистр данных индекс порта состояния для адаптера}
@@4: IN AL,DX { Получаем из порта адаптера данные }
TEST AL,08h { Проверяем что это начало хода обратного луча }
JNZ @@4 { Ждем конца текущего обратного хода луча }
@@5: IN AL,DX { Получаем из порта адаптера данные }
TEST AL,08h { Проверяем что это начало хода обратного луча }
JZ @@5 { А теперь ждем начала следующего обратного хода луча }
MOV DX,03D4h { Кладем в регистр данных индекс контроллера CRT}
MOV AL,08h { Кладем в регистр признак предварительная горизонтальная развертка}
OUT DX,AL { отсылаем в регистр контроллера CRT }
INC DX { Переключаемся на следующий порт CRT }
MOV AL,00h { Записываем в AL 0 }
OUT DX,AL { Отправляем значение в порт CRT 03D5h }
PUSH DS { Кладем в стек DS }
MOV AX,0B800h { Приравниваем AX адрес видеобуфера ДОС }
MOV ES,AX { Кладем в ES }
MOV DS,AX { Кладем его же в DS }
MOV SI,00A0h { Кладем в индекс источника 160 }
MOV DI,0000h { Кладем в адрес приемика 0 }
MOV CX,1040h { Кладем в счетчик 4160 }
REPE
MOVSB { Пересылаем из SI в DI 26 текстовых строк}
POP DS { Достаем DS из стека}
POP BP { Окончание процедуры, достаем из стека регистр указателя базы кадра стека }