Hacker #06
08 января 1997

 Кусочек ассемблера.                          .ПРОГРАММИРОВАНИЕ 
                                                                
    Как  Вы  уже  наверно  заметили,  этот раздел будет посвящен
ассемблеру  и  программированию в нем. И вести этот раздел, судя
по всему, буду я, то есть ANDY Inc. В разделе будут представлены
различные  проЦедурки:  гасилки,  скроллеры,  анализаторы и тому
подобные  прибамбасы,  которые были написаны мной или дернуты из
каких либо демок,  INTR0... По возможности я буду расписывать их
принЦипы  работы. Каждая проЦедура будет находиться в приложении
в виде файла TASM-4.XLD (самый удобный на мой взгляд ассемблер).
Но  учтите,  этот ассемблер расчитан на 128К, поэтому владельЦам
48К  можно  попробовать  проассемблировать  проЦедурки и если не
получится,  то  переписать  (или  перекодировать) текст в формат
какого-нибудь  48К ассемблера. А лучше купить 128К-машину, и как
можно  быстрее.  Итак,  как  я  уже  писал, все проЦедурки будут
находиться  в  файлах  TASM-4,  а  здесь я буду расписывать лишь
наиболее  хитрые части программ. Кстати, у меня дурная привычка:
перемешивать  системы счисления. Поэтому не пугайтесь, если один
адрес будет десятичный, а соседний - шестнадЦатеричный.         
                                                                
   Начнем-с.                                                    
                                                                
    Первая программа: LIN+А2                                    
                                                                
    Бегущая строка с довольно интересными свойствами. А точнее -
строку можно увеличивать по вертикали (или уменьшать) кнопками 8
(увеличивать)  и 9 (соответственно, уменьшать). Кроме того, если
у  Вас  подгружена  и  проигрывается  музыка на АУ, то клавишами
А,В,С  Вы  можете установить режим работы строки как анализатора
соответствующих  каналов.  Зеленый  Цвет  на бордюре показывает,
какую  часть  HALT-а занимает программа (читайте ZX Ревю за 199б
год).   Программа   использует  для  буфера  под  строку  память
#FFOO-#FFFF и под буфер вывода 25000-25128.                     
                                                                
    Теперь рассмотрим наиболее интересные участки программы.    
                                                                
1.    DI                 ;запрещаем прерывания                  
      LD    (DES+1),SP   ;сохраняем стек                        
      LD    SP,22528     ;устанавливаем стек на конеЦ экрана + 1
      LD    HL,0         ;в HL записываем 0                     
      DEFS  1024,#E5     ;1024 байта по #E5 (PUSH HL)           
DES   LD    SP,0         ;восстанавливаем стек                  
      EI                 ;разрешаем прерывания                  
                                                                
    Данная  часть  программы  очень  быстро (быстрее уже некуда)
очищает  нижнюю  треть  экрана. Для этого используется стек. Как
известно,  стек  растет  вниз: при комане PUSH HL (или DE,ВС...)
указатель  стека  уменьшается на 2. Мы же ставим указатель стека
на  адрес  начала  экранных  аттрибутов, т.е на конеЦ экрана + 1
байт,  записываем  в  HL  0  и делаем 1024 раза PUSH HL (команда
ассемблера  DEFS  Х,Y делает Х повторений числа Y). Тем самым мы
заносим  на  стек  2048 значений 0 с адреса #4800 по #57FF, т.е.
делаем  ни  что иное, как очистку экрана. Такой способ очистки -
самый  быстрый способ очистки непрерывних областей памяти. Но он
занимает много памяти (более 1КБ), поэтому можно воспользоваться
Циклом типа:                                                    
      LD    HL,0       ;мы делаем то же самое,                  
      LD    В,б4       ;но медленнее                            
LX1   DEFS  1б,#E5     ;и занимает это гораздо меньше памяти    
      DJNZ  LX1        ;                                        
                                                                
2.    LD    HL,25000   ;в HL - начало буфера под стек           
      LD    DE,#5000   ;в DE - адрес в экране (крайний левый)   
      LD    В,б4       ;в В - высота используемой области экрана
KLP1  LD    (HL),E     ;в (HL) младший байт адреса              
      INC   HL         ;HL=HL+1                                 
      LD    (HL),D     ;в (HL) старший байт адреса              
      INC   HL         ;HL=HL+1                                 
      CALL  INCD       ;расчет адреса следующей линии в экране  
      DJNZ  KLP1       ;Цикл на б4 линии                        
      RET                                                       
                                                                
