Работа с памятью: адресация выделенной области памяти - Assembler
Формулировка задачи:
Привет, ребят! Допустим я создал (выделил) какой-то участок памяти (функция 48h).. Вооот И мне очень хотелось бы его как-то адресовать (в моем понимании адресовать - значит обращаться к нужному мне участку выделенной памяти и, при необходимости его изменять). По сути это просто буфер, в который я бы хотел запихивать данные, но я никак не пойму, как к нему обратиться.. Пробовал
Подскажите, пожалуйста, как быть! А я пока попробую сам найти ответ)))
mov byte ptr [buffer], 20 ;хочу занести в первый байт двадцатку, но вместо этого просто изменяется значение переменной
;buffer....
;........
;........
buffer dw ?
end LPРешение задачи: «Работа с памятью: адресация выделенной области памяти»
textual
Листинг программы
.model tiny
.code
.startup
BufSizeParas = 4096 ; размер буфера в параграфах (по 16 байт)
StackSize = 256 ; размер стека (в байтах, должен быть кратен 16 байтам для корректных расчётов)
BufOfs = (TheEnd-@Startup+100h+StackSize+15) and 0FFF0h ; смещение буфера относительно cs, ds (с выравниванием по 16 байтам)
lea sp,StackStart
mov ax,ds:[2] ; сегмент после программы (последний выделенный программе сегмент + 1)
mov dx,cs ; сегмент кода
sub ax,dx ; кол-во параграфов, выделенных программе
cmp ax,BufOfs/16+BufSizeParas ; достаточно ли свободной памяти?
jb LowMemory
add dx,BufOfs/16 ; получение сегмента буфера
mov es,dx ; es = сегмент буфера
xor di,di
mov cx,BufSizeParas*8
xor ax,ax
rep stosw ; инициализируем буфер нулями
mov byte ptr es:[0],20 ; один вариант записи в буфер
mov es:Buffer,21 ; второй вариант записи в буфер
int 20h ; ret делать нельзя, т.к. в стеке у нас нет 0 (мы же изменили sp)
LowMemory:
mov ah,9
lea dx,mLowMemory
int 21h
int 20h ; ret делать нельзя, т.к. в стеке у нас нет 0 (мы же изменили sp)
mLowMemory db 'Too low memory :(',13,10,'$'
TheEnd: ; конец программы
org BufOfs
StackStart: ; начало стека (он растёт вниз, при записи первого слова значение будет записано по адресу -2 относительно текущего)
org 0 ; чтобы буфер начинался со смещения 0
Buffer label byte
end
Объяснение кода листинга программы
Список элементов кода:
- Установка размера буфера в параграфах и байтах.
- Вычисление смещения буфера относительно cs, ds.
- Выделение сегмента стека.
- Вычисление сегмента кода.
- Проверка доступности свободной памяти.
- Получение сегмента буфера.
- Инициализация буфера нулями.
- Запись в буфер.
- Обработка ситуации нехватки памяти.
- Вывод сообщения о нехватке памяти.
- Вычисление сегмента окончания программы.
- Вычисление начала стека.
- Установка начала буфера на 0.
- Создание метки для буфера.
- Конец программы.
- Организация стека.
- Вывод сообщения о нехватке памяти.
- Вычисление сегмента окончания программы.
- Вычисление начала буфера на 0.
- Создание метки для буфера.