home *** CD-ROM | disk | FTP | other *** search
/ The CDPD Public Domain Collection for CDTV 4 / CDPD_IV.bin / amfm / amfm11 / techcorner / example.a.pp / example.a
Text File  |  1994-06-20  |  8KB  |  363 lines

  1. ;Audio hardware offsets
  2. ac_ptr    EQU    $00
  3. ac_len    EQU    $04
  4. ac_per    EQU    $06
  5. ac_vol    EQU    $08
  6. ac_end    EQU    $0C
  7.  
  8.         SECTION    "text",CODE
  9.  
  10.         XREF    _period1,_period2,_slen,_sample
  11.         XDEF    _play,_endplay
  12.  
  13. ;**************************************************************************
  14. ;*
  15. ;*        8 CHANNEL PLAY ROUTINE
  16. ;*
  17. ;**************************************************************************
  18.  
  19. ; This code does the magic 8 channel thing (mixing).
  20. MAGIC_8TRK    MACRO
  21.         swap    d6
  22.         swap    d7
  23.         move.b    0(a3,d6.w),d0
  24.         add.b    0(a4,d7.w),d0
  25.         move.b    d0,(a1)+
  26.         swap    d6
  27.         swap    d7
  28.         add.l    d1,d6
  29.         add.l    d2,d7
  30.         ENDM
  31.  
  32. _IntHandler8:    movem.l    d2/d5-d7/a2-a5,-(sp)
  33.         lea    DB,a6
  34. ; ================ 8 channel handling (buffer swap) ======
  35.         not.b    whichbuff-DB(a6)    ;swap buffer
  36.         bne.s    usebuff1
  37.         move.l    a1,$a0(a0)
  38.         move.w    #100,$a4(a0)
  39.         bra.s    buffset
  40. usebuff1    lea    200(a1),a1
  41.         move.l    a1,$a0(a0)
  42.         move.w    #100,$a4(a0)
  43. buffset        move.w    #1<<7,$9c(a0)
  44.         move.w    #64,$a8(a0)
  45. ; ============== fill buffers ============
  46. startfillb    lea    track0hw-DB(a6),a2
  47. ;calculate channel A period
  48.         move.l    #3719168,d7    ;227 * 16384
  49.         move.w    ac_per(a2),d6
  50.         beq.s    setpzero0
  51.         move.l    d7,d2
  52.         divu     d6,d2
  53.         moveq    #0,d1
  54.         move.w    d2,d1
  55.         add.l    d1,d1
  56.         add.l    d1,d1
  57. ;get channel A addresses
  58.         move.l    ac_end(a2),a5
  59.         move.l    (a2),d0
  60.         beq.s    setpzero0
  61. chA_dfnd    move.l    d0,a3    ;a3 = start address, a5 = end address
  62. ;calc bytes before end
  63.         mulu    #200<<3,d2
  64.         clr.w    d2
  65.         swap    d2
  66. ; d2 = # of bytes/fill
  67.         add.l    a3,d2    ;d2 = end position after this fill
  68.         sub.l    a5,d2    ;subtract sample end
  69.         bmi.s    norestart0
  70.         clr.l    (a2)
  71. setpzero0    lea    zerodata-DB(a6),a3
  72.         moveq    #0,d1
  73. norestart0
  74. ;channel B period
  75.         move.w    SIZE4TRKHW+ac_per(a2),d6
  76.         beq.s    setpzero0b
  77.         divu    d6,d7
  78.         moveq    #0,d2
  79.         move.w    d7,d2
  80.         add.l    d2,d2
  81.         add.l    d2,d2
  82. ;channel B addresses
  83.         move.l    SIZE4TRKHW+ac_end(a2),a5
  84.         move.l    SIZE4TRKHW(a2),d0
  85.         beq.s    setpzero0b
  86.         move.l    d0,a4
  87.         mulu    #200<<3,d7
  88.         clr.w    d7
  89.         swap    d7
  90.         add.l    a4,d7
  91.         sub.l    a5,d7
  92.         bmi.s    norestart0b
  93.         clr.l    SIZE4TRKHW(a2)
  94. setpzero0b    lea    zerodata-DB(a6),a4
  95.         moveq    #0,d2
  96. norestart0b    moveq    #0,d6
  97.         moveq    #0,d7
  98.         moveq    #9,d5
  99. do8trkmagic
  100.         MAGIC_8TRK    ;20 times..
  101.         MAGIC_8TRK
  102.         MAGIC_8TRK
  103.         MAGIC_8TRK
  104.         MAGIC_8TRK
  105.         MAGIC_8TRK
  106.         MAGIC_8TRK
  107.         MAGIC_8TRK
  108.         MAGIC_8TRK
  109.         MAGIC_8TRK
  110.         MAGIC_8TRK
  111.         MAGIC_8TRK
  112.         MAGIC_8TRK
  113.         MAGIC_8TRK
  114.         MAGIC_8TRK
  115.         MAGIC_8TRK
  116.         MAGIC_8TRK
  117.         MAGIC_8TRK
  118.         MAGIC_8TRK
  119.         MAGIC_8TRK
  120.  
  121.         dbf    d5,do8trkmagic    ;do until cnt zero
  122. end8trkmagic    clr.w    d6
  123.         clr.w    d7
  124.         swap    d6
  125.         swap    d7
  126.         add.l    d6,(a2)
  127.         add.l    d7,SIZE4TRKHW(a2)
  128.         movem.l    (sp)+,d2/d5-d7/a2-a5
  129.         rts
  130.  
  131. playsound    ;plays the notes (normally this would happen within the
  132.         ;            interrupt)
  133.         lea    track0hw,a0    ;pointer to "pseudo"-hardware
  134.         move.w    _period1,ac_per(a0)
  135.         move.l    _sample,d0
  136.         move.l    d0,ac_ptr(a0)
  137.         add.l    _slen,d0
  138.         move.l    d0,ac_end(a0)
  139.         ; and the other channel
  140.         lea    track4hw,a0
  141.         move.w    _period2,ac_per(a0)
  142.         move.l    _sample+4,d0
  143.         move.l    d0,ac_ptr(a0)
  144.         add.l    _slen+4,d0
  145.         move.l    d0,ac_end(a0)
  146.         rts
  147.  
  148. _play:        bsr.w    _InitPlayer8
  149.         tst.l    d0
  150.         bne.s    x_play
  151.         bsr.s    playsound
  152.         bsr.s    _Start8Play
  153. x_play:        rts
  154.  
  155. _endplay    bra.w    _RemPlayer8
  156.  
  157.  
  158. _Wait1line:    move.l    d0,-(sp)
  159.         moveq    #$79,d0
  160. wl0:        move.b    $dff007,d1
  161. wl1:        cmp.b    $dff007,d1
  162.         beq.s    wl1
  163.         dbf    d0,wl0
  164.         move.l    (sp)+,d0
  165.         rts
  166.  
  167. _Start8Play:    ;d0 = pstate
  168.         lea    _audiobuff,a0
  169.         move.w    #200-1,d1
  170. clrbuffloop:    clr.w    (a0)+        ;clear track buffers
  171.         dbf    d1,clrbuffloop
  172.         lea    $dff000,a0
  173.         move.w    #100,$a4(a0)    ;set audio buffer sizes (100 words)
  174.         move.w    #227,$a6(a0)
  175.         move.l    #_audiobuff,$a0(a0)
  176.         move.w    #64,$a8(a0)
  177.         clr.b    whichbuff-DB(a6)
  178.         movea.l    4,a1
  179.         move.w    #$4000,$9a(a0)
  180.         addq.b    #1,$126(a1)
  181.         lea    track0hw-DB(a6),a1
  182.         clr.l    (a1)
  183.         clr.w    ac_per(a1)
  184.         move.w    #$0001,$dff096    ;audio DMA off
  185.         bsr.w    _Wait1line    ;wait until all stopped
  186.         st    play8-DB(a6)
  187.         move.w    #$8080,$9a(a0)
  188.         move.w    #$8001,$96(a0)    ;DMA audio channel 1 ON
  189.         movea.l    4,a1
  190.         subq.b    #1,$126(a1)
  191.         bge.s    x8play
  192.         move.w    #$c000,$9a(a0)
  193. x8play        rts
  194.  
  195. _End8Play:    tst.b    play8
  196.         beq.s    noend8play
  197.         move.w    #1<<7,$dff09a
  198.         move.w    #$F,$dff096
  199.         clr.b    play8
  200. noend8play    rts
  201.  
  202. _Rem8chan:    move.l    a6,-(sp)
  203.         lea    DB,a6
  204.         move.b    eightrkon-DB(a6),d0
  205.         beq.s    no8init
  206.         clr.b    eightrkon-DB(a6)
  207.         move.w    #1<<7,$dff09a
  208.         moveq    #7,d0
  209.         move.l    prevaud-DB(a6),d0
  210.         beq.s    no8init
  211.         move.l    d0,a1
  212.         move.l    4,a6
  213.         jsr    -$a2(a6)
  214. no8init        move.l    (sp)+,a6
  215.         rts
  216.  
  217. ; *************************************************************************
  218. ; InitPlayer8() -- allocate interrupt, audio, serial port etc...
  219. ; *************************************************************************
  220. _InitPlayer8:    bsr.s    _AudioInit
  221.         tst.l    d0
  222.         bne.s    IP_error
  223.         rts
  224. IP_error    bsr.s    _RemPlayer8
  225.         moveq    #-1,d0
  226.         rts
  227.  
  228. ; *************************************************************************
  229. ; RemPlayer8() -- free interrupt, audio, serial port etc..
  230. ; *************************************************************************
  231. _RemPlayer8:    bsr    _End8Play
  232. ;        vvvvvvvvvvvvvvvv  to _AudioRem
  233. ; *************************************************************************
  234. _AudioRem:    movem.l    a5-a6,-(sp)
  235.         lea    DB,a5
  236.         bsr.w    _Rem8chan
  237.         movea.l    4,a6
  238.         tst.b    audiodevopen-DB(a5)
  239.         beq.s    rem2
  240.         clr.b    audiodevopen-DB(a5)
  241.         move.w    #$000f,$dff096    ;stop audio DMA
  242. ;    +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+ close audio.device
  243.         lea    allocreq-DB(a5),a1
  244.         jsr    -$1c2(a6)    ;CloseDevice()
  245. rem2:        moveq    #0,d0
  246.         move.b    sigbitnum-DB(a5),d0
  247.         bmi.s    rem3
  248. ;    +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+ free signal bit
  249.         jsr    -$150(a6)    ;FreeSignal()
  250.         st    sigbitnum-DB(a5)
  251. rem3:        movem.l    (sp)+,a5-a6
  252.         rts
  253.  
  254. _AudioInit:    movem.l    a4/a6/d2-d3,-(sp)
  255.         lea    DB,a4
  256.         movea.l    4,a6
  257.         moveq    #0,d2
  258. ;    +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+ alloc signal bit
  259.         moveq    #1,d2
  260.         moveq    #-1,d0
  261.         jsr    -$14a(a6)    ;AllocSignal()
  262.         tst.b    d0
  263.         bmi.w    initerr
  264.         move.b    d0,sigbitnum-DB(a4)
  265. ;    +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+ prepare IORequest
  266.         lea    allocport-DB(a4),a1
  267.         move.b    d0,15(a1)    ;set mp_SigBit
  268.         move.l    a1,-(sp)
  269.         suba.l    a1,a1
  270.         jsr    -$126(a6)    ;FindTask(0)
  271.         move.l    (sp)+,a1
  272.         move.l    d0,16(a1)    ;set mp_SigTask
  273.         lea    reqlist-DB(a4),a0
  274.         move.l    a0,(a0)        ;NEWLIST begins...
  275.         addq.l    #4,(a0)
  276.         clr.l    4(a0)
  277.         move.l    a0,8(a0)    ;NEWLIST ends...
  278. ;    +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+ open audio.device
  279.         moveq    #2,d2
  280.         lea    allocreq-DB(a4),a1
  281.         lea    audiodevname-DB(a4),a0
  282.         moveq    #0,d0
  283.         moveq    #0,d1
  284.         jsr    -$1bc(a6)    ;OpenDevice()
  285.         tst.b    d0
  286.         bne.w    initerr
  287.         st.b    audiodevopen-DB(a4)
  288.         move.w    #1<<7,$dff09a    ;Init 8 channel stuff
  289.         moveq    #7,d0        ;Audio channel 0 interrupt
  290.         lea    audiointerrupt-DB(a4),a1
  291.         jsr    -$a2(a6)    ;SetIntVector()
  292.         move.l    d0,prevaud-DB(a4)
  293.         st    eightrkon-DB(a4)
  294.         moveq    #0,d0
  295. initret:    movem.l    (sp)+,a4/a6/d2-d3
  296.         rts
  297. initerr:    move.l    d2,d0
  298.         bra.s    initret
  299.  
  300.         DATA
  301. DB:        ;Data base pointer
  302. sigbitnum    dc.b    -1
  303. audiodevopen    dc.b    0
  304. allocm        dc.b    $F,0
  305. allocport    dc.l    0,0    ;succ, pred
  306.         dc.b    4,0    ;NT_MSGPORT
  307.         dc.l    0    ;name
  308.         dc.b    0,0    ;flags = PA_SIGNAL
  309.         dc.l    0    ;task
  310. reqlist        dc.l    0,0,0    ;list head, tail and tailpred
  311.         dc.b    5,0
  312. allocreq    dc.l    0,0
  313.         dc.b    0,127    ;NT_UNKNOWN, use maximum priority (127)
  314.         dc.l    0,allocport    ;name, replyport
  315.         dc.w    68        ;length
  316.         dc.l    0    ;io_Device
  317.         dc.l    0    ;io_Unit
  318.         dc.w    0    ;io_Command
  319.         dc.b    0,0    ;io_Flags, io_Error
  320.         dc.w    0    ;ioa_AllocKey
  321.         dc.l    allocm    ;ioa_Data
  322.         dc.l    1    ;ioa_Length
  323.         dc.w    0,0,0    ;ioa_Period, Volume, Cycles
  324.         dc.w    0,0,0,0,0,0,0,0,0,0    ;ioa_WriteMsg
  325. audiodevname    dc.b    'audio.device',0
  326.         even
  327.  
  328. zerodata    dc.w    0
  329. whichbuff    dc.w    0
  330.  
  331. track0hw    dc.l    0,0,tmpvol,0
  332. track4hw    dc.l    0,0,tmpvol,0
  333. SIZE4TRKHW    equ    16
  334.  
  335. tmpvol        dc.b    0,0,0,0
  336.  
  337. audintname    dc.b    'AM/FM AudioInterrupt example',0
  338.         even
  339. audiointerrupt    dc.w    0,0,0,0,0
  340.         dc.l    audintname,_audiobuff,_IntHandler8
  341. prevaud        dc.l    0
  342. play8        dc.b    0
  343. eightrkon    dc.b    0
  344.         
  345.         EVEN
  346.  
  347. per0    dc.w    856,808,762,720,678,640,604,570,538,508,480,453
  348.     dc.w    428,404,381,360,339,320,302,285,269,254,240,226
  349.     dc.w    214,202,190,180,170,160,151,143,135,127,120,113
  350.     dc.w    214,202,190,180,170,160,151,143,135,127,120,113
  351.     dc.w    214,202,190,180,170,160,151,143,135,127,120,113
  352.     dc.w    214,202,190,180,170,160,151,143,135,127,120,113
  353.  
  354.     IFND    __G2
  355.         section "datachip",bss,chip ;for A68k
  356.     ENDC
  357.     IFD    __G2
  358.         section "datachip",bss_c ;this is for Devpac 2
  359.     ENDC
  360.  
  361. _audiobuff:    ds.w    100*2        ;two 200-byte buffers
  362.         END
  363.