INCD  INC   D       ;это уже многим знакомая проЦедура расчета  
      LD    А,D     ;следующего адреса в экране для DE.         
      AND   7       ;(принЦип действия я расписал в HACKER-5)   
      RET   NZ                                                  
      LD    А,E                                                 
      ADD   А,32                                                
      LD    E,А                                                 
      RET   С                                                   
      LD    А,Н                                                 
      SUB   8                                                   
      LD    Н,А                                                 
      RET                                                       
                                                                
    Данная  программка  вызывается  перед  работой  программы  и
создает   б   буфере   (заданной   области   памяти;   в  данной
программе:25000-25128) таблиЦу адресов левых краев экрана нижней
трети. Там получается что-то типа:                              
                                                                
    25000 - #00    25004 - #00     ...........                  
    25001 - #50    25005 - #52     ...........                  
    25002 - #00    ...........     2512б - #E0                  
    25003 - #51    ...........     25127 - #57                  
                                                                
    Т.е.   получается   таблиЦа   адресов.  Установливаем  адрес
указателя   стека  на  25000.  После  этого  делаем  POP  HL.  В
результате  получаем  адрес  линии в начале нижней трети экрана.
Делаем  еще  один  POP HL и теперь получаем в HL адрес следующей
линии  экрана.  Т.е. этот буфер создавался для того, чтобы можно
было очень быстро узнать адрес следующей линии в экране (гораздо
быстрее,  чем  проЦедурой  типа INCD). Такой способ используется
почти  во  всех музыкалках,для быстрого вывода летающих спрайтов
или   синусоидальных  строк.  Для  этого  он  и  используется  в
программе.                                                      
                                                                
     DI                                                         
     LD     (STK+1),SP     ;сохраняем стек                      
     LD     HL,#FFOO       ;адрес буфера бегущей строки         
     LD     SP,25000       ;стек на начало буфера               
     LD     В,8            ;Цикл на 8 линий (высота буквы)      
