О макросе бедном замолвите слово-2
или
Макрос возвращается.
В этой статье мы продолжим знакомство с
представителями замечательного семейства
макросов :) Вы узнаете, как с их помощью
ещё больше облегчить себе жизнь при прог-
раммировании.Как всегда,примеры разработа-
ны применительно к ALASM. Для ALASM версии
4.46 и выше параметры макросов обозначают-
ся префиксом '' вместо двоеточия.
Вам,наверное уже известны способы полу-
чать адреса,выравненные по какой-то грани-
це. Вот один из вариантов:
ORG '($-1)+1<8
Это выравнивание по границе 256 байт.
Можно определить более общий случай:
MACRO ALIGN
ORG +$-1&(-( ))
ENDM
[Желательно вместо ORG использовать DS,
чтобы не допустить заполнения памяти неиз-
вестно чем,каковое неизвестно что пакуется
обычно хуже,чем нули. Сделайте макрос с DS
- это вам домашнее задание.]
- это параметр макроса. В данном
случае параметр имеет значение границы вы-
равнивания. [В скобки он заключен потому,
что параметром может оказаться выражение.
При вызове макросов параметры передаются в
том виде,как они стоят в строке вызова.Ес-
ли макрос вызывает макрос, то параметры
внешнего макроса раскрываются.] Очевидно,
что если в программе много подобных вырав-
ниваний, то возникают довольно большие по-
тери памяти. Но у нас есть макросы,значит,
мы можем попытаться проконтролировать эти
потери и затем попытаться их минимизиро-
вать. Модифицируем наш макрос:
MACRO ALIGN
LOCAL
OLDADR=$
ORG +$-1&(-( ))
IFN $-OLDADR
DISPLAY "Memory leak before ",/H,$
DISPLAY "Leak size=",$-OLDADR
ENDIF
ENDL
ENDM
Теперь при компиляции мы будем получать
сообщения типа:
Memory leak before #a700
Leak size=253
Если мы соптимизируем код до адреса
#a603 на 3 байта, то получим выигрыш в 256
байт!
К сожалению, данный макрос не работает
при компиляции в верхней памяти - без ука-
зания страницы ORG по умолчанию компилиру-
ет в нулевую. [Текст писался давно, и для
ALASM 4.46 это замечание уже не справедли-
во.]
Иногда бывает,что на одном диске храни-
тся несколько проектов. И часть файлов ис-
ходников принадлежит нескольким проектам,
причём зависимости могут быть самыми запу-
танными.Иногда возникают случаи,когда один
и тот же файл бывает включён несколько
раз. Чтобы избежать этого и раз и навсегда
обезопасить себя от дальнейшей головной
боли, оформляем файлы следующим образом:
IFN ?_UNIQUE_NAME_ ;в самом начале файла
_UNIQUE_NAME_=0
...
ENDIF ;в самом конце файла
Как вы уже догадались, _UNIQUE_NAME_
должно быть для каждого файла уникальным.
Работает всё это очень просто.Если включа-
емый файл не обнаруживает в пространстве
меток свой идентификатор, он его объявляет
и со спокойной совестью компилируется.Ина-
че он просто пропускается.
Обычно программа существует в двух вер-
сиях - отладочной и итоговой. Отладочная
версия,как вы уже поняли,существует только
у программиста,который её и делает. Итого-
вая версия - это то,что попадает к пользо-
вателю. Между двумя этими версиями может
быть довольно большая разница. Начиная от
выхода (в отладочной версии это возврат в
ассемблер,а в итоговой или выход в дос или
игнорирование) и заканчивая заменой целых
кусков кода. Как это реализовать удобно,
чтобы не забыть в предрелизной суматохе
заменить нужные строчки. Очень просто. В
критических местах программы расставляем
строки:
IFN ?_DEBUG_ ;0=метка уже = чему-то
;1=не присвоена и used
;-1=вообще нет метки
... ;release version
ELSE
... ;debug version
ENDIF
А в самом начале программы пишем строч-
ку:
_DEBUG_
При релизе ее просто нужно будет заком-
ментировать. "Реакция" исходника на версию
может быть самой разной.Это может быть на-
поминание о проверке версии программы, вы-
вод диагностических сообщений и т.д.
ALASM с версии 4.46 поддерживает неза-
крытие скобок условной компиляции в макро-
сах, поэтому вышеприведенные примеры можно
слегка модифицировать, создав макросы:
MACRO IFDEF
IF ?
ENDM
MACRO IFNDEF
IFN ?
ENDM
Как их применять, думаю, вы уже догада-
лись :)
Работа с множествами.
Иногда возникают задачи хранения мно-
жеств дискретных данных, например, набор
гласных или согласных букв.Вывести законо-
мерность довольно трудно,поэтому приходит-
ся прописывать данные. Обычно задается та-
блица, и поиск по ней происходит с помощью
команды CPIR или подобным образом. Но тра-
тить 1 байт на обозначение факта присутст-
вия элемента довольно накладно, ведь можно
на это дело потратить 1 бит. Ниже приведён
текст макроса, позволяющего автоматизиро-
вать работу с такими множествами.
При задании множества макросу передают-
ся параметры:
- адрес битовой карты (определяется ди-
намически);
- минимальные и максимальные значения;
- начальное множество.
Сначала файл примера:
INCLUDE "MAKESET",199
ORG 24576
;пустое множество
MAKESET SET1,"A","B",""
;множество из двух букв
MAKESET SET2,"B","Z","CD"
ORG 24576 ;обязательно!!!
И текст самого макроса:
MACRO MAKESET
;MAKESET NAMESET,MIN,MAX,....
DS 2-1+8&#FFF8>3
IF ?BITOPER+1
BITOPER RRA
RR L
RRA
RR L
RRA
RR L
RRA
RRA
BITOPA OR #46
LD (BITOP+1),A
BITOP DB #CB,0 ;$+1
RET
ENDIF
_MIN =1
_MAX =2
ADD LD L,A
LD A,#C6
JR OP
DEL LD L,A
LD A,86
JR OP
ISIN LD L,A
LD A,#46