ХХХ1 POP    DE             ;берем со стека адрес в экрана       
     LD     С,#FF          ;в С всегда 255, чтобы не изменялся В
     LDI                   ;32 раза LDI (32 LDI занимает 512    
     LDI                   ;тактов проЦессора, а LDIR на 32 бай-
      ....   всего 32 раза ;та - более бб7! почувствуте разниЦу!
     DJNZ   ХХХ1           ;В=В-1, если В=0 то                  
STK  LD SP,0               ;восстанавливаем стек                
     EI                                                         
                                                                
    Эта  проЦедура  не  из  файла, там она немного сложнее, т.к.
приходится иногда повторять одну и ту же линию скролла несколько
раз. Если Вы даже немного разбираетесь в ассемблере и читали мои
статьи  в  HACKER-5,  то  в  тексте этой бегущей строки вы легко
найдете и головной блок, и расчет адреса символа, и сдвиг строки
в  буфере  (я лишь только раскрыл Цикл, чтобы программа работала
быстрее,  правда  ее  можно  еще немного убыстрить), и проЦедуру
анализатора.  Если  Вы  не  читали  те  статьи,  то  советую  их
прочитать. Полезно, для общего развития.                        
Метка SETT - вызывается проЦедура, считывает громкость с задан- 
ного канала АУ и записывает ее в метку C0PY+1. NEXXAX - вывод   
строки на экран. LINE - головной блок бегущей строки.           
                                                                
   Вторая программа: WATERSCR                                   
                                                                
    Эта  проЦедура  тоже  является бегущей строкой, но бежит она
уже  вверх.  Кроме  того,  при  скроллировании  вверх происходит
попиксельный  сдвиг строк то влево, то вправо: получается эффект
воды.  Данная  программа  занимает времени немного более HALT-а,
т.к.  при  убыстрении  она  бежит  гораздо  быстрее  и читать ее
довольно  сложно. Музыку в строку можно вставить, подвесив ее на
IM 2.                                                           
  Перед началом работы программа создает таблиЦу адресов экрана,
уже знакомую Вам по предыдущей программе.                       
  ПроЦедура скроллирования SCR0LL:                              
                                                                
      LD    SP,2б25б   ;стек на начало таблиЦы адресов экрана   
      LD    А,б3       ;сдвигаем вверх б3 экранных строки:      
SC1   POP   DE         ;в DE - адрес линии в экране             
      POP   HL         ;в HL - адрес следующей линии            
      PUSH  HL         ;сохраняем HL для следующего Цикла       
      LDI - 32 раза    ;копируем нижнюю строку на верхнюю       
      DEC   А          ;                                        
      JP    NZ,SC1     ;                                        
                                                                
 ПроЦедура сдвигов SUPPL:                                       
                                                                
      .............                                             
      LD    SP,2525б ;                                          
      LD    В,1б     ;Цикл на 1б*4 (=б4) строк                  
SUP1  POP   HL       ;пропускаем строку                         
      POP   HL       ;в HL адрес начала линии в экране          
      LD    С,32     ;                                          
      AND   А        ;сдвигаем ее вправо                        
АА1   RR    (HL)     ;                                          
      INC   L        ;                                          
      DEC   С        ;                                          
      JP    NZ,АА1   ;                                          
      POP   HL       ;пропускаем линию                          
      POP   HL       ;                                          
      LD    А,L      ;устанавливаем в HL адрес последнего байта 
      0R    31       ;линии в экране                            
      LD    L,А      ;                                          
      LD    С,32     ;                                          
      AND   А        ;                                          
АА2   RL    (HL)     ;сдвигаем линию влево                      
      DEC   L        ;                                          
      DEC   С        ;                                          
      JP    NZ,АА2   ;                                          
      DJNZ  SUP1     ;                                          
      ..........                                                
                                                                
    Конечно, программу можно значительно ускорить, раскрыв Циклы
АА1 и АА2, но это не приведет к хорошим результатам. Если убрать
строки, помеченные ";", то строка будет еще более "водянистая". 
                                                                
    Номер 3: IM2TEST                                            
                                                                
    Эта программа демонстрирует возможности режима IM 2. Она    
подгружает в память блок, содержащий 9 музонов (TEST.С). После  
того, как Вы проассемблируете программу, выходите в BASIC и     
набирайте RAND0MIZE USR б5000. Сразу заиграет музон. Переклю-   
чить музыку можно нажатием одновременно клавишь: SYMB0L SHIFT+  
ENTER+ кнопка от 1 до 9. IM 2 работает и в TR DOS, но правда му-
зыка притормаживает, когда идет обращение к диску (прерывания   
запрещаются). А в BASIC-е можно работать почти без проблем.     
Единственной проблемой является количество свободной памяти:    
где-то до 30000. Но это уже детали...                           
                                                                
    Программа 4: SETMUL2                                        
                                                                
    Ну а это просто маленький глюк. Точнее бордюрный глюк. Когда
Вы  запустите  эту  программку,  то на экране и бордюре появятся
полосы,  которые, если у Вас PROFI+, должны совпадать полностью.
Но этого может и не быть, т.к. программа настроена под мой C0MP,
а  на  разных  компьютерах количество тактов в HALT-е может быть
различным.  Кнопками  "Q"  и  "А"  можно  попытаться  подстроить
полосы.  Это  может  не  получится,  т.к. данная программа имеет
точность  подстройки  4  такта. Ну а в Целом эту программу можно
считать  примерчиком, показывающим, как можно подстроить эффекты
на бордюре под компьютер.                                       
                                                                
       Кроме  проЦедур  в  TASM-е,  в приложении есть маленькая,
очень хитрая программа: WIYЗ. Она может показать на одном экране
два  черно-белых  без потерь пикселов. Программа работает только
на 128К-машинах, т.к. для работы она использует два экрана: 48-й
и  128-й.  На  48К ее написать будет весьма проблематично: нужен
жутко  быстрый,  занимающий  менее  HALT-а, алгоритм копирования
блоков памяти по б144 байт. А такого я еще не видел...          
                                                                
полосы.  Это  может  не  получится,  т.к. данная программа имеет
точность  подстройки  4  такта. Ну а в Целом эту программу можно
считать  примерчиком, показывающим, как можно подстроить эффекты
на бордюре под компьютер.                                       
                                                                
       Кроме  проЦедур  в  TASM-е,  в приложении есть маленькая,
очень хитрая программа: WIYЗ. Она может показать на одном экране
два  черно-белых  без потерь пикселов. Программа работает только
на 128К-машинах, т.к. для работы она использует два экрана: 48-й
и  128-й.  На  48К ее написать будет весьма проблематично: нужен
жутко  быстрый,  занимающий  менее  HALT-а, алгоритм копирования
блоков памяти по б144 байт. А такого я еще не видел...          
                                                                
    На  этом я закончу раздел и напишу, что я буду рассматривать
в  следующем  номере:  это  будут различные эффекты из различных
INTR0  (RST  7,  M0RTAL  COMBAT  .....).  Также в 7 номере будут
тексты  в  TASM-е  INTR0  к  HACKER-ам  5 и б с соответствующими
файлами.                                                        
   На этом я прощаюсь до следующего номера.                     
   Пока!                                                        
                                                     ANDY Inc.  
                                                                



Other articles:


Темы: Игры, Программное обеспечение, Пресса, Аппаратное обеспечение, Сеть, Демосцена, Люди, Программирование

Similar articles:
Entry - the contents of rooms.
Iron - CONTROLLER IBM-compatible keyboard and mouse for each computer type ZX-SPECTRUM (How to work and connect V 2.0).

В этот день...   28 April